전용 기기 설명서

이 설명서는 개발자와 시스템 통합자가 사용할 수 있습니다. 방법 안내 레시피에 따라 전용 기기를 위한 솔루션을 찾아보세요. 확인할 수 있습니다 이 설명서는 이미 전용 처음 시작하는 경우 전용 기기 개요를 참조하세요.

맞춤 홈 앱

이 레시피는 Android Home을 대체하는 앱을 개발하는 경우에 유용합니다. 화면과 런처.

홈 앱으로 활용하기

앱을 기기의 홈 앱으로 설정하여 실행할 수 있습니다. 자동으로 작동합니다. 또한 홈 버튼을 사용 설정하면 버튼 - 허용 목록에 있는 앱을 잠금 상태에서 포그라운드로 가져옵니다. 태스크 모드입니다.

모든 홈 앱은 CATEGORY_HOME 인텐트 카테고리를 처리합니다. 시스템이 홈 앱을 인식하는 방법입니다 기본 홈 앱이 되려면 기본 홈 앱을 설정하세요. 원하는 홈 인텐트 핸들러로 지정할 수도 있습니다. DevicePolicyManager.addPersistentPreferredActivity() 다음과 같습니다.

Kotlin

// Create an intent filter to specify the Home category.
val filter = IntentFilter(Intent.ACTION_MAIN)
filter.addCategory(Intent.CATEGORY_HOME)
filter.addCategory(Intent.CATEGORY_DEFAULT)

// Set the activity as the preferred option for the device.
val activity = ComponentName(context, KioskModeActivity::class.java)
val dpm = context.getSystemService(Context.DEVICE_POLICY_SERVICE)
        as DevicePolicyManager
dpm.addPersistentPreferredActivity(adminName, filter, activity)

자바

// Create an intent filter to specify the Home category.
IntentFilter filter = new IntentFilter(Intent.ACTION_MAIN);
filter.addCategory(Intent.CATEGORY_HOME);
filter.addCategory(Intent.CATEGORY_DEFAULT);

// Set the activity as the preferred option for the device.
ComponentName activity = new ComponentName(context, KioskModeActivity.class);
DevicePolicyManager dpm =
    (DevicePolicyManager) context.getSystemService(Context.DEVICE_POLICY_SERVICE);
dpm.addPersistentPreferredActivity(adminName, filter, activity);

인텐트 필터를 선언해야 함 을 선언할 수 있습니다.

<activity
        android:name=".KioskModeActivity"
        android:label="@string/kiosk_mode"
        android:launchMode="singleInstance"
        android:excludeFromRecents="true">
    <intent-filter>
        <action android:name="android.intent.action.MAIN"/>
        <category android:name="android.intent.category.HOME"/>
        <category android:name="android.intent.category.DEFAULT"/>
    </intent-filter>
</activity>

일반적으로 런처 앱이 최근 사용 화면에 표시되는 것은 바람직하지 않습니다. 하지만 excludeFromRecents를 이는 Android의 런처에서 처음 실행된 .

개별 할 일 표시

FLAG_ACTIVITY_NEW_TASK는 각 새 작업이 전체보기 화면 개요 화면의 작업에 관해 자세히 알아보려면 최근 사용 내역을 읽어보세요. 화면.

공개 키오스크

이러한 레시피는 공공장소에 있는 사람이 없는 기기에도 유용하지만 많은 전용 기기 사용자가 작업에 집중할 수 있습니다.

기기 잠그기

기기가 원래의 용도로 사용되도록 하려면 사용자 제한사항을 따릅니다

표 1. 키오스크 기기의 사용자 제한사항
사용자 제한 설명
DISALLOW_FACTORY_RESET 기기 사용자가 기기를 초기화하는 것을 방지합니다. 완전 관리형 기기의 관리자 및 기본 사용자가 이 설정을 설정할 수 있습니다. 제한입니다.
DISALLOW_SAFE_BOOT 기기 사용자가 다음 시간 이후에 기기를 시작하지 못하도록 합니다. 안전 모드 이런 경우 시스템에서 자동으로 앱을 실행하지 않습니다. 완전한 관리자 기본 사용자가 이 제한을 설정할 수 있습니다.
DISALLOW_MOUNT_PHYSICAL_MEDIA 기기 사용자가 저장소 볼륨을 마운트하지 못하도록 합니다. 장치에 연결합니다. 완전 관리형 기기 및 기본 사용자의 관리자 이 제한을 설정할 수 있습니다
DISALLOW_ADJUST_VOLUME 기기를 음소거하고 기기 사용자가 소리를 변경하지 못하게 합니다. 볼륨 및 진동 설정을 탭합니다. 키오스크에 오디오가 필요하지 않은지 확인하기 미디어 재생 또는 접근성 기능을 사용하는 것이 좋습니다 완전 관리형의 관리자 기본 사용자, 보조 사용자, 직장 프로필에서 이 설정을 적용할 수 있습니다. 제한입니다.
DISALLOW_ADD_USER 기기 사용자가 보조 사용자 또는 보조 사용자와 같은 새 사용자를 추가하지 못하게 합니다. 액세스할 수 없습니다. 시스템에서 자동으로 이 사용자 제한을 완전 관리형 기기이지만 삭제되었을 수도 있습니다 완전한 관리자 기본 사용자가 이 제한을 설정할 수 있습니다.

다음 스니펫은 제한사항을 설정하는 방법을 보여줍니다.

Kotlin

// If the system is running in lock task mode, set the user restrictions
// for a kiosk after launching the activity.
arrayOf(
        UserManager.DISALLOW_FACTORY_RESET,
        UserManager.DISALLOW_SAFE_BOOT,
        UserManager.DISALLOW_MOUNT_PHYSICAL_MEDIA,
        UserManager.DISALLOW_ADJUST_VOLUME,
        UserManager.DISALLOW_ADD_USER).forEach { dpm.addUserRestriction(adminName, it) }

자바

// If the system is running in lock task mode, set the user restrictions
// for a kiosk after launching the activity.
String[] restrictions = {
    UserManager.DISALLOW_FACTORY_RESET,
    UserManager.DISALLOW_SAFE_BOOT,
    UserManager.DISALLOW_MOUNT_PHYSICAL_MEDIA,
    UserManager.DISALLOW_ADJUST_VOLUME,
    UserManager.DISALLOW_ADD_USER};

for (String restriction: restrictions) dpm.addUserRestriction(adminName, restriction);

앱이 관리자 모드일 때 이러한 제한을 삭제하는 것이 좋습니다. IT 관리자가 계속해서 기기 유지관리를 위해 이러한 기능을 사용할 수 있다고 밝혔습니다. 지우기 제한, 호출 DevicePolicyManager.clearUserRestriction()

오류 대화상자 숨기기

소매 데모 또는 공공 정보 제공과 같은 일부 환경 사용자에게 오류 대화상자를 표시하고 싶지 않을 수 있습니다. Android 9.0 (API) 28) 또는 그 이상에서는 다운되었거나 비정상 종료에 대한 시스템 오류 대화상자를 앱이 응답하지 않는 경우 DISALLOW_SYSTEM_ERROR_DIALOGS 사용자 제한입니다. 기기 사용자가 종료한 것처럼 시스템에서 응답하지 않는 앱을 다시 시작함 선택합니다. 다음의 예시는 그 방법을 나타냅니다.

Kotlin

override fun onEnabled(context: Context, intent: Intent) {
    val dpm = getManager(context)
    val adminName = getWho(context)

    dpm.addUserRestriction(adminName, UserManager.DISALLOW_SYSTEM_ERROR_DIALOGS)
}

자바

public void onEnabled(Context context, Intent intent) {
  DevicePolicyManager dpm = getManager(context);
  ComponentName adminName = getWho(context);

  dpm.addUserRestriction(adminName, UserManager.DISALLOW_SYSTEM_ERROR_DIALOGS);
}

기본 또는 보조 사용자의 관리자가 이 제한을 설정하면 시스템은 해당 사용자에 대해서만 오류 대화상자를 억제합니다. 완전 관리형 서비스의 관리자가 기기에서 이 제한을 설정하면 시스템에서 모든 사용자에 대해 대화상자를 표시하지 않습니다.

화면을 켜진 상태로 유지

키오스크를 구축 중인 경우 기기가 Google Home으로 절전 모드로 전환됩니다. 추가 FLAG_KEEP_SCREEN_ON 레이아웃 플래그를 앱의 창에 표시됩니다.

Kotlin

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)

    // Keep the screen on and bright while this kiosk activity is running.
    window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
}

자바

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

  // Keep the screen on and bright while this kiosk activity is running.
  getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
}

기기가 AC, USB 또는 무선에 연결되어 있는지 확인하세요. 충전기에 연결합니다. 배터리 변경 브로드캐스트를 등록하고 BatteryManager를 사용합니다. 값을 사용하여 충전 상태를 파악합니다. IT 부서에 원격 경보를 보내고, 관리자에게 알립니다. 단계별 안내는 다음을 참조하세요. 배터리 수준 및 충전 모니터링 State입니다.

STAY_ON_WHILE_PLUGGED_IN 전역 설정에서는 전원에 연결되어 있는 동안 기기를 켜진 상태로 유지할 수 있습니다. Android 6.0 (API 수준 23) 이상에서 완전 관리형 기기의 관리자는 다음 작업을 할 수 있습니다. 다음과 같이 DevicePolicyManager.setGlobalSetting()를 호출합니다. 예를 들면 다음과 같습니다.

Kotlin

val pluggedInto = BatteryManager.BATTERY_PLUGGED_AC or
        BatteryManager.BATTERY_PLUGGED_USB or
        BatteryManager.BATTERY_PLUGGED_WIRELESS
dpm.setGlobalSetting(adminName,
        Settings.Global.STAY_ON_WHILE_PLUGGED_IN, pluggedInto.toString())

자바

int pluggedInto = BatteryManager.BATTERY_PLUGGED_AC |
    BatteryManager.BATTERY_PLUGGED_USB |
    BatteryManager.BATTERY_PLUGGED_WIRELESS;
dpm.setGlobalSetting( adminName,
    Settings.Global.STAY_ON_WHILE_PLUGGED_IN, String.valueOf(pluggedInto));

앱 패키지

이 섹션에서는 전용 기기에 앱을 효율적으로 설치하는 방법에 대해 설명합니다.

앱 패키지 캐시

공유 기기의 사용자가 모두 공통의 앱 세트를 공유하는 경우 가능하면 앱을 다운로드하지 않는 것이 좋습니다. 사용자를 간소화하기 위해 특정 사용자 그룹이 있는 공유 기기에서 Android 9.0 (API 레벨 28) 이상에서 앱을 캐시할 수 있는 경우 패키지 (APK)를 만듭니다.

기기에 이미 설치되어 있는 캐시된 APK의 설치는 다음에서 발생합니다. 2단계:

  1. 완전 관리형 기기 (또는 대리인)의 관리 구성요소입니다. )은 기기에 유지할 APK 목록을 설정합니다.
  2. 연결된 보조 사용자 (또는 해당 대리인)의 관리 구성요소는 사용자를 대신하여 캐시된 APK를 설치할 수 있습니다. 완전 관리형 기본 사용자, 연결된 직장 프로필 (또는 필요한 경우 캐시된 앱을 설치할 수도 있습니다.

관리자는 기기에 보관할 APK 목록을 설정하기 위해 DevicePolicyManager.setKeepUninstalledPackages() 이 방법은 APK가 기기에 설치되어 있는지 확인하지 않으며, 설치하려는 경우에 유용합니다. 배포 목록에서 이미 설정된 경우 DevicePolicyManager.getKeepUninstalledPackages() 변경사항이 있는 setKeepUninstalledPackages()를 호출한 후 또는 보조 요청이 사용자가 삭제되면 시스템은 더 이상 필요하지 않은 캐시된 APK를 모두 삭제합니다.

캐시된 APK를 설치하려면 다음을 호출합니다. DevicePolicyManager.installExistingPackage() 이 방법은 시스템이 이미 캐시한 앱( 전용 기기 솔루션 (또는 기기 사용자)이 먼저 이 메서드를 호출할 수 있어야 합니다.

다음 샘플은 완전 관리형 기기 및 보조 사용자:

Kotlin

// Set the package to keep. This method assumes that the package is already
// installed on the device by managed Google Play.
val cachedAppPackageName = "com.example.android.myapp"
dpm.setKeepUninstalledPackages(adminName, listOf(cachedAppPackageName))

// ...

// The admin of a secondary user installs the app.
val success = dpm.installExistingPackage(adminName, cachedAppPackageName)

자바

// Set the package to keep. This method assumes that the package is already
// installed on the device by managed Google Play.
String cachedAppPackageName = "com.example.android.myapp";
List<String> packages = new ArrayList<String>();
packages.add(cachedAppPackageName);
dpm.setKeepUninstalledPackages(adminName, packages);

// ...

// The admin of a secondary user installs the app.
boolean success = dpm.installExistingPackage(adminName, cachedAppPackageName);

앱 위임

앱 캐싱을 관리하도록 다른 앱에 위임할 수 있습니다. 다음과 같은 작업을 할 수 있습니다. 솔루션의 기능을 분리하거나 IT 관리자가 사용할 수 있는 제공할 수 있습니다. 위임 앱에 관리자와 동일한 권한이 부여됨 구성요소를 사용합니다. 예를 들어 보조 사용자의 관리자의 앱 대리인은 installExistingPackage()이지만 setKeepUninstalledPackages()를 호출할 수 없습니다.

위임 전화 걸기 DevicePolicyManager.setDelegatedScopes()DELEGATION_KEEP_UNINSTALLED_PACKAGES 범위 인수에 입력합니다. 다음 예는 다른 앱을 만드는 방법을 보여줍니다. 델리게이트:

Kotlin

var delegatePackageName = "com.example.tools.kept_app_assist"

// Check that the package is installed before delegating.
try {
    context.packageManager.getPackageInfo(delegatePackageName, 0)
    dpm.setDelegatedScopes(
            adminName,
            delegatePackageName,
            listOf(DevicePolicyManager.DELEGATION_KEEP_UNINSTALLED_PACKAGES))
} catch (e: PackageManager.NameNotFoundException) {
    // The delegate app isn't installed. Send a report to the IT admin ...
}

자바

String delegatePackageName = "com.example.tools.kept_app_assist";

// Check that the package is installed before delegating.
try {
  context.getPackageManager().getPackageInfo(delegatePackageName, 0);
  dpm.setDelegatedScopes(
      adminName,
      delegatePackageName,
      Arrays.asList(DevicePolicyManager.DELEGATION_KEEP_UNINSTALLED_PACKAGES));
} catch (PackageManager.NameNotFoundException e) {
  // The delegate app isn't installed. Send a report to the IT admin ...
}

모든 것이 잘 진행되면 위임 앱은 ACTION_APPLICATION_DELEGATION_SCOPES_CHANGED 드림 브로드캐스트되며 위임이 됩니다. 앱은 이 가이드의 메서드를 호출할 수 있습니다. 데이터를 공유할 수 있습니다. 통화 시 DevicePolicyManager 메서드: 대리자가 관리자를 위해 null를 전달합니다. component 인수를 사용합니다.

앱 패키지 설치

경우에 따라 로컬에 캐시된 맞춤 앱을 있습니다. 일례로, 네트워크 계층의 경우, 대역폭이 제한된 환경이나 인터넷 연결이 없는 지역에서 데이터를 사용할 수 있습니다. 내 전용 기기 솔루션은 고객의 대역폭을 고려해야 합니다. 내 앱이 다른 앱 패키지 (APK)를 설치할 때 PackageInstaller 클래스

모든 앱에서 APK를 설치할 수 있지만 완전 관리형 기기의 관리자는 사용자 상호작용 없이 패키지를 설치 (또는 제거)할 수 있습니다. 관리자가 연결된 보조 사용자 또는 연결된 직장 프로필로 이동합니다. 후(After) 설치가 완료되면 시스템은 모든 기기 사용자에게 볼 수 있습니다 알림은 기기 사용자에게 앱이 설치되었음을 알립니다 (또는 업데이트)가 표시됩니다.

표 2. 패키지 설치를 지원하는 Android 버전 사용자 상호작용 없이
Android 버전 설치 및 제거를 위한 관리자 구성요소
Android 9.0 (API 수준 28) 이상 완전 관리형에 연결된 보조 사용자 및 직장 프로필 기기
Android 6.0(API 수준 23) 이상 완전히 관리되는 기기

하나 이상의 APK 사본을 전용 기기에 배포하는 방법은 기기가 얼마나 멀리 떨어져 있는지, 기기와 기기의 거리가 얼마나 되는지에 따라 다릅니다. 서로 영향을 줍니다. 솔루션이 보안 권장사항을 따라야 함 을 사용해야 합니다.

PackageInstaller.Session를 사용하여 세션을 큐에 추가하는 세션을 만들 수 있습니다. 하나 이상의 APK가 있어야 합니다. 다음 예에서는 (singleTop 모드)에서 피드백이 제공되지만 broadcast receiver를 제공합니다.

Kotlin

// First, create a package installer session.
val packageInstaller = context.packageManager.packageInstaller
val params = PackageInstaller.SessionParams(
        PackageInstaller.SessionParams.MODE_FULL_INSTALL)
val sessionId = packageInstaller.createSession(params)
val session = packageInstaller.openSession(sessionId)

// Add the APK binary to the session. The APK is included in our app binary
// and is read from res/raw but file storage is a more typical location.
// The I/O streams can't be open when installation begins.
session.openWrite("apk", 0, -1).use { output ->
    getContext().resources.openRawResource(R.raw.app).use { input ->
        input.copyTo(output, 2048)
    }
}

// Create a status receiver to report progress of the installation.
// We'll use the current activity.
// Here we're requesting status feedback to our Activity but this can be a
// service or broadcast receiver.
val intent = Intent(context, activity.javaClass)
intent.action = "com.android.example.APK_INSTALLATION_ACTION"
val pendingIntent = PendingIntent.getActivity(context, 0, intent, 0)
val statusReceiver = pendingIntent.intentSender

// Start the installation. Because we're an admin of a fully managed device,
// there isn't any user interaction.
session.commit(statusReceiver)

자바

// First, create a package installer session.
PackageInstaller packageInstaller = context.getPackageManager().getPackageInstaller();
PackageInstaller.SessionParams params = new PackageInstaller.SessionParams(
    PackageInstaller.SessionParams.MODE_FULL_INSTALL);
int sessionId = packageInstaller.createSession(params);
PackageInstaller.Session session = packageInstaller.openSession(sessionId);

// Add the APK binary to the session. The APK is included in our app binary
// and is read from res/raw but file storage is a more typical location.
try (
    // These I/O streams can't be open when installation begins.
    OutputStream output = session.openWrite("apk", 0, -1);
    InputStream input = getContext().getResources().openRawResource(R.raw.app);
) {
  byte[] buffer = new byte[2048];
  int n;
  while ((n = input.read(buffer)) >= 0) {
    output.write(buffer, 0, n);
  }
}

// Create a status receiver to report progress of the installation.
// We'll use the current activity.
// Here we're requesting status feedback to our Activity but this can be a
// service or broadcast receiver.
Intent intent = new Intent(context, getActivity().getClass());
intent.setAction("com.android.example.APK_INSTALLATION_ACTION");
PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, 0);
IntentSender statusReceiver = pendingIntent.getIntentSender();

// Start the installation. Because we're an admin of a fully managed device,
// there isn't any user interaction.
session.commit(statusReceiver);

세션은 인텐트를 사용하여 설치에 관한 상태 피드백을 전송합니다. 확인 각 인텐트의 EXTRA_STATUS 필드를 이용해 상태입니다. 관리자는 STATUS_PENDING_USER_ACTION 상태 업데이트 기기 사용자가 설치를 승인할 필요가 없기 때문입니다.

앱을 제거하려면 PackageInstaller.uninstall을 호출하면 됩니다. 완전 관리형 기기, 사용자, 직장 프로필의 관리자가 패키지를 제거할 수 있음 사용자 상호작용 없이 지원되는 Android 버전 실행( 표 2).

시스템 업데이트 정지

Android 기기가 시스템 및 애플리케이션에 무선 업데이트 (OTA)를 수신함 있습니다. 연말연시나 휴일과 같은 중요한 기간에 OS 버전을 고정하기 위해 다른 사용량이 많은 시간에 대해서는 전용 기기에서 최대 90분 동안 OTA 시스템 업데이트를 일 자세한 내용은 시스템 업데이트 관리하기를 참고하세요.

원격 구성

IT 관리자는 Android의 관리 구성을 사용하여 다음을 수행할 수 있습니다. 앱을 원격으로 구성할 수 있습니다. 다음과 같은 설정을 노출하는 것이 좋습니다. 허용 목록, 네트워크 호스트 또는 콘텐츠 URL 등을 사용하여 IT 부서에 앱을 더욱 유용하게 만들 수 있습니다. 관리됩니다.

앱이 구성을 노출하는 경우 문서를 참조하세요. 앱 구성 노출 및 설정에서 변경하려면 관리 구성 설정하기를 참고하세요.

개발 설정

전용 기기용 솔루션을 개발하는 동안 앱을 초기화 없이 완전 관리형 기기의 관리자로 설정하는 데 유용합니다. 재설정합니다. 완전 관리형 기기의 관리자를 설정하려면 다음 단계를 따르세요.

  1. 기기에서 기기 정책 컨트롤러 (DPC) 앱을 빌드하고 설치합니다.
  2. 기기에 계정이 없는지 확인합니다.
  3. Android 디버그 브리지 (adb) 셸에서 다음 명령어를 실행합니다. 나 예시의 com.example.dpc/.MyDeviceAdminReceiver를 다음으로 바꿔야 합니다. 앱의 관리 구성요소 이름:

    adb shell dpm set-device-owner com.example.dpc/.MyDeviceAdminReceiver

고객이 솔루션을 배포할 수 있도록 지원하려면 기타 등록을 확인해야 합니다. 메서드를 사용합니다. QR 코드 등록을 통해 전용 기기입니다.

추가 리소스

전용 기기에 관해 자세히 알아보려면 다음 문서를 참고하세요.