前端Ajax获取当前外网IP地址并通过腾讯接口解析地理位置

目录

一、获取访问端IP地址

二、可用的IP获取接口

1、韩小韩IP获取接口:

 2、ipify API

 附3、失败的太平洋接口

三、腾讯位置服务-IP位置查询接口


一、获取访问端IP地址

原计划使用后端HttpServletRequest 获取访问端的IP地址,但在nginx和堡垒机等阻碍下始终只能获得网关的地址,方法如下:

    public String buildLicense_2(@RequestBody Map map, HttpServletRequest request){
       //只能获取到网关的ip,获取不到真实IP
        String ipAddress = IpUtil.getIpAddr(request);
        System.err.println("IP地址:"+ipAddress);
    }
/**
     * 获取IP地址
     *
     * 使用Nginx等反向代理软件, 则不能通过request.getRemoteAddr()获取IP地址
     * 如果使用了多级反向代理的话,X-Forwarded-For的值并不止一个,而是一串IP地址,X-Forwarded-For中第一个非unknown的有效IP字符串,则为真实IP地址
     */
    public static String getIpAddr(HttpServletRequest request) {
        if (request == null) {
            return "unknown";
        }
        String ip = request.getHeader("x-forwarded-for");
        System.out.println("x-forwarded-for IP地址:"+ip);
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("Proxy-Client-IP");
            System.out.println("Proxy-Client-IP IP地址:"+ip);
        }
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("X-Forwarded-For");
            System.out.println("X-Forwarded-For IP地址:"+ip);
        }
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("WL-Proxy-Client-IP");
            System.out.println("WL-Proxy-Client-IP IP地址:"+ip);
        }
        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("X-Real-IP");
            System.out.println("X-Real-IP IP地址:"+ip);
        }

        if (ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getRemoteAddr();
        }

        try{
            System.out.println("getRemoteAddr() IP地址:"+request.getRemoteAddr());
        }
        catch (Exception ex){

        }

        return "0:0:0:0:0:0:0:1".equals(ip) ? LOCAL_IP : ip;
    }

故在前端通过第三方接口,获取当前ip地址后再传到后端

具体如下:

function getIpInfo() {
    $.ajax({
        url: "https://api.vvhan.com/api/visitor.info",// "https://api.ipify.org?format=json",
        type: "GET", 
        //data: { val1: "1", val2: "2" },
        dataType: "json", 
        success: function (result) {
            console.log("IP地址:");
            console.log(result);
            ipData = result;
        },
        error: function () {
            console.log('获取ip失败');
        }
    });
}

二、可用的IP获取接口

如上所示,使用的是第三方

1、韩小韩IP获取接口:

API地址:https://api.vvhan.com/api/visitor.info

API文档地址:https://api.vvhan.com/fangke.html

返回示例:

 使用说明:

 韩小韩接口站API大全:韩小韩API接口站 - 免费API数据接口调用服务平台

 2、ipify API

API地址:https://api.ipify.org?format=json

官网地址:https://www.ipify.org/

 可再各个环境下调用

 附3、失败的太平洋接口
var whois = {
    root: 'http://whois.pconline.com.cn',
    version: 2.0,
    jsonIp: function () {
        var s = document.getElementsByTagName('head')[0].appendChild(document.createElement("script"));
        /*s.src = this.root + "/jsAlert.jsp?ip=" + ip;*/
        s.type = "application/javascript";
        s.src = this.root + "/ipJson.jsp?callback=callbackRepos";
        console.log(s.src);
    },
    lableIp: function (id, ip) {
        var s = document.getElementsByTagName('head')[0].appendChild(document.createElement("script"));
        s.src = this.root + "/jsLabel.jsp?ip=" + ip + "&id=" + id;
    }
}
function getCurIP() {
    whois.jsonIp();
}
function callbackRepos(res) {
    console.log(res);
    //var data = JSON.stringify(res); //json对象转成字符串
    //console.log(data);
    ipData = res;
}

接口地址:

http://whois.pconline.com.cn

http://whois.pconline.com.cn/ipJson.jsp

只能以如上所示方式调用,在本地可用,一旦部署到外网环境下就是会失败403错误。还会存在跨域问题。所以此法不可用,却浪费了我许多时间。

三、腾讯位置服务-IP位置查询接口

在后台通过腾讯接口将IP地址转换为县区市级别的位置信息,以上的接口只能查询到地级市。

API文档地址:WebService API | 腾讯位置服务

注册腾讯位置服务,创建App,获取app key之后即可在后台调用,

如下所示,返回 省-市-县-县代码

String s = sendGet(ip, KEY);
//        System.out.println("IP地址查询结果s=" + s);
        JSONObject map =new JSONObject(s);
        String message = (String) map.get("message");
        if("Success".equals(message)){
            Map result = (Map) map.get("result");
            Map addressInfo = (Map) result.get("ad_info");
            String nation = (String) addressInfo.get("nation");
            String province = (String) addressInfo.get("province");
            String district = (String) addressInfo.get("district");
            String city = (String) addressInfo.get("city");
            Integer XZQDM = (Integer) addressInfo.get("adcode");
            String address = province + "-" + city + "-" + district + "-"  + XZQDM;
            return address;
        }else{
            System.out.println("message="+message);
            return message;
        }
 //根据在腾讯位置服务上申请的key进行请求操作
    private static String sendGet(String ip, String key) {
        String result = "";
        BufferedReader in = null;
        try {
            String urlNameString = "https://apis.map.qq.com/ws/location/v1/ip?ip="+ip+"&key="+key;
            URL realUrl = new URL(urlNameString);
            // 打开和URL之间的连接
            URLConnection connection = realUrl.openConnection();
            // 设置通用的请求属性
            connection.setRequestProperty("accept", "*/*");
            connection.setRequestProperty("connection", "Keep-Alive");
            connection.setRequestProperty("user-agent",
                    "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
            // 建立实际的连接
            connection.connect();
            // 获取所有响应头字段
            Map<String, List<String>> map = connection.getHeaderFields();
            // 遍历所有的响应头字段
//            for (Map.Entry entry : map.entrySet()) {
//                System.out.println(key + "--->" + entry);
//            }
            // 定义 BufferedReader输入流来读取URL的响应
            in = new BufferedReader(new InputStreamReader(
                    connection.getInputStream()));
            String line;
            while ((line = in.readLine()) != null) {
                result += line;
            }
        } catch (Exception e) {
            System.out.println("发送GET请求出现异常!" + e);
            e.printStackTrace();
        }
        // 使用finally块来关闭输入流
        finally {
            try {
                if (in != null) {
                    in.close();
                }
            } catch (Exception e2) {
                e2.printStackTrace();
            }
        }
        return result;
    }

附参考文章:

Ajax请求后端接口(GET、POST、轮询请求)_ajax post_IamaMartian的博客-CSDN博客

 

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/416401.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Vision Pro与Quest生态对比

数据对比情况分析&#xff1a; Quest应用和AVP应用在类型上存在差异。Quest更偏向于游戏应用&#xff0c;而AVP则更多地关注非游戏应用。这可能反映了两个平台在定位和受众群体上的不同。在技术选择上&#xff0c;Quest游戏主要使用不太适合应用开发的3D游戏引擎&#xff0c;而…

ZYNQ-AXI4_LITE

文章目录 数据接口 数据接口 分为三个通道&#xff0c;写地址通道&#xff0c;写数据通道&#xff0c;应答通道。其中AWPROT,WSTRB用的比较少。 WSTRB为写的数据的掩码&#xff0c;写的数据为32bit&#xff0c;4个Byte&#xff0c;所以WSTRB为4bit位宽&#xff0c;WSTRB为4位对…

金三银四面试必问:Redis真的是单线程吗?

文章目录 01 Redis中的多线程1&#xff09;redis-server&#xff1a;2&#xff09;jemalloc_bg_thd3&#xff09;bio_xxx&#xff1a; 02 I/O多线程03 Redis中的多进程04 结论▼延伸阅读 由面试题“Redis是否为单线程”引发的思考 作者&#xff1a;李乐 来源&#xff1a;IT阅读…

尚硅谷JavaSE笔记

JavaSE Java概述 Java语言的特点 面向对象健壮性跨平台性 Java两种核心机制 Java虚拟机 (Java Virtal Machine) 字节码文件运行在JVM上 垃圾收集机制 (Garbage Collection) JDK、JRE、JVM JDK JRE 开发工具集JRE JVM JavaSE标准类库 配置环境变量Path 配置JAVA_H…

【vuex之五大核心概念】

vuex:五大核心概念 一、state状态1.state的含义2.如何访问以及使用仓库的数据&#xff08;1&#xff09;通过store直接访问获取store对象 &#xff08;2&#xff09;通过辅助函数MapState 二、mutations1.作用2.严格模式3.操作流程定义 mutations 对象&#xff0c;对象中存放修…

了解GPT:ChatGPT的终极指南

在人工智能&#xff08;AI&#xff09;的世界里&#xff0c;有一颗冉冉升起的新星正在革命性地改变我们与机器的交互方式&#xff1a;ChatGPT。在本文中&#xff0c;我们将深入研究什么是ChatGPT&#xff0c;为什么底层技术GPT如此强大&#xff0c;以及它是如何实现其卓越功能的…

马尔可夫决策过程

马尔可夫决策过程 马尔可夫过程马尔可夫性值马尔科夫过程 马尔可夫奖励过程回报与价值函数贝尔曼方程 马尔可夫决策过程策略马尔科夫决策过程中的价值函数状态价值函数和动作价值函数的 关系 贝尔曼期望方程最优价值函数最优策略寻找最优策略贝尔曼最优方程 马尔可夫过程 马尔…

Jenkins配置在远程服务器上执行shell脚本(两种方式)

Jenkins配置在远程服务器上执行shell脚本 方式一&#xff1a;通过SSH免密方式执行 说明&#xff1a;Jenkins部署在ServerA&#xff1a;10.1.1.74上&#xff0c;要运行的程序在ServerB&#xff1a;10.1.1.196 分两步 第一步&#xff1a;Linux Centos7配置SSH免密登录 Linux…

T - SQL使用事务 及 在Winform使用事务

事务适用场景 1 事务使用在存储过程中&#xff0c;直接在数据库中进行编写 2 事务使用在Winfrom项目中 SQl&#xff1a;使用事务转账操作的实例 一般都会找一个变量记录错误的个数&#xff0c;error记录上一句sql的错误和错误编号 declare errornum int 0 -- 定义…

Linux系统安装使用nginx

1.编译安装Nginx服务 (1)关闭防火墙&#xff0c;将安装nginx所需要软件包传到/opt目录下 systemctl stop firewalld systemctl disable firewalld setenforce 0 将压缩包传入到/opt目录下 cd /opt wget http://nginx.org/download/nginx-1.18.0.tar.gz (2). 安装依赖…

【MATLAB】ICEEMDAN_ MFE_SVM_LSTM 神经网络时序预测算法

有意向获取代码&#xff0c;请转文末观看代码获取方式~也可转原文链接获取~ 1 基本定义 ICEEMDAN是指“改进的完全扩展经验模态分解与自适应噪声”&#xff08;Improved Complete Ensemble Empirical Mode Decomposition with Adaptive Noise&#xff09;&#xff0c;它是CEEM…

Constructor构造方法

在我们创建实例时&#xff0c;我们经常需要同时初始化这个实例&#xff0c;例如&#xff1a; Person ming new Person(); ming.setName("卫什么"); ming.setAge("18"); 这样需要三行代码&#xff0c;实际上&#xff0c;在我们创建实例时&#xff0c;是通过…

MATLAB环境下脑电信号EEG的谱分析

脑电信号一直伴随着人类的生命&#xff0c;脑电波是脑神经细胞发生新陈代谢、离子交换时细胞群兴奋突触电位总和&#xff0c;脑电信号的节律性则和丘脑相关&#xff0c;含有丰富的大脑活动信息。通常我们所接触的脑电图都是头皮脑电图&#xff0c;在有些特殊场合还需要皮下部位…

ad18学习笔记十六:如何放置精准焊盘到特定位置,捕抓功能的讲解

网上倒是一堆相关的指导 AD软件熟练度提升&#xff0c;如何设置板框捕捉&#xff1f;_哔哩哔哩_bilibili 关于Altium Designer 20 的捕抓功能的讲解_ad捕捉设置-CSDN博客 AD软件捕捉进阶实例&#xff0c;如何精确的放置布局元器件&#xff1f;_哔哩哔哩_bilibili AD绘制PCB…

学习阶段单片机买esp32还是stm32?

学习阶段单片机买esp32还是stm32? 在开始前我有一些资料&#xff0c;是我根据网友给的问题精心整理了一份「stm32的资料从专业入门到高级教程」&#xff0c; 点个关注在评论区回复“888”之后私信回复“888”&#xff0c;全部无偿共享给大家&#xff01;&#xff01;&#xf…

【InternLM 实战营笔记】LMDeploy 的量化和部署

环境配置 vgpu-smi 查看显卡资源使用情况 新开一个终端执行下面的命令实时观察 GPU 资源的使用情况。 watch vgpu-smi复制环境到我们自己的 conda 环境 /root/share/install_conda_env_internlm_base.sh lmdeploy激活环境 conda activate lmdeploy安装依赖库 # 解决 Modu…

深度测试:指定DoC ID对ES写入性能的影响

在[[使用python批量写入ES索引数据]]中已经介绍了如何批量写入ES数据。基于该流程实际测试一下指定文档ID对ES性能的影响有多大。 一句话版 指定ID比不指定ID的性能下降了63%&#xff0c;且加剧趋势。 以下是测评验证的细节。 百万数据量 索引默认使用1分片和1副本。 指定…

JVM(3)

垃圾回收(GC)相关 在C/C中,当我们使用类似于malloc的内存开辟,还需要手动释放内存空间,这样的机制在使用时给我们造成了诸多不便,但在Java中,有垃圾回收这样的机制,这就是指:我们不再需要手动释放,程序会自动判定,某个内存空间是否可以继续使用,如果内存不使用了,就会自动释放…

Hack The Box-Fawn

目录 TASK 1 TASK 2 TASK 3 TASK 4 TASK 5 TASK 6 TASK 7 TASK 8 TASK 9 TASK 10 TASK 11 SUBMIT FLAG TASK 1 What does the 3-letter acronym FTP stand for?File Transfer Protocol (文件传输协议 FTP)TASK 2 Which port does the FTP service listen on usual…

腾讯云优惠券领取入口、云服务器优惠、领取方法及使用教程

腾讯云服务器多少钱一年&#xff1f;62元一年起&#xff0c;2核2G3M配置&#xff0c;腾讯云2核4G5M轻量应用服务器218元一年、756元3年&#xff0c;4核16G12M服务器32元1个月、312元一年&#xff0c;8核32G22M服务器115元1个月、345元3个月&#xff0c;腾讯云服务器网txyfwq.co…