diff --git a/packages/backend-tasks/README.md b/packages/backend-tasks/README.md index e98c997af0..f8a2009af0 100644 --- a/packages/backend-tasks/README.md +++ b/packages/backend-tasks/README.md @@ -16,6 +16,7 @@ then make use of its facilities as necessary: ```typescript import { TaskManager } from '@backstage/backend-tasks'; +import { Duration } from 'luxon'; const manager = TaskManager.fromConfig(rootConfig).forPlugin('my-plugin'); diff --git a/packages/backend-tasks/src/tasks/util.test.ts b/packages/backend-tasks/src/tasks/util.test.ts index 75fd9f3673..f74669a7f4 100644 --- a/packages/backend-tasks/src/tasks/util.test.ts +++ b/packages/backend-tasks/src/tasks/util.test.ts @@ -14,10 +14,44 @@ * limitations under the License. */ +import { Duration } from 'luxon'; import { AbortController } from 'node-abort-controller'; -import { delegateAbortController } from './util'; +import { delegateAbortController, sleep, validateId } from './util'; describe('util', () => { + describe('validateId', () => { + it.each(['a', 'a_b', 'ab123c_2'])( + 'accepts valid inputs, %p', + async input => { + expect(validateId(input)).toBeUndefined(); + }, + ); + + it.each(['', 'a!', 'A', 'a-b', 'a.b', '_a', 'a_', null, Symbol('a')])( + 'rejects invalid inputs, %p', + async input => { + expect(() => validateId(input as any)).toThrow(); + }, + ); + }); + + describe('sleep', () => { + it('finishes the wait as expected with no signal', async () => { + const ac = new AbortController(); + const start = Date.now(); + await sleep(Duration.fromObject({ seconds: 1 }), ac.signal); + expect(Date.now() - start).toBeGreaterThan(800); + }, 5_000); + + it('aborts properly on the signal', async () => { + const ac = new AbortController(); + const promise = sleep(Duration.fromObject({ seconds: 10 }), ac.signal); + ac.abort(); + await promise; + expect(true).toBe(true); + }, 1_000); + }); + describe('delegateAbortController', () => { it('inherits parent abort state', () => { const parent = new AbortController();