Skip to content

Commit

Permalink
Add a new config: 'outputFolder' to support generate file into a cust…
Browse files Browse the repository at this point in the history
…omized folder (#123)
  • Loading branch information
ringcrl authored and jdneo committed Feb 16, 2019
1 parent b15f4f8 commit 1cdca10
Show file tree
Hide file tree
Showing 2 changed files with 54 additions and 10 deletions.
5 changes: 5 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -247,6 +247,11 @@
"leetcode-cn"
],
"description": "Endpoint of the user account."
},
"leetcode.outputFolder": {
"type": "string",
"scope": "application",
"description": "Specify the relative path to save the problem files."
}
}
}
Expand Down
59 changes: 49 additions & 10 deletions src/commands/show.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@
// Licensed under the MIT license.

import * as fse from "fs-extra";
import * as path from "path";
import * as vscode from "vscode";
import { LeetCodeNode } from "../explorer/LeetCodeNode";
import { leetCodeChannel } from "../leetCodeChannel";
import { leetCodeExecutor } from "../leetCodeExecutor";
import { leetCodeManager } from "../leetCodeManager";
import { IProblem, IQuickItemEx, languages, ProblemState } from "../shared";
Expand All @@ -16,15 +18,15 @@ export async function showProblem(node?: LeetCodeNode): Promise<void> {
if (!node) {
return;
}
await showProblemInternal(node.id);
await showProblemInternal(node);
}

export async function searchProblem(): Promise<void> {
if (!leetCodeManager.getUser()) {
promptForSignIn();
return;
}
const choice: IQuickItemEx<string> | undefined = await vscode.window.showQuickPick(
const choice: IQuickItemEx<IProblem> | undefined = await vscode.window.showQuickPick(
parseProblemsToPicks(list.listProblems()),
{
matchOnDetail: true,
Expand All @@ -37,7 +39,7 @@ export async function searchProblem(): Promise<void> {
await showProblemInternal(choice.value);
}

async function showProblemInternal(id: string): Promise<void> {
async function showProblemInternal(node: IProblem): Promise<void> {
try {
const leetCodeConfig: vscode.WorkspaceConfiguration = vscode.workspace.getConfiguration("leetcode");
let defaultLanguage: string | undefined = leetCodeConfig.get<string>("defaultLanguage");
Expand All @@ -49,9 +51,21 @@ async function showProblemInternal(id: string): Promise<void> {
return;
}

const outDir: string = await selectWorkspaceFolder();
let outDir: string = await selectWorkspaceFolder();
let relativePath: string = (leetCodeConfig.get<string>("outputFolder") || "").trim();
const matchResult: RegExpMatchArray | null = relativePath.match(/\$\{(.*?)\}/);
if (matchResult) {
const resolvedPath: string | undefined = await resolveRelativePath(matchResult[1].toLocaleLowerCase(), node, language);
if (!resolvedPath) {
leetCodeChannel.appendLine("Showing problem canceled by user.");
return;
}
relativePath = resolvedPath;
}

outDir = path.join(outDir, relativePath);
await fse.ensureDir(outDir);
const result: string = await leetCodeExecutor.showProblem(id, language, outDir);
const result: string = await leetCodeExecutor.showProblem(node.id, language, outDir);
const reg: RegExp = /\* Source Code:\s*(.*)/;
const match: RegExpMatchArray | null = result.match(reg);
if (match && match.length >= 2) {
Expand All @@ -76,17 +90,17 @@ async function showProblemInternal(id: string): Promise<void> {
}
}
} catch (error) {
await promptForOpenOutputChannel("Failed to fetch the problem information. Please open the output channel for details.", DialogType.error);
await promptForOpenOutputChannel("Failed to show the problem. Please open the output channel for details.", DialogType.error);
}
}

async function parseProblemsToPicks(p: Promise<IProblem[]>): Promise<Array<IQuickItemEx<string>>> {
return new Promise(async (resolve: (res: Array<IQuickItemEx<string>>) => void): Promise<void> => {
const picks: Array<IQuickItemEx<string>> = (await p).map((problem: IProblem) => Object.assign({}, {
async function parseProblemsToPicks(p: Promise<IProblem[]>): Promise<Array<IQuickItemEx<IProblem>>> {
return new Promise(async (resolve: (res: Array<IQuickItemEx<IProblem>>) => void): Promise<void> => {
const picks: Array<IQuickItemEx<IProblem>> = (await p).map((problem: IProblem) => Object.assign({}, {
label: `${parseProblemDecorator(problem.state, problem.locked)}${problem.id}.${problem.name}`,
description: "",
detail: `AC rate: ${problem.passRate}, Difficulty: ${problem.difficulty}`,
value: problem.id,
value: problem,
}));
resolve(picks);
});
Expand All @@ -102,3 +116,28 @@ function parseProblemDecorator(state: ProblemState, locked: boolean): string {
return locked ? "$(lock) " : "";
}
}

async function resolveRelativePath(value: string, node: IProblem, selectedLanguage: string): Promise<string | undefined> {
switch (value) {
case "tag":
if (node.tags.length === 1) {
return node.tags[0];
}
return await vscode.window.showQuickPick(
node.tags,
{
matchOnDetail: true,
placeHolder: "Multiple tags available, please select one",
ignoreFocusOut: true,
},
);
case "language":
return selectedLanguage;
case "difficulty":
return node.difficulty;
default:
const errorMsg: string = `The config '${value}' is not supported.`;
leetCodeChannel.appendLine(errorMsg);
throw new Error(errorMsg);
}
}

0 comments on commit 1cdca10

Please sign in to comment.