版本記錄
| 版本號(hào) | 時(shí)間 |
|---|---|
| V1.0 | 2018.07.15 |
前言
我們做APP很多時(shí)候都需要推送功能,以直播為例,如果你關(guān)注的主播開(kāi)播了,那么就需要向關(guān)注這個(gè)主播的人發(fā)送開(kāi)播通知,提醒用戶去看播,這個(gè)只是一個(gè)小的方面,具體應(yīng)用根據(jù)公司的業(yè)務(wù)邏輯而定。前面已經(jīng)花了很多篇幅介紹了極光推送,其實(shí)極光推送無(wú)非就是將我們客戶端和服務(wù)端做的很多東西封裝了一下,節(jié)省了我們很多處理邏輯和流程,這一篇開(kāi)始,我們就利用系統(tǒng)的原生推送類結(jié)合工程實(shí)踐說(shuō)一下系統(tǒng)推送的集成,希望我的講解能讓大家很清楚的理解它。感興趣的可以看上面幾篇。
1. 系統(tǒng)推送的集成(一) —— 基本集成流程(一)
2. 系統(tǒng)推送的集成(二) —— 推送遇到的幾個(gè)坑之BadDeviceToken問(wèn)題(一)
3. 系統(tǒng)推送的集成(三) —— 本地和遠(yuǎn)程通知編程指南之你的App的通知 - 本地和遠(yuǎn)程通知概覽(一)
4. 系統(tǒng)推送的集成(四) —— 本地和遠(yuǎn)程通知編程指南之你的App的通知 - 管理您的應(yīng)用程序的通知支持(二)
5. 系統(tǒng)推送的集成(五) —— 本地和遠(yuǎn)程通知編程指南之你的App的通知 - 調(diào)度和處理本地通知(三)
6. 系統(tǒng)推送的集成(六) —— 本地和遠(yuǎn)程通知編程指南之你的App的通知 - 配置遠(yuǎn)程通知支持(四)
7. 系統(tǒng)推送的集成(七) —— 本地和遠(yuǎn)程通知編程指南之你的App的通知 - 修改和顯示通知(五)
8. 系統(tǒng)推送的集成(八) —— 本地和遠(yuǎn)程通知編程指南之蘋(píng)果推送通知服務(wù)APNs - APNs概覽(一)
9. 系統(tǒng)推送的集成(九) —— 本地和遠(yuǎn)程通知編程指南之蘋(píng)果推送通知服務(wù)APNs - 創(chuàng)建遠(yuǎn)程通知Payload(二)
10. 系統(tǒng)推送的集成(十) —— 本地和遠(yuǎn)程通知編程指南之蘋(píng)果推送通知服務(wù)APNs - 與APNs通信(三)
11. 系統(tǒng)推送的集成(十一) —— 本地和遠(yuǎn)程通知編程指南之蘋(píng)果推送通知服務(wù)APNs - Payload Key參考(四)
12. 系統(tǒng)推送的集成(十二) —— 本地和遠(yuǎn)程通知編程指南之Legacy信息 - 二進(jìn)制Provider API(一)
Legacy Notification Format - Legacy通知格式
新開(kāi)發(fā)應(yīng)使用現(xiàn)代格式連接到APNs,如 Communicating with APNs中所述。
這些格式不包括優(yōu)先權(quán); 假設(shè)優(yōu)先級(jí)為10。
圖B-1顯示了這種格式。

legacy格式中的第一個(gè)字節(jié)是命令值0(零)。 其他字段與增強(qiáng)格式相同。 Listing B-1給出了一個(gè)函數(shù)示例,該函數(shù)使用legacy通知格式通過(guò)二進(jìn)制接口向APNs發(fā)送遠(yuǎn)程通知。 該示例假設(shè)先前SSL連接到gateway.push.apple.com(或gateway.sandbox.push.apple.com)和對(duì)等交換驗(yàn)證。
// Listing B-1 Sending a notification in the legacy format via the binary interface
static bool sendPayload(SSL *sslPtr, char *deviceTokenBinary, char *payloadBuff, size_t payloadLength)
{
bool rtn = false;
if (sslPtr && deviceTokenBinary && payloadBuff && payloadLength)
{
uint8_t command = 0; /* command number */
char binaryMessageBuff[sizeof(uint8_t) + sizeof(uint16_t) +
DEVICE_BINARY_SIZE + sizeof(uint16_t) + MAXPAYLOAD_SIZE];
/* message format is, |COMMAND|TOKENLEN|TOKEN|PAYLOADLEN|PAYLOAD| */
char *binaryMessagePt = binaryMessageBuff;
uint16_t networkOrderTokenLength = htons(DEVICE_BINARY_SIZE);
uint16_t networkOrderPayloadLength = htons(payloadLength);
/* command */
*binaryMessagePt++ = command;
/* token length network order */
memcpy(binaryMessagePt, &networkOrderTokenLength, sizeof(uint16_t));
binaryMessagePt += sizeof(uint16_t);
/* device token */
memcpy(binaryMessagePt, deviceTokenBinary, DEVICE_BINARY_SIZE);
binaryMessagePt += DEVICE_BINARY_SIZE;
/* payload length network order */
memcpy(binaryMessagePt, &networkOrderPayloadLength, sizeof(uint16_t));
binaryMessagePt += sizeof(uint16_t);
/* payload */
memcpy(binaryMessagePt, payloadBuff, payloadLength);
binaryMessagePt += payloadLength;
if (SSL_write(sslPtr, binaryMessageBuff, (binaryMessagePt - binaryMessageBuff)) > 0)
rtn = true;
}
return rtn;
}
Enhanced Notification Format - 增強(qiáng)的通知格式
增強(qiáng)格式與legacy格式相比有幾處改進(jìn):
Error response - 錯(cuò)誤響應(yīng)。使用
legacy格式,如果您發(fā)送以某種方式格式錯(cuò)誤的通知數(shù)據(jù)包 - 例如,有效負(fù)載超出規(guī)定的限制 - APNs通過(guò)切斷連接進(jìn)行響應(yīng)。它沒(méi)有說(shuō)明它拒絕通知的原因。增強(qiáng)格式允許提供者使用任意標(biāo)識(shí)符標(biāo)記通知。如果存在錯(cuò)誤,APNs將返回將錯(cuò)誤代碼與標(biāo)識(shí)符相關(guān)聯(lián)的數(shù)據(jù)包。此響應(yīng)使provider能夠定位并更正格式錯(cuò)誤的通知。Notification expiration - 通知到期。 APNs具有存儲(chǔ)轉(zhuǎn)發(fā)功能,可將最新通知發(fā)送到設(shè)備上的應(yīng)用程序。如果設(shè)備在交付時(shí)處于脫機(jī)狀態(tài),則APNs會(huì)在設(shè)備下次聯(lián)機(jī)時(shí)發(fā)送通知。使用
legacy格式,無(wú)論通知的相關(guān)性如何,都會(huì)發(fā)送通知。換句話說(shuō),通知隨著時(shí)間的推移會(huì)變得“陳舊”。增強(qiáng)格式包括指示通知有效期的到期值。當(dāng)此期限到期時(shí),APNs會(huì)在存儲(chǔ)轉(zhuǎn)發(fā)中丟棄通知。
圖B-2描述了通知數(shù)據(jù)包的格式。

通知格式中的第一個(gè)字節(jié)是命令值1,其余字段如下:
Identifier - 標(biāo)識(shí)符 - 標(biāo)識(shí)此通知的任意值。 如果APNs無(wú)法解釋通知,則在錯(cuò)誤響應(yīng)數(shù)據(jù)包中返回相同的標(biāo)識(shí)符。
Expiry - 到期 - 以秒(UTC)表示的固定UNIX紀(jì)元日期,用于標(biāo)識(shí)通知何時(shí)不再有效且可以丟棄。 到期值使用網(wǎng)絡(luò)字節(jié)順序(大端)。 如果到期值非零,則APNs嘗試至少傳遞一次通知。 指定零以請(qǐng)求APNs根本不存儲(chǔ)通知。
Token length - 令牌長(zhǎng)度 - 設(shè)備令牌網(wǎng)絡(luò)順序的長(zhǎng)度(即大端)
Device token - 設(shè)備令牌 - 二進(jìn)制形式的設(shè)備令牌。
Payload length - 有效負(fù)載長(zhǎng)度 - 網(wǎng)絡(luò)順序中有效負(fù)載的長(zhǎng)度(即大端)。 有效負(fù)載不得超過(guò)256個(gè)字節(jié),且不得以空值終止。
Payload - 有效負(fù)載 - 通知負(fù)載。
Listing B-2在將其發(fā)送到APNs之前以增強(qiáng)格式組成遠(yuǎn)程通知。 它假設(shè)優(yōu)先SSL連接到gateway.push.apple.com(或gateway.sandbox.push.apple.com)和對(duì)等交換驗(yàn)證。
// Listing B-2 Sending a notification in the enhanced format via the binary interface
static bool sendPayload(SSL *sslPtr, char *deviceTokenBinary, char *payloadBuff, size_t payloadLength)
{
bool rtn = false;
if (sslPtr && deviceTokenBinary && payloadBuff && payloadLength)
{
uint8_t command = 1; /* command number */
char binaryMessageBuff[sizeof(uint8_t) + sizeof(uint32_t) + sizeof(uint32_t) + sizeof(uint16_t) +
DEVICE_BINARY_SIZE + sizeof(uint16_t) + MAXPAYLOAD_SIZE];
/* message format is, |COMMAND|ID|EXPIRY|TOKENLEN|TOKEN|PAYLOADLEN|PAYLOAD| */
char *binaryMessagePt = binaryMessageBuff;
uint32_t whicheverOrderIWantToGetBackInAErrorResponse_ID = 1234;
uint32_t networkOrderExpiryEpochUTC = htonl(time(NULL)+86400); // expire message if not delivered in 1 day
uint16_t networkOrderTokenLength = htons(DEVICE_BINARY_SIZE);
uint16_t networkOrderPayloadLength = htons(payloadLength);
/* command */
*binaryMessagePt++ = command;
/* provider preference ordered ID */
memcpy(binaryMessagePt, &whicheverOrderIWantToGetBackInAErrorResponse_ID, sizeof(uint32_t));
binaryMessagePt += sizeof(uint32_t);
/* expiry date network order */
memcpy(binaryMessagePt, &networkOrderExpiryEpochUTC, sizeof(uint32_t));
binaryMessagePt += sizeof(uint32_t);
/* token length network order */
memcpy(binaryMessagePt, &networkOrderTokenLength, sizeof(uint16_t));
binaryMessagePt += sizeof(uint16_t);
/* device token */
memcpy(binaryMessagePt, deviceTokenBinary, DEVICE_BINARY_SIZE);
binaryMessagePt += DEVICE_BINARY_SIZE;
/* payload length network order */
memcpy(binaryMessagePt, &networkOrderPayloadLength, sizeof(uint16_t));
binaryMessagePt += sizeof(uint16_t);
/* payload */
memcpy(binaryMessagePt, payloadBuff, payloadLength);
binaryMessagePt += payloadLength;
if (SSL_write(sslPtr, binaryMessageBuff, (binaryMessagePt - binaryMessageBuff)) > 0)
rtn = true;
}
return rtn;
}
后記
本篇主要講述了Legacy通知格式,感興趣的給個(gè)贊或者關(guān)注~~~~
