blux-start 1.0.0 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/bin/index.js CHANGED
@@ -1,9 +1,12 @@
1
1
  #!/usr/bin/env node
2
2
 
3
3
  import { Command } from 'commander';
4
+ import { input } from '@inquirer/prompts'
5
+
4
6
  import chalk from 'chalk';
5
7
  import fs from 'fs-extra';
6
8
  import path from 'path';
9
+ import { spawn } from 'child_process'
7
10
 
8
11
  const program = new Command();
9
12
 
@@ -12,6 +15,7 @@ program
12
15
  .description('A simple CLI to scaffold a TypeScript boilerplate project for blu projects')
13
16
  .version('1.0.0');
14
17
 
18
+
15
19
  program
16
20
  .command('init')
17
21
  .argument('<project-name>', 'Name of the project directory')
@@ -280,14 +284,44 @@ export async function DbConnect(){
280
284
 
281
285
  // 5. Success Message
282
286
  console.log(chalk.green(`✨ Successfully scaffolded ${chalk.bold(projectName)}!`));
283
- console.log('\nNext steps:');
284
- console.log(chalk.cyan(` cd ${projectName}`));
285
- console.log(chalk.cyan(' npm install'));
286
- console.log(chalk.cyan(' npm run dev\n'));
287
287
 
288
+ // Vite ?
289
+
290
+ const vite = await input({
291
+ message:'Would you like create a client-side application ?: (y/n)',
292
+ required:false
293
+ })
294
+
295
+ if(vite === 'y'){
296
+ console.log(chalk.blue('\nšŸš€ Kicking off Vite process...\n'));
297
+ const viteProcess = spawn('npm', ['create', 'vite@latest'], {
298
+ cwd: process.cwd(),
299
+ stdio: 'inherit',
300
+ shell: true
301
+ });
302
+
303
+ viteProcess.on('close', (code) => {
304
+ if (code === 0) {
305
+ console.log(chalk.green('\n✨ Client application successfully scaffolded with Vite!'));
306
+ } else {
307
+ console.log(chalk.red(`\nVite scaffolding exited with code ${code}`));
308
+ }
309
+ });
310
+ }
311
+ else {
312
+ console.log('\nNext steps:');
313
+ console.log(chalk.cyan(` cd ${projectName}`));
314
+ console.log(chalk.cyan(' npm install'));
315
+ console.log(chalk.cyan(' npm run dev\n'));
316
+ }
288
317
  } catch (err) {
289
- console.error(chalk.red('āŒ Something went wrong during generation:'), err);
318
+ if(err.message){
319
+ console.error(chalk.red(err.message))
320
+ }{
321
+ console.error(chalk.red('āŒ Something went wrong during generation:'), err);
322
+ }
290
323
  }
291
- });
324
+ })
325
+
292
326
 
293
327
  program.parse(process.argv);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "blux-start",
3
- "version": "1.0.0",
3
+ "version": "1.2.0",
4
4
  "description": "",
5
5
  "license": "ISC",
6
6
  "author": "Xavier",
@@ -13,9 +13,11 @@
13
13
  "test": "echo \"Error: no test specified\" && exit 1"
14
14
  },
15
15
  "dependencies": {
16
+ "@inquirer/prompts": "^8.5.2",
16
17
  "chalk": "^5.6.2",
17
18
  "commander": "^15.0.0",
18
19
  "fs-extra": "^11.3.5",
19
- "prompts": "^2.4.2"
20
+ "prompts": "^2.4.2",
21
+ "vite": "^8.0.16"
20
22
  }
21
23
  }
package/readme.md ADDED
@@ -0,0 +1,27 @@
1
+ # blux-start
2
+
3
+ A zero-configuration CLI boilerplate generator to kickstart Node.js applications with a production-ready stack.
4
+
5
+ ## ✨ Features
6
+
7
+ * **TypeScript** - Fully configured compiler and path aliases
8
+ * **Express** - Fast, unopinionated, minimalist web framework
9
+ * **MSSQL** - Pre-configured Microsoft SQL Server database integration
10
+ * **Structure** - Organized folder layout for scalable architecture
11
+
12
+ ## šŸš€ Quick Start
13
+
14
+ You can generate a new project instantly without installing the package globally. Run the following command in your terminal:
15
+
16
+ ```bash
17
+ npx blux-start@latest init <projectName>
18
+ ```
19
+
20
+ Replace `<projectName>` with the actual name of your project folder.
21
+
22
+ ## šŸ“‹ Prerequisites
23
+
24
+ Before running the boilerplate, ensure you have the following installed on your machine:
25
+
26
+ * **Node.js** (v18.0.0 or higher recommended)
27
+ * **npm** (v9.0.0 or higher)
@@ -0,0 +1,50 @@
1
+
2
+ import { DbConnect } from './db/db.ts'
3
+ import createError from 'http-errors';
4
+ import express from 'express';
5
+ import path from 'path';
6
+ import { fileURLToPath } from 'url';
7
+ import cookieParser from 'cookie-parser';
8
+ import logger from 'morgan';
9
+ import cors from 'cors'
10
+
11
+ import indexRouter from './routes/index.ts';
12
+
13
+ const __dirname = path.dirname(fileURLToPath(import.meta.url));
14
+ const app = express();
15
+
16
+ // view engine setup
17
+ // app.set('views', path.join(__dirname, 'views'));
18
+ // app.set('view engine', 'html');
19
+
20
+ app.use(cors({
21
+ origin:"localhost:5173" // local reactapp
22
+ }))
23
+
24
+ app.use(logger('dev'));
25
+ app.use(express.json());
26
+ app.use(express.urlencoded({ extended: false }));
27
+ app.use(cookieParser());
28
+ app.use(express.static(path.join(__dirname, 'public')));
29
+
30
+ app.use('/', indexRouter);
31
+
32
+ // catch 404 and forward to error handler
33
+ app.use(function(req, res, next) {
34
+ next(createError(404));
35
+ });
36
+
37
+ // setup connection DbConnect()
38
+
39
+ // error handler
40
+ app.use((err: { message: string; status?: number }, req: express.Request, res: express.Response, _next: express.NextFunction) => {
41
+ res.locals.message = err.message;
42
+ res.locals.error = req.app.get('env') === 'development' ? err : {};
43
+
44
+ res.status(err.status || 500);
45
+ });
46
+
47
+ export default app;
48
+
49
+
50
+
@@ -0,0 +1,65 @@
1
+
2
+ import app from '../app.ts';
3
+ import debugLib from 'debug';
4
+ import http from 'http';
5
+
6
+ const debug = debugLib('site:server');
7
+
8
+ const port = normalizePort(process.env.PORT || '3000');
9
+ app.set('port', port);
10
+
11
+ const server = http.createServer(app);
12
+
13
+ server.listen(port);
14
+ server.on('error', onError);
15
+ server.on('listening', onListening);
16
+
17
+
18
+ console.log('Listening on port: 3000');
19
+
20
+
21
+ function normalizePort(val) {
22
+ const port = parseInt(val, 10);
23
+
24
+ if (isNaN(port)) {
25
+ return val;
26
+ }
27
+
28
+ if (port >= 0) {
29
+ return port;
30
+ }
31
+
32
+ return false;
33
+ }
34
+
35
+ function onError(error) {
36
+ if (error.syscall !== 'listen') {
37
+ throw error;
38
+ }
39
+
40
+ const bind = typeof port === 'string'
41
+ ? 'Pipe ' + port
42
+ : 'Port ' + port;
43
+
44
+ switch (error.code) {
45
+ case 'EACCES':
46
+ console.error(bind + ' requires elevated privileges');
47
+ process.exit(1);
48
+ break;
49
+ case 'EADDRINUSE':
50
+ console.error(bind + ' is already in use');
51
+ process.exit(1);
52
+ break;
53
+ default:
54
+ throw error;
55
+ }
56
+ }
57
+
58
+ function onListening() {
59
+ const addr = server.address();
60
+ const bind = typeof addr === 'string'
61
+ ? 'pipe ' + addr
62
+ : 'port ' + addr.port;
63
+ debug('Listening on ' + bind);
64
+ }
65
+
@@ -0,0 +1,13 @@
1
+
2
+ import sql from 'mssql'
3
+ import dotenv from 'dotenv'
4
+
5
+ export async function DbConnect(){
6
+ try {
7
+ const conn = await sql.connect('Server=dbhost,port;Database=dbname;User Id=dbuser;Password=$dbpass;Encrypt=true')
8
+ console.log('DB Con Status: ',conn.healthy)
9
+ } catch (err) {
10
+ console.log(err)
11
+ }
12
+ }
13
+
@@ -0,0 +1,32 @@
1
+ {
2
+ "name": "testthis",
3
+ "version": "1.0.0",
4
+ "description": "Backend generated by xtech",
5
+ "main": "./bin/www",
6
+ "type": "module",
7
+ "scripts": {
8
+ "build": "tsc",
9
+ "start": "node ./bin/www",
10
+ "dev": "tsc --watch"
11
+ },
12
+ "dependencies": {
13
+ "cookie-parser": "~1.4.4",
14
+ "cors": "^2.8.6",
15
+ "debug": "~2.6.9",
16
+ "dotenv": "^17.4.2",
17
+ "express": "~4.16.1",
18
+ "http-errors": "~1.6.3",
19
+ "morgan": "~1.9.1",
20
+ "nodemon": "^3.1.14",
21
+ "mssql": "^12.5.5"
22
+ },
23
+ "devDependencies": {
24
+ "typescript": "^6.0.3",
25
+ "@types/node": "^25.9.3",
26
+ "tsx": "^4.22.4",
27
+ "@types/cookie-parser": "^1.4.10",
28
+ "@types/cors": "^2.8.19",
29
+ "@types/express": "^5.0.6",
30
+ "@types/morgan": "^1.9.10"
31
+ }
32
+ }
@@ -0,0 +1,14 @@
1
+
2
+ import { Router } from 'express';
3
+ import type { Request, Response, NextFunction } from 'express';
4
+
5
+ const router = Router();
6
+
7
+ router.get('/', (_req: Request, _res: Response, _next: NextFunction) => {
8
+ _res.json({
9
+ message:"HELLO FROM SERVER"
10
+ })
11
+ });
12
+
13
+ export default router;
14
+
@@ -0,0 +1,24 @@
1
+ {
2
+ "compilerOptions": {
3
+ "module": "nodenext",
4
+ "target": "esnext",
5
+ "types": [],
6
+ "sourceMap": true,
7
+ "declaration": true,
8
+ "declarationMap": true,
9
+ "noUncheckedIndexedAccess": true,
10
+ "exactOptionalPropertyTypes": true,
11
+ "strict": true,
12
+ "jsx": "react-jsx",
13
+ "verbatimModuleSyntax": true,
14
+ "isolatedModules": true,
15
+ "noUncheckedSideEffectImports": true,
16
+ "moduleDetection": "force",
17
+ "skipLibCheck": true,
18
+ "rewriteRelativeImportExtensions": true,
19
+ "allowImportingTsExtensions": true
20
+ },
21
+ "include": [
22
+ "src/**/*"
23
+ ]
24
+ }
@@ -0,0 +1,73 @@
1
+ # React + TypeScript + Vite
2
+
3
+ This template provides a minimal setup to get React working in Vite with HMR and some ESLint rules.
4
+
5
+ Currently, two official plugins are available:
6
+
7
+ - [@vitejs/plugin-react](https://github.com/vitejs/vite-plugin-react/blob/main/packages/plugin-react) uses [Oxc](https://oxc.rs)
8
+ - [@vitejs/plugin-react-swc](https://github.com/vitejs/vite-plugin-react/blob/main/packages/plugin-react-swc) uses [SWC](https://swc.rs/)
9
+
10
+ ## React Compiler
11
+
12
+ The React Compiler is not enabled on this template because of its impact on dev & build performances. To add it, see [this documentation](https://react.dev/learn/react-compiler/installation).
13
+
14
+ ## Expanding the ESLint configuration
15
+
16
+ If you are developing a production application, we recommend updating the configuration to enable type-aware lint rules:
17
+
18
+ ```js
19
+ export default defineConfig([
20
+ globalIgnores(['dist']),
21
+ {
22
+ files: ['**/*.{ts,tsx}'],
23
+ extends: [
24
+ // Other configs...
25
+
26
+ // Remove tseslint.configs.recommended and replace with this
27
+ tseslint.configs.recommendedTypeChecked,
28
+ // Alternatively, use this for stricter rules
29
+ tseslint.configs.strictTypeChecked,
30
+ // Optionally, add this for stylistic rules
31
+ tseslint.configs.stylisticTypeChecked,
32
+
33
+ // Other configs...
34
+ ],
35
+ languageOptions: {
36
+ parserOptions: {
37
+ project: ['./tsconfig.node.json', './tsconfig.app.json'],
38
+ tsconfigRootDir: import.meta.dirname,
39
+ },
40
+ // other options...
41
+ },
42
+ },
43
+ ])
44
+ ```
45
+
46
+ You can also install [eslint-plugin-react-x](https://github.com/Rel1cx/eslint-react/tree/main/packages/plugins/eslint-plugin-react-x) and [eslint-plugin-react-dom](https://github.com/Rel1cx/eslint-react/tree/main/packages/plugins/eslint-plugin-react-dom) for React-specific lint rules:
47
+
48
+ ```js
49
+ // eslint.config.js
50
+ import reactX from 'eslint-plugin-react-x'
51
+ import reactDom from 'eslint-plugin-react-dom'
52
+
53
+ export default defineConfig([
54
+ globalIgnores(['dist']),
55
+ {
56
+ files: ['**/*.{ts,tsx}'],
57
+ extends: [
58
+ // Other configs...
59
+ // Enable lint rules for React
60
+ reactX.configs['recommended-typescript'],
61
+ // Enable lint rules for React DOM
62
+ reactDom.configs.recommended,
63
+ ],
64
+ languageOptions: {
65
+ parserOptions: {
66
+ project: ['./tsconfig.node.json', './tsconfig.app.json'],
67
+ tsconfigRootDir: import.meta.dirname,
68
+ },
69
+ // other options...
70
+ },
71
+ },
72
+ ])
73
+ ```
@@ -0,0 +1,22 @@
1
+ import js from '@eslint/js'
2
+ import globals from 'globals'
3
+ import reactHooks from 'eslint-plugin-react-hooks'
4
+ import reactRefresh from 'eslint-plugin-react-refresh'
5
+ import tseslint from 'typescript-eslint'
6
+ import { defineConfig, globalIgnores } from 'eslint/config'
7
+
8
+ export default defineConfig([
9
+ globalIgnores(['dist']),
10
+ {
11
+ files: ['**/*.{ts,tsx}'],
12
+ extends: [
13
+ js.configs.recommended,
14
+ tseslint.configs.recommended,
15
+ reactHooks.configs.flat.recommended,
16
+ reactRefresh.configs.vite,
17
+ ],
18
+ languageOptions: {
19
+ globals: globals.browser,
20
+ },
21
+ },
22
+ ])
@@ -0,0 +1,13 @@
1
+ <!doctype html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8" />
5
+ <link rel="icon" type="image/svg+xml" href="/favicon.svg" />
6
+ <meta name="viewport" content="width=device-width, initial-scale=1.0" />
7
+ <title>vite-project</title>
8
+ </head>
9
+ <body>
10
+ <div id="root"></div>
11
+ <script type="module" src="/src/main.tsx"></script>
12
+ </body>
13
+ </html>