1
0
Fork 0

Remove state from context

pull/1562/head
Nikolai Laevskii 2023-10-12 05:54:13 +02:00
parent b4df76861f
commit 36629a3962
4 changed files with 33 additions and 58 deletions

View File

@ -74,16 +74,13 @@ describe('command-runner', () => {
expect(middleware).toHaveBeenCalledWith( expect(middleware).toHaveBeenCalledWith(
expect.objectContaining({ expect.objectContaining({
commandLine: 'echo',
args: ['hello', 'world'], args: ['hello', 'world'],
options: expect.objectContaining({ commandLine: 'echo',
silent: true
}),
stdout: 'hello',
stderr: '',
exitCode: 0,
execerr: null, execerr: null,
state: null exitCode: 0,
options: {failOnStdErr: false, ignoreReturnCode: true, silent: true},
stderr: '',
stdout: 'hello'
}), }),
expect.any(Function) expect.any(Function)
) )

View File

@ -25,10 +25,10 @@ const commandRunnerActions = {
log: produceLog log: produceLog
} as const } as const
export class CommandRunner<S = unknown> extends CommandRunnerBase<S> { export class CommandRunner extends CommandRunnerBase {
on( on(
event: CommandRunnerEventTypeExtended | CommandRunnerEventTypeExtended[], event: CommandRunnerEventTypeExtended | CommandRunnerEventTypeExtended[],
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
const middleware = const middleware =
@ -36,12 +36,12 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
? [commandRunnerActions[action](message)] ? [commandRunnerActions[action](message)]
: [action] : [action]
this.use(matchEvent(event, middleware as CommandRunnerMiddleware[])) this.use(matchEvent(event, middleware))
return this return this
} }
onEmptyOutput( onEmptyOutput(
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
this.onOutput(stdout => stdout?.trim() === '', action, message) this.onOutput(stdout => stdout?.trim() === '', action, message)
@ -49,7 +49,7 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
} }
onExecutionError( onExecutionError(
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
const middleware = const middleware =
@ -57,18 +57,13 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
? [commandRunnerActions[action](message)] ? [commandRunnerActions[action](message)]
: [action] : [action]
this.use( this.use(matchSpecificError(({type}) => type === 'execerr', middleware))
matchSpecificError(
({type}) => type === 'execerr',
middleware as CommandRunnerMiddleware[]
)
)
return this return this
} }
onStdError( onStdError(
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
const middleware = const middleware =
@ -76,18 +71,13 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
? [commandRunnerActions[action](message)] ? [commandRunnerActions[action](message)]
: [action] : [action]
this.use( this.use(matchSpecificError(({type}) => type === 'stderr', middleware))
matchSpecificError(
({type}) => type === 'stderr',
middleware as CommandRunnerMiddleware[]
)
)
return this return this
} }
onError( onError(
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
return this.on(['execerr', 'stderr'], action, message) return this.on(['execerr', 'stderr'], action, message)
@ -95,7 +85,7 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
onSpecificError( onSpecificError(
matcher: ErrorMatcher, matcher: ErrorMatcher,
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
const middleware = const middleware =
@ -103,15 +93,13 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
? [commandRunnerActions[action](message)] ? [commandRunnerActions[action](message)]
: [action] : [action]
this.use( this.use(matchSpecificError(matcher, middleware))
matchSpecificError(matcher, middleware as CommandRunnerMiddleware[])
)
return this return this
} }
onSuccess( onSuccess(
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
return this.on('ok', action, message) return this.on('ok', action, message)
@ -119,7 +107,7 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
onExitCode( onExitCode(
matcher: ExitCodeMatcher, matcher: ExitCodeMatcher,
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
const middleware = const middleware =
@ -127,14 +115,14 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
? [commandRunnerActions[action](message)] ? [commandRunnerActions[action](message)]
: [action] : [action]
this.use(matchExitCode(matcher, middleware as CommandRunnerMiddleware[])) this.use(matchExitCode(matcher, middleware))
return this return this
} }
onOutput( onOutput(
matcher: OutputMatcher, matcher: OutputMatcher,
action: CommandRunnerActionType | CommandRunnerMiddleware<S>, action: CommandRunnerActionType | CommandRunnerMiddleware,
message?: string message?: string
): this { ): this {
const middleware = const middleware =
@ -142,14 +130,14 @@ export class CommandRunner<S = unknown> extends CommandRunnerBase<S> {
? [commandRunnerActions[action](message)] ? [commandRunnerActions[action](message)]
: [action] : [action]
this.use(matchOutput(matcher, middleware as CommandRunnerMiddleware[])) this.use(matchOutput(matcher, middleware))
return this return this
} }
} }
export const createCommandRunner = <S = unknown>( export const createCommandRunner = (
commandLine: string, commandLine: string,
args: string[] = [], args: string[] = [],
options: CommandRunnerOptions = {} options: CommandRunnerOptions = {}
): CommandRunner<S> => new CommandRunner(commandLine, args, options, exec.exec) ): CommandRunner => new CommandRunner(commandLine, args, options, exec.exec)

View File

@ -8,9 +8,7 @@ import {
} from './types' } from './types'
export const promisifyCommandRunnerMiddleware = export const promisifyCommandRunnerMiddleware =
( (middleware: CommandRunnerMiddleware): CommandRunnerMiddlewarePromisified =>
middleware: CommandRunnerMiddleware<unknown>
): CommandRunnerMiddlewarePromisified =>
async (ctx, next) => { async (ctx, next) => {
return Promise.resolve(middleware(ctx, next)) return Promise.resolve(middleware(ctx, next))
} }
@ -36,7 +34,7 @@ export const composeCommandRunnerMiddleware =
await nextLocal() await nextLocal()
} }
export class CommandRunnerBase<S = unknown> { export class CommandRunnerBase {
private middleware: CommandRunnerMiddlewarePromisified[] = [] private middleware: CommandRunnerMiddlewarePromisified[] = []
constructor( constructor(
@ -46,12 +44,8 @@ export class CommandRunnerBase<S = unknown> {
private executor: typeof exec.exec = exec.exec private executor: typeof exec.exec = exec.exec
) {} ) {}
use(middleware: CommandRunnerMiddleware<S>): this { use(middleware: CommandRunnerMiddleware): this {
this.middleware.push( this.middleware.push(promisifyCommandRunnerMiddleware(middleware))
promisifyCommandRunnerMiddleware(
middleware as CommandRunnerMiddleware<unknown>
)
)
return this return this
} }
@ -64,21 +58,20 @@ export class CommandRunnerBase<S = unknown> {
/* overrides options for this specific execution if not undefined */ /* overrides options for this specific execution if not undefined */
options?: CommandRunnerOptions options?: CommandRunnerOptions
): Promise<CommandRunnerContext<S>> { ): Promise<CommandRunnerContext> {
const requiredOptions: exec.ExecOptions = { const requiredOptions: exec.ExecOptions = {
ignoreReturnCode: true, ignoreReturnCode: true,
failOnStdErr: false failOnStdErr: false
} }
const context: CommandRunnerContext<S> = { const context: CommandRunnerContext = {
commandLine: commandLine ?? this.commandLine, commandLine: commandLine ?? this.commandLine,
args: args ?? this.args, args: args ?? this.args,
options: {...(options ?? this.options), ...requiredOptions}, options: {...(options ?? this.options), ...requiredOptions},
stdout: null, stdout: null,
stderr: null, stderr: null,
execerr: null, execerr: null,
exitCode: null, exitCode: null
state: null
} }
try { try {

View File

@ -2,7 +2,7 @@ import * as exec from '@actions/exec'
/* CommandRunner core */ /* CommandRunner core */
export interface CommandRunnerContext<S = unknown> { export interface CommandRunnerContext {
/* Inputs with which command was executed */ /* Inputs with which command was executed */
commandLine: string commandLine: string
args: string[] args: string[]
@ -13,9 +13,6 @@ export interface CommandRunnerContext<S = unknown> {
stderr: string | null stderr: string | null
stdout: string | null stdout: string | null
exitCode: number | null exitCode: number | null
/* Arbitrary state that can be change during middleware execution if needed */
state: S | null
} }
/* Middlewares as used internally in CommandRunner */ /* Middlewares as used internally in CommandRunner */
@ -25,8 +22,8 @@ export type CommandRunnerMiddlewarePromisified = (
) => Promise<void> ) => Promise<void>
/* Middlewares as used by the user */ /* Middlewares as used by the user */
export type CommandRunnerMiddleware<S = unknown> = ( export type CommandRunnerMiddleware = (
ctx: CommandRunnerContext<S>, ctx: CommandRunnerContext,
next: () => Promise<void> next: () => Promise<void>
) => void | Promise<void> ) => void | Promise<void>