Skip to content

Commit 94c2076

Browse files
authored
support leetcode cn (LeetCode-OpenSource#57)
1 parent 45bd545 commit 94c2076

File tree

9 files changed

+117
-11
lines changed

9 files changed

+117
-11
lines changed

package-lock.json

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 30 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
],
2626
"preview": true,
2727
"activationEvents": [
28+
"onCommand:leetcode.toogleLeetCodeCn",
2829
"onCommand:leetcode.signin",
2930
"onCommand:leetcode.signout",
3031
"onCommand:leetcode.selectSessions",
@@ -39,6 +40,12 @@
3940
"main": "./out/src/extension",
4041
"contributes": {
4142
"commands": [
43+
{
44+
"command": "leetcode.toogleLeetCodeCn",
45+
"title": "Switch endpoint",
46+
"category": "LeetCode",
47+
"icon": "resources/cn.png"
48+
},
4249
{
4350
"command": "leetcode.signin",
4451
"title": "Sign in",
@@ -114,19 +121,24 @@
114121
"menus": {
115122
"view/title": [
116123
{
117-
"command": "leetcode.signin",
124+
"command": "leetcode.toogleLeetCodeCn",
118125
"when": "view == leetCodeExplorer",
119126
"group": "navigation@0"
120127
},
121128
{
122-
"command": "leetcode.searchProblem",
129+
"command": "leetcode.signin",
123130
"when": "view == leetCodeExplorer",
124131
"group": "navigation@1"
125132
},
126133
{
127-
"command": "leetcode.refreshExplorer",
134+
"command": "leetcode.searchProblem",
128135
"when": "view == leetCodeExplorer",
129136
"group": "navigation@2"
137+
},
138+
{
139+
"command": "leetcode.refreshExplorer",
140+
"when": "view == leetCodeExplorer",
141+
"group": "navigation@3"
130142
}
131143
],
132144
"view/item/context": [
@@ -172,7 +184,7 @@
172184
"leetcode.showLocked": {
173185
"type": "boolean",
174186
"default": false,
175-
"scope": "window",
187+
"scope": "application",
176188
"description": "Show locked problems."
177189
},
178190
"leetcode.defaultLanguage": {
@@ -193,20 +205,30 @@
193205
"scala",
194206
"swift"
195207
],
196-
"scope": "window",
208+
"scope": "application",
197209
"description": "Default language for solving the problems."
198210
},
199211
"leetcode.showSetDefaultLanguageHint": {
200212
"type": "boolean",
201213
"default": true,
202-
"scope": "window",
214+
"scope": "application",
203215
"description": "Show a hint to set the default language."
204216
},
205217
"leetcode.useWsl": {
206218
"type": "boolean",
207219
"default": false,
208-
"scope": "window",
220+
"scope": "application",
209221
"description": "Use Node.js inside the Windows Subsystem for Linux."
222+
},
223+
"leetcode.endpoint": {
224+
"type": "string",
225+
"default": "leetcode",
226+
"scope": "application",
227+
"enum": [
228+
"leetcode",
229+
"leetcode-cn"
230+
],
231+
"description": "Endpoint of the user account."
210232
}
211233
}
212234
}
@@ -216,7 +238,7 @@
216238
"vscode:prepublish": "npm run compile",
217239
"compile": "tsc -p ./",
218240
"watch": "tsc -watch -p ./",
219-
"postinstall": "node ./node_modules/vscode/bin/install",
241+
"postinstall": "node ./node_modules/vscode/bin/install && node ./node_modules/leetcode-cli/bin/leetcode plugin -i leetcode.cn",
220242
"test": "npm run compile && node ./node_modules/vscode/bin/test",
221243
"lint": "tslint --project tsconfig.json -e src/*.d.ts -t verbose"
222244
},

resources/cn.png

4.8 KB
Loading

src/commands/plugin.ts

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
"use strict";
2+
3+
import * as vscode from "vscode";
4+
import { leetCodeExecutor } from "../leetCodeExecutor";
5+
import { IQuickItemEx } from "../shared";
6+
import { Endpoint } from "../shared";
7+
import { DialogType, promptForOpenOutputChannel, promptForSignIn } from "../utils/uiUtils";
8+
9+
export async function toogleLeetCodeCn(): Promise<void> {
10+
const isCnEnbaled: boolean = isLeetCodeCnEnabled();
11+
const picks: Array<IQuickItemEx<string>> = [];
12+
picks.push(
13+
{
14+
label: `${isCnEnbaled ? "$(check) " : ""}On`,
15+
description: "",
16+
detail: `Enable ${Endpoint.LeetCodeCN}.`,
17+
value: "on",
18+
},
19+
{
20+
label: `${isCnEnbaled ? "" : "$(check) "}Off`,
21+
description: "",
22+
detail: `Disable ${Endpoint.LeetCodeCN}.`,
23+
value: "off",
24+
},
25+
);
26+
const choice: IQuickItemEx<string> | undefined = await vscode.window.showQuickPick(picks);
27+
if (!choice) {
28+
return;
29+
}
30+
const leetCodeConfig: vscode.WorkspaceConfiguration = vscode.workspace.getConfiguration("leetcode");
31+
try {
32+
const enabled: boolean = choice.value === "on";
33+
const endpoint: string = enabled ? Endpoint.LeetCodeCN : Endpoint.LeetCode;
34+
await leetCodeExecutor.toggleLeetCodeCn(enabled);
35+
await leetCodeConfig.update("endpoint", endpoint, true /* UserSetting */);
36+
vscode.window.showInformationMessage(`Switched the endpoint to ${endpoint}`);
37+
} catch (error) {
38+
await promptForOpenOutputChannel("Failed to switch endpoint. Please open the output channel for details.", DialogType.error);
39+
}
40+
41+
try {
42+
await vscode.commands.executeCommand("leetcode.signout");
43+
await promptForSignIn();
44+
} catch (error) {
45+
await promptForOpenOutputChannel("Failed to sign in. Please open the output channel for details.", DialogType.error);
46+
}
47+
}
48+
49+
export async function initializeEndpoint(): Promise<void> {
50+
await leetCodeExecutor.toggleLeetCodeCn(isLeetCodeCnEnabled());
51+
}
52+
53+
export function isLeetCodeCnEnabled(): boolean {
54+
const leetCodeConfig: vscode.WorkspaceConfiguration = vscode.workspace.getConfiguration("leetcode");
55+
const endpoint: string | undefined = leetCodeConfig.get<string>("endpoint");
56+
if (endpoint && endpoint === Endpoint.LeetCodeCN) {
57+
return true;
58+
}
59+
return false;
60+
}

src/extension.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
"use strict";
22

33
import * as vscode from "vscode";
4+
import * as plugin from "./commands/plugin";
45
import * as session from "./commands/session";
56
import * as show from "./commands/show";
67
import * as submit from "./commands/submit";
@@ -20,6 +21,7 @@ export async function activate(context: vscode.ExtensionContext): Promise<void>
2021

2122
context.subscriptions.push(
2223
vscode.window.registerTreeDataProvider("leetCodeExplorer", leetCodeTreeDataProvider),
24+
vscode.commands.registerCommand("leetcode.toogleLeetCodeCn", () => plugin.toogleLeetCodeCn()),
2325
vscode.commands.registerCommand("leetcode.signin", () => leetCodeManager.signIn()),
2426
vscode.commands.registerCommand("leetcode.signout", () => leetCodeManager.signOut()),
2527
vscode.commands.registerCommand("leetcode.selectSessions", () => session.selectSession()),
@@ -31,6 +33,8 @@ export async function activate(context: vscode.ExtensionContext): Promise<void>
3133
vscode.commands.registerCommand("leetcode.submitSolution", (uri?: vscode.Uri) => submit.submitSolution(uri)),
3234
);
3335

36+
await plugin.initializeEndpoint();
37+
3438
leetCodeManager.on("statusChanged", () => {
3539
leetCodeStatusBarItem.updateStatusBar(leetCodeManager.getStatus(), leetCodeManager.getUser());
3640
leetCodeTreeDataProvider.refresh();

src/leetCodeExecutor.ts

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,9 @@ export interface ILeetCodeExecutor {
3030
/* section for solution command */
3131
submitSolution(filePath: string): Promise<string>;
3232
testSolution(filePath: string, testString?: string): Promise<string>;
33+
34+
/* section for plugin command */
35+
toggleLeetCodeCn(isEnable: boolean): Promise<string>;
3336
}
3437

3538
class LeetCodeExecutor implements ILeetCodeExecutor {
@@ -109,6 +112,13 @@ class LeetCodeExecutor implements ILeetCodeExecutor {
109112
return await this.executeCommandWithProgressEx("Submitting to LeetCode...", "node", [await this.getLeetCodeBinaryPath(), "test", `"${filePath}"`]);
110113
}
111114

115+
public async toggleLeetCodeCn(isEnable: boolean): Promise<string> {
116+
if (isEnable) {
117+
return await this.executeCommandEx("node", [await this.getLeetCodeBinaryPath(), "plugin", "-e", "leetcode.cn"]);
118+
}
119+
return await this.executeCommandEx("node", [await this.getLeetCodeBinaryPath(), "plugin", "-d", "leetcode.cn"]);
120+
}
121+
112122
private async executeCommandEx(command: string, args: string[], options: cp.SpawnOptions = { shell: true }): Promise<string> {
113123
if (wsl.useWsl()) {
114124
return await executeCommand("wsl", [command].concat(args), options);

src/leetCodeManager.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -109,7 +109,7 @@ class LeetCodeManager extends EventEmitter implements ILeetCodeManager {
109109
this.userStatus = UserStatus.SignedOut;
110110
this.emit("statusChanged");
111111
} catch (error) {
112-
promptForOpenOutputChannel("Failed to sign out. Please open the output channel for details", DialogType.error);
112+
// swallow the error when sign out.
113113
}
114114
}
115115

src/shared.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,3 +33,8 @@ export enum ProblemState {
3333
NotAC = 2,
3434
Unknown = 3,
3535
}
36+
37+
export enum Endpoint {
38+
LeetCode = "leetcode",
39+
LeetCodeCN = "leetcode-cn",
40+
}

src/utils/uiUtils.ts

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import * as opn from "opn";
55
import * as os from "os";
66
import * as path from "path";
77
import * as vscode from "vscode";
8+
import { isLeetCodeCnEnabled } from "../commands/plugin";
89
import { leetCodeChannel } from "../leetCodeChannel";
910

1011
export namespace DialogOptions {
@@ -48,7 +49,11 @@ export async function promptForSignIn(): Promise<void> {
4849
await vscode.commands.executeCommand("leetcode.signin");
4950
break;
5051
case DialogOptions.singUp:
51-
opn("https://leetcode.com");
52+
if (isLeetCodeCnEnabled()) {
53+
opn("https://leetcode-cn.com");
54+
} else {
55+
opn("https://leetcode.com");
56+
}
5257
break;
5358
default:
5459
break;

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy