什么是Apn
Apn,Access Point Name,接入点名称,是手机上网必须要配置的一个参数,他决定了手机通过什么方式访问哪种网络环境。对于手机用户来讲,可以访问的网络类型有英特网,WAP网络,集团企业内部网络。而WAP网络估计现在已经被遗忘的差不多了,WAP是专门针对早期性能比较差的手机设计的精简版的网络协议,看下图相信大家就会有所记忆,尤其是80,90后,随着智能手机的发展,由于WAP不能满足智能手机强大的浏览器,所以很多WAP网站陆陆续续被关停。
移动手机默认两种CMWAP和CMNET,一些使用移动办公的大客户,通常会使用专用APN,其接入点随意定义,只要和该省运营商其他APN不冲突即可。
CMWAP也叫移动梦网,通过该接入点可接入一个比较大的移动私网,网内有大量的手机应用下载及资源访问。因为CMWAP不接入互联网,只接入移动运营商的私网,所以流量费用比较低廉。
CMNET也叫GPRS连接互联网,通常每个省的运营商会提供若干个Internet出口以供CMNET拨号用户使用。其流量费用较CMWAP要高一些。
目前国内销售的手机,如果是非智能机,通常已配置好CMWAP连接,智能机通常会配置CMWAP和CMNET连接。如需手动添加这些配置,请参考手机说明书。
代码设置Apn
private Uri APN_URI = Uri.parse("content://telephony/carriers");
private Uri CURRENT_APN_URI = Uri.parse("content://telephony/carriers/preferapn");
//新增Apn节点
private int addApn(Context context, String apnName) {
int id = -1;
String simInfo = getSimInfo(context);
Log.e("SetApnReceiver", "simInfo " + simInfo);
if (TextUtils.isEmpty(simInfo)) {
return -1;
}
ContentResolver resolver = context.getContentResolver();
ContentValues values = new ContentValues();
//apn中文描述
values.put("name", apnName);
//apn名称
values.put("apn", apnName);
//apn类型
values.put("type", "default");
values.put("numeric", simInfo);
values.put("mcc", simInfo.substring(0, 3));
values.put("mnc", simInfo.substring(3, 5));
//代理
values.put("proxy", "");
//端口
values.put("port", "");
//彩信代理
values.put("mmsproxy", "");
//彩信端口
values.put("mmsport", "");
//用户名
values.put("user", "");
//服务器
values.put("server", "");
//密码
values.put("password", "");
//MMSC
values.put("mmsc", "");
Cursor c = null;
Uri newRow = resolver.insert(APN_URI, values);
if (newRow != null) {
c = resolver.query(newRow, null, null, null, null);
int idIndex = c.getColumnIndex("_id");
c.moveToFirst();
id = c.getShort(idIndex);
}
if (c != null) {
c.close();
}
return id;
}
//获取SIM卡的IMSI码,由MCC、MNC、MSIN组成
//网上很多人使用的是getSimOperator()方法,但是本人使用时获取为空,
//所以使用getSubscriberId()方法
@SuppressLint("MissingPermission")
public static String getSimInfo(Context context)
//
TelephonyManager iPhoneManager = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
return iPhoneManager.getSubscriberId();
}
// 设置接入点
public void setAPN(Context context, int id) {
ContentResolver resolver = context.getContentResolver();
ContentValues values = new ContentValues();
values.put("apn_id", id);
resolver.update(CURRENT_APN_URI, values, null, null);
}
//获取apn的id
public int getAPN(Context context, String apnName) {
ContentResolver resolver = context.getContentResolver();
Cursor c = resolver.query(APN_URI, new String[]{"_id", "name",
"apn"}, "apn like '%" + apnName + "%'", null, null);
// 该项APN存在
if (c != null && c.moveToNext()) {
int id = c.getShort(c.getColumnIndex("_id"));
String name = c.getString(c.getColumnIndex("name"));
String apn = c.getString(c.getColumnIndex("apn"));
Log.e("SetApnReceiver", "APN has exist " + id + name + apn);
return id;
} else {
Log.e("SetApnReceiver", "APN has not exist ");
}
return -1;
}
//获取当前Apn
public int getCurrentAPN(Context context) {
ContentResolver resolver = context.getContentResolver();
Cursor c = resolver.query(CURRENT_APN_URI, null, null, null, null);
// 该项APN存在
if (c != null && c.moveToNext()) {
int id = c.getShort(c.getColumnIndex("_id"));
String name = c.getString(c.getColumnIndex("name"));
String apn = c.getString(c.getColumnIndex("apn"));
String user = c.getString(c.getColumnIndex("user"));
String pass = c.getString(c.getColumnIndex("password"));
Log.e("SetApnReceiver", "current APN " + id + name + apn);
Log.e("SetApnReceiver", "current APN " + user + pass);
return id;
} else {
Log.e("SetApnReceiver", "current APN is null");
}
return -1;
}
使用如下
int id = getAPN(context, apnName);
//如果在apn列表中存在则直接设置
if (id == -1) {
id = addApn(context, apnName);
}
setAPN(context, id);
需要开启权限
<!-- 开关APN的权限 -->
<uses-permission android:name="android.permission.WRITE_APN_SETTINGS" />
注意
1.设置Apn的对象是手机(或者其他android终端设备)系统,而不是4G卡,系统中/system/etc路径下apns-conf.xml文件记录了大量详细的国内apn节点,也就是说getAPN()方法里查询到的apn节点内容也是来自这里。
2.如果用户使用自己专用的APN节点不存在设备系统中,则手机卡插入设备中不能访问该节点网络。
3.MCC=移动国家号码,由3位数字组成,唯一地识别移动用户所属的国家,我国为460。
MNC=移动网号,一般大多由2位数字组成,中国移动的是00或02,中国联通的是01。
运营商号码就是MCC+MNC
46000, “CHINA MOBILE”, “CN” 中国移动
46001, “CHN-CUGSM”, “CN” 中国联通
46002, “CHINA MOBILE”, “CN” 中国移动