Fields Summary |
---|
private final ITestRunListener | mTestListener |
private TestResult | mCurrentTestResultStores the status values for the test result currently being parsed |
private String | mCurrentKeyStores the current "key" portion of the status key-value being parsed. |
private StringBuilder | mCurrentValueStores the current "value" portion of the status key-value being parsed. |
private boolean | mTestStartReportedTrue if start of test has already been reported to listener. |
private long | mTestTimeThe elapsed time of the test run, in milliseconds. |
private boolean | mIsCancelledTrue if current test run has been canceled by user. |
private static final String | LOG_TAG |
Methods Summary |
---|
public void | cancel()Requests cancellation of test run.
mIsCancelled = true;
|
private void | clearCurrentTestInfo()
mCurrentTestResult = null;
|
public void | done()Called by parent when adb session is complete.
super.done();
mTestListener.testRunEnded(mTestTime);
|
private com.android.ddmlib.testrunner.InstrumentationResultParser$TestResult | getCurrentTestInfo()
if (mCurrentTestResult == null) {
mCurrentTestResult = new TestResult();
}
return mCurrentTestResult;
|
private java.lang.String | getTrace(com.android.ddmlib.testrunner.InstrumentationResultParser$TestResult testInfo)Returns the stack trace of the current failed test, from the provided testInfo.
if (testInfo.mStackTrace != null) {
return testInfo.mStackTrace;
} else {
Log.e(LOG_TAG, "Could not find stack trace for failed test ");
return new Throwable("Unknown failure").toString();
}
|
private void | handleTestRunFailed(java.lang.String errorMsg)Process a instrumentation run failure
mTestListener.testRunFailed(errorMsg == null ? "Unknown error" : errorMsg);
|
public boolean | isCancelled()Returns true if test run canceled.
return mIsCancelled;
|
private void | parse(java.lang.String line)Parse an individual output line. Expects a line that is one of:
-
The start of a new status line (starts with Prefixes.STATUS or Prefixes.STATUS_CODE),
and thus there is a new key=value pair to parse, and the previous key-value pair is
finished.
-
A continuation of the previous status (the "value" portion of the key has wrapped
to the next line).
- A line reporting a fatal error in the test run (Prefixes.STATUS_FAILED)
- A line reporting the total elapsed time of the test run. (Prefixes.TIME_REPORT)
if (line.startsWith(Prefixes.STATUS_CODE)) {
// Previous status key-value has been collected. Store it.
submitCurrentKeyValue();
parseStatusCode(line);
} else if (line.startsWith(Prefixes.STATUS)) {
// Previous status key-value has been collected. Store it.
submitCurrentKeyValue();
parseKey(line, Prefixes.STATUS.length());
} else if (line.startsWith(Prefixes.RESULT)) {
// Previous status key-value has been collected. Store it.
submitCurrentKeyValue();
parseKey(line, Prefixes.RESULT.length());
} else if (line.startsWith(Prefixes.STATUS_FAILED) ||
line.startsWith(Prefixes.CODE)) {
// Previous status key-value has been collected. Store it.
submitCurrentKeyValue();
// just ignore the remaining data on this line
} else if (line.startsWith(Prefixes.TIME_REPORT)) {
parseTime(line, Prefixes.TIME_REPORT.length());
} else {
if (mCurrentValue != null) {
// this is a value that has wrapped to next line.
mCurrentValue.append("\r\n");
mCurrentValue.append(line);
} else {
Log.w(LOG_TAG, "unrecognized line " + line);
}
}
|
private void | parseKey(java.lang.String line, int keyStartPos)Parses the key from the current line.
Expects format of "key=value".
int endKeyPos = line.indexOf('=", keyStartPos);
if (endKeyPos != -1) {
mCurrentKey = line.substring(keyStartPos, endKeyPos).trim();
parseValue(line, endKeyPos + 1);
}
|
private void | parseStatusCode(java.lang.String line)Parses out a status code result.
String value = line.substring(Prefixes.STATUS_CODE.length()).trim();
TestResult testInfo = getCurrentTestInfo();
try {
testInfo.mCode = Integer.parseInt(value);
} catch (NumberFormatException e) {
Log.e(LOG_TAG, "Expected integer status code, received: " + value);
}
// this means we're done with current test result bundle
reportResult(testInfo);
clearCurrentTestInfo();
|
private void | parseTime(java.lang.String line, int startPos)Parses out and store the elapsed time.
String timeString = line.substring(startPos);
try {
float timeSeconds = Float.parseFloat(timeString);
mTestTime = (long) (timeSeconds * 1000);
} catch (NumberFormatException e) {
Log.e(LOG_TAG, "Unexpected time format " + timeString);
}
|
private void | parseValue(java.lang.String line, int valueStartPos)Parses the start of a key=value pair.
mCurrentValue = new StringBuilder();
mCurrentValue.append(line.substring(valueStartPos));
|
public void | processNewLines(java.lang.String[] lines)Processes the instrumentation test output from shell.
for (String line : lines) {
parse(line);
// in verbose mode, dump all adb output to log
Log.v(LOG_TAG, line);
}
|
private void | reportResult(com.android.ddmlib.testrunner.InstrumentationResultParser$TestResult testInfo)Reports a test result to the test run listener. Must be called when a individual test
result has been fully parsed.
if (!testInfo.isComplete()) {
Log.w(LOG_TAG, "invalid instrumentation status bundle " + testInfo.toString());
return;
}
reportTestRunStarted(testInfo);
TestIdentifier testId = new TestIdentifier(testInfo.mTestClass, testInfo.mTestName);
switch (testInfo.mCode) {
case StatusCodes.START:
mTestListener.testStarted(testId);
break;
case StatusCodes.FAILURE:
mTestListener.testFailed(ITestRunListener.TestFailure.FAILURE, testId,
getTrace(testInfo));
mTestListener.testEnded(testId);
break;
case StatusCodes.ERROR:
mTestListener.testFailed(ITestRunListener.TestFailure.ERROR, testId,
getTrace(testInfo));
mTestListener.testEnded(testId);
break;
case StatusCodes.OK:
mTestListener.testEnded(testId);
break;
default:
Log.e(LOG_TAG, "Unknown status code received: " + testInfo.mCode);
mTestListener.testEnded(testId);
break;
}
|
private void | reportTestRunStarted(com.android.ddmlib.testrunner.InstrumentationResultParser$TestResult testInfo)Reports the start of a test run, and the total test count, if it has not been previously
reported.
// if start test run not reported yet
if (!mTestStartReported && testInfo.mNumTests != null) {
mTestListener.testRunStarted(testInfo.mNumTests);
mTestStartReported = true;
}
|
private void | submitCurrentKeyValue()Stores the currently parsed key-value pair into mCurrentTestInfo.
if (mCurrentKey != null && mCurrentValue != null) {
TestResult testInfo = getCurrentTestInfo();
String statusValue = mCurrentValue.toString();
if (mCurrentKey.equals(StatusKeys.CLASS)) {
testInfo.mTestClass = statusValue.trim();
} else if (mCurrentKey.equals(StatusKeys.TEST)) {
testInfo.mTestName = statusValue.trim();
} else if (mCurrentKey.equals(StatusKeys.NUMTESTS)) {
try {
testInfo.mNumTests = Integer.parseInt(statusValue);
} catch (NumberFormatException e) {
Log.e(LOG_TAG, "Unexpected integer number of tests, received " + statusValue);
}
} else if (mCurrentKey.equals(StatusKeys.ERROR) ||
mCurrentKey.equals(StatusKeys.SHORTMSG)) {
// test run must have failed
handleTestRunFailed(statusValue);
} else if (mCurrentKey.equals(StatusKeys.STACK)) {
testInfo.mStackTrace = statusValue;
}
mCurrentKey = null;
mCurrentValue = null;
}
|