Skip to content
This repository has been archived by the owner on Jul 3, 2019. It is now read-only.

Commit

Permalink
refactoring
Browse files Browse the repository at this point in the history
- separate file for localSource
- new type for local source paths
  • Loading branch information
tineheller committed Feb 22, 2019
1 parent 04afb24 commit 537a32b
Show file tree
Hide file tree
Showing 8 changed files with 167 additions and 130 deletions.
7 changes: 2 additions & 5 deletions src/config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,10 @@ import { LogConfiguration } from 'node-file-log';
import { isAbsolute, join } from 'path';
import * as vscode from 'vscode';
import { DebugProtocol } from 'vscode-debugprotocol';
import { LocalSourcesPattern } from './localSource';
import { getVersion } from './version';


export interface LocalSources {
include: string;
exclude: string;
}

export interface CommonArguments {
/** The debugger port to attach to. */
Expand All @@ -20,7 +17,7 @@ export interface CommonArguments {
log: LogConfiguration;
/** Time in ms until we give up trying to connect. */
timeout: number;
localSources: LocalSources;
localSources: LocalSourcesPattern;
/** Required for IPC communication. */
processId: number;
workspace: string;
Expand Down
28 changes: 13 additions & 15 deletions src/debugSession.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,9 @@ import { DebugConnection } from './connection';
import { Context, ContextId } from './context';
import { FrameMap } from './frameMap';
import { DebugAdapterIPC } from './ipcClient';
import { LocalPaths, LocalSource } from './localSource';
import { Breakpoint, Command, Response, StackFrame, Variable, variableValueToString } from './protocol';
import { LocalSource, ServerSource, SourceMap } from './sourceMap';
import { ServerSource, SourceMap } from './sourceMap';
import { VariablesContainer, VariablesMap } from './variablesMap';

const log = Logger.create('JanusDebugSession');
Expand Down Expand Up @@ -98,10 +99,10 @@ export class JanusDebugSession extends DebugSession {
supportsGotoTargetsRequest: false,
supportsHitConditionalBreakpoints: false,
supportsRestartFrame: false,
supportsRunInTerminalRequest: false,
supportsSetVariable: false,
supportsStepBack: false,
supportsStepInTargetsRequest: false,
supportsDelayedStackTraceLoading: false
};
response.body = body;
this.sendResponse(response);
Expand Down Expand Up @@ -168,8 +169,6 @@ export class JanusDebugSession extends DebugSession {
const principal: string = args.principal || '';
const password = args.password.length > 0 ? crypt_md5(args.password, 'o3') : '';
const stopOnEntry = args.stopOnEntry;
const include = args.localSources ? args.localSources.include : undefined;
const exclude = args.localSources ? args.localSources.exclude : undefined;

let scriptIdentifier: string | undefined;

Expand All @@ -183,10 +182,10 @@ export class JanusDebugSession extends DebugSession {

const source = new LocalSource(args.script);

let uris: string[] | undefined;
let uris: LocalPaths[] | undefined;
try {
await this.ipcClient.connect(args.processId);
uris = await this.ipcClient.findURIsInWorkspace(include, exclude);
uris = await this.ipcClient.findURIsInWorkspace(args.localSources);
// log.debug(`found ${JSON.stringify(uris)} URIs in workspace`);
this.sourceMap.setLocalUrls(uris);
} catch (e) {
Expand Down Expand Up @@ -437,15 +436,12 @@ export class JanusDebugSession extends DebugSession {
this.terminateOnDisconnect = args.terminateOnDisconnect;
this.breakOnAttach = args.breakOnAttach;

const include = args.localSources ? args.localSources.include : undefined;
const exclude = args.localSources ? args.localSources.exclude : undefined;

log.debug(`my workspace: ${args.workspace}`);

let uris: string[] | undefined;
let uris: LocalPaths[] | undefined;
try {
await this.ipcClient.connect(args.processId);
uris = await this.ipcClient.findURIsInWorkspace(include, exclude);
uris = await this.ipcClient.findURIsInWorkspace(args.localSources);
// log.debug(`found ${JSON.stringify(uris)} URIs in workspace`);
this.sourceMap.setLocalUrls(uris);
} catch (e) {
Expand Down Expand Up @@ -772,10 +768,10 @@ export class JanusDebugSession extends DebugSession {
if (this.sourceMap.serverSource.hiddenStatement) {
// if the server source contains the internal "debugger;" statement, execute single step,
// stopped event will be sent after script has been stopped
log.debug(`'debugger;' statement -> sending 'next' to remote`);
log.debug(`preceding 'debugger;' statement -> sending 'next' to remote`);
await this.connection.sendRequest(new Command('next', this.attachedContextId));
} else {
log.info("no 'debugger;' statement -> check attached context");
log.info("no preceding 'debugger;' statement -> check if context is paused");
if (this.connection.coordinator.getContext(this.attachedContextId).isStopped()) {
this.reportStopped('pause', this.attachedContextId);
}
Expand Down Expand Up @@ -1035,6 +1031,9 @@ export class JanusDebugSession extends DebugSession {
protected stackTraceRequest(response: DebugProtocol.StackTraceResponse, args: DebugProtocol.StackTraceArguments): void {
log.info(`stackTraceRequest`);

// await new Promise(resolve => setTimeout(resolve, 3000));


if (this.connection === undefined) {
throw new Error('No connection');
}
Expand Down Expand Up @@ -1074,7 +1073,6 @@ export class JanusDebugSession extends DebugSession {
throw new Error('No connection');
}

// this default result is actually not used
const result: DebugProtocol.StackFrame = {
column: 0,
id: frame.frameId,
Expand Down Expand Up @@ -1147,7 +1145,7 @@ export class JanusDebugSession extends DebugSession {
// return the created stackframes to vscode
response.body = {
stackFrames: result,
totalFrames: trace.length,
// totalFrames: trace.length,
};
// log.debug(`stackTraceRequest succeeded response.body: ${JSON.stringify(response.body)}`);
response.success = true;
Expand Down
7 changes: 4 additions & 3 deletions src/ipcClient.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import ipc = require('node-ipc');
import { Logger } from 'node-file-log';
import { timeout } from 'promised-timeout';
import { LocalPaths, LocalSourcesPattern } from './localSource';

ipc.config.appspace = 'vscode-janus-debug.';
ipc.config.id = 'debug_adapter';
Expand Down Expand Up @@ -50,11 +51,11 @@ export class DebugAdapterIPC {
}

public async showContextQuickPick(contextList: string[]): Promise<string> {
return this.ipcRequest<string>('showContextQuickPick', 'contextChosen', this.contextChosenDefault, (2 * 60 * 1000), contextList);
return await this.ipcRequest<string>('showContextQuickPick', 'contextChosen', this.contextChosenDefault, (2 * 60 * 1000), contextList);
}

public async findURIsInWorkspace(include?: string, exclude?: string): Promise<string[]> {
return this.ipcRequest<string[]>('findURIsInWorkspace', 'urisFound', this.urisFoundDefault, (5 * 60 * 1000), {include, exclude});
public async findURIsInWorkspace(sourcePattern: LocalSourcesPattern): Promise<LocalPaths[]> {
return await this.ipcRequest<LocalPaths[]>('findURIsInWorkspace', 'urisFound', this.urisFoundDefault, (5 * 60 * 1000), sourcePattern);
}

public async displaySourceNotice(message: string): Promise<void> {
Expand Down
66 changes: 39 additions & 27 deletions src/ipcServer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import * as fs from 'fs';
import ipc = require('node-ipc');
import * as path from 'path';
import { window, workspace } from 'vscode';
import { LocalPaths, LocalSourcesPattern } from './localSource';

// We use a UNIX Domain or Windows socket, respectively, for having a
// communication channel from the debug adapter process back to the extension.
Expand Down Expand Up @@ -63,7 +64,7 @@ export class VSCodeExtensionIPC {
// check for scripts with same name
// const multiNames = contextList.filter((value, index, self) => (self.indexOf(value) !== index));

const picked: string | undefined = await window.showQuickPick(contextList);
const picked: string | undefined = await window.showQuickPick(contextList, {ignoreFocusOut: true});

// send answer in any case because server is waiting
ipc.server.emit(socket, 'contextChosen', picked);
Expand All @@ -77,53 +78,64 @@ export class VSCodeExtensionIPC {
* workspace, the user can choose the correct script, or they can choose to
* simply ignore all scripts with names.
*/
ipc.server.on('findURIsInWorkspace', async (globPaterns: {include?: string, exclude?: string}, socket) => {
ipc.server.on('findURIsInWorkspace', async (globPaterns: LocalSourcesPattern, socket) => {
console.log('findURIsInWorkspace');

const include = globPaterns.include ? globPaterns.include : '**/*.js';
const exclude = globPaterns.exclude ? globPaterns.exclude : '**/node_modules/**';
const uris = await workspace.findFiles(include, exclude);

// if multiple scripts with same name, user has to select
const uriPaths: string[] = [];
// if multiple scripts with same name, collect all paths
const uriPaths: LocalPaths[] = [];
const uriNames: string[] = [];
const ignored: string[] = [];

let ignoreDuplicates = false;
// tslint:disable-next-line:prefer-for-of
for (let i = 0; i < uris.length; i++) {
const currentPath = uris[i].fsPath;
const currentName = path.basename(currentPath);
const duplIndex = uriNames.indexOf(currentName);
if (duplIndex >= 0) {
const duplicate = uriPaths.find((fspaths) => {
if (fspaths.name === currentName) {
return true;
}
return false;
});
if (duplicate) {
// duplicate script found
let selected: string | undefined = "";
if (!ignoreDuplicates) {
const message = `Multiple scripts with name '${currentName}', please select one`;
const ingoreMsg = "Ignore all scripts with same name";
const prevPath = uriPaths[duplIndex];
selected = await window.showQuickPick([prevPath, currentPath, ingoreMsg], {ignoreFocusOut: true, placeHolder: message});
if (selected === ingoreMsg || selected === undefined) {
ignoreDuplicates = true;
selected = "";
}
}

// check again! ignoreDuplicates could have been changed
if (ignoreDuplicates) {
ignored.push(currentName);
if (duplicate.path) {
duplicate.paths.push(duplicate.path);
duplicate.path = undefined;
}
duplicate.paths.push(currentPath);
} else {
if (duplicate.path) {
const msgSameName = `Multiple scripts with name '${currentName}', please select one`;
const msgIgnoreSameNames = "Ignore all scripts with same name";
selected = await window.showQuickPick([duplicate.path, currentPath, msgIgnoreSameNames], {ignoreFocusOut: true, placeHolder: msgSameName});
if (selected === msgIgnoreSameNames || selected === undefined) {
ignoreDuplicates = true;
duplicate.paths.push(duplicate.path);
duplicate.path = undefined;
duplicate.paths.push(currentPath);
} else if (selected === duplicate.path) {
// duplicate.path = prevPath; // already set
duplicate.paths.push(currentPath);
} else if (selected === currentPath) {
duplicate.path = currentPath;
duplicate.paths.push(duplicate.path);
}
} else {
duplicate.path = currentPath;
}
}
uriPaths[duplIndex] = selected;
// uriNames[prevIndex] already set
} else {
uriPaths.push(currentPath);
uriPaths.push({name: currentName, path: currentPath, paths: []});
uriNames.push(currentName);
}
}

if (ignored.length > 0) {
window.showInformationMessage(`The following scripts will be ignored and cannot be debugged\n ${JSON.stringify(ignored)}`);
}

ipc.server.emit(socket, 'urisFound', uriPaths);
});

Expand Down
84 changes: 84 additions & 0 deletions src/localSource.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
import * as fs from 'fs';
import { Logger } from 'node-file-log';
import { parse } from 'path';



export interface LocalPaths {
name: string;
path: string | undefined;
paths: string[];
}

export interface LocalSourcesPattern {
include: string;
exclude: string;
}


const localSourceLog = Logger.create('SourceMap');


/**
* A local source file.
*/
export class LocalSource {
/** The name of this source. Usually a file name. */
public readonly name: string;
/** The local absolute path to this source. */
public path: string;
public paths?: string[];
/** An array of possible alias names. */
public aliasNames: string[];
/** An artificial key that iff > 0 is used by VS Code to retrieve the source through the SourceRequest. */
public sourceReference: number;

constructor(path: string, paths?: string[]) {
const parsedPath = parse(path);
this.path = path;
this.name = parsedPath.base;
this.aliasNames = [
parsedPath.name,
parsedPath.base
];
this.sourceReference = 0;
if (paths && paths.length > 0) {
this.paths = paths;
localSourceLog.info(`Additional paths found ${JSON.stringify(this.paths)}`);
}
}

public loadFromDisk(): string {
return fs.readFileSync(this.path, 'utf8');
}

public getSourceLine(lineNo: number): string {
const fileContents = this.loadFromDisk();
const lines = fileContents.split("\n");
const ret = lines[lineNo - 1];
if (ret === undefined) {
throw new Error(`Line ${lineNo} does not exist in ${this.name}`);
}
return ret.trim();
}

public leadingDebuggerStmts(): number {
let counter = 0;
const fileContents = this.loadFromDisk();
const lines = fileContents.split("\n");
// tslint:disable-next-line:prefer-for-of
for (let i = 0; i < lines.length; i++) {
if (lines[i].trim().startsWith("debugger;")) {
counter++;
} else {
break;
}
}
return counter;
}

public sourceName(): string {
return parse(this.path).name;
}
}

Loading

0 comments on commit 537a32b

Please sign in to comment.