Comparing version 0.11.3 to 0.12.0
@@ -15,6 +15,11 @@ import colors from 'colors'; | ||
arg: ['-D', '--delete-all'], | ||
description: 'CURRENTLY DISABLED. Automatically delete all node_modules folders that are found.', | ||
description: 'Auto-delete all node_modules folders that are found.', | ||
name: 'delete-all', | ||
}, | ||
{ | ||
arg: ['-y'], | ||
description: 'Avoid displaying a warning when executing --delete-all.', | ||
name: 'yes', | ||
}, | ||
{ | ||
arg: ['-e', '--hide-errors'], | ||
@@ -65,2 +70,7 @@ description: 'Hide errors if any.', | ||
{ | ||
arg: ['--dry-run'], | ||
description: 'It does not delete anything (will simulate it with a random delay).', | ||
name: 'dry-run', | ||
}, | ||
{ | ||
arg: ['-v', '--version'], | ||
@@ -79,2 +89,3 @@ description: 'Show version.', | ||
🭲 home, end: move to the first and last result | ||
🭲 o: open the parent directory of the selected result | ||
🭲 e: show errors popup, next page`; | ||
@@ -81,0 +92,0 @@ export const HELP_PROGRESSBAR = ` ------- PROGRESS BAR -------------------- |
@@ -12,2 +12,3 @@ export const MIN_CLI_COLUMNS_SIZE = 60; | ||
deleteAll: false, | ||
dryRun: false, | ||
exclude: ['.git'], | ||
@@ -20,2 +21,3 @@ excludeHiddenDirectories: false, | ||
targetFolder: 'node_modules', | ||
yes: false, | ||
}; | ||
@@ -34,12 +36,15 @@ export const MARGINS = { | ||
export const UI_POSITIONS = { | ||
FOLDER_SIZE_HEADER: { x: -1, y: 7 }, | ||
FOLDER_SIZE_HEADER: { x: -1, y: 7 }, // x is calculated in controller | ||
INITIAL: { x: 0, y: 0 }, | ||
VERSION: { x: 38, y: 5 }, | ||
DRY_RUN_NOTICE: { x: 1, y: 6 }, | ||
NEW_UPDATE_FOUND: { x: 42, y: 0 }, | ||
SPACE_RELEASED: { x: 50, y: 4 }, | ||
STATUS: { x: 50, y: 5 }, | ||
STATUS_BAR: { x: 50, y: 6 }, | ||
TOTAL_SPACE: { x: 50, y: 3 }, | ||
ERRORS_COUNT: { x: 50, y: 2 }, | ||
SPACE_RELEASED: { x: 50, y: 3 }, | ||
STATUS: { x: 50, y: 4 }, | ||
STATUS_BAR: { x: 50, y: 5 }, | ||
PENDING_TASKS: { x: 50, y: 6 }, //Starting position. It will then be replaced. | ||
TOTAL_SPACE: { x: 50, y: 2 }, | ||
ERRORS_COUNT: { x: 50, y: 1 }, | ||
TUTORIAL_TIP: { x: 1, y: 7 }, | ||
WARNINGS: { x: 0, y: 9 }, | ||
}; | ||
@@ -46,0 +51,0 @@ // export const VALID_KEYS: string[] = [ |
export const HELP_MSGS = { | ||
BASIC_USAGE: '> CURSORS for select; SPACE to delete <', | ||
BASIC_USAGE: ' CURSORS for select - SPACE to delete', | ||
}; | ||
@@ -8,5 +8,3 @@ export const INFO_MSGS = { | ||
ERROR_DELETING_FOLDER: '[ ERROR ] ', | ||
DISABLED: '[-D, --delete-all] option has been disabled until future versions. ' + | ||
'Please restart npkill without this option.', | ||
HEADER_COLUMNS: 'last_mod size', | ||
HEADER_COLUMNS: 'Last_mod Size', | ||
HELP_TITLE: ' NPKILL HELP ', | ||
@@ -21,8 +19,14 @@ MIN_CLI_CLOMUNS: 'Oh no! The terminal is too narrow. Please, ' + | ||
STARTING: 'Initializing ', | ||
SEARCHING: 'searching ', | ||
CALCULATING_STATS: 'calculating stats ', | ||
SEARCHING: 'Searching ', | ||
CALCULATING_STATS: 'Calculating stats ', | ||
FATAL_ERROR: 'Fatal error ', | ||
SEARCH_COMPLETED: 'search completed ', | ||
SPACE_RELEASED: 'space saved: ', | ||
TOTAL_SPACE: 'releasable space: ', | ||
SEARCH_COMPLETED: 'Search completed ', | ||
SPACE_RELEASED: 'Space saved: ', | ||
TOTAL_SPACE: 'Releasable space: ', | ||
DRY_RUN: 'Dry run mode', | ||
DELETE_ALL_WARNING: ' --delete-all may have undesirable effects and\n' + | ||
' delete dependencies needed by some applications.\n' + | ||
' Recommended to use -x and preview with --dry-run.\n\n' + | ||
' Press y to continue.\n\n' + | ||
' pass -y to not show this next time', | ||
}; | ||
@@ -29,0 +33,0 @@ export const ERROR_MSG = { |
@@ -7,3 +7,3 @@ import { DEFAULT_CONFIG, MIN_CLI_COLUMNS_SIZE, UI_POSITIONS, } from './constants/index.js'; | ||
import { FOLDER_SORT } from './constants/sort.result.js'; | ||
import { StatusUi, StatsUi, ResultsUi, LogsUi, HelpUi, HeaderUi, GeneralUi, } from './ui/index.js'; | ||
import { StatusUi, StatsUi, ResultsUi, LogsUi, HelpUi, HeaderUi, GeneralUi, WarningUi, } from './ui/index.js'; | ||
import _dirname from './dirname.js'; | ||
@@ -13,2 +13,3 @@ import colors from 'colors'; | ||
import path from 'path'; | ||
import openExplorer from 'open-file-explorer'; | ||
export class Controller { | ||
@@ -34,2 +35,3 @@ logger; | ||
uiLogs; | ||
uiWarning; | ||
activeComponent = null; | ||
@@ -58,8 +60,23 @@ constructor(logger, searchStatus, fileService, spinnerService, consoleService, updateService, resultsService, uiService) { | ||
this.setupEventsListener(); | ||
this.uiStatus.start(); | ||
if (this.config.checkUpdates) { | ||
this.checkVersion(); | ||
} | ||
if (this.config.deleteAll && !this.config.yes) { | ||
this.showDeleteAllWarning(); | ||
this.uiWarning.confirm$ | ||
.pipe(tap(() => { | ||
this.activeComponent = this.uiResults; | ||
this.uiWarning.setDeleteAllWarningVisibility(false); | ||
this.uiService.renderAll(); | ||
this.scan(); | ||
})) | ||
.subscribe(); | ||
return; | ||
} | ||
this.scan(); | ||
} | ||
showDeleteAllWarning() { | ||
this.uiWarning.setDeleteAllWarningVisibility(true); | ||
this.activeComponent = this.uiWarning; | ||
} | ||
initUi() { | ||
@@ -78,2 +95,4 @@ this.uiHeader = new HeaderUi(); | ||
this.uiService.add(this.uiLogs); | ||
this.uiWarning = new WarningUi(); | ||
this.uiService.add(this.uiWarning); | ||
// Set Events | ||
@@ -83,2 +102,3 @@ this.uiResults.delete$.subscribe((folder) => this.deleteFolder(folder)); | ||
this.uiLogs.close$.subscribe(() => this.showErrorPopup(false)); | ||
this.uiResults.openFolder$.subscribe((path) => openExplorer(path)); | ||
// Activate the main interactive component | ||
@@ -98,4 +118,3 @@ this.activeComponent = this.uiResults; | ||
if (options.isTrue('delete-all')) { | ||
this.showObsoleteMessage(); | ||
process.exit(); | ||
this.config.deleteAll = true; | ||
} | ||
@@ -143,2 +162,9 @@ if (options.isTrue('sort-by')) { | ||
} | ||
if (options.isTrue('dry-run')) { | ||
this.config.dryRun = true; | ||
this.uiHeader.isDryRun = true; | ||
} | ||
if (options.isTrue('yes')) { | ||
this.config.yes = true; | ||
} | ||
// Remove trailing slash from folderRoot for consistency | ||
@@ -174,5 +200,2 @@ this.folderRoot = this.folderRoot.replace(/[/\\]$/, ''); | ||
} | ||
showObsoleteMessage() { | ||
this.uiService.print(INFO_MSGS.DISABLED); | ||
} | ||
setColor(color) { | ||
@@ -289,2 +312,3 @@ if (this.isValidColor(color)) { | ||
scan() { | ||
this.uiStatus.start(); | ||
const params = this.prepareListDirParams(); | ||
@@ -323,3 +347,7 @@ const isExcludedDangerousDirectory = (path) => this.config.excludeHiddenDirectories && | ||
return this.calculateFolderStats(nodeFolder); | ||
}, 2), tap(() => this.searchStatus.completeStatCalculation())) | ||
}, 2), tap(() => this.searchStatus.completeStatCalculation()), tap((folder) => { | ||
if (this.config.deleteAll) { | ||
this.deleteFolder(folder); | ||
} | ||
})) | ||
.subscribe({ | ||
@@ -351,3 +379,3 @@ next: () => this.printFoldersSection(), | ||
nodeFolder.modificationTime = -1; | ||
return; | ||
return nodeFolder; | ||
} | ||
@@ -358,2 +386,3 @@ const parentFolder = path.join(nodeFolder.path, '../'); | ||
this.logger.info(`Last mod. of ${nodeFolder.path}: ${result}`); | ||
return nodeFolder; | ||
}), tap(() => { | ||
@@ -417,8 +446,15 @@ this.finishFolderStats(); | ||
folder.status = 'deleting'; | ||
this.searchStatus.pendingDeletions++; | ||
this.uiStatus.render(); | ||
this.printFoldersSection(); | ||
this.fileService | ||
.deleteDir(folder.path) | ||
const deleteFunction = this.config | ||
.dryRun | ||
? this.fileService.fakeDeleteDir | ||
: this.fileService.deleteDir; | ||
deleteFunction(folder.path) | ||
.then(() => { | ||
folder.status = 'deleted'; | ||
this.searchStatus.pendingDeletions--; | ||
this.uiStats.render(); | ||
this.uiStatus.render(); | ||
this.printFoldersSection(); | ||
@@ -429,2 +465,4 @@ this.logger.info(`Deleted ${folder.path}`); | ||
folder.status = 'error-deleting'; | ||
this.searchStatus.pendingDeletions--; | ||
this.uiStatus.render(); | ||
this.printFoldersSection(); | ||
@@ -431,0 +469,0 @@ this.newError(e.message); |
@@ -7,2 +7,3 @@ export class SearchStatus { | ||
resultsFound = 0; | ||
pendingDeletions = 0; | ||
workerStatus = 'stopped'; | ||
@@ -9,0 +10,0 @@ workersJobs; |
import fs, { accessSync, readFileSync, statSync } from 'fs'; | ||
import { readdir, stat } from 'fs/promises'; | ||
export class FileService { | ||
/** Used for dry-run or testing. */ | ||
async fakeDeleteDir(_path) { | ||
const randomDelay = Math.floor(Math.random() * 4000 + 200); | ||
await new Promise((r) => setTimeout(r, randomDelay)); | ||
return true; | ||
} | ||
isValidRootFolder(path) { | ||
@@ -5,0 +11,0 @@ let stat; |
@@ -6,11 +6,15 @@ import { BANNER, UI_POSITIONS, HELP_MSGS, INFO_MSGS, DEFAULT_SIZE, } from '../../../constants/index.js'; | ||
programVersion; | ||
isDryRun; | ||
render() { | ||
// banner and tutorial | ||
this.printAt(BANNER, UI_POSITIONS.INITIAL); | ||
this.printAt(colors.yellow(colors.inverse(HELP_MSGS.BASIC_USAGE)), UI_POSITIONS.TUTORIAL_TIP); | ||
this.renderHeader(); | ||
if (this.programVersion !== undefined) { | ||
this.printAt(colors.gray(this.programVersion), UI_POSITIONS.VERSION); | ||
} | ||
if (this.isDryRun) { | ||
this.printAt(colors.black(colors.bgMagenta(` ${INFO_MSGS.DRY_RUN} `)), UI_POSITIONS.DRY_RUN_NOTICE); | ||
} | ||
// Columns headers | ||
this.printAt(colors.gray(INFO_MSGS.HEADER_COLUMNS), { | ||
this.printAt(colors.bgYellow(colors.black(INFO_MSGS.HEADER_COLUMNS)), { | ||
x: this.terminal.columns - INFO_MSGS.HEADER_COLUMNS.length - 4, | ||
@@ -23,2 +27,8 @@ y: UI_POSITIONS.FOLDER_SIZE_HEADER.y, | ||
} | ||
renderHeader() { | ||
const { columns } = this.terminal; | ||
const spaceToFill = Math.max(0, columns - HELP_MSGS.BASIC_USAGE.length - 2); | ||
const text = HELP_MSGS.BASIC_USAGE + ' '.repeat(spaceToFill); | ||
this.printAt(colors.yellow(colors.inverse(text)), UI_POSITIONS.TUTORIAL_TIP); | ||
} | ||
} |
@@ -8,2 +8,10 @@ import { UI_POSITIONS, INFO_MSGS } from '../../../constants/index.js'; | ||
logger; | ||
lastValues = { | ||
totalSpace: '', | ||
spaceReleased: '', | ||
}; | ||
timeouts = { | ||
totalSpace: setTimeout(() => { }), | ||
spaceReleased: setTimeout(() => { }), | ||
}; | ||
constructor(config, resultsService, logger) { | ||
@@ -17,8 +25,16 @@ super(); | ||
const { totalSpace, spaceReleased } = this.resultsService.getStats(); | ||
const totalSpacePosition = { ...UI_POSITIONS.TOTAL_SPACE }; | ||
const spaceReleasedPosition = { ...UI_POSITIONS.SPACE_RELEASED }; | ||
totalSpacePosition.x += INFO_MSGS.TOTAL_SPACE.length; | ||
spaceReleasedPosition.x += INFO_MSGS.SPACE_RELEASED.length; | ||
this.printAt(totalSpace, totalSpacePosition); | ||
this.printAt(spaceReleased, spaceReleasedPosition); | ||
this.showStat({ | ||
description: INFO_MSGS.TOTAL_SPACE, | ||
value: totalSpace, | ||
lastValueKey: 'totalSpace', | ||
position: UI_POSITIONS.TOTAL_SPACE, | ||
updateColor: 'yellow', | ||
}); | ||
this.showStat({ | ||
description: INFO_MSGS.SPACE_RELEASED, | ||
value: spaceReleased, | ||
lastValueKey: 'spaceReleased', | ||
position: UI_POSITIONS.SPACE_RELEASED, | ||
updateColor: 'green', | ||
}); | ||
if (this.config.showErrors) { | ||
@@ -28,2 +44,26 @@ this.showErrorsCount(); | ||
} | ||
/** Print the value of the stat and if it is a different value from the | ||
* previous run, highlight it for a while. | ||
*/ | ||
showStat({ description, value, lastValueKey, position, updateColor, }) { | ||
if (value === this.lastValues[lastValueKey]) { | ||
return; | ||
} | ||
const statPosition = { ...position }; | ||
statPosition.x += description.length; | ||
// If is first render, initialize. | ||
if (!this.lastValues[lastValueKey]) { | ||
this.printAt(value, statPosition); | ||
this.lastValues[lastValueKey] = value; | ||
return; | ||
} | ||
this.printAt(colors[updateColor](`${value} ▲`), statPosition); | ||
if (this.timeouts[lastValueKey]) { | ||
clearTimeout(this.timeouts[lastValueKey]); | ||
} | ||
this.timeouts[lastValueKey] = setTimeout(() => { | ||
this.printAt(value + ' ', statPosition); | ||
}, 700); | ||
this.lastValues[lastValueKey] = value; | ||
} | ||
showErrorsCount() { | ||
@@ -30,0 +70,0 @@ const errors = this.logger.get('error').length; |
@@ -14,2 +14,4 @@ import { BaseUi } from '../../base.ui.js'; | ||
barClosing = false; | ||
showProgressBar = true; | ||
pendingTasksPosition = { ...UI_POSITIONS.PENDING_TASKS }; | ||
searchEnd$ = new Subject(); | ||
@@ -46,4 +48,20 @@ SEARCH_STATES = { | ||
this.printAt(this.text, UI_POSITIONS.STATUS); | ||
this.renderProgressBar(); | ||
if (this.showProgressBar) { | ||
this.renderProgressBar(); | ||
} | ||
this.renderPendingTasks(); | ||
} | ||
renderPendingTasks() { | ||
this.clearPendingTasks(); | ||
if (this.searchStatus.pendingDeletions === 0) { | ||
return; | ||
} | ||
const { pendingDeletions } = this.searchStatus; | ||
const text = pendingDeletions > 1 ? 'pending tasks' : 'pending task '; | ||
this.printAt(colors.yellow(`${pendingDeletions} ${text}`), this.pendingTasksPosition); | ||
} | ||
clearPendingTasks() { | ||
const PENDING_TASK_LENGHT = 17; | ||
this.printAt(' '.repeat(PENDING_TASK_LENGHT), this.pendingTasksPosition); | ||
} | ||
renderProgressBar() { | ||
@@ -62,10 +80,6 @@ const { pendingSearchTasks, completedSearchTasks, completedStatsCalculation, pendingStatsCalculation, } = this.searchStatus; | ||
const barSearchMax = pendingSearchTasks + completedSearchTasks; | ||
const barStatsMax = completedStatsCalculation + pendingStatsCalculation; | ||
let barLenght = proportional(barSearchMax, BAR_WIDTH, barSearchMax); | ||
if (barLenght === 0) { | ||
barLenght = BAR_WIDTH; | ||
} | ||
barLenght = Math.floor(barLenght * modifier); | ||
const barStatsMax = pendingStatsCalculation + completedStatsCalculation; | ||
let barLenght = Math.ceil(BAR_WIDTH * modifier); | ||
let searchBarLenght = proportional(completedSearchTasks, BAR_WIDTH, barSearchMax); | ||
searchBarLenght = Math.floor(searchBarLenght * modifier); | ||
searchBarLenght = Math.ceil(searchBarLenght * modifier); | ||
let doneBarLenght = proportional(completedStatsCalculation, searchBarLenght, barStatsMax); | ||
@@ -98,2 +112,4 @@ doneBarLenght = Math.floor(doneBarLenght * modifier); | ||
this.barNormalizedWidth = 0; | ||
this.showProgressBar = false; | ||
this.movePendingTaskToTop(); | ||
return; | ||
@@ -105,6 +121,14 @@ } | ||
} | ||
/** When the progress bar disappears, "pending tasks" will move up one | ||
position. */ | ||
movePendingTaskToTop() { | ||
this.clearPendingTasks(); | ||
this.pendingTasksPosition = { ...UI_POSITIONS.STATUS_BAR }; | ||
this.renderPendingTasks(); | ||
} | ||
printProgressBar(progressBar) { | ||
if (this.barClosing) { | ||
const postX = Math.round(UI_POSITIONS.STATUS_BAR.x + | ||
(BAR_WIDTH / 2) * (1 - this.barNormalizedWidth)); | ||
const postX = UI_POSITIONS.STATUS_BAR.x - | ||
1 + | ||
Math.round((BAR_WIDTH / 2) * (1 - this.barNormalizedWidth)); | ||
// Clear previus bar | ||
@@ -111,0 +135,0 @@ this.printAt(' '.repeat(BAR_WIDTH), UI_POSITIONS.STATUS_BAR); |
@@ -6,2 +6,3 @@ import { DECIMALS_SIZE, DEFAULT_CONFIG, MARGINS, OVERFLOW_CUT_FROM, } from '../../constants/main.constants.js'; | ||
import colors from 'colors'; | ||
import { resolve } from 'node:path'; | ||
export class ResultsUi extends HeavyUi { | ||
@@ -17,2 +18,3 @@ resultsService; | ||
showErrors$ = new Subject(); | ||
openFolder$ = new Subject(); | ||
config = DEFAULT_CONFIG; | ||
@@ -35,2 +37,3 @@ KEYS = { | ||
e: () => this.showErrorsPopup(), | ||
o: () => this.openFolder(), | ||
}; | ||
@@ -43,2 +46,7 @@ constructor(resultsService, consoleService, fileService) { | ||
} | ||
openFolder() { | ||
const folder = this.resultsService.results[this.resultIndex]; | ||
const parentPath = resolve(folder.path, '..'); | ||
this.openFolder$.next(parentPath); | ||
} | ||
onKeyInput({ name }) { | ||
@@ -45,0 +53,0 @@ const action = this.KEYS[name]; |
@@ -6,2 +6,3 @@ export * from './base.ui.js'; | ||
export * from './components/logs.ui.js'; | ||
export * from './components/warning.ui.js'; | ||
export * from './components/results.ui.js'; | ||
@@ -8,0 +9,0 @@ export * from './components/header/header.ui.js'; |
{ | ||
"name": "npkill", | ||
"version": "0.11.3", | ||
"version": "0.12.0", | ||
"description": "List any node_modules directories in your system, as well as the space they take up. You can then select which ones you want to erase to free up space.", | ||
@@ -50,40 +50,41 @@ "exports": "./lib/index.js", | ||
"dependencies": { | ||
"ansi-escapes": "^6.0.0", | ||
"ansi-escapes": "^6.2.1", | ||
"colors": "1.4.0", | ||
"get-folder-size": "^2.0.0", | ||
"node-emoji": "^1.10.0", | ||
"rxjs": "^7.5.7" | ||
"get-folder-size": "^4.0.0", | ||
"node-emoji": "^2.1.3", | ||
"open-file-explorer": "^1.0.2", | ||
"rxjs": "^7.8.1" | ||
}, | ||
"devDependencies": { | ||
"@commitlint/config-conventional": "^17.1.0", | ||
"@stryker-mutator/core": "^6.2.2", | ||
"@stryker-mutator/jest-runner": "^6.2.2", | ||
"@commitlint/config-conventional": "^19.2.2", | ||
"@stryker-mutator/core": "^8.2.6", | ||
"@stryker-mutator/jest-runner": "^8.2.6", | ||
"@types/colors": "^1.2.1", | ||
"@types/gulp": "^4.0.9", | ||
"@types/jest": "^29.1.2", | ||
"@types/node": "^18.15.10", | ||
"@types/gulp": "^4.0.17", | ||
"@types/jest": "^29.5.12", | ||
"@types/node": "^20.12.7", | ||
"@types/rimraf": "^3.0.2", | ||
"@typescript-eslint/eslint-plugin": "^5.56.0", | ||
"commitlint": "^17.1.2", | ||
"del": "^7.0.0", | ||
"eslint": "^8.36.0", | ||
"eslint-config-prettier": "^8.8.0", | ||
"@typescript-eslint/eslint-plugin": "^5.62.0", | ||
"commitlint": "^19.2.2", | ||
"del": "^7.1.0", | ||
"eslint": "^8.57.0", | ||
"eslint-config-prettier": "^9.1.0", | ||
"eslint-config-standard-with-typescript": "^34.0.1", | ||
"eslint-plugin-import": "^2.27.5", | ||
"eslint-plugin-n": "^15.6.1", | ||
"eslint-plugin-import": "^2.29.1", | ||
"eslint-plugin-n": "^15.7.0", | ||
"eslint-plugin-promise": "^6.1.1", | ||
"gulp": "^4.0.2", | ||
"gulp": "^5.0.0", | ||
"gulp-typescript": "^6.0.0-alpha.1", | ||
"husky": "^8.0.0", | ||
"jest": "^29.1.2", | ||
"lint-staged": "^13.0.3", | ||
"np": "^7.6.3", | ||
"husky": "^9.0.11", | ||
"jest": "^29.7.0", | ||
"lint-staged": "^15.2.2", | ||
"np": "^10.0.3", | ||
"pre-commit": "^1.2.2", | ||
"prettier": "^2.7.1", | ||
"rimraf": "^3.0.2", | ||
"prettier": "^3.2.5", | ||
"rimraf": "^5.0.5", | ||
"stryker-cli": "^1.0.2", | ||
"ts-jest": "^29.0.3", | ||
"ts-node": "^10.9.1", | ||
"ts-jest": "^29.1.2", | ||
"ts-node": "^10.9.2", | ||
"tslint": "^6.1.0", | ||
"typescript": "^4.9.5" | ||
"typescript": "^5.4.5" | ||
}, | ||
@@ -90,0 +91,0 @@ "husky": { |
@@ -83,2 +83,4 @@ <p align="center"> | ||
Puedes abrir el directorio donde se aloja el resultado seleccionado pulsando <kbd>o</kbd>. | ||
Para salir de Npkill, utiliza <kbd>Q</kbd>, o si te sientes valiente, <kbd>Ctrl</kbd> + <kbd>c</kbd>. | ||
@@ -96,3 +98,3 @@ | ||
| -d, --directory | Permite seleccionar el directorio desde el que comienza la búsqueda. Por defecto, se empieza en . | | ||
| -D, --delete-all | ACTUALMENTE DESHABILITADA. Borra automáticamente todos los node_modules que se encuentran | | ||
| -D, --delete-all | Borra automáticamente todos los node_modules que se encuentren. Recomendable utilizar junto a `-x` | | ||
| -e, --hide-errors | Esconde los errores en el caso de que ocurra alguno | | ||
@@ -107,2 +109,3 @@ | -E, --exclude | Excluye directorios de la búsqueda (la lista de directorios debe estar entre comillas dobles "", cada directorio separado por ',' Ejemplo: "ignore1, ignore2") | | ||
| -x, --exclude-hidden-directories | Excluye directorios ocultos (directorios "dot") de la búsqueda | | ||
| --dry-run | No borra nada (simula un tiempo de borrado aleatorio) | | ||
| -v, --version | Muestra la versión de Npkill | | ||
@@ -153,3 +156,2 @@ | ||
```bash | ||
# Deshabilitado por razones de seguridad (puedes utilizar esta opción en la versión 0.2.4 bajo tu propia responsabilidad) | ||
npkill -d ~/backups/ --delete-all | ||
@@ -156,0 +158,0 @@ ``` |
@@ -86,4 +86,6 @@ <p align="center"> | ||
Move between the listed folders with <kbd>↓</kbd> <kbd>↑</kbd>, and use <kbd>Space</kbd> or <kbd>Del</kbd> to delete the selected folder. | ||
You can also use <kbd>j</kbd> and <kbd>k</kbd> to move between the results | ||
You can also use <kbd>j</kbd> and <kbd>k</kbd> to move between the results. | ||
You can open the directory where the selected result is placed by pressing <kbd>o</kbd>. | ||
To exit, <kbd>Q</kbd> or <kbd>Ctrl</kbd> + <kbd>c</kbd> if you're brave. | ||
@@ -101,3 +103,3 @@ | ||
| -d, --directory | Set the directory from which to begin searching. By default, starting-point is . | | ||
| -D, --delete-all | CURRENTLY DISABLED. Automatically delete all node_modules folders that are found | | ||
| -D, --delete-all | Automatically delete all node_modules folders that are found. Suggested to be used together with `-x`. | | ||
| -e, --hide-errors | Hide errors if any | | ||
@@ -112,2 +114,3 @@ | -E, --exclude | Exclude directories from search (directory list must be inside double quotes "", each directory separated by ',' ) Example: "ignore1, ignore2" | | ||
| -x, --exclude-hidden-directories | Exclude hidden directories ("dot" directories) from search. | | ||
| --dry-run | It does not delete anything (will simulate it with a random delay). | | ||
| -v, --version | Show npkill version | | ||
@@ -158,3 +161,2 @@ | ||
```bash | ||
# Disabled for security reasons (you can use it in version 0.2.4 at your risk) | ||
npkill -d ~/backups/ --delete-all | ||
@@ -161,0 +163,0 @@ ``` |
134261
70
2834
255
6
+ Addedopen-file-explorer@^1.0.2
+ Added@sindresorhus/is@4.6.0(transitive)
+ Addedchar-regex@1.0.2(transitive)
+ Addedemojilib@2.4.0(transitive)
+ Addedget-folder-size@4.0.0(transitive)
+ Addednode-emoji@2.2.0(transitive)
+ Addedopen-file-explorer@1.0.2(transitive)
+ Addedskin-tone@2.0.0(transitive)
+ Addedunicode-emoji-modifier-base@1.0.0(transitive)
- Removedget-folder-size@2.0.1(transitive)
- Removedlodash@4.17.21(transitive)
- Removednode-emoji@1.11.0(transitive)
- Removedtiny-each-async@2.0.3(transitive)
Updatedansi-escapes@^6.2.1
Updatedget-folder-size@^4.0.0
Updatednode-emoji@^2.1.3
Updatedrxjs@^7.8.1