import { LoggingSession } from "./logging-session" ; import { AutorestDiagnostic , AutorestError , AutorestLogger , AutorestWarning , LoggerAsyncProcessor , LoggerProcessor , LoggerSink , LogInfo , } from "./types" ; import { Progress } from "." ; export interface AutorestLoggerBaseOptions < T > { processors ? : T [ ] ; sinks : LoggerSink [ ] ; } export abstract class AutorestLoggerBase < T > implements AutorestLogger { public diagnostics : AutorestDiagnostic [ ] = [ ] ; protected sinks : LoggerSink [ ] ; protected processors : T [ ] ; public constructor ( options ) { this . sinks = options . sinks ; this . processors = options . processors ?? [ ] ; } public debug ( message ) { this . log ( { level : "debug" , message , } ) ; } public verbose ( message ) { this . log ( { level : "verbose" , message , } ) ; } public info ( message ) { this . log ( { level : "information" , message , } ) ; } public fatal ( message ) { this . log ( { level : "fatal" , message , } ) ; } public trackWarning ( warning ) { this . trackDiagnostic ( { level : "warning" , ... warning , } ) ; } public trackError ( error ) { this . trackDiagnostic ( { level : "error" , ... error , } ) ; } public startProgress ( initialName ? ) { const sinkProgressTrackers = this . sinks . map ( ( x ) => x . startProgress ( initialName ) ) ; const update = ( progress ) => { for ( const tracker of sinkProgressTrackers ) { tracker . update ( progress ) ; } } ; const stop = ( ) => { for ( const tracker of sinkProgressTrackers ) { tracker . stop ( ) ; } } ; return { update , stop , } ; } protected emitLog ( log ) { for ( const sink of this . sinks ) { sink . log ( log ) ; } } public abstract with ( ... processors ) ; public abstract trackDiagnostic ( diagnostic ) ; public abstract log ( log ) ; } export interface AutorestLoggerOptions extends AutorestLoggerBaseOptions < LoggerProcessor > { } export class AutorestSyncLogger extends AutorestLoggerBase < LoggerProcessor > { public diagnostics : AutorestDiagnostic [ ] = [ ] ; public constructor ( options ) { super ( options ) ; } public with ( ... processors ) { return new AutorestSyncLogger ( { sinks : this . sinks , processors : [ ... processors , ... this . processors ] , } ) ; } public override trackDiagnostic ( diagnostic ) { const processed = this . process ( diagnostic ) ; if ( processed === undefined ) { return ; } this . diagnostics . push ( processed as any ) ; this . emitLog ( processed ) ; } public override log ( log ) { const processed = this . process ( log ) ; if ( processed === undefined ) { return ; } this . emitLog ( processed ) ; } protected emitLog ( log ) { for ( const sink of this . sinks ) { sink . log ( log ) ; } } protected process ( log ) { let current = log ; for ( const processor of this . processors ) { const processed = processor . process ( log ) ; if ( processed === undefined ) { return undefined ; } else { current = processed ; } } return current ; } } export interface AutorestAsyncLoggerOptions extends AutorestLoggerBaseOptions < LoggerProcessor | LoggerAsyncProcessor > { asyncSession : LoggingSession ; } export class AutorestAsyncLogger extends AutorestLoggerBase < LoggerProcessor | LoggerAsyncProcessor > { public diagnostics : AutorestDiagnostic [ ] = [ ] ; private asyncSession : LoggingSession ; public constructor ( options ) { super ( options ) ; this . asyncSession = options . asyncSession ; } public with ( ... processors ) { return new AutorestAsyncLogger ( { asyncSession : this . asyncSession , sinks : this . sinks , processors : [ ... processors , ... this . processors ] , } ) ; } protected emitLog ( log ) { for ( const sink of this . sinks ) { sink . log ( log ) ; } } public override log ( log ) { this . asyncSession . registerLog ( ( ) => this . logMessageAsync ( log ) ) ; } public override trackDiagnostic ( diagnostic ) { this . asyncSession . registerLog ( ( ) => this . trackDiagnosticAsync ( diagnostic ) ) ; } private async logMessageAsync ( log ) { const processed = await this . process ( log ) ; if ( processed === undefined ) { return ; } this . emitLog ( processed ) ; } private async trackDiagnosticAsync ( diagnostic ) { const processed = await this . process ( diagnostic ) ; if ( processed === undefined ) { return ; } this . diagnostics . push ( processed as any ) ; this . emitLog ( processed ) ; } protected async process ( log ) { let current = log ; for ( const processor of this . processors ) { const processed = await processor . process ( log ) ; if ( processed === undefined ) { return undefined ; } else { current = processed ; } } return current ; } }