SkyEagle888
SkyEagle888

Reputation: 1009

Apple Push Message

I am integrating a Push Provider Server with the codes (php-apns) from google codes. Everything seems to be fine except the number of bytes per message.

The number of bytes per payload should be maximum 256 characters.

If some Chinse characters or UTF8 characters are sent. After JSON_enode, each character would occupy 6 bytes. Am I right ?

So the maximum number of UTF8 characters in each push message is around 38.

But ... Whatsapp (iPhone application) uses PUSH too, but it can push more Chinese characters ... in one push message ?

Any hint ?

Upvotes: 3

Views: 2043

Answers (2)

AK_
AK_

Reputation: 2079

Here is the solution to your problem:

go to ~/APNS/Message.php

and replace this function:

public function getPayload() {...}

with this:

/**
 * Convert the message in a JSON-encoded payload.
 *
 * @throws ApnsPHP_Message_Exception if payload is longer than maximum allowed
 *         size and AutoAdjustLongPayload is disabled.
 * @return @type string JSON-encoded payload.
 */
public function getPayload()
{
    $sJSONString = preg_replace_callback('/\\\u([0-9a-f]{4})/i', 
                        function($matches) {
                            if (function_exists('mb_convert_encoding')) {
                                return mb_convert_encoding(pack('H*', $matches[1]), 'UTF-8', 'UTF-16');
                            } else {
                                //Slower conversion from UTF-16 to UTF-8 (BMP Only)
                                //See: http://www.cl.cam.ac.uk/~mgk25/unicode.html
                                $decimal_code = hexdec($matches[1]);
                                $character = "";
                                if ((0x7F & $decimal_code) == $decimal_code) {
                                    //UTF-8 1-byte aka ASCII
                                    $first_byte     = 0x7F & $decimal_code;
                                    $character      = chr($first_byte);
                                } elseif ((0x7FF & $decimal_code) == $decimal_code) {
                                    //UTF-8 2-bytes
                                    $first_byte     = 0xC0 | (($decimal_code >> 6) & 0x1F);
                                    $second_byte    = 0x80 | ($decimal_code & 0x3F);
                                    $character      = chr($first_byte) . chr($second_byte);
                                } elseif ((0xFFFF & $decimal_code) == $decimal_code) {
                                    //UTF-8 3-bytes
                                    $first_byte     = 0xE0 | (($decimal_code >> 12) & 0x0F);
                                    $second_byte    = 0x80 | (($decimal_code >> 6) & 0x3F);
                                    $third_byte     = 0x80 | ($decimal_code & 0x3F);
                                    $character      = chr($first_byte) . chr($second_byte) . chr($third_byte);
                                }
                                return $character;
                            }
                        },
                        json_encode($this->_getPayload()));
    $sJSONPayload = str_replace(
        '"' . self::APPLE_RESERVED_NAMESPACE . '":[]',
        '"' . self::APPLE_RESERVED_NAMESPACE . '":{}',
        $sJSONString
    );
    $nJSONPayloadLen = strlen($sJSONPayload);

    if ($nJSONPayloadLen > self::PAYLOAD_MAXIMUM_SIZE) {
        if ($this->_bAutoAdjustLongPayload) {
            $nMaxTextLen = $nTextLen = strlen($this->_sText) - ($nJSONPayloadLen - self::PAYLOAD_MAXIMUM_SIZE);
            if ($nMaxTextLen > 0) {
                while (strlen($this->_sText = mb_substr($this->_sText, 0, --$nTextLen, 'UTF-8')) > $nMaxTextLen);
                return $this->getPayload();
            } else {
                throw new ApnsPHP_Message_Exception(
                    "JSON Payload is too long: {$nJSONPayloadLen} bytes. Maximum size is " .
                    self::PAYLOAD_MAXIMUM_SIZE . " bytes. The message text can not be auto-adjusted."
                );
            }
        } else {
            throw new ApnsPHP_Message_Exception(
                "JSON Payload is too long: {$nJSONPayloadLen} bytes. Maximum size is " .
                self::PAYLOAD_MAXIMUM_SIZE . " bytes"
            );
        }
    }

    return $sJSONPayload;
}

Tada! now you will be able to receive long utf-8 message without problems.

source

Upvotes: 5

SkyEagle888
SkyEagle888

Reputation: 1009

I found it out.

If those UTF8 Chinese chracters are JSON_encoded, then it is converted to 6 characters.

Therefore, I need to modify php-apns to make sure that those UTF8 characters would be put into the JSON_encoded string to save space

Upvotes: 1

Related Questions