设为首页 收藏本站
查看: 1125|回复: 0

[经验分享] JAVA获取客户端IP地址和MAC地址

[复制链接]

尚未签到

发表于 2017-7-6 09:21:40 | 显示全部楼层 |阅读模式
  1.获取客户端IP地址



public String getIp(HttpServletRequest request) throws Exception {
String ip = request.getHeader("X-Forwarded-For");
if (ip != null) {
if (!ip.isEmpty() && !"unKnown".equalsIgnoreCase(ip)) {
int index = ip.indexOf(",");
if (index != -1) {
return ip.substring(0, index);
} else {
return ip;
}
}
}
ip = request.getHeader("X-Real-IP");
if (ip != null) {
if (!ip.isEmpty() && !"unKnown".equalsIgnoreCase(ip)) {
return ip;
}
}
return request.getRemoteAddr();
}
  为什么不直接使用request.getRemoteAddr();而要在之前判断两个请求头"X-Forwarded-For"和"X-Real-IP"


X-Forwarded-For: client1, proxy1, proxy2, proxy3  其中的值通过一个 逗号+空格 把多个IP地址区分开, 最左边(client1)是最原始客户端的IP地址, 代理服务器每成功收到一个请求,就把请求来源IP地址添加到右边。
  所有我们只取第一个IP地址
  X-Real-IP,一般只记录真实发出请求的客户端IP
  解决用localhost访问ip为0:0:0:0:0:0:0:1的问题



public String getIp(HttpServletRequest request) throws Exception {
String ip = request.getHeader("X-Forwarded-For");
if (ip != null) {
if (!ip.isEmpty() && !"unKnown".equalsIgnoreCase(ip)) {
int index = ip.indexOf(",");
if (index != -1) {
return ip.substring(0, index);
} else {
return ip;
}
}
}
ip = request.getHeader("X-Real-IP");
if (ip != null) {
if (!ip.isEmpty() && !"unKnown".equalsIgnoreCase(ip)) {
return ip;
}
}
ip = request.getHeader("Proxy-Client-IP");
if (ip != null) {
if (!ip.isEmpty() && !"unKnown".equalsIgnoreCase(ip)) {
return ip;
}
}
ip = request.getHeader("WL-Proxy-Client-IP");
if (ip != null) {
if (!ip.isEmpty() && !"unKnown".equalsIgnoreCase(ip)) {
return ip;
}
}
ip =  request.getRemoteAddr();
return ip.equals("0:0:0:0:0:0:0:1") ? "127.0.0.1" : ip;
}
  2.获取客户端MAC地址



UdpGetClientMacAddr umac = new UdpGetClientMacAddr(sip);
String smac = umac.GetRemoteMacAddr();
  添加一个获取MAC的时间限制



final UdpGetClientMacAddr umac = new UdpGetClientMacAddr(sip);
//---长时间获取不到MAC地址则放弃
ExecutorService exec = Executors.newFixedThreadPool(1);
Callable<String> call = new Callable<String>() {
public String call() throws Exception {
return umac.GetRemoteMacAddr();
}
};
try {
Future<String> future = exec.submit(call);
String smac = future.get(1000 * 1, TimeUnit.MILLISECONDS);
loginMonitor.setMacAddress(smac);
} catch (TimeoutException ex) {
loginMonitor.setMacAddress("获取失败");
logger.info("获取MAC地址超时");
ex.printStackTrace();
}
// 关闭线程池  
exec.shutdown();
//---
  需要先获取IP地址作为参数构造一个UdpGetClientMacAddr
  UdpGetClientMacAddr.java



package shmc.commonsys.security.controller;
import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;

/**
* 主机A向主机B发送“UDP-NetBIOS-NS”询问包,即向主机B的137端口,发Query包来询问主机B的NetBIOS Names信息。
* 其次,主机B接收到“UDP-NetBIOS-NS”询问包,假设主机B正确安装了NetBIOS服务........... 而且137端口开放,则主机B会向主机A发送一个“UDP-NetBIOS-NS”应答包,即发Answer包给主机A。
* 并利用UDP(NetBIOS Name Service)来快速获取远程主机MAC地址的方法
*  
*/  
public class UdpGetClientMacAddr {  
private String sRemoteAddr;  
private int iRemotePort=137;  
private byte[] buffer = new byte[1024];  
private DatagramSocket ds=null;  
public UdpGetClientMacAddr(String strAddr) throws Exception{  
sRemoteAddr = strAddr;  
ds = new DatagramSocket();  
}  
public final DatagramPacket send(final byte[] bytes) throws IOException {  
DatagramPacket dp = new DatagramPacket(bytes,bytes.length,InetAddress.getByName(sRemoteAddr),iRemotePort);  
ds.send(dp);  
return dp;  
}  
public final DatagramPacket receive() throws Exception {  
DatagramPacket dp = new DatagramPacket(buffer,buffer.length);  
ds.receive(dp);  
return dp;  
}  
public byte[] GetQueryCmd() throws Exception {  
byte[] t_ns = new byte[50];  
t_ns[0] = 0x00;  
t_ns[1] = 0x00;  
t_ns[2] = 0x00;  
t_ns[3] = 0x10;  
t_ns[4] = 0x00;  
t_ns[5] = 0x01;  
t_ns[6] = 0x00;  
t_ns[7] = 0x00;  
t_ns[8] = 0x00;  
t_ns[9] = 0x00;  
t_ns[10] = 0x00;  
t_ns[11] = 0x00;  
t_ns[12] = 0x20;  
t_ns[13] = 0x43;  
t_ns[14] = 0x4B;  
for(int i = 15; i < 45; i++){  
t_ns = 0x41;  
}  
t_ns[45] = 0x00;  
t_ns[46] = 0x00;  
t_ns[47] = 0x21;  
t_ns[48] = 0x00;  
t_ns[49] = 0x01;  
return t_ns;  
}  
public final String GetMacAddr(byte[] brevdata) throws Exception {  
// 获取计算机名  
int i = brevdata[56] * 18 + 56;  
String sAddr="";  
StringBuffer sb = new StringBuffer(17);  
// 先从第56字节位置,读出Number Of Names(NetBIOS名字的个数,其中每个NetBIOS Names Info部分占18个字节)  
// 然后可计算出“Unit ID”字段的位置=56+Number Of Names×18,最后从该位置起连续读取6个字节,就是目的主机的MAC地址。  
for(int j = 1; j < 7;j++)  
{  
sAddr = Integer.toHexString(0xFF & brevdata[i+j]);  
if(sAddr.length() < 2)  
{  
sb.append(0);  
}  
sb.append(sAddr.toUpperCase());  
if(j < 6) sb.append(':');  
}  
return sb.toString();  
}  
public final void close() throws Exception {  
ds.close();  
}  
public final String GetRemoteMacAddr() throws Exception {  
byte[] bqcmd = GetQueryCmd();  
send(bqcmd);  
DatagramPacket dp = receive();  
String smac = GetMacAddr(dp.getData());  
close();  
return smac;  
}  
public static void main(String args[]) throws Exception{  
UdpGetClientMacAddr umac=new UdpGetClientMacAddr("172.19.1.198");  
umac=new UdpGetClientMacAddr("192.168.16.83");  
System.out.println(umac.GetRemoteMacAddr());  
}  
}

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-390964-1-1.html 上篇帖子: Darren_聂微东 - 关注前端技术完成《前端攻略系列》仅仅是第一步... 下篇帖子: mac 上配置apache虚拟主机
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表