Refactoring

This commit is contained in:
konsoletyper 2014-07-30 21:51:21 +04:00
parent c2eecaefca
commit 25789825fc
23 changed files with 377 additions and 390 deletions

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd; package org.teavm.chromerdp;
/** /**
* *

View File

@ -1,46 +1,24 @@
/* package org.teavm.chromerdp;
* Copyright 2014 Alexey Andreev.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.teavm.chromerpd;
import java.io.IOException; import java.io.IOException;
import java.util.HashMap; import java.util.*;
import java.util.Map;
import javax.websocket.OnClose;
import javax.websocket.OnMessage;
import javax.websocket.OnOpen;
import javax.websocket.Session;
import javax.websocket.server.ServerEndpoint;
import org.codehaus.jackson.JsonNode; import org.codehaus.jackson.JsonNode;
import org.codehaus.jackson.map.ObjectMapper; import org.codehaus.jackson.map.ObjectMapper;
import org.teavm.chromerpd.data.CallFrameDTO; import org.teavm.chromerdp.data.CallFrameDTO;
import org.teavm.chromerpd.data.LocationDTO; import org.teavm.chromerdp.data.LocationDTO;
import org.teavm.chromerpd.data.Message; import org.teavm.chromerdp.data.Message;
import org.teavm.chromerpd.data.Response; import org.teavm.chromerdp.data.Response;
import org.teavm.chromerpd.messages.*; import org.teavm.chromerdp.messages.*;
import org.teavm.debugging.JavaScriptBreakpoint; import org.teavm.debugging.*;
import org.teavm.debugging.JavaScriptCallFrame;
import org.teavm.debugging.JavaScriptLocation;
/** /**
* *
* @author Alexey Andreev * @author Alexey Andreev <konsoletyper@gmail.com>
*/ */
@ServerEndpoint("/") public class ChromeRDPDebugger implements JavaScriptDebugger, ChromeRDPExchangeConsumer {
public class ChromeRDPDebuggerEndpoint { private ChromeRDPExchange exchange;
private Session session; private List<JavaScriptDebuggerListener> listeners = new ArrayList<>();
private Set<RDPBreakpoint> breakpoints = new HashSet<>();
private RDPCallFrame[] callStack = new RDPCallFrame[0]; private RDPCallFrame[] callStack = new RDPCallFrame[0];
private Map<String, String> scripts = new HashMap<>(); private Map<String, String> scripts = new HashMap<>();
private Map<String, String> scriptIds = new HashMap<>(); private Map<String, String> scriptIds = new HashMap<>();
@ -48,30 +26,36 @@ public class ChromeRDPDebuggerEndpoint {
private ObjectMapper mapper = new ObjectMapper(); private ObjectMapper mapper = new ObjectMapper();
private Map<Integer, ResponseHandler> responseHandlers = new HashMap<>(); private Map<Integer, ResponseHandler> responseHandlers = new HashMap<>();
private int messageIdGenerator; private int messageIdGenerator;
boolean closed;
private ChromeRDPDebugger debugger;
@OnOpen @Override
public void open(Session session) { public void setExchange(ChromeRDPExchange exchange) {
this.session = session; if (this.exchange == exchange) {
Object debugger = session.getUserProperties().get("chrome.rdp"); return;
if (debugger instanceof ChromeRDPDebugger) { }
this.debugger = (ChromeRDPDebugger)debugger; if (this.exchange != null) {
this.debugger.setEndpoint(this); this.exchange.removeListener(exchangeListener);
}
this.exchange = exchange;
if (exchange != null) {
for (RDPBreakpoint breakpoint : breakpoints) {
updateBreakpoint(breakpoint);
}
for (JavaScriptDebuggerListener listener : listeners) {
listener.attached();
}
} else {
suspended = false;
for (JavaScriptDebuggerListener listener : listeners) {
listener.detached();
}
}
if (this.exchange != null) {
this.exchange.addListener(exchangeListener);
} }
} }
@OnClose private ChromeRDPExchangeListener exchangeListener = new ChromeRDPExchangeListener() {
public void close() { @Override public void received(String messageText) throws IOException {
closed = true;
if (this.debugger != null) {
this.debugger.setEndpoint(null);
this.debugger = null;
}
}
@OnMessage
public void receive(String messageText) throws IOException {
JsonNode jsonMessage = mapper.readTree(messageText); JsonNode jsonMessage = mapper.readTree(messageText);
if (jsonMessage.has("result")) { if (jsonMessage.has("result")) {
Response response = mapper.reader(Response.class).readValue(jsonMessage); Response response = mapper.reader(Response.class).readValue(jsonMessage);
@ -91,10 +75,8 @@ public class ChromeRDPDebuggerEndpoint {
} }
} }
} }
};
private <T> T parseJson(Class<T> type, JsonNode node) throws IOException {
return mapper.reader(type).readValue(node);
}
private synchronized void firePaused(SuspendedNotification params) { private synchronized void firePaused(SuspendedNotification params) {
suspended = true; suspended = true;
@ -104,7 +86,183 @@ public class ChromeRDPDebuggerEndpoint {
callStack[i] = map(callFrameDTOs[i]); callStack[i] = map(callFrameDTOs[i]);
} }
this.callStack = callStack; this.callStack = callStack;
debugger.firePaused(); for (JavaScriptDebuggerListener listener : listeners) {
listener.paused();
}
}
private synchronized void fireResumed() {
suspended = false;
callStack = null;
for (JavaScriptDebuggerListener listener : listeners) {
listener.resumed();
}
}
private synchronized void scriptParsed(ScriptParsedNotification params) {
if (scripts.containsKey(params.getScriptId())) {
return;
}
scripts.put(params.getScriptId(), params.getUrl());
scriptIds.put(params.getUrl(), params.getScriptId());
for (JavaScriptDebuggerListener listener : listeners) {
listener.scriptAdded(params.getUrl());
}
}
@Override
public void addListener(JavaScriptDebuggerListener listener) {
listeners.add(listener);
}
@Override
public void removeListener(JavaScriptDebuggerListener listener) {
listeners.remove(listener);
}
@Override
public void suspend() {
if (exchange == null) {
return;
}
Message message = new Message();
message.setMethod("Debugger.pause");
sendMessage(message);
}
@Override
public void resume() {
if (exchange == null) {
return;
}
Message message = new Message();
message.setMethod("Debugger.resume");
sendMessage(message);
}
@Override
public void stepInto() {
if (exchange == null) {
return;
}
Message message = new Message();
message.setMethod("Debugger.stepInto");
sendMessage(message);
}
@Override
public void stepOut() {
if (exchange == null) {
return;
}
Message message = new Message();
message.setMethod("Debugger.stepOut");
sendMessage(message);
}
@Override
public void stepOver() {
if (exchange == null) {
return;
}
Message message = new Message();
message.setMethod("Debugger.stepOver");
sendMessage(message);
}
@Override
public void continueToLocation(JavaScriptLocation location) {
if (exchange == null) {
return;
}
Message message = new Message();
message.setMethod("Debugger.continueToLocation");
ContinueToLocationCommand params = new ContinueToLocationCommand();
params.setLocation(unmap(location));
message.setParams(mapper.valueToTree(params));
sendMessage(message);
}
@Override
public boolean isSuspended() {
return exchange != null && suspended;
}
@Override
public boolean isAttached() {
return exchange != null;
}
@Override
public JavaScriptCallFrame[] getCallStack() {
if (exchange == null) {
return null;
}
return callStack != null ? callStack.clone() : null;
}
@Override
public JavaScriptBreakpoint createBreakpoint(JavaScriptLocation location) {
RDPBreakpoint breakpoint = new RDPBreakpoint(this, location);
breakpoints.add(breakpoint);
updateBreakpoint(breakpoint);
return breakpoint;
}
void destroyBreakpoint(RDPBreakpoint breakpoint) {
if (breakpoint.chromeId != null) {
Message message = new Message();
message.setMethod("Debugger.removeBreakpoint");
RemoveBreakpointCommand params = new RemoveBreakpointCommand();
params.setBreakpointId(breakpoint.chromeId);
message.setParams(mapper.valueToTree(params));
sendMessage(message);
}
}
void fireScriptAdded(String script) {
for (JavaScriptDebuggerListener listener : listeners) {
listener.scriptAdded(script);
}
}
void updateBreakpoint(final RDPBreakpoint breakpoint) {
if (exchange == null) {
return;
}
Message message = new Message();
message.setId(++messageIdGenerator);
message.setMethod("Debugger.setBreakpoint");
SetBreakpointCommand params = new SetBreakpointCommand();
params.setLocation(unmap(breakpoint.getLocation()));
message.setParams(mapper.valueToTree(params));
ResponseHandler handler = new ResponseHandler() {
@Override public void received(JsonNode node) throws IOException {
SetBreakpointResponse response = mapper.reader(SetBreakpointResponse.class).readValue(node);
breakpoint.chromeId = response.getBreakpointId();
for (JavaScriptDebuggerListener listener : listeners) {
listener.breakpointChanged(breakpoint);
}
}
};
responseHandlers.put(message.getId(), handler);
sendMessage(message);
}
private <T> T parseJson(Class<T> type, JsonNode node) throws IOException {
return mapper.reader(type).readValue(node);
}
private void sendMessage(Message message) {
if (exchange == null) {
return;
}
try {
exchange.send(mapper.writer().writeValueAsString(message));
} catch (IOException e) {
throw new RuntimeException(e);
}
} }
RDPCallFrame map(CallFrameDTO dto) { RDPCallFrame map(CallFrameDTO dto) {
@ -123,128 +281,6 @@ public class ChromeRDPDebuggerEndpoint {
return dto; return dto;
} }
private synchronized void fireResumed() {
suspended = false;
callStack = null;
debugger.fireResumed();
}
private synchronized void scriptParsed(ScriptParsedNotification params) {
if (scripts.containsKey(params.getScriptId())) {
return;
}
scripts.put(params.getScriptId(), params.getUrl());
scriptIds.put(params.getUrl(), params.getScriptId());
debugger.fireScriptAdded(params.getUrl());
}
private void sendMessage(Message message) {
if (closed) {
return;
}
try {
String messageText = mapper.writer().writeValueAsString(message);
session.getAsyncRemote().sendText(messageText);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
public void suspend() {
if (closed) {
return;
}
Message message = new Message();
message.setMethod("Debugger.pause");
sendMessage(message);
}
public void resume() {
if (closed) {
return;
}
Message message = new Message();
message.setMethod("Debugger.resume");
sendMessage(message);
}
public void stepInto() {
if (closed) {
return;
}
Message message = new Message();
message.setMethod("Debugger.stepInto");
sendMessage(message);
}
public void stepOut() {
if (closed) {
return;
}
Message message = new Message();
message.setMethod("Debugger.stepOut");
sendMessage(message);
}
public void stepOver() {
if (closed) {
return;
}
Message message = new Message();
message.setMethod("Debugger.stepOver");
sendMessage(message);
}
public synchronized void continueToLocation(JavaScriptLocation location) {
Message message = new Message();
message.setMethod("Debugger.continueToLocation");
ContinueToLocationCommand params = new ContinueToLocationCommand();
params.setLocation(unmap(location));
message.setParams(mapper.valueToTree(params));
sendMessage(message);
}
public synchronized boolean isSuspended() {
return suspended;
}
public synchronized JavaScriptCallFrame[] getCallStack() {
return callStack;
}
public synchronized JavaScriptBreakpoint getCurrentBreakpoint() {
return null;
}
public synchronized void updateBreakpoint(final RDPBreakpoint breakpoint) {
Message message = new Message();
message.setId(++messageIdGenerator);
message.setMethod("Debugger.setBreakpoint");
SetBreakpointCommand params = new SetBreakpointCommand();
params.setLocation(unmap(breakpoint.getLocation()));
message.setParams(mapper.valueToTree(params));
ResponseHandler handler = new ResponseHandler() {
@Override public void received(JsonNode node) throws IOException {
SetBreakpointResponse response = mapper.reader(SetBreakpointResponse.class).readValue(node);
breakpoint.chromeId = response.getBreakpointId();
debugger.fireBreakpointStatusChanged(breakpoint);
}
};
responseHandlers.put(message.getId(), handler);
sendMessage(message);
}
void destroyBreakpoint(RDPBreakpoint breakpoint) {
if (breakpoint.chromeId != null) {
Message message = new Message();
message.setMethod("Debugger.removeBreakpoint");
RemoveBreakpointCommand params = new RemoveBreakpointCommand();
params.setBreakpointId(breakpoint.chromeId);
message.setParams(mapper.valueToTree(params));
sendMessage(message);
}
}
interface ResponseHandler { interface ResponseHandler {
void received(JsonNode node) throws IOException; void received(JsonNode node) throws IOException;
} }

View File

@ -0,0 +1,76 @@
/*
* Copyright 2014 Alexey Andreev.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.teavm.chromerdp;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import javax.websocket.OnClose;
import javax.websocket.OnMessage;
import javax.websocket.OnOpen;
import javax.websocket.Session;
import javax.websocket.server.ServerEndpoint;
/**
*
* @author Alexey Andreev
*/
@ServerEndpoint("/")
public class ChromeRDPDebuggerEndpoint implements ChromeRDPExchange {
private Session session;
private ChromeRDPExchangeConsumer debugger;
private List<ChromeRDPExchangeListener> listeners = new ArrayList<>();
@OnOpen
public void open(Session session) {
this.session = session;
Object debugger = session.getUserProperties().get("chrome.rdp");
if (debugger instanceof ChromeRDPExchangeConsumer) {
this.debugger = (ChromeRDPExchangeConsumer)debugger;
this.debugger.setExchange(this);
}
}
@OnClose
public void close() {
if (this.debugger != null) {
this.debugger.setExchange(null);
this.debugger = null;
}
}
@OnMessage
public void receive(String message) throws IOException {
for (ChromeRDPExchangeListener listener : listeners) {
listener.received(message);
}
}
@Override
public void send(String message) {
session.getAsyncRemote().sendText(message);
}
@Override
public void addListener(ChromeRDPExchangeListener listener) {
listeners.add(listener);
}
@Override
public void removeListener(ChromeRDPExchangeListener listener) {
listeners.remove(listener);
}
}

View File

@ -0,0 +1,13 @@
package org.teavm.chromerdp;
/**
*
* @author Alexey Andreev <konsoletyper@gmail.com>
*/
public interface ChromeRDPExchange {
void send(String message);
void addListener(ChromeRDPExchangeListener listener);
void removeListener(ChromeRDPExchangeListener listener);
}

View File

@ -0,0 +1,9 @@
package org.teavm.chromerdp;
/**
*
* @author Alexey Andreev <konsoletyper@gmail.com>
*/
public interface ChromeRDPExchangeConsumer {
void setExchange(ChromeRDPExchange exchange);
}

View File

@ -0,0 +1,11 @@
package org.teavm.chromerdp;
import java.io.IOException;
/**
*
* @author Alexey Andreev <konsoletyper@gmail.com>
*/
public interface ChromeRDPExchangeListener {
void received(String message) throws IOException;
}

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd; package org.teavm.chromerdp;
import java.util.*; import java.util.*;
import javax.websocket.Decoder; import javax.websocket.Decoder;
@ -25,7 +25,6 @@ import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.server.ServerConnector; import org.eclipse.jetty.server.ServerConnector;
import org.eclipse.jetty.servlet.ServletContextHandler; import org.eclipse.jetty.servlet.ServletContextHandler;
import org.eclipse.jetty.websocket.jsr356.server.deploy.WebSocketServerContainerInitializer; import org.eclipse.jetty.websocket.jsr356.server.deploy.WebSocketServerContainerInitializer;
import org.teavm.debugging.JavaScriptDebugger;
/** /**
* *
@ -33,8 +32,7 @@ import org.teavm.debugging.JavaScriptDebugger;
*/ */
public class ChromeRDPServer { public class ChromeRDPServer {
private int port = 2357; private int port = 2357;
private Appendable output = System.err; private ChromeRDPExchangeConsumer exchangeConsumer;
private ChromeRDPDebugger debugger = new ChromeRDPDebugger();
public int getPort() { public int getPort() {
return port; return port;
@ -44,12 +42,12 @@ public class ChromeRDPServer {
this.port = port; this.port = port;
} }
public Appendable getOutput() { public ChromeRDPExchangeConsumer getExchangeConsumer() {
return output; return exchangeConsumer;
} }
public void setOutput(Appendable output) { public void setExchangeConsumer(ChromeRDPExchangeConsumer exchangeConsumer) {
this.output = output; this.exchangeConsumer = exchangeConsumer;
} }
public void start() { public void start() {
@ -67,7 +65,6 @@ public class ChromeRDPServer {
try { try {
wscontainer.addEndpoint(new RPDEndpointConfig()); wscontainer.addEndpoint(new RPDEndpointConfig());
server.start(); server.start();
server.dump(output);
server.join(); server.join();
} catch (Exception e) { } catch (Exception e) {
throw new RuntimeException(e); throw new RuntimeException(e);
@ -78,7 +75,7 @@ public class ChromeRDPServer {
private Map<String, Object> userProperties = new HashMap<>(); private Map<String, Object> userProperties = new HashMap<>();
public RPDEndpointConfig() { public RPDEndpointConfig() {
userProperties.put("chrome.rdp", debugger); userProperties.put("chrome.rdp", exchangeConsumer);
} }
@Override @Override
@ -121,8 +118,4 @@ public class ChromeRDPServer {
return Collections.emptyList(); return Collections.emptyList();
} }
} }
public JavaScriptDebugger getDebugger() {
return debugger;
}
} }

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd; package org.teavm.chromerdp;
import org.teavm.debugging.JavaScriptBreakpoint; import org.teavm.debugging.JavaScriptBreakpoint;
import org.teavm.debugging.JavaScriptLocation; import org.teavm.debugging.JavaScriptLocation;

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd; package org.teavm.chromerdp;
import org.teavm.debugging.JavaScriptCallFrame; import org.teavm.debugging.JavaScriptCallFrame;
import org.teavm.debugging.JavaScriptLocation; import org.teavm.debugging.JavaScriptLocation;

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.data; package org.teavm.chromerdp.data;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.data; package org.teavm.chromerdp.data;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.data; package org.teavm.chromerdp.data;
import org.codehaus.jackson.JsonNode; import org.codehaus.jackson.JsonNode;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.data; package org.teavm.chromerdp.data;
import org.codehaus.jackson.JsonNode; import org.codehaus.jackson.JsonNode;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;

View File

@ -13,10 +13,10 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.messages; package org.teavm.chromerdp.messages;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;
import org.teavm.chromerpd.data.LocationDTO; import org.teavm.chromerdp.data.LocationDTO;
/** /**
* *

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.messages; package org.teavm.chromerdp.messages;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;

View File

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.messages; package org.teavm.chromerdp.messages;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;

View File

@ -13,10 +13,10 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.messages; package org.teavm.chromerdp.messages;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;
import org.teavm.chromerpd.data.LocationDTO; import org.teavm.chromerdp.data.LocationDTO;
/** /**
* *

View File

@ -13,10 +13,10 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.messages; package org.teavm.chromerdp.messages;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;
import org.teavm.chromerpd.data.LocationDTO; import org.teavm.chromerdp.data.LocationDTO;
/** /**
* *

View File

@ -13,11 +13,11 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
package org.teavm.chromerpd.messages; package org.teavm.chromerdp.messages;
import org.codehaus.jackson.JsonNode; import org.codehaus.jackson.JsonNode;
import org.codehaus.jackson.annotate.JsonIgnoreProperties; import org.codehaus.jackson.annotate.JsonIgnoreProperties;
import org.teavm.chromerpd.data.CallFrameDTO; import org.teavm.chromerdp.data.CallFrameDTO;
/** /**
* *

View File

@ -1,149 +0,0 @@
package org.teavm.chromerpd;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import org.teavm.debugging.*;
/**
*
* @author Alexey Andreev <konsoletyper@gmail.com>
*/
public class ChromeRDPDebugger implements JavaScriptDebugger {
private ChromeRDPDebuggerEndpoint endpoint;
private List<JavaScriptDebuggerListener> listeners = new ArrayList<>();
private Set<RDPBreakpoint> breakpoints = new HashSet<>();
void setEndpoint(ChromeRDPDebuggerEndpoint endpoint) {
if (this.endpoint == endpoint) {
return;
}
this.endpoint = endpoint;
if (endpoint != null) {
for (RDPBreakpoint breakpoint : breakpoints) {
endpoint.updateBreakpoint(breakpoint);
}
for (JavaScriptDebuggerListener listener : listeners) {
listener.attached();
}
} else {
for (JavaScriptDebuggerListener listener : listeners) {
listener.detached();
}
}
}
@Override
public void addListener(JavaScriptDebuggerListener listener) {
listeners.add(listener);
}
@Override
public void removeListener(JavaScriptDebuggerListener listener) {
listeners.remove(listener);
}
@Override
public void suspend() {
if (endpoint != null) {
endpoint.suspend();
}
}
@Override
public void resume() {
if (endpoint != null) {
endpoint.resume();
}
}
@Override
public void stepInto() {
if (endpoint != null) {
endpoint.stepInto();
}
}
@Override
public void stepOut() {
if (endpoint != null) {
endpoint.stepOut();
}
}
@Override
public void stepOver() {
if (endpoint != null) {
endpoint.stepOver();
}
}
@Override
public void continueToLocation(JavaScriptLocation location) {
if (endpoint != null) {
endpoint.continueToLocation(location);
}
}
@Override
public boolean isSuspended() {
return endpoint != null && endpoint.isSuspended();
}
@Override
public boolean isAttached() {
return endpoint != null;
}
@Override
public JavaScriptCallFrame[] getCallStack() {
return endpoint != null ? endpoint.getCallStack() : null;
}
@Override
public JavaScriptBreakpoint getCurrentBreakpoint() {
return endpoint != null ? endpoint.getCurrentBreakpoint() : null;
}
@Override
public synchronized JavaScriptBreakpoint createBreakpoint(JavaScriptLocation location) {
RDPBreakpoint breakpoint = new RDPBreakpoint(this, location);
breakpoints.add(breakpoint);
if (endpoint != null) {
endpoint.updateBreakpoint(breakpoint);
}
return breakpoint;
}
synchronized void destroyBreakpoint(RDPBreakpoint breakpoint) {
breakpoints.remove(breakpoint);
if (endpoint != null) {
endpoint.destroyBreakpoint(breakpoint);
}
}
void fireResumed() {
for (JavaScriptDebuggerListener listener : listeners) {
listener.resumed();
}
}
void firePaused() {
for (JavaScriptDebuggerListener listener : listeners) {
listener.paused();
}
}
void fireScriptAdded(String script) {
for (JavaScriptDebuggerListener listener : listeners) {
listener.scriptAdded(script);
}
}
void fireBreakpointStatusChanged(RDPBreakpoint breakpoint) {
for (JavaScriptDebuggerListener listener : listeners) {
listener.breakpointChanged(breakpoint);
}
}
}

View File

@ -37,7 +37,7 @@ public class Breakpoint {
return location; return location;
} }
public synchronized void destroy() { public void destroy() {
debugger.destroyBreakpoint(this); debugger.destroyBreakpoint(this);
debugger = null; debugger = null;
} }

View File

@ -79,7 +79,7 @@ public class Debugger {
continueToLocation(location.getFileName(), location.getLine()); continueToLocation(location.getFileName(), location.getLine());
} }
public synchronized void continueToLocation(String fileName, int line) { public void continueToLocation(String fileName, int line) {
if (!javaScriptDebugger.isSuspended()) { if (!javaScriptDebugger.isSuspended()) {
return; return;
} }
@ -105,7 +105,7 @@ public class Debugger {
return createBreakpoint(new SourceLocation(file, line)); return createBreakpoint(new SourceLocation(file, line));
} }
public synchronized Breakpoint createBreakpoint(SourceLocation location) { public Breakpoint createBreakpoint(SourceLocation location) {
Breakpoint breakpoint = new Breakpoint(this, location); Breakpoint breakpoint = new Breakpoint(this, location);
breakpoints.add(breakpoint); breakpoints.add(breakpoint);
updateInternalBreakpoints(breakpoint); updateInternalBreakpoints(breakpoint);
@ -113,7 +113,7 @@ public class Debugger {
return breakpoint; return breakpoint;
} }
public synchronized Set<Breakpoint> getBreakpoints() { public Set<Breakpoint> getBreakpoints() {
return new HashSet<>(breakpoints); return new HashSet<>(breakpoints);
} }
@ -153,7 +153,7 @@ public class Debugger {
} }
} }
public synchronized CallFrame[] getCallStack() { public CallFrame[] getCallStack() {
if (!isSuspended()) { if (!isSuspended()) {
return null; return null;
} }
@ -184,7 +184,7 @@ public class Debugger {
return callStack.clone(); return callStack.clone();
} }
private synchronized void addScript(String name) { private void addScript(String name) {
if (debugInformationMap.containsKey(name)) { if (debugInformationMap.containsKey(name)) {
return; return;
} }
@ -212,7 +212,7 @@ public class Debugger {
return javaScriptDebugger.isAttached(); return javaScriptDebugger.isAttached();
} }
synchronized void destroyBreakpoint(Breakpoint breakpoint) { void destroyBreakpoint(Breakpoint breakpoint) {
for (JavaScriptBreakpoint jsBreakpoint : breakpoint.jsBreakpoints) { for (JavaScriptBreakpoint jsBreakpoint : breakpoint.jsBreakpoints) {
jsBreakpoint.destroy(); jsBreakpoint.destroy();
breakpointMap.remove(jsBreakpoint); breakpointMap.remove(jsBreakpoint);
@ -221,7 +221,7 @@ public class Debugger {
breakpoints.remove(this); breakpoints.remove(this);
} }
private synchronized void fireResumed() { private void fireResumed() {
for (JavaScriptBreakpoint jsBreakpoint : temporaryJsBreakpoints) { for (JavaScriptBreakpoint jsBreakpoint : temporaryJsBreakpoints) {
jsBreakpoint.destroy(); jsBreakpoint.destroy();
} }
@ -231,7 +231,7 @@ public class Debugger {
} }
} }
private synchronized void fireAttached() { private void fireAttached() {
for (Breakpoint breakpoint : breakpoints) { for (Breakpoint breakpoint : breakpoints) {
updateInternalBreakpoints(breakpoint); updateInternalBreakpoints(breakpoint);
updateBreakpointStatus(breakpoint, false); updateBreakpointStatus(breakpoint, false);
@ -241,7 +241,7 @@ public class Debugger {
} }
} }
private synchronized void fireDetached() { private void fireDetached() {
for (Breakpoint breakpoint : breakpoints) { for (Breakpoint breakpoint : breakpoints) {
updateBreakpointStatus(breakpoint, false); updateBreakpointStatus(breakpoint, false);
} }
@ -250,7 +250,7 @@ public class Debugger {
} }
} }
private synchronized void fireBreakpointChanged(JavaScriptBreakpoint jsBreakpoint) { private void fireBreakpointChanged(JavaScriptBreakpoint jsBreakpoint) {
Breakpoint breakpoint = breakpointMap.get(jsBreakpoint); Breakpoint breakpoint = breakpointMap.get(jsBreakpoint);
if (breakpoint != null) { if (breakpoint != null) {
updateBreakpointStatus(breakpoint, true); updateBreakpointStatus(breakpoint, true);

View File

@ -42,7 +42,5 @@ public interface JavaScriptDebugger {
JavaScriptCallFrame[] getCallStack(); JavaScriptCallFrame[] getCallStack();
JavaScriptBreakpoint getCurrentBreakpoint();
JavaScriptBreakpoint createBreakpoint(JavaScriptLocation location); JavaScriptBreakpoint createBreakpoint(JavaScriptLocation location);
} }