※iOS8でのやり方がわかったので一番下に追記しました
SwiftでPush通知を実装してみました。
証明書の取得等はこちらを参考にしています。
【iOSでプッシュ通知を実装する方法の超詳細まとめ(前編)】
http://www.lancork.net/2013/08/how-to-ios-push-first/
【iOSでプッシュ通知を実装する方法の超詳細まとめ(後編)】
http://www.lancork.net/2013/08/how-to-ios-push-second/
元記事:http://sawapi.hatenablog.com/entry/2014/06/08/230719
コードの解説
Push通知を有効にする
func application( application: UIApplication, didFinishLaunchingWithOptions launchOptions: NSDictionary? ) -> Bool {
application.registerForRemoteNotificationTypes(
UIRemoteNotificationType.Badge |
UIRemoteNotificationType.Sound |
UIRemoteNotificationType.Alert )
return true
}
AppDelegate.swiftのapplication didFinishLaunchingWithOptionsにて
application.registerForRemoteNotificationTypesを呼び出し、有効にするものを指定します。
- UIRemoteNotificationType.Badge・・・アイコンバッジ
- UIRemoteNotificationType.Sound・・・Push通知時になる音
- UIRemoteNotificationType.Alert・・・Push通知時に表示される文字列
上記の処理が成功するとapplication didRegisterForRemoteNotificationsWithDeviceTokenが呼ばれるのでその中でデバイストークンを取得します。
デバイストークンの取得
func application( application: UIApplication, didRegisterForRemoteNotificationsWithDeviceToken deviceToken: NSData ) {
// <>と" "(空白)を取る
var characterSet: NSCharacterSet = NSCharacterSet( charactersInString: "<>" )
var deviceTokenString: String = ( deviceToken.description as NSString )
.stringByTrimmingCharactersInSet( characterSet )
.stringByReplacingOccurrencesOfString( " ", withString: "" ) as String
println( deviceTokenString )
}
devideToken.descriptionには、
<00000000 11111111 22222222 33333333 aaaaaaaa bbbbbbbb cccccccc dddddddd>
というような文字列で入っているため、"<"と">"と" (スペース)"を取る必要があります。
Swiftの文字の整形の仕方が分からず、、一旦NSStringに変換し、余分な文字を取り除きました。
( いい方法がありましたら教えて下さい。。。)
上記までを実行するとデバイストークンを取得できるのでメモしておきます。
Push通知が届くかテスト
Push通知がちゃんと届くかテストするために以下のスクリプトでテストしてみました。
<?php
$deviceToken = '************';
// 送信する文字列
$alert = 'Push test.';
// バッジ
$badge = 1;
$body = array();
$body['aps'] = array( 'alert' => $alert );
$body['aps']['badge'] = $badge;
// SSL証明書
$cert = '********.pem';
$url = 'ssl://gateway.sandbox.push.apple.com:2195'; // 開発用
//$url = 'ssl://gateway.push.apple.com:2195'; // 本番用
$context = stream_context_create();
stream_context_set_option( $context, 'ssl', 'local_cert', $cert );
$fp = stream_socket_client( $url, $err, $errstr, 60, STREAM_CLIENT_CONNECT, $context );
if( !$fp ) {
echo 'Failed to connect.' . PHP_EOL;
exit( 1 );
}
$payload = json_encode( $body );
$message = chr( 0 ) . pack( 'n', 32 ) . pack( 'H*', $deviceToken ) . pack( 'n', strlen($payload ) ) . $payload;
print 'send message:' . $payload . PHP_EOL;
fwrite( $fp, $message );
fclose( $fp );
ソースコード
gistにあげました。
https://gist.github.com/sawapi/a7cee65e4ad95578044d
(´・ω・`)
ここまで書いて気づいたんですが、registerForRemoteNotificationTypesメソッドは
iOS8からDeprecatedになってるんですね。。。
試しに新しいやり方でやってみましたがうまくいかない、、というか
やり方がよくわかりませんでした。
var types: UIUserNotificationType = UIUserNotificationType.Badge |
UIUserNotificationType.Alert |
UIUserNotificationType.Sound
var settings: UIUserNotificationSettings = UIUserNotificationSettings.settingsForTypes( types, categories: nil )
application.registerUserNotificationSettings( settings )
application.registerForRemoteNotifications()
これでできると思ったんですが、こんなエラーがでます(´・ω・`)
'settingsForTypes' is unavailable: use object construction 'UIUserNotificationSettings(forTypes:categories:)'
UIUserNotificationSettings.settingsForTypes
Objective-Cだとこんな感じでうまくいってるみたいなんですが。。
http://stackoverflow.com/questions/24049266/get-the-push-notification-list-on-ios8
やり方わかったら書き直します(´・ω・`)
※6/13追記
やり方分かりました。
エラーログにちゃんと書いてあるのに気付かなかった。。。
func application( application: UIApplication, didFinishLaunchingWithOptions launchOptions: NSDictionary? ) -> Bool {
var types: UIUserNotificationType = UIUserNotificationType.Badge |
UIUserNotificationType.Alert |
UIUserNotificationType.Sound
var settings: UIUserNotificationSettings = UIUserNotificationSettings( forTypes: types, categories: nil )
application.registerUserNotificationSettings( settings )
application.registerForRemoteNotifications()
return true
}
これでできそうですー!