@@ -23,22 +23,36 @@ export interface CargoFeatures {
2323 allFeatures : boolean ;
2424 features : string [ ] ;
2525}
26+
27+ export const enum UpdatesChannel {
28+ Stable = "stable" ,
29+ Nightly = "nightly"
30+ }
31+
32+ export const NIGHTLY_TAG = "nightly" ;
2633export class Config {
27- private static readonly rootSection = "rust-analyzer" ;
28- private static readonly requiresReloadOpts = [
34+ readonly extensionId = "matklad.rust-analyzer" ;
35+
36+ private readonly rootSection = "rust-analyzer" ;
37+ private readonly requiresReloadOpts = [
2938 "cargoFeatures" ,
3039 "cargo-watch" ,
3140 "highlighting.semanticTokens" ,
3241 "inlayHints" ,
3342 ]
34- . map ( opt => `${ Config . rootSection } .${ opt } ` ) ;
43+ . map ( opt => `${ this . rootSection } .${ opt } ` ) ;
3544
36- private static readonly extensionVersion : string = ( ( ) => {
45+ /**
46+ * Either `nightly` or `YYYY-MM-DD` (i.e. `stable` release)
47+ */
48+ private readonly extensionVersion : string = ( ( ) => {
3749 const packageJsonVersion = vscode
3850 . extensions
39- . getExtension ( "matklad.rust-analyzer" ) !
51+ . getExtension ( this . extensionId ) !
4052 . packageJSON
41- . version as string ; // n.n.YYYYMMDD
53+ . version as string ;
54+
55+ if ( packageJsonVersion . endsWith ( NIGHTLY_TAG ) ) return NIGHTLY_TAG ;
4256
4357 const realVersionRegexp = / ^ \d + \. \d + \. ( \d { 4 } ) ( \d { 2 } ) ( \d { 2 } ) / ;
4458 const [ , yyyy , mm , dd ] = packageJsonVersion . match ( realVersionRegexp ) ! ;
@@ -54,7 +68,7 @@ export class Config {
5468 }
5569
5670 private refreshConfig ( ) {
57- this . cfg = vscode . workspace . getConfiguration ( Config . rootSection ) ;
71+ this . cfg = vscode . workspace . getConfiguration ( this . rootSection ) ;
5872 const enableLogging = this . cfg . get ( "trace.extension" ) as boolean ;
5973 log . setEnabled ( enableLogging ) ;
6074 log . debug ( "Using configuration:" , this . cfg ) ;
@@ -63,7 +77,7 @@ export class Config {
6377 private async onConfigChange ( event : vscode . ConfigurationChangeEvent ) {
6478 this . refreshConfig ( ) ;
6579
66- const requiresReloadOpt = Config . requiresReloadOpts . find (
80+ const requiresReloadOpt = this . requiresReloadOpts . find (
6781 opt => event . affectsConfiguration ( opt )
6882 ) ;
6983
@@ -121,8 +135,16 @@ export class Config {
121135 }
122136 }
123137
138+ get installedExtensionUpdateChannel ( ) {
139+ if ( this . serverPath !== null ) return null ;
140+
141+ return this . extensionVersion === NIGHTLY_TAG
142+ ? UpdatesChannel . Nightly
143+ : UpdatesChannel . Stable ;
144+ }
145+
124146 get serverSource ( ) : null | ArtifactSource {
125- const serverPath = RA_LSP_DEBUG ?? this . cfg . get < null | string > ( " serverPath" ) ;
147+ const serverPath = RA_LSP_DEBUG ?? this . serverPath ;
126148
127149 if ( serverPath ) {
128150 return {
@@ -135,23 +157,47 @@ export class Config {
135157
136158 if ( ! prebuiltBinaryName ) return null ;
137159
160+ return this . createGithubReleaseSource (
161+ prebuiltBinaryName ,
162+ this . extensionVersion
163+ ) ;
164+ }
165+
166+ private createGithubReleaseSource ( file : string , tag : string ) : ArtifactSource . GithubRelease {
138167 return {
139168 type : ArtifactSource . Type . GithubRelease ,
169+ file,
170+ tag,
140171 dir : this . ctx . globalStoragePath ,
141- file : prebuiltBinaryName ,
142- storage : this . ctx . globalState ,
143- tag : Config . extensionVersion ,
144- askBeforeDownload : this . cfg . get ( "updates.askBeforeDownload" ) as boolean ,
145172 repo : {
146173 name : "rust-analyzer" ,
147- owner : "rust-analyzer" ,
174+ owner : "rust-analyzer"
148175 }
149- } ;
176+ }
150177 }
151178
179+ get nightlyVsixSource ( ) : ArtifactSource . GithubRelease {
180+ return this . createGithubReleaseSource ( "rust-analyzer.vsix" , NIGHTLY_TAG ) ;
181+ }
182+
183+ readonly installedNightlyExtensionReleaseDate = new DateStorage (
184+ "rust-analyzer-installed-nightly-extension-release-date" ,
185+ this . ctx . globalState
186+ ) ;
187+ readonly serverReleaseDate = new DateStorage (
188+ "rust-analyzer-server-release-date" ,
189+ this . ctx . globalState
190+ ) ;
191+ readonly serverReleaseTag = new StringStorage (
192+ "rust-analyzer-release-tag" , this . ctx . globalState
193+ ) ;
194+
152195 // We don't do runtime config validation here for simplicity. More on stackoverflow:
153196 // https://stackoverflow.com/questions/60135780/what-is-the-best-way-to-type-check-the-configuration-for-vscode-extension
154197
198+ private get serverPath ( ) { return this . cfg . get ( "serverPath" ) as null | string ; }
199+ get updatesChannel ( ) { return this . cfg . get ( "updates.channel" ) as UpdatesChannel ; }
200+ get askBeforeDownload ( ) { return this . cfg . get ( "updates.askBeforeDownload" ) as boolean ; }
155201 get highlightingSemanticTokens ( ) { return this . cfg . get ( "highlighting.semanticTokens" ) as boolean ; }
156202 get highlightingOn ( ) { return this . cfg . get ( "highlightingOn" ) as boolean ; }
157203 get rainbowHighlightingOn ( ) { return this . cfg . get ( "rainbowHighlightingOn" ) as boolean ; }
@@ -189,3 +235,38 @@ export class Config {
189235 // for internal use
190236 get withSysroot ( ) { return this . cfg . get ( "withSysroot" , true ) as boolean ; }
191237}
238+
239+ export class StringStorage {
240+ constructor (
241+ private readonly key : string ,
242+ private readonly storage : vscode . Memento
243+ ) { }
244+
245+ get ( ) : null | string {
246+ const tag = this . storage . get ( this . key , null ) ;
247+ log . debug ( this . key , "==" , tag ) ;
248+ return tag ;
249+ }
250+ async set ( tag : string ) {
251+ log . debug ( this . key , "=" , tag ) ;
252+ await this . storage . update ( this . key , tag ) ;
253+ }
254+ }
255+ export class DateStorage {
256+
257+ constructor (
258+ private readonly key : string ,
259+ private readonly storage : vscode . Memento
260+ ) { }
261+
262+ get ( ) : null | Date {
263+ const date = this . storage . get ( this . key , null ) ;
264+ log . debug ( this . key , "==" , date ) ;
265+ return date ? new Date ( date ) : null ;
266+ }
267+
268+ async set ( date : null | Date ) {
269+ log . debug ( this . key , "=" , date ) ;
270+ await this . storage . update ( this . key , date ) ;
271+ }
272+ }
0 commit comments