Skip to content
This repository was archived by the owner on Dec 8, 2020. It is now read-only.

Commit 5442989

Browse files
authored
Allows developers to specify the nightly toolchain (#299)
1 parent e78420c commit 5442989

File tree

5 files changed

+277
-204
lines changed

5 files changed

+277
-204
lines changed

doc/common_configuration_parameters.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,3 +10,8 @@ This configuration parameter specifies which toolchain the extension will invoke
1010
It is used for getting sysroot, installing components, invoking Cargo
1111

1212
However there are few exceptions. Currently RLS is available for nightly hence RLS and rust-analysis are installed for the nightly toolchain.
13+
14+
### nightlyToolchain
15+
16+
This configuration parameter specifies which toolchain the extension will invoke rustup with.
17+
It is used for installing RLS and related stuff.

package.json

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -477,6 +477,14 @@
477477
"string",
478478
"null"
479479
]
480+
},
481+
"nightlyToolchain": {
482+
"default": null,
483+
"description": "The nightly toolchain to use for installing RLS and related components and running RLS",
484+
"type": [
485+
"string",
486+
"null"
487+
]
480488
}
481489
}
482490
},

src/components/configuration/RlsConfiguration.ts

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,13 @@ export class RlsConfiguration {
2727
return new RlsConfiguration(rustup, rustSource, executableUserPath);
2828
}
2929

30+
/**
31+
* Returns if there is some executable path specified by the user
32+
*/
33+
public isExecutableUserPathSet(): boolean {
34+
return this._executableUserPath !== undefined;
35+
}
36+
3037
/**
3138
* Returns a path to RLS executable
3239
*/
@@ -47,7 +54,12 @@ export class RlsConfiguration {
4754
// When the user specifies some executable path, the user expects the extension not to add
4855
// some arguments
4956
if (this._executableUserPath === undefined && this._rustup && this._rustup.isRlsInstalled()) {
50-
return ['run', 'nightly', 'rls'].concat(this._userArgs);
57+
const userToolchain = this._rustup.getUserNightlyToolchain();
58+
if (!userToolchain) {
59+
// It is actually impossible because `isRlsInstalled` uses `getUserNightlyToolchain`
60+
return this._userArgs;
61+
}
62+
return ['run', userToolchain.toString(true, false), 'rls'].concat(this._userArgs);
5163
} else {
5264
return this._userArgs;
5365
}

src/components/configuration/Rustup.ts

Lines changed: 46 additions & 73 deletions
Original file line numberDiff line numberDiff line change
@@ -27,12 +27,6 @@ export class Rustup {
2727
*/
2828
private pathToRustSourceCode: string | undefined;
2929

30-
/**
31-
* A path to the executable of RLS.
32-
* It can be undefined if the component "rls" is not installed
33-
*/
34-
private pathToRlsExecutable: string | undefined;
35-
3630
/**
3731
* Components received by invoking rustup
3832
*/
@@ -48,6 +42,10 @@ export class Rustup {
4842
*/
4943
private _userToolchain: Toolchain | undefined;
5044

45+
/**
46+
* The nightly toolchain chosen by the user
47+
*/
48+
private _userNightlyToolchain: Toolchain | undefined;
5149

5250
/**
5351
* Returns the executable of Rustup
@@ -70,26 +68,6 @@ export class Rustup {
7068
return rustup;
7169
}
7270

73-
/**
74-
* Return either the only nightly toolchain or undefined if there is no nightly toolchain or
75-
* there are several nightly toolchains
76-
*/
77-
public getNightlyToolchain(logger: ChildLogger): Toolchain | undefined {
78-
const functionLogger = logger.createChildLogger('getNightlyToolchain: ');
79-
const nightlyToolchains = this.getNightlyToolchains();
80-
switch (nightlyToolchains.length) {
81-
case 0:
82-
functionLogger.error('There is no nightly toolchain');
83-
return undefined;
84-
case 1:
85-
functionLogger.debug('There is only one nightly toolchain');
86-
return nightlyToolchains[0];
87-
default:
88-
functionLogger.debug(`There are ${nightlyToolchains.length} nightly toolchains`);
89-
return undefined;
90-
}
91-
}
92-
9371
/**
9472
* Returns either the default toolchain or undefined if there are no installed toolchains
9573
*/
@@ -109,6 +87,10 @@ export class Rustup {
10987
return this.toolchains;
11088
}
11189

90+
public getNightlyToolchains(): Toolchain[] {
91+
return this.toolchains.filter(t => t.channel === 'nightly');
92+
}
93+
11294
/**
11395
* Checks if the toolchain is installed
11496
* @param toolchain The toolchain to check
@@ -125,10 +107,24 @@ export class Rustup {
125107
}
126108

127109
/**
128-
* Returns either the path to the executable of RLS or undefined
110+
* Returns either the nightly toolchain chosen by the user or undefined
129111
*/
130-
public getPathToRlsExecutable(): string | undefined {
131-
return this.pathToRlsExecutable;
112+
public getUserNightlyToolchain(): Toolchain | undefined {
113+
return this._userNightlyToolchain;
114+
}
115+
116+
/**
117+
* Sets the new value of the nightly toolchain in the object and in the configuration
118+
* @param toolchain The new value
119+
*/
120+
public setUserNightlyToolchain(toolchain: Toolchain | undefined): void {
121+
if (this._userNightlyToolchain === toolchain) {
122+
return;
123+
}
124+
this._userNightlyToolchain = toolchain;
125+
updateUserConfigurationParameter(c => {
126+
c.nightlyToolchain = toolchain ? toolchain.toString(true, false) : null;
127+
});
132128
}
133129

134130
/**
@@ -143,7 +139,9 @@ export class Rustup {
143139
return;
144140
}
145141
this._userToolchain = toolchain;
146-
updateUserConfigurationParameter(c => c.toolchain = toolchain ? toolchain.toString(true, false) : null);
142+
updateUserConfigurationParameter(c => {
143+
c.toolchain = toolchain ? toolchain.toString(true, false) : null;
144+
});
147145
}
148146

149147
/**
@@ -188,7 +186,7 @@ export class Rustup {
188186
*/
189187
public async installRls(): Promise<boolean> {
190188
const logger = this.logger.createChildLogger('installRls: ');
191-
const nightlyToolchain = this.getNightlyToolchain(logger);
189+
const nightlyToolchain = this.getUserNightlyToolchain();
192190
if (!nightlyToolchain) {
193191
logger.error('no nightly toolchain');
194192
return false;
@@ -197,17 +195,7 @@ export class Rustup {
197195
nightlyToolchain,
198196
Rustup.getRlsComponentName()
199197
);
200-
if (!isComponentInstalled) {
201-
return false;
202-
}
203-
// We need to update the field
204-
await this.updatePathToRlsExecutable();
205-
if (!this.pathToRlsExecutable) {
206-
logger.error('RLS had been installed successfully, but we failed to find it in PATH. This should have not happened');
207-
208-
return false;
209-
}
210-
return true;
198+
return isComponentInstalled;
211199
}
212200

213201
/**
@@ -216,7 +204,7 @@ export class Rustup {
216204
*/
217205
public async installRustAnalysis(): Promise<boolean> {
218206
const logger = this.logger.createChildLogger('installRustAnalysis: ');
219-
const nightlyToolchain = this.getNightlyToolchain(logger);
207+
const nightlyToolchain = this.getUserNightlyToolchain();
220208
if (!nightlyToolchain) {
221209
logger.error('no nightly toolchain');
222210
return false;
@@ -291,31 +279,13 @@ export class Rustup {
291279
}
292280
}
293281

294-
/**
295-
* Checks if the executable of RLS is installed.
296-
* This method assigns either a path to the executable or undefined to the field `pathToRlsExecutable`, depending on if the executable is found
297-
* This method is asynchronous because it checks if the executable exists
298-
*/
299-
public async updatePathToRlsExecutable(): Promise<void> {
300-
const logger = this.logger.createChildLogger('updatePathToRlsExecutable: ');
301-
this.pathToRlsExecutable = undefined;
302-
const rlsPath: string | undefined = await FileSystem.findExecutablePath('rls');
303-
logger.debug(`rlsPath=${rlsPath}`);
304-
if (!rlsPath) {
305-
// RLS is installed via Rustup, but isn't found. Let a user know about it
306-
logger.error(`Rustup had reported that RLS had been installed, but RLS wasn't found in PATH=${process.env.PATH}`);
307-
return;
308-
}
309-
this.pathToRlsExecutable = rlsPath;
310-
}
311-
312282
/**
313283
* Requests Rustup give a list of components, parses it, checks if RLS is present in the list and returns if it is
314284
* @returns true if RLS can be installed otherwise false
315285
*/
316286
public canInstallRls(): boolean {
317287
const logger = this.logger.createChildLogger('canInstallRls: ');
318-
const nightlyToolchain = this.getNightlyToolchain(logger);
288+
const nightlyToolchain = this.getUserNightlyToolchain();
319289
if (!nightlyToolchain) {
320290
logger.error('no nightly toolchain');
321291
return false;
@@ -343,7 +313,7 @@ export class Rustup {
343313
*/
344314
public isRlsInstalled(): boolean {
345315
const logger = this.logger.createChildLogger('isRlsInstalled: ');
346-
const nightlyToolchain = this.getNightlyToolchain(logger);
316+
const nightlyToolchain = this.getUserNightlyToolchain();
347317
if (!nightlyToolchain) {
348318
logger.error('no nightly toolchain');
349319
return false;
@@ -357,7 +327,7 @@ export class Rustup {
357327
*/
358328
public isRustAnalysisInstalled(): boolean {
359329
const logger = this.logger.createChildLogger('isRustAnalysisInstalled: ');
360-
const nightlyToolchain = this.getNightlyToolchain(logger);
330+
const nightlyToolchain = this.getUserNightlyToolchain();
361331
if (!nightlyToolchain) {
362332
logger.error('no nightly toolchain');
363333
return false;
@@ -371,7 +341,7 @@ export class Rustup {
371341
*/
372342
public canInstallRustAnalysis(): boolean {
373343
const logger = this.logger.createChildLogger('canInstallRustAnalysis: ');
374-
const nightlyToolchain = this.getNightlyToolchain(logger);
344+
const nightlyToolchain = this.getUserNightlyToolchain();
375345
if (!nightlyToolchain) {
376346
logger.error('no nightly toolchain');
377347
return false;
@@ -502,20 +472,15 @@ export class Rustup {
502472
* @param logger A value for the field `logger`
503473
* @param pathToRustcSysRoot A value for the field `pathToRustcSysRoot`
504474
* @param pathToRustSourceCode A value for the field `pathToRustSourceCode`
505-
* @param pathToRlsExecutable A value fo the field `pathToRlsExecutable`
506475
*/
507476
private constructor(logger: ChildLogger) {
508477
this.logger = logger;
509478
this.pathToRustcSysRoot = undefined;
510479
this.pathToRustSourceCode = undefined;
511-
this.pathToRlsExecutable = undefined;
512480
this.components = {};
513481
this.toolchains = [];
514482
this._userToolchain = getUserToolchain();
515-
}
516-
517-
private getNightlyToolchains(): Toolchain[] {
518-
return this.toolchains.filter(t => t.channel === 'nightly');
483+
this._userNightlyToolchain = getUserNightlyToolchain();
519484
}
520485

521486
/**
@@ -580,12 +545,12 @@ function getUserConfiguration(): any {
580545
return rustupConfiguration;
581546
}
582547

583-
function getUserToolchain(): Toolchain | undefined {
548+
function getToolchainFromConfigurationParameter(parameter: string): Toolchain | undefined {
584549
const rustupConfiguration = getUserConfiguration();
585550
if (!rustupConfiguration) {
586551
return undefined;
587552
}
588-
const toolchainAsString = rustupConfiguration.toolchain;
553+
const toolchainAsString = rustupConfiguration[parameter];
589554
if (!toolchainAsString) {
590555
return undefined;
591556
}
@@ -597,6 +562,14 @@ function getUserToolchain(): Toolchain | undefined {
597562
}
598563
}
599564

565+
function getUserNightlyToolchain(): Toolchain | undefined {
566+
return getToolchainFromConfigurationParameter('nightlyToolchain');
567+
}
568+
569+
function getUserToolchain(): Toolchain | undefined {
570+
return getToolchainFromConfigurationParameter('toolchain');
571+
}
572+
600573
function updateUserConfigurationParameter(updateParameter: (c: any) => void): void {
601574
let configuration = getUserConfiguration();
602575
if (!configuration) {

0 commit comments

Comments
 (0)