给自己网站增加一个定位插件——调用美团API定位到访者的IP地址

给自己网站增加一个定位插件——调用美团API定位到访者的IP地址

V+变量
2025-05-02 / 0 评论 / 11 阅读 / 正在检测是否收录...

1 前言

美团通过IP地址可以快速定位,利用美团API可以给网站增加一个定位到访者的插件。
美团API地址为:https://apimobile.meituan.com/locate/v2/ip/loc?rgeo=true&ip=
本文介绍如何调用美团API定位到访者的IP地址,给自己网站增加一个定位插件。

2 部署教程

2.1 新建ip.php文件

在网站目录下新建ip.php文件,如可以选择在子目录tools下新建ip.php文件,其代码如下:

<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_POST['ip'])) {
    $ip = $_POST['ip'];
    $ipData = json_decode(file_get_contents("https://apimobile.meituan.com/locate/v2/ip/loc?rgeo=true&ip=" . urlencode($ip)), true);
    if (!$ipData || !isset($ipData['data']['lat'])) exit(json_encode(['success' => false]));
    
    $lat = $ipData['data']['lat']; $lng = $ipData['data']['lng']; $rgeo = $ipData['data']['rgeo'];
    $cityData = json_decode(file_get_contents("https://apimobile.meituan.com/group/v1/city/latlng/{$lat},{$lng}?tag=0"), true)['data'] ?? [];
    
    exit(json_encode(['success' => true, 'ip' => $ip, 'lat' => $lat, 'lng' => $lng, 
        'country' => $rgeo['country'] ?? '', 'province' => $rgeo['province'] ?? '', 
        'city' => $rgeo['city'] ?? '', 'district' => $rgeo['district'] ?? '', 
        'detail' => $cityData['detail'] ?? '']));
}
?>
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8"><title>IP Locator</title><meta name="viewport" content="width=device-width,initial-scale=1">
    <script src="https://cdn.tailwindcss.com"></script>
    <link href="https://fastly.jsdelivr.net/npm/[email protected]/dist/leaflet.min.css" rel="stylesheet"/>
    <script src="https://fastly.jsdelivr.net/npm/[email protected]/dist/leaflet.min.js"></script>
</head>
<body class="bg-slate-50 font-sans p-3 md:p-6">
    <div class="max-w-4xl mx-auto">
        <h1 class="text-xl font-medium mb-6 text-center text-gray-700">访客地址</h1>
        <div class="grid md:grid-cols-2 gap-4" id="cards"></div>
        <div class="text-center text-xs text-gray-400 mt-6">Powered by <a href="https://www.Vvars.com">V+变量建站日记</a></div>
    </div>
    <script>
    (async () => {
        const sources = [
            {id: 'f', url: 'https://ipv4.lvhai.org/', label: '代理IP', color: '#3b82f6'},
            {id: 'd', url: 'https://ipv4_cu.itdog.cn/', label: '访客地址', color: '#10b981'}
        ];
        
        // Create cards & fetch IPs
        sources.forEach(s => {
            document.getElementById('cards').innerHTML += `
                <div class="bg-white rounded-lg shadow-sm border border-gray-100 overflow-hidden">
                    <div class="px-3 py-2 border-b border-gray-100 flex items-center justify-between">
                        <h2 class="text-sm font-medium text-gray-700">${s.label}</h2>
                        <div class="h-2 w-2 rounded-full" style="background:${s.color}"></div>
                    </div>
                    <div id="${s.id}-content" class="p-3 text-sm">
                        <div class="animate-pulse h-4 w-20 bg-gray-200 rounded"></div>
                    </div>
                    <div id="${s.id}-map" class="h-40 rounded-md mt-2 hidden"></div>
                </div>`;
            
            // Process IP
            (async () => {
                try {
                    // Get IP
                    const ip = await fetch(s.url).then(r => s.url.includes('lvhai') ? 
                        r.text().then(t => { try { return JSON.parse(t).ip || t.trim(); } catch { return t.trim(); } }) : 
                        r.json().then(j => j.ip)).catch(() => null);
                    
                    if (!ip) {
                        document.getElementById(`${s.id}-content`).innerHTML = `<div class="text-red-500">Failed to get IP</div>`;
                        return;
                    }
                    
                    document.getElementById(`${s.id}-content`).innerHTML = `<div class="font-mono text-gray-600">IP: ${ip}</div>`;
                    
                    // Get location
                    const data = await fetch(location.href, {
                        method: 'POST', 
                        headers: {'Content-Type': 'application/x-www-form-urlencoded'},
                        body: `ip=${encodeURIComponent(ip)}`
                    }).then(r => r.json());
                    
                    if (!data.success) {
                        document.getElementById(`${s.id}-content`).innerHTML += `<div class="text-red-500 text-xs mt-1">Location failed</div>`;
                        return;
                    }
                    
                    // Update content
                    document.getElementById(`${s.id}-content`).innerHTML = `
                        <div class="font-mono text-gray-600">IP: ${ip}</div>
                        <div class="grid grid-cols-2 gap-x-2 gap-y-1 text-xs mt-2">
                            <div><span class="text-gray-500">国家:</span> ${data.country||'—'}</div>
                            <div><span class="text-gray-500">省区:</span> ${data.province||'—'}</div>
                            <div><span class="text-gray-500">城市:</span> ${data.city||'—'}</div>
                            <div><span class="text-gray-500">区县:</span> ${data.district||'—'}</div>
                        </div>`;
                    
                    // Show map with CARTO basemap
                    const mapEl = document.getElementById(`${s.id}-map`);
                    mapEl.classList.remove('hidden');
                    const map = L.map(mapEl, {zoomControl: false, attributionControl: false}).setView([data.lat, data.lng], 10);
                    L.tileLayer('https://{s}.basemaps.cartocdn.com/light_all/{z}//{y}{r}.png', {
                        subdomains: 'abcd'
                    }).addTo(map);
                    L.circleMarker([data.lat, data.lng], {radius: 6, color: s.color, weight: 2, fillOpacity: 0.3}).addTo(map);
                    setTimeout(() => map.invalidateSize(), 100);
                } catch (err) {
                    document.getElementById(`${s.id}-content`).innerHTML = `<div class="text-red-500">Error: ${err.message}</div>`;
                }
            })();
        });
    })();
    </script>
</body>
</html>

2.2 在网站模板中加入调用代码

可以采用iframe调用,示例代码如下:

<iframe frameborder=0
src="https://www.vvars.com/tools/ip.php"
style="border-radius:8px; height: 300px;
transform: scale(0.85); transform-origin: top left;"></iframe>

代码参考,需要自行调整height和scale数值。

3 最终效果

IP显示页面
调用效果

IP显示:https://www.vvars.com/tools/ip.php
网站调用显示:https://www.vvars.com/Website-construction/Add-a-location-plug-in-to-your-website---call-Meituan-API-to-locate-the-visitor-s-IP-address.html

0

评论 (0)

取消