项目中获取IP和城市名称
在项目实际开发中,获取当前客户端的ip和城市名称这种需求,已经是很普遍的。我这里总结一下,我是如何处理的
1. 前端
相信大家在百度可以搜到很多开源的第三方的获取ip地址和城市名称的api
或者js
脚本,因此,也会有很多的方式去获取这个结果并使用
1.1 原生h5
中的使用方式 (这里使用搜狗的做案例)
//引用js脚本文件
<script src="http://pv.sohu.com/cityjson?ie=utf-8"></script>
//获取其中的参数
<script>
console.log(returnCitySN.cname);
console.log(JSON.stringify(returnCitySN));
// {"cip":"112.192.209.176","cid":"510800","cname":"四川省广元市"}
</script>
1.2 vue
中的使用 (这种方式有点不优雅,大家可以补充其它更好的方式)
将第三方的js
脚本文件当作api
的方式去调用,需要注意的是,调用第三方api很可能出现跨域问题,跨域问题
1、 这里使用代理的方式解决跨域,在项目根目录创建vue.config.js
文件
devServer: {
proxy: {
'/getIpName': {
target: 'http://pv.sohu.com/cityjson',//搜狐的域名
ws: true,
changOrigin: true,//允许跨域
pathRewrite: {
'^/getIpName': ''//请求的时候使用这个api就可以
}
},
},
},
1、 调用服务
this.$axios.get("/getIpName").then(res =>{
let result = res.data;
let location = result.substring(result.indexOf("{"), result.indexOf("}") +1 );
let json = JSON.parse(location)
this.loginLocation = json.cname
})
效果如下
1. 后端提供接口,前端直接调用
1、 获取ip地址和名称的工具类 (通过ip获取地址的第三方接口有调用次数,免费三次 ^-^,有点坑)
public class GetRealIp
{
/**
* 获取当前用户的ip
* @param request
* @return
*/
public static String getIpaddr(HttpServletRequest request){
String ipAddress = request.getHeader("x-forwarded-for");
if(ipAddress == null || ipAddress.length() ==0 || "unknown".equals(ipAddress)){
ipAddress = request.getHeader("Proxy-Client-IP");
}
if(ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
ipAddress = request.getHeader("WL-Proxy-Client-IP");
}
if (StringUtils.isEmpty(ipAddress) || "unknown".equalsIgnoreCase(ipAddress)) {
ipAddress = request.getHeader("HTTP_CLIENT_IP");
}
if (StringUtils.isEmpty(ipAddress) || "unknown".equalsIgnoreCase(ipAddress)) {
ipAddress = request.getHeader("HTTP_X_FORWARDED_FOR");
}
if(ipAddress == null || ipAddress.length() == 0 || "unknown".equalsIgnoreCase(ipAddress)) {
ipAddress = request.getRemoteAddr();
if(ipAddress.equals("127.0.0.1") || ipAddress.equals("0:0:0:0:0:0:0:1")){
//根据网卡取本机配置的IP
InetAddress inet=null;
try {
inet = InetAddress.getLocalHost();
} catch (UnknownHostException e) {
e.printStackTrace();
}
ipAddress= inet.getHostAddress();
}
}
//对于通过多个代理的情况,第一个IP为客户端真实IP,多个IP按照','分割
if(ipAddress!=null && ipAddress.length()>15){ //"***.***.***.***".length() = 15
if(ipAddress.indexOf(",")>0){
ipAddress = ipAddress.substring(0,ipAddress.indexOf(","));
}
}
return ipAddress;
}
/**
* 通过ip 获取地址
* @param ip
* 根据IP地址获取详细的地域信息
* 淘宝API : http://ip.taobao.com/service/getIpInfo.php?ip=218.192.3.42
* 新浪API : http://int.dpool.sina.com.cn/iplookup/iplookup.php?format=json&ip=218.192.3.42
*
* @return
*/
public static String getAddress(String ip,String encodingString) throws UnsupportedEncodingException{
String urlStr = "http://ip.taobao.com/service/getIpInfo.php";
// 从http://whois.pconline.com.cn取得IP所在的省市区信息
String returnStr = getResult(urlStr, content, encodingString);
if (returnStr != null) {
// 处理返回的省市区信息
System.out.println("(1) unicode转换成中文前的returnStr : " + returnStr);
returnStr = decodeUnicode(returnStr);
System.out.println("(2) unicode转换成中文后的returnStr : " + returnStr);
String[] temp = returnStr.split(",");
if (temp.length < 3) {
return "0";//无效IP,局域网测试
}
return returnStr;
}
return null;
}
/**
* @param urlStr 请求的地址
* @param content 请求的参数 格式为:name=xxx&pwd=xxx
* @param encoding 服务器端请求编码。如GBK,UTF-8等
* @return
*/
private static String getResult(String urlStr, String content, String encoding) {
URL url = null;
HttpURLConnection connection = null;
try {
url = new URL(urlStr);
connection = (HttpURLConnection) url.openConnection();// 新建连接实例
connection.setConnectTimeout(8000);// 设置连接超时时间,单位毫秒
connection.setReadTimeout(8000);// 设置读取数据超时时间,单位毫秒
connection.setDoOutput(true);// 是否打开输出流 true|false
connection.setDoInput(true);// 是否打开输入流true|false
connection.setRequestMethod("POST");// 提交方法POST|GET
connection.setUseCaches(false);// 是否缓存true|false
connection.connect();// 打开连接端口
DataOutputStream out = new DataOutputStream(connection
.getOutputStream());// 打开输出流往对端服务器写数据
out.writeBytes(content);// 写数据,也就是提交你的表单 name=xxx&pwd=xxx
out.flush();// 刷新
out.close();// 关闭输出流
BufferedReader reader = new BufferedReader(new InputStreamReader(
connection.getInputStream(), encoding));// 往对端写完数据对端服务器返回数据
// ,以BufferedReader流来读取
StringBuffer buffer = new StringBuffer();
String line = "";
while ((line = reader.readLine()) != null) {
buffer.append(line);
}
reader.close();
return buffer.toString();
}
catch (IOException e) {
e.printStackTrace();
}
finally {
if (connection != null) {
connection.disconnect();// 关闭连接
}
}
return null;
}
/**
* unicode 转换成 中文
*
* @param theString
* @return
*/
public static String decodeUnicode(String theString) {
char aChar;
int len = theString.length();
StringBuffer outBuffer = new StringBuffer(len);
for (int x = 0; x < len; ) {
aChar = theString.charAt(x++);
if (aChar == '\\') {
aChar = theString.charAt(x++);
if (aChar == 'u') {
int value = 0;
for (int i = 0; i < 4; i++) {
aChar = theString.charAt(x++);
switch (aChar) {
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
value = (value << 4) + aChar - '0';
break;
case 'a':
case 'b':
case 'c':
case 'd':
case 'e':
case 'f':
value = (value << 4) + 10 + aChar - 'a';
break;
case 'A':
case 'B':
case 'C':
case 'D':
case 'E':
case 'F':
value = (value << 4) + 10 + aChar - 'A';
break;
default:
throw new IllegalArgumentException(
"Malformed encoding.");
}
}
outBuffer.append((char) value);
}
else {
if (aChar == 't') {
aChar = '\t';
}
else if (aChar == 'r') {
aChar = '\r';
}
else if (aChar == 'n') {
aChar = '\n';
}
else if (aChar == 'f') {
aChar = '\f';
}
outBuffer.append(aChar);
}
}
else {
outBuffer.append(aChar);
}
}
return outBuffer.toString();
}
}
1、 控制层调用测试
@RestController
@Api(tags = "IP地址相关")
@RequestMapping("/ip")
public class IPController {
@RequestMapping(value = "/getIp" ,method = RequestMethod.GET)
public String getRealIp(HttpServletRequest request){
String ip = GetRealIp.getIpaddr(request);
String ipName = GetRealIp.getAddress(ip);
return "当前访问用户的ip为:" + ip + "城市名称为: " + ipName;
}
}
版权声明: 本文为博主整理而来,并非原创,参考文件blog.csdn.net/qq_26898033…, 若有版权侵犯请告知!