android - 如何设置接收器以在 SMS 应用程序中获取“已发送”和“已交付”报告(应用程序设置为默认应用程序)
问题描述
我目前正在使用一项服务来获取 SMS 的发送和发送报告。我想知道如何设置接收器,这样我就可以在没有任何前台服务的情况下获得“交付”和“发送”报告。我的应用程序设置为默认应用程序,如果需要更多详细信息,请告诉我。
我一直在寻找解决方案很长时间,但没有得到任何线索,任何见解都将受到高度欢迎!
谢谢!
public class SendMySMS extends Service {
int count = 0;
public static final String PRIMARY_NOTIF_CHANNEL = "default";
public static final int PRIMARY_FOREGROUND_NOTIF_SERVICE_ID = 1009;
BroadcastReceiver sendReceiver;
BroadcastReceiver deliveryReceiver;
@Override
public IBinder onBind(Intent intent) {
return null;
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
super.onStartCommand(intent, flags, startId);
if (intent!=null) {
String str_number = intent.getStringExtra("KEY_number");
String str_body = intent.getStringExtra("KEY_body");
String str_subId = intent.getStringExtra("KEY_sub_id");
sendSMS(str_number, str_body, str_subId);
}
return START_STICKY;
}
@Override
public void onCreate() {
super.onCreate();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
NotificationChannel chan1 = new NotificationChannel(PRIMARY_NOTIF_CHANNEL, "Background", NotificationManager.IMPORTANCE_NONE);
chan1.setLightColor(Color.TRANSPARENT);
chan1.setLockscreenVisibility(Notification.VISIBILITY_SECRET);
notificationManager.createNotificationChannel(chan1);
Intent intent1 = new Intent(this, MainActivity.class);
intent1.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent1, PendingIntent.FLAG_UPDATE_CURRENT);
Notification notification = new NotificationCompat.Builder(this, PRIMARY_NOTIF_CHANNEL)
.setSmallIcon(R.drawable.ic_sms_notif)
.setContentTitle("Waiting for delivery report..")
.setPriority(NotificationCompat.PRIORITY_MIN)
.setAutoCancel(true)
.build();
startForeground(PRIMARY_FOREGROUND_NOTIF_SERVICE_ID, notification);
}
}
@Override
public void onDestroy() {
try {
unregisterReceiver(sendReceiver);
unregisterReceiver(deliveryReceiver);
} catch (Exception e) {
e.printStackTrace();
}
}
public void sendSMS(final String mobNo, String message, String subId) {
sendReceiver = new SendReceiver();
deliveryReceiver = new DeliveryReceiver();
String smsSent = "SMS_SENT"+msgId;
String smsDelivered = "SMS_DELIVERED"+msgId;
Intent sentIntent = new Intent(smsSent);
sentIntent.addFlags(Intent.FLAG_INCLUDE_STOPPED_PACKAGES);
sentIntent.putExtra("key_msg_id", msgId);
sentIntent.putExtra("key_number", mobNo);
PendingIntent sentPI = PendingIntent.getBroadcast(this, 0, sentIntent, PendingIntent.FLAG_ONE_SHOT);
Intent deliveryIntent = new Intent(smsDelivered);
deliveryIntent.addFlags(Intent.FLAG_INCLUDE_STOPPED_PACKAGES);
deliveryIntent.putExtra("key_msg_id", msgId);
deliveryIntent.putExtra("key_number", mobNo);
PendingIntent deliveredPI = PendingIntent.getBroadcast(this, 0, deliveryIntent, PendingIntent.FLAG_ONE_SHOT);
registerReceiver(sendReceiver, new IntentFilter(smsSent));
registerReceiver(deliveryReceiver, new IntentFilter(smsDelivered));
SmsManager.getSmsManagerForSubscriptionId(Integer.parseInt(subId)).sendTextMessage(mobNo, null, message, sentPI, deliveredPI);
}
class SendReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context arg0, Intent arg1) {
Bundle bundle = arg1.getExtras();
String msgId1="";
String number="";
if (bundle!=null) {
msgId1 = bundle.getString("key_msg_id");
number = bundle.getString("key_number");
}
switch (getResultCode()) {
case Activity.RESULT_OK:
Toast.makeText(getBaseContext(), "SMS sent", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_GENERIC_FAILURE:
Toast.makeText(getBaseContext(), "Generic failure", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_NO_SERVICE:
Toast.makeText(getBaseContext(), "No service", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_NULL_PDU:
Toast.makeText(getBaseContext(), "Null PDU", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_RADIO_OFF:
Toast.makeText(getBaseContext(), "Radio off", Toast.LENGTH_LONG).show();
break;
default:
Toast.makeText(getBaseContext(), "Unknown-"+getResultCode(), Toast.LENGTH_LONG).show();
}
}
}
class DeliveryReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context arg0, Intent arg1) {
Bundle bundle = arg1.getExtras();
String msgId1="";
String number="";
if (bundle!=null) {
msgId1 = bundle.getString("key_msg_id");
number = bundle.getString("key_number");
}
switch (getResultCode()) {
case Activity.RESULT_OK:
Toast.makeText(getBaseContext(), "SMS delivered", Toast.LENGTH_LONG).show();
count--;
if (count==0){
stopSelf();
}
break;
case Activity.RESULT_CANCELED:
Toast.makeText(getBaseContext(), "SMS not delivered", Toast.LENGTH_LONG).show();
count--;
if (count==0){
stopSelf();
}
break;
default:
Toast.makeText(getBaseContext(), "SMS not delivered", Toast.LENGTH_LONG).show();
count--;
if (count==0){
stopSelf();
}
break;
}
}
}
}
解决方案
我在区分两个单独的 SMS 的交付报告中找到了解决方案......下面是完整的工作代码供参考。
public class SendMySMS extends Service {
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
super.onStartCommand(intent, flags, startId);
if (intent!=null) {
String str_number = intent.getStringExtra("KEY_number");
String str_body = intent.getStringExtra("KEY_body");
String str_subId = intent.getStringExtra("KEY_sub_id");
sendSMS(str_number, str_body, str_subId);
}
return START_STICKY;
}
public void sendSMS(final String mobNo, String message, String subId) {
long tsLong = System.currentTimeMillis();
String ts = Long.toString(tsLong);
ContentValues values = new ContentValues();
values.put("address", mobNo);
values.put("body", message);
values.put("sub_id", subId);
values.put("date_sent", ts);
values.put("status", "-1");
values.put("error_code", "2");
getApplicationContext().getContentResolver().insert(Uri.parse("content://sms/sent"), values);
String msgId="";
String[] reqCols = new String[] {"_id", "address", "date_sent"};
Uri uriMsg = Uri.parse(String.valueOf(Telephony.Sms.CONTENT_URI));
ContentResolver cr = this.getContentResolver();
Cursor c = cr.query(uriMsg, reqCols, null, null, null);
assert c != null;
int totalSMS = Math.min(c.getCount(), 10);
if (c.moveToFirst()) {
for (int i=0; i<totalSMS; i++) {
if (c.getString(c.getColumnIndexOrThrow("date_sent")).equals(ts) && c.getString(c.getColumnIndexOrThrow("address")).equals(mobNo)) {
msgId = c.getString(0);
break;
}else{
msgId="not_found";
}
c.moveToNext();
}
}
c.close();
String smsSent = "SMS_SENT"+msgId;
String smsDelivered = "SMS_DELIVERED"+msgId;
Intent sentIntent = new Intent(getBaseContext(), SendReceiver.class);
sentIntent.setAction(smsSent);
sentIntent.putExtra("key_msg_id", msgId);
sentIntent.putExtra("key_number", mobNo);
PendingIntent sentPI = PendingIntent.getBroadcast(this, 0, sentIntent, PendingIntent.FLAG_ONE_SHOT);
Intent deliveryIntent = new Intent(getBaseContext(), DeliveredReceiver.class);
deliveryIntent.setAction(smsDelivered);
deliveryIntent.putExtra("key_msg_id", msgId);
deliveryIntent.putExtra("key_number", mobNo);
PendingIntent deliveredPI = PendingIntent.getBroadcast(this, 0, deliveryIntent, PendingIntent.FLAG_ONE_SHOT);
SmsManager.getSmsManagerForSubscriptionId(Integer.parseInt(subId)).sendTextMessage(mobNo, null, message, sentPI, deliveredPI);
}
}
接收器:
public class SendReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context arg0, Intent arg1) {
Bundle bundle = arg1.getExtras();
String msgId1="";
String number="";
if (bundle!=null) {
msgId1 = bundle.getString("key_msg_id");
number = bundle.getString("key_number");
}
switch (getResultCode()) {
case Activity.RESULT_OK://-1
Toast.makeText(arg0, "SMS sent", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_GENERIC_FAILURE: //1
Toast.makeText(arg0, "Generic failure", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_NO_SERVICE://4
Toast.makeText(arg0, "No service", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_NULL_PDU://3
Toast.makeText(arg0, "Null PDU", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_RADIO_OFF://2
Toast.makeText(arg0, "Radio off", Toast.LENGTH_LONG).show();
break;
case SmsManager.RESULT_ERROR_SHORT_CODE_NEVER_ALLOWED://8
case SmsManager.RESULT_ERROR_SHORT_CODE_NOT_ALLOWED://7
Toast.makeText(arg0, "Can't send to Short code", Toast.LENGTH_LONG).show();
break;
case 17:
Toast.makeText(arg0, "No balance!", Toast.LENGTH_LONG).show();
break;
default:
}
}
}
public class DeliveredReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context arg0, Intent arg1) {
Bundle bundle = arg1.getExtras();
String msgId1="";
String number="";
if (bundle!=null) {
msgId1 = bundle.getString("key_msg_id");
number = bundle.getString("key_number");
Object pdu = Objects.requireNonNull(arg1.getExtras()).get("pdu");
SmsMessage message = SmsMessage.createFromPdu((byte[]) pdu);
int status = message.getStatus();
if (status!=0) {
Toast.makeText(arg0, "SMS not delivered", Toast.LENGTH_LONG).show();
return;
}
}
switch (getResultCode()) {
case Activity.RESULT_OK:
Toast.makeText(arg0, "SMS delivered", Toast.LENGTH_LONG).show();
break;
case Activity.RESULT_CANCELED:
Toast.makeText(arg0, "SMS not delivered", Toast.LENGTH_LONG).show();
break;
default:
Toast.makeText(arg0, "SMS not delivered (Error-100)", Toast.LENGTH_LONG).show();
break;
}
}
}
显现:
<receiver android:name=".SendReceiver" />
<receiver android:name=".DeliveredReceiver" />
推荐阅读
- php - PHP中的光标分页与列
- dojo - 如何知道执行了特定的行?
- javascript - jQuery KendoEditor 不剥离粘贴的 HTML
- java - 如何使用intellij进行远程调试?
- twilio-api - 如何在 Ballerina 的 Twilio-Connector 中修复 404“请求的资源 /2010-04-01/Accounts//SMS/Messages.json”错误
- tensorflow - 为什么 tensorflow 会抛出“无法按拓扑顺序对图形进行排序”?
- javascript - 日期时间选择器显示在模态 jquery-confirm 模态后面
- hashicorp-vault - 如何在我的 curl 请求中使用存储在harsicorp 中的秘密
- string - groovy 脚本列表包含字符串值
- oauth-2.0 - 客户端如何根据用户请求两个不同的范围?这有意义吗?打开 Id Connect // 身份服务器 4