はじめに
両APIの概要と特徴
MapboxとZENRIN Maps APIは、両者とも強力な地図サービスを提供していますが、それぞれに特徴があります。
Mapboxは世界的に有名な地図プラットフォームで、高速でカスタマイズ可能な地図描画が特徴です。
一方、ZENRIN Maps APIは日本国内で強みを持つ地図サービスです。
ZENRINの詳細な地図データを使用しており、日本国内の詳細で正確な地図情報を利用できる点が特徴です。
記事の目的
本記事の目的は、日本の住所検索におけるこれら2つのAPIの強みと弱みを明らかにすることです。
MapboxとZENRIN Maps APIの住所検索機能を多角的に比較し、それぞれの特性と用途に応じた適用例について考察します。
この比較を通じて、開発者や企業が自身のプロジェクトに最適な選択ができるよう支援することを目指します。
APIキーの取得
Mapbox
アクセストークンの取得方法
1.まずは下記のページに接続してください。
mapboxコンソール
2.「View all tokens」をクリックしてください。
3.「Create a token」をクリックして必要な情報を入力し、トークンを作成してください
4.トークンの作成が完了すると「Access tokens」の画面にて、トークンが追加されるため、
画面赤枠内のトークンを使用してください。
ZENRIN Maps API
1.検証用IDとパスワード(PW)取得
ZENRIN Maps APIを使用するためには、検証用IDとPWを取得します。
1-1.検証用IDとPWの発行を依頼
ZENRIN Maps API 無料お試しID お申込みフォームから必要事項を入力して送信します。
1-2.検証用IDとPWの確認
フォーム送信から3営業日以内にメールにて検証用IDとPWが発行されます。
2.コンソールにログイン
以下のURLでメールにて送られてきたIDとPWを入力し、ログインをします。
3.ユーザーの設定
ユーザー設定にて、「コンソール管理者メールアドレス」と「情報配信用メールアドレス」を設定します。
特にコンソール管理者メールアドレスはZENRIN Maps API コンソールのパスワードを忘れて再設定が必要となった場合に必要になります。
4.チャネルの認証方式の設定、チャネル名変更
チャネルの設定変更は左メニューの「チャネル設定」から行うことができます。
「チャネル設定」押下後表示される画面にはチャネルの一覧が表示されています。
設定を行うチャネルの「編集」ボタンを押下してください。
認証方式は3種類あり、設定したいタブを押下するとそれぞれの認証方式の設定項目が表示されます。
認証方式を有効にするには、「無効」を「有効」に変更してください。
有効にしたい認証方式が複数ある場合は、それぞれの認証方式のタブで「有効」状態に変更してください。
それぞれの設定項目を入力後「変更」ボタンを押下すると有効状態と設定項目が反映されます。
5.APIキーの取得・API利用開始
「チャネル一覧」のグレーアウトされている箇所にマウスオーバーすると表示される「APIキー」を使い、
APIリファレンスに則りAPIの利用を開始してください。
サンプルコード
Mapbox
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Mapbox 住所検索</title>
<script src='https://api.mapbox.com/mapbox-gl-js/v2.9.1/mapbox-gl.js'></script>
<link href='https://api.mapbox.com/mapbox-gl-js/v2.9.1/mapbox-gl.css' rel='stylesheet' />
<script src="https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-geocoder/v5.0.0/mapbox-gl-geocoder.min.js"></script>
<link rel="stylesheet" href="https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-geocoder/v5.0.0/mapbox-gl-geocoder.css" type="text/css">
<script src='https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-language/v1.0.0/mapbox-gl-language.js'></script>
<style>
#map { width: 100%; height: 400px; }
</style>
</head>
<body>
<div id="map"></div>
<div id="address-info"></div>
<script>
mapboxgl.accessToken = 'YOUR_MAPBOX_ACCESS_TOKEN';
var map = new mapboxgl.Map({
container: 'map',
style: 'mapbox://styles/mapbox/streets-v11',
center: [139.7670516, 35.6811673], // 東京駅周辺
zoom: 12
});
// 日本語表記に変更
map.addControl(new MapboxLanguage({
defaultLanguage: 'ja'
}));
var geocoder = new MapboxGeocoder({
accessToken: mapboxgl.accessToken,
mapboxgl: mapboxgl,
language: 'ja',
countries: 'jp'
});
map.addControl(geocoder);
geocoder.on('result', function(e) {
var addressInfo = document.getElementById('address-info');
var coordinates = e.result.geometry.coordinates;
addressInfo.innerHTML = '<h3>検索結果:</h3>' +
'<p>住所: ' + e.result.place_name + '</p>' +
'<p>読み: ' + (e.result.properties.yomi || '読みデータなし') + '</p>' +
'<p>緯度: ' + coordinates[1] + '</p>' +
'<p>経度: ' + coordinates[0] + '</p>';
// マーカーを追加
new mapboxgl.Marker()
.setLngLat(coordinates)
.addTo(map);
});
</script>
</body>
</html>
ZENRIN Maps API
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>Display a map</title>
<style>
body { margin: 0; padding: 0; font-family: Arial, sans-serif; }
#search-bar {
position: absolute;
top: 10px;
left: 10px;
background-color: #fff;
padding: 10px;
border-radius: 5px;
box-shadow: 0 0 10px rgba(0,0,0,0.2);
z-index: 1;
}
#result {
position: absolute;
top: 70px;
left: 10px;
background-color: rgba(255, 255, 255, 0.9);
padding: 10px;
border-radius: 5px;
box-shadow: 0 0 10px rgba(0,0,0,0.2);
z-index: 1;
display: none;
}
#ZMap {
position: absolute;
top: 0;
bottom: 0;
width: 100%;
}
</style>
<!-- ローダーを読み込む -->
<script src="https://test-js.zmaps-api.com/zma_loader.js?ke=YOUR_API_KEY&auth=referer"></script>
</head>
<body>
<div id="search-bar">
<input type="text" id="address" placeholder="住所を入力してください">
<button onclick="searchAddress()">検索</button>
</div>
<!-- 検索結果の表示エリア! -->
<div id="result">
<p><strong>検索結果:</strong></p>
<p>住所: <span id="result-address">-</span></p>
<p>住所読み: <span id="result-address_read">-</span></p>
<p>緯度: <span id="result-lat">-</span></p>
<p>経度: <span id="result-lng">-</span></p>
</div>
<div id="ZMap"></div>
<script src="js/zma_address_search.js"></script>
</body>
</html>
// グローバル変数として `map` と `mrk_widget` を定義
let map;
let mrk_widget;
// ローダーのメソッド実行
ZMALoader.setOnLoad(function (mapOptions, error) {
if (error) {
console.error(error)
return
}
// 地図オブジェクト
// var map;
// 中心点の緯度経度(東京駅)
const lat = 35.681406, lng = 139.767132;
// マップコンテナ要素を取得する
const mapElement = document.getElementById('ZMap');
// MapOptionsをデフォルト値から変更する場合各パラメータに値を設定
// 中心点の緯度経度を設定
mapOptions.center = new ZDC.LatLng(lat, lng);
mapOptions.zipsMapType = 'kP8KjZdn'
mapOptions.mouseWheelReverseZoom = true; // ★マウスホイールのズーム方向の反転を指定
// 地図を生成
map = new ZDC.Map(
mapElement,
mapOptions,
function() {
// コントロールを追加する
// 左上 拡大縮小ボタン表示
map.addControl(new ZDC.ZoomButton('bottom-right', new ZDC.Point(-20, -35)));
// 右上 コンパス表示
map.addControl(new ZDC.Compass('top-right'));
// 左下 スケールバー表示
map.addControl(new ZDC.ScaleBar('bottom-left'));
},
function() {
// Failure callback
}
);
})
async function searchAddress() {
const address = document.getElementById("address").value;
if (!address) {
alert("住所を入力してください");
return;
}
try {
const response = await fetch('https://test-web.zmaps-api.com/search/address', {
method: 'POST',
headers: {
'Content-Type': 'application/x-www-form-urlencoded',
'x-api-key': 'YOUR_API_KEY',
'Authorization': 'referer'
},
body: new URLSearchParams({
word: address,
word_match_type: '3'
})
});
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const data = await response.json();
console.log(data.result.item);
if (data.status === "OK" && data.result.info.hit > 0) {
const location = data.result.item[0].position;
// 配列の順序が[経度, 緯度]であることを確認
const lng = location[0];
const lat = location[1];
const latLng = new ZDC.LatLng(lat, lng);
// 地図をその位置に移動
map.setCenter(latLng);
/* Markerの設置 */
center_mrk =new ZDC.CenterMarker();
// MarkerをMapに追加
map.addControl(center_mrk);
// 検索結果を表示
document.getElementById("result-address").textContent = data.result.item[0].address;
document.getElementById("result-address_read").textContent = data.result.item[0].address_read;
document.getElementById("result-lat").textContent = lat;
document.getElementById("result-lng").textContent = lng;
document.getElementById("result").style.display = "block";
console.log("緯度:", lat, "経度:", lng);
} else {
alert("住所の位置情報が見つかりませんでした");
}
} catch (error) {
console.error("エラーが発生しました:", error);
alert("住所の検索中にエラーが発生しました");
}
}
地図表示
Mapbox
ZENRIN Maps API
ZENRINMapsAPI 住所検索
解説
Mapbox
1.HTMLドキュメントの宣言と<head>
セクション
この部分では、基本的なHTML構造を定義しています。
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Mapbox 住所検索</title>
<script src='https://api.mapbox.com/mapbox-gl-js/v2.9.1/mapbox-gl.js'></script>
<link href='https://api.mapbox.com/mapbox-gl-js/v2.9.1/mapbox-gl.css' rel='stylesheet' />
<script src="https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-geocoder/v5.0.0/mapbox-gl-geocoder.min.js"></script>
<link rel="stylesheet" href="https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-geocoder/v5.0.0/mapbox-gl-geocoder.css" type="text/css">
<script src='https://api.mapbox.com/mapbox-gl-js/plugins/mapbox-gl-language/v1.0.0/mapbox-gl-language.js'></script>
<style>
#map { width: 100%; height: 400px; }
</style>
</head>
<meta name="viewport" ...>
: ビューポートの設定を行います。レスポンシブデザインのために重要です。
<title>Mapbox 住所検索</title>
: ブラウザのタブに表示されるタイトルを設定します。
<script src='...mapbox-gl.js'></script>
: Mapbox GL JSライブラリを読み込みます。
<link href='...mapbox-gl.css' rel='stylesheet' />
: Mapbox GL JSのスタイルシートを読み込みます。
<script src="...mapbox-gl-geocoder.min.js"></script>
: Mapbox Geocoderプラグインを読み込みます。これは住所検索機能を提供します。
<link rel="stylesheet" ...mapbox-gl-geocoder.css" ...>
: Mapbox Geocoderプラグインのスタイルシートを読み込みます。
<script src='...mapbox-gl-language.js'></script>
: Mapbox Languageプラグインを読み込みます。地図のラベルを多言語対応にするためのものです。
<style>
: 地図コンテナ(#map)
のサイズを指定するCSSを定義します。
2.<body>
セクション
<body>
<div id="map"></div>
<div id="address-info"></div>
<script>
// JavaScriptコード
</script>
</body>
<div id="map"></div>
: 地図を表示するためのコンテナ要素です。JavaScriptコードでこの要素にMapboxの地図がレンダリングされます。
<div id="address-info"></div>
: 住所検索の結果を表示するためのコンテナ要素です。検索結果(住所、緯度、経度など)がここに表示されます。
3.JavaScriptコード
<script>
mapboxgl.accessToken = 'YOUR_MAPBOX_ACCESS_TOKEN';
var map = new mapboxgl.Map({
container: 'map',
style: 'mapbox://styles/mapbox/streets-v11',
center: [139.7670516, 35.6811673], // 東京駅周辺
zoom: 12
});
// 日本語表記に変更
map.addControl(new MapboxLanguage({
defaultLanguage: 'ja'
}));
var geocoder = new MapboxGeocoder({
accessToken: mapboxgl.accessToken,
mapboxgl: mapboxgl,
language: 'ja',
countries: 'jp'
});
map.addControl(geocoder);
geocoder.on('result', function(e) {
var addressInfo = document.getElementById('address-info');
var coordinates = e.result.geometry.coordinates;
addressInfo.innerHTML = '<h3>検索結果:</h3>' +
'<p>住所: ' + e.result.place_name + '</p>' +
'<p>読み: ' + (e.result.properties.yomi || '読みデータなし') + '</p>' +
'<p>緯度: ' + coordinates[1] + '</p>' +
'<p>経度: ' + coordinates[0] + '</p>';
// マーカーを追加
new mapboxgl.Marker()
.setLngLat(coordinates)
.addTo(map);
});
</script>
mapboxgl.accessToken = 'YOUR_MAPBOX_ACCESS_TOKEN'
: Mapboxのアクセストークンを設定します。YOUR_MAPBOX_ACCESS_TOKENは、自分のMapboxアカウントから取得したアクセストークンに置き換える必要があります。このトークンがないと、Mapboxの地図を表示できません。
var map = new mapboxgl.Map({...});
: Mapboxの地図インスタンスを作成します。
container: 'map'
: 地図を表示するHTML要素のIDを指定します。
style: 'mapbox://styles/mapbox/streets-v11'
: 地図のスタイルを指定します。ここではMapboxのデフォルトのストリートスタイルを使用しています。
center: [139.7670516, 35.6811673]
: 地図の中心座標を[経度, 緯度]の形式で指定します。ここでは東京駅周辺を初期の中心に設定しています。
zoom: 12
: 地図の初期ズームレベルを指定します。
map.addControl(new MapboxLanguage({...}));
: Mapbox Languageプラグインを追加し、地図のラベルを日本語で表示するように設定します。
defaultLanguage: 'ja'
: 地図のデフォルト言語を日本語に設定します。
var geocoder = new MapboxGeocoder({...});
: Mapbox Geocoderプラグインのインスタンスを作成します。
accessToken: mapboxgl.accessToken
: GeocoderがMapbox APIにアクセスするためのアクセストークンを設定します。
mapboxgl: mapboxgl
: 使用するMapbox GL JSライブラリのインスタンスを指定します。
language: 'ja'
: 検索時の言語を日本語に設定します。
countries: 'jp'
: 検索対象の国を日本に限定します。
map.addControl(geocoder);
: 地図にGeocoderコントロール(検索ボックス)を追加します。
geocoder.on('result', function(e) {...});
: Geocoderで住所が検索され、結果が返されたときに実行される関数を定義します。
var addressInfo = document.getElementById('address-info');
: 検索結果を表示するHTML要素を取得します。
var coordinates = e.result.geometry.coordinates;
: 検索結果の座標(緯度と経度)を取得します。
addressInfo.innerHTML = ...
: 検索結果の情報をHTML要素に表示します。住所、読み(利用可能な場合)、緯度、経度を表示します。
new mapboxgl.Marker().setLngLat(coordinates).addTo(map);
: 検索結果の位置にマーカーを追加します。
4.住所読み取り関数 extractAddressReading()
function extractAddressReading(addressComponents) {
for (let component of addressComponents) {
if (component.types.includes("political") || component.types.includes("sublocality") || component.types.includes("locality")) {
if (component.long_name && component.short_name) {
return component.short_name; // ふりがな情報(省略形がふりがなの可能性あり)
}
}
}
return null;
}
住所読み取りの抽出: 住所のコンポーネントから、政治的または地域的な要素を探し、その短縮名(ふりがな情報として使用)を返します。
ZENRIN Maps API
1.地図の初期化
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<title>Display a map</title>
<style>
/* スタイル設定 */
body { margin: 0; padding: 0; font-family: Arial, sans-serif; }
#search-bar {
position: absolute;
top: 10px;
left: 10px;
background-color: #fff;
padding: 10px;
border-radius: 5px;
box-shadow: 0 0 10px rgba(0,0,0,0.2);
z-index: 1;
}
#result {
position: absolute;
top: 70px;
left: 10px;
background-color: rgba(255, 255, 255, 0.9);
padding: 10px;
border-radius: 5px;
box-shadow: 0 0 10px rgba(0,0,0,0.2);
z-index: 1;
display: none;
}
#ZMap {
position: absolute;
top: 0;
bottom: 0;
width: 100%;
}
</style>
<!-- ローダーを読み込む -->
<script src="https://test-js.zmaps-api.com/zma_loader.js?key=YOUR_API_KEY&auth=referer"></script>
</head>
<body>
<div id="search-bar">
<input type="text" id="address" placeholder="住所を入力してください">
<button onclick="searchAddress()">検索</button>
</div>
<!-- 検索結果の表示エリア -->
<div id="result">
<p><strong>検索結果:</strong></p>
<p>住所: <span id="result-address">-</span></p>
<p>住所読み: <span id="result-address_read">-</span></p>
<p>緯度: <span id="result-lat">-</span></p>
<p>経度: <span id="result-lng">-</span></p>
</div>
<div id="ZMap"></div>
<script src="js/zma_address_search.js"></script>
</body>
</html>
基本構造: HTML文書の基本的な構造を定義しています。
スタイル設定: CSSスタイルで、検索バー、結果表示エリア、地図のレイアウトを設定しています。
ローダーの読み込み: ZENRIN Maps APIのローダーを読み込みます。
2.初期関数
ZMALoader.setOnLoad(function (mapOptions, error) {
if (error) {
console.error(error)
return
}
// 地図オブジェクト
const lat = 35.681406, lng = 139.767132;
const mapElement = document.getElementById('ZMap');
// MapOptionsを設定
mapOptions.center = new ZDC.LatLng(lat, lng);
mapOptions.zipsMapType = 'VeAmBrmV'
mapOptions.mouseWheelReverseZoom = true;
// 地図を生成
map = new ZDC.Map(
mapElement,
mapOptions,
function() {
// Success callback
map.addControl(new ZDC.ZoomButton('bottom-right', new ZDC.Point(-20, -35)));
map.addControl(new ZDC.Compass('top-right'));
map.addControl(new ZDC.ScaleBar('bottom-left'));
},
function() {
// Failure callback
}
);
})
地図の初期化: 東京駅を中心に地図を初期化し、ズームボタンやコンパスなどのコントロールを追加します。
3.住所検索関数 searchAddress()
async function searchAddress() {
const address = document.getElementById("address").value;
if (!address) {
alert("住所を入力してください");
return;
}
try {
const response = await fetch('https://test-web.zmaps-api.com/search/address', {
method: 'POST',
headers: {
'Content-Type': 'application/x-www-form-urlencoded',
'x-api-key': 'YOUR_API_KEY',
'Authorization': 'referer'
},
body: new URLSearchParams({
word: address,
word_match_type: '3'
})
});
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const data = await response.json();
console.log(data.result.item);
if (data.status === "OK" && data.result.info.hit > 0) {
const location = data.result.item[0].position;
const lng = location[0];
const lat = location[1];
const latLng = new ZDC.LatLng(lat, lng);
// 地図をその位置に移動
map.setCenter(latLng);
/* Markerの設置 */
center_mrk = new ZDC.CenterMarker();
map.addControl(center_mrk);
// 検索結果を表示
document.getElementById("result-address").textContent = data.result.item[0].address;
document.getElementById("result-address_read").textContent = data.result.item[0].address_read;
document.getElementById("result-lat").textContent = lat;
document.getElementById("result-lng").textContent = lng;
document.getElementById("result").style.display = "block";
console.log("緯度:", lat, "経度:", lng);
} else {
alert("住所の位置情報が見つかりませんでした");
}
} catch (error) {
console.error("エラーが発生しました:", error);
alert("住所の検索中にエラーが発生しました");
}
}
住所入力のチェック: 住所が入力されていない場合、アラートを表示します。
住所検索APIの呼び出し: ZENRIN Maps APIの住所検索APIを使用して、入力された住所の位置情報を取得します。
地図の更新と結果表示: 検索結果に基づいて地図を更新し、住所や緯度経度を表示します。
検索結果の比較
1. 東京都港区芝公園4丁目2−8(東京タワー)
2. 北海道旭川市東旭川町倉沼(旭山動物園)
3. 沖縄県国頭郡本部町石川424番地(美ら海水族館)
主な結論
曖昧な住所検索
ZENRIN Maps APIは日本の複雑な住所体系に強く、曖昧な住所でも正確な結果を返す傾向があります。
一方、Mapboxは一般的な住所では問題ありませんが、日本特有の複雑な住所では精度が落ちる可能性があります。
日本特有の機能
ZENRIN Maps APIは住所の読み情報を提供しており、これは日本語の難読地名対策として非常に有用です。Mapboxにはこの機能がありません。
ZENRIN Maps APIは地番レベルまでの詳細な住所情報を持っており、「沖縄県国頭郡本部町字石川424」のような地番表記にも対応しています。これは日本の住所システムに特化した機能です。
カスタマイズ性と拡張性
ZENRIN Maps APIは、カスタマイズ性が高く、日本国内特有の道路事情や規制に対応した詳細な設定が可能です。
各APIの適した使用シーン
ZENRIN Maps API: 日本国内の詳細な地図情報が必要な場合、特に不動産、物流、地方自治体向けのアプリケーションに適しています。
Mapbox: グローバルな対応が必要な場合や、高度なカスタマイズを要する国際的なアプリケーションに適しています。