Skip to content

Commit 0ef695a

Browse files
committed
Use bundled environment activation script file
1 parent 0650829 commit 0ef695a

18 files changed

+300
-51
lines changed

vscode/activation.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
env = { env: ENV.to_h, yjit: !!defined?(RubyVM::YJIT), version: RUBY_VERSION, gemPath: Gem.path }.to_json
2+
STDERR.print("RUBY_LSP_ACTIVATION_SEPARATOR#{env}RUBY_LSP_ACTIVATION_SEPARATOR")

vscode/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -720,7 +720,7 @@
720720
}
721721
},
722722
"scripts": {
723-
"vscode:prepublish": "yarn run esbuild-base --minify",
723+
"vscode:prepublish": "yarn run esbuild-base --minify && cp activation.rb out/activation.rb",
724724
"package": "vsce package --out vscode-ruby-lsp.vsix --baseImagesUrl https://github.com/Shopify/ruby-lsp/raw/HEAD/vscode",
725725
"package_prerelease": "vsce package --pre-release --out vscode-ruby-lsp.vsix --baseImagesUrl https://github.com/Shopify/ruby-lsp/raw/HEAD/vscode",
726726
"esbuild-base": "esbuild ./src/extension.ts --bundle --outfile=out/extension.js --external:vscode --format=cjs --platform=node",

vscode/src/ruby.ts

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -135,6 +135,7 @@ export class Ruby implements RubyInterface {
135135
new None(
136136
this.workspaceFolder,
137137
this.outputChannel,
138+
this.context,
138139
this.manuallySelectRuby.bind(this),
139140
workspaceRubyPath,
140141
),
@@ -165,6 +166,7 @@ export class Ruby implements RubyInterface {
165166
new None(
166167
this.workspaceFolder,
167168
this.outputChannel,
169+
this.context,
168170
this.manuallySelectRuby.bind(this),
169171
globalRubyPath,
170172
),
@@ -315,6 +317,7 @@ export class Ruby implements RubyInterface {
315317
new Asdf(
316318
this.workspaceFolder,
317319
this.outputChannel,
320+
this.context,
318321
this.manuallySelectRuby.bind(this),
319322
),
320323
);
@@ -324,6 +327,7 @@ export class Ruby implements RubyInterface {
324327
new Chruby(
325328
this.workspaceFolder,
326329
this.outputChannel,
330+
this.context,
327331
this.manuallySelectRuby.bind(this),
328332
),
329333
);
@@ -333,6 +337,7 @@ export class Ruby implements RubyInterface {
333337
new Rbenv(
334338
this.workspaceFolder,
335339
this.outputChannel,
340+
this.context,
336341
this.manuallySelectRuby.bind(this),
337342
),
338343
);
@@ -342,6 +347,7 @@ export class Ruby implements RubyInterface {
342347
new Rvm(
343348
this.workspaceFolder,
344349
this.outputChannel,
350+
this.context,
345351
this.manuallySelectRuby.bind(this),
346352
),
347353
);
@@ -351,6 +357,7 @@ export class Ruby implements RubyInterface {
351357
new Mise(
352358
this.workspaceFolder,
353359
this.outputChannel,
360+
this.context,
354361
this.manuallySelectRuby.bind(this),
355362
),
356363
);
@@ -360,6 +367,7 @@ export class Ruby implements RubyInterface {
360367
new RubyInstaller(
361368
this.workspaceFolder,
362369
this.outputChannel,
370+
this.context,
363371
this.manuallySelectRuby.bind(this),
364372
),
365373
);
@@ -369,6 +377,7 @@ export class Ruby implements RubyInterface {
369377
new Custom(
370378
this.workspaceFolder,
371379
this.outputChannel,
380+
this.context,
372381
this.manuallySelectRuby.bind(this),
373382
),
374383
);
@@ -378,6 +387,7 @@ export class Ruby implements RubyInterface {
378387
new None(
379388
this.workspaceFolder,
380389
this.outputChannel,
390+
this.context,
381391
this.manuallySelectRuby.bind(this),
382392
),
383393
);
@@ -387,6 +397,7 @@ export class Ruby implements RubyInterface {
387397
new Shadowenv(
388398
this.workspaceFolder,
389399
this.outputChannel,
400+
this.context,
390401
this.manuallySelectRuby.bind(this),
391402
),
392403
);

vscode/src/ruby/chruby.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,9 +31,10 @@ export class Chruby extends VersionManager {
3131
constructor(
3232
workspaceFolder: vscode.WorkspaceFolder,
3333
outputChannel: WorkspaceChannel,
34+
context: vscode.ExtensionContext,
3435
manuallySelectRuby: () => Promise<void>,
3536
) {
36-
super(workspaceFolder, outputChannel, manuallySelectRuby);
37+
super(workspaceFolder, outputChannel, context, manuallySelectRuby);
3738

3839
const configuredRubies = vscode.workspace
3940
.getConfiguration("rubyLsp")

vscode/src/ruby/none.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,11 @@ export class None extends VersionManager {
1919
constructor(
2020
workspaceFolder: vscode.WorkspaceFolder,
2121
outputChannel: WorkspaceChannel,
22+
context: vscode.ExtensionContext,
2223
manuallySelectRuby: () => Promise<void>,
2324
rubyPath?: string,
2425
) {
25-
super(workspaceFolder, outputChannel, manuallySelectRuby);
26+
super(workspaceFolder, outputChannel, context, manuallySelectRuby);
2627
this.rubyPath = rubyPath ?? "ruby";
2728
}
2829

vscode/src/ruby/versionManager.ts

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -17,26 +17,23 @@ export interface ActivationResult {
1717
export const ACTIVATION_SEPARATOR = "RUBY_LSP_ACTIVATION_SEPARATOR";
1818

1919
export abstract class VersionManager {
20-
public activationScript = [
21-
`STDERR.print("${ACTIVATION_SEPARATOR}" + `,
22-
"{ env: ENV.to_h, yjit: !!defined?(RubyVM::YJIT), version: RUBY_VERSION, gemPath: Gem.path }.to_json + ",
23-
`"${ACTIVATION_SEPARATOR}")`,
24-
].join("");
25-
2620
protected readonly outputChannel: WorkspaceChannel;
2721
protected readonly workspaceFolder: vscode.WorkspaceFolder;
2822
protected readonly bundleUri: vscode.Uri;
2923
protected readonly manuallySelectRuby: () => Promise<void>;
3024

25+
private readonly context: vscode.ExtensionContext;
3126
private readonly customBundleGemfile?: string;
3227

3328
constructor(
3429
workspaceFolder: vscode.WorkspaceFolder,
3530
outputChannel: WorkspaceChannel,
31+
context: vscode.ExtensionContext,
3632
manuallySelectRuby: () => Promise<void>,
3733
) {
3834
this.workspaceFolder = workspaceFolder;
3935
this.outputChannel = outputChannel;
36+
this.context = context;
4037
this.manuallySelectRuby = manuallySelectRuby;
4138
const customBundleGemfile: string = vscode.workspace
4239
.getConfiguration("rubyLsp")
@@ -60,8 +57,12 @@ export abstract class VersionManager {
6057
abstract activate(): Promise<ActivationResult>;
6158

6259
protected async runEnvActivationScript(activatedRuby: string) {
60+
const activationUri = vscode.Uri.joinPath(
61+
this.context.extensionUri,
62+
"activation.rb",
63+
);
6364
const result = await this.runScript(
64-
`${activatedRuby} -W0 -rjson -e '${this.activationScript}'`,
65+
`${activatedRuby} -W0 -rjson '${activationUri.fsPath}'`,
6566
);
6667

6768
const activationContent = new RegExp(

vscode/src/test/suite/client.test.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,7 @@ async function launchClient(workspaceUri: vscode.Uri) {
8181
get: (_name: string) => undefined,
8282
update: (_name: string, _value: any) => Promise.resolve(),
8383
},
84+
extensionUri: vscode.Uri.file(path.join(workspaceUri.fsPath, "vscode")),
8485
} as unknown as vscode.ExtensionContext;
8586
const fakeLogger = new FakeLogger();
8687
const outputChannel = new WorkspaceChannel("fake", fakeLogger as any);

vscode/src/test/suite/debugger.test.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -192,12 +192,16 @@ suite("Debugger", () => {
192192
'source "https://rubygems.org"\ngem "debug"',
193193
);
194194

195+
const extensionPath = path.dirname(
196+
path.dirname(path.dirname(path.dirname(__dirname))),
197+
);
195198
const context = {
196199
subscriptions: [],
197200
workspaceState: {
198201
get: () => undefined,
199202
update: () => undefined,
200203
},
204+
extensionUri: vscode.Uri.file(path.join(extensionPath, "vscode")),
201205
} as unknown as vscode.ExtensionContext;
202206
const outputChannel = new WorkspaceChannel("fake", LOG_CHANNEL);
203207
const workspaceFolder: vscode.WorkspaceFolder = {

vscode/src/test/suite/ruby.test.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ suite("Ruby environment activation", () => {
2929
get: () => undefined,
3030
update: () => undefined,
3131
},
32+
extensionUri: vscode.Uri.file(path.join(workspacePath, "vscode")),
3233
} as unknown as vscode.ExtensionContext;
3334
const outputChannel = new WorkspaceChannel("fake", LOG_CHANNEL);
3435

vscode/src/test/suite/ruby/asdf.test.ts

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,15 @@ suite("Asdf", () => {
1616
console.log("Skipping Asdf tests on Windows");
1717
return;
1818
}
19+
const context = {
20+
extensionMode: vscode.ExtensionMode.Test,
21+
subscriptions: [],
22+
workspaceState: {
23+
get: (_name: string) => undefined,
24+
update: (_name: string, _value: any) => Promise.resolve(),
25+
},
26+
extensionUri: vscode.Uri.parse("file:///fake"),
27+
} as unknown as vscode.ExtensionContext;
1928

2029
test("Finds Ruby based on .tool-versions", async () => {
2130
// eslint-disable-next-line no-process-env
@@ -26,7 +35,12 @@ suite("Asdf", () => {
2635
index: 0,
2736
};
2837
const outputChannel = new WorkspaceChannel("fake", common.LOG_CHANNEL);
29-
const asdf = new Asdf(workspaceFolder, outputChannel, async () => {});
38+
const asdf = new Asdf(
39+
workspaceFolder,
40+
outputChannel,
41+
context,
42+
async () => {},
43+
);
3044
const envStub = {
3145
env: { ANY: "true" },
3246
yjit: true,
@@ -47,7 +61,7 @@ suite("Asdf", () => {
4761

4862
assert.ok(
4963
execStub.calledOnceWithExactly(
50-
`. ${os.homedir()}/.asdf/asdf.sh && asdf exec ruby -W0 -rjson -e '${asdf.activationScript}'`,
64+
`. ${os.homedir()}/.asdf/asdf.sh && asdf exec ruby -W0 -rjson '/fake/activation.rb'`,
5165
{
5266
cwd: workspacePath,
5367
shell: "/bin/bash",
@@ -75,7 +89,12 @@ suite("Asdf", () => {
7589
index: 0,
7690
};
7791
const outputChannel = new WorkspaceChannel("fake", common.LOG_CHANNEL);
78-
const asdf = new Asdf(workspaceFolder, outputChannel, async () => {});
92+
const asdf = new Asdf(
93+
workspaceFolder,
94+
outputChannel,
95+
context,
96+
async () => {},
97+
);
7998
const envStub = {
8099
env: { ANY: "true" },
81100
yjit: true,
@@ -98,7 +117,7 @@ suite("Asdf", () => {
98117

99118
assert.ok(
100119
execStub.calledOnceWithExactly(
101-
`. ${os.homedir()}/.asdf/asdf.fish && asdf exec ruby -W0 -rjson -e '${asdf.activationScript}'`,
120+
`. ${os.homedir()}/.asdf/asdf.fish && asdf exec ruby -W0 -rjson '/fake/activation.rb'`,
102121
{
103122
cwd: workspacePath,
104123
shell: "/opt/homebrew/bin/fish",

0 commit comments

Comments
 (0)