2016-09-23 5 views
6

Интересно, можно ли отправлять push-уведомления на мобильные устройства Android каждый раз, когда Firebase добавляет новый ребенок на определенную сущность. Например, предположим, что существует объект Firebase под названием Tasks. Всякий раз, когда новая задача добавляется к этой коллекции firebase, происходит событие «child_added», а затем, в некотором роде, push-уведомление отправляется мобильному клиенту. Триггер - это событие child_added. Тем не менее, я не уверен, возможна ли отправка push-уведомления прямо из событий Firebase.Как отправить уведомление клиенту, когда Firebase имеет новую запись?

+0

Есть несколько руководств по отправке уведомлений между устройствами? Эта ссылка (https://firebase.googleblog.com/2016/08/sending-notifications-between-android. html) очень полезен, но я не знаю, как его использовать. – Carlo

ответ

6

Вы можете сделать очень простой Node.js сервер или Java Servlet (на основе вашего языковые предпочтения), то с помощью сервера firebase sdk вы можете добавить childEventListener. При изменении значения вы можете использовать FCM для отправки push-уведомлений с использованием протокола http. Я использую это в своем приложении, и это очень возможно и надежно.

Примечание: Если вы используете этот поток для приложения для Android, то использование java-сервера sdk будет полезным, поскольку оно почти похоже на то, что у вас есть на android.

EDIT: После получения некоторого внимания в этом ответе я решил поделиться дополнительной информацией относительно того же.

// Пример node.js сервера, как показано на this official firebase blog

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-сервлет - это всего лишь персональный тест. Некоторые части были отредактированы или удалены, чтобы дать представление о его настройке, это никоим образом не готовый сервлет пожалуйста, не просто скопируйте - вставьте. Я рекомендую вам понять и построить свои собственные ».

1

Edit: вы должны смотреть на Firebase Cloud Functions, который позволит вам сделать это без того, чтобы создать сервер Node.js

Смежные вопросы