/* Copyright (C) 2009 Mobile Sorcery AB
This program is free software; you can redistribute it and/or modify it
under the terms of the Eclipse Public License v1.0.
This program is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the Eclipse Public License v1.0 for
more details.
You should have received a copy of the Eclipse Public License v1.0 along
with this program. It is also available at http://www.eclipse.org/legal/epl-v10.html
*/
/**
*
*/
package com.mobilesorcery.sdk.testing.emulator;
import java.io.IOException;
import java.io.PipedInputStream;
import java.io.PipedOutputStream;
import org.eclipse.debug.core.ILaunchConfiguration;
import com.mobilesorcery.sdk.core.CoreMoSyncPlugin;
import com.mobilesorcery.sdk.core.IEmulatorProcessListener;
import com.mobilesorcery.sdk.testing.IRelaunchableTestSession;
import com.mobilesorcery.sdk.testing.TestSession;
import com.mobilesorcery.sdk.testing.TestSessionEvent;
public class EmulatorTestSession extends TestSession implements IEmulatorProcessListener, IRelaunchableTestSession {
static final byte[] TEST_MARKUP_PREFIX = "__TEST_MARKUP__".getBytes();
static final int TEST_MARKUP_PREFIX_LEN = TEST_MARKUP_PREFIX.length;
public final static String FILE_KEY = XMLTestReportParser.FILE_ATTR;
public final static String LINE_KEY = XMLTestReportParser.LINE_ATTR;
private boolean parserStarted;
private PipedOutputStream buffer;
private ILaunchConfiguration launchConfig;
private int emulatorId;
public EmulatorTestSession(String name, ILaunchConfiguration launchConfig, int emulatorId) {
super(name);
this.launchConfig = launchConfig;
this.emulatorId = emulatorId;
}
public void start() {
checkStartable();
CoreMoSyncPlugin.getDefault().getEmulatorProcessManager().addEmulatorProcessListener(emulatorId, this);
// Expects it to be started externally...
notifyListeners(new TestSessionEvent(TestSessionEvent.SESSION_STARTED, this, this));
}
public void finish() {
CoreMoSyncPlugin.getDefault().getEmulatorProcessManager().removeEmulatorProcessListener(this);
notifyListeners(new TestSessionEvent(TestSessionEvent.SESSION_FINISHED, this, this));
}
public void dataStreamed(int id, byte[] data, int offset, int length) {
try {
if (length < TEST_MARKUP_PREFIX_LEN) {
return;
}
for (int i = 0; i < TEST_MARKUP_PREFIX_LEN; i++) {
if (TEST_MARKUP_PREFIX[i] != data[offset + i]) {
return;
}
}
feedIntoParser(data, offset + TEST_MARKUP_PREFIX_LEN, length - TEST_MARKUP_PREFIX_LEN);
} catch (IOException e) {
// We don't report this to the UI, since it will for sure be reported by the other thread;
// if we would report it, a potentially large number of spurious error messages could show up.
e.printStackTrace();
}
}
private void feedIntoParser(byte[] data, int offset, int length) throws IOException {
if (!parserStarted) {
parserStarted = true;
XMLTestReportParser parser = new XMLTestReportParser(this, this);
PipedInputStream input = new PipedInputStream();
buffer = new PipedOutputStream();
buffer.connect(input);
// A small fix; we always need a root element, but the test framework will not give that to us.
buffer.write("<root>\n".getBytes());
parser.parse(input);
}
buffer.write(data, offset, length);
}
public void processStarted(int id) {
}
public void processStopped(int id) {
try {
// A small fix; we always need a root element, but the test framework will not give that to us.
buffer.write("</root>\n".getBytes());
buffer.close();
} catch (IOException e) {
reportSessionError(e);
}
}
void reportSessionError(Exception e) {
getTestResult().addFailure(this, e);
}
public ILaunchConfiguration getLaunchConfiguration() {
return launchConfig;
}
}