Merge "Add NetworkProvider to VcnManagementService"

This commit is contained in:
Benedict Wong
2020-11-17 22:26:04 +00:00
committed by Gerrit Code Review
2 changed files with 111 additions and 2 deletions

View File

@@ -20,10 +20,18 @@ import static java.util.Objects.requireNonNull;
import android.annotation.NonNull;
import android.content.Context;
import android.net.ConnectivityManager;
import android.net.NetworkProvider;
import android.net.NetworkRequest;
import android.net.vcn.IVcnManagementService;
import android.net.vcn.VcnConfig;
import android.os.HandlerThread;
import android.os.Looper;
import android.os.ParcelUuid;
import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.annotations.VisibleForTesting.Visibility;
/**
* VcnManagementService manages Virtual Carrier Network profiles and lifecycles.
*
@@ -88,9 +96,16 @@ public class VcnManagementService extends IVcnManagementService.Stub {
@NonNull private final Context mContext;
@NonNull private final Dependencies mDeps;
private VcnManagementService(@NonNull Context context, @NonNull Dependencies deps) {
@NonNull private final Looper mLooper;
@NonNull private final VcnNetworkProvider mNetworkProvider;
@VisibleForTesting(visibility = Visibility.PRIVATE)
VcnManagementService(@NonNull Context context, @NonNull Dependencies deps) {
mContext = requireNonNull(context, "Missing context");
mDeps = requireNonNull(deps, "Missing dependencies");
mLooper = mDeps.getLooper();
mNetworkProvider = new VcnNetworkProvider(mContext, mLooper);
}
// Package-visibility for SystemServer to create instances.
@@ -98,11 +113,31 @@ public class VcnManagementService extends IVcnManagementService.Stub {
return new VcnManagementService(context, new Dependencies());
}
private static class Dependencies {}
/** External dependencies used by VcnManagementService, for injection in tests */
@VisibleForTesting(visibility = Visibility.PRIVATE)
public static class Dependencies {
private HandlerThread mHandlerThread;
/** Retrieves a looper for the VcnManagementService */
public Looper getLooper() {
if (mHandlerThread == null) {
synchronized (this) {
if (mHandlerThread == null) {
mHandlerThread = new HandlerThread(TAG);
mHandlerThread.start();
}
}
}
return mHandlerThread.getLooper();
}
}
/** Notifies the VcnManagementService that external dependencies can be set up. */
public void systemReady() {
// TODO: Retrieve existing profiles from KeyStore
mContext.getSystemService(ConnectivityManager.class)
.registerNetworkProvider(mNetworkProvider);
}
/**
@@ -129,4 +164,16 @@ public class VcnManagementService extends IVcnManagementService.Stub {
// TODO: Clear VCN configuration, trigger teardown as necessary
}
@VisibleForTesting(visibility = Visibility.PRIVATE)
class VcnNetworkProvider extends NetworkProvider {
VcnNetworkProvider(@NonNull Context context, @NonNull Looper looper) {
super(context, looper, VcnNetworkProvider.class.getSimpleName());
}
@Override
public void onNetworkRequested(@NonNull NetworkRequest request, int score, int providerId) {
// TODO: Handle network requests - Ensure VCN started, and start appropriate tunnels.
}
}
}

View File

@@ -0,0 +1,62 @@
/*
* Copyright (C) 2020 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.server;
import static org.mockito.Mockito.any;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import android.content.Context;
import android.net.ConnectivityManager;
import android.os.test.TestLooper;
import androidx.test.filters.SmallTest;
import androidx.test.runner.AndroidJUnit4;
import org.junit.Test;
import org.junit.runner.RunWith;
/** Tests for {@link VcnManagementService}. */
@RunWith(AndroidJUnit4.class)
@SmallTest
public class VcnManagementServiceTest {
private final Context mMockContext = mock(Context.class);
private final VcnManagementService.Dependencies mMockDeps =
mock(VcnManagementService.Dependencies.class);
private final TestLooper mTestLooper = new TestLooper();
private final ConnectivityManager mConnMgr = mock(ConnectivityManager.class);
private final VcnManagementService mVcnMgmtSvc;
public VcnManagementServiceTest() {
doReturn(Context.CONNECTIVITY_SERVICE)
.when(mMockContext)
.getSystemServiceName(ConnectivityManager.class);
doReturn(mConnMgr).when(mMockContext).getSystemService(Context.CONNECTIVITY_SERVICE);
doReturn(mTestLooper.getLooper()).when(mMockDeps).getLooper();
mVcnMgmtSvc = new VcnManagementService(mMockContext, mMockDeps);
}
@Test
public void testSystemReady() throws Exception {
mVcnMgmtSvc.systemReady();
verify(mConnMgr)
.registerNetworkProvider(any(VcnManagementService.VcnNetworkProvider.class));
}
}