From bed31c1f4995bbf7d8d0a483f562788172e29919 Mon Sep 17 00:00:00 2001 From: "Tofix.js" <73693639+Tofix26@users.noreply.github.com> Date: Tue, 13 Sep 2022 06:35:02 +0200 Subject: [PATCH] feat!: re-write to TypeScript Co-authored-by: Evo <85353424+EvolutionX-10@users.noreply.github.com> --- .prettierignore | 3 +- package-lock.json | 87 ++++++++----------- package.json | 11 ++- src/commands/{extra.js => extra.ts} | 3 +- src/commands/{help.js => help.ts} | 11 ++- src/commands/{init.js => init.ts} | 82 ++++++++--------- src/commands/{plugins.js => plugins.ts} | 14 +-- src/{index.js => index.ts} | 0 src/prompts/{extra.js => extra.ts} | 4 +- src/prompts/{init.js => init.ts} | 27 +++--- src/prompts/{plugin.js => plugin.ts} | 28 +++--- src/utilities/{create.js => create.ts} | 30 ++++--- src/utilities/{edits.js => edits.ts} | 38 ++++---- src/utilities/{fromCwd.js => fromCwd.ts} | 5 +- src/utilities/{getLang.js => getLang.ts} | 4 +- src/utilities/{install.js => install.ts} | 35 ++++---- src/utilities/{npm.js => npm.ts} | 0 src/utilities/types.ts | 1 + src/utilities/{version.js => version.ts} | 0 .../extra/Dockerfile.JS.sern | 0 .../extra/Dockerfile.TS.sern | 0 tsconfig.json | 25 +++--- 22 files changed, 193 insertions(+), 215 deletions(-) rename src/commands/{extra.js => extra.ts} (86%) rename src/commands/{help.js => help.ts} (62%) rename src/commands/{init.js => init.ts} (67%) rename src/commands/{plugins.js => plugins.ts} (80%) rename src/{index.js => index.ts} (100%) rename src/prompts/{extra.js => extra.ts} (80%) rename src/prompts/{init.js => init.ts} (79%) rename src/prompts/{plugin.js => plugin.ts} (55%) rename src/utilities/{create.js => create.ts} (59%) rename src/utilities/{edits.js => edits.ts} (70%) rename src/utilities/{fromCwd.js => fromCwd.ts} (52%) rename src/utilities/{getLang.js => getLang.ts} (80%) rename src/utilities/{install.js => install.ts} (74%) rename src/utilities/{npm.js => npm.ts} (100%) create mode 100644 src/utilities/types.ts rename src/utilities/{version.js => version.ts} (100%) rename {src/templates => templates}/extra/Dockerfile.JS.sern (100%) rename {src/templates => templates}/extra/Dockerfile.TS.sern (100%) diff --git a/.prettierignore b/.prettierignore index ec8174d..ea1bc72 100644 --- a/.prettierignore +++ b/.prettierignore @@ -1,2 +1,3 @@ .github/ -CHANGELOG.md \ No newline at end of file +CHANGELOG.md +dist/ \ No newline at end of file diff --git a/package-lock.json b/package-lock.json index 433bec1..f9766c9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -18,14 +18,15 @@ "undici": "^5.6.1" }, "bin": { - "sern": "src/index.js" + "sern": "dist/index.js" }, "devDependencies": { "@favware/npm-deprecate": "1.0.5", "@types/prompts": "2.0.14", - "prettier": "2.7.1" + "prettier": "2.7.1", + "typescript": "4.7.4" }, - "peerDependencies": { + "engines": { "node": ">= 16.10.x" } }, @@ -806,9 +807,9 @@ } }, "node_modules/lru-cache": { - "version": "7.13.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.13.1.tgz", - "integrity": "sha512-CHqbAq7NFlW3RSnoWXLJBxCWaZVBrfa9UEHId2M3AW8iEBurbqduNexEUCGc3SHc6iCYXNJCDi903LajSVAEPQ==", + "version": "7.14.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.14.0.tgz", + "integrity": "sha512-EIRtP1GrSJny0dqb50QXRUNBxHJhcpxHC++M5tD7RYbvLLn5KVWKsbyswSSqDuU15UFi3bgTQIY8nhDMeF6aDQ==", "dev": true, "engines": { "node": ">=12" @@ -1009,28 +1010,6 @@ "node": ">= 0.6" } }, - "node_modules/node": { - "version": "18.7.0", - "resolved": "https://registry.npmjs.org/node/-/node-18.7.0.tgz", - "integrity": "sha512-h5wBtW3jnRfJzAfKldQ3lp9V8EOmbS9EHg00nUlUWWVeMtX8NGyaYB3L+AnPAGNjgWSPPDHcsqJAwlysyGiZ0g==", - "hasInstallScript": true, - "peer": true, - "dependencies": { - "node-bin-setup": "^1.0.0" - }, - "bin": { - "node": "bin/node" - }, - "engines": { - "npm": ">=5.0.0" - } - }, - "node_modules/node-bin-setup": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/node-bin-setup/-/node-bin-setup-1.1.0.tgz", - "integrity": "sha512-pTeU6NgUrexiLNtd+AKwvg6cngHMvj5FZ5e2bbv2ogBSIc9yhkXSSaTScfSRZnwHIh5YFmYSYlemLWkiKD7rog==", - "peer": true - }, "node_modules/node-fetch": { "version": "2.6.7", "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", @@ -1605,10 +1584,23 @@ "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", "dev": true }, + "node_modules/typescript": { + "version": "4.7.4", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.7.4.tgz", + "integrity": "sha512-C0WQT0gezHuw6AdY1M2jxUO83Rjf0HP7Sk1DtXj6j1EwkQNZrHAg2XPWlq62oqEhYvONq5pkC2Y9oPljWToLmQ==", + "dev": true, + "bin": { + "tsc": "bin/tsc", + "tsserver": "bin/tsserver" + }, + "engines": { + "node": ">=4.2.0" + } + }, "node_modules/undici": { - "version": "5.8.0", - "resolved": "https://registry.npmjs.org/undici/-/undici-5.8.0.tgz", - "integrity": "sha512-1F7Vtcez5w/LwH2G2tGnFIihuWUlc58YidwLiCv+jR2Z50x0tNXpRRw7eOIJ+GvqCqIkg9SB7NWAJ/T9TLfv8Q==", + "version": "5.10.0", + "resolved": "https://registry.npmjs.org/undici/-/undici-5.10.0.tgz", + "integrity": "sha512-c8HsD3IbwmjjbLvoZuRI26TZic+TSEe8FPMLLOkN1AfYRhdjnKBU6yL+IwcSCbdZiX4e5t0lfMDLDCqj4Sq70g==", "engines": { "node": ">=12.18" } @@ -2263,9 +2255,9 @@ } }, "lru-cache": { - "version": "7.13.1", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.13.1.tgz", - "integrity": "sha512-CHqbAq7NFlW3RSnoWXLJBxCWaZVBrfa9UEHId2M3AW8iEBurbqduNexEUCGc3SHc6iCYXNJCDi903LajSVAEPQ==", + "version": "7.14.0", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-7.14.0.tgz", + "integrity": "sha512-EIRtP1GrSJny0dqb50QXRUNBxHJhcpxHC++M5tD7RYbvLLn5KVWKsbyswSSqDuU15UFi3bgTQIY8nhDMeF6aDQ==", "dev": true }, "make-fetch-happen": { @@ -2416,21 +2408,6 @@ "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", "dev": true }, - "node": { - "version": "18.7.0", - "resolved": "https://registry.npmjs.org/node/-/node-18.7.0.tgz", - "integrity": "sha512-h5wBtW3jnRfJzAfKldQ3lp9V8EOmbS9EHg00nUlUWWVeMtX8NGyaYB3L+AnPAGNjgWSPPDHcsqJAwlysyGiZ0g==", - "peer": true, - "requires": { - "node-bin-setup": "^1.0.0" - } - }, - "node-bin-setup": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/node-bin-setup/-/node-bin-setup-1.1.0.tgz", - "integrity": "sha512-pTeU6NgUrexiLNtd+AKwvg6cngHMvj5FZ5e2bbv2ogBSIc9yhkXSSaTScfSRZnwHIh5YFmYSYlemLWkiKD7rog==", - "peer": true - }, "node-fetch": { "version": "2.6.7", "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", @@ -2824,10 +2801,16 @@ "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", "dev": true }, + "typescript": { + "version": "4.7.4", + "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.7.4.tgz", + "integrity": "sha512-C0WQT0gezHuw6AdY1M2jxUO83Rjf0HP7Sk1DtXj6j1EwkQNZrHAg2XPWlq62oqEhYvONq5pkC2Y9oPljWToLmQ==", + "dev": true + }, "undici": { - "version": "5.8.0", - "resolved": "https://registry.npmjs.org/undici/-/undici-5.8.0.tgz", - "integrity": "sha512-1F7Vtcez5w/LwH2G2tGnFIihuWUlc58YidwLiCv+jR2Z50x0tNXpRRw7eOIJ+GvqCqIkg9SB7NWAJ/T9TLfv8Q==" + "version": "5.10.0", + "resolved": "https://registry.npmjs.org/undici/-/undici-5.10.0.tgz", + "integrity": "sha512-c8HsD3IbwmjjbLvoZuRI26TZic+TSEe8FPMLLOkN1AfYRhdjnKBU6yL+IwcSCbdZiX4e5t0lfMDLDCqj4Sq70g==" }, "unique-filename": { "version": "1.1.1", diff --git a/package.json b/package.json index 5f1f9e7..438874a 100644 --- a/package.json +++ b/package.json @@ -2,15 +2,17 @@ "name": "@sern/cli", "version": "0.4.2", "description": "Official CLI for @sern/handler", - "exports": "./src/index.js", + "exports": "./dist/index.js", "bin": { - "sern": "./src/index.js" + "sern": "./dist/index.js" }, "type": "module", "scripts": { "test": "echo \"Error: no test specified\" && exit 1", "format": "prettier --check .", - "fix": "prettier --write ." + "fix": "prettier --write .", + "build": "tsc", + "watch": "tsc --watch" }, "repository": { "type": "git", @@ -41,7 +43,8 @@ "devDependencies": { "@favware/npm-deprecate": "1.0.5", "@types/prompts": "2.0.14", - "prettier": "2.7.1" + "prettier": "2.7.1", + "typescript": "4.7.4" }, "engines": { "node": ">= 16.10.x" diff --git a/src/commands/extra.js b/src/commands/extra.ts similarity index 86% rename from src/commands/extra.js rename to src/commands/extra.ts index 9eb9e8f..b2ae834 100644 --- a/src/commands/extra.js +++ b/src/commands/extra.ts @@ -1,7 +1,6 @@ -import prompts from 'prompts'; +import prompt from 'prompts'; import { extraPrompt } from '../prompts/extra.js'; import { create } from '../utilities/create.js'; -const { prompt } = prompts; export async function extra() { const extra = await prompt([extraPrompt]); diff --git a/src/commands/help.js b/src/commands/help.ts similarity index 62% rename from src/commands/help.js rename to src/commands/help.ts index ef01038..5f44b6a 100644 --- a/src/commands/help.js +++ b/src/commands/help.ts @@ -1,19 +1,18 @@ -import { cyanBright, green, yellowBright } from 'colorette'; +import { cyanBright, green, magentaBright } from 'colorette'; export function help() { - return ` + return ` ___ ___ _ __ _ __ / __|/ _ \\ '__| '_ \\ \\__ \\ __/ | | | | | |___/\\___|_| |_| |_| - + Welcome! - If you're new to ${cyanBright('sern')}, run ${yellowBright( + If you're new to ${cyanBright('sern')}, run ${magentaBright( 'sern init' )} for an interactive setup to your new bot project! ${green( `If you have any ideas, suggestions, bug reports, kindly join our support server: https://discord.gg/xzK5fUKT4r` - )} -`; + )}`; } diff --git a/src/commands/init.js b/src/commands/init.ts similarity index 67% rename from src/commands/init.js rename to src/commands/init.ts index 821c653..acbaf3e 100644 --- a/src/commands/init.js +++ b/src/commands/init.ts @@ -1,36 +1,32 @@ -import prompts from 'prompts'; -import ora from 'ora'; import { greenBright, redBright } from 'colorette'; import { execa } from 'execa'; import { findUp } from 'find-up'; +import ora from 'ora'; +import prompt from 'prompts'; import { cmds_dir, + gitInit, lang, main_dir, - gitInit, - which_manager, - skip_install_dep, name, + skip_install_dep, + which_manager, } from '../prompts/init.js'; -import { npm } from '../utilities/npm.js'; -import { cloneRepo, installDeps } from '../utilities/install.js'; -import { editDirs, editMain } from '../utilities/edits.js'; import { writeFile } from 'fs/promises'; -const { prompt } = prompts; +import { editDirs, editMain } from '../utilities/edits.js'; +import { cloneRepo, installDeps } from '../utilities/install.js'; +import { npm } from '../utilities/npm.js'; +import type { PackageManagerChoice } from '../utilities/types.js'; -/** - * @param {{ y: string; sync: string; }} flags - */ -export async function init(flags) { - let data; - let git_init; - let pm; +export async function init(flags: Flags) { + let data: PromptData; + let git_init = true; // the default; + let pm = flags.sync ? undefined : flags.y ? 'npm' : await npm(); if (flags.y) { const projectName = await prompt([name]); git_init = true; - pm = 'npm'; data = { name: projectName.name, lang: 'typescript', @@ -38,12 +34,12 @@ export async function init(flags) { cmds_dir: 'commands', }; } else if (flags.sync) { - data = await prompt([lang, main_dir, cmds_dir]); + data = (await prompt([lang, main_dir, cmds_dir])) as PromptData; } else { - data = await prompt([name, lang, main_dir, cmds_dir]); + data = (await prompt([name, lang, main_dir, cmds_dir])) as PromptData; git_init = (await prompt([gitInit])).gitinit; - pm = await npm(); } + const language = data.lang === 'javascript-esm' ? 'javascript' : data.lang; const config = { language, @@ -68,9 +64,7 @@ export async function init(flags) { if (!pkg) throw new Error('No package.json found!'); - if (pkg) { - await writeFile(pkg.replace('package.json', 'sern.config.json'), file); - } + await writeFile(pkg.replace('package.json', 'sern.config.json'), file); if (flags.sync) { console.log('Project was successfully synced!'); @@ -79,14 +73,14 @@ export async function init(flags) { git_init ? await git(data) : console.log(`Skipping git init...\n`); - let choice; + let choice: PackageManagerChoice; if (pm === 'both') { - const chosen = await prompt([which_manager]); - choice = chosen.manager; + choice = (await prompt([which_manager])).manager; } else { - const chosen = await prompt([skip_install_dep]); - choice = chosen.skip_install_dep ? pm : 'skip'; + choice = ( + (await prompt([skip_install_dep])).skip_install_dep ? pm : 'skip' + ) as PackageManagerChoice; } await installDeps(choice, data.name); @@ -97,11 +91,8 @@ export async function init(flags) { process.exit(0); } -/** - * It initializes git - * @param data - The data object that contains the name of the project. - */ -async function git(data) { +/** It initializes git */ +async function git(data: Data) { const spin = ora({ text: 'Initializing git...', spinner: 'aesthetic', @@ -122,13 +113,24 @@ async function git(data) { spin.succeed('Git initialized!'); } -/** - * Wait for a specified number of milliseconds, then return a promise that resolves to undefined. - * @param {number} ms - The number of milliseconds to wait. - * @returns A function that takes a single argument, ms, and returns a promise that resolves after ms - * milliseconds. - */ -async function wait(ms) { +/** Wait for a specified number of milliseconds, then return a promise that resolves to undefined. */ +async function wait(ms: number) { const wait = (await import('util')).promisify(setTimeout); return wait(ms); } + +interface Data { + name: string; +} + +interface Flags { + y: boolean; + sync: boolean; +} + +interface PromptData { + name: string; + lang: 'typescript' | 'javascript' | 'javascript-esm'; + main_dir: string; + cmds_dir: string; +} diff --git a/src/commands/plugins.js b/src/commands/plugins.ts similarity index 80% rename from src/commands/plugins.js rename to src/commands/plugins.ts index f7c2741..b7f0d5d 100644 --- a/src/commands/plugins.js +++ b/src/commands/plugins.ts @@ -1,19 +1,15 @@ import { pluginsQ } from '../prompts/plugin.js'; -import prompts from 'prompts'; +import prompt from 'prompts'; import { fetch } from 'undici'; import fs from 'fs'; import { greenBright } from 'colorette'; import { fromCwd } from '../utilities/fromCwd.js'; -const { prompt } = prompts; /** * Installs plugins to project */ export async function plugins() { - /** - * @type {string[]} - */ - const e = (await prompt([await pluginsQ()])).list; + const e: string[] = (await prompt([await pluginsQ()])).list; if (!e) process.exit(1); for await (const url of e) { @@ -27,11 +23,7 @@ export async function plugins() { ); } -/** - * @param {string} url - * @returns File - */ -async function download(url) { +async function download(url: string) { const data = await fetch(url, { method: 'GET' }) .then((res) => res.text()) .catch(() => null); diff --git a/src/index.js b/src/index.ts similarity index 100% rename from src/index.js rename to src/index.ts diff --git a/src/prompts/extra.js b/src/prompts/extra.ts similarity index 80% rename from src/prompts/extra.js rename to src/prompts/extra.ts index d100b73..8c21724 100644 --- a/src/prompts/extra.js +++ b/src/prompts/extra.ts @@ -1,4 +1,6 @@ -export const extraPrompt = { +import type { PromptObject } from 'prompts'; + +export const extraPrompt: PromptObject = { message: 'What extra feature do you want to add?', name: 'extra', type: 'select', diff --git a/src/prompts/init.js b/src/prompts/init.ts similarity index 79% rename from src/prompts/init.js rename to src/prompts/init.ts index e8a06f6..79b9168 100644 --- a/src/prompts/init.js +++ b/src/prompts/init.ts @@ -1,6 +1,7 @@ import { blueBright } from 'colorette'; +import type { PromptObject } from 'prompts'; -export const lang = { +export const lang: PromptObject = { message: 'What language do you want the project to be in?', name: 'lang', type: 'select', @@ -23,40 +24,37 @@ export const lang = { ], }; -export const main_dir = { +export const main_dir: PromptObject = { message: 'What is the main directory of your project?', name: 'main_dir', type: 'text', initial: 'src', }; -export const cmds_dir = { +export const cmds_dir: PromptObject = { message: 'What is the directory of your commands?', name: 'cmds_dir', type: 'text', initial: 'commands', - validate: (/** @type {string} */ dir) => + validate: (dir: string) => dir === 'src' ? 'You can not use src as a directory' : true, }; -/** - * @type {import('prompts').PromptObject} - */ -export const npmInit = { +export const npmInit: PromptObject = { name: 'npm_init', type: 'confirm', message: `Do you want ${blueBright('me')} to initialize npm?`, initial: true, }; -export const gitInit = { +export const gitInit: PromptObject = { name: 'gitinit', type: 'confirm', message: `Do you want to ${blueBright('me')} to initialize git?`, initial: true, }; -export const which_manager = { +export const which_manager: PromptObject = { message: `Which manager do you want to use?`, name: 'manager', type: 'select', @@ -80,21 +78,18 @@ export const which_manager = { ], }; -export const skip_install_dep = { +export const skip_install_dep: PromptObject = { name: 'skip_install_dep', type: 'confirm', message: `Do you want ${blueBright('me')} to install dependencies?`, initial: false, }; -/** - * @type {import('prompts').PromptObject} - */ -export const name = { +export const name: PromptObject = { message: 'What is your project name?', name: 'name', type: 'text', - validate: (/**@type {string}*/ name) => + validate: (name: string) => name.match('^(?:@[a-z0-9-*~][a-z0-9-*._~]*/)?[a-z0-9-~][a-z0-9-._~]*$') ? true : 'Invalid name', diff --git a/src/prompts/plugin.js b/src/prompts/plugin.ts similarity index 55% rename from src/prompts/plugin.js rename to src/prompts/plugin.ts index 43fb7f8..8592884 100644 --- a/src/prompts/plugin.js +++ b/src/prompts/plugin.ts @@ -1,7 +1,8 @@ +import type { Choice, PromptObject } from 'prompts'; import { fetch } from 'undici'; import { getLang } from '../utilities/getLang.js'; -function upperCase(string) { +function upperCase(string: string | null) { if (string === null) { console.error('Lang property not found!'); process.exit(0); @@ -9,24 +10,24 @@ function upperCase(string) { return string === 'typescript' ? 'TypeScript' : 'JavaScript'; } -async function gimmechoices() { +async function gimmechoices(): Promise { const lang = upperCase(await getLang().catch(() => null)); const link = `https://api.github.com/repos/sern-handler/awesome-plugins/contents/${lang}`; const resp = await fetch(link).catch(() => null); - if (!resp) return { title: 'No plugins found!', value: '', disabled: true }; + if (!resp) + return [{ title: 'No plugins found!', value: '', disabled: true }]; - const data = await resp.json(); - return data.map( - (/** @type {{ name: string; download_url: string; }} */ e) => ({ - title: e.name, - value: e.download_url, - }) - ); + const data = (await resp.json()) as Data[]; + const choices = data.map((e) => ({ + title: e.name, + value: e.download_url, + })); + return choices; } -export async function pluginsQ() { +export async function pluginsQ(): Promise { return { name: 'list', type: 'autocompleteMultiselect', @@ -35,3 +36,8 @@ export async function pluginsQ() { min: 1, }; } + +interface Data { + name: string; + download_url: string; +} diff --git a/src/utilities/create.js b/src/utilities/create.ts similarity index 59% rename from src/utilities/create.js rename to src/utilities/create.ts index 703f604..19e2aaf 100644 --- a/src/utilities/create.js +++ b/src/utilities/create.ts @@ -1,7 +1,7 @@ import { URL, fileURLToPath } from 'url'; import { resolve, dirname } from 'node:path'; import { readFile, mkdir, writeFile } from 'fs/promises'; -const root = new URL('../', import.meta.url); +const root = new URL('../../', import.meta.url); const templates = new URL('./templates/', root); const extraURL = new URL('./extra/', templates); @@ -9,13 +9,17 @@ const extraFolder = fileURLToPath(extraURL); /** * It creates a file with the name `name.lang.sern` in the `location` directory - * @param {string} name - The name of the file. - * @param {string} lang - The language you want to use. - * @param {string} location - The location of the file to be created. - * @param {boolean} no_ext - If true, the file will be created without an extension. - * @returns File + * @param name - The name of the file. + * @param lang - The language you want to use. + * @param location - The location of the file to be created. + * @param no_ext - If true, the file will be created without an extension. */ -export async function create(name, lang, location, no_ext) { +export async function create( + name: string, + lang: string, + location: string, + no_ext: boolean +) { const file = `${name}.${lang}.sern`; const target = no_ext @@ -27,10 +31,10 @@ export async function create(name, lang, location, no_ext) { /** * It reads a file from a template folder, and writes it to a target folder - * @param {string} template - The name of the file to be created. - * @param {string} target - The location of the file to be created. + * @param template - The name of the file to be created. + * @param target - The location of the file to be created. */ -async function createFile(template, target) { +async function createFile(template: string, target: string) { const location = `${extraFolder}${template}`; const file = await readFile(location, 'utf8'); @@ -40,11 +44,11 @@ async function createFile(template, target) { /** * It creates a directory recursively, then writes a file to it - * @param {string} target - The path to the file you want to write to. - * @param {string} data - The data to write to the file. + * @param target - The path to the file you want to write to. + * @param data - The data to write to the file. * @returns A promise that resolves to the result of the writeFile function. */ -async function writeFileRecursive(target, data) { +async function writeFileRecursive(target: string, data: string) { const resolvedTarget = resolve(target); const dir = dirname(resolvedTarget); diff --git a/src/utilities/edits.js b/src/utilities/edits.ts similarity index 70% rename from src/utilities/edits.js rename to src/utilities/edits.ts index cf1efc3..0ff551d 100644 --- a/src/utilities/edits.js +++ b/src/utilities/edits.ts @@ -5,13 +5,12 @@ import { fromCwd } from './fromCwd.js'; /** * It takes a string, finds the package.json file in the directory of the string, and changes the name * of the package.json file to the string. - * @param {string} name - The name of the project. - * @returns A promise. + * @param name - The name of the project. */ -export async function editMain(name) { - const pjLocation = await findUp('package.json', { +export async function editMain(name: string) { + const pjLocation = (await findUp('package.json', { cwd: fromCwd('/' + name), - }); + })) as string; const output = JSON.parse(await readFile(pjLocation, 'utf8')); if (!output) throw new Error("Can't read your package.json."); @@ -24,36 +23,35 @@ export async function editMain(name) { /** * It renames the `src` and `commands` directories, and edits the `index.ts` file to reflect the * changes - * @param {string} srcName - The name of the folder that will contain your main files. - * @param {string} cmds_dirName - The name of the directory where your commands will be stored. - * @param {string} name - The name of the folder you want to edit. - * @param {'javascript' | 'typescript'} lang - The language you want to use. - * @returns void + * @param srcName - The name of the folder that will contain your main files. + * @param cmds_dirName - The name of the directory where your commands will be stored. + * @param name - The name of the folder you want to edit. + * @param lang - The language you want to use. */ export async function editDirs( - srcName, - cmds_dirName, - name, - lang = 'typescript' + srcName: string, + cmds_dirName: string, + name: string, + lang: 'javascript' | 'typescript' | 'javascript-esm' = 'typescript' ) { - const path = await findUp('src', { + const path = (await findUp('src', { cwd: fromCwd(name), type: 'directory', - }); + })) as string; const ext = lang === 'typescript' ? 'ts' : 'js'; const newMainDir = path?.replace('src', srcName); await rename(path, newMainDir); - const cmdsPath = await findUp('commands', { + const cmdsPath = (await findUp('commands', { cwd: fromCwd(name, srcName), type: 'directory', - }); + })) as string; - const index = await findUp(`index.${ext}`, { + const index = (await findUp(`index.${ext}`, { cwd: fromCwd(name, srcName), - }); + })) as string; const newCmdsPath = cmdsPath?.replace('commands', cmds_dirName); await rename(cmdsPath, newCmdsPath); diff --git a/src/utilities/fromCwd.js b/src/utilities/fromCwd.ts similarity index 52% rename from src/utilities/fromCwd.js rename to src/utilities/fromCwd.ts index 0669e0e..86d4c8e 100644 --- a/src/utilities/fromCwd.js +++ b/src/utilities/fromCwd.ts @@ -1,8 +1,5 @@ import path from 'path'; -/** - * @param {string[]} dir - */ -export function fromCwd(...dir) { +export function fromCwd(...dir: string[]) { return path.join(...[process.cwd(), ...dir]); } diff --git a/src/utilities/getLang.js b/src/utilities/getLang.ts similarity index 80% rename from src/utilities/getLang.js rename to src/utilities/getLang.ts index 72899ba..443d8b1 100644 --- a/src/utilities/getLang.js +++ b/src/utilities/getLang.ts @@ -3,9 +3,9 @@ import { readFile } from 'node:fs/promises'; /** * It finds the sern.config.json file, reads it, and returns the language property - * @returns {Promise} The language of the project. + * @returns The language of the project. */ -export async function getLang() { +export async function getLang(): Promise<'typescript' | 'javascript'> { const sernLocation = await findUp('sern.config.json'); if (!sernLocation) throw new Error("Can't find sern.config.json"); diff --git a/src/utilities/install.js b/src/utilities/install.ts similarity index 74% rename from src/utilities/install.js rename to src/utilities/install.ts index 5ff8d06..436779d 100644 --- a/src/utilities/install.js +++ b/src/utilities/install.ts @@ -1,18 +1,18 @@ -import { execa } from 'execa'; import { redBright } from 'colorette'; -import fs from 'fs'; -import path from 'path'; -import { readFile } from 'fs/promises'; +import { execa } from 'execa'; import { findUp } from 'find-up'; +import fs from 'fs'; +import { readFile } from 'fs/promises'; import ora from 'ora'; +import path from 'path'; +import type { PackageManagerChoice } from './types'; /** * It installs dependencies from a package.json file - * @param {'skip' | 'npm' | 'yarn'} choice - The package manager to use. - * @param {string} name - The name of the project - * @returns a promise. + * @param choice - The package manager to use. + * @param name - The name of the project */ -export async function installDeps(choice, name) { +export async function installDeps(choice: PackageManagerChoice, name: string) { const pkg = await findUp('package.json', { cwd: process.cwd() + '/' + name, }); @@ -44,10 +44,10 @@ export async function installDeps(choice, name) { /** * Clone the repo, copy the files from the repo to the new project directory, and delete the repo - * @param {string} lang - The language of the template - * @param {string} name - The name of the project + * @param lang - The language of the template + * @param name - The name of the project */ -export async function cloneRepo(lang, name) { +export async function cloneRepo(lang: string, name: string) { await execa('git', [ 'clone', `https://github.com/sern-handler/templates.git`, @@ -60,13 +60,13 @@ export async function cloneRepo(lang, name) { * If the source is a directory, create the destination directory and then recursively copy the * contents of the source directory to the destination directory. If the source is not a directory, * copy the source file to the destination file - * @param {string} src - The source path. - * @param {string} dest - The destination folder where the files will be copied to. + * @param src - The source path. + * @param dest - The destination folder where the files will be copied to. */ -export function copyRecursiveSync(src, dest) { +export function copyRecursiveSync(src: string, dest: string) { const exists = fs.existsSync(src); - const stats = exists && fs.statSync(src); + const stats = (exists && fs.statSync(src)) as fs.Stats; const isDirectory = exists && stats.isDirectory(); if (isDirectory) { @@ -82,8 +82,3 @@ export function copyRecursiveSync(src, dest) { fs.copyFileSync(src, dest); } } - -// async function wait(ms) { -// const wait = (await import('util')).promisify(setTimeout); -// return wait(ms); -// } diff --git a/src/utilities/npm.js b/src/utilities/npm.ts similarity index 100% rename from src/utilities/npm.js rename to src/utilities/npm.ts diff --git a/src/utilities/types.ts b/src/utilities/types.ts new file mode 100644 index 0000000..cf7dad6 --- /dev/null +++ b/src/utilities/types.ts @@ -0,0 +1 @@ +export type PackageManagerChoice = 'skip' | 'npm' | 'yarn'; diff --git a/src/utilities/version.js b/src/utilities/version.ts similarity index 100% rename from src/utilities/version.js rename to src/utilities/version.ts diff --git a/src/templates/extra/Dockerfile.JS.sern b/templates/extra/Dockerfile.JS.sern similarity index 100% rename from src/templates/extra/Dockerfile.JS.sern rename to templates/extra/Dockerfile.JS.sern diff --git a/src/templates/extra/Dockerfile.TS.sern b/templates/extra/Dockerfile.TS.sern similarity index 100% rename from src/templates/extra/Dockerfile.TS.sern rename to templates/extra/Dockerfile.TS.sern diff --git a/tsconfig.json b/tsconfig.json index e93aaad..fb88401 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -1,17 +1,18 @@ { "compilerOptions": { - "target": "ES2022", + "target": "ESNext", "module": "ESNext", - "moduleResolution": "NodeNext", - "lib": ["es2017", "dom"], - "allowJs": true, - "checkJs": true, - "noEmit": true, - "strict": false, - "noImplicitThis": true, - "alwaysStrict": true, + "moduleResolution": "Node", + "outDir": "dist", + "rootDir": "src", + "declaration": true, + "declarationMap": true, + "strict": true, "esModuleInterop": true, - "resolveJsonModule": true - }, - "include": ["test", "src"] + "noImplicitAny": true, + "strictNullChecks": true, + "importsNotUsedAsValues": "error", + "skipLibCheck": true, + "forceConsistentCasingInFileNames": true + } }