android 用户空间切换流程

在Android开发中,创建和切换用户是一个重要的功能,特别是在需要多用户支持的应用中,下面讲述一下用户切换的流程。

一、CarUserManager.java

准备创建新用户,可以减少真正创建用户的时间

 @RequiresPermission(anyOf = {Manifest.permission.MANAGE_USERS,
              Manifest.permission.CREATE_USERS})
      public @NonNull UserInfo preCreateUser(@NonNull String userType)
              throws UserOperationException {
         try {
             return mService.preCreateUserWithThrow(userType);
          } catch (ServiceSpecificException e) {
             throw UserOperationException.from(e);
          } catch (RemoteException re) {
              throw re.rethrowFromSystemServer();
         }
      }

用户类型一般有车主、亲情、访客、临时还有一个system空间


51      @AddedIn(PlatformVersion.TIRAMISU_0)
52      public static final @UserIdInt int USER_SYSTEM = UserHandle.USER_SYSTEM;
55      @AddedIn(PlatformVersion.TIRAMISU_0)
56      public static final int FLAG_PRIMARY = UserInfo.FLAG_PRIMARY;
57      @AddedIn(PlatformVersion.TIRAMISU_0)
58      public static final int FLAG_ADMIN = UserInfo.FLAG_ADMIN;
59      @AddedIn(PlatformVersion.TIRAMISU_0)
60      public static final int FLAG_GUEST = UserInfo.FLAG_GUEST;
72      public static final int FLAG_EPHEMERAL = UserInfo.FLAG_EPHEMERAL;

创建用户需要MANAGE_USERSManifest.permission.CREATE_USERS权限,默认是会创建车主或者临时空间

    @Deprecated
674      @AddedInOrBefore(majorVersion = 33, softRemovalVersion = 35, hardRemovalVersion = 37)
675      @RequiresPermission(anyOf = {android.Manifest.permission.MANAGE_USERS,
676              android.Manifest.permission.CREATE_USERS})
677      public AsyncFuture<UserCreationResult> createUser(@Nullable String name,
678              int flags) {
679          AndroidFuture<UserCreationResult> future = new AndroidFuture<>();
680          UserCreationRequest.Builder userCreationRequestBuilder = new UserCreationRequest.Builder();
681          if (name != null) {
682              userCreationRequestBuilder.setName(name);
683          }
684
685          if ((flags & UserManagerHelper.FLAG_ADMIN) == UserManagerHelper.FLAG_ADMIN) {
686              userCreationRequestBuilder.setAdmin();
687          }
688
689          if ((flags & UserManagerHelper.FLAG_EPHEMERAL) == UserManagerHelper.FLAG_EPHEMERAL) {
690              userCreationRequestBuilder.setEphemeral();
691          }
692
693          createUser(userCreationRequestBuilder.build(), Runnable::run, future::complete);
694          return new AndroidAsyncFuture<>(future);
695      }

这里会调用CarUserService的createUser去创建用户

public void createUser(@NonNull UserCreationRequest userCreationRequest,
711              @NonNull @CallbackExecutor Executor executor,
712              @NonNull ResultCallback<UserCreationResult> callback) {
713        ...
742              mService.createUser(userCreationRequest, HAL_TIMEOUT_MS, resultCallbackImpl);
743         ...
751      }

切换用户

 @SystemApi
545      @RequiresPermission(anyOf = {android.Manifest.permission.MANAGE_USERS,
546              android.Manifest.permission.CREATE_USERS})
547      @ApiRequirements(minCarVersion = ApiRequirements.CarVersion.UPSIDE_DOWN_CAKE_0,
548              minPlatformVersion = ApiRequirements.PlatformVersion.TIRAMISU_0)
549      public void switchUser(@NonNull UserSwitchRequest userSwitchRequest,
550              @NonNull @CallbackExecutor Executor executor,
551              @NonNull ResultCallback<UserSwitchResult> callback) {
552          int uid = myUid();
553          int targetUserId = userSwitchRequest.getUserHandle().getIdentifier();
571              mService.switchUser(targetUserId, HAL_TIMEOUT_MS, resultCallbackImpl);
572 
580      }

退出用户

  @RequiresPermission(anyOf = {android.Manifest.permission.MANAGE_USERS,
607              android.Manifest.permission.CREATE_USERS})
608      @AddedInOrBefore(majorVersion = 33)
609      public AsyncFuture<UserSwitchResult> logoutUser() {
610          int uid = myUid();
                 ...
629              mService.logoutUser(HAL_TIMEOUT_MS, resultCallbackImpl);
                 ...
638      }

删除用户

   public UserRemovalResult removeUser(@UserIdInt int userId) {
834           ...
836           removeUser(userRemovalRequest, Runnable::run, userRemovalResultCallback);
              ...
853      }

     @SystemApi
781      @RequiresPermission(anyOf = {android.Manifest.permission.MANAGE_USERS,
782              android.Manifest.permission.CREATE_USERS})
783      @ApiRequirements(minCarVersion = ApiRequirements.CarVersion.UPSIDE_DOWN_CAKE_0,
784              minPlatformVersion = ApiRequirements.PlatformVersion.TIRAMISU_0)
785      public void removeUser(@NonNull UserRemovalRequest userRemovalRequest,
786              @NonNull @CallbackExecutor Executor executor,
787              @NonNull ResultCallback<UserRemovalResult> callback) {
788              ...
802              mService.removeUser(userRemovalRequest.getUserHandle().getIdentifier(),
803                      resultCallbackImpl);
804               ...
812      }

监听用户切换

 @RequiresPermission(anyOf = {INTERACT_ACROSS_USERS, INTERACT_ACROSS_USERS_FULL})
864      @AddedInOrBefore(majorVersion = 33)
865      public void addListener(@NonNull @CallbackExecutor Executor executor,
866              @NonNull UserLifecycleListener listener) {
867          addListenerInternal(executor, /* filter= */null, listener);
868      }


  public interface UserLifecycleListener {
1486          /**
1487           * Called to notify the given {@code event}.
1488           */1489          @AddedInOrBefore(majorVersion = 33)
1490          void onEvent(@NonNull UserLifecycleEvent event);
1491      }

用户切换返回 UserLifecycleEvent的状态有,可以在返回的各个状态去做对应处理

  /**
1371           * Gets the event type.
1372           *
1373           * @return either {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_STARTING},
1374           * {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_SWITCHING},
1375           * {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_UNLOCKING},
1376           * {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_UNLOCKED},
1377           * {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_STOPPING} or
1378           * {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_STOPPED} for all apps;
1379           * for apps {@link CarPackageManager#getTargetCarVersion() targeting car version}
1380           * {@link CarVersion.VERSION_CODES#TIRAMISU_1} or higher, it could be new types
1381           * added on later releases, such as
1382           * {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_CREATED},
1383           * {@link CarUserManager#USER_LIFECYCLE_EVENT_TYPE_REMOVED} and possibly others.
1384           *
1385           */
二、CarUserService
  1. 权限检查,每次会判断是否有ALLOWED_FLAGS_FOR_CREATE_USERS_PERMISSION中的权限,没有权限会直接抛异常,

2875      private static final int ALLOWED_FLAGS_FOR_CREATE_USERS_PERMISSION =
              UserManagerHelper.FLAG_MANAGED_PROFILE2877             
               | UserManagerHelper.FLAG_PROFILE2878              
               | UserManagerHelper.FLAG_EPHEMERAL2879
               | UserManagerHelper.FLAG_RESTRICTED2880
               | UserManagerHelper.FLAG_GUEST2881              
               | UserManagerHelper.FLAG_DEMO2882              
               | UserManagerHelper.FLAG_FULL;
             
2898      private static void checkManageOrCreateUsersPermission(int creationFlags) {
2899          if ((creationFlags & ~ALLOWED_FLAGS_FOR_CREATE_USERS_PERMISSION) == 0) {
2900              if (!hasManageOrCreateUsersPermission()) {
2901                  throw new SecurityException("You either need " + MANAGE_USERS + " or "2902                          + CREATE_USERS + "permission to create a user with flags "2903                          + creationFlags);
2904              }
2905          } else if (!hasManageUsersPermission()) {
2906              throw new SecurityException("You need " + MANAGE_USERS + " permission to create a user"
2907                      + " with flags " + creationFlags);
2908          }
2909      }

检查是否是系统应用跟是否有root权限

2911      private static boolean hasManageUsersPermission() {
2912          final int callingUid = Binder.getCallingUid();
2913          return isSameApp(callingUid, Process.SYSTEM_UID)
2914                  || callingUid == Process.ROOT_UID2915 
                      || hasPermissionGranted(MANAGE_USERS, callingUid);
2916      }
  1. 权限满足才会去创建用户,创建空间先生成NewUserResponse请求,里面有用户名、用户类型等,会先调用UserManager去创建用户,拿到UserHandler后会去判断是否支持User HAL,再调用UserHalService去创建用户,创建失败或者异常会调用removeCreatedUser去删除UserManager创建的newUser。

1299      @Override
1300      public void createUser(@NonNull UserCreationRequest userCreationRequest, int timeoutMs,1301              ResultCallbackImpl<UserCreationResult> callback) {
1302          String name = userCreationRequest.getName();
1303          String userType = userCreationRequest.isGuest() ? UserManager.USER_TYPE_FULL_GUEST1304                  : UserManager.USER_TYPE_FULL_SECONDARY;
1305          int flags = 0;
1306          flags |= userCreationRequest.isAdmin() ? UserManagerHelper.FLAG_ADMIN : 0;
1307          flags |= userCreationRequest.isEphemeral() ? UserManagerHelper.FLAG_EPHEMERAL : 0;
1308  
1309          createUser(name, userType, flags, timeoutMs, callback, /* hasCallerRestrictions= */ false);
1310      }
1311  
1381      private void handleCreateUser(@Nullable String name, @NonNull String userType,
1382              int flags, int timeoutMs, @NonNull ResultCallbackImpl<UserCreationResult> callback,
1383              @NonNull UserHandle callingUser, boolean hasCallerRestrictions) {
              //当前是访客没必要切换
1384          if (userType.equals(UserManager.USER_TYPE_FULL_GUEST) && flags != 0) {
1385              // Non-zero flags are not allowed when creating a guest user.
1386              String internalErroMessage = String
1387                      .format(ERROR_TEMPLATE_INVALID_FLAGS_FOR_GUEST_CREATI
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

踏雪羽翼

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值