web-dev-qa-db-ja.com

ホスト名、ポートなどを取得するためにJDBC URLを解析する方法は?

JDBC URL(Oracleまたはsqlserver)を解析して、ホスト名、ポート、およびデータベース名を取得するにはどうすればよいですか。 URLの形式は異なります。

31
Mickel Lee

次のようなものから始めます。

 String url = "jdbc:derby:// localhost:1527/netld; collat​​ion = TERRITORY_BASED:PRIMARY"; 
 String cleanURI = url.substring(5); 
 
 URI uri = URI.create(cleanURI); 
 System.out.println(uri.getScheme()); 
 System.out.println(uri.getHost()); 
 System.out.println(uri.getPort()); 
 System.out.println(uri.getPath()); 

上記の出力:

 derby 
 localhost 
 1527 
/netld; collat​​ion = TERRITORY_BASED:PRIMARY 
49
brettw

それは私にはうまくいきませんでした。ホスト名とポートは常にコロンで結合されているという仮定に基づいて、これらの方法を思いつきました。この仮定は、私が仕事で扱う必要があるすべてのデータベース(Oracle、Vertica、MySQLなど)に当てはまります。しかし、ネットワークポートに到達しないものに対してはおそらく機能しません。

String url = null; // set elsewhere in the class
final public String regexForHostAndPort = "[.\\w]+:\\d+";
final public Pattern hostAndPortPattern = Pattern.compile(regexForHostAndPort);
public String getHostFromUrl() {
    Matcher matcher = hostAndPortPattern.matcher(url); 
    matcher.find();
    int start = matcher.start();
    int end = matcher.end();
    if(start >= 0 && end >= 0) {
        String hostAndPort = url.substring(start, end);
        String [] array = hostAndPort.split(":");
        if(array.length >= 2)
            return array[0];
    }
    throw new IllegalArgumentException("couldn't find pattern '" + regexForHostAndPort + "' in '" + url + "'");
}

public int getPortFromUrl() {
    Matcher matcher = hostAndPortPattern.matcher(url); 
    matcher.find();
    int start = matcher.start();
    int end = matcher.end();
    if(start >= 0 && end >= 0) {
        String hostAndPort = url.substring(start, end);
        String [] array = hostAndPort.split(":");
        if(array.length >= 2)
            return Integer.parseInt(array[1]);
    }
    throw new IllegalArgumentException("couldn't find pattern '" + regexForHostAndPort + "' in '" + url + "'");
}
6
timbaileyjones

@brettwの回答が一部の有効なJDBC URLで失敗する可能性があることに注意してください。ホスト名にアンダースコアuriが含まれている場合、getHost()はnullを返し( こちら を参照)、getPost()は-1を返します。

これを回避するために、nullホストのチェックを追加しました。

  String jdbcUrl = "jdbc:jtds:sqlserver://ABC_XYZ:1433/Database";
  String cleanURI = jdbcUrl.substring("jdbc:jtds:".length());

  URI uri = URI.create(cleanURI);
  String Host = uri.getHost();
  int port = uri.getPort();

  if(Host == null){
    String regex = ".*://(\\w*):(\\d++)/.*";
    Pattern p = Pattern.compile(regex);

    Matcher matcher = p.matcher(jdbcUrl);
    if(matcher.find()){
      Host =  matcher.group(1);
      port =  Integer.valueOf(matcher.group(2));
    } else {
      // handle fail
    }
  }

  System.out.println("Host = " + Host);
  System.out.println("port = " + port);
1
JPC

私は自分のプロジェクトでこのクラスを使用しています。使い方は本当に簡単です。

/**
 * Split di una url JDBC nei componenti.
 * Estrae i componenti di una uri JDBC del tipo: <br>
 * String url = "jdbc:derby://localhost:1527/netld;collation=TERRITORY_BASED:PRIMARY"; <br>
 * nelle rispettive variabili pubbliche.
 * @author Nicola De Nisco
 */
public class JdbcUrlSplitter
{
  public String driverName, Host, port, database, params;

  public JdbcUrlSplitter(String jdbcUrl)
  {
    int pos, pos1, pos2;
    String connUri;

    if(jdbcUrl == null || !jdbcUrl.startsWith("jdbc:")
       || (pos1 = jdbcUrl.indexOf(':', 5)) == -1)
      throw new IllegalArgumentException("Invalid JDBC url.");

    driverName = jdbcUrl.substring(5, pos1);
    if((pos2 = jdbcUrl.indexOf(';', pos1)) == -1)
    {
      connUri = jdbcUrl.substring(pos1 + 1);
    }
    else
    {
      connUri = jdbcUrl.substring(pos1 + 1, pos2);
      params = jdbcUrl.substring(pos2 + 1);
    }

    if(connUri.startsWith("//"))
    {
      if((pos = connUri.indexOf('/', 2)) != -1)
      {
        Host = connUri.substring(2, pos);
        database = connUri.substring(pos + 1);

        if((pos = Host.indexOf(':')) != -1)
        {
          port = Host.substring(pos + 1);
          Host = Host.substring(0, pos);
        }
      }
    }
    else
    {
      database = connUri;
    }
  }
}
1
Nicola De Nisco