Skip to content

Commit 0a4e62c

Browse files
authored
chore(test-project): Switch tui-tasks to TypeScript (#11926)
1 parent fc09755 commit 0a4e62c

File tree

7 files changed

+65
-56
lines changed

7 files changed

+65
-56
lines changed

tasks/test-project/codemods/models.js

Lines changed: 5 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,4 @@
1-
/* eslint-env node, es6*/
2-
3-
const post = `model Post {
1+
export const post = `model Post {
42
id Int @id @default(autoincrement())
53
title String
64
body String
@@ -9,15 +7,15 @@ const post = `model Post {
97
createdAt DateTime @default(now())
108
}`
119

12-
const contact = `model Contact {
10+
export const contact = `model Contact {
1311
id Int @id @default(autoincrement())
1412
name String
1513
email String
1614
message String
1715
createdAt DateTime @default(now())
1816
}`
1917

20-
const user = `model User {
18+
export const user = `model User {
2119
id Int @id @default(autoincrement())
2220
email String @unique
2321
hashedPassword String
@@ -29,7 +27,7 @@ const user = `model User {
2927
posts Post[]
3028
}`
3129

32-
const produce = `model Produce {
30+
export const produce = `model Produce {
3331
id String @id @default(cuid())
3432
name String @unique
3533
quantity Int
@@ -48,11 +46,9 @@ const produce = `model Produce {
4846
stallId String
4947
}`
5048

51-
const stall = `model Stall {
49+
export const stall = `model Stall {
5250
id String @id @default(cuid())
5351
name String
5452
stallNumber String @unique
5553
produce Produce[]
5654
}`
57-
58-
module.exports = { post, contact, user, produce, stall }

tasks/test-project/rebuild-fragments-test-project-fixture.ts

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ import {
1515
copyFrameworkPackages,
1616
} from './frameworkLinking'
1717
import { webTasks, apiTasks, fragmentsTasks } from './tui-tasks'
18-
import { isAwaitable } from './typing'
18+
import { isAwaitable, isTuiError } from './typing'
1919
import type { TuiTaskDef } from './typing'
2020
import {
2121
getExecaOptions as utilGetExecaOptions,
@@ -140,13 +140,16 @@ async function tuiTask({ step, title, content, task, parent }: TuiTaskDef) {
140140
'stdout:\n' + e.stdout + '\n\n' + 'stderr:\n' + e.stderr,
141141
)
142142
} else {
143+
const message = isTuiError(e) ? e.message : ''
144+
143145
tui.displayError(
144146
'Failed ' + title.toLowerCase().replace('...', ''),
145-
e.message,
147+
message || '',
146148
)
147149
}
148150

149-
process.exit(e.exitCode)
151+
const exitCode = isTuiError(e) ? e.exitCode : undefined
152+
process.exit(exitCode)
150153
}
151154

152155
if (isAwaitable(promise)) {
@@ -197,11 +200,8 @@ async function tuiTask({ step, title, content, task, parent }: TuiTaskDef) {
197200
/**
198201
* Function that returns a string to show when skipping the task, or just
199202
* true|false to indicate whether the task should be skipped or not.
200-
*
201-
* @param {string} startStep
202-
* @param {string} currentStep
203203
*/
204-
function skipFn(startStep, currentStep) {
204+
function skipFn(startStep: string, currentStep: string) {
205205
const startStepNrs = startStep.split('.').map((s) => parseInt(s, 10))
206206
const currentStepNrs = currentStep.split('.').map((s) => parseInt(s, 10))
207207

tasks/test-project/rebuild-test-project-fixture.ts

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ import {
1515
copyFrameworkPackages,
1616
} from './frameworkLinking'
1717
import { webTasks, apiTasks } from './tui-tasks'
18-
import { isAwaitable } from './typing'
18+
import { isAwaitable, isTuiError } from './typing'
1919
import type { TuiTaskDef } from './typing'
2020
import {
2121
getExecaOptions as utilGetExecaOptions,
@@ -140,13 +140,16 @@ async function tuiTask({ step, title, content, task, parent }: TuiTaskDef) {
140140
'stdout:\n' + e.stdout + '\n\n' + 'stderr:\n' + e.stderr,
141141
)
142142
} else {
143+
const message = isTuiError(e) ? e.message : ''
144+
143145
tui.displayError(
144146
'Failed ' + title.toLowerCase().replace('...', ''),
145-
e.message,
147+
message || '',
146148
)
147149
}
148150

149-
process.exit(e.exitCode)
151+
const exitCode = isTuiError(e) ? e.exitCode : undefined
152+
process.exit(exitCode)
150153
}
151154

152155
if (isAwaitable(promise)) {
@@ -197,11 +200,8 @@ async function tuiTask({ step, title, content, task, parent }: TuiTaskDef) {
197200
/**
198201
* Function that returns a string to show when skipping the task, or just
199202
* true|false to indicate whether the task should be skipped or not.
200-
*
201-
* @param {string} startStep
202-
* @param {string} currentStep
203203
*/
204-
function skipFn(startStep, currentStep) {
204+
function skipFn(startStep: string, currentStep: string) {
205205
const startStepNrs = startStep.split('.').map((s) => parseInt(s, 10))
206206
const currentStepNrs = currentStep.split('.').map((s) => parseInt(s, 10))
207207

tasks/test-project/tasks.js

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -388,7 +388,6 @@ async function apiTasks(outputPath, { verbose, linkWithLatestFwBuild }) {
388388
await execa(
389389
'yarn rw g dbAuth --no-webauthn --username-label=username --password-label=password',
390390
[],
391-
execaOptions,
392391
)
393392

394393
// update directive in contacts.sdl.ts

tasks/test-project/tui-tasks.js renamed to tasks/test-project/tui-tasks.ts

Lines changed: 30 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,11 @@
11
/* eslint-env node, es2021*/
2-
//@ts-check
3-
const fs = require('fs')
4-
const path = require('path')
2+
3+
import fs from 'node:fs'
4+
import path from 'node:path'
5+
6+
import type { Options as ExecaOptions, ExecaChildProcess } from 'execa'
7+
8+
import type { TuiTaskList } from './typing.js'
59

610
const {
711
getExecaOptions: utilGetExecaOptions,
@@ -10,18 +14,17 @@ const {
1014
exec,
1115
} = require('./util')
1216

13-
/** @type {(string) => import('execa').Options} */
14-
function getExecaOptions(cwd) {
17+
function getExecaOptions(cwd: string): ExecaOptions {
1518
return { ...utilGetExecaOptions(cwd), stdio: 'pipe' }
1619
}
1720

1821
// This variable gets used in other functions
1922
// and is set when webTasks or apiTasks are called
20-
let OUTPUT_PATH
23+
let OUTPUT_PATH: string
2124

2225
const RW_FRAMEWORK_PATH = path.join(__dirname, '../../')
2326

24-
function fullPath(name, { addExtension } = { addExtension: true }) {
27+
function fullPath(name: string, { addExtension } = { addExtension: true }) {
2528
if (addExtension) {
2629
if (name.startsWith('api')) {
2730
name += '.ts'
@@ -34,7 +37,7 @@ function fullPath(name, { addExtension } = { addExtension: true }) {
3437
}
3538

3639
// TODO: Import from ./util.js when everything is using @rwjs/tui
37-
async function applyCodemod(codemod, target) {
40+
async function applyCodemod(codemod: string, target: string) {
3841
const args = [
3942
'--fail-on-error',
4043
'-t',
@@ -56,14 +59,14 @@ async function applyCodemod(codemod, target) {
5659
}
5760

5861
/**
59-
* @param {string} cmd The command to run
60-
* @returns {((positionalArguments: string | string[]) => import('execa').ExecaChildProcess<string>)
61-
* & (() => import('execa').ExecaChildProcess<string>)}
62+
* @param cmd The command to run
6263
*/
63-
const createBuilder = (cmd) => {
64+
function createBuilder(cmd: string) {
6465
const execaOptions = getExecaOptions(OUTPUT_PATH)
6566

66-
return function (positionalArguments) {
67+
return function (
68+
positionalArguments?: string | string[],
69+
): ExecaChildProcess<string> {
6770
const subprocess = exec(
6871
cmd,
6972
Array.isArray(positionalArguments)
@@ -76,16 +79,18 @@ const createBuilder = (cmd) => {
7679
}
7780
}
7881

79-
async function webTasks(outputPath, { linkWithLatestFwBuild }) {
82+
export async function webTasks(
83+
outputPath: string,
84+
{ linkWithLatestFwBuild }: { linkWithLatestFwBuild: boolean },
85+
) {
8086
OUTPUT_PATH = outputPath
8187

8288
const execaOptions = getExecaOptions(outputPath)
8389

8490
const createPages = async () => {
8591
const createPage = createBuilder('yarn redwood g page')
8692

87-
/** @type import('./typing').TuiTaskList */
88-
const tuiTaskList = [
93+
const tuiTaskList: TuiTaskList = [
8994
{
9095
title: 'Creating home page',
9196
task: async () => {
@@ -317,8 +322,7 @@ async function webTasks(outputPath, { linkWithLatestFwBuild }) {
317322
)
318323
}
319324

320-
/** @type import('./typing').TuiTaskList */
321-
const tuiTaskList = [
325+
const tuiTaskList: TuiTaskList = [
322326
{
323327
title: 'Creating pages',
324328
task: () => createPages(),
@@ -389,15 +393,18 @@ async function webTasks(outputPath, { linkWithLatestFwBuild }) {
389393
return tuiTaskList
390394
}
391395

392-
async function addModel(schema) {
396+
async function addModel(schema: string) {
393397
const path = `${OUTPUT_PATH}/api/db/schema.prisma`
394398

395399
const current = fs.readFileSync(path, 'utf-8')
396400

397401
fs.writeFileSync(path, `${current.trim()}\n\n${schema}\n`)
398402
}
399403

400-
async function apiTasks(outputPath, { linkWithLatestFwBuild }) {
404+
export async function apiTasks(
405+
outputPath: string,
406+
{ linkWithLatestFwBuild }: { linkWithLatestFwBuild: boolean },
407+
) {
401408
OUTPUT_PATH = outputPath
402409

403410
const execaOptions = getExecaOptions(outputPath)
@@ -714,8 +721,7 @@ export default DoublePage`
714721

715722
const generateScaffold = createBuilder('yarn rw g scaffold')
716723

717-
/** @type import('./typing').TuiTaskList */
718-
const tuiTaskList = [
724+
const tuiTaskList: TuiTaskList = [
719725
{
720726
title: 'Adding post and user model to prisma',
721727
task: async () => {
@@ -917,11 +923,10 @@ export default DoublePage`
917923
* Tasks to add GraphQL Fragments support to the test-project, and some queries
918924
* to test fragments
919925
*/
920-
async function fragmentsTasks(outputPath) {
926+
export async function fragmentsTasks(outputPath: string) {
921927
OUTPUT_PATH = outputPath
922928

923-
/** @type import('./typing').TuiTaskList */
924-
const tuiTaskList = [
929+
const tuiTaskList: TuiTaskList = [
925930
{
926931
title: 'Enable fragments',
927932
task: async () => {
@@ -1029,9 +1034,3 @@ async function fragmentsTasks(outputPath) {
10291034

10301035
return tuiTaskList
10311036
}
1032-
1033-
module.exports = {
1034-
apiTasks,
1035-
webTasks,
1036-
fragmentsTasks,
1037-
}

tasks/test-project/typing.ts

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,14 @@ export interface TuiTaskDef {
1616
task: () => Promise<unknown> | void
1717
}
1818

19+
interface TuiTaskListItem {
20+
title: string
21+
enabled?: boolean | (() => boolean)
22+
task: () => Promise<unknown> | void
23+
}
24+
25+
export type TuiTaskList = TuiTaskListItem[]
26+
1927
export function isAwaitable(promise: unknown): promise is Promise<unknown> {
2028
return (
2129
!!promise &&
@@ -24,3 +32,9 @@ export function isAwaitable(promise: unknown): promise is Promise<unknown> {
2432
typeof promise.then === 'function'
2533
)
2634
}
35+
36+
export function isTuiError(
37+
error: unknown,
38+
): error is { message?: string; exitCode?: number } {
39+
return error instanceof Object
40+
}

tasks/tsconfig.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
"extends": "../tsconfig.compilerOption.json",
33
"compilerOptions": {
44
"moduleResolution": "NodeNext",
5-
"module": "NodeNext"
5+
"module": "NodeNext",
6+
"allowJs": true
67
}
78
}

0 commit comments

Comments
 (0)