Merge change 3761 into donut
* changes: Added support to record page load time for each url.
This commit is contained in:
@@ -18,6 +18,7 @@ import time
|
||||
TEST_LIST_FILE = "/sdcard/android/reliability_tests_list.txt"
|
||||
TEST_STATUS_FILE = "/sdcard/android/reliability_running_test.txt"
|
||||
TEST_TIMEOUT_FILE = "/sdcard/android/reliability_timeout_test.txt"
|
||||
TEST_LOAD_TIME_FILE = "/sdcard/android/reliability_load_time.txt"
|
||||
HTTP_URL_FILE = "urllist_http"
|
||||
HTTPS_URL_FILE = "urllist_https"
|
||||
NUM_URLS = 25
|
||||
@@ -62,6 +63,36 @@ def Bugreport(url, bugreport_dir, adb_cmd):
|
||||
os.system(cmd)
|
||||
|
||||
|
||||
def ProcessPageLoadTime(raw_log):
|
||||
"""Processes the raw page load time logged by test app."""
|
||||
log_handle = open(raw_log, "r")
|
||||
load_times = {}
|
||||
|
||||
for line in log_handle:
|
||||
line = line.strip()
|
||||
pair = line.split("|")
|
||||
if len(pair) != 2:
|
||||
logging.info("Line has more than one '|': " + line)
|
||||
continue
|
||||
if pair[0] not in load_times:
|
||||
load_times[pair[0]] = [0, 0]
|
||||
try:
|
||||
pair[1] = int(pair[1])
|
||||
except ValueError:
|
||||
logging.info("Lins has non-numeric load time: " + line)
|
||||
continue
|
||||
load_times[pair[0]][0] += pair[1]
|
||||
load_times[pair[0]][1] += 1
|
||||
|
||||
log_handle.close()
|
||||
|
||||
# rewrite the average time to file
|
||||
log_handle = open(raw_log, "w")
|
||||
for url, times in load_times.iteritems():
|
||||
log_handle.write("%s|%f\n" % (url, float(times[0]) / times[1]))
|
||||
log_handle.close()
|
||||
|
||||
|
||||
def main(options, args):
|
||||
"""Send the url list to device and start testing, restart if crashed."""
|
||||
|
||||
@@ -141,8 +172,13 @@ def main(options, args):
|
||||
# Call ReliabilityTestsAutoTest#startReliabilityTests
|
||||
test_cmd = (test_cmd_prefix + " -e class "
|
||||
"com.android.dumprendertree.ReliabilityTest#"
|
||||
"runReliabilityTest -e timeout %s -e delay %s %s" %
|
||||
(str(timeout_ms), str(manual_delay), test_cmd_postfix))
|
||||
"runReliabilityTest -e timeout %s -e delay %s" %
|
||||
(str(timeout_ms), str(manual_delay)))
|
||||
|
||||
if options.logtime:
|
||||
test_cmd += " -e logtime true"
|
||||
|
||||
test_cmd += test_cmd_postfix
|
||||
|
||||
adb_output = subprocess.Popen(test_cmd, shell=True,
|
||||
stdout=subprocess.PIPE,
|
||||
@@ -176,12 +212,20 @@ def main(options, args):
|
||||
else:
|
||||
logging.info("No crash found.")
|
||||
|
||||
# get timeout file from sdcard
|
||||
test_cmd = (adb_cmd + "pull \"" + TEST_TIMEOUT_FILE + "\" \""
|
||||
+ timedout_file + "\"")
|
||||
|
||||
subprocess.Popen(test_cmd, shell=True, stdout=subprocess.PIPE,
|
||||
stderr=subprocess.PIPE).communicate()
|
||||
|
||||
if options.logtime:
|
||||
# get logged page load times from sdcard
|
||||
test_cmd = (adb_cmd + "pull \"" + TEST_LOAD_TIME_FILE + "\" \""
|
||||
+ options.logtime + "\"")
|
||||
subprocess.Popen(test_cmd, shell=True, stdout=subprocess.PIPE,
|
||||
stderr=subprocess.PIPE).communicate()
|
||||
ProcessPageLoadTime(options.logtime)
|
||||
|
||||
|
||||
if "__main__" == __name__:
|
||||
option_parser = optparse.OptionParser()
|
||||
@@ -206,5 +250,8 @@ if "__main__" == __name__:
|
||||
option_parser.add_option("-b", "--bugreport",
|
||||
default=".",
|
||||
help="the directory to store bugreport for crashes")
|
||||
option_parser.add_option("-l", "--logtime",
|
||||
default=None,
|
||||
help="Logs page load time for each url to the file")
|
||||
opts, arguments = option_parser.parse_args()
|
||||
main(opts, arguments)
|
||||
|
||||
@@ -69,11 +69,16 @@ public class LayoutTestsAutoRunner extends InstrumentationTestRunner {
|
||||
String r = (String)icicle.get("rebaseline");
|
||||
this.mRebaseline = (r != null && r.toLowerCase().equals("true"));
|
||||
super.onCreate(icicle);
|
||||
|
||||
String logtime = (String) icicle.get("logtime");
|
||||
this.mLogtime = (logtime != null
|
||||
&& logtime.toLowerCase().equals("true"));
|
||||
}
|
||||
|
||||
public String mTestPath = null;
|
||||
public int mTimeoutInMillis = 0;
|
||||
public int mDelay = 0;
|
||||
public boolean mRebaseline = false;
|
||||
public boolean mLogtime = false;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
package com.android.dumprendertree;
|
||||
|
||||
import android.os.Handler;
|
||||
import android.os.Message;
|
||||
import android.test.ActivityInstrumentationTestCase2;
|
||||
import android.util.Log;
|
||||
|
||||
@@ -15,43 +16,44 @@ import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
|
||||
public class ReliabilityTest extends ActivityInstrumentationTestCase2<ReliabilityTestActivity> {
|
||||
|
||||
|
||||
private static final String LOGTAG = "ReliabilityTest";
|
||||
private static final String PKG_NAME = "com.android.dumprendertree";
|
||||
private static final String TEST_LIST_FILE = "/sdcard/android/reliability_tests_list.txt";
|
||||
private static final String TEST_STATUS_FILE = "/sdcard/android/reliability_running_test.txt";
|
||||
private static final String TEST_TIMEOUT_FILE = "/sdcard/android/reliability_timeout_test.txt";
|
||||
private static final String TEST_LOAD_TIME_FILE = "/sdcard/android/reliability_load_time.txt";
|
||||
private static final String TEST_DONE = "#DONE";
|
||||
static final String RELIABILITY_TEST_RUNNER_FILES[] = {
|
||||
"run_reliability_tests.py"
|
||||
};
|
||||
|
||||
|
||||
public ReliabilityTest() {
|
||||
super(PKG_NAME, ReliabilityTestActivity.class);
|
||||
}
|
||||
|
||||
|
||||
public void runReliabilityTest() throws Throwable {
|
||||
ReliabilityTestActivity activity = getActivity();
|
||||
LayoutTestsAutoRunner runner = (LayoutTestsAutoRunner)getInstrumentation();
|
||||
|
||||
|
||||
File testListFile = new File(TEST_LIST_FILE);
|
||||
if(!testListFile.exists())
|
||||
throw new FileNotFoundException("test list file not found.");
|
||||
|
||||
|
||||
BufferedReader listReader = new BufferedReader(
|
||||
new FileReader(testListFile));
|
||||
|
||||
|
||||
//always try to resume first, hence cleaning up status will be the
|
||||
//responsibility of driver scripts
|
||||
String lastUrl = readTestStatus();
|
||||
if(lastUrl != null && !TEST_DONE.equals(lastUrl))
|
||||
fastForward(listReader, lastUrl);
|
||||
|
||||
|
||||
String url = null;
|
||||
Handler handler = null;
|
||||
boolean timeoutFlag = false;
|
||||
long start, elapsed;
|
||||
|
||||
|
||||
//read from BufferedReader instead of populating a list in advance,
|
||||
//this will avoid excessive memory usage in case of a large list
|
||||
while((url = listReader.readLine()) != null) {
|
||||
@@ -65,9 +67,13 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
//use message to send new URL to avoid interacting with
|
||||
//WebView in non-UI thread
|
||||
handler = activity.getHandler();
|
||||
handler.sendMessage(handler.obtainMessage(
|
||||
ReliabilityTestActivity.MSG_NAVIGATE,
|
||||
runner.mTimeoutInMillis, runner.mDelay, url));
|
||||
Message msg = handler.obtainMessage(
|
||||
ReliabilityTestActivity.MSG_NAVIGATE,
|
||||
runner.mTimeoutInMillis, runner.mDelay);
|
||||
msg.getData().putString(ReliabilityTestActivity.MSG_NAV_URL, url);
|
||||
msg.getData().putBoolean(ReliabilityTestActivity.MSG_NAV_LOGTIME,
|
||||
runner.mLogtime);
|
||||
handler.sendMessage(msg);
|
||||
timeoutFlag = activity.waitUntilDone();
|
||||
elapsed = System.currentTimeMillis() - start;
|
||||
if(elapsed < 1000) {
|
||||
@@ -79,6 +85,9 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
if(timeoutFlag) {
|
||||
writeTimeoutFile(url);
|
||||
}
|
||||
if(runner.mLogtime) {
|
||||
writeLoadTime(url, activity.getPageLoadTime());
|
||||
}
|
||||
System.runFinalization();
|
||||
System.gc();
|
||||
System.gc();
|
||||
@@ -87,7 +96,7 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
activity.finish();
|
||||
listReader.close();
|
||||
}
|
||||
|
||||
|
||||
public void copyRunnerAssetsToCache() {
|
||||
try {
|
||||
String out_dir = getActivity().getApplicationContext()
|
||||
@@ -112,7 +121,7 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
Log.e(LOGTAG, "Cannot extract scripts for testing.", e);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private void updateTestStatus(String s) {
|
||||
// write last tested url into status file
|
||||
try {
|
||||
@@ -124,7 +133,7 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
Log.e(LOGTAG, "Cannot update file " + TEST_STATUS_FILE, e);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private String readTestStatus() {
|
||||
// read out the test name it stopped last time.
|
||||
String status = null;
|
||||
@@ -141,12 +150,12 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
|
||||
private void fastForward(BufferedReader testListReader, String lastUrl) {
|
||||
//fastforward the BufferedReader to the position right after last url
|
||||
if(lastUrl == null)
|
||||
return;
|
||||
|
||||
|
||||
String line = null;
|
||||
try {
|
||||
while((line = testListReader.readLine()) != null) {
|
||||
@@ -160,7 +169,7 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
}
|
||||
|
||||
private void writeTimeoutFile(String s) {
|
||||
//append to the file containing the list of timeout urls
|
||||
//append to the file containing the list of timeout urls
|
||||
try {
|
||||
BufferedOutputStream bos = new BufferedOutputStream(
|
||||
new FileOutputStream(TEST_TIMEOUT_FILE, true));
|
||||
@@ -171,4 +180,16 @@ public class ReliabilityTest extends ActivityInstrumentationTestCase2<Reliabilit
|
||||
Log.e(LOGTAG, "Cannot update file " + TEST_TIMEOUT_FILE, e);
|
||||
}
|
||||
}
|
||||
|
||||
private void writeLoadTime(String s, long time) {
|
||||
//append to the file containing the list of timeout urls
|
||||
try {
|
||||
BufferedOutputStream bos = new BufferedOutputStream(
|
||||
new FileOutputStream(TEST_LOAD_TIME_FILE, true));
|
||||
bos.write((s + '|' + time + '\n').getBytes());
|
||||
bos.close();
|
||||
} catch (Exception e) {
|
||||
Log.e(LOGTAG, "Cannot update file " + TEST_LOAD_TIME_FILE, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,52 +21,57 @@ import android.widget.LinearLayout;
|
||||
import android.widget.LinearLayout.LayoutParams;
|
||||
|
||||
public class ReliabilityTestActivity extends Activity {
|
||||
|
||||
|
||||
public static final String TEST_URL_ACTION = "com.andrdoid.dumprendertree.TestUrlAction";
|
||||
public static final String PARAM_URL = "URL";
|
||||
public static final String PARAM_TIMEOUT = "Timeout";
|
||||
public static final int RESULT_TIMEOUT = 0xDEAD;
|
||||
public static final int MSG_TIMEOUT = 0xC001;
|
||||
public static final int MSG_NAVIGATE = 0xC002;
|
||||
|
||||
public static final String MSG_NAV_URL = "url";
|
||||
public static final String MSG_NAV_LOGTIME = "logtime";
|
||||
|
||||
private static final String LOGTAG = "ReliabilityTestActivity";
|
||||
|
||||
|
||||
private WebView webView;
|
||||
private SimpleWebViewClient webViewClient;
|
||||
private SimpleChromeClient chromeClient;
|
||||
private Handler handler;
|
||||
private boolean timeoutFlag;
|
||||
private boolean logTime;
|
||||
private boolean pageDone;
|
||||
private Object pageDoneLock;
|
||||
private int pageStartCount;
|
||||
private int manualDelay;
|
||||
private long startTime;
|
||||
private long pageLoadTime;
|
||||
private PageDoneRunner pageDoneRunner = new PageDoneRunner();
|
||||
|
||||
|
||||
@Override
|
||||
protected void onCreate(Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
|
||||
Log.v(LOGTAG, "onCreate, inst=" + Integer.toHexString(hashCode()));
|
||||
|
||||
|
||||
LinearLayout contentView = new LinearLayout(this);
|
||||
contentView.setOrientation(LinearLayout.VERTICAL);
|
||||
setContentView(contentView);
|
||||
setTitle("Idle");
|
||||
|
||||
|
||||
webView = new WebView(this);
|
||||
webView.getSettings().setJavaScriptEnabled(true);
|
||||
webView.getSettings().setJavaScriptCanOpenWindowsAutomatically(false);
|
||||
webView.getSettings().setLayoutAlgorithm(LayoutAlgorithm.NORMAL);
|
||||
|
||||
|
||||
webViewClient = new SimpleWebViewClient();
|
||||
chromeClient = new SimpleChromeClient();
|
||||
webView.setWebViewClient(webViewClient);
|
||||
webView.setWebChromeClient(chromeClient);
|
||||
|
||||
|
||||
contentView.addView(webView, new LayoutParams(
|
||||
ViewGroup.LayoutParams.FILL_PARENT,
|
||||
ViewGroup.LayoutParams.FILL_PARENT, 0.0f));
|
||||
|
||||
|
||||
handler = new Handler() {
|
||||
@Override
|
||||
public void handleMessage(Message msg) {
|
||||
@@ -76,15 +81,16 @@ public class ReliabilityTestActivity extends Activity {
|
||||
return;
|
||||
case MSG_NAVIGATE:
|
||||
manualDelay = msg.arg2;
|
||||
navigate((String)msg.obj, msg.arg1);
|
||||
navigate(msg.getData().getString(MSG_NAV_URL), msg.arg1);
|
||||
logTime = msg.getData().getBoolean(MSG_NAV_LOGTIME);
|
||||
return;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
pageDoneLock = new Object();
|
||||
}
|
||||
|
||||
|
||||
public void reset() {
|
||||
synchronized (pageDoneLock) {
|
||||
pageDone = false;
|
||||
@@ -93,42 +99,46 @@ public class ReliabilityTestActivity extends Activity {
|
||||
pageStartCount = 0;
|
||||
chromeClient.resetJsTimeout();
|
||||
}
|
||||
|
||||
|
||||
private void navigate(String url, int timeout) {
|
||||
if(url == null) {
|
||||
Log.v(LOGTAG, "URL is null, cancelling...");
|
||||
finish();
|
||||
}
|
||||
webView.stopLoading();
|
||||
if(logTime) {
|
||||
webView.clearCache(true);
|
||||
}
|
||||
startTime = System.currentTimeMillis();
|
||||
Log.v(LOGTAG, "Navigating to URL: " + url);
|
||||
webView.loadUrl(url);
|
||||
|
||||
|
||||
if(timeout != 0) {
|
||||
//set a timer with specified timeout (in ms)
|
||||
handler.sendMessageDelayed(handler.obtainMessage(MSG_TIMEOUT),
|
||||
timeout);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected void onDestroy() {
|
||||
Log.v(LOGTAG, "onDestroy, inst=" + Integer.toHexString(hashCode()));
|
||||
super.onDestroy();
|
||||
}
|
||||
|
||||
|
||||
private boolean isPageDone() {
|
||||
synchronized (pageDoneLock) {
|
||||
return pageDone;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private void setPageDone(boolean pageDone) {
|
||||
synchronized (pageDoneLock) {
|
||||
this.pageDone = pageDone;
|
||||
pageDoneLock.notifyAll();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private void handleTimeout() {
|
||||
int progress = webView.getProgress();
|
||||
webView.stopLoading();
|
||||
@@ -136,7 +146,7 @@ public class ReliabilityTestActivity extends Activity {
|
||||
timeoutFlag = true;
|
||||
handler.postDelayed(pageDoneRunner, manualDelay);
|
||||
}
|
||||
|
||||
|
||||
public boolean waitUntilDone() {
|
||||
validateNotAppThread();
|
||||
synchronized (pageDoneLock) {
|
||||
@@ -150,11 +160,11 @@ public class ReliabilityTestActivity extends Activity {
|
||||
}
|
||||
return timeoutFlag;
|
||||
}
|
||||
|
||||
|
||||
public Handler getHandler() {
|
||||
return handler;
|
||||
}
|
||||
|
||||
|
||||
private final void validateNotAppThread() {
|
||||
if (ActivityThread.currentActivityThread() != null) {
|
||||
throw new RuntimeException(
|
||||
@@ -162,8 +172,12 @@ public class ReliabilityTestActivity extends Activity {
|
||||
}
|
||||
}
|
||||
|
||||
public long getPageLoadTime() {
|
||||
return pageLoadTime;
|
||||
}
|
||||
|
||||
class SimpleWebViewClient extends WebViewClient {
|
||||
|
||||
|
||||
@Override
|
||||
public void onReceivedError(WebView view, int errorCode, String description,
|
||||
String failingUrl) {
|
||||
@@ -171,27 +185,27 @@ public class ReliabilityTestActivity extends Activity {
|
||||
+ ", description=" + description
|
||||
+ ", url=" + failingUrl);
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
|
||||
//ignore certificate error
|
||||
Log.v(LOGTAG, "Received SSL error: " + error.toString());
|
||||
handler.proceed();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void onReceivedHttpAuthRequest(WebView view, HttpAuthHandler handler, String host,
|
||||
String realm) {
|
||||
// cancel http auth request
|
||||
handler.cancel();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void onPageStarted(WebView view, String url, Bitmap favicon) {
|
||||
pageStartCount++;
|
||||
Log.v(LOGTAG, "onPageStarted: " + url);
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void onPageFinished(WebView view, String url) {
|
||||
Log.v(LOGTAG, "onPageFinished: " + url);
|
||||
@@ -200,23 +214,23 @@ public class ReliabilityTestActivity extends Activity {
|
||||
handler.postDelayed(new WebViewStatusChecker(), 500);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class SimpleChromeClient extends WebChromeClient {
|
||||
|
||||
|
||||
private int timeoutCounter = 0;
|
||||
|
||||
|
||||
@Override
|
||||
public boolean onJsAlert(WebView view, String url, String message, JsResult result) {
|
||||
result.confirm();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean onJsBeforeUnload(WebView view, String url, String message, JsResult result) {
|
||||
result.confirm();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean onJsConfirm(WebView view, String url, String message, JsResult result) {
|
||||
result.confirm();
|
||||
@@ -229,32 +243,32 @@ public class ReliabilityTestActivity extends Activity {
|
||||
result.confirm();
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean onJsTimeout() {
|
||||
timeoutCounter++;
|
||||
Log.v(LOGTAG, "JavaScript timeout, count=" + timeoutCounter);
|
||||
return timeoutCounter > 2;
|
||||
}
|
||||
|
||||
|
||||
public void resetJsTimeout() {
|
||||
timeoutCounter = 0;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public void onReceivedTitle(WebView view, String title) {
|
||||
ReliabilityTestActivity.this.setTitle(title);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class WebViewStatusChecker implements Runnable {
|
||||
|
||||
|
||||
private int initialStartCount;
|
||||
|
||||
|
||||
public WebViewStatusChecker() {
|
||||
initialStartCount = pageStartCount;
|
||||
}
|
||||
|
||||
|
||||
public void run() {
|
||||
if (initialStartCount == pageStartCount) {
|
||||
//perform cleanup
|
||||
@@ -264,11 +278,12 @@ public class ReliabilityTestActivity extends Activity {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class PageDoneRunner implements Runnable {
|
||||
|
||||
|
||||
public void run() {
|
||||
Log.v(LOGTAG, "Finishing URL: " + webView.getUrl());
|
||||
pageLoadTime = System.currentTimeMillis() - startTime;
|
||||
setPageDone(true);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user