@@ -14,10 +14,12 @@ export class DeviceIdService {
1414 private deviceIdPromise : Promise < string > | undefined = undefined ;
1515 private abortController : AbortController | undefined = undefined ;
1616 private logger : LoggerBase ;
17- private getMachineId : ( ) => Promise < string > ;
17+ private readonly getMachineId : ( ) => Promise < string > ;
18+ private timeout : number ;
1819
19- private constructor ( logger : LoggerBase ) {
20+ private constructor ( logger : LoggerBase , timeout : number ) {
2021 this . logger = logger ;
22+ this . timeout = timeout ;
2123 this . getMachineId = ( ) : Promise < string > => nodeMachineId . machineId ( true ) ;
2224 // Start device ID calculation immediately
2325 this . startDeviceIdCalculation ( ) ;
@@ -29,36 +31,33 @@ export class DeviceIdService {
2931 * @param logger - The logger instance to use
3032 * @returns The DeviceIdService instance
3133 */
32- public static init ( logger : LoggerBase ) : DeviceIdService {
34+ public static init ( logger : LoggerBase , timeout ?: number ) : DeviceIdService {
3335 if ( DeviceIdService . instance ) {
3436 return DeviceIdService . instance ;
3537 }
36- DeviceIdService . instance = new DeviceIdService ( logger ) ;
38+ DeviceIdService . instance = new DeviceIdService ( logger , timeout ?? DEVICE_ID_TIMEOUT ) ;
3739 return DeviceIdService . instance ;
3840 }
3941
42+ /**
43+ * Checks if the DeviceIdService is initialized.
44+ * @returns True if the DeviceIdService is initialized, false otherwise
45+ */
46+ public static isInitialized ( ) : boolean {
47+ return DeviceIdService . instance !== undefined ;
48+ }
49+
4050 /**
4151 * Gets the singleton instance of DeviceIdService.
4252 * @returns The DeviceIdService instance
4353 */
4454 public static getInstance ( ) : DeviceIdService {
4555 if ( ! DeviceIdService . instance ) {
46- throw Error ( "DeviceIdService not initialized" ) ;
56+ throw new Error ( "DeviceIdService not initialized" ) ;
4757 }
4858 return DeviceIdService . instance ;
4959 }
5060
51- /**
52- * Resets the singleton instance (mainly for testing).
53- */
54- static resetInstance ( ) : void {
55- // abort any ongoing calculation
56- if ( DeviceIdService . instance ?. abortController ) {
57- DeviceIdService . instance . abortController . abort ( ) ;
58- }
59- DeviceIdService . instance = undefined ;
60- }
61-
6261 /**
6362 * Starts the device ID calculation process.
6463 * This method is called automatically in the constructor.
@@ -77,28 +76,27 @@ export class DeviceIdService {
7776 * @returns Promise that resolves to the device ID string
7877 */
7978 public async getDeviceId ( ) : Promise < string > {
80- // Return cached value if available
8179 if ( this . deviceId !== undefined ) {
8280 return this . deviceId ;
8381 }
8482
85- // If calculation is already in progress, wait for it
86- if ( this . deviceIdPromise ) {
87- return this . deviceIdPromise ;
83+ if ( ! this . deviceIdPromise ) {
84+ throw new Error ( "DeviceIdService calculation not started" ) ;
8885 }
8986
90- // If somehow we don't have a promise, raise an error
91- throw new Error ( "Failed to get device ID" ) ;
87+ return this . deviceIdPromise ;
9288 }
9389 /**
9490 * Aborts any ongoing device ID calculation.
9591 */
96- abortCalculation ( ) : void {
92+ public close ( ) : void {
9793 if ( this . abortController ) {
9894 this . abortController . abort ( ) ;
9995 this . abortController = undefined ;
10096 }
97+ this . deviceId = undefined ;
10198 this . deviceIdPromise = undefined ;
99+ DeviceIdService . instance = undefined ;
102100 }
103101
104102 /**
@@ -113,8 +111,9 @@ export class DeviceIdService {
113111 const deviceId = await getDeviceId ( {
114112 getMachineId : this . getMachineId ,
115113 onError : ( reason , error ) => {
116- this . handleDeviceIdError ( reason , error ) ;
114+ this . handleDeviceIdError ( reason , String ( error ) ) ;
117115 } ,
116+ timeout : this . timeout ,
118117 abortSignal : this . abortController . signal ,
119118 } ) ;
120119
@@ -128,7 +127,7 @@ export class DeviceIdService {
128127 }
129128
130129 this . logger . debug ( {
131- id : LogId . telemetryDeviceIdFailure ,
130+ id : LogId . deviceIdResolutionError ,
132131 context : "deviceId" ,
133132 message : `Failed to get device ID: ${ String ( error ) } ` ,
134133 } ) ;
@@ -146,20 +145,21 @@ export class DeviceIdService {
146145 * @param reason - The reason for the error
147146 * @param error - The error object
148147 */
149- private handleDeviceIdError ( reason : string , error : Error ) : void {
148+ private handleDeviceIdError ( reason : string , error : string ) : void {
150149 switch ( reason ) {
151150 case "resolutionError" :
152151 this . logger . debug ( {
153- id : LogId . telemetryDeviceIdFailure ,
152+ id : LogId . deviceIdResolutionError ,
154153 context : "deviceId" ,
155- message : `Device ID resolution error: ${ String ( error ) } ` ,
154+ message : `Resolution error: ${ String ( error ) } ` ,
156155 } ) ;
157156 break ;
158157 case "timeout" :
159158 this . logger . debug ( {
160- id : LogId . telemetryDeviceIdTimeout ,
159+ id : LogId . deviceIdTimeout ,
161160 context : "deviceId" ,
162161 message : "Device ID retrieval timed out" ,
162+ noRedaction : true ,
163163 } ) ;
164164 break ;
165165 case "abort" :
0 commit comments