【问题标题】:How to push notification to client when Firebase has a new entry?Firebase有新条目时如何向客户端推送通知?
【发布时间】:2017-02-01 21:33:30
【问题描述】:

我想知道是否可以在 Firebase 在特定实体上添加新子项时向 Android 移动设备发送推送通知。 例如,假设 Firebase 上有一个名为 Tasks 的实体。每当向该 firebase 集合添加新任务时,都会触发“child_added”事件,然后以某种方式向移动客户端发送推送通知。 触发器是 child_added 事件。但是,我不确定直接从 Firebase 事件发送推送通知是否可行。

【问题讨论】:

标签: android firebase push-notification


【解决方案1】:

编辑:您应该看看Firebase Cloud Functions,它让您无需创建 Node.js 服务器即可完成此操作

【讨论】:

    【解决方案2】:

    您可以制作一个非常简单的 node.js 服务器或 java servlet(根据您的语言偏好),然后使用 firebase server sdk 添加 childEventListener。当值更改时,您可以使用 FCM 使用 http 协议发送推送通知。我在我的应用程序中使用它,它非常可行和可靠。

    注意:如果您将此流程用于 android 应用程序,那么使用 java server sdk 将是有益的,因为它与您在 android 上的几乎相似。

    编辑:在得到一些关于这个答案的关注之后,我想分享一些关于相同的更多信息。

    //this official firebase blog 上看到的示例 node.js 服务器

    var firebase = require('firebase');
    var request = require('request');
    
    var API_KEY = "..."; // Your Firebase Cloud Server API key
    
    firebase.initializeApp({
      serviceAccount: ".json",
      databaseURL: "https://.firebaseio.com/"
    });
    ref = firebase.database().ref();
    
    function listenForNotificationRequests() {
      var requests = ref.child('notificationRequests');
      ref.on('child_added', function(requestSnapshot) {
        var request = requestSnapshot.val();
        sendNotificationToUser(
          request.username, 
          request.message,
          function() {
            request.ref().remove();
          }
        );
      }, function(error) {
        console.error(error);
      });
    };
    
    function sendNotificationToUser(username, message, onSuccess) {
      request({
        url: 'https://fcm.googleapis.com/fcm/send',
        method: 'POST',
        headers: {
          'Content-Type' :' application/json',
          'Authorization': 'key='+API_KEY
        },
        body: JSON.stringify({
          notification: {
            title: message
          },
          to : '/topics/user_'+username
        })
      }, function(error, response, body) {
        if (error) { console.error(error); }
        else if (response.statusCode >= 400) { 
          console.error('HTTP Error: '+response.statusCode+' - '+response.statusMessage); 
        }
        else {
          onSuccess();
        }
      });
    }
    
    // start listening
    listenForNotificationRequests();
    

    //示例测试 java servlet 我只是为了演示这个用例

    @WebServlet("/TestServlet")
    public class MainServlet extends HttpServlet {
        * @see HttpServlet#HttpServlet()
             */
            public MainServlet() {
                super();
    
            }
    
            /**
             * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse
             *      response)
             */
            protected void doGet(HttpServletRequest request, HttpServletResponse response)
                    throws ServletException, IOException {
    
                // Get context and then relative path to saved json config file from
                // firebase
                ServletContext context = getServletContext();
                String fullPath = context.getRealPath(FILE_PATH_FOR_JSON_SERVER_AUTH);
    
    
                // Check if we actually got a file from above path
                if (fullPath != null) {
    
                } else {
    
                }
    
                // Setup connection to firebase database here
                FirebaseOptions options = new FirebaseOptions.Builder().setServiceAccount(new FileInputStream(fullPath))
                        .setDatabaseUrl(FIREBASE_DATABSE_URL).build();
    
    
                // Check to make sure we don't initialize firebase app each time webpage
                // is refreshed
                if (!exists) {
    
                    // If firebase app doesn't exist then initialize it here and set
                    // exists to true
                    FirebaseApp.initializeApp(options);
                    exists = true;
    
    
    
                }
    
    
            // Call this to begin listening *notify* node in firebase database for notifications
                addNotificationListener(request, response);
    
    
            }
    
            /**
             * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse
             *      response)
             */
            protected void doPost(HttpServletRequest request, HttpServletResponse response)
                    throws ServletException, IOException {
    
                // Build apache httpclient POST request
                HttpClient client = HttpClientBuilder.create().build();
                HttpPost post = new HttpPost(ENDPOINT_URL);
    
    
                //Get the required id stored in lastMsgId tree map here
                if (!(chatLogs.getLastMsgIdTreeMap().isEmpty())) {
    
    
                    sendToID = chatLogs.getLastMsgIdTreeMap().firstKey();
                    lstmsg = chatLogs.getLastMsgIdTreeMap().get(sendToID);
                }
    
                //Set up a unique id with concatenating sendToID and lstmsg
                uniqueID = sendToID + lstmsg;
                //Set up a previous id to check with unique id. To avoid instant duplicate notifications
                previousID = fcmHelper.getPreviousid();
    
                // Check uniqueId and PreviousID beforeSending
                if (!(uniqueID.equals(previousID))) {
                    fcmHelper.setPreviousid(uniqueID);
    
                    //Check if device token and user Id hashmap is not null
                    if (!(userLogs.getUserIdAndFcmTokenHashMap().isEmpty())) {
    
                        //Get the device token of sendTo Id here
                        deviceToken = userLogs.getUserIdAndFcmTokenHashMap().get(sendToID);
    
                        // Create JSON object for downstream data/notification
                        JSONObject mainNotificationJsonObj = new JSONObject();
                        JSONObject outerBaseJsonObj = new JSONObject();
                        try {
    
                            // Notification payload has 'title' and 'body' key
                            mainNotificationJsonObj.put(TITLE, NEW_MESSAGE_RECEIVED);
                            mainNotificationJsonObj.put(BODY, lstmsg);
                            mainNotificationJsonObj.put(NOTIFICATION_SOUND, NOTIFICATION_SOUND_TYPE_DEFAULT);
                            //mainNotificationJsonObj.put(TAG, fcmHelper.getFcmTagId());
                            System.out.println("This is sentBy id =" + fcmHelper.getFcmTagId());
    
                            // This will be used in case of both 'notification' or 'data' payload
                            outerBaseJsonObj.put(TO, deviceToken);
    
    
                            // Set priority of notification. For instant chat setting
                            // high will
                            // wake device from idle state - HIGH BATTERY DRAIN
                            outerBaseJsonObj.put(PRIORITY_KEY, PRIORITY_HIGH);
    
                            // Specify required payload key here either 'data' or
                            // 'notification'. We can even use both payloads in single
                            // message
                            outerBaseJsonObj.put(NOTIFICATION, mainNotificationJsonObj);
                        } catch (JSONException e) {
    
                            e.printStackTrace();
                        }
    
    
                        // Setup http entity with json data and 'Content-Type' header
                        StringEntity requestEntity = new StringEntity(outerBaseJsonObj.toString(),
                                ContentType.APPLICATION_JSON);
    
                        // Setup required Authorization header
                        post.setHeader(AUTHORIZATION, FIREBASE_SERVER_KEY);
    
                        // Pass setup entity to post request here
                        post.setEntity(requestEntity);
    
                        // Execute apache http client post response
                        HttpResponse fcmResponse = client.execute(post);
    
    
                        // Get status code from FCM server to debug error and success
                        System.out.println(RESPONSE_CODE + fcmResponse.getStatusLine().getStatusCode());
    
                        // Get response entity from FCM server and read throw lines
                        BufferedReader rd = new BufferedReader(new InputStreamReader(fcmResponse.getEntity().getContent()));
    
                        StringBuffer result = new StringBuffer();
                        String line = "";
                        while ((line = rd.readLine()) != null) {
                            result.append(line);
                        }
    
                        if (response != null) {
    
                            // Print out the response to webpage
                            PrintWriter out;
                            out = response.getWriter();
                            out.println(result);
                            System.out.println("This is Result - " + result);
                        }
                    } else {
                        //Abort this process if conditions not met
                        post.abort();
                        System.out.println(THIS_MSG_ALREADY_SENT);
                    }
    
                }
    
            }
    
    
    
    
    
            /*
             * This is the main method to be called to setup notifications listener on server startup
             */
    
            private void addNotificationListener(HttpServletRequest request, HttpServletResponse response) {
    
    
                //Initialize Value event listener 
                lastMsgListener = new ValueEventListener() {
    
                    @Override
                    public void onDataChange(DataSnapshot arg0) {
    
                        // Clear idLastMessagerecivedhash map if not null
                        if (lastMsgIdTreeMap != null) {
                            lastMsgIdTreeMap.clear();
                        }
    
    
    
                        //Get lastmsg to be sent as notification here
                        lstmsg = (String) arg0.child(LAST_MESSAGE).getValue();
    
                        //Get sendToID here
                        String sendToID = (String) arg0.child(SEND_TO).getValue();
    
                        //Get Sent by ID here
                        sentBy = (String) arg0.child(SENT_BY).getValue();
    
                        //Set fcmTag ID here
                        fcmHelper.setFcmTagId(sentBy);
    
                        //Check if lstmsg is not null
                        if (lstmsg != null) {
    
                            // Create lastmsgTimestampHashMap here
                            lastMsgIdTreeMap.put(sendToID, lstmsg);
    
    
    
                        }
                        //Check for null again
                        if (lastMsgIdTreeMap != null) {
    
                            chatLogs.setLastMsgIdTreeMap(lastMsgIdTreeMap);
    
                        }
    
                        try {
                            doPost(request, response);
                        } catch (ServletException e) {
    
                            e.printStackTrace();
                        } catch (IOException e) {
    
                            e.printStackTrace();
                        }
    
    
                    }
    
                    @Override
                    public void onCancelled(DatabaseError arg0) {
    
                    }
                };
    
                //Set up database reference to notify node here
                messageRef = FirebaseDatabase.getInstance().getReference().child(NOTIFY);
    
                //Add value listener to database reference here
                messageRef.addValueEventListener(lastMsgListener);
    
    
    
            }
    

    “Java servlet 只是一个个人测试。某些部分已被编辑或删除,只是为了说明它的设置这绝不是生产就绪的 servlet,请不要只是复制粘贴。我鼓励你去理解和建立你自己的。”

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-07-26
      • 1970-01-01
      • 1970-01-01
      • 2011-07-30
      相关资源
      最近更新 更多