JavaScript でルートドメイン(root domain)を取得する

はじめに

URLからルートドメインを取得する処理について考えます。

結果から言えば、正確な結果が必要ならば、素直にライブラリを使いましょう。

ルートドメインとは

ここで言う「ルートドメイン」とは、サブドメイン名やホスト名を含まない一般的に個人や組織が取得できるドメイン名のことを指します。

例として、「www.example.co.jp」であれば、「example.co.jp」のことを指します。

※「独自ドメイン名」「カスタムドメイン名」「ドメイン名」と呼ばれることもあります。
 「ルートドメイン」は、ドメイン名の一番右側のドットです。一般的に省略されます。
 そのため、ルートドメインは正確には誤用です。

サブドメインを含むドメイン名の取得処理

サブドメインを含むドメイン名は、次のように簡単に取得することができます。

console.log(document.domain);
console.log(window.location.hostname);
console.log(new URL('https://www.bugbugnow.net/').hostname);
// www.bugbugnow.net

簡易なルートドメインの取得処理

安易な考えとして、「.com」「.jp」「.co.jp」などのトップレベルドメイン(TLD)を考慮すれば、容易にルートドメインを取得できるように思えます。

簡易な実装として次のようなものが考えられます。

function GetDomain(url) {
  const hostname = new URL(url).hostname;
  const level = hostname.split('.');
  if (level[level.length-1] == '') { level.pop(); }

  let domain;
  const len = level.length;
  if (len > 2 && level[len-2].length == 2 && level[len-1].length == 2) {
    domain = level[len-3] + '.' + level[len-2] + '.' + level[len-1];
  } else if (len > 1) {
    domain = level[len-2] + '.' + level[len-1];
  } else {
    domain = level.join('.');
  }
  return domain;
}

ただし、この処理では多くの問題を含みます。

※「.co.jp」は、正確にはセカンドレベルドメインです。

簡易な処理の問題点

上記の処理の問題点は、次のパターンが漏れている点です。(他にも多く漏れています)

https://www.pref.aichi.jp/
https://www.city.iwakura.aichi.jp/

上記の GetDomain() では、共に「aichi.jp」を取得しますが、正しくは、「pref.aichi.jp」「city.iwakura.aichi.jp」を取得しなければなりません。これは、「都道府県型JPドメイン名」と「地域型JPドメイン名」と呼ばれるドメイン名です。

このURLは、「愛知県」「愛知県岩倉市」のホームページです。日本の公共的なURLを正確に判定できないのでは、簡易実装と言えど問題があります。

正確に取得する

正確に取得する方法として、「.com」「.jp」「.co.jp」などのサフィックスをすべて保持しておく方法があります。

すべてのサフィックスリストは、 Public Suffix List にあります。

すべてのサフィックスリストを保持することで正確なドメイン名を解釈できます。このため、正確なルートドメインを取得したい場合、ライブラリ等の利用を推奨します。

備考

上記変換機には、次のライブラリを使用しています。

試験用

入力
https://www.bugbugnow.net/
jprs.jp.
ttp://jprs.jp./
ttps://jprs.jp/
ttps://jprs.jp.
www.google.com
http://www.google.co.jp/
https://www.pref.aichi.jp/
https://www.city.iwakura.aichi.jp/
https://日本語.jp/
https://xn--wgv71a119e.jp/
https://はじめよう.みんな/

出力
bugbugnow.net
jprs.jp
google.com
google.co.jp
pref.aichi.jp
city.iwakura.aichi.jp
xn--wgv71a119e.jp
xn--wgv71a119e.jp
xn--p8j9a0d9c9a.xn--q9jyb4c

備考(JPドメイン名)

JPドメイン名には、次のようなドメインが存在します。

  • 「汎用JPドメイン名」(例:example.jp
  • 「属性型JPドメイン名」(例:example.co.jp
  • 「都道府県型JPドメイン名」(例:example.aichi.jp
  • 「地域型JPドメイン名」(例:example.iwakura.aichi.jp

※地域型JPドメイン名の新規登録は、2012年3月末で停止しています。
※参考:都道府県型JPドメイン名について | JPドメイン名について | JPRS

備考(Punycode)

Punycode とは、国際化ドメイン名で使用される文字符号化方式です。

ピリオドで区切られたドメイン名の各階層毎に、プレフィックスとして「xn--」を使用してエンコードされます。