mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-01-05 01:50:56 +07:00
added handling of absent remote files in python remote debug
This commit is contained in:
@@ -25,6 +25,7 @@ from pydevd_comm import CMD_CHANGE_VARIABLE, \
|
||||
CMD_CONSOLE_EXEC, \
|
||||
CMD_ADD_EXCEPTION_BREAK, \
|
||||
CMD_REMOVE_EXCEPTION_BREAK, \
|
||||
CMD_LOAD_SOURCE, \
|
||||
GetGlobalDebugger, \
|
||||
InternalChangeVariable, \
|
||||
InternalGetCompletions, \
|
||||
@@ -633,6 +634,17 @@ class PyDB:
|
||||
always_exception_set.remove(exc_type)
|
||||
update_exception_hook()
|
||||
|
||||
elif cmd_id == CMD_LOAD_SOURCE:
|
||||
path = text
|
||||
try:
|
||||
print path
|
||||
f = open(path, 'r')
|
||||
source = f.read()
|
||||
print source
|
||||
self.cmdFactory.makeLoadSourceMessage(seq, source, self)
|
||||
except:
|
||||
return self.cmdFactory.makeErrorMessage(seq, GetExceptionTracebackStr())
|
||||
|
||||
else:
|
||||
#I have no idea what this is all about
|
||||
cmd = self.cmdFactory.makeErrorMessage(seq, "unexpected command " + str(cmd_id))
|
||||
|
||||
@@ -103,7 +103,8 @@ CMD_RELOAD_CODE = 119
|
||||
CMD_GET_COMPLETIONS = 120
|
||||
CMD_CONSOLE_EXEC = 121
|
||||
CMD_ADD_EXCEPTION_BREAK = 122
|
||||
CMD_REMOVE_EXCEPTION_BREAK = 122
|
||||
CMD_REMOVE_EXCEPTION_BREAK = 123
|
||||
CMD_LOAD_SOURCE = 124
|
||||
CMD_VERSION = 501
|
||||
CMD_RETURN = 502
|
||||
CMD_ERROR = 901
|
||||
@@ -545,6 +546,14 @@ class NetCommandFactory:
|
||||
except Exception:
|
||||
return self.makeErrorMessage(seq, GetExceptionTracebackStr())
|
||||
|
||||
def makeLoadSourceMessage(self, seq, source, dbg=None):
|
||||
try:
|
||||
net = NetCommand(str(CMD_LOAD_SOURCE), seq, '%s' % source)
|
||||
if dbg:
|
||||
dbg.writer.addCommand(net)
|
||||
except:
|
||||
return self.makeErrorMessage(0, GetExceptionTracebackStr())
|
||||
|
||||
INTERNAL_TERMINATE_THREAD = 1
|
||||
INTERNAL_SUSPEND_THREAD = 2
|
||||
|
||||
|
||||
@@ -2,7 +2,6 @@ package com.jetbrains.python.debugger.pydev;
|
||||
|
||||
import com.jetbrains.python.debugger.PyDebuggerException;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
|
||||
public abstract class AbstractCommand {
|
||||
@@ -27,6 +26,7 @@ public abstract class AbstractCommand {
|
||||
public static final int CONSOLE_EXEC = 121;
|
||||
public static final int ADD_EXCEPTION_BREAKPOINT = 122;
|
||||
public static final int REMOVE_EXCEPTION_BREAKPOINT = 123;
|
||||
public static final int LOAD_SOURCE = 124;
|
||||
public static final int VERSION = 501;
|
||||
public static final String NEW_LINE_CHAR = "@_@NEW_LINE_CHAR@_@";
|
||||
public static final String TAB_CHAR = "@_@TAB_CHAR@_@";
|
||||
@@ -39,7 +39,7 @@ public abstract class AbstractCommand {
|
||||
myCommandCode = commandCode;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@NotNull
|
||||
public final String getPayload() {
|
||||
Payload payload = new Payload();
|
||||
buildPayload(payload);
|
||||
@@ -52,7 +52,6 @@ public abstract class AbstractCommand {
|
||||
return false;
|
||||
}
|
||||
|
||||
// todo: pass debugger to constructor(?)
|
||||
public void execute() throws PyDebuggerException {
|
||||
int sequence = myDebugger.getNextSequence();
|
||||
if (isResponseExpected()) {
|
||||
|
||||
@@ -0,0 +1,39 @@
|
||||
package com.jetbrains.python.debugger.pydev;
|
||||
|
||||
import com.jetbrains.python.debugger.PyDebuggerException;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
/**
|
||||
* @author traff
|
||||
*/
|
||||
public class LoadSourceCommand extends AbstractCommand {
|
||||
private final String myPath;
|
||||
|
||||
private String myContent = null;
|
||||
|
||||
protected LoadSourceCommand(@NotNull final RemoteDebugger debugger, String path) {
|
||||
super(debugger, LOAD_SOURCE);
|
||||
myPath = path;
|
||||
}
|
||||
|
||||
public boolean isResponseExpected() {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void processResponse(final ProtocolFrame response) throws PyDebuggerException {
|
||||
super.processResponse(response);
|
||||
myContent = ProtocolParser.parseSourceContent(response.getPayload());
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void buildPayload(Payload payload) {
|
||||
payload.add(myPath);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public String getContent() {
|
||||
return myContent;
|
||||
}
|
||||
}
|
||||
@@ -17,6 +17,10 @@ public class ProtocolParser {
|
||||
private ProtocolParser() {
|
||||
}
|
||||
|
||||
public static String parseSourceContent(String payload) throws PyDebuggerException {
|
||||
return payload;
|
||||
}
|
||||
|
||||
public static String decode(final String value) throws PyDebuggerException {
|
||||
try {
|
||||
return URLDecoder.decode(value, "UTF-8");
|
||||
|
||||
@@ -150,6 +150,18 @@ public class RemoteDebugger {
|
||||
return command.getNewValue();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public String loadSource(String path) {
|
||||
LoadSourceCommand command = new LoadSourceCommand(this, path);
|
||||
try {
|
||||
command.execute();
|
||||
return command.getContent();
|
||||
}
|
||||
catch (PyDebuggerException e) {
|
||||
return "print 1";
|
||||
}
|
||||
}
|
||||
|
||||
private static String composeName(final PyDebugValue var) {
|
||||
final StringBuilder sb = new StringBuilder(var.getTempName());
|
||||
PyDebugValue p = var;
|
||||
@@ -472,7 +484,7 @@ public class RemoteDebugger {
|
||||
}
|
||||
|
||||
private void fireCloseEvent() {
|
||||
for (RemoteDebuggerCloseListener listener: myCloseListeners) {
|
||||
for (RemoteDebuggerCloseListener listener : myCloseListeners) {
|
||||
listener.closed();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -88,6 +88,7 @@
|
||||
<highlightUsagesHandlerFactory implementation="com.jetbrains.python.codeInsight.highlighting.PyHighlightExitPointsHandlerFactory"/>
|
||||
|
||||
<configurationType implementation="com.jetbrains.python.run.remote.PyRemoteDebugConfigurationType"/>
|
||||
<fileEditorProvider implementation="com.jetbrains.python.debugger.remote.PyRemoteDebugEditorProvider"/>
|
||||
|
||||
<intentionAction>
|
||||
<className>com.jetbrains.python.codeInsight.intentions.ImportToImportFromIntention</className>
|
||||
|
||||
@@ -519,7 +519,7 @@ run.configuration.type.description=Starts server for remote debug
|
||||
|
||||
remote.debug.info=Info
|
||||
remote.debug.server.hint=Run this remote debug configuration to start debug server.
|
||||
remote.debug.server.hint2=Then copy \\helpers\\pydev package from your PyCharm distribution to location of your python script.
|
||||
remote.debug.server.hint2=Add pycharm-debug.egg from PyCharm distribution to python path of your script.
|
||||
remote.debug.server.hint3=Use the following command in your script to connect to debug server:
|
||||
remote.debug.settings=Settings
|
||||
remote.debug.remote.host=Remote host
|
||||
@@ -527,3 +527,5 @@ remote.debug.port=Port
|
||||
remote.debug.remote.root.folder=Remote root folder
|
||||
remote.debug.local.root.folder=Local root folder
|
||||
remote.debug.server.hint4=If you want to enable stdout and stderr redirection to PyCharm console, use following command in your script:
|
||||
remote.debug.local.host=Local host name
|
||||
remote.debug.redirect.output=Redirect output to console
|
||||
|
||||
@@ -41,8 +41,6 @@ import static javax.swing.SwingUtilities.invokeLater;
|
||||
// todo: pydevd supports module reloading - look for a way to use the feature
|
||||
// todo: smart step into
|
||||
public class PyDebugProcess extends XDebugProcess implements IPyDebugProcess, ProcessListener {
|
||||
|
||||
private final PyPositionConverter myPositionConverter;
|
||||
private final RemoteDebugger myDebugger;
|
||||
private final XBreakpointHandler[] myBreakpointHandlers;
|
||||
private final PyDebuggerEditorsProvider myEditorsProvider;
|
||||
@@ -58,18 +56,12 @@ public class PyDebugProcess extends XDebugProcess implements IPyDebugProcess, Pr
|
||||
|
||||
private boolean myClosing = false;
|
||||
|
||||
public PyDebugProcess(@NotNull XDebugSession session,
|
||||
@NotNull final ServerSocket serverSocket,
|
||||
@NotNull final ExecutionConsole executionConsole,
|
||||
@Nullable final ProcessHandler processHandler) {
|
||||
this(session, serverSocket, executionConsole, processHandler, new PyLocalPositionConverter());
|
||||
}
|
||||
|
||||
private PyPositionConverter myPositionConverter;
|
||||
|
||||
public PyDebugProcess(final @NotNull XDebugSession session,
|
||||
@NotNull final ServerSocket serverSocket,
|
||||
@NotNull final ExecutionConsole executionConsole,
|
||||
@Nullable final ProcessHandler processHandler, @NotNull PyPositionConverter positionConverter) {
|
||||
@Nullable final ProcessHandler processHandler) {
|
||||
super(session);
|
||||
session.setPauseActionSupported(true);
|
||||
myDebugger = new RemoteDebugger(this, serverSocket, 10);
|
||||
@@ -80,7 +72,7 @@ public class PyDebugProcess extends XDebugProcess implements IPyDebugProcess, Pr
|
||||
if (myProcessHandler != null) {
|
||||
myProcessHandler.addProcessListener(this);
|
||||
}
|
||||
myPositionConverter = positionConverter;
|
||||
myPositionConverter = new PyLocalPositionConverter();
|
||||
myDebugger.addCloseListener(new RemoteDebuggerCloseListener() {
|
||||
@Override
|
||||
public void closed() {
|
||||
@@ -89,6 +81,11 @@ public class PyDebugProcess extends XDebugProcess implements IPyDebugProcess, Pr
|
||||
});
|
||||
}
|
||||
|
||||
public void setPositionConverter(PyPositionConverter positionConverter) {
|
||||
myPositionConverter = positionConverter;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public PyPositionConverter getPositionConverter() {
|
||||
return myPositionConverter;
|
||||
@@ -272,6 +269,11 @@ public class PyDebugProcess extends XDebugProcess implements IPyDebugProcess, Pr
|
||||
myNewVariableValue.put(frame.getThreadFrameId(), newValue);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public String loadSource(String path) {
|
||||
return myDebugger.loadSource(path);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isVariable(String name) {
|
||||
final Project project = getSession().getProject();
|
||||
@@ -411,4 +413,8 @@ public class PyDebugProcess extends XDebugProcess implements IPyDebugProcess, Pr
|
||||
@Override
|
||||
public void onTextAvailable(ProcessEvent event, Key outputType) {
|
||||
}
|
||||
|
||||
public PyStackFrame createStackFrame(PyStackFrameInfo frameInfo) {
|
||||
return new PyStackFrame(this, frameInfo);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -53,7 +53,7 @@ public class PyExecutionStack extends XExecutionStack {
|
||||
}
|
||||
|
||||
private static PyStackFrame convert(final PyDebugProcess debugProcess, final PyStackFrameInfo frameInfo) {
|
||||
return new PyStackFrame(debugProcess, frameInfo);
|
||||
return debugProcess.createStackFrame(frameInfo);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -11,7 +11,7 @@ import org.jetbrains.annotations.Nullable;
|
||||
public class PyLocalPositionConverter implements PyPositionConverter {
|
||||
|
||||
protected static class PyLocalSourcePosition extends PySourcePosition {
|
||||
PyLocalSourcePosition(final String file, final int line) {
|
||||
public PyLocalSourcePosition(final String file, final int line) {
|
||||
super(file, line);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,40 +0,0 @@
|
||||
package com.jetbrains.python.debugger;
|
||||
|
||||
import com.intellij.openapi.util.io.FileUtil;
|
||||
import com.intellij.openapi.vfs.LocalFileSystem;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.xdebugger.XSourcePosition;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
/**
|
||||
* @author traff
|
||||
*/
|
||||
public class PyRemotePositionConverter extends PyLocalPositionConverter {
|
||||
private final String myLocalRoot;
|
||||
private final String myRemoteRoot;
|
||||
|
||||
public PyRemotePositionConverter(final String localRoot, final String remoteRoot) {
|
||||
myLocalRoot = FileUtil.toSystemIndependentName(localRoot);
|
||||
myRemoteRoot = FileUtil.toSystemIndependentName(remoteRoot);
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public PySourcePosition convert(@NotNull XSourcePosition position) {
|
||||
String path = FileUtil.toSystemIndependentName(position.getFile().getPath());
|
||||
if (myLocalRoot.length() > 0) {
|
||||
path = path.replace(myLocalRoot, myRemoteRoot);
|
||||
}
|
||||
return new PyLocalSourcePosition(path, position.getLine() + 1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public XSourcePosition convert(@NotNull PySourcePosition position) {
|
||||
String path = FileUtil.toSystemIndependentName(position.getFile());
|
||||
if (myRemoteRoot.length() > 0) {
|
||||
path = path.replace(myRemoteRoot, myLocalRoot);
|
||||
}
|
||||
final VirtualFile file = LocalFileSystem.getInstance().findFileByPath(path);
|
||||
return createXSourcePosition(file, position.getLine());
|
||||
}
|
||||
}
|
||||
@@ -110,4 +110,8 @@ public class PyStackFrame extends XStackFrame {
|
||||
return myFrameInfo.getThreadId() + ":" + myFrameInfo.getId();
|
||||
}
|
||||
|
||||
protected XSourcePosition getPosition() {
|
||||
return myPosition;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -707,7 +707,7 @@ public class PythonSdkType extends SdkType {
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static Sdk findPythonSdk(Module module) {
|
||||
public static Sdk findPythonSdk(@Nullable Module module) {
|
||||
if (module == null) return null;
|
||||
final Sdk sdk = ModuleRootManager.getInstance(module).getSdk();
|
||||
if (sdk != null && sdk.getSdkType() instanceof PythonSdkType) return sdk;
|
||||
|
||||
Reference in New Issue
Block a user