@@ -179,6 +179,12 @@ export interface TlsKeyOptions {
179179 usageRaTls ?: boolean ;
180180 usageServerAuth ?: boolean ;
181181 usageClientAuth ?: boolean ;
182+ // Certificate validity start (seconds since UNIX epoch). Requires dstack OS >= 0.5.7.
183+ notBefore ?: number ;
184+ // Certificate validity end (seconds since UNIX epoch). Requires dstack OS >= 0.5.7.
185+ notAfter ?: number ;
186+ // Embed app info into the certificate. Requires dstack OS >= 0.5.7.
187+ withAppInfo ?: boolean ;
182188}
183189
184190const SECP256K1_ALGORITHMS = new Set ( [ 'secp256k1' , 'k256' , '' ] )
@@ -217,6 +223,14 @@ export class DstackClient<T extends TcbInfo = TcbInfoV05x> {
217223 }
218224 }
219225
226+ private async ensureTlsKeyOptionsSupported ( featureNames : string [ ] ) : Promise < void > {
227+ try {
228+ await this . version ( )
229+ } catch {
230+ throw new Error ( `TLS key options [${ featureNames . join ( ', ' ) } ] are not supported: OS version too old (Version RPC unavailable)` )
231+ }
232+ }
233+
220234 async getKey ( path : string = '' , purpose : string = '' , algorithm : string = 'secp256k1' ) : Promise < GetKeyResponse > {
221235 await this . ensureAlgorithmSupported ( algorithm )
222236 const payload = JSON . stringify ( {
@@ -239,8 +253,19 @@ export class DstackClient<T extends TcbInfo = TcbInfoV05x> {
239253 usageRaTls = false ,
240254 usageServerAuth = true ,
241255 usageClientAuth = false ,
256+ notBefore,
257+ notAfter,
258+ withAppInfo,
242259 } = options ;
243260
261+ const newFeatures : string [ ] = [ ]
262+ if ( notBefore !== undefined ) newFeatures . push ( 'notBefore' )
263+ if ( notAfter !== undefined ) newFeatures . push ( 'notAfter' )
264+ if ( withAppInfo !== undefined ) newFeatures . push ( 'withAppInfo' )
265+ if ( newFeatures . length > 0 ) {
266+ await this . ensureTlsKeyOptionsSupported ( newFeatures )
267+ }
268+
244269 let raw : Record < string , any > = {
245270 subject,
246271 usage_ra_tls : usageRaTls ,
@@ -250,6 +275,15 @@ export class DstackClient<T extends TcbInfo = TcbInfoV05x> {
250275 if ( altNames && altNames . length ) {
251276 raw [ 'alt_names' ] = altNames
252277 }
278+ if ( notBefore !== undefined ) {
279+ raw [ 'not_before' ] = notBefore
280+ }
281+ if ( notAfter !== undefined ) {
282+ raw [ 'not_after' ] = notAfter
283+ }
284+ if ( withAppInfo !== undefined ) {
285+ raw [ 'with_app_info' ] = withAppInfo
286+ }
253287 const payload = JSON . stringify ( raw )
254288 const result = await send_rpc_request < GetTlsKeyResponse > ( this . endpoint , '/GetTlsKey' , payload )
255289 const asUint8Array = ( length ?: number ) => x509key_to_uint8array ( result . key , length )
0 commit comments