torch-it 2.3.0 → 2.4.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/README.md CHANGED
@@ -18,7 +18,7 @@ Well better still - try torching it 🔥🔥🔥🔥🔥🔥
18
18
 
19
19
  ## What does `torch-it` do?
20
20
 
21
- Nuke your local caches, dependencies, and Docker environment — then rebuild everything from a clean slate, **with a single command**.
21
+ Intelligently nukes your local caches, dependencies, and Docker environment depending on your framework and package manager — then rebuilds everything from a clean slate, **with a single command**.
22
22
 
23
23
  It's surprising how often this just fixes things. 🤞
24
24
 
@@ -28,7 +28,7 @@ It's surprising how often this just fixes things. 🤞
28
28
  - **Fully customizable** — specify any directories or files to delete
29
29
  - **Docker support** — removes containers, images, and volumes and rebuilds from scratch 🐳
30
30
  - **Cross-platform** — works on Windows, Linux, and macOS
31
- - **Zero-dependency** — no additional packages required
31
+ - **Zero-dependency** — lightweight and no additional packages required
32
32
 
33
33
  ## Supported Frameworks
34
34
 
@@ -43,15 +43,15 @@ React, Next.js, Vue, Vite, SvelteKit, React Native, Expo, and more.
43
43
  - **Removes build artifacts and cache directories** for common JavaScript/Node.js frameworks (e.g., `node_modules`, `dist`, `.next`, `.cache`, etc.).
44
44
  - **Removes custom directories/paths** that you define in `torchrc.json`.
45
45
  - **Cleans package manager caches** for npm, yarn, and pnpm.
46
- - **Reinstalls dependencies** using your preferred package manager (npm, yarn, or pnpm).
46
+ - **Reinstalls dependencies** using your preferred package manager (npm, yarn, or pnpm) - **skipped when `rebuild=false`**.
47
47
 
48
48
  ### Docker Operations (Only if Docker is Configured)
49
49
 
50
50
  If your project includes either a `Dockerfile`, `docker-compose.yml`, or `docker-compose.yaml`, `torch-it` will also:
51
51
 
52
52
  - **Stop and clean up Docker resources** (containers, images, volumes) if Docker is running.
53
- - **Rebuild Docker images** from scratch.
54
- - **Restart Docker services** in detached mode.
53
+ - **Rebuild Docker images** from scratch - **skipped when `rebuild=false`**.
54
+ - **Restart Docker services** in detached mode - **skipped when `rebuild=false`**.
55
55
 
56
56
  `torch-it` intelligently detects your project's configuration and only performs Docker operations when appropriate.
57
57
 
@@ -59,32 +59,47 @@ If your project includes either a `Dockerfile`, `docker-compose.yml`, or `docker
59
59
 
60
60
  ## Usage
61
61
 
62
- ### Install in your project
62
+ ### Global Installation (Recommended)
63
+
64
+ Install torch-it globally to run it from anywhere:
65
+
66
+ ```bash
67
+ npm install -g torch-it
68
+ ```
69
+
70
+ Then, in your project root,simply run:
71
+
72
+ ```bash
73
+ torch-it
74
+ ```
75
+
76
+ For per-project customisation, create a `torchrc.json` file in your project root (see Customization section below) or use command line flags (see Command Line Options section below).
77
+
78
+ ### Per-Project Installation (Alternative)
79
+
80
+ If you prefer to install torch-it per project:
63
81
 
64
82
  ```bash
65
83
  npm install torch-it --save-dev
66
84
  ```
67
85
 
68
- ### Run in npm scripts
86
+ Then run via npm scripts or npx:
69
87
 
70
- Add a script to your project's `package.json`:
88
+ Add to package.json scripts:
71
89
 
72
90
  ```json
73
91
  {
74
92
  "scripts": {
75
- "torch": "torch-it",
76
- "torch:test": "torch-it --test"
93
+ "torch": "torch-it"
77
94
  }
78
95
  }
79
96
  ```
80
97
 
81
- Then run:
82
-
83
98
  ```bash
84
99
  npm run torch
85
100
  ```
86
101
 
87
- ### Run without adding scripts
102
+ Or directly:
88
103
 
89
104
  ```bash
90
105
  npx torch-it
@@ -92,21 +107,22 @@ npx torch-it
92
107
 
93
108
  ### Dry Run (`--test`)
94
109
 
95
- Use `--test` to preview what `torch-it` would do without deleting directories, cleaning caches, installing dependencies, or changing Docker resources.
110
+ Use `--test` to preview what `torch-it` would do without deleting directories, cleaning caches, installing dependencies, or changing Docker resources. Results are saved to the `torch-it.log` file.
96
111
 
97
112
  ```bash
98
- npx torch-it --test
113
+ torch-it --test
99
114
  ```
100
115
  ---
101
116
  ## Customization
102
117
 
103
- For project-level customization (recommended), create `torchrc.json` in your project root:
118
+ For project-level customization, create a local `torchrc.json` file in your project root with the following structure:
104
119
 
105
120
  ```json
106
121
  {
107
122
  "customPaths": ["apps/web/.next", "services/api/tmp", ".turbo/cache", "coverage-final.json"],
108
123
  "protectedPaths": ["important-data/", "config/production.json"],
109
124
  "dockerMode": true,
125
+ "rebuild": true,
110
126
  "logfile": false
111
127
  }
112
128
  ```
@@ -114,14 +130,32 @@ For project-level customization (recommended), create `torchrc.json` in your pro
114
130
  - `customPaths`: Array of additional directories and files to remove during cleanup. Supports both directories and files. torch-it will remove these in the same cleanup pass as the built-in targets.
115
131
  - `protectedPaths`: Array of directories and files to skip during cleanup. These paths will be preserved even if they match built-in or custom cleanup targets.
116
132
  - `dockerMode`: Boolean flag to enable/disable Docker operations. Set to `false` to skip all Docker cleanup, rebuild, and launch steps. Defaults to `true`.
117
- - `logfile`: Boolean flag to enable or disable writing runtime output to `torch-it.log`. Set to `false` to disable file logging. Defaults to `true`.
133
+ - `rebuild`: Boolean flag to enable/disable rebuild operations. Set to `false` to skip both package manager dependency installation and Docker rebuild/launch while still performing cleanup. Defaults to `true`.
134
+ - `logfile`: Boolean flag to enable or disable writing runtime output to `torch-it.log`. Set to `true` to enable file logging. Defaults to `false`.
135
+
136
+ **Note**: The local `torchrc.json` file is completely optional. torch-it works with sensible defaults out of the box. Only create this file if you need to customize the behavior.
137
+
138
+ ## Command Line Options
139
+
140
+ You can override `torchrc.json` settings directly from the command line using flags. This is useful for one-off runs or CI/CD pipelines.
141
+
142
+ ```bash
143
+ torch-it --dockerMode=false --rebuild=false --customPaths=["temp/","logs/"]
144
+ ```
145
+
146
+ All configuration options can be overridden using `--optionName=value` syntax. For arrays and objects, use JSON syntax:
147
+
148
+ - `--customPaths=["path1","path2"]`
149
+ - `--dockerMode=false`
150
+ - `--rebuild=false`
151
+ - `--logfile=true`
118
152
 
119
- **Note**: The `torchrc.json` file is completely optional. torch-it works with sensible defaults out of the box. Only create this file if you need to customize the behavior.
153
+ Command line flags take precedence over `torchrc.json` settings.
120
154
 
121
155
 
122
156
  ## Logging
123
157
 
124
- `torch-it` outputs information to the console and writes logs to `torch-it.log` in your project root by default so you can troubleshoot any issues and see what was removed and reinstalled. If you set `logfile` to `false` in `torchrc.json`, no log file will be written.
158
+ `torch-it` outputs information to the console. By default, no log file is written. If you want to save runtime output to `torch-it.log` in your project root for troubleshooting purposes, set `logfile` to `true` in `torchrc.json`.
125
159
 
126
160
  This file should be ignored by git to avoid accidental commits. Add this to your `.gitignore`:
127
161
 
package/dist/torch-it.js CHANGED
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
- "use strict";var V=Object.create;var I=Object.defineProperty;var Q=Object.getOwnPropertyDescriptor;var Z=Object.getOwnPropertyNames;var ee=Object.getPrototypeOf,oe=Object.prototype.hasOwnProperty;var ne=(e,n,s,l)=>{if(n&&typeof n=="object"||typeof n=="function")for(let i of Z(n))!oe.call(e,i)&&i!==s&&I(e,i,{get:()=>n[i],enumerable:!(l=Q(n,i))||l.enumerable});return e};var R=(e,n,s)=>(s=e!=null?V(ee(e)):{},ne(n||!e||!e.__esModule?I(s,"default",{value:e,enumerable:!0}):s,e));var y=R(require("fs"));var h=(e,n)=>s=>`\x1B[${e}m${s}\x1B[${n}m`,t={BOLD:h("1","22"),CYAN:h("36","39"),GREEN:h("32","39"),RED:h("31","39"),YELLOW:h("33","39"),PURPLE:h("35","39"),RESET:e=>`\x1B[0m${e}`},r={INFO:"\u{1F525}",SUCCESS:"\u2705",FAIL:"\u274C",EXCLAMATION:"\u2757",WARN:"\u26A0\uFE0F",ROCKET:"\u{1F525}",CLEAN:"\u{1F525}",PHOENIX:"\u{1F525}",BUILD:"\u{1F528}",TARGET:"\u{1F525}",CELEBRATE:"\u{1F525}",STARS:"\u2728",BOX:"\u{1F4E6}",CLIPBOARD:"\u{1F4CB}",DOCKER:"\u{1F433}"};var O=R(require("fs")),L=!0;function se(e){let n=new RegExp("\x1B\\[[0-9;]*m","g");return e.replace(n,"")}var w=e=>{L=e},v=()=>{L&&O.default.writeFileSync("torch-it.log","")},k=e=>{if(!L)return;let n=se(e).replace(/^\n/,""),s=new Date().toISOString();O.default.appendFileSync("torch-it.log",`[${s}] ${n}
3
- `)};function o(e,n){let s;switch(n){case"info":s=`${t.CYAN(r.INFO)} ${t.BOLD(e)}${t.RESET("")}`;break;case"success":s=`${t.GREEN(r.SUCCESS)} ${e}${t.RESET("")}`;break;case"warn":s=`${t.YELLOW(r.WARN)} ${e}${t.RESET("")}`;break;case"fail":s=`${t.RED(r.FAIL)} ${e}${t.RESET("")}`;break;case"step":s=`
4
- ${t.PURPLE("\u25B6")} ${t.BOLD(e)}${t.RESET("")}`;break;default:s=e}console.log(s),k(s)}function P(){D([` ${r.TARGET} TORCH LIT ${r.ROCKET}`],t.PURPLE);let e=`
2
+ "use strict";var Z=Object.create;var v=Object.defineProperty;var ee=Object.getOwnPropertyDescriptor;var ne=Object.getOwnPropertyNames;var oe=Object.getPrototypeOf,se=Object.prototype.hasOwnProperty;var re=(e,o,s,l)=>{if(o&&typeof o=="object"||typeof o=="function")for(let t of ne(o))!se.call(e,t)&&t!==s&&v(e,t,{get:()=>o[t],enumerable:!(l=ee(o,t))||l.enumerable});return e};var k=(e,o,s)=>(s=e!=null?Z(oe(e)):{},re(o||!e||!e.__esModule?v(s,"default",{value:e,enumerable:!0}):s,e));var _=k(require("fs"));var g=(e,o)=>s=>`\x1B[${e}m${s}\x1B[${o}m`,i={BOLD:g("1","22"),CYAN:g("36","39"),GREEN:g("32","39"),RED:g("31","39"),YELLOW:g("33","39"),PURPLE:g("35","39"),RESET:e=>`\x1B[0m${e}`},r={INFO:"\u{1F525}",SUCCESS:"\u2705",FAIL:"\u274C",EXCLAMATION:"\u2757",WARN:"\u26A0\uFE0F",ROCKET:"\u{1F525}",CLEAN:"\u{1F525}",PHOENIX:"\u{1F525}",BUILD:"\u{1F528}",TARGET:"\u{1F525}",CELEBRATE:"\u{1F525}",STARS:"\u2728",BOX:"\u{1F4E6}",CLIPBOARD:"\u{1F4CB}",DOCKER:"\u{1F433}"};var T=k(require("fs")),L=!0;function te(e){let o=new RegExp("\x1B\\[[0-9;]*m","g");return e.replace(o,"")}var w=e=>{L=e},P=()=>{L&&T.default.writeFileSync("torch-it.log","")},D=e=>{if(!L)return;let o=te(e).replace(/^\n/,""),s=new Date().toISOString();T.default.appendFileSync("torch-it.log",`[${s}] ${o}
3
+ `)};function n(e,o){let s;switch(o){case"info":s=`${i.CYAN(r.INFO)} ${i.BOLD(e)}${i.RESET("")}`;break;case"success":s=`${i.GREEN(r.SUCCESS)} ${e}${i.RESET("")}`;break;case"warn":s=`${i.YELLOW(r.WARN)} ${e}${i.RESET("")}`;break;case"fail":s=`${i.RED(r.FAIL)} ${e}${i.RESET("")}`;break;case"step":s=`
4
+ ${i.PURPLE("\u25B6")} ${i.BOLD(e)}${i.RESET("")}`;break;default:s=e}console.log(s),D(s)}function F(){b([` ${r.TARGET} TORCH LIT ${r.ROCKET}`],i.PURPLE);let e=`
5
5
  ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) )
6
6
  (( (( (( (( (( (( (( (( (( (( (( (( (( ((
7
7
  ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) ) )
@@ -12,4 +12,4 @@ ${t.PURPLE("\u25B6")} ${t.BOLD(e)}${t.RESET("")}`;break;default:s=e}console.log(
12
12
  | _ \\| | | | |_) | \\| || || \\| | | _
13
13
  | |_) | |_| | _ <| |\\ || || |\\ | |_| |
14
14
  |____/ \\___/|_| \\_\\_| \\_|___|_| \\_|\\____|
15
- `;console.log(e),k(e)}function F(){console.log(""),D([` ${r.PHOENIX} RISING FROM THE ASHES ${r.PHOENIX}`],t.PURPLE)}function x(e){let n=new RegExp("\x1B\\[[0-9;]*m","g");return e.replace(n,"").length}function D(e,n=t.GREEN){let s=Math.max(56,...e.map(i=>x(i))),l=n("\u2550".repeat(s));console.log(n("\u2554"+l+"\u2557")),e.forEach(i=>{if(k(i),i.trim()==="")console.log(n("\u2551"+" ".repeat(s)+"\u2551"));else{let g=s-x(i);console.log(n("\u2551"+i+" ".repeat(g)+"\u2551"))}}),console.log(n("\u255A"+l+"\u255D"))}var _=require("child_process"),U=R(require("os"));function c(e,n={}){try{return(0,_.execSync)(e,{stdio:n.silent?"pipe":"inherit"}),!0}catch{return n.silent||o(`Command failed: ${e}`,"fail"),!1}}function a(e){try{return U.platform()==="win32"?(0,_.execSync)(`where ${e}`,{stdio:"ignore"}):(0,_.execSync)(`command -v ${e}`,{stdio:"ignore"}),!0}catch{return!1}}var m=R(require("fs"));var B=["node_modules","dist","build",".svelte-kit",".svelte",".next",".nuxt","out",".output",".vercel",".netlify",".astro",".angular",".angular/cache",".solid",".docusaurus",".vite",".cache",".parcel-cache",".webpack",".rollup.cache",".rpt2_cache",".swc",".eslintcache",".stylelintcache",".sass-cache",".tmp","tmp","temp","coverage",".nyc_output","storybook-static",".storybook-out",".turbo",".rush",".firebase",".serverless","android/.gradle","android/build","android/app/build","ios/Pods","ios/build",".expo",".expo-shared","lib","es","cjs","umd"],K=[".pnpm-store",".pnpm-debug.log",".yarn/cache",".yarn/unplugged",".yarn/install-state.gz",".yarn/build-state.yml",".npm","node_modules/.cache"],M=[];var f={customPaths:[],customDirs:[],customFiles:[],protectedPaths:[],dockerMode:!0,logfile:!0};var re=()=>{let e="torchrc.json";if(!m.existsSync(e))return{};try{return JSON.parse(m.readFileSync(e,"utf8"))}catch{return o("Invalid torchrc.json (must be valid JSON) - skipping custom config","warn"),{}}},p=()=>{let e=re();return{customPaths:e.customPaths??f.customPaths,customDirs:e.customDirs??f.customDirs,customFiles:e.customFiles??f.customFiles,protectedPaths:e.protectedPaths??f.protectedPaths,dockerMode:e.dockerMode??f.dockerMode,logfile:e.logfile??f.logfile}},te=()=>{let e=p();return[...e.customPaths,...e.customDirs,...e.customFiles].filter(s=>typeof s=="string").map(s=>s.trim()).filter(s=>s.length>0)},H=()=>{let e=process.env.TORCH_DRY_RUN==="1",n=0,s=p(),l=te(),i=s.protectedPaths,g=[...new Set([...B,...K,...M])],S=[...new Set(l)],$=g.filter(u=>!i.some(C=>u===C||u.startsWith(C+"/"))),b=S.filter(u=>!i.some(C=>u===C||u.startsWith(C+"/"))),A=u=>{if(m.existsSync(u)){o(`${e?"Would remove":"Removing"} ${u}...`,"step");try{e||m.rmSync(u,{recursive:!0,force:!0}),o(`${u} ${e?"marked for removal (dry-run)":"removed"}`,"success"),n++}catch{o(`Failed to remove ${u}`,"fail")}}};o("Scanning for build artifacts and cache directories...","step"),$.forEach(A),b.length>0&&(o("Deleting user defined custom directories and files","step"),b.forEach(A));let N=g.length-$.length+(S.length-b.length);return N>0&&o(`Skipped ${N} protected path(s) from torchrc.json`,"info"),n===0?(o("No build artifacts or cache directories found (project already clean)","info"),!1):(o(`Removed ${n} build/cache directories`,"success"),!0)},Y=()=>{let e=process.env.TORCH_DRY_RUN==="1",n=!1;return a("npm")&&(e||c("npm cache clean --force"))&&(o(e?"Dry-run: would clean npm cache":"npm cache cleaned","success"),n=!0),a("yarn")&&(e||c("yarn cache clean"))&&(o(e?"Dry-run: would clean yarn cache":"yarn cache cleaned","success"),n=!0),a("pnpm")&&(e||c("pnpm store prune"))&&(o(e?"Dry-run: would clean pnpm store":"pnpm store cleaned","success"),n=!0),n||o("No package manager caches cleaned (tools not available)","info"),n};function j(){return y.existsSync("Dockerfile")||y.existsSync("docker-compose.yml")||y.existsSync("docker-compose.yaml")}function G(){if(p().dockerMode===!1)return o("Docker mode disabled in torchrc.json - skipping Docker operations","info"),"NO_DOCKER";let n=process.env.TORCH_DRY_RUN==="1";return j()?(o("Stopping Docker services and removing all resources...","info"),a("docker")?c("docker info",{silent:!0})?c("docker compose ps",{silent:!0})?n?(o("Dry-run: would run 'docker compose down --rmi all --volumes'","info"),"OK"):c("docker compose down --rmi all --volumes")?(o("Docker services stopped and resources cleaned","success"),"OK"):(o("Docker cleanup encountered issues","warn"),o("Continuing with the rest of the script...","info"),"DOCKER_FAIL"):(o("No Docker Compose services found - skipping Docker cleanup","warn"),o("This is normal if no services were previously running","info"),"DOCKER_FAIL"):(o("Docker daemon is not running - skipping Docker cleanup","warn"),o("You may need to start Docker manually and run cleanup later","info"),"NO_DOCKER"):(o("Docker is not installed - skipping Docker cleanup","warn"),"NO_DOCKER")):(o("No Docker configuration found - skipping Docker operations","info"),"NO_DOCKER")}function W(){if(p().dockerMode===!1)return!1;let n=process.env.TORCH_DRY_RUN==="1";return j()?a("docker")?c("docker info",{silent:!0})?(o("Building Docker resources (this may take a while...)...","step"),console.log(` ${t.YELLOW("\u23F3 Please be patient - pulling fresh images and building...")}`),n?(o("Dry-run: would run 'docker-compose build --pull --no-cache'","info"),!0):c("docker-compose build --pull --no-cache")?!0:(o("Docker build encountered issues - check torch-it.log for details","fail"),!1)):(o("Docker daemon is not running - skipping Docker rebuild","warn"),o("Start Docker manually and run 'docker-compose build --pull --no-cache' later","info"),!1):(o("Docker is not installed - skipping Docker rebuild","warn"),!1):!1}function X(){if(p().dockerMode===!1)return!1;let n=process.env.TORCH_DRY_RUN==="1";return o("Starting Docker services in detached mode...","step"),n?(o("Dry-run: would run 'docker compose up -d'","info"),!0):c("docker compose up -d")?!0:(o("Failed to start Docker services - check torch-it.log for details","fail"),!1)}var E=R(require("fs"));var J=()=>{let e=process.env.TORCH_DRY_RUN==="1",n=!1;return o("Detecting package manager and installing dependencies...","step"),E.existsSync("pnpm-lock.yaml")&&a("pnpm")?(o("Using pnpm (detected pnpm-lock.yaml)...","step"),e||c("pnpm install")?(o(`Dependencies ${e?"would be installed":"installed successfully"} with pnpm`,"success"),n=!0):o("pnpm install failed","fail")):E.existsSync("yarn.lock")&&a("yarn")?(o("Using yarn (detected yarn.lock)...","step"),e||c("yarn install")?(o(`Dependencies ${e?"would be installed":"installed successfully"} with yarn`,"success"),n=!0):o("yarn install failed","fail")):E.existsSync("package-lock.json")&&a("npm")?(o("Using npm (detected package-lock.json)...","step"),e||c("npm install")?(o(`Dependencies ${e?"would be installed":"installed successfully"} with npm`,"success"),n=!0):o("npm install failed","fail")):a("npm")?(o("Using npm (fallback)...","info"),e||c("npm install")?(o(`Dependencies ${e?"would be installed":"installed successfully"} with npm`,"success"),n=!0):o("npm install failed","fail")):a("yarn")?(o("Using yarn (fallback)...","info"),e||c("yarn install")?(o(`Dependencies ${e?"would be installed":"installed successfully"} with yarn`,"success"),n=!0):o("yarn install failed","")):a("pnpm")?(o("Using pnpm (fallback)...","info"),e||c("pnpm install")?(o(`Dependencies ${e?"would be installed":"installed successfully"} with pnpm`,"success"),n=!0):o("pnpm install failed","fail")):o("No package manager found (npm/yarn/pnpm). Please install dependencies manually.","fail"),n};var q=e=>{let n="",s="",l="";e.dockerClean==="NO_DOCKER"?n=`${r.DOCKER} No Docker containers found`:e.dockerClean==="DOCKER_FAIL"&&(n=`${r.FAIL} Failed to remove Docker containers`),e.dockerClean==="OK"&&(e.dockerRebuild?s=`${r.DOCKER} Docker containers rebuilt from scratch`:s=`${r.FAIL} Failed to rebuild Docker containers`,e.dockerLaunch&&e.dockerRebuild?l=`${r.ROCKET} Services running in detached mode`:l=`${r.FAIL} Failed to start Docker containers`);let i=e.buildAndCacheClean&&e.packageManagerClean?`${r.CLEAN} All build artifacts & caches removed`:`${r.FAIL} Build artifacts or cache directories not found`,g=e.dependencyInstall?`${r.BOX} Dependencies freshly installed`:`${r.FAIL} Failed to install dependencies`;console.log(""),D(["\u{1F525} PROJECT SUCCESSFULLY TORCHED! \u{1F525}","",`${i}`,`${g}`,`${n}`,`${s}`,`${l}`,"",e.logfile===!1?`${r.CLIPBOARD} Logging to torch-it.log is disabled; set "logfile": true in torchrc.json to enable it`:`${r.CLIPBOARD} Check torch-it.log for detailed logs`])};var ce=process.argv.slice(2),z=ce.includes("--test");z&&(process.env.TORCH_DRY_RUN="1");var T=p();w(T.logfile);T.logfile&&v();P();z&&o("Running in --test dry-run mode (no files or services will be changed)","warn");var d={dockerClean:"NO_DOCKER",buildAndCacheClean:!1,packageManagerClean:!1,dependencyInstall:!1,dockerRebuild:!1,dockerLaunch:!1,logfile:T.logfile};o(`${r.CLEAN} DOCKER CLEANUP`,"step");d.dockerClean=G();o(`${r.CLEAN} BUILD ARTIFACTS & CACHE CLEANUP`,"step");d.buildAndCacheClean=H();o("Cleaning package manager caches...","step");d.packageManagerClean=Y();F();o(`${r.BUILD} DEPENDENCY INSTALLATION`,"step");d.dependencyInstall=J();d.dockerClean&&(o(`${r.BUILD} DOCKER REBUILD`,"step"),d.dockerRebuild=W());d.dockerRebuild&&(d.dockerLaunch=X(),o(`${r.ROCKET} LAUNCH`,"step"));q(d);
15
+ `;console.log(e),D(e)}function U(){console.log(""),b([` ${r.PHOENIX} RISING FROM THE ASHES ${r.PHOENIX}`],i.PURPLE)}function x(e){let o=new RegExp("\x1B\\[[0-9;]*m","g");return e.replace(o,"").length}function b(e,o=i.GREEN){let s=Math.max(56,...e.map(t=>x(t))),l=o("\u2550".repeat(s));console.log(o("\u2554"+l+"\u2557")),e.forEach(t=>{if(D(t),t.trim()==="")console.log(o("\u2551"+" ".repeat(s)+"\u2551"));else{let f=s-x(t);console.log(o("\u2551"+t+" ".repeat(f)+"\u2551"))}}),console.log(o("\u255A"+l+"\u255D"))}var y=require("child_process"),B=k(require("os"));function c(e,o={}){try{return(0,y.execSync)(e,{stdio:o.silent?"pipe":"inherit"}),!0}catch{return o.silent||n(`Command failed: ${e}`,"fail"),!1}}function a(e){try{return B.platform()==="win32"?(0,y.execSync)(`where ${e}`,{stdio:"ignore"}):(0,y.execSync)(`command -v ${e}`,{stdio:"ignore"}),!0}catch{return!1}}var m=k(require("fs"));var K=["node_modules","dist","build",".svelte-kit",".svelte",".next",".nuxt","out",".output",".vercel",".netlify",".astro",".angular",".angular/cache",".solid",".docusaurus",".vite",".cache",".parcel-cache",".webpack",".rollup.cache",".rpt2_cache",".swc",".eslintcache",".stylelintcache",".sass-cache",".tmp","tmp","temp","coverage",".nyc_output","storybook-static",".storybook-out",".turbo",".rush",".firebase",".serverless","android/.gradle","android/build","android/app/build","ios/Pods","ios/build",".expo",".expo-shared","lib","es","cjs","umd"],M=[".pnpm-store",".pnpm-debug.log",".yarn/cache",".yarn/unplugged",".yarn/install-state.gz",".yarn/build-state.yml",".npm","node_modules/.cache"],H=[];var p={customPaths:[],customDirs:[],customFiles:[],protectedPaths:[],dockerMode:!0,logfile:!1,rebuild:!0};var ie=e=>{let o={};for(let s of e){if(!s.startsWith("--"))continue;let[l,t]=s.slice(2).split("=",2);if(!(!l||!t))try{let f=JSON.parse(t);o[l]=f}catch{t==="true"?o[l]=!0:t==="false"?o[l]=!1:o[l]=t}}return o},ce=()=>{let e="torchrc.json";if(!m.existsSync(e))return{};try{return JSON.parse(m.readFileSync(e,"utf8"))}catch{return n("Invalid torchrc.json (must be valid JSON) - skipping custom config","warn"),{}}},S=()=>{let e=ce();return{customPaths:e.customPaths??p.customPaths,customDirs:e.customDirs??p.customDirs,customFiles:e.customFiles??p.customFiles,protectedPaths:e.protectedPaths??p.protectedPaths,dockerMode:e.dockerMode??p.dockerMode,logfile:e.logfile??p.logfile,rebuild:e.rebuild??p.rebuild}},C=(e=[])=>{let o=S(),s=ie(e);return{...o,...s}},le=()=>{let e=S();return[...e.customPaths,...e.customDirs,...e.customFiles].filter(s=>typeof s=="string").map(s=>s.trim()).filter(s=>s.length>0)},Y=()=>{let e=process.env.TORCH_DRY_RUN==="1",o=0,s=S(),l=le(),t=s.protectedPaths,f=[...new Set([...K,...M,...H])],$=[...new Set(l)],N=f.filter(u=>!t.some(R=>u===R||u.startsWith(R+"/"))),O=$.filter(u=>!t.some(R=>u===R||u.startsWith(R+"/"))),A=u=>{if(m.existsSync(u)){n(`${e?"Would remove":"Removing"} ${u}...`,"step");try{e||m.rmSync(u,{recursive:!0,force:!0}),n(`${u} ${e?"marked for removal (dry-run)":"removed"}`,"success"),o++}catch{n(`Failed to remove ${u}`,"fail")}}};n("Scanning for build artifacts and cache directories...","step"),N.forEach(A),O.length>0&&(n("Deleting user defined custom directories and files","step"),O.forEach(A));let I=f.length-N.length+($.length-O.length);return I>0&&n(`Skipped ${I} protected path(s) from torchrc.json`,"info"),o===0?(n("No build artifacts or cache directories found (project already clean)","info"),!1):(n(`Removed ${o} build/cache directories`,"success"),!0)},j=()=>{let e=process.env.TORCH_DRY_RUN==="1",o=!1;return a("npm")&&(e||c("npm cache clean --force"))&&(n(e?"Dry-run: would clean npm cache":"npm cache cleaned","success"),o=!0),a("yarn")&&(e||c("yarn cache clean"))&&(n(e?"Dry-run: would clean yarn cache":"yarn cache cleaned","success"),o=!0),a("pnpm")&&(e||c("pnpm store prune"))&&(n(e?"Dry-run: would clean pnpm store":"pnpm store cleaned","success"),o=!0),o||n("No package manager caches cleaned (tools not available)","info"),o};function W(){return _.existsSync("Dockerfile")||_.existsSync("docker-compose.yml")||_.existsSync("docker-compose.yaml")}function G(){if(C().dockerMode===!1)return n("Docker mode disabled in torchrc.json - skipping Docker operations","info"),"NO_DOCKER";let o=process.env.TORCH_DRY_RUN==="1";return W()?(n("Stopping Docker services and removing all resources...","info"),a("docker")?c("docker info",{silent:!0})?c("docker compose ps",{silent:!0})?o?(n("Dry-run: would run 'docker compose down --rmi all --volumes'","info"),"OK"):c("docker compose down --rmi all --volumes")?(n("Docker services stopped and resources cleaned","success"),"OK"):(n("Docker cleanup encountered issues","warn"),n("Continuing with the rest of the script...","info"),"DOCKER_FAIL"):(n("No Docker Compose services found - skipping Docker cleanup","warn"),n("This is normal if no services were previously running","info"),"DOCKER_FAIL"):(n("Docker daemon is not running - skipping Docker cleanup","warn"),n("You may need to start Docker manually and run cleanup later","info"),"NO_DOCKER"):(n("Docker is not installed - skipping Docker cleanup","warn"),"NO_DOCKER")):(n("No Docker configuration found - skipping Docker operations","info"),"NO_DOCKER")}function X(){let e=C();if(e.dockerMode===!1)return!1;if(e.rebuild===!1)return n("Rebuild disabled in torchrc.json - skipping Docker rebuild","info"),!1;let o=process.env.TORCH_DRY_RUN==="1";return W()?a("docker")?c("docker info",{silent:!0})?(n("Building Docker resources (this may take a while...)...","step"),console.log(` ${i.YELLOW("\u23F3 Please be patient - pulling fresh images and building...")}`),o?(n("Dry-run: would run 'docker-compose build --pull --no-cache'","info"),!0):c("docker-compose build --pull --no-cache")?!0:(n("Docker build encountered issues - check torch-it.log for details","fail"),!1)):(n("Docker daemon is not running - skipping Docker rebuild","warn"),n("Start Docker manually and run 'docker-compose build --pull --no-cache' later","info"),!1):(n("Docker is not installed - skipping Docker rebuild","warn"),!1):!1}function J(){if(C().dockerMode===!1)return!1;let o=process.env.TORCH_DRY_RUN==="1";return n("Starting Docker services in detached mode...","step"),o?(n("Dry-run: would run 'docker compose up -d'","info"),!0):c("docker compose up -d")?!0:(n("Failed to start Docker services - check torch-it.log for details","fail"),!1)}var E=k(require("fs"));var q=()=>{let e=process.env.TORCH_DRY_RUN==="1",o=!1;return n("Detecting package manager and installing dependencies...","step"),E.existsSync("pnpm-lock.yaml")&&a("pnpm")?(n("Using pnpm (detected pnpm-lock.yaml)...","step"),e||c("pnpm install")?(n(`Dependencies ${e?"would be installed":"installed successfully"} with pnpm`,"success"),o=!0):n("pnpm install failed","fail")):E.existsSync("yarn.lock")&&a("yarn")?(n("Using yarn (detected yarn.lock)...","step"),e||c("yarn install")?(n(`Dependencies ${e?"would be installed":"installed successfully"} with yarn`,"success"),o=!0):n("yarn install failed","fail")):E.existsSync("package-lock.json")&&a("npm")?(n("Using npm (detected package-lock.json)...","step"),e||c("npm install")?(n(`Dependencies ${e?"would be installed":"installed successfully"} with npm`,"success"),o=!0):n("npm install failed","fail")):a("npm")?(n("Using npm (fallback)...","info"),e||c("npm install")?(n(`Dependencies ${e?"would be installed":"installed successfully"} with npm`,"success"),o=!0):n("npm install failed","fail")):a("yarn")?(n("Using yarn (fallback)...","info"),e||c("yarn install")?(n(`Dependencies ${e?"would be installed":"installed successfully"} with yarn`,"success"),o=!0):n("yarn install failed","")):a("pnpm")?(n("Using pnpm (fallback)...","info"),e||c("pnpm install")?(n(`Dependencies ${e?"would be installed":"installed successfully"} with pnpm`,"success"),o=!0):n("pnpm install failed","fail")):n("No package manager found (npm/yarn/pnpm). Please install dependencies manually.","fail"),o};var V=e=>{let o="",s="",l="";e.dockerClean==="NO_DOCKER"?o=`${r.DOCKER} No Docker containers found`:e.dockerClean==="DOCKER_FAIL"&&(o=`${r.FAIL} Failed to remove Docker containers`),e.dockerClean==="OK"&&(e.dockerRebuild?s=`${r.DOCKER} Docker containers rebuilt from scratch`:s=`${r.FAIL} Failed to rebuild Docker containers`,e.dockerLaunch&&e.dockerRebuild?l=`${r.ROCKET} Services running in detached mode`:l=`${r.FAIL} Failed to start Docker containers`);let t=e.buildAndCacheClean&&e.packageManagerClean?`${r.CLEAN} All build artifacts & caches removed`:`${r.FAIL} Build artifacts or cache directories not found`,f=e.dependencyInstall?`${r.BOX} Dependencies freshly installed`:`${r.FAIL} Failed to install dependencies`;console.log(""),b(["\u{1F525} PROJECT SUCCESSFULLY TORCHED! \u{1F525}","",`${t}`,`${f}`,`${o}`,`${s}`,`${l}`,"",e.logfile===!1?`${r.CLIPBOARD} Logging to torch-it.log is disabled; set "logfile": true in torchrc.json to enable it`:`${r.CLIPBOARD} Check torch-it.log for detailed logs`])};var z=process.argv.slice(2),Q=z.includes("--test");Q&&(process.env.TORCH_DRY_RUN="1");var h=C(z.filter(e=>e!=="--test"));w(h.logfile);h.logfile&&P();F();Q&&n("Running in --test dry-run mode (no files or services will be changed)","warn");var d={dockerClean:"NO_DOCKER",buildAndCacheClean:!1,packageManagerClean:!1,dependencyInstall:!1,dockerRebuild:!1,dockerLaunch:!1,logfile:h.logfile};n(`${r.CLEAN} DOCKER CLEANUP`,"step");d.dockerClean=G();n(`${r.CLEAN} BUILD ARTIFACTS & CACHE CLEANUP`,"step");d.buildAndCacheClean=Y();n("Cleaning package manager caches...","step");d.packageManagerClean=j();h.rebuild!==!1?(U(),n(`${r.BUILD} DEPENDENCY INSTALLATION`,"step"),d.dependencyInstall=q()):(n("Rebuild disabled - skipping dependency installation","info"),d.dependencyInstall=!1);d.dockerClean!=="NO_DOCKER"&&h.rebuild!==!1?(n(`${r.BUILD} DOCKER REBUILD`,"step"),d.dockerRebuild=X()):d.dockerClean!=="NO_DOCKER"&&h.rebuild===!1&&(n("Rebuild disabled - skipping Docker rebuild","info"),d.dockerRebuild=!1);d.dockerRebuild&&(d.dockerLaunch=J(),n(`${r.ROCKET} LAUNCH`,"step"));V(d);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "torch-it",
3
- "version": "2.3.0",
3
+ "version": "2.4.0",
4
4
  "description": "CLI to reset, clean, and rebuild Node.js project environments.",
5
5
  "keywords": [
6
6
  "cleanup",