Текст книги "iOS. Приемы программирования"
Автор книги: Вандад Нахавандипур
Жанр: Зарубежная компьютерная литература, Зарубежная литература
сообщить о неприемлемом содержимом
Текущая страница: 48 (всего у книги 59 страниц)
15.7. Настройка приложения для получения пуш-уведомлений
Постановка задачиТребуется сконфигурировать приложение таким образом, чтобы сервер мог по своей инициативе отправлять уведомления на различные устройства.
РешениеВыполните следующие шаги.
1. Настройте профиль инициализации для вашего приложения, активизировав в нем возможность получения пуш-уведомлений.
2. В приложении зарегистрируйте устройство для получения пуш-уведомлений для этого приложения.
3. Возьмите идентификатор пуш-уведомлений данного устройства для вашего приложения и отошлите этот идентификатор на сервер.
ОбсуждениеВ этом разделе мы поговорим о приложении, применяемом для внесения настроек и регистрации вашего приложения для получения пуш-уведомлений. Серверную часть этой технологии затрагивать не будем, этим вопросам будет посвящен отдельный раздел.
Пуш-уведомления похожи на локальные уведомления тем, что позволяют сообщать пользователю определенную информацию, даже если ваше приложение неактивно при поступлении уведомления. В то время как локальные уведомления назначаются самим приложением, пуш-уведомления конфигурируются на сервере и отсылаются с него в Apple, а Apple сама раздает эти уведомления на разные устройства, работающие по всему миру. Мы должны выполнять серверную часть работы, поэтому сами составляем пуш-уведомления и отправляем их на серверы APNS (Apple Push Notifications Services). Затем APNS пытается доставлять наши пуш-уведомления по защищенным каналам на устройства, которые зарегистрированы для получения таких уведомлений.
Чтобы приложение для iOS могли получать пуш-уведомления, у него должен быть валидный профиль инициализации, в котором активизирована возможность получения пуш-уведомлений. Чтобы правильно сконфигурировать профиль, выполните следующие шаги.
Предполагается, что вы уже настроили на портале разработчика ваши сертификаты для разработки и распространения приложения. Чтобы автоматически сконфигурировать сертификаты, можете воспользоваться новой настройкой Accounts (Учетные записи), появившейся в Xcode. Просто перейдите в раздел Xcode Preferences (Настройки), в нем откройте область Accounts (Учетные записи). Добавьте в список учетных записей ваш идентификатор Apple ID, а далее Xcode сконфигурирует сертификаты за вас.
1. Войдите в центр для разработки для iOS.
2. Перейдите в раздел Certificates, Identifiers & Profiles (Сертификаты, идентификаторы и профили) – он расположен справа.
3. В разделе Identifiers (Идентификаторы) создайте для себя новый идентификатор App ID. Он должен иметь валидный Explicit App ID (явный идентификатор приложения), например com.pixolity.ios.cookbook.PushNotificationApp. Обратите внимание: это имя построено по принципу обратной записи домена в стиле, который я выбрал для этого приложения. Выберите такой идентификатор приложения в стиле обратной записи домена, который подходит вам и вашей организации.
4. В разделе App Services (Сервисы приложения) на странице идентификатора приложения убедитесь, что установили флажок для пуш-уведомлений (Push Notifications) (рис. 15.5).
Рис. 15.5. Активизация пуш-уведомлений для App ID
5. Как только вас устроит конфигурация идентификатора приложения (рис. 15.6), отправьте ваш App ID в Apple.
Рис. 15.6. Создание идентификатора приложения с поддержкой пуш-уведомлений
6. После того как настроите все детали конфигурации идентификатора приложения, перейдите в раздел Provisioning Profiles (Профили инициализации) вашего iOS-портала.
7. Создайте профиль инициализации для разработки (Development). Позже вы можете создать и другие профили – Ad Hoc и App Store, так что об этом не волнуйтесь. Когда будете готовы отправить ваше приложение в App Store, можете просто вернуться к этому шагу и сгенерировать профили Ad Hoc и App Store.
8. Убедитесь, что новый профиль инициализации для разработки приложения связан с идентификатором приложения, который вы сгенерировали ранее. Это первый вопрос, который у вас попытается выяснить система при генерации профиля инициализации.
9. Когда профиль будет готов, скачайте его и перетащите в программу iTunes на своем компьютере, чтобы установить. При установке профиля не делайте двойных щелчков на нем. При двойном щелчке кнопкой мыши имя файла установленного профиля будет сброшено и заменено хеш-именем MD5, по которому файл очень сложно идентифицировать на диске. Если вы аккуратно перетащите профиль в iTunes, то iTunes установит профиль под его оригинальным именем.
10. В Xcode в настройках сборки вашего приложения просто выберите сборку в соответствии с тем профилем, который только что создали. Убедитесь, что при разработке (схема Development) вы используете именно этот профиль, а затем примените в схеме Release (Релиз) профиль App Store или Ad Hoc, созданием которых займетесь позже.
11. Перетащите ваш профиль инициализации в текстовый редактор для OS X – например, в TextEdit. Найдите в файле профиля ключ Entitlements. Весь этот раздел моего профиля инициализации выглядит так:
<key>Entitlements</key>
<dict>
<key>application-identifier</key>
<string>F3FU372W5M.com.pixolity.ios.cookbook.PushNotificationApp</string>
<key>aps-environment</key>
<string>development</string>
<key>get-task-allow</key>
<true/>
<key>keychain-access-groups</key>
<array>
<string>F3FU372W5M.*</string>
</array>
</dict>
12. Создайте новый PLIST-файл для вашего проекта в Xcode, назовите этот файл Entitlements.plist. В Xcode щелкните на этом файле правой кнопкой мыши, выберите Open As (Открыть как) и далее Source Code (Исходный код). Содержимое вашего файла изначально будет выглядеть вот так:
<plist version="1.0">
<dict/>
</plist>
13. Поместите разрешения вашего профиля инициализации прямо в файл Entitlements.plist, чтобы его содержимое выглядело вот так:
<plist version="1.0">
<dict>
<key>application-identifier</key>
<string>F3FU372W5M.com.pixolity.ios.cookbook.PushNotificationApp</string>
<key>aps-environment</key>
<string>development</string>
<key>get-task-allow</key>
<true/>
<key>keychain-access-groups</key>
<array>
<string>F3FU372W5M.*</string>
</array>
</dict>
</plist>
Значения, приведенные в рассматриваемых здесь листингах, относятся к профилям, которые создал я. В вашем профиле будут другие значения и, конечно же, будет другой идентификатор приложения (App ID). Поэтому внимательно выполните предыдущие шаги, чтобы правильно создать идентификатор вашего приложения и профиль. Потом возьмите разрешения из своего профиля и вставьте их в файл Entitlements.plist вашего проекта.
14. Далее перейдите в настройки сборки вашего проекта. В разделе Code Signing Entitlements (Разрешения для подписания кода) введите значение $(SRCROOT)/$(TARGET_NAME)/Entitlements.plist (если создали файл разрешений в целевом каталоге проекта) или $(SRCROOT)/Entitlements.plist (если создали файл разрешений в корневом каталоге, включающем в себя весь исходный код). Если не знаете, какой вариант выбрать, просто попробуйте оба этих значения, попытайтесь собрать проект с каждым из них. Если Xcode сообщит, что не может найти файл разрешений, поставьте второе значение, и оно сработает. Настройка сборки Code Signing Entitlements (Разрешения для подписания кода) требует указания относительного пути, идущего к файлу разрешений от корневого каталога исходного кода. Поэтому, если вы поместите файл разрешений в какой-то другой каталог, вам потребуется выстроить этот путь вручную, а потом записать полученный путь в это поле.
15. Соберите проект и убедитесь, что Xcode не выдает никаких ошибок. Если получите сообщение о какой-либо ошибке, то, вероятно, дело в том, что вы задали неверный профиль инициализации либо указали в настройках сборки неверный путь к файлу разрешений для подписания кода.
16. В делегате вашего приложения вызовите метод registerForRemoteNotificationTypes:, относящийся к классу UIApplication, а затем передайте этому методу значения UIRemoteNotificationTypeAlert, UIRemoteNotificationTypeBadge и UIRemoteNotificationTypeSound, как показано далее:
– (BOOL) application:(UIApplication *)application
didFinishLaunchingWithOptions:(NSDictionary *)launchOptions{
[[UIApplication sharedApplication] registerForRemoteNotificationTypes:
UIRemoteNotificationTypeAlert |
UIRemoteNotificationTypeBadge |
UIRemoteNotificationTypeSound];
self.window = [[UIWindow alloc]
initWithFrame: [[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
return YES;
}
Так вы зарегистрируете ваше приложение для получения пуш-уведомлений. Такие уведомления могут содержать информацию с предупреждениями, изменения номера ярлыка вашего приложения, а также звуки. Пока не будем вдаваться в эти подробности. Просто зарегистрируйте приложение для получения пуш-уведомлений, как показано ранее. Как только вы это сделаете, iOS отошлет запрос о регистрации к APNS. Перед тем как это делать, iOS попросит у пользователя разрешения зарегистрировать данное приложение для получения пуш-уведомлений. Пользовательский интерфейс, открывающийся в iOS при этом запросе, показан на рис. 15.7.
Рис. 15.7. iOS выдает пользователю запрос о разрешении на получение пуш-уведомлений
17. Теперь реализуйте метод application: didRegisterForRemoteNotificationsWithDeviceToken: делегата вашего приложения. Этот метод вызывается, когда iOS удается успешно зарегистрировать устройство в APNS и присвоить ему маркер. Этот маркер действует только для конкретного приложения, установленного именно на данном устройстве.
18. Далее реализуйте метод application: didFailToRegisterForRemoteNotificationsWithError: делегата вашего приложения. Этот метод вызывается, если iOS не удается зарегистрировать приложение для получения пуш-уведомлений. Это может произойти потому, что ваш профиль настроен неправильно или устройство не подключено к Интернету, а также по многим другим причинам. В параметре didFailToRegisterForRemoteNotificationsWithError этого метода вы получите ошибку типа NSError. Ее можно проанализировать и узнать, по какой причине возникла проблема.
Теперь вы знаете все необходимое, чтобы настроить ваше приложение на получение пуш-уведомлений.
См. такжеРаздел 15.0.
15.8. Доставка пуш-уведомлений в приложение
Постановка задачиТребуется отправлять пуш-уведомления на пользовательские устройства, которые зарегистрированы для получения таких уведомлений.
РешениеУбедитесь, что вы собрали маркеры-идентификаторы пуш-уведомлений этих приложений (см. раздел 15.7). Затем сгенерируйте SSL-сертификаты, которые будут использоваться вашими веб-сервисами для отправки пуш-уведомлений на устройства. Затем создайте простой веб-сервис для отправки пуш-уведомлений на зарегистрированные устройства.
ОбсуждениеЭтот материал – продолжение раздела 15.7. Обязательно прочтите предыдущий раздел и полностью в нем разберитесь, прежде чем переходить к изучению данного раздела.
Чтобы обмениваться информацией с серверами APNS, ваши веб-сервисы должны совершить акт квитирования[11]11
Употребляется и буквальный перевод – «рукопожатие». – Примеч. пер.
[Закрыть] (handshaking). Это обмен сигналами с сервером, при котором используется выданный Apple SSL-сертификат. Чтобы сгенерировать такой сертификат, выполните следующие шаги.
1. Войдите в центр разработки для iOS.
2. Перейдите в раздел Certificates, Identifiers & Profiles (Сертификаты, идентификаторы, профили), расположенный справа.
3. В разделе идентификаторов приложений (App ID) найдите идентификатор вашего приложения, для которого задано получение пуш-уведомлений, выберите этот идентификатор и нажмите кнопку Settings (Настройки), чтобы его сконфигурировать, как показано на рис. 15.8.
Рис. 15.8. Изменение настроек имеющегося идентификатора приложения
4. В разделе настроек, называемом Push Notifications (Пуш-уведомления), найдите подраздел Development SSL Certificate (SSL-сертификат для разработки) и нажмите кнопку Create Certificate (Создать сертификат) (рис. 15.9). Далее следуйте указаниям Apple по созданию сертификата. Пока мы создаем SSL-сертификат для разработки приложения, поскольку на данном этапе нас интересует исключительно разработка. Позже, когда будем готовы отправить наше приложение в App Store, просто повторите подобный процесс и создайте SSL-сертификаты для распространения (Distribution).
Рис. 15.9. Создание SSL-сертификата, используемого для операций с пуш-уведомлениями и разработки приложения
5. Как только сертификат будет готов (рис. 15.10), скачайте его на компьютер и дважды щелкните на нем кнопкой мыши, чтобы импортировать его в вашу связку ключей.
Рис. 15.10. SSL-сертификат для обмена информацией с APNS на этапе разработки приложения готов к скачиванию
6. Теперь откройте окно Keychain Access (Доступ к связке ключей) на OS X и перейдите к связке ключей Login (если эта связка ключей задана у вас по умолчанию). В разделе My Certificates (Мои сертификаты) найдите тот сертификат, который вы только что импортировали в связку ключей, и раскройте его, щелкнув на маленькой кнопке со стрелкой слева. Так вы узнаете ассоциированный с этим приложением закрытый ключ (рис. 15.11).
Рис. 15.11. Сертификат для работы с пуш-уведомлениями на этапе разработки и его закрытый ключ
7. Щелкните на сертификате правой кнопкой мыши и экспортируйте его как. cer-сертификат (а не как файл. p12). Назовите его PushCertificate.cer.
8. Щелкните правой кнопкой мыши на закрытом ключе и экспортируйте его как файл. p12 (а не как файл сертификата). Назовите его PushKey.p12. Здесь потребуется указать пароль к закрытому ключу. Обязательно используйте такой пароль, который впоследствии сможете вспомнить.
Отлично. Теперь, чтобы упростить дальнейший материал этого раздела, перейдем к использованию PHP. Применим этот язык для отправки на наше устройство простого пуш-уведомления. В разделе 15.7 мы уже настроили получение пуш-уведомлений в этом приложении. Поскольку настройка использования PHP на сервере Apache не относится к темам этой книги, мы воспользуемся упрощенным вариантом и применим MAMP. MAMP установит у вас на компьютере Apache и PHP, если вы еще не сделали этого. На сайте MAMP даются подробные инструкции о том, какие шаги потребуется выполнить. Когда вы установите MAMP, корневой каталог со всеми вашими PHP-файлами будет находиться по адресу /Applications/MAMP/htdocs/. Если при последующей установке этот каталог изменится, откройте MAMP, перейдите в раздел Preferences (Настройки), а потом – к Apache. Вы найдете там и корневой каталог Apache.
Чтобы наш PHP-сценарий мог обмениваться информацией с APNS, потребуется задать ему SSL-сертификат, который мы сгенерировали ранее, на портале разработки для iOS. Именно поэтому мы извлекли. cer-файл сертификата и файл. p12 закрытого ключа – теперь мы должны задать эти файлы нашему PHP-сценарию. Чтобы это сработало, используем в окне терминала openssl, а затем комбинируем сертификат и закрытый ключ. p12 в едином PEM-файле. В этой книге мы не можем подробно поговорить о PEM-файлах – это тема для отдельной книги. Однако вы можете подробнее познакомиться с этой темой в документе RFC 1421.
Для создания PEM-файла выполните следующие шаги (предполагается, что вы уже экспортировали файлы PushKey.p12 и PushCertificate.cer на ПК, как было описано ранее).
1. Откройте окно терминала (Terminal) в OS X. Введите в окне терминала следующую команду:
openssl x509 -in PushCertificate.cer -inform der -out PushCertificate.pem
2. Чтобы преобразовать файл. p12 в PEM-файл, введите в окне терминала следующую команду:
openssl pkcs12 -nocerts -in PushKey.p12 -out PushKey.pem
3. Система потребует ввести пароль, который вы задали для этого закрытого ключа, когда экспортировали его из раздела Keychain Access. После того как пароль для импорта будет проверен и подтвержден, OpenSSL запросит у вас фразу-пароль для результирующего PEM-файла. Этот пароль должен содержать не менее четырех символов. Задайте такой пароль и хорошо запомните его для последующего использования.
4. Теперь у вас на ПК должно быть два PEM-файла: PushCertificate.pem и PushKey.pem. Нужно сложить их в единый PEM-файл – этот формат распознается PHP. Для этого воспользуйтесь следующей командой:
cat PushCertificate.pem PushKey.pem > PushCertificateAndKey.pem
5. Теперь проверим, сможем ли мы подключиться к песочнице (речь идет о тестовой версии, только для целей разработки) с помощью сгенерированных нами PEM-файлов. В качестве песочницы используется защищенный APNS-сервер. Выполните в окне терминала следующую команду:
openssl s_client -connect gateway.sandbox.push.apple.com:2195
– cert PushCertificate.pem -key PushKey.pem
Если все будет нормально, то на данном этапе потребуется ввести фразу-пароль для вашего закрытого ключа. Помните ее? Хорошо, вводите. Если соединение будет успешно установлено, откроется OpenSSL, ожидающий от вас нескольких символов в качестве ввода. После получения этого ввода соединение будет закрыто. Введите любые случайные символы и нажмите Enter (Ввод). Соединение закрыто. Вам удалось успешно связаться с APNS-сервером, воспользовавшись вашим сертификатом и закрытым ключом.
Теперь напишем несложный PHP-сценарий для отправки простого пуш-уведомления на устройство. Но прежде чем мы двинемся дальше, необходимо получить маркер пуш-уведомлений, действующий на нашем устройстве. Мы должны получить его в таком формате, который понятен PHP. iOS инкапсулирует маркер пуш-уведомления в экземпляр NSData, но PHP неизвестно, что такое NSData. Нам нужно преобразовать этот маркер в строку, которую мы сможем использовать в нашем PHP-сценарии. Для этого считываем весь маркер байт за байтом и преобразуем каждый байт в шестнадцатеричное строковое представление:
– (void) application:(UIApplication *)application
didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken{
/* Каждый байт данных будет преобразован в свое шестнадцатеричное
значение, например 0x01 или 0xAB. При этом часть 0x отбрасывается.
Итак, для представления 1 байта нам потребуются два символа, поэтому
здесь указано * 2 */
NSMutableString *tokenAsString = [[NSMutableString alloc]
initWithCapacity: deviceToken.length * 2];
char *bytes = malloc(deviceToken.length);
[deviceToken getBytes: bytes];
for (NSUInteger byteCounter = 0;
byteCounter < deviceToken.length;
byteCounter++){
char byte = bytes[byteCounter];
[tokenAsString appendFormat:@"%02hhX", byte];
}
free(bytes);
NSLog(@"Token = %@", tokenAsString);
}
Запустите ваше приложение и убедитесь, что маркер устройства выводится на консоль, вот так:
Token = 05924634A8EB6B84437A1E8CE02E6BE6683DEC83FB38680A7DFD6A04C6CC586E
Отметьте себе этот маркер устройства, так как мы будем пользоваться им в PHP-сценарии:
<?php
/* При разработке мы пользуемся защищенной версией APNS. При подготовке
приложения для использования в реальных условиях измените это значение
на ssl://gateway.push.apple.com:2195 */
$apnsServer = 'ssl://gateway.sandbox.push.apple.com:2195';
/* Убедитесь, что это значение совпадает с паролем, который вы задали
для закрытого ключа при экспорте в.pem-файл, когда использовали openssl
в системе OS X */
$privateKeyPassword = '1234';
/* Если хотите, запишите здесь собственное сообщение */
$message = 'Welcome to iOS 7 Push Notifications';
/* Запишите здесь маркер вашего устройства */
$deviceToken =
'05924634A8EB6B84437A1E8CE02E6BE6683DEC83FB38680A7DFD6A04C6CC586E';
/* Замените эту информацию именем файла, указанного в файле вашего
сценария. В этом файле должны содержаться сгенерированные вами ранее
сертификат и закрытый ключ */
$pushCertAndKeyPemFile = 'PushCertificateAndKey.pem';
$stream = stream_context_create();
stream_context_set_option($stream,
'ssl',
'passphrase',
$privateKeyPassword);
stream_context_set_option($stream,
'ssl',
'local_cert',
$pushCertAndKeyPemFile);
$connectionTimeout = 20;
$connectionType = STREAM_CLIENT_CONNECT | STREAM_CLIENT_PERSISTENT;
$connection = stream_socket_client($apnsServer,
$errorNumber,
$errorString,
$connectionTimeout,
$connectionType,
$stream);
if (!$connection){
echo «Failed to connect to the APNS server. Error no = $errorNumber<br/>»;
exit;
} else {
echo «Successfully connected to the APNS. Processing…</br>»;
}
$messageBody['aps'] = array('alert' => $message,
'sound' => 'default',
'badge' => 2,
);
$payload = json_encode($messageBody);
$notification = chr(0).
pack('n', 32).
pack('H*', $deviceToken).
pack('n', strlen($payload)).
$payload;
$wroteSuccessfully = fwrite($connection, $notification,
strlen($notification));
if (!$wroteSuccessfully){
echo «Could not send the message<br/>»;
}
else {
echo «Successfully sent the message<br/>»;
}
fclose($connection);
Если вы даже не программируете на PHP, внимательно просмотрите этот сценарий и почитайте комментарии к нему. Обязательно замените все значения в этом сценарии теми, что соответствуют вашему приложению. Например, используемый здесь маркер относится к моему устройству. Пользуйтесь маркером своего устройства, который выяснили ранее в этом разделе. У вас будут иные пароли, pem-файлы, скорее всего, будут находиться в других местах. Ради дополнительного упрощения этого раздела я поместил свой PHP-сценарий в тот же каталог, в котором ранее сохранил закрытый ключ и. pem-файл сертификата (PushCertificateAndKey.pem). Поэтому я могу обращаться к. pem-файлу просто по его имени.
Если вы правильно выполнили все шаги и инструкции, описанные в этом разделе, то ваш PHP-сценарий должен открываться в браузере. После этого на устройство начнут поступать уведомления. Сценарий посылает уведомление на APNS-сервер, который уже доставляет это уведомление на устройство. Когда пуш-уведомление попадает на устройство (предполагается, что на устройстве в этот момент отображается экран блокировки), вы увидите на экране примерно такую картинку, какая показана на рис. 15.12.
Рис. 15.12. Пуш-уведомление, отображенное на экране блокировки
Правообладателям!
Это произведение, предположительно, находится в статусе 'public domain'. Если это не так и размещение материала нарушает чьи-либо права, то сообщите нам об этом.