1 /* 2 * Copyright 2015 The gRPC Authors 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package io.grpc.android.integrationtest; 18 19 import android.content.Context; 20 import android.content.Intent; 21 import android.net.LocalSocketAddress.Namespace; 22 import android.os.Bundle; 23 import android.text.TextUtils; 24 import android.util.Log; 25 import android.view.View; 26 import android.view.inputmethod.InputMethodManager; 27 import android.widget.Button; 28 import android.widget.CheckBox; 29 import android.widget.EditText; 30 import android.widget.TextView; 31 import androidx.appcompat.app.AppCompatActivity; 32 import com.google.android.gms.security.ProviderInstaller; 33 import io.grpc.ManagedChannel; 34 import io.grpc.android.UdsChannelBuilder; 35 import java.io.IOException; 36 import java.io.InputStream; 37 import java.util.ArrayList; 38 import java.util.List; 39 40 public class TesterActivity extends AppCompatActivity 41 implements ProviderInstaller.ProviderInstallListener, InteropTask.Listener { 42 private static final String LOG_TAG = "GrpcTesterActivity"; 43 44 private List<Button> buttons; 45 private EditText hostEdit; 46 private EditText portEdit; 47 private CheckBox useUdsCheckBox; 48 private EditText udsEdit; 49 private TextView resultText; 50 private CheckBox testCertCheckBox; 51 52 private UdsTcpEndpointConnector endpointConnector; 53 54 @Override onCreate(Bundle savedInstanceState)55 protected void onCreate(Bundle savedInstanceState) { 56 super.onCreate(savedInstanceState); 57 setContentView(R.layout.activity_tester); 58 buttons = new ArrayList<>(); 59 buttons.add((Button) findViewById(R.id.empty_unary_button)); 60 buttons.add((Button) findViewById(R.id.large_unary_button)); 61 buttons.add((Button) findViewById(R.id.client_streaming_button)); 62 buttons.add((Button) findViewById(R.id.server_streaming_button)); 63 buttons.add((Button) findViewById(R.id.ping_pong_button)); 64 65 hostEdit = (EditText) findViewById(R.id.host_edit_text); 66 portEdit = (EditText) findViewById(R.id.port_edit_text); 67 useUdsCheckBox = (CheckBox) findViewById(R.id.use_uds_checkbox); 68 udsEdit = (EditText) findViewById(R.id.uds_proxy_edit_text); 69 resultText = (TextView) findViewById(R.id.grpc_response_text); 70 testCertCheckBox = (CheckBox) findViewById(R.id.test_cert_checkbox); 71 72 ProviderInstaller.installIfNeededAsync(this, this); 73 // Disable buttons until the security provider installing finishes. 74 enableButtons(false); 75 } 76 77 /** Click handler for unix domain socket. */ enableUds(View view)78 public void enableUds(View view) { 79 boolean enabled = ((CheckBox) view).isChecked(); 80 udsEdit.setEnabled(enabled); 81 testCertCheckBox.setEnabled(!enabled); 82 if (enabled) { 83 testCertCheckBox.setChecked(false); 84 } 85 } 86 startEmptyUnary(View view)87 public void startEmptyUnary(View view) { 88 startTest("empty_unary"); 89 } 90 startLargeUnary(View view)91 public void startLargeUnary(View view) { 92 startTest("large_unary"); 93 } 94 startClientStreaming(View view)95 public void startClientStreaming(View view) { 96 startTest("client_streaming"); 97 } 98 startServerStreaming(View view)99 public void startServerStreaming(View view) { 100 startTest("server_streaming"); 101 } 102 startPingPong(View view)103 public void startPingPong(View view) { 104 startTest("ping_pong"); 105 } 106 enableButtons(boolean enable)107 private void enableButtons(boolean enable) { 108 for (Button button : buttons) { 109 button.setEnabled(enable); 110 } 111 } 112 113 @Override onComplete(String result)114 public void onComplete(String result) { 115 if (endpointConnector != null) { 116 endpointConnector.shutDown(); 117 endpointConnector = null; 118 } 119 resultText.setText(result); 120 enableButtons(true); 121 } 122 startTest(String testCase)123 private void startTest(String testCase) { 124 ((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE)).hideSoftInputFromWindow( 125 hostEdit.getWindowToken(), 0); 126 enableButtons(false); 127 resultText.setText("Testing..."); 128 129 String host = hostEdit.getText().toString(); 130 String portStr = portEdit.getText().toString(); 131 int port = TextUtils.isEmpty(portStr) ? 8080 : Integer.valueOf(portStr); 132 boolean udsEnabled = useUdsCheckBox.isChecked(); 133 String udsPath = 134 TextUtils.isEmpty(udsEdit.getText()) ? "default" : udsEdit.getText().toString(); 135 136 String serverHostOverride; 137 InputStream testCert; 138 if (testCertCheckBox.isChecked()) { 139 serverHostOverride = "foo.test.google.fr"; 140 testCert = getResources().openRawResource(R.raw.ca); 141 } else { 142 serverHostOverride = null; 143 testCert = null; 144 } 145 146 // Create Channel 147 ManagedChannel channel; 148 if (udsEnabled) { 149 channel = UdsChannelBuilder.forPath(udsPath, Namespace.ABSTRACT).build(); 150 } else { 151 channel = TesterOkHttpChannelBuilder.build(host, port, serverHostOverride, true, testCert); 152 } 153 154 // Port-forward uds local port to server exposing tcp endpoint. 155 if (udsEnabled) { 156 endpointConnector = new UdsTcpEndpointConnector(udsPath, host, port); 157 try { 158 endpointConnector.start(); 159 } catch (IOException e) { 160 Log.e(LOG_TAG, "Failed to start UDS-TCP Endpoint Connector."); 161 } 162 } 163 164 // Start Test. 165 new InteropTask(TesterActivity.this, channel, testCase).execute(); 166 } 167 168 @Override onProviderInstalled()169 public void onProviderInstalled() { 170 // Provider is up-to-date, app can make secure network calls. 171 enableButtons(true); 172 } 173 174 @Override onProviderInstallFailed(int errorCode, Intent recoveryIntent)175 public void onProviderInstallFailed(int errorCode, Intent recoveryIntent) { 176 // The provider is helpful, but it is possible to succeed without it. 177 // Hope that the system-provided libraries are new enough. 178 Log.w(LOG_TAG, "Failed installing security provider, error code: " + errorCode); 179 enableButtons(true); 180 } 181 } 182