개발자의 끄적끄적

[android] FCM 웹(JAVA)서버에서 푸시메세지 보내기 [펌] 본문

개발/java & jsp

[android] FCM 웹(JAVA)서버에서 푸시메세지 보내기 [펌]

효벨 2020. 6. 7. 00:06
728x90
반응형

[android] FCM 웹(JAVA)서버에서 푸시메세지 보내기 [펌]

 

안드로이드의 기존 GCM에서 FCM으로 바뀌었다

 

구글 클라우드 메세지에서 파이어베이스 클라우드 메세지로 바뀐건진 정확히 모르겠지만..

 

 

일단 뜬금없이 웹개발하다가 갑자기 회사에서 안드로이드 개발할 일이 생겼지만

 

웹뷰로 때워버리자! 라고 외친 후 만들어 놓고 보니 안드로이드 알림 메세지가 가야 한단다...

 

 

하....

 

그래서 뭐 삽질좀 하고 여기저기 뒤적뒤적이면서 구현을 했다

 

 

 

일단 가장 먼저

 

https://console.firebase.google.com/u/0/

 

당연히 구글 아이디는 있을것이지 콘솔 파이어베이스로 들어가

 

알람메세지 구현알 어플을 등록해준다.

 

이곳의 도움을 많이 받았다. 기초 설정은 여기 보고 따라하자

 

사실 저 블로그만 봐도

 

어지간하면 구현 가능하다.

 

 

진짜 생각보다 좀 간단하다.

 

 

1. Android 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

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

import android.content.SharedPreferences;

import android.util.Log;

 

import com.google.firebase.iid.FirebaseInstanceId;

import com.google.firebase.iid.FirebaseInstanceIdService;

 

import java.io.IOException;

 

import okhttp3.FormBody;

import okhttp3.OkHttpClient;

import okhttp3.Request;

import okhttp3.RequestBody;

 

 

public class MyFirebaseInstanceIDService extends FirebaseInstanceIdService {

 

    private static final String TAG = "MyFirebaseIIDService";

 

    /**

     * Called if InstanceID token is updated. This may occur if the security of

     * the previous token had been compromised. Note that this is called when the InstanceID token

     * is initially generated so this is where you would retrieve the token.

     */

    // [START refresh_token]

    @Override

    public void onTokenRefresh() {

        // 설치할때 여기서 토큰을 자동으로 만들어 준다

        String refreshedToken = FirebaseInstanceId.getInstance().getToken();

        Log.d(TAG, "Refreshed token: " + refreshedToken);

 

        // 생성한 토큰을 서버로 날려서 저장하기 위해서 만든거

        sendRegistrationToServer(refreshedToken);

    }

    

    private void sendRegistrationToServer(String token) {

        // Add custom implementation, as needed.

 

        // OKHTTP를 이용해 웹서버로 토큰값을 날려준다. 

        OkHttpClient client = new OkHttpClient();

        RequestBody body = new FormBody.Builder()

                .add("Token", token)

                .build();

 

        //request

        Request request = new Request.Builder()

                .url("토큰 저장할라고 보낼 URL")

                .post(body)

                .build();

 

        try {

            client.newCall(request).execute();

        } catch (IOException e) {

            e.printStackTrace();

        }

 

    }

}

Colored by Color Scripter

cs

 

 

 

여기서 우리가 잘 봐야 할 건

 

30번 라인과 

 

37번라인의 sendRegistrationToServer 메소드다

 

30번라인에서 토큰을 생성하는데 여기선 어플을 설치할때 한번 생성한다.

 

그럼 만들어지자마자 

 

37번라인 메소드로 날려서 HTTP로 전송한다.

 

그럼 웹서버에서 저 토큰을 받고 저장을 하게 되고

 

그 해당 토큰으로 메세지를 날려주면 되는 것이다.

 

 

 

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

import android.app.NotificationManager;

import android.app.PendingIntent;

import android.content.Context;

import android.content.Intent;

import android.media.RingtoneManager;

import android.net.Uri;

import android.support.v4.app.NotificationCompat;

 

import com.google.firebase.messaging.RemoteMessage;

 

 

public class MyFirebaseMessagingService extends com.google.firebase.messaging.FirebaseMessagingService {

    private static final String TAG = "FirebaseMsgService";

 

    // [START receive_message]

    @Override

    public void onMessageReceived(RemoteMessage remoteMessage) {

 

        //추가한것

        sendNotification(remoteMessage.getData().get("message"));

    }

 

    private void sendNotification(String messageBody) {

        Intent intent = new Intent(this, MainActivity.class);

        intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);

        PendingIntent pendingIntent = PendingIntent.getActivity(this0 /* Request code */, intent,

                PendingIntent.FLAG_ONE_SHOT);

 

        Uri defaultSoundUri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);

        NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)

                .setSmallIcon(R.mipmap.ic_launcher)

                .setContentTitle("FCM Push Test"// 이부분은 어플 켜놓은 상태에서 알림 메세지 받으면 저 텍스트로 띄워준다.

                .setContentText(messageBody)

                .setAutoCancel(true)

                .setSound(defaultSoundUri)

                .setContentIntent(pendingIntent);

 

        NotificationManager notificationManager =

                (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

 

        notificationManager.notify(0 /* ID of notification */, notificationBuilder.build());

    }

 

}

 

Colored by Color Scripter

cs

MyFirebaseMessagingService.java 얘는 알림메세지를 받았을때 처리하는건데

사실 딱히 건들일거 없이 그대로 사용 하면 된다.

 

 

 

 

 

 

 

일단 저 블로그에서

 

MyFirebaseInstanceIDService.java 와

MyFirebaseMessagingService.java

 

 

이 두개를 구현했다면 

 

 

 

여기로 들어와서 앱단위로 앱선택하고 보내면

 

모든 앱 설치자들에게 메세지가 날아간다.

 

 

하지만 우린 웹서버에서 푸시메세지를 날려주고 싶을 것이다.

 

알람이라면 뭐 값이 변한다거나 새로운 정보가 등록 되었을때 날려줘야 하니까

 

그때마다 저기 접속해서 날려주기엔 너무 귀찮으니까 분명히

 

웹서버에서 인터벌을 돌리든 트리거를 걸든 해서 웹서버에서 날려주고 싶을 것이다

 

그런데 웹서버에서 날려주는건

 

잘 안나와있고 복사 붙여넣기 해도 안되는 경우도 있고 하니까

 

내가 해서 성공한 코드를 보자

 

 

 

 

 

 

 

 

 

2. JAVA Web Server 

 

 

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

@RequestMapping(value="mobile/sendFCM")

    public String index(Model model, HttpServletRequest request, HttpSession session, MobileTokenVO vo)throws Exception{

            

            List<MobileTokenVO> tokenList = fcmService.loadFCMInfoList(vo); 

            

                String token = tokenList.get(count).getDEVICE_ID();

                

                final String apiKey = "파이어 베이스의 서버 API키를 여기에 넣는다";

                URL url = new URL("https://fcm.googleapis.com/fcm/send");

                HttpURLConnection conn = (HttpURLConnection) url.openConnection();

                conn.setDoOutput(true);

                conn.setRequestMethod("POST");

                conn.setRequestProperty("Content-Type""application/json");

                conn.setRequestProperty("Authorization""key=" + apiKey);

 

                conn.setDoOutput(true);

                

                String userId =(String) request.getSession().getAttribute("ssUserId");

 

                // 이렇게 보내면 주제를 ALL로 지정해놓은 모든 사람들한테 알림을 날려준다.

                String input = "{\"notification\" : {\"title\" : \"여기다 제목 넣기 \", \"body\" : \"여기다 내용 넣기\"}, \"to\":\"/topics/ALL\"}";

                

                // 이걸로 보내면 특정 토큰을 가지고있는 어플에만 알림을 날려준다  위에 둘중에 한개 골라서 날려주자

                String input = "{\"notification\" : {\"title\" : \" 여기다 제목넣기 \", \"body\" : \"여기다 내용 넣기\"}, \"to\":\" 여기가 받을 사람 토큰  \"}";

 

                OutputStream os = conn.getOutputStream();

                

                // 서버에서 날려서 한글 깨지는 사람은 아래처럼  UTF-8로 인코딩해서 날려주자

                os.write(input.getBytes("UTF-8"));

                os.flush();

                os.close();

 

                int responseCode = conn.getResponseCode();

                System.out.println("\nSending 'POST' request to URL : " + url);

                System.out.println("Post parameters : " + input);

                System.out.println("Response Code : " + responseCode);

                

                BufferedReader in = new BufferedReader(new InputStreamReader(conn.getInputStream()));

                String inputLine;

                StringBuffer response = new StringBuffer();

 

                while ((inputLine = in.readLine()) != null) {

                    response.append(inputLine);

                }

                in.close();

                // print result

                System.out.println(response.toString());

                

 

        return "jsonView";

    }

Colored by Color Scripter

cs

 

 

위의 코드처럼 쓰면 된다.

 

 

8번 라인의 API키는 

 

 

 

 

 

저 파이어베이스 콘솔에서 빨간동그라미 누르고 프로젝트 설정의 클라우드 메세징으로 가면

 

서버키가 나와있다 그 서버키를 넣으면 된다. 

 

 

 

그런데 20번 21번 라인의  주제가 ALL인걸 어떻게 지정 하냐고?

 

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

 protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

 

 

        // 웹뷰 셋팅팅

       mWebView = (WebView)findViewById(webView);

        mWebView.getSettings().setJavaScriptEnabled(true);

 

        mWebView.loadUrl(myUrl+"/mobile/login");

        mWebView.setWebChromeClient(new WebChromeClient());

        mWebView.setWebViewClient(new WebViewClientClass());

 

        mWebView.addJavascriptInterface(new AndroidBridge(), "android");

 

 

        //이렇게 ALL 추가 하면 이 디바이스는 ALL을 구독한다는 얘기가 된다.

        FirebaseMessaging.getInstance().subscribeToTopic("ALL");

 

    }

Colored by Color Scripter

cs

 

 

안드로이드의 MainActivity.java 의 oncreate에다가 저 18번 라인을 추가 해주자

 

그런데 주제 등록은 즉시 안되고 몇시간 기다리거나 몇일 기다려야 등록 되는 경우도

 

있다고 하니까 급하게 하진 말자.

 

그리고 24번 라인에 들어가는 토큰은 MyFirebaseInstanceIDService.java 의 36번 메소드에 날려준 값이다

 

 

출처: https://yamea-guide.tistory.com/entry/안드로이드-FCM-푸시메세지-웹서버JAVA에서-보내기 [기타치는 개발자의 야매 가이드]

반응형
Comments