Googleはこの18か月で、Maps JavaScript APIのよく使われる4つの機能を非推奨にしました。そのうちHeatmap LayerとDrawing Libraryの2つは、2026年5月から利用できません。残るDirectionsServiceとDistanceMatrixServiceはLegacyかつ非推奨ですが、現在も動作しており、提供終了日も決まっていません。
このガイドでは、それぞれの現在の状況をGoogle自身のページへのリンクとともに整理し、置き換え方を説明します。MapAtlasを代替に使う箇所では、実際のエンドポイントとレスポンス形式でコードを示します。
非推奨になったものとまだ動くもの
| サービス | 状況 | 主な日付 | Googleの代替 |
|---|---|---|---|
| Heatmap Layer | 削除済み | 2025年5月27日に非推奨、バージョン3.65.1c(2026年5月20日)で提供終了 | deck.glなどのサードパーティライブラリ |
| Drawing Library(DrawingManager) | 削除済み | 2025年8月に非推奨、2026年5月から利用不可(バージョン3.65.3b、2026年6月4日で確認) | Terra Drawなどのサードパーティライブラリ |
| DirectionsService | Legacy、非推奨 | 2025年3月1日からLegacy、2026年2月25日から非推奨(バージョン3.64.2b)、提供終了日なし | RoutesライブラリのRouteクラス |
| DistanceMatrixService | Legacy、非推奨 | 2025年3月1日からLegacy、2026年2月25日から非推奨(バージョン3.64.2b)、提供終了日なし | RoutesライブラリのRouteMatrixクラス |
出典:Google Maps Platformの非推奨ページ、Maps JavaScript APIのリリースノート、Legacyプロダクトのページ。
Legacyには明確な意味があります。Googleによると、Legacyのサービスは新機能が追加されず、新しいCloudプロジェクトでは有効にできませんが、既存のプロジェクトでは引き続きサポートされます。Googleは提供終了の少なくとも12か月前に通知すると約束しており、DirectionsServiceとDistanceMatrixServiceを非推奨にしたリリースノートでも、提供終了の予定はなく重大なリグレッションは引き続き修正されると述べています。2025年3月1日の同じLegacy化では、WebサービスのDirections APIとDistance Matrix API、Places API、JavaScript Places Serviceも対象になりました。
動かなくなるコード
次のコードは、現在のMaps JavaScript APIではすでにエラーになります。
// Removed in 2026: these constructors no longer work
const heatmap = new google.maps.visualization.HeatmapLayer({ data: points });
const drawingManager = new google.maps.drawing.DrawingManager();
次のコードは既存のプロジェクトではまだ動きますが、非推奨であり、新しいCloudプロジェクトでは動きません。
// Legacy and deprecated, no shutdown date yet
const directionsService = new google.maps.DirectionsService();
const distanceMatrixService = new google.maps.DistanceMatrixService();
サイトのヒートマップや描画ツールが2026年5月に動かなくなった場合、原因はこれです。まずそちらを直してください。そのうえで、Googleが日付を発表する前にルーティングの移行を計画しましょう。
Googleが用意している代替
ルーティングについてGoogleは2つの方法を用意しており、どちらもロジックをサーバーに移す必要はありません。
- ブラウザで: Maps JavaScript APIのRoutesライブラリ。
RouteクラスがDirectionsServiceを、RouteMatrixクラスがDistanceMatrixServiceを置き換えます。 - サーバーで: Compute RoutesとCompute Route Matrixのメソッドを持つRESTサービス、Routes API。
可視化については、Google自身の選択肢はもうありません。ヒートマップのページはdeck.glを案内し、非推奨ページは描画用にTerra Drawを挙げています。
移行チェックリスト
1. コードベースを調べる
対象のクラスを検索します。
# Find all files using deprecated Google Maps services
grep -rn "DirectionsService\|DistanceMatrixService\|DirectionsRenderer\|HeatmapLayer\|DrawingManager" \
--include="*.js" --include="*.ts" --include="*.tsx" --include="*.jsx" src/
それらを使っているファイルとコンポーネントをすべて記録し、呼び出しがブラウザとサーバーのどちらで動いているかも書き留めます。
2. サービスごとの使い方を記録する
使用箇所ごとに次の点を記録します。
- 移動手段(車、徒歩、自転車、公共交通機関)
- 経由地(AからBの単純なルートか、複数の停車地があるルートか)
- 読み取っているレスポンスのフィールド(距離、所要時間、ポリライン、ステップ、運賃)
- 量(1日と1か月あたりのリクエスト数、コスト見積もり用)
- レイテンシーの要件(ユーザー向けのリアルタイム処理か、バッチ処理か)
3. 移行先を選ぶ
選択肢A:Googleを使い続ける。 RouteクラスとRouteMatrixクラス、またはRoutes APIに移行します。レスポンス形式はLegacyのクラスと異なるため、使っているフィールドを移行ガイドと照らし合わせてください。
選択肢B:プロバイダーを変える。 どちらにしても連携部分は書き直すので、手順2の要件でプロバイダーを比較してください。
4. 新旧を並行して動かす
その場で置き換えないでください。しばらく両方の実装を並行して動かし、切り替える前に実際のルートで距離、所要時間、レイテンシーを比較します。
5. エラー処理を更新する
Legacyのクラスはコールバック内のステータス値でエラーを返していました。RESTの代替はHTTPステータスコードとエラー本文を返すため、エラー処理も変える必要があります。
MapAtlasで各サービスを置き換える
MapAtlasのルーティング用エンドポイントはgateway.mapmetrics-atlas.net上のRESTサービスで、MapAtlas APIドキュメントに説明があります。トークンをクエリパラメーターで受け取るため、バックエンドから呼び出してください。
DirectionsServiceからMapAtlas Directions APIへ
移行前(Google、Legacy):
const directionsService = new google.maps.DirectionsService();
directionsService.route(
{
origin: { lat: 52.52, lng: 13.405 },
destination: { lat: 48.8566, lng: 2.3522 },
travelMode: google.maps.TravelMode.DRIVING,
waypoints: [
{ location: { lat: 50.9375, lng: 6.9603 }, stopover: true }
],
},
(result, status) => {
if (status === "OK") {
const route = result.routes[0];
console.log("Distance:", route.legs[0].distance.text);
console.log("Duration:", route.legs[0].duration.text);
}
}
);
移行後(MapAtlas Directions API):
const response = await fetch(
`https://gateway.mapmetrics-atlas.net/directions/?token=${process.env.MAPATLAS_API_KEY}`,
{
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
// Ordered stops: origin, waypoints, destination
locations: [
{ lat: 52.52, lon: 13.405 },
{ lat: 50.9375, lon: 6.9603 },
{ lat: 48.8566, lon: 2.3522 },
],
costing: "auto", // auto, bicycle, pedestrian, bus, truck, taxi, motor_scooter
units: "kilometers",
}),
}
);
const { trip } = await response.json();
console.log("Distance (km):", trip.summary.length);
console.log("Duration (s):", trip.summary.time);
// Each leg carries its geometry as an encoded polyline (precision 6)
const shapes = trip.legs.map((leg) => leg.shape);
主な違いは次のとおりです。
- JavaScriptのクラスではなく、バックエンドから行うREST呼び出しです。
- 経由地は
locationsの途中の要素です。 - レスポンスの構造が異なります。 合計値は
trip.summaryにあり、各区間はshapeにエンコード済みのポリラインを持ちます。ルートを描画する前にデコードしてください(後述のバックエンドの例を参照)。
DistanceMatrixServiceからMapAtlas Matrix APIへ
MapAtlas Matrix APIは、出発地と目的地のすべての組み合わせについて所要時間と距離を1回の呼び出しで返します。このエンドポイントでは各組み合わせのルート距離が400 kmまでに制限されているため、例ではベルリン周辺の地点を使っています。
移行前(Google、Legacy):
const service = new google.maps.DistanceMatrixService();
service.getDistanceMatrix(
{
origins: [
{ lat: 52.52, lng: 13.405 },
{ lat: 52.3906, lng: 13.0645 },
],
destinations: [
{ lat: 51.3397, lng: 12.3731 },
{ lat: 51.0504, lng: 13.7373 },
],
travelMode: google.maps.TravelMode.DRIVING,
},
(response, status) => {
if (status === "OK") {
response.rows.forEach((row, i) => {
row.elements.forEach((element, j) => {
console.log(`Origin ${i} -> Dest ${j}:`,
element.distance.text, element.duration.text);
});
});
}
}
);
移行後(MapAtlas Matrix API):
const response = await fetch(
`https://gateway.mapmetrics-atlas.net/matrix/?token=${process.env.MAPATLAS_API_KEY}`,
{
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
sources: [
{ lat: 52.52, lon: 13.405 },
{ lat: 52.3906, lon: 13.0645 },
],
targets: [
{ lat: 51.3397, lon: 12.3731 },
{ lat: 51.0504, lon: 13.7373 },
],
costing: "auto",
units: "kilometers",
}),
}
);
const data = await response.json();
// One row per source, one cell per target
data.sources_to_targets.forEach((row: any[], i: number) => {
row.forEach((cell, j) => {
console.log(`Origin ${i} -> Dest ${j}:`, cell.distance, "km", cell.time, "s");
});
});
このグリッドはGoogleのrowsとelementsに相当します。距離は指定した単位の数値で、時間は秒で返るため、表示用の書式は自分で整えてください。
Heatmap Layerの置き換え
選択肢1:MapLibre GL JSのヒートマップレイヤー(オープンソース)
import maplibregl from "maplibre-gl";
const map = new maplibregl.Map({
container: "map",
style: "https://gateway.mapmetrics-atlas.net/styles/?fileName=YOUR_ACCOUNT_ID/mapstyle.json&token=YOUR_API_KEY",
center: [13.405, 52.52],
zoom: 10,
});
map.on("load", () => {
map.addSource("heat-data", {
type: "geojson",
data: {
type: "FeatureCollection",
features: heatmapPoints.map((point) => ({
type: "Feature",
geometry: { type: "Point", coordinates: [point.lng, point.lat] },
properties: { weight: point.weight },
})),
},
});
map.addLayer({
id: "heatmap-layer",
type: "heatmap",
source: "heat-data",
paint: {
"heatmap-weight": ["get", "weight"],
"heatmap-intensity": 1,
"heatmap-radius": 20,
"heatmap-opacity": 0.7,
},
});
});
ヒートマップは地図ライブラリ自体で描画され、追加のサービスは必要ありません。
選択肢2:Googleのドキュメントが勧めるdeck.glのHeatmapLayer
import { HeatmapLayer } from "@deck.gl/aggregation-layers";
const heatmapLayer = new HeatmapLayer({
data: heatmapPoints,
getPosition: (d) => [d.lng, d.lat],
getWeight: (d) => d.weight,
radiusPixels: 30,
});
どちらも使えます。MapLibre GL JSはMapAtlasのスタイルを直接読み込み、deck.glは任意のベースマップに重ねられます。
Drawing Libraryの置き換え
DrawingManagerでは、ユーザーが地図上にマーカー、線、円、ポリゴンを描けました。Googleの非推奨ページが挙げるTerra Drawは同じ描画モードを備え、Google MapsやMapLibre GL JSを含む複数の地図ライブラリ向けのアダプターがあります。描いた図形はGeoJSONで返るので、そのまま保存したり、ジオフェンスや等時線のサービスに送ったりできます。
コスト比較
Googleの定価は、ルーティングのLegacy SKUとその代替となるEssentials SKUで同じです。以下の価格はすべてGoogle Maps Platformの料金ページとMapAtlasの料金ページから取得し、2026年9月26日に確認したものです。
| サービス | Google、月間無料枠 | Google、超過分1,000件あたり(最初の段階) | MapAtlas、月間無料枠 | MapAtlas、超過分1,000件あたり(最初の段階) |
|---|---|---|---|---|
| Directions(Legacy)またはCompute Routes Essentials | 10,000 | 5.00ドル | ナビゲーション10万リクエスト | 1.53ユーロ |
| Directions Advanced(Legacy)またはCompute Routes Pro | 5,000 | 10.00ドル | 同じナビゲーションの段階 | 1.53ユーロ |
| Distance Matrix(Legacy)またはCompute Route Matrix Essentials | 10,000要素 | 5.00ドル | 料金ページを参照 | 料金ページを参照 |
| Geocoding | 10,000 | 5.00ドル | 25,000 | 3.90ユーロ |
Googleは米ドル、MapAtlasはユーロで請求するため、比較する前に換算してください。どちらも量が増えると単価が下がります。月50万件のルートリクエストで試算すると次のとおりです。
- Google Compute Routes Essentials: 10,000件が無料、90,000件が5.00ドル、400,000件が4.00ドルで、合計2,050ドル。
- MapAtlasのナビゲーション: 100,000件が無料、400,000件が1.53ユーロで、合計約610ユーロ。
完全な例:バックエンドのルートと地図
この構成ではAPIキーをサーバーに置いたまま、ブラウザにはルートのジオメトリだけを送ります。
バックエンドのAPIルート(Next.js)
// app/api/directions/route.ts
import { NextRequest, NextResponse } from "next/server";
// Decode an encoded polyline with precision 6 into [lon, lat] pairs
function decodePolyline6(str: string): [number, number][] {
const coords: [number, number][] = [];
let index = 0, lat = 0, lng = 0;
while (index < str.length) {
for (const axis of [0, 1]) {
let result = 0, shift = 0, byte: number;
do {
byte = str.charCodeAt(index++) - 63;
result |= (byte & 0x1f) << shift;
shift += 5;
} while (byte >= 0x20);
const delta = result & 1 ? ~(result >> 1) : result >> 1;
if (axis === 0) lat += delta; else lng += delta;
}
coords.push([lng / 1e6, lat / 1e6]);
}
return coords;
}
export async function GET(request: NextRequest) {
const { searchParams } = new URL(request.url);
const [oLat, oLon] = searchParams.get("origin")!.split(",").map(Number);
const [dLat, dLon] = searchParams.get("destination")!.split(",").map(Number);
const response = await fetch(
`https://gateway.mapmetrics-atlas.net/directions/?token=${process.env.MAPATLAS_API_KEY}`,
{
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({
locations: [{ lat: oLat, lon: oLon }, { lat: dLat, lon: dLon }],
costing: "auto",
units: "kilometers",
}),
}
);
if (!response.ok) {
return NextResponse.json({ error: "routing failed" }, { status: 502 });
}
const { trip } = await response.json();
const coordinates = trip.legs.flatMap((leg: { shape: string }) => decodePolyline6(leg.shape));
return NextResponse.json({
coordinates,
distanceKm: trip.summary.length,
durationS: trip.summary.time,
});
}
地図コンポーネント(ReactとMapLibre GL JS)
import { useEffect, useRef } from "react";
import maplibregl from "maplibre-gl";
function DirectionsMap({ origin, destination }: {
origin: { lat: number; lng: number };
destination: { lat: number; lng: number };
}) {
const mapRef = useRef<HTMLDivElement>(null);
useEffect(() => {
const map = new maplibregl.Map({
container: mapRef.current!,
style: "https://gateway.mapmetrics-atlas.net/styles/?fileName=YOUR_ACCOUNT_ID/mapstyle.json&token=YOUR_API_KEY",
center: [origin.lng, origin.lat],
zoom: 7,
});
map.on("load", async () => {
const res = await fetch(
"/api/directions?" +
new URLSearchParams({
origin: `${origin.lat},${origin.lng}`,
destination: `${destination.lat},${destination.lng}`,
})
);
if (!res.ok) return;
const { coordinates } = await res.json();
map.addSource("route", {
type: "geojson",
data: {
type: "Feature",
geometry: { type: "LineString", coordinates },
properties: {},
},
});
map.addLayer({
id: "route-line",
type: "line",
source: "route",
paint: { "line-color": "#4A90D9", "line-width": 5 },
});
const bounds = coordinates.reduce(
(b: maplibregl.LngLatBounds, coord: [number, number]) => b.extend(coord),
new maplibregl.LngLatBounds(coordinates[0], coordinates[0])
);
map.fitBounds(bounds, { padding: 50 });
});
return () => map.remove();
}, [origin, destination]);
return <div ref={mapRef} style={{ width: "100%", height: "400px" }} />;
}
移行をテストする方法
ステップ1:両方の実装を比較する
テスト期間中は、同じリクエストで旧サービスと新サービスの両方を呼び出します。両方の距離と所要時間を記録し、実際のルートでの差を確認してください。特にフェリー、有料道路、通行制限のある道路に注意します。
ステップ2:フィーチャーフラグを使う
デプロイなしで元に戻せるよう、プロバイダーの切り替えをフラグの後ろに置きます。
const useMapAtlasDirections = process.env.FEATURE_MAPATLAS_DIRECTIONS === "true";
const directions = useMapAtlasDirections
? await fetchMapAtlasDirections(origin, destination)
: await fetchGoogleDirections(origin, destination);
ステップ3:エラー率を監視する
切り替え後は次の点を監視します。
- 新しいAPIのHTTP 4xxと5xxの割合
- レイテンシーの変化
- UIが読み取っているフィールドの欠落
- フェリー、有料道路、通行制限区域などの境界ケースでのルートの違い
ステップ4:本番公開前に負荷テストをする
物流プラットフォームの朝の配車のようにトラフィックにピークがある場合は、新しいAPIに頼る前に、ピーク時の2倍の量で負荷テストをしてください。
今やるべきこと
- Heatmap LayerやDrawing Libraryをまだ読み込んでいる場合: まずそれらを置き換えてください。現在のMaps JavaScript APIでは動作しません。
- ルーティングのコードを調べる: DirectionsService、DirectionsRenderer、DistanceMatrixServiceの呼び出しをすべて見つけます。
- 代替を選ぶ:
RouteクラスとRouteMatrixクラス、Routes API、または別のプロバイダー。 - 1つずつ移行する: フィーチャーフラグの後ろで移行し、切り替え前に結果を比較します。
- Googleの非推奨ページを確認し続ける: 提供終了日が発表された場合に備えます。GoogleはLegacyのサービスについて、少なくとも12か月前に通知すると約束しています。
MapAtlasのルーティングAPIを試すには、無料アカウントを作成してAPIドキュメントをご覧ください。移行の支援が必要な場合はお問い合わせページからご連絡ください。
よくある質問
Google MapsのDrawing Libraryはまだ使えますか?
使えません。GoogleはDrawingManagerを含むDrawing Libraryを2025年8月に非推奨とし、非推奨ページでは2026年5月以降は利用不可と記載しています。Maps JavaScript APIバージョン3.65.3b(2026年6月4日)のリリースノートでも、DrawingManagerが利用できなくなったことが確認できます。Googleは代替としてTerra Drawを挙げています。
Heatmap Layerはまだ使えますか?
使えません。GoogleはHeatmap Layerを2025年5月27日に非推奨とし、2026年5月20日のバージョン3.65.1cで提供を終了したと記載しています。代わりにdeck.glのHeatmapLayerなどのサードパーティライブラリを推奨しています。
DirectionsServiceとDistanceMatrixServiceはいつ使えなくなりますか?
Googleは日付を決めていません。どちらも2025年3月1日からLegacyのステータスで、2026年2月25日から非推奨です。Googleのリリースノートによると、提供終了の予定はなく、重大なリグレッションの修正は続き、サポート終了の少なくとも12か月前に通知されます。Legacyのサービスは新しいCloudプロジェクトでは使えないため、新規プロジェクトではRouteクラスとRouteMatrixクラス、または別のプロバイダーが必要です。
段階的に移行できますか?それとも一度にすべて切り替える必要がありますか?
1つずつ移行できます。非推奨のクラスはそれぞれ独立しています。すでに動かないDrawing LibraryとHeatmap Layerを先に置き換え、その後DirectionsServiceとDistanceMatrixServiceを自分のスケジュールで移行してください。
MapAtlasは経由地や複数の移動手段に対応していますか?
対応しています。MapAtlas Directions APIは順序付きの地点リストを受け取り、最初と最後の間にある地点はすべて経由地になります。コストモデルはauto、bicycle、pedestrian、bus、truck、taxi、motor_scooterに対応しています。RESTエンドポイントなので、APIキーがクライアントに渡らないようバックエンドから呼び出してください。

