日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 运维知识 > Android >内容正文

Android

Android短信发送流程之多收件人发送(原)

發(fā)布時間:2025/3/15 Android 23 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Android短信发送流程之多收件人发送(原) 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.
?? ? ? 前面的《 Android短信發(fā)送流程之長短信發(fā)送 》中介紹了長短信對于普通短信的區(qū)別,而對于多收件人的情況,在SmsMessageSender的queueMessage()方法中我們了解到,發(fā)送之前,將多收件人的短信進(jìn)行拆分,放入"content://sms/queued"隊列中,在接下來的流程中,將會在SmsReceiverService中通過sendFirstQueuedMessage()方法取出隊列中的第一條短信并發(fā)送,那么,隊列中的其他消息是如何被發(fā)送出去的呢?
? ? ? ? 我們從第一條短信發(fā)送完畢后的流程來尋找答案。
? ? ? ? 由于在GsmSMSDispatcher向RILJ發(fā)送消息時所注冊的回應(yīng)消息是EVENT_SEND_SMS_COMPLETE,所以當(dāng)短信發(fā)送成功時,就會收到該消息的回應(yīng)。
? ? ? ? 在SMSDispatcher中對該回應(yīng)進(jìn)行處理: [java]?view plaincopy
  • @SMSDispatcher.java??
  • public?void?handleMessage(Message?msg)?{??
  • ????switch?(msg.what)?{??
  • ????????case?EVENT_SEND_SMS_COMPLETE:??
  • ????????????//發(fā)送成功??
  • ????????????handleSendComplete((AsyncResult)?msg.obj);??
  • ????????????break;??
  • ????????default:??
  • ????????????Rlog.e(TAG,?"handleMessage()?ignoring?message?of?unexpected?type?"?+?msg.what);??
  • ????}??
  • }??
  • ? ? ? ? 然后進(jìn)入handleSendComplete()方法中處理: [java]?view plaincopy
  • protected?void?handleSendComplete(AsyncResult?ar)?{??
  • ????SmsTracker?tracker?=?(SmsTracker)?ar.userObj;??
  • ????PendingIntent?sentIntent?=?tracker.mSentIntent;??
  • ??
  • ??
  • ????if?(ar.result?!=?null)?{??
  • ????????tracker.mMessageRef?=?((SmsResponse)ar.result).mMessageRef;??
  • ????}?else?{??
  • ????}??
  • ??
  • ??
  • ????if?(ar.exception?==?null)?{??
  • ????????//發(fā)送成功??
  • ????????if?(tracker.mDeliveryIntent?!=?null)?{??
  • ????????????//將當(dāng)前短信的tracker保存??
  • ????????????deliveryPendingList.add(tracker);??
  • ????????}??
  • ????????//回調(diào)到SmsTracker內(nèi)部??
  • ????????tracker.onSent(mContext);??
  • ????}?else?{??
  • ????????//發(fā)送失敗??
  • ????}??
  • }??
  • ? ? ? ? 在上面的過程中,對短信發(fā)送的結(jié)果進(jìn)行區(qū)分,如果失敗,將會根據(jù)失敗原因通知SmsTracker,如果成功,將會進(jìn)入SmsTracker中繼續(xù)處理: [java]?view plaincopy
  • public?void?onSent(Context?context)?{??
  • ????boolean?isSinglePartOrLastPart?=?true;??
  • ????if?(mUnsentPartCount?!=?null)?{??
  • ????????//判斷是否已經(jīng)將長短新最后一條發(fā)送完畢??
  • ????????isSinglePartOrLastPart?=?mUnsentPartCount.decrementAndGet()?==?0;??
  • ????}??
  • ????if?(isSinglePartOrLastPart)?{??
  • ????????//當(dāng)前所有短信發(fā)送完畢,更新數(shù)據(jù)庫狀態(tài)??
  • ????????boolean?success?=?true;??
  • ????????if?(mAnyPartFailed?!=?null?&&?mAnyPartFailed.get())?{??
  • ????????????success?=?false;??
  • ????????}??
  • ????????if?(success)?{??
  • ????????????setMessageFinalState(context,?Sms.MESSAGE_TYPE_SENT);??
  • ????????}?else?{??
  • ????????????setMessageFinalState(context,?Sms.MESSAGE_TYPE_FAILED);??
  • ????????}??
  • ????}??
  • ????//把發(fā)送短信之前保存在SmsTracker中的Intent取出來發(fā)送出去,通知短信已經(jīng)發(fā)送成功。??
  • ????if?(mSentIntent?!=?null)?{??
  • ????????try?{??
  • ????????????//?Extra?information?to?send?with?the?sent?intent??
  • ????????????Intent?fillIn?=?new?Intent();??
  • ????????????if?(mMessageUri?!=?null)?{??
  • ????????????????//?Pass?this?to?SMS?apps?so?that?they?know?where?it?is?stored??
  • ????????????????fillIn.putExtra("uri",?mMessageUri.toString());??
  • ????????????}??
  • ????????????if?(mUnsentPartCount?!=?null?&&?isSinglePartOrLastPart)?{??
  • ????????????????//?Is?multipart?and?last?part??
  • ????????????????fillIn.putExtra(SEND_NEXT_MSG_EXTRA,?true);??
  • ????????????}??
  • ????????????mSentIntent.send(context,?Activity.RESULT_OK,?fillIn);??
  • ????????}?catch?(CanceledException?ex)?{??
  • ????????????Rlog.e(TAG,?"Failed?to?send?result");??
  • ????????}??
  • ????}??
  • }??
  • ? ? ? ? 由于此時無論是長短信還是普通短信,都已經(jīng)發(fā)送完畢(只發(fā)送了一個收件人),因此isSinglePartOrLastPart的判定將會是true,從而更新數(shù)據(jù)庫中該短信的狀態(tài),然后再將發(fā)送時附加在SmsTracker中的mSentIntent取出來并發(fā)送出去,同時指定返回結(jié)果為“Activity.RESULT_OK”。
    ? ? ? ? 而這里的mSentIntent就是在SmsSingleRecipientSender中指定的,我們再來回顧以下當(dāng)時的狀態(tài): [java]?view plaincopy
  • @SmsSingleRecipientSender.java??
  • public?boolean?sendMessage(long?token)?throws?MmsException?{??
  • ????if?(mMessageText?==?null)?{??
  • ????????throw?new?MmsException("Null?message?body?or?have?multiple?destinations.");??
  • ????}??
  • ????SmsManager?smsManager?=?SmsManager.getDefault();??
  • ????ArrayList<String>?messages?=?null;??
  • ????//拆分長短信??
  • ????if?((MmsConfig.getEmailGateway()?!=?null)?&&?(Mms.isEmailAddress(mDest)?||?MessageUtils.isAlias(mDest)))?{??
  • ????????//彩信??
  • ????????String?msgText;??
  • ????????msgText?=?mDest?+?"?"?+?mMessageText;??
  • ????????mDest?=?MmsConfig.getEmailGateway();??
  • ????????messages?=?smsManager.divideMessage(msgText);??
  • ????}?else?{??
  • ????????//短信??
  • ????????messages?=?smsManager.divideMessage(mMessageText);??
  • ????????mDest?=?PhoneNumberUtils.stripSeparators(mDest);??
  • ????????mDest?=?Conversation.verifySingleRecipient(mContext,?mThreadId,?mDest);??
  • ????}??
  • ????int?messageCount?=?messages.size();??
  • ??
  • ??
  • ????if?(messageCount?==?0)?{??
  • ????????throw?new?MmsException("SmsMessageSender.sendMessage:?divideMessage?returned?"?+?"empty?messages.?Original?message?is?\""?+?mMessageText?+?"\"");??
  • ????}??
  • ??
  • ??
  • ????boolean?moved?=?Sms.moveMessageToFolder(mContext,?mUri,?Sms.MESSAGE_TYPE_OUTBOX,?0);??
  • ????if?(!moved)?{??
  • ????????throw?new?MmsException("SmsMessageSender.sendMessage:?couldn't?move?message?"?+?"to?outbox:?"?+?mUri);??
  • ????}??
  • ????ArrayList<PendingIntent>?deliveryIntents?=??new?ArrayList<PendingIntent>(messageCount);??
  • ????ArrayList<PendingIntent>?sentIntents?=?new?ArrayList<PendingIntent>(messageCount);??
  • ????for?(int?i?=?0;?i?<?messageCount;?i++)?{??
  • ????????if?(mRequestDeliveryReport?&&?(i?==?(messageCount?-?1)))?{??
  • ????????????//所有短信被發(fā)送完畢后,在最后一條短信后面添加送達(dá)報告的Intent??
  • ????????????deliveryIntents.add(PendingIntent.getBroadcast(??
  • ????????????????????????mContext,?0,??
  • ????????????????????????new?Intent(??
  • ????????????????????????????MessageStatusReceiver.MESSAGE_STATUS_RECEIVED_ACTION,??
  • ????????????????????????????mUri,??
  • ????????????????????????????mContext,??
  • ????????????????????????????MessageStatusReceiver.class),??
  • ????????????????????????0));??
  • ????????}?else?{??
  • ????????????deliveryIntents.add(null);??
  • ????????}??
  • ????????//對于拆分后的短消息,需要在每條信息發(fā)送完畢后發(fā)送該Intent,從而接著發(fā)送剩下的拆分短信??
  • ????????Intent?intent??=?new?Intent(SmsReceiverService.MESSAGE_SENT_ACTION,??
  • ????????????????mUri,??
  • ????????????????mContext,??
  • ????????????????SmsReceiver.class);??
  • ??
  • ??
  • ????????int?requestCode?=?0;??
  • ????????if?(i?==?messageCount?-1)?{??
  • ????????????//收到該附加數(shù)據(jù)說明當(dāng)前的拆分短信已經(jīng)發(fā)送完畢??
  • ????????????requestCode?=?1;??
  • ????????????intent.putExtra(SmsReceiverService.EXTRA_MESSAGE_SENT_SEND_NEXT,?true);??
  • ????????}??
  • ????????sentIntents.add(PendingIntent.getBroadcast(mContext,?requestCode,?intent,?0));??
  • ????}??
  • ????try?{??
  • ????????//發(fā)送??
  • ????????smsManager.sendMultipartTextMessage(mDest,?mServiceCenter,?messages,?sentIntents,?deliveryIntents);??
  • ????}?catch?(Exception?ex)?{??
  • ????????throw?new?MmsException("SmsMessageSender.sendMessage:?caught?"?+?ex?+?"?from?SmsManager.sendTextMessage()");??
  • ????}??
  • ????return?false;??
  • }??
  • ? ? ? ? 從這里我們看到,當(dāng)前的mSentIntent發(fā)送對象是SmsReceiver,內(nèi)容是MESSAGE_SENT_ACTION,而且包含了附加數(shù)據(jù)EXTRA_MESSAGE_SENT_SEND_NEXT=true,并且SmsTracker發(fā)送該Intent時傳送的結(jié)果是“Activity.RESULT_OK”。
    ? ? ? ? 由于SmsReceiver會把所有Intent轉(zhuǎn)交給SmsReceiverService處理,我們直接來看SmsReceiverService的處理: [java]?view plaincopy
  • @SmsReceiverService.java??
  • public?void?handleMessage(Message?msg)?{??
  • ????int?serviceId?=?msg.arg1;??
  • ????Intent?intent?=?(Intent)msg.obj;??
  • ????if?(intent?!=?null?&&?MmsConfig.isSmsEnabled(getApplicationContext()))?{??
  • ????????String?action?=?intent.getAction();??
  • ????????int?error?=?intent.getIntExtra("errorCode",?0);??
  • ??
  • ??
  • ????????if?(MESSAGE_SENT_ACTION.equals(intent.getAction()))?{??
  • ????????????//處理??
  • ????????????handleSmsSent(intent,?error);??
  • ????????}?else?if?(SMS_DELIVER_ACTION.equals(action))?{??
  • ????????????handleSmsReceived(intent,?error);??
  • ????????}?else?if?(ACTION_BOOT_COMPLETED.equals(action))?{??
  • ????????????handleBootCompleted();??
  • ????????}?else?if?(TelephonyIntents.ACTION_SERVICE_STATE_CHANGED.equals(action))?{??
  • ????????????handleServiceStateChanged(intent);??
  • ????????}?else?if?(ACTION_SEND_MESSAGE.endsWith(action))?{??
  • ????????????handleSendMessage();??
  • ????????}?else?if?(ACTION_SEND_INACTIVE_MESSAGE.equals(action))?{??
  • ????????????handleSendInactiveMessage();??
  • ????????}??
  • ????}??
  • ????SmsReceiver.finishStartingService(SmsReceiverService.this,?serviceId);??
  • }??
  • ? ? ? ? 對于當(dāng)前的Intent,將會在handleSmsSent()中處理: [java]?view plaincopy
  • private?void?handleSmsSent(Intent?intent,?int?error)?{??
  • ????Uri?uri?=?intent.getData();??
  • ????mSending?=?false;??
  • ????//EXTRA_MESSAGE_SENT_SEND_NEXT表示是否是長短新的最后一條??
  • ????boolean?sendNextMsg?=?intent.getBooleanExtra(EXTRA_MESSAGE_SENT_SEND_NEXT,?false);??
  • ????if?(mResultCode?==?Activity.RESULT_OK)?{??
  • ????????//將已經(jīng)發(fā)送成功的短信移入發(fā)件箱,更新其狀態(tài)為已發(fā)送??
  • ????????if?(!Sms.moveMessageToFolder(this,?uri,?Sms.MESSAGE_TYPE_SENT,?error))?{??
  • ????????????Log.e(TAG,?"handleSmsSent:?failed?to?move?message?"?+?uri?+?"?to?sent?folder");??
  • ????????}??
  • ????????if?(sendNextMsg)?{??
  • ????????????//繼續(xù)發(fā)送其他收件人??
  • ????????????sendFirstQueuedMessage();??
  • ????????}??
  • ????????//?Update?the?notification?for?failed?messages?since?they?may?be?deleted.??
  • ????????MessagingNotification.nonBlockingUpdateSendFailedNotification(this);??
  • ????}?else?if?((mResultCode?==?SmsManager.RESULT_ERROR_RADIO_OFF)?||??
  • ????????????(mResultCode?==?SmsManager.RESULT_ERROR_NO_SERVICE))?{??
  • ????????//?We?got?an?error?with?no?service?or?no?radio.?Register?for?state?changes?so??
  • ????????//?when?the?status?of?the?connection/radio?changes,?we?can?try?to?send?the??
  • ????????//?queued?up?messages.??
  • ????????registerForServiceStateChanges();??
  • ????????//?We?couldn't?send?the?message,?put?in?the?queue?to?retry?later.??
  • ????????Sms.moveMessageToFolder(this,?uri,?Sms.MESSAGE_TYPE_QUEUED,?error);??
  • ????????mToastHandler.post(new?Runnable()?{??
  • ????????????public?void?run()?{??
  • ????????????????Toast.makeText(SmsReceiverService.this,?getString(R.string.message_queued),??
  • ????????????????????Toast.LENGTH_SHORT).show();??
  • ????????????}??
  • ????????});??
  • ????}?else?if?(mResultCode?==?SmsManager.RESULT_ERROR_FDN_CHECK_FAILURE)?{??
  • ????????messageFailedToSend(uri,?mResultCode);??
  • ????????mToastHandler.post(new?Runnable()?{??
  • ????????????public?void?run()?{??
  • ????????????????Toast.makeText(SmsReceiverService.this,?getString(R.string.fdn_check_failure),??
  • ????????????????????Toast.LENGTH_SHORT).show();??
  • ????????????}??
  • ????????});??
  • ????}?else?{??
  • ????????messageFailedToSend(uri,?error);??
  • ????????if?(sendNextMsg)?{??
  • ????????????sendFirstQueuedMessage();??
  • ????????}??
  • ????}??
  • }??
  • ? ? ? ? 由于當(dāng)前resultCode=OK,并且sendNextMsg=true,首先會通過Sms.moveMessageToFolder()操作將發(fā)送成功的短信從"content://sms/queued"隊列移動到"content://sms/sent"隊列。
    ? ? ? ? 然后在sendFirstQueuedMessage()中繼續(xù)處理: [java]?view plaincopy
  • public?synchronized?void?sendFirstQueuedMessage()?{??
  • ????boolean?success?=?true;??
  • ????final?Uri?uri?=?Uri.parse("content://sms/queued");??
  • ????ContentResolver?resolver?=?getContentResolver();??
  • ????Cursor?c?=?SqliteWrapper.query(this,?resolver,?uri,?SEND_PROJECTION,?null,?null,?"date?ASC");???//?date?ASC?so?we?send?out?in??
  • ????if?(c?!=?null)?{??
  • ????????try?{??
  • ????????????if?(c.moveToFirst())?{??
  • ????????????????//從隊列中取出第一個并發(fā)送??
  • ????????????????String?msgText?=?c.getString(SEND_COLUMN_BODY);??
  • ????????????????String?address?=?c.getString(SEND_COLUMN_ADDRESS);??
  • ????????????????int?threadId?=?c.getInt(SEND_COLUMN_THREAD_ID);??
  • ????????????????int?status?=?c.getInt(SEND_COLUMN_STATUS);??
  • ??
  • ??
  • ????????????????int?msgId?=?c.getInt(SEND_COLUMN_ID);??
  • ????????????????Uri?msgUri?=?ContentUris.withAppendedId(Sms.CONTENT_URI,?msgId);??
  • ??
  • ??
  • ????????????????SmsMessageSender?sender?=?new?SmsSingleRecipientSender(this,??
  • ????????????????????????address,?msgText,?threadId,?status?==?Sms.STATUS_PENDING,??
  • ????????????????????????msgUri);??
  • ????????????????try?{??
  • ????????????????????sender.sendMessage(SendingProgressTokenManager.NO_TOKEN);;??
  • ????????????????????mSending?=?true;??
  • ????????????????}?catch?(MmsException?e)?{??
  • ????????????????????mSending?=?false;??
  • ????????????????????messageFailedToSend(msgUri,?SmsManager.RESULT_ERROR_GENERIC_FAILURE);??
  • ????????????????????success?=?false;??
  • ????????????????????//?Sending?current?message?fails.?Try?to?send?more?pending?messages??
  • ????????????????????//?if?there?is?any.??
  • ????????????????????sendBroadcast(new?Intent(SmsReceiverService.ACTION_SEND_MESSAGE,??
  • ????????????????????????????????null,??
  • ????????????????????????????????this,??
  • ????????????????????????????????SmsReceiver.class));??
  • ????????????????}??
  • ????????????}??
  • ????????}?finally?{??
  • ????????????c.close();??
  • ????????}??
  • ????}??
  • ????if?(success)?{??
  • ????????//?We?successfully?sent?all?the?messages?in?the?queue.?We?don't?need?to??
  • ????????//?be?notified?of?any?service?changes?any?longer.??
  • ????????unRegisterForServiceStateChanges();??
  • ????}??
  • }??
  • ? ? ? ? 在上面的過程中,檢測發(fā)送隊列中是否有未發(fā)送的短信,對于多收件人的情況,由于我們之前只發(fā)送出去了第一條短信,而且已經(jīng)將已發(fā)送的短信從該隊列移出,因此此時的隊列中只有其他收件人的短信,然后取出其中的一條,再次進(jìn)入發(fā)送通道,接下來的流程和之前的相同。

    ? ? ? ? 這就是多收件人的發(fā)送流程。


    Source:?http://blog.csdn.net/u010961631/article/details/50272753

    總結(jié)

    以上是生活随笔為你收集整理的Android短信发送流程之多收件人发送(原)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。

    主站蜘蛛池模板: 五月天丁香激情 | 97久久精品人人澡人人爽 | 风韵丰满熟妇啪啪区老熟熟女 | 一区视频| 欧美日韩加勒比 | 免费在线观看日韩 | 樱花电影最新免费观看国语版 | 久久精精品久久久久噜噜 | 亚洲专区一 | 朋友的姐姐2在线观看 | 日韩亚洲精品中文字幕 | 国产精品传媒麻豆hd | 91在线网站| 奇米影视777第四色 2019中文字幕在线免费观看 | 成人免费看片入口 | 成人tv| 美女av在线免费观看 | 性色国产成人久久久精品 | 天天舔天天爽 | a三级黄色片 | 国产av无码专区亚洲av毛片搜 | 伊人精品一区二区三区 | 尤物视频在线观看国产 | 日本男男激情gay办公室 | 精品久久综合 | 天堂综合在线 | 精品一区二区三区免费看 | 久久大香焦 | 日本一区二区三区四区视频 | 日本一区二区免费在线 | 成人黄色片免费 | 国产精品欧美一区二区 | 久久这里只有精品6 | 美国免费高清电影在线观看 | 成人乱人乱一区二区三区一级视频 | 五月天综合视频 | 国产一区二区三区精品愉拍 | a视频免费观看 | 亚洲av人人澡人人爽人人夜夜 | 曰本女人与公拘交酡 | 欧美激情 亚洲 | 国产污视频网站 | 国产日韩在线一区 | 欧美片网站yy | 一级一片免费看 | 成人天堂噜噜噜 | 久久久精品影院 | 爱插网| 中文字幕一区二区人妻痴汉电车 | 日本高清视频在线播放 | 天天干天天做天天操 | 国产亚洲av在线 | 一区二区三区日韩在线 | 奶水旺盛的少妇在线播放 | 日本黄色大片免费 | 亚洲欧美一区二区激情 | 尤物网站在线 | 日韩视频一区二区三区 | xvideos永久免费入口 | 精品国产av无码一区二区三区 | 麻豆精品 | 好吊色视频在线观看 | 久久免费播放视频 | 97操操 | 91精东传媒理伦片在线观看 | 综合av第一页 | 久久久久亚洲AV成人 | 日韩专区一区二区三区 | 亚洲高清视频在线观看 | 午夜影院一区二区三区 | 黄色av电影在线观看 | 精品国产三级a∨在线 | 激情婷| 国产又大又粗又硬 | 捆绑调教在线观看 | 色资源av | 日韩视频三区 | 亚洲综合色婷婷 | 亚洲最新中文字幕 | 精品国产一区一区二区三亚瑟 | 成人免费网站 | av噜噜在线观看 | 欧美寡妇性猛交 | 免费在线成人av | 成人一区二 | 最新av在线| 激情六月综合 | 日韩av一区二区在线播放 | 中文字幕亚洲一区 | 三上悠亚激情av一区二区三区 | 精品视频免费观看 | 顶级毛片| 国产v片在线观看 | 午夜影院 | 中出在线视频 | 成人无码视频 | 阿拉伯性视频xxxx | 国产调教打屁股xxxx网站 | 四虎精品视频 |