Firebase推送通知服务端实现

Firebase控制台配置

Firebase后台创建项目,获取相关参数和配置如下

(1)点击Project Overview -> 项目设置 -> 云消息传递 中获取服务器密钥(建议,当然旧版服务器密钥也可以使用)

(2)服务账号 -> 点击生成新的私钥,获取私钥配置(json文件,丢失后可以重新生成,重新生成后需要替换旧的配置)

(3)Database -> 以测试模式创建数据库 -> 选择 Realtime Database 获得数据库url

发送推送通知

参考:https://fcm.googleapis.com/fcm/send

要发送消息,应用服务器需发出POST请求。例如:

请求地址:https://fcm.googleapis.com/fcm/send

HTTP请求头必须包含:

1
2
Authorization: key=YOUR_SERVER_KEY
Content-Type: application/json 或 application/x-www-form-urlencoded;charset=UTF-8(纯文本格式)。如果省略Content-Type,即视为纯文本格式

HTTP 正文内容取决于您使用的是 JSON 还是纯文本。有关 JSON 或纯文本消息中可能包含的所有参数列表,请参阅服务器参考。
https://firebase.google.com/docs/cloud-messaging/http-server-ref?hl=zh-cn#params

(1) 可以使用to单个推送,也可以使用registration_ids批量发送,但是做多1000个token
(2) 给多个人推,有两种:一种是给组推,一种是给主题推

Node.js实现

1
2
3
# node install firebase
# node install request
# node fcm.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
var firebase = require('firebase');
var request = require('request');

var API_KEY = 'AAAA8mBttg8:APA91bFv9xob7x7-lBRqDwYdd1IbR5DcqUUmQE8t_cWKJSA5WjNbbp0jOWpCCHnarD2JV3MGyqEM3DfQGd8Kvt5swlGJlGqRoPGFPaSrNn44ZzLLz-HotPRzd08koeJf5bshdPzxKoq1';

var token = 'chPUpTJMeS8:APA91bGlo27OQVskyiqlXvDQGulrIFi9iIpowsjsrKe-0k5rilbjfB3WADSzujtZH3u-HEPcNMZiHZd7j8-CpXauLY39-u8m9kllLxOOo9Ja1LFAtmSB3vXKhiJAwQC31BlhSqILvSqb';

firebase.initializeApp({
serviceAccount: "pandadeal-firebase-push.json",
databaseURL: "https://panda-deal-ios.firebaseio.com/"
});

var payload = {
//to: token,
to: '/topics/activity',
notification: {
body: "通知内容",
title: "Firebase Cloud Message",
data: {'type': 'test', 'path': '/home'}
}
}

setTimeout(function (args) {
sendNotificationToUser(payload);
}, 200);

function sendNotificationToUser(message, onSuccess) {
request({
url: 'https://fcm.googleapis.com/fcm/send',
method: 'POST',
headers: {
'Content-Type' : 'application/json',
'Authorization': 'key=' + API_KEY
},
body: JSON.stringify(message)
}, function(error, response, body) {
if (error) {
console.log('---message send error---', error);
}
else if (response.statusCode >= 400) {
console.log('HTTP Error: ' + response.statusCode + ' - ' + response.statusMessage);
}
else {
console.log(body)
console.log('---message send success---')
onSuccess && onSuccess();
}
});
}

Java实现

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
public class TestFireBase {

public final static String AUTH_KEY_FCM= ""; //App服务密钥

public final static String API_URL_FCM = "https://fcm.googleapis.com/fcm/send"; //谷歌推送地址

public static void main(String[] args) {
pushFCMNotification();
}

public static void pushFCMNotification() {
try {
URL url = new URL(API_URL_FCM);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setUseCaches(false);
conn.setDoInput(true);
conn.setDoOutput(true);
conn.setRequestMethod("POST");
conn.setRequestProperty("Authorization", "key="+AUTH_KEY_FCM);
conn.setRequestProperty("Content-Type", "application/json"); //不设置默认发送文本格式
JSONObject json = new JSONObject();
json.put("to", "App Token"); //单一推送
//json.put("registration_ids", tokens); //批量推送,最多1000个token,此处的tokens是一个token JSONArray数组
JSONObject info = new JSONObject();
info.put("title", "Notification Tilte");
info.put("body", "Hello Test Notification");
info.put("icon", "myicon");
json.put("notification", info); //json还可以put其他参数

OutputStreamWriter wr = new OutputStreamWriter(conn.getOutputStream());
wr.write(json.toString());
wr.flush();
BufferedReader reader = new BufferedReader(new InputStreamReader(conn.getInputStream()));
String line = null;
while ((line = reader.readLine())!= null) {
System.out.println(line);
}
wr.close();
reader.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}

PHP实现

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
namespace App\Http\Controllers;

use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;

use cn\appblog\fcm\Client;
use cn\appblog\fcm\Message;
use cn\appblog\fcm\Recipient\Device;
use cn\appblog\fcm\Notification;

class FcmController extends Controller {

private $apikey;
public function __construct()
{
$this->apikey = 'API_KEY';
}

//用Fcm推送消息
public function push($content='', $fcmtoken='')
{
$apiKey = $this->apikey;
$client = new Client();
$client->setApiKey($apiKey);
$client->injectHttpClient(new \GuzzleHttp\Client());

//$note = new Notification('test title', '现在时间是 '.date('Y-m-d H:i:s'));
$note = new Notification('', $content);
$note->setIcon('smile')
->setColor('#ffffff')
->setBadge(1);

$message = new Message();
$message->addRecipient(new Device($fcmtoken));
$message->setNotification($note)
->setData(array('someId' => 11112));
$message->setNotification($note);

$response = $client->send($message);
var_dump($response->getStatusCode());
}

/**
* @param array $requestData
* @return bool
*/
public function old_insertIntoGroup($requestData=[])
{
if(!$requestData['tuid'] || !$requestData['version'] || !$requestData['fcmtoken']) {
return false;
}

//创建和添加设备组的url
$url = 'https://android.googleapis.com/gcm/notification';

$header = [
'Content-Type:application/json',
'Authorization:key = '.$this->apikey,
'project_id: 项目id',
];
$groupkey = '';
//先查找表中最近新的设备组的key,若key里面的子账号已经达到一定数目,就新建一个组
$gdata=DB::select('select count(id) num,groupkey from zeai_andro_push group by groupkey order by id desc limit 1;');
//$gdata=DB::select('select groupkey from zeai_andro_push order by id desc limit 1;');

//确保能有推送fcmtoken
if(!DB::table('zeai_andro_push')->where(['tuid'=>$requestData['tuid']])->count(['id'])) {
$requestData['groupkey'] = $gdata[0]->groupkey;
DB::table('zeai_andro_push')->insertGetId($requestData);
}
$groupkey=$gdata[0]->groupkey;
$data = [
"operation"=>"add",
"notification_key_name"=> "appUser-Chris", //设备组名
"notification_key"=>$groupkey,
"registration_ids"=>[$requestData['fcmtoken']]
];

$res = json_decode($this->http($url, $data, 'post', $header), true);
if (isset($res['notification_key'])) {
$res=DB::table('zeai_andro_push')
->where(['tuid'=>$requestData['tuid']])
->update([
'groupkey'=>$res['notification_key']
]);
return $res ? true : false;
} else {
//一个设备组是否满员未能测试
return false;
}
}

/**
* 添加用户的主题,保存用户的fcmtoken
* @param array $requestData
* @return bool
*/
public function insertIntoGroup($requestData=[])
{
if (!$requestData['tuid'] || !$requestData['version'] || !$requestData['fcmtoken']) {
return false;
}
$this->oldmyTopic($requestData['fcmtoken']);
//先查找表中最近新的设备组的key,若key里面的子账号已经达到一定数目,就新建一个组

//确保能有推送fcmtoken
if (!DB::table('zeai_andro_push')->where(['tuid'=>$requestData['tuid']])->count(['id'])) {
$requestData['groupkey'] = 0;
DB::table('zeai_andro_push')->insertGetId($requestData);
}
}

//创建设备组
public function createGroup($fcmtoken='')
{
//创建和添加设备组的 url
$url = 'https://android.googleapis.com/gcm/notification';
$header = [
'Content-Type:application/json',
'Authorization:key='.$this->apikey,
'project_id:196236249110',
];
$data = [
"operation"=>"create",
"notification_key_name"=> (string)time(),//设备组名
"registration_ids"=>[$fcmtoken]
];
$res = json_decode( $this->http($url, $data, 'post', $header), true);
return $res['notification_key'];
}

//向主题发送消息
public function sendMessageToGroup()
{
$url = 'https://fcm.googleapis.com/fcm/send';
$header = [
'Content-Type:application/json',
'Authorization:key='.$this->apikey,
'project_id:196236249110',
];
$data = [
'to'=>'/topics/主题名',
"notification"=>[
'body'=>"^_^ Come and get the coins.There are a lot of new tasks. ^_^",
'title'=>'',
'icon'=>'myicon'
],
];
$res = $this->http($url,$data,'post',$header);
var_dump($res);
}

/**
* 获取自己的主题内容
*/
private function myTopic($fcmtoken='')
{
$url='https://iid.googleapis.com/iid/info/'.$fcmtoken.'?details=true';
$header = [
//'Content-Type:application/json',
'Authorization:key='.$this->apikey,
'details:true',
];
$res=$this->http($url, '', 'get', $header);
var_dump($res);
}

/**
* 给自己添加主题 wdwdinstagram
* @param $fcmtoken
*/
private function oldmyTopic($fcmtoken)
{
$url='https://iid.googleapis.com/iid/v1/'.$fcmtoken.'/rel/topics/主题名';
$header = [
'Content-Type:application/json',
'Authorization:key='.$this->apikey,
'Content-Length: 0',
];
$this->http($url, '', 'post', $header);
}
}

注:需翻墙,否则报错SERVICE_NOT_AVAILABLE

Powered by AppBlog.CN     浙ICP备14037229号

Copyright © 2012 - 2020 APP开发技术博客 All Rights Reserved.

访客数 : | 访问量 :