안정적인 인터넷 연결에 의존하는 애플리케이션이 있다고 가정해 보겠습니다. 인터넷 연결이 변경될 때 애플리케이션이 알림을 받길 원합니다. 어떻게 합니까? 가능한 솔루션은 항상 인터넷 연결을 확인하는 서비스입니다. 이 구현은 여러 가지 이유로 좋지 않으므로 고려조차 하지 않습니다. 이 문제에 대한 해결책은 브로드캐스트 리시버이며 사용자가 지시한 변경 사항을 수신합니다. 브로드캐스트 수신기는 애플리케이션 상태에 관계없이 항상 브로드캐스트 알림을 받습니다. 애플리케이션이 현재 실행 중인지, 백그라운드에서 실행 중인지 아니면 전혀 실행 중인지 여부는 중요하지 않습니다.
배경
브로드캐스트 수신기는 다른 콘센트에서 브로드캐스트 메시지(또는 이벤트)를 수신하는 Android 애플리케이션의 구성요소입니다.
- 다른 애플리케이션에서
- 시스템 자체에서
- 신청서에서
즉, 청취하도록 프로그래밍된(즉, 방송) 특정 작업이 발생할 때 호출됩니다.
브로드캐스트는 단순히 의도 개체 내부에 래핑된 메시지입니다. 브로드캐스트는 암시적이거나 명시적일 수 있습니다.
- 암시적 브로드캐스트 귀하의 애플리케이션을 특별히 대상으로 하지 않으므로 귀하의 애플리케이션에만 국한되지 않습니다. 등록하려면 IntentFilter를 사용하고 매니페스트에서 선언해야 합니다. Android 운영 체제는 매니페스트에서 선언된 모든 인텐트 필터를 검토하고 일치하는 항목이 있는지 확인하기 때문에 이 모든 작업을 수행해야 합니다. 이 동작 때문에 암시적 브로드캐스트에는 대상 속성이 없습니다. 암시적 브로드캐스트의 예는 수신 SMS 메시지의 동작입니다.
- 노골적인 방송 사전에 알려진 구성 요소의 응용 프로그램을 위해 특별히 대상으로 지정된 것입니다. 이는 애플리케이션의 패키지 이름 또는 구성 요소 클래스 이름을 포함하는 대상 속성으로 인해 발생합니다.
수신자를 선언하는 방법에는 두 가지가 있습니다.
- AndroidManifest.xml 파일에서
태그(정적이라고도 함)를 사용하여 선언
<receiver android:name=".YourBrodcastReceiverClass" android:exported="true">
<intent-filter>
<!-- The actions you wish to listen to, below is an example -->
<action android:name="android.intent.action.BOOT_COMPLETED"/>
</intent-filter>
</receiver>
위에 선언된 브로드캐스트 수신기에는 exported="true" 속성이 있음을 알 수 있습니다. . 이 속성은 수신자에게 애플리케이션 범위 외부에서 브로드캐스트를 수신할 수 있음을 알려줍니다.
2. 또는 registerReceiver에 인스턴스를 등록하여 동적으로(컨텍스트 등록됨)
public abstract Intent registerReceiver (BroadcastReceiver receiver,
IntentFilter filter);
구현
자신의 브로드캐스트 수신기를 만들려면 먼저 BroadcastReceiver 상위 클래스를 확장하고 필수 메서드인 onReceive:
를 재정의해야 합니다.public void onReceive(Context context, Intent intent) {
//Implement your logic here
}
모두 합치면 다음과 같습니다.
public class MyBroadcastReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
StringBuilder sb = new StringBuilder();
sb.append("Action: " + intent.getAction() + "\n");
sb.append("URI: " + intent.toUri(Intent.URI_INTENT_SCHEME).toString() + "\n");
String log = sb.toString();
Toast.makeText(context, log, Toast.LENGTH_LONG).show();
}
}
⚠️onReceive 메소드는 메인 스레드에서 실행되기 때문에 실행 시간이 짧아야 합니다.
긴 프로세스가 실행되면 메서드가 반환된 후 시스템이 프로세스를 종료할 수 있습니다. 이를 피하려면 goAsync를 사용하거나 작업을 예약하는 것이 좋습니다. 이 문서 하단에서 작업 예약에 대해 자세히 알아볼 수 있습니다.
동적 등록 예
컨텍스트에 수신기를 등록하려면 먼저 브로드캐스트 수신기의 인스턴스를 인스턴스화해야 합니다.
BroadcastReceiver myBroadcastReceiver = new MyBroadcastReceiver();
그런 다음 원하는 특정 컨텍스트에 따라 등록할 수 있습니다.
IntentFilter filter = new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION);
filter.addAction(Intent.ACTION_AIRPLANE_MODE_CHANGED);
this.registerReceiver(myBroadcastReceiver, filter);
더 이상 필요하지 않을 때 브로드캐스트 수신기를 등록 취소하는 것을 잊지 마십시오.
@Override
protected void onStop() {
super.onStop();
unregisterReceiver(myBroadcastReceiver);
}
이벤트 방송
애플리케이션에서 메시지를 브로드캐스트하는 것의 요점은 애플리케이션이 내부에서 발생하는 이벤트에 응답할 수 있도록 하는 것입니다. 코드의 한 부분에서 사용자가 특정 작업을 수행하고 이로 인해 다른 위치에 있는 다른 로직을 실행하려는 시나리오를 생각해 보십시오.
브로드캐스트를 보내는 방법에는 세 가지가 있습니다.
- sendOrderedBroadcast 방법을 사용하는 경우 한 번에 하나의 수신기에만 브로드캐스트를 보내야 합니다. 각 브로드캐스트는 차례로 데이터를 따라오는 사람에게 데이터를 전달하거나 뒤따르는 수신기로의 브로드캐스트 전파를 중지할 수 있습니다.
- sendBroadcast 위에서 언급한 방법과 유사하지만 한 가지 차이점이 있습니다. 모든 브로드캐스트 수신자는 메시지를 수신하며 서로 의존하지 않습니다.
- LocalBroadcastManager.sendBroadcast 메소드는 애플리케이션 내부에 정의된 수신자에게만 브로드캐스트를 보내고 애플리케이션의 범위를 초과하지 않습니다. 사용자 정의 브로드캐스트를 보내는 예
https://giphy.com/gifs/23gUJhHyWkXEwl7UYV/html5
주의해야 할 사항 및 주의해야 할 사항
- 암시적 브로드캐스트를 통해 민감한 데이터를 보내지 마십시오. 민감한 데이터를 수신하는 모든 애플리케이션이 이를 수신하기 때문입니다. 패키지를 지정하거나 브로드캐스트에 권한을 첨부하여 이를 방지할 수 있습니다.
- 사용자 경험이 부족하므로 수신된 방송에서 활동을 시작하지 마십시오. 대신 알림을 표시하도록 선택하세요.
다음 글머리 기호는 Android OS 버전(7.0부터)별 브로드캐스트 수신기의 변경 사항을 나타냅니다. 각 버전에 대해 특정 제한 사항이 발생했으며 동작도 변경되었습니다. 브로드캐스트 수신기를 사용할 때 이러한 제한 사항을 염두에 두십시오.
- 7.0 이상(API 레벨 24) - Action_New_Picture 및 Action_New_Video의 두 시스템 브로드캐스트가 비활성화되었습니다(그러나 등록된 수신기의 경우 Android O에서 다시 가져옴).
- 8.0 이상(API 레벨 26) - 대부분의 암시적 브로드캐스트는 (매니페스트에서) 정적으로가 아니라 동적으로 등록되어야 합니다. 이 링크에서 허용된 방송을 찾을 수 있습니다.
- 9.0 이상(API 레벨 28) - Wi-Fi 시스템 브로드캐스트 및 Network_State_Changed_Action에 대해 수신되는 정보가 적습니다.
Android O의 변경 사항은 가장 주의해야 할 사항입니다. 이러한 변경이 이루어진 이유는 성능 문제, 배터리 소모 및 사용자 경험 저하로 이어지기 때문입니다. 이것은 많은 응용 프로그램(현재 실행되지 않는 응용 프로그램 포함)이 시스템 전체의 변경 사항을 수신하고 있었고 해당 변경 사항이 발생했을 때 혼란이 뒤따랐기 때문에 발생했습니다. 작업에 등록된 모든 응용 프로그램이 브로드캐스트로 인해 작업을 수행해야 하는지 확인하기 위해 활성화되었다고 상상해 보십시오. 자주 변경되는 Wi-Fi 상태와 같은 것을 고려하면 이러한 변경이 발생한 이유를 이해하기 시작할 것입니다.
방송 수신기의 대안
이러한 모든 제한 사항을 더 쉽게 탐색할 수 있도록 다음은 브로드캐스트 수신기가 없을 때 사용할 수 있는 다른 구성 요소에 대한 분석입니다. 각각의 책임과 사용 사례가 다르므로 필요에 맞는 것이 무엇인지 파악하십시오.
- LocalBroadcastManager - 위에서 언급했듯이 이것은 애플리케이션 내의 브로드캐스트에만 유효합니다.
- 작업 예약 - 수신된 신호 또는 트리거에 따라 작업이 실행될 수 있으므로 듣고 있던 방송이 작업으로 대체될 수 있음을 알 수 있습니다. 또한 JobScheduler는 작업이 완료되는 것을 보장하지만 언제 실행해야 하는지 결정하기 위해 다양한 시스템 요소(시간 및 조건)를 고려합니다. 작업을 만들 때 onStartJob 메서드를 재정의합니다. . 이 메서드는 메인 스레드에서 실행되므로 제한된 시간 내에 작업을 완료해야 합니다. 복잡한 논리를 수행해야 하는 경우 백그라운드 작업 시작을 고려하십시오. 또한 이 메서드의 반환 값은 부울입니다. 여기서 true는 특정 작업이 아직 수행되고 있음을 나타내고 false는 작업이 완료되었음을 나타냅니다.
브로드캐스트 수신기의 기쁨과 경이로움을 직접 경험하고 싶다면 다음 링크를 따라 제가 설정한 리포지토리로 이동할 수 있습니다.
- 맞춤 방송(매니페스트 선언 포함)
- 브로드캐스트 등록(매니페스트에서 선언하지 않음)
- LocalBroadcastManager
방송을 종료합니다.