aris-mac-cleaner 2.0.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 +68 -0
- package/bin/cli.js +247 -0
- package/package.json +32 -0
package/README.md
ADDED
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
# Aris Mac Cleaner π§Ή
|
|
2
|
+
|
|
3
|
+
Sistema de manutenΓ§Γ£o automΓ‘tica para macOS.
|
|
4
|
+
|
|
5
|
+
**Criado por Salvador Reis**
|
|
6
|
+
|
|
7
|
+
## InstalaΓ§Γ£o rΓ‘pida
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npx aris-mac-cleaner
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
Ou instalar globalmente:
|
|
14
|
+
|
|
15
|
+
```bash
|
|
16
|
+
npm install -g aris-mac-cleaner
|
|
17
|
+
aris-mac-cleaner
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
## O que faz?
|
|
21
|
+
|
|
22
|
+
- β
Limpa caches (Chrome, Spotify, npm, Xcode, etc.)
|
|
23
|
+
- β
Remove ficheiros temporΓ‘rios
|
|
24
|
+
- β
Liberta espaΓ§o em disco
|
|
25
|
+
- β
Mostra diagnΓ³stico do sistema
|
|
26
|
+
- β
Calcula Health Score (0-100)
|
|
27
|
+
|
|
28
|
+
## Screenshot
|
|
29
|
+
|
|
30
|
+
```
|
|
31
|
+
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
|
32
|
+
β ARIS MAC CLEANER v2.0 β
|
|
33
|
+
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
|
34
|
+
|
|
35
|
+
βΆ FASE 1: DIAGNΓSTICO DO SISTEMA
|
|
36
|
+
β’ Disco 92Gi livres β Excelente
|
|
37
|
+
β’ RAM 60% em uso β OK
|
|
38
|
+
β’ Swap 615MB β OK
|
|
39
|
+
β’ CPU 42% β OK
|
|
40
|
+
|
|
41
|
+
βΆ FASE 2: ANΓLISE DE LIMPEZA
|
|
42
|
+
β’ Google Cache 142 MB
|
|
43
|
+
β’ npm Cache 1522 MB
|
|
44
|
+
β Total a libertar: ~2 GB
|
|
45
|
+
|
|
46
|
+
βΆ FASE 3: LIMPEZA EM PROGRESSO
|
|
47
|
+
β npm cache
|
|
48
|
+
β Google Cache
|
|
49
|
+
β Logs do sistema
|
|
50
|
+
|
|
51
|
+
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
|
52
|
+
β RELATΓRIO FINAL β
|
|
53
|
+
β Disco: 94Gi disponΓveis β
|
|
54
|
+
β Libertado: +2 GB β
|
|
55
|
+
β Health Score: 100/100 - Excelente β
|
|
56
|
+
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
|
57
|
+
|
|
58
|
+
β Pronto para trabalhar!
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
## Requisitos
|
|
62
|
+
|
|
63
|
+
- macOS (Darwin)
|
|
64
|
+
- Node.js >= 14
|
|
65
|
+
|
|
66
|
+
## LicenΓ§a
|
|
67
|
+
|
|
68
|
+
MIT Β© Salvador Reis
|
package/bin/cli.js
ADDED
|
@@ -0,0 +1,247 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
const { execSync, spawnSync } = require('child_process');
|
|
4
|
+
const os = require('os');
|
|
5
|
+
const fs = require('fs');
|
|
6
|
+
const path = require('path');
|
|
7
|
+
|
|
8
|
+
// Cores
|
|
9
|
+
const colors = {
|
|
10
|
+
reset: '\x1b[0m',
|
|
11
|
+
red: '\x1b[31m',
|
|
12
|
+
green: '\x1b[32m',
|
|
13
|
+
yellow: '\x1b[33m',
|
|
14
|
+
blue: '\x1b[34m',
|
|
15
|
+
cyan: '\x1b[36m',
|
|
16
|
+
white: '\x1b[37m',
|
|
17
|
+
bold: '\x1b[1m',
|
|
18
|
+
dim: '\x1b[2m'
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
const c = colors;
|
|
22
|
+
|
|
23
|
+
// Verificar se Γ© macOS
|
|
24
|
+
if (os.platform() !== 'darwin') {
|
|
25
|
+
console.log(`${c.red}Este programa sΓ³ funciona em macOS${c.reset}`);
|
|
26
|
+
process.exit(1);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
const HOME = os.homedir();
|
|
30
|
+
|
|
31
|
+
// FunΓ§Γ£o para executar comandos
|
|
32
|
+
function exec(cmd) {
|
|
33
|
+
try {
|
|
34
|
+
return execSync(cmd, { encoding: 'utf8', stdio: ['pipe', 'pipe', 'pipe'] }).trim();
|
|
35
|
+
} catch (e) {
|
|
36
|
+
return '';
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
// FunΓ§Γ£o para obter tamanho de pasta
|
|
41
|
+
function getSize(path) {
|
|
42
|
+
try {
|
|
43
|
+
const result = exec(`du -sm "${path}" 2>/dev/null`);
|
|
44
|
+
return parseInt(result.split('\t')[0]) || 0;
|
|
45
|
+
} catch (e) {
|
|
46
|
+
return 0;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// FunΓ§Γ£o para limpar pasta
|
|
51
|
+
function cleanPath(p, name) {
|
|
52
|
+
const fullPath = p.replace('~', HOME);
|
|
53
|
+
if (fs.existsSync(fullPath)) {
|
|
54
|
+
try {
|
|
55
|
+
execSync(`rm -rf "${fullPath}"`, { stdio: 'ignore' });
|
|
56
|
+
console.log(` ${c.green}β${c.reset} ${name}`);
|
|
57
|
+
return true;
|
|
58
|
+
} catch (e) {
|
|
59
|
+
return false;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
return false;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
// Limpar consola
|
|
66
|
+
console.clear();
|
|
67
|
+
|
|
68
|
+
// Header
|
|
69
|
+
console.log();
|
|
70
|
+
console.log(`${c.cyan}ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
71
|
+
console.log(`${c.cyan}β${c.reset}${c.bold}${c.white} ARIS MAC CLEANER v2.0 ${c.reset}${c.cyan}β${c.reset}`);
|
|
72
|
+
console.log(`${c.cyan}β${c.reset}${c.dim} por Salvador Reis ${c.reset}${c.cyan}β${c.reset}`);
|
|
73
|
+
console.log(`${c.cyan}ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
74
|
+
console.log();
|
|
75
|
+
|
|
76
|
+
// FASE 1: DIAGNΓSTICO
|
|
77
|
+
console.log(`${c.white}βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
78
|
+
console.log(`${c.white}β${c.reset} ${c.blue}βΆ FASE 1: DIAGNΓSTICO DO SISTEMA${c.reset} ${c.white}β${c.reset}`);
|
|
79
|
+
console.log(`${c.white}βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
80
|
+
console.log();
|
|
81
|
+
|
|
82
|
+
// Disco
|
|
83
|
+
const diskInfo = exec("df -h / | tail -1").split(/\s+/);
|
|
84
|
+
const diskTotal = diskInfo[1];
|
|
85
|
+
const diskUsed = diskInfo[2];
|
|
86
|
+
const diskFree = diskInfo[3];
|
|
87
|
+
const diskPercent = parseInt(diskInfo[4]);
|
|
88
|
+
const diskFreeBefore = parseInt(exec("df / | tail -1").split(/\s+/)[3]);
|
|
89
|
+
|
|
90
|
+
let diskStatus = `${c.green}β Excelente${c.reset}`;
|
|
91
|
+
if (diskPercent >= 80) diskStatus = `${c.red}β CrΓtico${c.reset}`;
|
|
92
|
+
else if (diskPercent >= 50) diskStatus = `${c.yellow}! AtenΓ§Γ£o${c.reset}`;
|
|
93
|
+
|
|
94
|
+
// RAM
|
|
95
|
+
const ramFreePercent = parseInt(exec("memory_pressure 2>/dev/null | grep 'System-wide' | awk '{print $5}'")) || 50;
|
|
96
|
+
const ramUsedPercent = 100 - ramFreePercent;
|
|
97
|
+
|
|
98
|
+
let ramStatus = `${c.green}β OK${c.reset}`;
|
|
99
|
+
if (ramUsedPercent >= 90) ramStatus = `${c.red}β CrΓtico${c.reset}`;
|
|
100
|
+
else if (ramUsedPercent >= 70) ramStatus = `${c.yellow}! PressΓ£o${c.reset}`;
|
|
101
|
+
|
|
102
|
+
// Swap
|
|
103
|
+
const swapUsed = parseInt(exec("sysctl vm.swapusage 2>/dev/null | awk '{print int($7)}'")) || 0;
|
|
104
|
+
|
|
105
|
+
let swapStatus = `${c.green}β OK${c.reset}`;
|
|
106
|
+
if (swapUsed >= 8000) swapStatus = `${c.red}β CrΓtico${c.reset}`;
|
|
107
|
+
else if (swapUsed >= 2000) swapStatus = `${c.yellow}! Alto${c.reset}`;
|
|
108
|
+
|
|
109
|
+
// CPU
|
|
110
|
+
const cpuIdle = parseFloat(exec("top -l 1 | grep 'CPU usage' | awk '{print $7}'")) || 50;
|
|
111
|
+
const cpuUsed = Math.round(100 - cpuIdle);
|
|
112
|
+
|
|
113
|
+
let cpuStatus = `${c.green}β OK${c.reset}`;
|
|
114
|
+
if (cpuUsed >= 80) cpuStatus = `${c.red}β Sobrecarregado${c.reset}`;
|
|
115
|
+
else if (cpuUsed >= 50) cpuStatus = `${c.yellow}! Ocupado${c.reset}`;
|
|
116
|
+
|
|
117
|
+
console.log(` β’ ${c.bold}Disco${c.reset} ${diskFree} livres de ${diskTotal} ${diskStatus}`);
|
|
118
|
+
console.log(` β’ ${c.bold}RAM${c.reset} ${ramUsedPercent}% em uso ${ramStatus}`);
|
|
119
|
+
console.log(` β’ ${c.bold}Swap${c.reset} ${swapUsed}MB em uso ${swapStatus}`);
|
|
120
|
+
console.log(` β’ ${c.bold}CPU${c.reset} ${cpuUsed}% em uso ${cpuStatus}`);
|
|
121
|
+
console.log();
|
|
122
|
+
|
|
123
|
+
// FASE 2: ANΓLISE
|
|
124
|
+
console.log(`${c.white}βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
125
|
+
console.log(`${c.white}β${c.reset} ${c.blue}βΆ FASE 2: ANΓLISE DE LIMPEZA${c.reset} ${c.white}β${c.reset}`);
|
|
126
|
+
console.log(`${c.white}βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
127
|
+
console.log();
|
|
128
|
+
|
|
129
|
+
const cleanPaths = [
|
|
130
|
+
{ path: `${HOME}/Library/Caches/Google`, name: 'Google Cache' },
|
|
131
|
+
{ path: `${HOME}/Library/Caches/com.spotify.client`, name: 'Spotify Cache' },
|
|
132
|
+
{ path: `${HOME}/Library/Caches/CocoaPods`, name: 'CocoaPods Cache' },
|
|
133
|
+
{ path: `${HOME}/Library/Caches/Homebrew`, name: 'Homebrew Cache' },
|
|
134
|
+
{ path: `${HOME}/Library/Caches/typescript`, name: 'TypeScript Cache' },
|
|
135
|
+
{ path: `${HOME}/Library/Caches/node-gyp`, name: 'Node-gyp Cache' },
|
|
136
|
+
{ path: `${HOME}/Library/Caches/pip`, name: 'Pip Cache' },
|
|
137
|
+
{ path: `${HOME}/Library/Caches/yarn`, name: 'Yarn Cache' },
|
|
138
|
+
{ path: `${HOME}/Library/Caches/pnpm`, name: 'pnpm Cache' },
|
|
139
|
+
{ path: `${HOME}/.npm`, name: 'npm Cache' },
|
|
140
|
+
{ path: `${HOME}/Library/Application Support/Code/User/workspaceStorage`, name: 'VS Code Storage' },
|
|
141
|
+
{ path: `${HOME}/Library/Developer/Xcode/DerivedData`, name: 'Xcode DerivedData' },
|
|
142
|
+
{ path: `${HOME}/Library/Application Support/Google/GoogleUpdater/crx_cache`, name: 'Google Updater' },
|
|
143
|
+
{ path: `${HOME}/Library/Application Support/Google/Chrome/component_crx_cache`, name: 'Chrome Components' },
|
|
144
|
+
];
|
|
145
|
+
|
|
146
|
+
let totalClean = 0;
|
|
147
|
+
|
|
148
|
+
cleanPaths.forEach(item => {
|
|
149
|
+
const size = getSize(item.path);
|
|
150
|
+
if (size > 0) {
|
|
151
|
+
totalClean += size;
|
|
152
|
+
console.log(` β’ ${item.name.padEnd(25)} ${c.dim}${String(size).padStart(6)} MB${c.reset}`);
|
|
153
|
+
}
|
|
154
|
+
});
|
|
155
|
+
|
|
156
|
+
console.log();
|
|
157
|
+
console.log(` β ${c.bold}Total a libertar:${c.reset} ${c.green}~${Math.round(totalClean / 1024)} GB${c.reset} ${c.dim}(${totalClean} MB)${c.reset}`);
|
|
158
|
+
console.log();
|
|
159
|
+
|
|
160
|
+
// FASE 3: LIMPEZA
|
|
161
|
+
console.log(`${c.white}βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
162
|
+
console.log(`${c.white}β${c.reset} ${c.blue}βΆ FASE 3: LIMPEZA EM PROGRESSO${c.reset} ${c.white}β${c.reset}`);
|
|
163
|
+
console.log(`${c.white}βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
164
|
+
console.log();
|
|
165
|
+
|
|
166
|
+
// npm cache
|
|
167
|
+
try {
|
|
168
|
+
execSync('npm cache clean --force 2>/dev/null', { stdio: 'ignore' });
|
|
169
|
+
console.log(` ${c.green}β${c.reset} npm cache`);
|
|
170
|
+
} catch (e) {}
|
|
171
|
+
|
|
172
|
+
// Limpar paths
|
|
173
|
+
cleanPaths.forEach(item => {
|
|
174
|
+
cleanPath(item.path, item.name);
|
|
175
|
+
});
|
|
176
|
+
|
|
177
|
+
// Claude versΓ΅es antigas
|
|
178
|
+
const claudeVersionsPath = `${HOME}/.local/share/claude/versions`;
|
|
179
|
+
if (fs.existsSync(claudeVersionsPath)) {
|
|
180
|
+
try {
|
|
181
|
+
const versions = fs.readdirSync(claudeVersionsPath).sort().reverse();
|
|
182
|
+
if (versions.length > 1) {
|
|
183
|
+
versions.slice(1).forEach(v => {
|
|
184
|
+
fs.rmSync(path.join(claudeVersionsPath, v), { recursive: true, force: true });
|
|
185
|
+
});
|
|
186
|
+
console.log(` ${c.green}β${c.reset} Claude (${versions.length - 1} versΓ΅es antigas)`);
|
|
187
|
+
}
|
|
188
|
+
} catch (e) {}
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
// Downloads antigos
|
|
192
|
+
try {
|
|
193
|
+
execSync('find ~/Downloads -name "*.dmg" -mtime +7 -delete 2>/dev/null', { stdio: 'ignore' });
|
|
194
|
+
execSync('find ~/Downloads -name "*.zip" -mtime +30 -delete 2>/dev/null', { stdio: 'ignore' });
|
|
195
|
+
} catch (e) {}
|
|
196
|
+
|
|
197
|
+
// Logs
|
|
198
|
+
try {
|
|
199
|
+
execSync('rm -rf ~/Library/Logs/*.log 2>/dev/null', { stdio: 'ignore' });
|
|
200
|
+
console.log(` ${c.green}β${c.reset} Logs do sistema`);
|
|
201
|
+
} catch (e) {}
|
|
202
|
+
|
|
203
|
+
console.log();
|
|
204
|
+
|
|
205
|
+
// FASE 4: RESULTADO
|
|
206
|
+
const diskFreeAfter = parseInt(exec("df / | tail -1").split(/\s+/)[3]);
|
|
207
|
+
const freed = Math.round((diskFreeAfter - diskFreeBefore) / 1024 / 1024);
|
|
208
|
+
const diskFreeGBAfter = exec("df -h / | tail -1").split(/\s+/)[3];
|
|
209
|
+
const diskPercentAfter = parseInt(exec("df / | tail -1").split(/\s+/)[4]);
|
|
210
|
+
|
|
211
|
+
// Health Score
|
|
212
|
+
let healthScore = 100;
|
|
213
|
+
if (diskPercentAfter > 80) healthScore -= 30;
|
|
214
|
+
else if (diskPercentAfter > 60) healthScore -= 10;
|
|
215
|
+
if (ramUsedPercent > 90) healthScore -= 30;
|
|
216
|
+
else if (ramUsedPercent > 70) healthScore -= 10;
|
|
217
|
+
if (swapUsed > 8000) healthScore -= 20;
|
|
218
|
+
else if (swapUsed > 4000) healthScore -= 10;
|
|
219
|
+
|
|
220
|
+
let healthColor = c.green;
|
|
221
|
+
let healthText = 'Excelente';
|
|
222
|
+
if (healthScore < 60) { healthColor = c.red; healthText = 'AtenΓ§Γ£o'; }
|
|
223
|
+
else if (healthScore < 80) { healthColor = c.yellow; healthText = 'Bom'; }
|
|
224
|
+
|
|
225
|
+
console.log(`${c.cyan}ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
226
|
+
console.log(`${c.cyan}β${c.reset}${c.bold}${c.white} RELATΓRIO FINAL ${c.reset}${c.cyan}β${c.reset}`);
|
|
227
|
+
console.log(`${c.cyan}β βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ£${c.reset}`);
|
|
228
|
+
console.log(`${c.cyan}β${c.reset} ${c.cyan}β${c.reset}`);
|
|
229
|
+
console.log(`${c.cyan}β${c.reset} ${c.bold}Disco${c.reset} ${c.cyan}β${c.reset}`);
|
|
230
|
+
console.log(`${c.cyan}β${c.reset} β DisponΓvel: ${c.green}${diskFreeGBAfter}${c.reset} ${c.cyan}β${c.reset}`);
|
|
231
|
+
if (freed > 0) {
|
|
232
|
+
console.log(`${c.cyan}β${c.reset} β Libertado: ${c.green}+${freed} GB${c.reset} ${c.cyan}β${c.reset}`);
|
|
233
|
+
}
|
|
234
|
+
console.log(`${c.cyan}β${c.reset} ${c.cyan}β${c.reset}`);
|
|
235
|
+
console.log(`${c.cyan}β${c.reset} ${c.bold}Health Score${c.reset} ${c.cyan}β${c.reset}`);
|
|
236
|
+
console.log(`${c.cyan}β${c.reset} β ${healthColor}${healthScore}/100 - ${healthText}${c.reset} ${c.cyan}β${c.reset}`);
|
|
237
|
+
console.log(`${c.cyan}β${c.reset} ${c.cyan}β${c.reset}`);
|
|
238
|
+
console.log(`${c.cyan}ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ${c.reset}`);
|
|
239
|
+
console.log();
|
|
240
|
+
|
|
241
|
+
if (swapUsed > 5000 || ramUsedPercent > 85) {
|
|
242
|
+
console.log(`${c.yellow}β RecomendaΓ§Γ£o: Reinicia o Mac para limpar memΓ³ria${c.reset}`);
|
|
243
|
+
console.log();
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
console.log(`${c.green}β Pronto para trabalhar!${c.reset}`);
|
|
247
|
+
console.log();
|
package/package.json
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "aris-mac-cleaner",
|
|
3
|
+
"version": "2.0.0",
|
|
4
|
+
"description": "Sistema de manutenΓ§Γ£o automΓ‘tica para macOS - Limpa caches, liberta espaΓ§o e mostra Health Score",
|
|
5
|
+
"author": "Salvador Reis",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"bin": {
|
|
8
|
+
"aris-mac-cleaner": "./bin/cli.js"
|
|
9
|
+
},
|
|
10
|
+
"keywords": [
|
|
11
|
+
"mac",
|
|
12
|
+
"cleaner",
|
|
13
|
+
"macos",
|
|
14
|
+
"cleanup",
|
|
15
|
+
"cache",
|
|
16
|
+
"maintenance",
|
|
17
|
+
"optimization"
|
|
18
|
+
],
|
|
19
|
+
"repository": {
|
|
20
|
+
"type": "git",
|
|
21
|
+
"url": "https://github.com/salvadorreis/mac-cleaner-pro"
|
|
22
|
+
},
|
|
23
|
+
"engines": {
|
|
24
|
+
"node": ">=14.0.0"
|
|
25
|
+
},
|
|
26
|
+
"os": [
|
|
27
|
+
"darwin"
|
|
28
|
+
],
|
|
29
|
+
"files": [
|
|
30
|
+
"bin"
|
|
31
|
+
]
|
|
32
|
+
}
|