OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 package org.chromium.net; | 5 package org.chromium.net; |
6 | 6 |
| 7 import android.content.Context; |
7 import android.test.AndroidTestCase; | 8 import android.test.AndroidTestCase; |
8 | 9 |
9 import org.chromium.base.ContextUtils; | 10 import org.chromium.base.ContextUtils; |
10 import org.chromium.base.PathUtils; | 11 import org.chromium.base.PathUtils; |
| 12 import org.chromium.base.annotations.SuppressFBWarnings; |
11 import org.chromium.net.impl.CronetEngineBase; | 13 import org.chromium.net.impl.CronetEngineBase; |
12 import org.chromium.net.impl.JavaCronetEngine; | 14 import org.chromium.net.impl.JavaCronetEngine; |
13 import org.chromium.net.impl.JavaCronetProvider; | 15 import org.chromium.net.impl.JavaCronetProvider; |
14 import org.chromium.net.impl.UserAgent; | 16 import org.chromium.net.impl.UserAgent; |
15 | 17 |
| 18 import java.io.File; |
16 import java.lang.annotation.ElementType; | 19 import java.lang.annotation.ElementType; |
17 import java.lang.annotation.Retention; | 20 import java.lang.annotation.Retention; |
18 import java.lang.annotation.RetentionPolicy; | 21 import java.lang.annotation.RetentionPolicy; |
19 import java.lang.annotation.Target; | 22 import java.lang.annotation.Target; |
20 import java.lang.reflect.AnnotatedElement; | 23 import java.lang.reflect.AnnotatedElement; |
21 import java.net.URL; | 24 import java.net.URL; |
| 25 import java.net.URLStreamHandlerFactory; |
22 | 26 |
23 /** | 27 /** |
24 * Base test class for all CronetTest based tests. | 28 * Base test class for all CronetTest based tests. |
25 */ | 29 */ |
26 public class CronetTestBase extends AndroidTestCase { | 30 public class CronetTestBase extends AndroidTestCase { |
27 /** | 31 /** |
| 32 * Creates and holds pointer to CronetEngine. |
| 33 */ |
| 34 public static class CronetTestFramework { |
| 35 public CronetEngineBase mCronetEngine; |
| 36 |
| 37 public CronetTestFramework(Context context) { |
| 38 mCronetEngine = (CronetEngineBase) new ExperimentalCronetEngine.Buil
der(context) |
| 39 .enableQuic(true) |
| 40 .build(); |
| 41 // Start collecting metrics. |
| 42 mCronetEngine.getGlobalMetricsDeltas(); |
| 43 } |
| 44 } |
| 45 |
| 46 /** |
28 * Name of the file that contains the test server certificate in PEM format. | 47 * Name of the file that contains the test server certificate in PEM format. |
29 */ | 48 */ |
30 static final String SERVER_CERT_PEM = "quic_test.example.com.crt"; | 49 static final String SERVER_CERT_PEM = "quic_test.example.com.crt"; |
31 | 50 |
32 /** | 51 /** |
33 * Name of the file that contains the test server private key in PKCS8 PEM f
ormat. | 52 * Name of the file that contains the test server private key in PKCS8 PEM f
ormat. |
34 */ | 53 */ |
35 static final String SERVER_KEY_PKCS8_PEM = "quic_test.example.com.key.pkcs8.
pem"; | 54 static final String SERVER_KEY_PKCS8_PEM = "quic_test.example.com.key.pkcs8.
pem"; |
36 | 55 |
37 private static final String PRIVATE_DATA_DIRECTORY_SUFFIX = "cronet_test"; | 56 private static final String PRIVATE_DATA_DIRECTORY_SUFFIX = "cronet_test"; |
38 private static final String LOOPBACK_ADDRESS = "127.0.0.1"; | 57 private static final String LOOPBACK_ADDRESS = "127.0.0.1"; |
39 | 58 |
40 private CronetTestFramework mCronetTestFramework; | 59 private CronetTestFramework mCronetTestFramework; |
| 60 private URLStreamHandlerFactory mStreamHandlerFactory; |
| 61 |
41 // {@code true} when test is being run against system HttpURLConnection impl
ementation. | 62 // {@code true} when test is being run against system HttpURLConnection impl
ementation. |
42 private boolean mTestingSystemHttpURLConnection; | 63 private boolean mTestingSystemHttpURLConnection; |
43 private boolean mTestingJavaImpl = false; | 64 private boolean mTestingJavaImpl = false; |
44 | 65 |
45 @Override | 66 @Override |
46 protected void setUp() throws Exception { | 67 protected void setUp() throws Exception { |
47 super.setUp(); | 68 super.setUp(); |
48 System.loadLibrary("cronet_tests"); | 69 System.loadLibrary("cronet_tests"); |
49 ContextUtils.initApplicationContext(getContext().getApplicationContext()
); | 70 ContextUtils.initApplicationContext(getContext().getApplicationContext()
); |
50 PathUtils.setPrivateDataDirectorySuffix(PRIVATE_DATA_DIRECTORY_SUFFIX); | 71 PathUtils.setPrivateDataDirectorySuffix(PRIVATE_DATA_DIRECTORY_SUFFIX); |
51 CronetTestFramework.prepareTestStorage(getContext()); | 72 prepareTestStorage(getContext()); |
52 } | 73 } |
53 | 74 |
54 /** | 75 /** |
55 * Starts the CronetTest framework. | 76 * Starts the CronetTest framework. |
56 */ | 77 */ |
57 protected CronetTestFramework startCronetTestFramework() { | 78 protected CronetTestFramework startCronetTestFramework() { |
58 return startCronetTestFrameworkWithUrlAndCronetEngineBuilder(null, null)
; | 79 mCronetTestFramework = new CronetTestFramework(getContext()); |
59 } | |
60 | |
61 /** | |
62 * Starts the CronetTest framework and loads the given URL. The URL can be | |
63 * null. | |
64 */ | |
65 protected CronetTestFramework startCronetTestFrameworkWithUrl(String url) { | |
66 return startCronetTestFrameworkWithUrlAndCronetEngineBuilder(url, null); | |
67 } | |
68 | |
69 /** | |
70 * Starts the CronetTest framework using the provided CronetEngine.Builder | |
71 * and loads the given URL. The URL can be null. | |
72 */ | |
73 protected CronetTestFramework startCronetTestFrameworkWithUrlAndCronetEngine
Builder( | |
74 String url, ExperimentalCronetEngine.Builder builder) { | |
75 mCronetTestFramework = new CronetTestFramework(url, null, getContext(),
builder); | |
76 return mCronetTestFramework; | 80 return mCronetTestFramework; |
77 } | 81 } |
78 | 82 |
79 /** | |
80 * Starts the CronetTest framework appending the provided command line | |
81 * arguments and loads the given URL. The URL can be null. | |
82 */ | |
83 protected CronetTestFramework startCronetTestFrameworkWithUrlAndCommandLineA
rgs( | |
84 String url, String[] commandLineArgs) { | |
85 mCronetTestFramework = new CronetTestFramework(url, commandLineArgs, get
Context(), null); | |
86 return mCronetTestFramework; | |
87 } | |
88 | |
89 // Helper method to tell the framework to skip library init during construct
ion. | |
90 protected CronetTestFramework startCronetTestFrameworkAndSkipLibraryInit() { | |
91 String[] commandLineArgs = { | |
92 CronetTestFramework.LIBRARY_INIT_KEY, CronetTestFramework.Librar
yInitType.NONE}; | |
93 mCronetTestFramework = | |
94 startCronetTestFrameworkWithUrlAndCommandLineArgs(null, commandL
ineArgs); | |
95 return mCronetTestFramework; | |
96 } | |
97 | |
98 /** | 83 /** |
99 * Returns {@code true} when test is being run against system HttpURLConnect
ion implementation. | 84 * Returns {@code true} when test is being run against system HttpURLConnect
ion implementation. |
100 */ | 85 */ |
101 protected boolean testingSystemHttpURLConnection() { | 86 protected boolean testingSystemHttpURLConnection() { |
102 return mTestingSystemHttpURLConnection; | 87 return mTestingSystemHttpURLConnection; |
103 } | 88 } |
104 | 89 |
105 /** | 90 /** |
106 * Returns {@code true} when test is being run against the java implementati
on of CronetEngine. | 91 * Returns {@code true} when test is being run against the java implementati
on of CronetEngine. |
107 */ | 92 */ |
108 protected boolean testingJavaImpl() { | 93 protected boolean testingJavaImpl() { |
109 return mTestingJavaImpl; | 94 return mTestingJavaImpl; |
110 } | 95 } |
111 | 96 |
112 @Override | 97 @Override |
113 protected void runTest() throws Throwable { | 98 protected void runTest() throws Throwable { |
114 mTestingSystemHttpURLConnection = false; | 99 mTestingSystemHttpURLConnection = false; |
115 mTestingJavaImpl = false; | 100 mTestingJavaImpl = false; |
116 String packageName = getClass().getPackage().getName(); | 101 String packageName = getClass().getPackage().getName(); |
117 if (packageName.equals("org.chromium.net.urlconnection")) { | 102 if (packageName.equals("org.chromium.net.urlconnection")) { |
118 try { | 103 try { |
119 AnnotatedElement method = getClass().getMethod(getName(), (Class
[]) null); | 104 AnnotatedElement method = getClass().getMethod(getName(), (Class
[]) null); |
120 if (method.isAnnotationPresent(CompareDefaultWithCronet.class))
{ | 105 if (method.isAnnotationPresent(CompareDefaultWithCronet.class))
{ |
121 // Run with the default HttpURLConnection implementation fir
st. | 106 // Run with the default HttpURLConnection implementation fir
st. |
122 mTestingSystemHttpURLConnection = true; | 107 mTestingSystemHttpURLConnection = true; |
123 super.runTest(); | 108 super.runTest(); |
124 // Use Cronet's implementation, and run the same test. | 109 // Use Cronet's implementation, and run the same test. |
125 mTestingSystemHttpURLConnection = false; | 110 mTestingSystemHttpURLConnection = false; |
126 URL.setURLStreamHandlerFactory(mCronetTestFramework.mStreamH
andlerFactory); | 111 URL.setURLStreamHandlerFactory(mStreamHandlerFactory); |
127 super.runTest(); | 112 super.runTest(); |
128 } else if (method.isAnnotationPresent(OnlyRunCronetHttpURLConnec
tion.class)) { | 113 } else if (method.isAnnotationPresent(OnlyRunCronetHttpURLConnec
tion.class)) { |
129 // Run only with Cronet's implementation. | 114 // Run only with Cronet's implementation. |
130 URL.setURLStreamHandlerFactory(mCronetTestFramework.mStreamH
andlerFactory); | 115 URL.setURLStreamHandlerFactory(mStreamHandlerFactory); |
131 super.runTest(); | 116 super.runTest(); |
132 } else { | 117 } else { |
133 // For all other tests. | 118 // For all other tests. |
134 super.runTest(); | 119 super.runTest(); |
135 } | 120 } |
136 } catch (Throwable e) { | 121 } catch (Throwable e) { |
137 throw new Throwable("CronetTestBase#runTest failed.", e); | 122 throw new Throwable("CronetTestBase#runTest failed.", e); |
138 } | 123 } |
139 } else if (packageName.equals("org.chromium.net")) { | 124 } else if (packageName.equals("org.chromium.net")) { |
140 try { | 125 try { |
(...skipping 30 matching lines...) Expand all Loading... |
171 } | 156 } |
172 | 157 |
173 public void assertResponseEquals(UrlResponseInfo expected, UrlResponseInfo a
ctual) { | 158 public void assertResponseEquals(UrlResponseInfo expected, UrlResponseInfo a
ctual) { |
174 assertEquals(expected.getAllHeaders(), actual.getAllHeaders()); | 159 assertEquals(expected.getAllHeaders(), actual.getAllHeaders()); |
175 assertEquals(expected.getAllHeadersAsList(), actual.getAllHeadersAsList(
)); | 160 assertEquals(expected.getAllHeadersAsList(), actual.getAllHeadersAsList(
)); |
176 assertEquals(expected.getHttpStatusCode(), actual.getHttpStatusCode()); | 161 assertEquals(expected.getHttpStatusCode(), actual.getHttpStatusCode()); |
177 assertEquals(expected.getHttpStatusText(), actual.getHttpStatusText()); | 162 assertEquals(expected.getHttpStatusText(), actual.getHttpStatusText()); |
178 assertEquals(expected.getUrlChain(), actual.getUrlChain()); | 163 assertEquals(expected.getUrlChain(), actual.getUrlChain()); |
179 assertEquals(expected.getUrl(), actual.getUrl()); | 164 assertEquals(expected.getUrl(), actual.getUrl()); |
180 // Transferred bytes and proxy server are not supported in pure java | 165 // Transferred bytes and proxy server are not supported in pure java |
181 if (!(mCronetTestFramework.mCronetEngine instanceof JavaCronetEngine)) { | 166 if (!testingJavaImpl()) { |
182 assertEquals(expected.getReceivedByteCount(), actual.getReceivedByte
Count()); | 167 assertEquals(expected.getReceivedByteCount(), actual.getReceivedByte
Count()); |
183 assertEquals(expected.getProxyServer(), actual.getProxyServer()); | 168 assertEquals(expected.getProxyServer(), actual.getProxyServer()); |
184 // This is a place where behavior intentionally differs between nati
ve and java | 169 // This is a place where behavior intentionally differs between nati
ve and java |
185 assertEquals(expected.getNegotiatedProtocol(), actual.getNegotiatedP
rotocol()); | 170 assertEquals(expected.getNegotiatedProtocol(), actual.getNegotiatedP
rotocol()); |
186 } | 171 } |
187 } | 172 } |
188 | 173 |
189 public static void assertContains(String expectedSubstring, String actualStr
ing) { | 174 public static void assertContains(String expectedSubstring, String actualStr
ing) { |
190 assertNotNull(actualString); | 175 assertNotNull(actualString); |
191 if (!actualString.contains(expectedSubstring)) { | 176 if (!actualString.contains(expectedSubstring)) { |
192 fail("String [" + actualString + "] doesn't contain substring [" + e
xpectedSubstring | 177 fail("String [" + actualString + "] doesn't contain substring [" + e
xpectedSubstring |
193 + "]"); | 178 + "]"); |
194 } | 179 } |
195 } | 180 } |
196 | 181 |
| 182 public CronetEngine.Builder enableDiskCache(CronetEngine.Builder cronetEngin
eBuilder) { |
| 183 cronetEngineBuilder.setStoragePath(getTestStorage(getContext())); |
| 184 cronetEngineBuilder.enableHttpCache(CronetEngine.Builder.HTTP_CACHE_DISK
, 1000 * 1024); |
| 185 return cronetEngineBuilder; |
| 186 } |
| 187 |
| 188 /** |
| 189 * Sets the {@link URLStreamHandlerFactory} from {@code cronetEngine}. This
should be called |
| 190 * during setUp() and is installed by {@link runTest()} as the default when
Cronet is tested. |
| 191 */ |
| 192 public void setStreamHandlerFactory(CronetEngine cronetEngine) { |
| 193 mStreamHandlerFactory = cronetEngine.createURLStreamHandlerFactory(); |
| 194 } |
| 195 |
197 @Target(ElementType.METHOD) | 196 @Target(ElementType.METHOD) |
198 @Retention(RetentionPolicy.RUNTIME) | 197 @Retention(RetentionPolicy.RUNTIME) |
199 public @interface CompareDefaultWithCronet { | 198 public @interface CompareDefaultWithCronet { |
200 } | 199 } |
201 | 200 |
202 @Target(ElementType.METHOD) | 201 @Target(ElementType.METHOD) |
203 @Retention(RetentionPolicy.RUNTIME) | 202 @Retention(RetentionPolicy.RUNTIME) |
204 public @interface OnlyRunCronetHttpURLConnection { | 203 public @interface OnlyRunCronetHttpURLConnection { |
205 } | 204 } |
206 | 205 |
207 @Target(ElementType.METHOD) | 206 @Target(ElementType.METHOD) |
208 @Retention(RetentionPolicy.RUNTIME) | 207 @Retention(RetentionPolicy.RUNTIME) |
209 public @interface OnlyRunNativeCronet {} | 208 public @interface OnlyRunNativeCronet {} |
| 209 |
| 210 /** |
| 211 * Prepares the path for the test storage (http cache, QUIC server info). |
| 212 */ |
| 213 public static void prepareTestStorage(Context context) { |
| 214 File storage = new File(getTestStorageDirectory()); |
| 215 if (storage.exists()) { |
| 216 assertTrue(recursiveDelete(storage)); |
| 217 } |
| 218 ensureTestStorageExists(); |
| 219 } |
| 220 |
| 221 /** |
| 222 * Returns the path for the test storage (http cache, QUIC server info). |
| 223 * NOTE: Does not ensure it exists; tests should use {@link #getTestStorage}
. |
| 224 */ |
| 225 private static String getTestStorageDirectory() { |
| 226 return PathUtils.getDataDirectory() + "/test_storage"; |
| 227 } |
| 228 |
| 229 /** |
| 230 * Ensures test storage directory exists, i.e. creates one if it does not ex
ist. |
| 231 */ |
| 232 private static void ensureTestStorageExists() { |
| 233 File storage = new File(getTestStorageDirectory()); |
| 234 if (!storage.exists()) { |
| 235 assertTrue(storage.mkdir()); |
| 236 } |
| 237 } |
| 238 |
| 239 /** |
| 240 * Returns the path for the test storage (http cache, QUIC server info). |
| 241 * Also ensures it exists. |
| 242 */ |
| 243 static String getTestStorage(Context context) { |
| 244 ensureTestStorageExists(); |
| 245 return getTestStorageDirectory(); |
| 246 } |
| 247 |
| 248 @SuppressFBWarnings("NP_NULL_ON_SOME_PATH_FROM_RETURN_VALUE") |
| 249 private static boolean recursiveDelete(File path) { |
| 250 if (path.isDirectory()) { |
| 251 for (File c : path.listFiles()) { |
| 252 if (!recursiveDelete(c)) { |
| 253 return false; |
| 254 } |
| 255 } |
| 256 } |
| 257 return path.delete(); |
| 258 } |
210 } | 259 } |
OLD | NEW |