错误请求 [400],FCM 旧版 HTTP API 与改造
Bad Request [400], FCM Legacy HTTP API with Retrofit
URL = https://fcm.googleapis.com/fcm/send
请求正文
{
"registration_ids": ["token 1","token 2"],
"priority": "high",
"notification": {
"title": "Divine Public School",
"body": "Test Message."
} }
页眉
{
"Content-Type: application/json",
"Authorization: key=<myServerKey>"
}
我收到状态代码 200,甚至在从 Postman 点击 url 时在客户端应用程序中收到通知。但是当我尝试在 android 中使用 retrofit 做同样的事情时,我得到状态 400 Bad Request.
Android 下面的代码
interface NotificationService {
@Headers("Content-Type: application/json",
"Authorization: key=<my server key>")
@POST("fcm/send")
fun sendNotification(@Body body: NotificationBody): Call<ResponseBody> }
数据Class
data class NotificationBody(
@SerializedName("registration_ids")
var registration_ids : ArrayList<String>,
@SerializedName("priority")
var priority:String,
@SerializedName("notification")
var notification:Notification )
data class Notification(
@SerializedName("title")
var title:String,
@SerializedName("body")
var body:String )
改造调用
val generalRetrofit = Retrofit.Builder()
.addConverterFactory(GsonConverterFactory.create())
.baseUrl("https://fcm.googleapis.com/")
.build()!!
val service = generalRetrofit.create(NotificationService::class.java)
val data = NotificationBody(....)
val call = service.sendNotification(data)
call.enqueue(object : Callback<ResponseBody> {
override fun onFailure(call: Call<ResponseBody>, t: Throwable) {}
override fun onResponse(call: Call<ResponseBody>,response: Response<ResponseBody>)
{
Log.d("TAG", response.code().toString())
})
NotificationBody 对象的日志输出
D/TAG: NotificationBody(registration_ids=[cxd-PHM-QOyLcnLcPozjKA:APA91bGIG-NDg-hSYMlTGWm-ZVaM0hR7Om77CaksvZ4bLDKM0gU_xYk9_Um1aOzPExGR40FeHAqQpkjt_7-HiG8SMPtF5HLrUjCrcD4Asq_ZcEv-Du5AcMthcYjaZjisduLkBPhgPH0b], priority=higher, notification=Notification(title=Divine Public School, body=Hello))
不是一个合适的解决方案,但在我现有的 Node 项目中做了一个终点。
任何遇到此问题的人都可以使用它。
URLhttps://pankaj-oil-api.herokuapp.com/notify
您需要 post 这个对象在上面 url。
"registration_ids" 是一个字符串数组,可以包含最少 1 个和最多 1000 个标记。
{
"registration_ids" : ["Client Token 1","Client Token 2"],
"serverKey": "<Your (Authorization) Server Key Here>",
"title": "<Enter your Notification Title here >",
"msg":"<Enter your Notification Message here >"
}
这只是一个临时解决方案。仍在寻找解决方案。
用 rxJava 制作,它会工作。重要的一点是使用 'condition'
interface NotificationService {
@Headers("Content-Type: application/json",
"Authorization: key=<my server key>")
@POST("fcm/send")
fun sendNotification(@Body body: NotificationBody): Single<Any> }
数据class
data class NotificationMultipleBody(
@SerializedName("condition")
var condition : String,
@SerializedName("priority")
var priority:String,
@SerializedName("notification")
var notification:Notification
)
data class Notification(
@SerializedName("body")
var body:String,
@SerializedName("sound")
var sound:String
)
改造
class ApiClient {
private val BASE_URL = "https://fcm.googleapis.com/"
private val api = Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.addCallAdapterFactory(RxJava3CallAdapterFactory.create())
.build()
.create(NotificationHelper::class.java)
fun sendNotification(tokens:ArrayList<String>,msg: String): Single<Any> {
var topicStr = ""
tokens.forEachIndexed { index, str ->
topicStr += if(index==tokens.size-1){
"'$str' in topics"
} else {
"'$str' in topics || "
}
}
val notif = Notification(
msg,"default"
)
val notifBody = NotificationMultipleBody(
topicStr,"high",notif
)
return api.sendNotification(notifBody)
}
}
通知发送部分
private val pushHelper = ApiClient()
private val disposable = CompositeDisposable()
private val tokenList = ArrayList<String>()
disposable.add(pushHelper.sendNotification(tokenList,message).subscribeOn(Schedulers.newThread()).observeOn(
AndroidSchedulers.mainThread()).subscribeWith(object :
DisposableSingleObserver<Any>(){
override fun onSuccess(t: Any) {
binding.btnBackFriend.performClick()
Log.d("logD","multiple notification sent success")
Log.d("logD","$t")
}
override fun onError(e: Throwable) {
binding.btnBackFriend.performClick()
Log.d("logD","sent fail")
val error = e as HttpException
Log.d("logD", "${error.response()?.errorBody()?.string()}")
}
}))
URL = https://fcm.googleapis.com/fcm/send
请求正文
{
"registration_ids": ["token 1","token 2"],
"priority": "high",
"notification": {
"title": "Divine Public School",
"body": "Test Message."
} }
页眉
{
"Content-Type: application/json",
"Authorization: key=<myServerKey>"
}
我收到状态代码 200,甚至在从 Postman 点击 url 时在客户端应用程序中收到通知。但是当我尝试在 android 中使用 retrofit 做同样的事情时,我得到状态 400 Bad Request.
Android 下面的代码
interface NotificationService {
@Headers("Content-Type: application/json",
"Authorization: key=<my server key>")
@POST("fcm/send")
fun sendNotification(@Body body: NotificationBody): Call<ResponseBody> }
数据Class
data class NotificationBody(
@SerializedName("registration_ids")
var registration_ids : ArrayList<String>,
@SerializedName("priority")
var priority:String,
@SerializedName("notification")
var notification:Notification )
data class Notification(
@SerializedName("title")
var title:String,
@SerializedName("body")
var body:String )
改造调用
val generalRetrofit = Retrofit.Builder()
.addConverterFactory(GsonConverterFactory.create())
.baseUrl("https://fcm.googleapis.com/")
.build()!!
val service = generalRetrofit.create(NotificationService::class.java)
val data = NotificationBody(....)
val call = service.sendNotification(data)
call.enqueue(object : Callback<ResponseBody> {
override fun onFailure(call: Call<ResponseBody>, t: Throwable) {}
override fun onResponse(call: Call<ResponseBody>,response: Response<ResponseBody>)
{
Log.d("TAG", response.code().toString())
})
NotificationBody 对象的日志输出
D/TAG: NotificationBody(registration_ids=[cxd-PHM-QOyLcnLcPozjKA:APA91bGIG-NDg-hSYMlTGWm-ZVaM0hR7Om77CaksvZ4bLDKM0gU_xYk9_Um1aOzPExGR40FeHAqQpkjt_7-HiG8SMPtF5HLrUjCrcD4Asq_ZcEv-Du5AcMthcYjaZjisduLkBPhgPH0b], priority=higher, notification=Notification(title=Divine Public School, body=Hello))
不是一个合适的解决方案,但在我现有的 Node 项目中做了一个终点。 任何遇到此问题的人都可以使用它。 URLhttps://pankaj-oil-api.herokuapp.com/notify
您需要 post 这个对象在上面 url。 "registration_ids" 是一个字符串数组,可以包含最少 1 个和最多 1000 个标记。
{
"registration_ids" : ["Client Token 1","Client Token 2"],
"serverKey": "<Your (Authorization) Server Key Here>",
"title": "<Enter your Notification Title here >",
"msg":"<Enter your Notification Message here >"
}
这只是一个临时解决方案。仍在寻找解决方案。
用 rxJava 制作,它会工作。重要的一点是使用 'condition'
interface NotificationService {
@Headers("Content-Type: application/json",
"Authorization: key=<my server key>")
@POST("fcm/send")
fun sendNotification(@Body body: NotificationBody): Single<Any> }
数据class
data class NotificationMultipleBody(
@SerializedName("condition")
var condition : String,
@SerializedName("priority")
var priority:String,
@SerializedName("notification")
var notification:Notification
)
data class Notification(
@SerializedName("body")
var body:String,
@SerializedName("sound")
var sound:String
)
改造
class ApiClient {
private val BASE_URL = "https://fcm.googleapis.com/"
private val api = Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create())
.addCallAdapterFactory(RxJava3CallAdapterFactory.create())
.build()
.create(NotificationHelper::class.java)
fun sendNotification(tokens:ArrayList<String>,msg: String): Single<Any> {
var topicStr = ""
tokens.forEachIndexed { index, str ->
topicStr += if(index==tokens.size-1){
"'$str' in topics"
} else {
"'$str' in topics || "
}
}
val notif = Notification(
msg,"default"
)
val notifBody = NotificationMultipleBody(
topicStr,"high",notif
)
return api.sendNotification(notifBody)
}
}
通知发送部分
private val pushHelper = ApiClient()
private val disposable = CompositeDisposable()
private val tokenList = ArrayList<String>()
disposable.add(pushHelper.sendNotification(tokenList,message).subscribeOn(Schedulers.newThread()).observeOn(
AndroidSchedulers.mainThread()).subscribeWith(object :
DisposableSingleObserver<Any>(){
override fun onSuccess(t: Any) {
binding.btnBackFriend.performClick()
Log.d("logD","multiple notification sent success")
Log.d("logD","$t")
}
override fun onError(e: Throwable) {
binding.btnBackFriend.performClick()
Log.d("logD","sent fail")
val error = e as HttpException
Log.d("logD", "${error.response()?.errorBody()?.string()}")
}
}))