안녕하세요.

앱을 만들고 있는데요.

서버에서 공지사항 등록을 하면 앱에 공지사항이 등록되었다는 Notification을 주려고 합니다.

찾아보니까 Android Cloud to Device Messaging (C2DM) 이라는 구글에서 제공하는 서비스가 있더라구요.

문서보고서 그대로 했다고 생각하는데 안되네요.ㅜㅜ 3일동안 고생하고 있습니다.


http://code.google.com/intl/ko-KR/android/c2dm/signup.html

위 링크에서 등록하고 메일 받았습니다.


그리고 제 manifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="kr.co.wizi" android:versionCode="1"
android:versionName="1.0">
       <application android:icon="@drawable/icon_7272"
android:label="@string/app_name" android:theme="@android:style/
Theme.NoTitleBar">
               <activity android:configChanges="keyboardHidden|orientation"
android:screenOrientation="portrait"
android:name="kr.co.wizi.mobile.Intro">
                       <intent-filter>
                               <action android:name="android.intent.action.MAIN"></action>
                               <category android:name="android.intent.category.LAUNCHER"></
category>
                       </intent-filter>
               </activity>
               <receiver android:name="kr.co.wizi.mobile.c2dm.C2DMReceiver"
android:permission="com.google.android.c2dm.permission.SEND">
                       <intent-filter>
                               <action android:name="com.google.android.c2dm.intent.RECEIVE"/>
                               <category android:name="kr.co.wizi.mobile.c2dm"/>
                       </intent-filter>
                       <intent-filter>
                               <action android:name="com.google.android.c2dm.intent.REGISTRATION"/
>
                               <category android:name="kr.co.wizi.mobile.c2dm"/>
                       </intent-filter>
               </receiver>
               <activity android:screenOrientation="landscape"
android:configChanges="keyboardHidden|orientation"
android:name="kr.co.wizi.mobile.MediaplayerPage"></activity>
               ...
               <activity android:screenOrientation="portrait"
android:configChanges="keyboardHidden|orientation"
android:name="kr.co.wizi.mobile.facebook.FacebookView"></activity>
               <activity android:screenOrientation="portrait"
android:configChanges="keyboardHidden|orientation"
android:name="kr.co.wizi.mobile.facebook.Feed"></activity>
               <activity android:screenOrientation="portrait"
android:configChanges="keyboardHidden|orientation"
android:name="kr.co.wizi.mobile.c2dm.PushNotification"></activity>
               <activity android:screenOrientation="portrait"
android:configChanges="keyboardHidden|orientation"
android:name="kr.co.wizi.mobile.c2dm.PushConfigure"></activity>
       </application>
       <permission
android:name="kr.co.wizi.mobile.c2dm.permission.C2D_MESSAGE"
android:protectionLevel="signature"/>
       <uses-permission
android:name="kr.co.wizi.mobile.c2dm.permission.C2D_MESSAGE"/>
       <uses-permission
android:name="com.google.android.c2dm.permission.RECEIVE"/>
       <uses-permission android:name="android.permission.INTERNET"/>
       <uses-permission
android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
       <uses-permission
android:name="android.permission.READ_EXTERNAL_STORAGE"/>
       <uses-permission
android:name="android.permission.ACCESS_NETWORK_STATE"/>
       <uses-permission android:name="android.permission.RESTART_PACKAGES"/>
       <uses-permission
android:name="android.permission.ACCESS_CHECKIN_PROPERTIES"/>
       <uses-permission android:name="android.permission.WAKE_LOCK"/>
       <uses-permission android:name="android.permission.GET_ACCOUNTS"/>
       <uses-permission android:name="android.permission.USE_CREDENTIALS"/>
       <uses-permission android:name="android.permission.READ_PHONE_STATE"/>
       <uses-sdk android:minSdkVersion="8"/>
</manifest>


버튼을 누르면 C2DM에 Push 메시지를 받겠다는 메시지를 보내는 intent

public class PushConfigure extends Activity implements OnClickListener {
    private static String HOST = "https://www.google.com/accounts/ClientLogin";
    private static String EMAIL = "XXXX@gmail.com";
    private static String PASS = "XXXX";
    private static String SOURCE = "Wizi_Smart_Mobile_Learning";
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        // TODO Auto-generated method stub
        super.onCreate(savedInstanceState);

        setContentView(R.layout.push_configure);

        Button btRegist = (Button)findViewById(R.id.c2dm_btnRegist);
        Button btUnregist = (Button)findViewById(R.id.c2dm_btnUnregist);

        btRegist.setOnClickListener(this);
        btUnregist.setOnClickListener(this);

        try{
            StringBuffer postDataBuilder = new StringBuffer();
            postDataBuilder.append("Email=" + EMAIL);
            postDataBuilder.append("&Passwd=" + PASS);
            postDataBuilder.append("&accountType=GOOGLE");
            postDataBuilder.append("&source=" + SOURCE);
            postDataBuilder.append("&service=ac2dm");
             
            byte[] postData = postDataBuilder.toString().getBytes("UTF8");
             
            URL url = new URL("HOST);
            HttpURLConnection conn = (HttpURLConnection) url.openConnection();
             
            conn.setDoOutput(true);
            conn.setUseCaches(false);
            conn.setRequestMethod("POST");
            conn.setRequestProperty("Content-Type","application/x-www-form-urlencoded");
            conn.setRequestProperty("Content-Length",Integer.toString(postData.length));
            OutputStream out = conn.getOutputStream();
            out.write(postData);
            out.close();
            BufferedReader in = new BufferedReader(   new InputStreamReader(conn.getInputStream()));

            String inputLine;
            while ((inputLine = in.readLine()) != null) {
                Log.e("inputLine", inputLine); // 여기서 AUTH_ID는 보입니다.
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    @Override
    public void onClick(View v) {
        // TODO Auto-generated method stub
        switch(v.getId()){
        case R.id.c2dm_btnRegist:
            Log.e("Register", "Register");
            //Android C2DM에Push메시지를 받겠다는메시지를보내는Intent
            //정상적으로등록이되면Android C2DM Server쪽에서 인증키를보내준다.
            //이인증키는해당어플리케이션과해당기기를대표하는인증키로서버에서메시지를보낼때사용되며
            //서버에등록을할때마다인증키는달라진다.
            Intent registrationIntent = new Intent("com.google.android.c2dm.intent.REGISTER");

            //인텐트에함께보내는내용은"app"과"sender"가있는데이두Key는 모두google에서 제시한것이기때문에
            //임의로변경이불가능하다.
            //app에는 해당어플리케이션정보를담아서보내고
            //sender에는 개발자의주소를담아서보낸다.
            registrationIntent.putExtra("app", PendingIntent.getBroadcast(this, 0, new Intent(), 0));
            registrationIntent.putExtra("sender", EMAIL);

            startService(registrationIntent);

            break;
        case R.id.c2dm_btnUnregist:
            Log.e("Unregister", "Unregister");
            //Android C2DM에Push메시지를 그만받겠다는메시지를보내는Intent
            Intent unregIntent = new Intent("com.google.android.c2dm.intent.UNREGISTER");
            unregIntent.putExtra("app", PendingIntent.getBroadcast(this, 0, new Intent(), 0));

            startService(unregIntent);

            break;
        }
    }
}


C2DM으로부터 응답을 받는 Receiver

public class C2DMReceiver extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {
        // TODO Auto-generated method stub
        Log.e("onReceive : ", "<<<<<<<<<<<<<<<<<<<<<<<<<<<<< test");
        if(intent.getAction().equals("com.google.android.c2dm.intent.REGISTRATION")){
            handleRegistration(context, intent);
        }else if(intent.getAction().equals("com.google.android.c2dm.intent.RECEIVE")){
            handleMessage(context, intent);
        }
    }

    /**
    * <pre>
    * C2DM의사용신청후서버에서오는메시지를처리하는메소드
    * </pre>
    *
    * @param context
    * @param intent
    */
    private void handleRegistration(Context context, Intent intent)
    {
        Log.e("C2DM", "handleRegistration");

        //서버에서넘어오는메시지의내용에key이름 "registration_id"에는이기기에만사용하는인증키값이담겨서넘어온다.
        String registration = intent.getStringExtra("registration_id");

        if (intent.getStringExtra("error") != null)
        {
            Log.e("C2DM", "error");
        }
        else if (intent.getStringExtra("unregistered") != null)
        {
            Log.e("C2DM", "unregistered");
        }
        else if (registration != null)
        {
            Log.e("C2DM", registration);
        }
    }
     
    /**
    * <pre>
    * C2DM서버에서오는메시지(개발자측이보내는메시지)를처리하는메소드
    * </pre>
    *
    * @param context
    * @param intent
    */
    private void handleMessage(Context context, Intent intent)
    {
        Log.e("C2DM", "handleMessage");

        String title = intent.getStringExtra("title");
        String msg = intent.getStringExtra("msg");

        Log.e("title : ", title);
        Log.e("msg : ", msg);
    }
}


이러면 C2DM으로 부터 registration_id를 받아서 서버쪽에 셋팅을 해 줘야 정상적으로 서버 -> C2DM -> App 이런 식으로 메세지 전달이 되는거 같은데 registration_id를 못 받고 있습니다.

log에 Log.e("onReceive : ", "<<<<<<<<<<<<<<<<<<<<<<<<<<<<< test"); 이부분이 전혀 찍히지 않는것을 보면 Receiver가 응답을 못 받는거 같은데 뭐가 잘못됐을까요?


참고로 갤럭시s 2.3.3에서 테스트 하고 있습니다.