package com.jetbrains.python.debugger.pydev; import com.intellij.openapi.diagnostic.Logger; import java.io.File; import java.io.UnsupportedEncodingException; import java.net.URLDecoder; import java.net.URLEncoder; /** * Run a custom bit of Python in the context of the specified debug target. * <p> * This command takes a variable or expression (expressed as an {@link PyVariableLocator#getPyDBLocation()} style * location) and passes it to the function provided in the constructor. The constructor also takes either a code * snippet that should define the function, or a file to execfile that should define the function. * <p> * Once created, the command should be posted to the target with {@link AbstractDebugTarget#postCommand(AbstractDebuggerCommand)}. * Optionally, the function run on the target can return a string for further processing. In this case the command's * {@link #setCompletionListener(ICommandResponseListener)} should be set and on completion, {@link #getResponsePayload()} * can be used to obtain the returned value. * <p> * For an example, see {@link PrettyPrintCommandHandler} */ public class RunCustomOperationCommand<T> extends AbstractCommand<T> { private static final Logger LOG = Logger.getInstance(RunCustomOperationCommand.class); private String myEncodedCodeOrFile; private String myOperationFnName; private PyVariableLocator myLocator; private String myStyle; private RunCustomOperationCommand(RemoteDebugger target, PyVariableLocator locator, String style, String codeOrFile, String operationFnName) { super(target, CMD_RUN_CUSTOM_OPERATION); this.myLocator = locator; this.myStyle = style; this.myEncodedCodeOrFile = encode(codeOrFile); this.myOperationFnName = operationFnName; } /** * Create a new command to run with the function defined in a string. * * @param target Debug Target to run on * @param locator Location of variable or expression. * @param operationSource Definition of the function to be run (this code is "exec"ed by the target) * @param operationFnName Function to call, must be defined by operationSource */ public RunCustomOperationCommand(RemoteDebugger target, PyVariableLocator locator, String operationSource, String operationFnName) { this(target, locator, "EXEC", operationSource, operationFnName); } @Override protected void buildPayload(Payload payload) { payload.add(myLocator.getPyDBLocation() + "||" + myStyle).add(myEncodedCodeOrFile).add(myOperationFnName); } @Override public boolean isResponseExpected() { return true; } private static String encode(String in) { try { return URLEncoder.encode(in, "UTF-8"); } catch (UnsupportedEncodingException e) { LOG.error("Unreachable? UTF-8 is always supported.", e); return ""; } } protected static String decode(String in) { try { return URLDecoder.decode(in, "UTF-8"); } catch (UnsupportedEncodingException e) { LOG.error("Unreachable? UTF-8 is always supported.", e); return ""; } } }