我們現在做的項目,移動端和pc端網站通路的是同一套接口,那麼如何在接口中區分是手機通路還是pc短通路呢?
核心思想:根據請求頭(request header)來判斷,如何請求沒有header或僞造user agent則無法判斷.
先看一些user agent的執行個體:
mozilla/5.0 (windows nt 6.1; wow64; rv:35.0) gecko/20100101 firefox/35.0
mozilla/5.0 (iphone; cpu iphone os 8_1_2 like mac os x) applewebkit/600.1.4 (khtml, like gecko) (engine, like url) mobile/12b440 micromessenger/6.0.1 nettype/3g+
mozilla/5.0 (linux; u; android 4.2.2; zh-cn; 2013023 build/hm2013023) applewebkit/533.1 (khtml, like gecko) version/4.0 ucbrowser/9.9.5.489 u3/0.8.0 mobile safari/533.1
opera/9.80 (android 2.3.7; linux; opera mobi/46154) presto/2.11.355 version/12.10
mozilla/5.0 (linux; u; android 4.2.1; zh-cn; huawei g700-u00 build/huaweig700-u00) applewebkit/534.30 (khtml, like gecko) version/4.0 mobile safari/534.30 v1_and_sq_5.3.1_196_yyb_d qq/5.3.1.2335 nettype/wifi
mozilla/5.0 (linux; u; android 4.0.4; zh-cn; hs-eg906 build/imm76d) applewebkit/534.30 (khtml, like gecko) version/4.0 mobile safari/534.30 micromessenger/5.3.1.67_r745169.462
mozilla/5.0 (linux; u; android 4.4.2; zh-cn; gt-i9500 build/kot49h) applewebkit/537.36 (khtml, like gecko)version/4.0 mqqbrowser/5.0 qq-manager mobile safari/537.36

以下是我封裝的一套方法
clientosinfo 是用于儲存通路裝置資訊的,結構如下(省略getter,setter):
public class clientosinfo {
/***
* 比如 android_3.0
*/
private string ostypeversion;
* pad或phone
private string devicetype;
* os type
private string ostype;
* 隻是版本号,例如"4.1.1"
private string version;
private string useragent;
/***
* 是否是移動裝置
* @return
public boolean ismobile(){
return (!valuewidget.isnullorempty(this.devicetype));
}
}
核心方法:
* 當移動端(手機或pad)通路網頁時擷取移動端作業系統資訊
* @param request
* @return
*/
public static clientosinfo getmobileosinfo(httpservletrequest request){
string useragent=request.getheader("user-agent");
if(valuewidget.isnullorempty(useragent)){
useragent=request.getheader("user-agent");
clientosinfo info= headerutil.getmobilos(useragent);
info.setuseragent(useragent);
return info;
核心工具類:用于解析user agent
package com.common.util;
import java.util.regex.matcher;
import java.util.regex.pattern;
import com.common.bean.clientosinfo;
import com.string.widget.util.valuewidget;
*
* @author huangwei
* @since 2013-08-15
public class headerutil {
public static final string ostype_android="android";
public static final string ostype_ios="ios";
public static final string ostype_wp="windows phone";
public static final string ostype_blackberry="blackberry";
* pad
public static final string device_type_pad="pad";
* 手機
public static final string device_type_phone="phone";
* 校驗管道終端版本号是否合法,eg:0.0.0.3
*
* @param clientversion
* @return true-->合法 ;false-->非法
public static boolean verifyclientversion(string clientversion) {
boolean result = pattern.matches("[\\d\\.]+", clientversion);
if (result) {
result = pattern.matches("^\\d\\.\\d\\.\\d\\.\\d$", clientversion);
return result;
} else {
return false;
}
/**
* 根據useragent和手機廠商查手機型号
* @param ua
* @param vendor
public static string getmobmodel(string ua, string operatingsystem) {
if (ua == null) {
return null;
// 存放正規表達式
string rex = "";
// 蘋果産品
if (operatingsystem.indexof("ios") != -1) {
if (ua.indexof("ipad") != -1) {// 判斷是否為ipad
return "ipad";
}
if (ua.indexof("ipod") != -1) {// 判斷是否為ipod
return "ipod";
if (ua.indexof("ipone") != -1) {// 判斷是否為ipone
return "ipone";
return "ios device";
// 安卓系統産品
if (operatingsystem.indexof("android") != -1) {
string re = "build";
rex = ".*" + ";" + "(.*)" + re;
pattern p = pattern.compile(rex, pattern.case_insensitive);
matcher m = p.matcher(ua);
boolean rs = m.find();
if (rs) {
system.out.println("mobil model is" + m.group(1));
return m.group(1);
return null;
* 判斷手機的作業系統 ios/android/windows phone/blackberry
public static clientosinfo getmobilos(string ua) {
ua=ua.touppercase();
clientosinfo osinfo=new clientosinfo();
// ios 判斷字元串
string iosstring = " like mac os x";
if (ua.indexof(iosstring) != -1) {
if(ismatch(ua, "\\([\\s]*iphone[\\s]*;", pattern.case_insensitive)){
osinfo.setdevicetype(device_type_phone);
}else if(ismatch(ua, "\\([\\s]*ipad[\\s]*;", pattern.case_insensitive)){
osinfo.setdevicetype(device_type_pad);
rex = ".*" + "[\\s]+(\\d[_\\d]*)" + iosstring;
string osversion= m.group(1).replace("_", ".");
osinfo.setversion(osversion);
// system.out.println("mobil os is" + " ios" +osversion);
osinfo.setostypeversion(ostype_ios+"_" + osversion);
}else{
system.out.println("ios");
osinfo.setostypeversion(ostype_ios);
osinfo.setostype(ostype_ios);
return osinfo;
// android 判斷
string androidstring = "android";
if (ua.indexof(androidstring) != -1) {
if(ismatch(ua, "\\bmobi", pattern.case_insensitive)){
}else {
rex = ".*" + androidstring + "[\\s]*(\\d*[\\._\\d]*)";
string version=m.group(1).replace("_", ".");
osinfo.setversion(version);
system.out.println("mobil os is " + ostype_android + version);
osinfo.setostypeversion(ostype_android+"_" + version);
system.out.println("android");
osinfo.setostypeversion(ostype_android);
osinfo.setostype(ostype_android);
// windows phone 判斷
string wpstring = "windows phone";
if (ua.indexof(wpstring) != -1) {
rex = ".*" + wpstring + "[\\s]*[os\\s]*([\\d][\\.\\d]*)";
system.out.println("mobil os is " + ostype_wp + m.group(1));
string version=m.group(1);
osinfo.setostypeversion(ostype_wp+"_" + version);
system.out.println("windows phone");
osinfo.setostypeversion(ostype_wp);
osinfo.setostype(ostype_wp);
// blackberry 黑莓系統判斷
string bbstring = "blackberry";
if (ua.indexof(bbstring) != -1) {
rex = ".*" + bbstring + "[\\s]*([\\d]*)";
system.out.println("mobil os is" + " blackberry " + m.group(1));
osinfo.setostypeversion(ostype_blackberry+"_" + version);
system.out.println("blackberry");
osinfo.setostypeversion(ostype_blackberry);
osinfo.setostype(ostype_blackberry);
if(ua.contains("linux")){//android
pattern p = pattern.compile("u;\\s*(adr[\\s]*)?(\\d[\\.\\d]*\\d)[\\s]*;",pattern.case_insensitive);
matcher m = p.matcher(ua);
boolean result = m.find();
string find_result = null;
if (result)
{
find_result = m.group(2);
}
if(valuewidget.isnullorempty(find_result)){
osinfo.setostypeversion(ostype_android);
return osinfo;
}else{
osinfo.setversion(find_result);
osinfo.setostypeversion(ostype_android+"_"+find_result);
//ucweb/2.0 (ios; u; iph os 4_3_2; zh-cn; iph4)
if(ua.matches(".*((ios)|(ipad)).*(iph).*")){
if(ismatch(ua, "[\\s]*iph[\\s]*", pattern.case_insensitive)){
pattern p = pattern.compile("u;\\s*(iph[\\s]*)?(os[\\s]*)?(\\d[\\._\\d]*\\d)[\\s]*;",pattern.case_insensitive);
find_result = m.group(3);
osinfo.setostypeversion(ostype_ios);
osinfo.setostype(ostype_ios);
string version=find_result.replace("_", ".");
osinfo.setversion(version);
osinfo.setostypeversion(ostype_ios+"_"+version);
return osinfo;
public static boolean ismatch(string source,string regx,int flags){
pattern p = pattern.compile(regx,flags);
matcher m = p.matcher(source);
boolean result = m.find();
return result;
應用場景:
通過user agent判斷是否是手機
* 判斷是否是手機(移動端)
* @param useragent
public static boolean ismobile(string useragent)
{
useragent=useragent.tolowercase();
string []mobile_agents = {"240x320","acer","acoon","acs-","abacho","ahong","airness","alcatel","amoi","android","anywhereyougo.com","applewebkit/525","applewebkit/532","asus","audio","au-mic","avantogo","becker","benq","bilbo","bird","blackberry","blazer","bleu","cdm-","compal","coolpad","danger","dbtel","dopod","elaine","eric","etouch","fly ","fly_","fly-","go.web","goodaccess","gradiente","grundig","haier","hedy","hitachi","htc","huawei","hutchison","inno","ipad","ipaq","ipod","jbrowser","kddi","kgt","kwc","lenovo","lg ","lg2","lg3","lg4","lg5","lg7","lg8","lg9","lg-","lge-","lge9","longcos","maemo","mercator","meridian","micromax","midp","mini","mitsu","mmm","mmp","mobi","mot-","moto","nec-","netfront","newgen","nexian","nf-browser","nintendo","nitro","nokia","nook","novarra","obigo","palm","panasonic","pantech","philips","phone","pg-","playstation","pocket","pt-","qc-","qtek","rover","sagem","sama","samu","sanyo","samsung","sch-","scooter","sec-","sendo","sgh-","sharp","siemens","sie-","softbank","sony","spice","sprint","spv","symbian","tablet","talkabout","tcl-","teleca","telit","tianyu","tim-","toshiba","tsm","up.browser","utec","utstar","verykool","virgin","vk-","voda","voxtel","vx","wap","wellco","wig browser","wii","windows ce","wireless","xda","xde","zte"};
boolean is_mobile = false;
for (string device : mobile_agents) {
if(useragent.contains(device)){
is_mobile=true;
break;
return is_mobile;
測試代碼:
@test
public void test_useragent()
string useragent="mozilla/5.0 (linux; u; android 4.1.1; en-cn; htc t528d) applewebkit/534.30 (khtml, like gecko) version/4.0 mobile safari/534.30 micromessenger/6.0.2.58_r984381.520 nettype/wifi";
system.out.println(headerutil.ismobile(useragent));
useragent="opera/9.80 (android 2.3.7; linux; opera mobi/46154) presto/2.11.355 version/12.10";
}