본문 바로가기
안드로이드 자바

[Android][Java] ConnectivityManager 네트워크 상태 모니터링

by teamnova 2023. 5. 11.

오늘은 ConnectivityManager 클래스를 사용해서 네트워크가 연결되거나 끊기는 것을 모니터링하는 예제를 만들어보겠습니다.

 

먼저 ConnectivityManager 클래스는 현재 사용중인 어플리케이션에 시스템의 네트워크 연결 상태를 알려주는 클래스입니다.

이를 통해서 저희는  즉각적인 연결상태를 확인하고 그에 맞는 대응을 할 수 있습니다.

예시로 만약 네트워크가 연결되어 있을 때 어플리케이션을 통해 알림을 받을 수 있는데 인터넷 연결이 끊겼다면 해당 알림이 오지 않을 것입니다, 이 때 ConnectivityManager를 사용해서 Callback을 등록하면 끊겼던 네트워크 연결이 다시 연결되었을 때  Callback 메소드가 호출되어 이전에 받지 못했던 알림을 띄워주는 등의 작업을 할 수 있습니다.

 

그 외에도 현재 연결된 네트워크에 관한 정보도 가져올 수 있는 유용한 클래스입니다.

하지만 오늘은 네트워크 상태 모니터링에 관해서만 예제를 만들어 보겠습니다.

 

 

AndroidManifest.xml (매니페스트 파일)

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools">

    <!--  네트워크 상태 접근 권한 명시  -->
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

    <application
        android:allowBackup="true"
        android:dataExtractionRules="@xml/data_extraction_rules"
        android:fullBackupContent="@xml/backup_rules"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:supportsRtl="true"
        android:theme="@style/Theme.Network_Receiver"
        tools:targetApi="31">
        <activity
            android:name=".MainActivity"
            android:exported="true">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>

 

activity_main.xml (레이아웃 파일)

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">

    <Button
        android:id="@+id/button"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="50dp"
        android:layout_marginTop="144dp"
        android:layout_marginEnd="50dp"
        android:text="네트워크 상태 감지 시작"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.498"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>

 

MainActivity.java

package com.teamnova.network_receiver;

import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;

import android.content.Context;
import android.net.ConnectivityManager;
import android.net.Network;
import android.net.NetworkRequest;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.Toast;

public class MainActivity extends AppCompatActivity {

    ConnectivityManager cm; // 네트워크 연결 상태와 관련된 응답을 하는 클래스
    ConnectivityManager.NetworkCallback networkCallback; // 네트워크 관련 콜백 메서드를 작성할 수 있는 클래스
    boolean network_receiver_on; // 네트워크 리시버 상태 저장 변수

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        // 변수 초기화
        network_receiver_on = false;

        // 버튼 뷰 초기화
        Button button = (Button) findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                if(network_receiver_on){ // 현재 네트워크 감지 중이면 감지 종료
                    network_receiver_on = false;
                    button.setText("네트워크 감지 시작");
                    Toast.makeText(getApplicationContext(), "네트워크 상태 감지를 종료합니다", Toast.LENGTH_SHORT).show();

                    // 네트워크 콜백 해제
                    cm.unregisterNetworkCallback(networkCallback);
                }else{ // 현재 네트워크 감지 종료 상태일 경우 다시 감지 상태로 변경
                    network_receiver_on = true;
                    button.setText("네트워크 감지 종료");
                    Toast.makeText(getApplicationContext(), "네트워크 상태 감지를 시작합니다", Toast.LENGTH_SHORT).show();

                    // 매개변수에 대응하는 안드로이드가 제공하는 시스템-레벨 서비스 요청
                    // 시스템으로부터 객체를 얻을 때 사용
                    cm = (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE);

                    // 네트워크 관련 요청을 할 때 사용하는 클래스 객체를 만들기위한 Builder 생성
                    NetworkRequest.Builder builder = new NetworkRequest.Builder();

                    // 네트워크 콜백 초기화
                    networkCallback = new ConnectivityManager.NetworkCallback(){
                        @Override
                        public void onAvailable(@NonNull Network network) {
                            // 등록되었을 때 네트워크가 연결되어있거나
                            // 네트워크가 다시 연결되면 호출되는 메소드
                            Toast.makeText(getApplicationContext(), "네트워크가 연결되었습니다", Toast.LENGTH_SHORT).show();
                        }

                        @Override
                        public void onLost(@NonNull Network network) {
                            // 네트워크가 끊기면 호출되는 메소드
                            Toast.makeText(getApplicationContext(), "네트워크가 끊겼습니다", Toast.LENGTH_SHORT).show();
                        }
                    };
                    // 네트워크 콜백 등록 요청
                    cm.registerNetworkCallback(builder.build(), networkCallback);
                }
            }
        });
    }
}

 

예제 영상