@amirdaraee/namewise 0.5.3 → 0.5.5

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.
Files changed (83) hide show
  1. package/CHANGELOG.md +9 -0
  2. package/README.md +60 -60
  3. package/dist/index.js +0 -0
  4. package/dist/services/claude-service.d.ts.map +1 -1
  5. package/dist/services/claude-service.js +3 -0
  6. package/dist/services/claude-service.js.map +1 -1
  7. package/dist/services/lmstudio-service.d.ts +1 -0
  8. package/dist/services/lmstudio-service.d.ts.map +1 -1
  9. package/dist/services/lmstudio-service.js +16 -1
  10. package/dist/services/lmstudio-service.js.map +1 -1
  11. package/dist/services/ollama-service.d.ts +1 -0
  12. package/dist/services/ollama-service.d.ts.map +1 -1
  13. package/dist/services/ollama-service.js +16 -1
  14. package/dist/services/ollama-service.js.map +1 -1
  15. package/dist/services/openai-service.d.ts.map +1 -1
  16. package/dist/services/openai-service.js +3 -0
  17. package/dist/services/openai-service.js.map +1 -1
  18. package/package.json +8 -8
  19. package/.github/ISSUE_TEMPLATE/bug_report.yml +0 -82
  20. package/.github/ISSUE_TEMPLATE/feature_request.yml +0 -61
  21. package/.github/workflows/auto-release.yml +0 -81
  22. package/.github/workflows/build.yml +0 -55
  23. package/.github/workflows/publish.yml +0 -134
  24. package/.github/workflows/test.yml +0 -45
  25. package/eng.traineddata +0 -0
  26. package/src/cli/commands.ts +0 -64
  27. package/src/cli/rename.ts +0 -171
  28. package/src/index.ts +0 -54
  29. package/src/parsers/excel-parser.ts +0 -66
  30. package/src/parsers/factory.ts +0 -38
  31. package/src/parsers/pdf-parser.ts +0 -99
  32. package/src/parsers/text-parser.ts +0 -43
  33. package/src/parsers/word-parser.ts +0 -50
  34. package/src/services/ai-factory.ts +0 -39
  35. package/src/services/claude-service.ts +0 -119
  36. package/src/services/file-renamer.ts +0 -141
  37. package/src/services/lmstudio-service.ts +0 -161
  38. package/src/services/ollama-service.ts +0 -191
  39. package/src/services/openai-service.ts +0 -117
  40. package/src/types/index.ts +0 -76
  41. package/src/types/pdf-extraction.d.ts +0 -7
  42. package/src/utils/ai-prompts.ts +0 -76
  43. package/src/utils/file-templates.ts +0 -275
  44. package/src/utils/naming-conventions.ts +0 -67
  45. package/src/utils/pdf-to-image.ts +0 -137
  46. package/tests/data/console-test-1.txt +0 -1
  47. package/tests/data/console-test-2.txt +0 -1
  48. package/tests/data/console-test-long-filename-for-display-testing.txt +0 -1
  49. package/tests/data/empty-file.txt +0 -0
  50. package/tests/data/failure.txt +0 -1
  51. package/tests/data/file1.txt +0 -1
  52. package/tests/data/file2.txt +0 -1
  53. package/tests/data/much-longer-filename-to-test-clearing.txt +0 -1
  54. package/tests/data/sample-markdown.md +0 -9
  55. package/tests/data/sample-pdf.pdf +0 -0
  56. package/tests/data/sample-text.txt +0 -25
  57. package/tests/data/short.txt +0 -1
  58. package/tests/data/single-file.txt +0 -1
  59. package/tests/data/success.txt +0 -1
  60. package/tests/data/this-is-a-very-long-filename-that-should-be-truncated-for-better-display-purposes.txt +0 -1
  61. package/tests/data/very-long-filename-that-should-be-cleared-properly.txt +0 -1
  62. package/tests/data/x.txt +0 -1
  63. package/tests/integration/ai-prompting.test.ts +0 -386
  64. package/tests/integration/end-to-end.test.ts +0 -209
  65. package/tests/integration/person-name-extraction.test.ts +0 -440
  66. package/tests/integration/workflow.test.ts +0 -336
  67. package/tests/mocks/mock-ai-service.ts +0 -58
  68. package/tests/unit/cli/commands.test.ts +0 -169
  69. package/tests/unit/parsers/factory.test.ts +0 -100
  70. package/tests/unit/parsers/pdf-parser.test.ts +0 -63
  71. package/tests/unit/parsers/text-parser.test.ts +0 -85
  72. package/tests/unit/services/ai-factory.test.ts +0 -85
  73. package/tests/unit/services/claude-service.test.ts +0 -188
  74. package/tests/unit/services/file-renamer.test.ts +0 -514
  75. package/tests/unit/services/lmstudio-service.test.ts +0 -326
  76. package/tests/unit/services/ollama-service.test.ts +0 -264
  77. package/tests/unit/services/openai-service.test.ts +0 -196
  78. package/tests/unit/utils/ai-prompts.test.ts +0 -213
  79. package/tests/unit/utils/file-templates.test.ts +0 -199
  80. package/tests/unit/utils/naming-conventions.test.ts +0 -88
  81. package/tests/unit/utils/pdf-to-image.test.ts +0 -127
  82. package/tsconfig.json +0 -20
  83. package/vitest.config.ts +0 -30
@@ -1,61 +0,0 @@
1
- name: Feature Request
2
- description: Suggest an idea for this project
3
- title: "[Feature]: "
4
- labels: ["enhancement", "feature-request"]
5
- body:
6
- - type: markdown
7
- attributes:
8
- value: |
9
- Thanks for suggesting a new feature!
10
-
11
- - type: textarea
12
- id: problem
13
- attributes:
14
- label: Problem Description
15
- description: Is your feature request related to a problem? Please describe.
16
- placeholder: A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
17
-
18
- - type: textarea
19
- id: solution
20
- attributes:
21
- label: Proposed Solution
22
- description: Describe the solution you'd like
23
- placeholder: A clear and concise description of what you want to happen.
24
- validations:
25
- required: true
26
-
27
- - type: textarea
28
- id: alternatives
29
- attributes:
30
- label: Alternative Solutions
31
- description: Describe alternatives you've considered
32
- placeholder: A clear and concise description of any alternative solutions or features you've considered.
33
-
34
- - type: dropdown
35
- id: priority
36
- attributes:
37
- label: Priority
38
- description: How important is this feature to you?
39
- options:
40
- - Low
41
- - Medium
42
- - High
43
- - Critical
44
- validations:
45
- required: true
46
-
47
- - type: checkboxes
48
- id: implementation
49
- attributes:
50
- label: Implementation
51
- description: Would you be willing to help implement this feature?
52
- options:
53
- - label: I would like to implement this feature
54
- - label: I need help implementing this feature
55
- - label: I can provide feedback during implementation
56
-
57
- - type: textarea
58
- id: additional
59
- attributes:
60
- label: Additional Context
61
- description: Add any other context, screenshots, or examples about the feature request here.
@@ -1,81 +0,0 @@
1
- name: Auto Release
2
-
3
- on:
4
- workflow_run:
5
- workflows: ["Build Pipeline"]
6
- types:
7
- - completed
8
- branches: [ main ]
9
-
10
- jobs:
11
- check-version:
12
- runs-on: ubuntu-latest
13
- # Only run if the build workflow succeeded
14
- if: ${{ github.event.workflow_run.conclusion == 'success' }}
15
- outputs:
16
- should-release: ${{ steps.version-check.outputs.should-release }}
17
- new-version: ${{ steps.version-check.outputs.new-version }}
18
-
19
- steps:
20
- - name: Checkout code
21
- uses: actions/checkout@v4
22
- with:
23
- fetch-depth: 0
24
-
25
- - name: Check if version changed
26
- id: version-check
27
- run: |
28
- # Get current version from package.json
29
- CURRENT_VERSION=$(node -p "require('./package.json').version")
30
- echo "Current version: $CURRENT_VERSION"
31
-
32
- # Check if tag already exists
33
- if git tag --list | grep -q "^v$CURRENT_VERSION$"; then
34
- echo "should-release=false" >> $GITHUB_OUTPUT
35
- echo "Tag v$CURRENT_VERSION already exists"
36
- else
37
- echo "should-release=true" >> $GITHUB_OUTPUT
38
- echo "new-version=$CURRENT_VERSION" >> $GITHUB_OUTPUT
39
- echo "New version detected: $CURRENT_VERSION"
40
- fi
41
-
42
- auto-release:
43
- needs: check-version
44
- runs-on: ubuntu-latest
45
- if: needs.check-version.outputs.should-release == 'true'
46
- permissions:
47
- contents: write
48
-
49
- steps:
50
- - name: Checkout code
51
- uses: actions/checkout@v4
52
-
53
- - name: Setup Node.js
54
- uses: actions/setup-node@v4
55
- with:
56
- node-version: '20.x'
57
- cache: 'npm'
58
- registry-url: 'https://registry.npmjs.org'
59
-
60
- - name: Install dependencies
61
- run: npm ci
62
-
63
- - name: Run tests
64
- run: npm run test:run
65
-
66
- - name: Build project
67
- run: npm run build
68
-
69
- - name: Create and push tag
70
- run: |
71
- git config --local user.email "action@github.com"
72
- git config --local user.name "GitHub Action"
73
- git tag -a "v${{ needs.check-version.outputs.new-version }}" -m "Release v${{ needs.check-version.outputs.new-version }}"
74
- git push origin "v${{ needs.check-version.outputs.new-version }}"
75
- env:
76
- GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
77
-
78
- - name: Publish to npm
79
- run: npm publish
80
- env:
81
- NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
@@ -1,55 +0,0 @@
1
- name: Build Pipeline
2
-
3
- on:
4
- workflow_dispatch: # Allows manual triggering
5
- push:
6
- branches: [ main ]
7
- workflow_call: # Allows this workflow to be called by other workflows
8
-
9
- jobs:
10
- test:
11
- name: Run Tests Before Build
12
- uses: ./.github/workflows/test.yml
13
-
14
- build:
15
- name: Build Project
16
- runs-on: ubuntu-latest
17
- needs: [test]
18
- if: ${{ needs.test.result == 'success' }}
19
-
20
- steps:
21
- - name: Checkout code
22
- uses: actions/checkout@v4
23
-
24
- - name: Setup Node.js
25
- uses: actions/setup-node@v4
26
- with:
27
- node-version: '22'
28
- cache: 'npm'
29
-
30
- - name: Install dependencies
31
- run: npm ci
32
-
33
- - name: Build project
34
- run: npm run build
35
-
36
- - name: Test CLI build
37
- run: |
38
- node dist/index.js --help
39
- node dist/index.js --version
40
-
41
- - name: Upload build artifacts
42
- uses: actions/upload-artifact@v4
43
- with:
44
- name: build-artifacts-${{ github.sha }}
45
- path: |
46
- dist/
47
- package.json
48
- package-lock.json
49
- README.md
50
- LICENSE
51
- CHANGELOG.md
52
- retention-days: 30
53
-
54
- - name: Build success notification
55
- run: echo "✅ Build completed successfully for commit ${{ github.sha }}"
@@ -1,134 +0,0 @@
1
- name: Publish Pipeline
2
-
3
- on:
4
- workflow_dispatch: # Allows manual triggering
5
- inputs:
6
- use_artifact:
7
- description: 'Use build artifact (provide artifact name or "latest")'
8
- required: false
9
- default: ''
10
- release:
11
- types: [published]
12
-
13
- jobs:
14
- build:
15
- name: Build for Publishing
16
- uses: ./.github/workflows/build.yml
17
- if: ${{ github.event.inputs.use_artifact == '' }}
18
-
19
- publish:
20
- name: Publish Package
21
- runs-on: ubuntu-latest
22
- needs: [build]
23
- if: ${{ always() && (needs.build.result == 'success' || github.event.inputs.use_artifact != '') }}
24
- environment: production # Requires environment approval for production
25
-
26
- steps:
27
- - name: Checkout code
28
- uses: actions/checkout@v4
29
-
30
- - name: Setup Node.js
31
- uses: actions/setup-node@v4
32
- with:
33
- node-version: '22'
34
- registry-url: 'https://registry.npmjs.org'
35
- cache: 'npm'
36
-
37
- - name: Download build artifacts (from current run)
38
- if: ${{ github.event.inputs.use_artifact == '' }}
39
- uses: actions/download-artifact@v4
40
- with:
41
- name: build-artifacts-${{ github.sha }}
42
- path: ./
43
-
44
- - name: Download build artifacts (from specific run)
45
- if: ${{ github.event.inputs.use_artifact != '' && github.event.inputs.use_artifact != 'latest' }}
46
- uses: actions/download-artifact@v4
47
- with:
48
- name: ${{ github.event.inputs.use_artifact }}
49
- path: ./
50
-
51
- - name: Download latest build artifacts
52
- if: ${{ github.event.inputs.use_artifact == 'latest' }}
53
- run: |
54
- echo "Downloading latest build artifacts..."
55
- gh run download --name "build-artifacts-*" --limit 1
56
- env:
57
- GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
58
-
59
- - name: Install dependencies (only for package.json)
60
- run: npm ci --production
61
-
62
- - name: Publish to NPM
63
- run: npm publish
64
- env:
65
- NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
66
-
67
- - name: Publish success notification
68
- run: echo "✅ Package published to NPM successfully"
69
-
70
- publish-github:
71
- name: Publish to GitHub Packages
72
- runs-on: ubuntu-latest
73
- needs: [build, publish]
74
- if: ${{ always() && needs.publish.result == 'success' }}
75
- permissions:
76
- contents: read
77
- packages: write
78
-
79
- steps:
80
- - name: Checkout code
81
- uses: actions/checkout@v4
82
-
83
- - name: Setup Node.js
84
- uses: actions/setup-node@v4
85
- with:
86
- node-version: '22'
87
- registry-url: 'https://npm.pkg.github.com'
88
- cache: 'npm'
89
-
90
- - name: Download build artifacts (reuse from publish job)
91
- if: ${{ github.event.inputs.use_artifact == '' }}
92
- uses: actions/download-artifact@v4
93
- with:
94
- name: build-artifacts-${{ github.sha }}
95
- path: ./
96
-
97
- - name: Download build artifacts (from specific run)
98
- if: ${{ github.event.inputs.use_artifact != '' && github.event.inputs.use_artifact != 'latest' }}
99
- uses: actions/download-artifact@v4
100
- with:
101
- name: ${{ github.event.inputs.use_artifact }}
102
- path: ./
103
-
104
- - name: Download latest build artifacts
105
- if: ${{ github.event.inputs.use_artifact == 'latest' }}
106
- run: |
107
- echo "Downloading latest build artifacts..."
108
- gh run download --name "build-artifacts-*" --limit 1
109
- env:
110
- GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
111
-
112
- - name: Install dependencies (only for package.json)
113
- run: npm ci --production
114
-
115
- - name: Configure package for GitHub Packages
116
- run: |
117
- cp package.json package.json.backup
118
- node -e "
119
- const pkg = require('./package.json');
120
- pkg.name = '@${{ github.repository_owner }}/' + pkg.name.split('/').pop();
121
- require('fs').writeFileSync('package.json', JSON.stringify(pkg, null, 2));
122
- "
123
-
124
- - name: Publish to GitHub Packages
125
- run: npm publish
126
- env:
127
- NODE_AUTH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
128
-
129
- - name: Restore original package.json
130
- run: mv package.json.backup package.json
131
- if: always()
132
-
133
- - name: GitHub Packages success notification
134
- run: echo "✅ Package published to GitHub Packages successfully"
@@ -1,45 +0,0 @@
1
- name: Test Pipeline
2
-
3
- on:
4
- workflow_dispatch: # Allows manual triggering
5
- workflow_call: # Allows this workflow to be called by other workflows
6
- pull_request:
7
- branches: [ main ]
8
-
9
- jobs:
10
- test:
11
- name: Run Tests
12
- runs-on: ubuntu-latest
13
-
14
- strategy:
15
- matrix:
16
- node-version: [18, 20, 22]
17
-
18
- steps:
19
- - name: Checkout code
20
- uses: actions/checkout@v4
21
-
22
- - name: Setup Node.js ${{ matrix.node-version }}
23
- uses: actions/setup-node@v4
24
- with:
25
- node-version: ${{ matrix.node-version }}
26
- cache: 'npm'
27
-
28
- - name: Install dependencies
29
- run: npm ci
30
-
31
- - name: Run linter (if available)
32
- run: npm run lint --if-present
33
-
34
- - name: Run tests
35
- run: npm run test:run
36
-
37
- - name: Generate coverage report
38
- run: npm run test:coverage
39
- if: matrix.node-version == '22'
40
-
41
- - name: Upload coverage reports
42
- uses: codecov/codecov-action@v3
43
- if: matrix.node-version == '22'
44
- with:
45
- fail_ci_if_error: false
package/eng.traineddata DELETED
Binary file
@@ -1,64 +0,0 @@
1
- import { Command } from 'commander';
2
- import { renameFiles } from './rename.js';
3
-
4
- export function setupCommands(program: Command): void {
5
- program
6
- .command('rename')
7
- .description('🚀 Rename files in a directory based on their content using AI analysis')
8
- .argument('[directory]', 'Directory containing files to rename (default: current directory)', '.')
9
- .option('-p, --provider <provider>', 'AI provider (claude|openai|ollama|lmstudio)', 'claude')
10
- .option('-k, --api-key <key>', 'API key for cloud providers (or set CLAUDE_API_KEY/OPENAI_API_KEY)')
11
- .option('-c, --case <convention>', 'Naming convention (kebab-case|snake_case|camelCase|PascalCase|lowercase|UPPERCASE)', 'kebab-case')
12
- .option('-t, --template <category>', 'File category template (document|movie|music|series|photo|book|general|auto)', 'general')
13
- .option('-n, --name <personalName>', 'Personal name to include in filenames (for document/photo templates)')
14
- .option('-d, --date <format>', 'Date format to include (YYYY-MM-DD|YYYY|YYYYMMDD|none)', 'none')
15
- .option('--dry-run', 'Preview changes without actually renaming files (RECOMMENDED first!)', false)
16
- .option('--max-size <size>', 'Maximum file size in MB to process', '10')
17
- .option('--base-url <url>', 'Base URL for local LLM providers (default: ollama=http://localhost:11434, lmstudio=http://localhost:1234)')
18
- .option('--model <name>', 'Model name for local LLM providers (default: ollama=llama3.1, lmstudio=local-model)')
19
- .addHelpText('after', `
20
-
21
- 🔍 How it works:
22
- 1. Scans directory for supported files (PDF, DOCX, XLSX, TXT, MD, RTF)
23
- 2. Extracts content and metadata from each file
24
- 3. For scanned PDFs with no text, converts to image for AI vision analysis
25
- 4. Uses AI to analyze content and generate descriptive names
26
- 5. Applies your chosen template and naming convention
27
- 6. Renames files (or shows preview with --dry-run)
28
-
29
- 💡 Pro Tips:
30
- • Always use --dry-run first to preview changes
31
- • Use 'auto' template for smart file type detection
32
- • Personal templates work great for documents and photos
33
- • Scanned PDFs are automatically handled via AI vision (Claude/OpenAI/Ollama)
34
- • Set API keys as environment variables for cloud providers
35
- • Local LLMs (Ollama/LMStudio) require running servers first
36
-
37
- 🖥️ Local LLM Setup:
38
- • Ollama: Start with 'ollama serve' (default: http://localhost:11434)
39
- • LMStudio: Enable local server mode (default: http://localhost:1234)
40
-
41
- 📝 Examples:
42
- # Current directory (no directory argument needed)
43
- namewise rename --dry-run
44
- namewise rename --provider claude --template document --name "alice"
45
-
46
- # Specific directory
47
- namewise rename ./documents --dry-run
48
-
49
- # Cloud providers (require API keys)
50
- namewise rename ./docs --provider claude --template document --name "alice"
51
- namewise rename ./media --provider openai --template auto
52
-
53
- # Local LLMs (no API key needed)
54
- namewise rename --provider ollama --model llama3.1 --dry-run
55
- namewise rename ./documents --provider ollama --model llama3.1
56
- namewise rename ./contracts --provider lmstudio --base-url http://localhost:1234
57
-
58
- # Custom Ollama setup
59
- namewise rename ./files --provider ollama --base-url http://192.168.1.100:11434 --model codellama
60
- `)
61
- .action(async (directory, options) => {
62
- await renameFiles(directory, options);
63
- });
64
- }
package/src/cli/rename.ts DELETED
@@ -1,171 +0,0 @@
1
- import { promises as fs } from 'fs';
2
- import path from 'path';
3
- import inquirer from 'inquirer';
4
- import { FileInfo, Config, RenameResult, FileCategory, DateFormat } from '../types/index.js';
5
- import { DocumentParserFactory } from '../parsers/factory.js';
6
- import { AIServiceFactory } from '../services/ai-factory.js';
7
- import { FileRenamer } from '../services/file-renamer.js';
8
-
9
- export async function renameFiles(directory: string, options: any): Promise<void> {
10
- try {
11
- // Validate directory exists
12
- const stats = await fs.stat(directory);
13
- if (!stats.isDirectory()) {
14
- throw new Error(`${directory} is not a directory`);
15
- }
16
-
17
- // Get API key for cloud providers only
18
- let apiKey = options.apiKey;
19
- const requiresApiKey = ['claude', 'openai'].includes(options.provider);
20
-
21
- if (requiresApiKey && !apiKey) {
22
- // Check environment variables first
23
- if (options.provider === 'claude' && process.env.CLAUDE_API_KEY) {
24
- apiKey = process.env.CLAUDE_API_KEY;
25
- } else if (options.provider === 'openai' && process.env.OPENAI_API_KEY) {
26
- apiKey = process.env.OPENAI_API_KEY;
27
- } else {
28
- const keyPrompt = await inquirer.prompt([
29
- {
30
- type: 'password',
31
- name: 'apiKey',
32
- message: `Enter your ${options.provider} API key:`,
33
- mask: '*'
34
- }
35
- ]);
36
- apiKey = keyPrompt.apiKey;
37
- }
38
- }
39
-
40
- // Create config
41
- const config: Config = {
42
- aiProvider: options.provider,
43
- apiKey,
44
- maxFileSize: parseInt(options.maxSize) * 1024 * 1024, // Convert MB to bytes
45
- supportedExtensions: ['.pdf', '.docx', '.doc', '.xlsx', '.xls', '.txt'],
46
- dryRun: options.dryRun,
47
- namingConvention: options.case,
48
- templateOptions: {
49
- category: options.template as FileCategory,
50
- personalName: options.name,
51
- dateFormat: options.date as DateFormat
52
- },
53
- // Local LLM specific configuration
54
- localLLMConfig: {
55
- baseUrl: options.baseUrl,
56
- model: options.model
57
- }
58
- };
59
-
60
- // Initialize services
61
- const parserFactory = new DocumentParserFactory(config);
62
- const aiService = AIServiceFactory.create(config.aiProvider, apiKey, config.localLLMConfig);
63
- const fileRenamer = new FileRenamer(parserFactory, aiService, config);
64
-
65
- // Get files to process
66
- const files = await getFilesToProcess(directory, config.supportedExtensions);
67
-
68
- if (files.length === 0) {
69
- console.log('No supported files found in the directory.');
70
- return;
71
- }
72
-
73
- console.log(`Found ${files.length} files to process:`);
74
- files.forEach(file => console.log(` - ${file.name}`));
75
-
76
- // Confirm before processing
77
- if (!config.dryRun) {
78
- const confirm = await inquirer.prompt([
79
- {
80
- type: 'confirm',
81
- name: 'proceed',
82
- message: 'Do you want to proceed with renaming these files?',
83
- default: false
84
- }
85
- ]);
86
-
87
- if (!confirm.proceed) {
88
- console.log('Operation cancelled.');
89
- return;
90
- }
91
- }
92
-
93
- // Process files
94
- console.log('\nProcessing files...');
95
- const results = await fileRenamer.renameFiles(files);
96
-
97
- // Display results
98
- displayResults(results, config.dryRun);
99
-
100
- } catch (error) {
101
- console.error('Error:', error instanceof Error ? error.message : 'Unknown error');
102
- process.exit(1);
103
- }
104
- }
105
-
106
- async function getFilesToProcess(directory: string, supportedExtensions: string[]): Promise<FileInfo[]> {
107
- const files: FileInfo[] = [];
108
- const entries = await fs.readdir(directory, { withFileTypes: true });
109
-
110
- for (const entry of entries) {
111
- if (entry.isFile()) {
112
- const filePath = path.join(directory, entry.name);
113
- const extension = path.extname(entry.name).toLowerCase();
114
-
115
- if (supportedExtensions.includes(extension)) {
116
- const stats = await fs.stat(filePath);
117
-
118
- // Extract folder context
119
- const parentFolder = path.basename(directory);
120
- const fullPath = path.resolve(filePath);
121
- const folderPath = path.dirname(fullPath).split(path.sep).filter(p => p);
122
-
123
- files.push({
124
- path: filePath,
125
- name: entry.name,
126
- extension,
127
- size: stats.size,
128
- // File system metadata
129
- createdAt: stats.birthtime,
130
- modifiedAt: stats.mtime,
131
- accessedAt: stats.atime,
132
- // Context metadata
133
- parentFolder,
134
- folderPath: folderPath.slice(-3), // Last 3 folder levels for context
135
- // Document metadata will be populated by parsers
136
- documentMetadata: undefined
137
- });
138
- }
139
- }
140
- }
141
-
142
- return files;
143
- }
144
-
145
- function displayResults(results: RenameResult[], dryRun: boolean): void {
146
- const successful = results.filter(r => r.success);
147
- const failed = results.filter(r => !r.success);
148
-
149
- console.log(`\n${dryRun ? 'Preview' : 'Results'}:`);
150
- console.log(`✅ ${successful.length} files ${dryRun ? 'would be' : 'successfully'} renamed`);
151
-
152
- if (failed.length > 0) {
153
- console.log(`❌ ${failed.length} files failed`);
154
- }
155
-
156
- console.log('\nDetails:');
157
- results.forEach(result => {
158
- const status = result.success ? '✅' : '❌';
159
- const originalName = path.basename(result.originalPath);
160
- const newName = path.basename(result.newPath);
161
-
162
- if (result.success) {
163
- console.log(`${status} ${originalName} → ${newName}`);
164
- } else {
165
- console.log(`${status} ${originalName} (failed)`);
166
- if (result.error) {
167
- console.log(` Error: ${result.error}`);
168
- }
169
- }
170
- });
171
- }
package/src/index.ts DELETED
@@ -1,54 +0,0 @@
1
- #!/usr/bin/env node
2
-
3
- import { program } from 'commander';
4
- import { setupCommands } from './cli/commands.js';
5
-
6
- async function main() {
7
- program
8
- .name('namewise')
9
- .description('🤖 AI-powered CLI tool that intelligently renames files based on their content using Claude or OpenAI')
10
- .version('0.3.1')
11
- .addHelpText('after', `
12
-
13
- 📋 Supported File Types:
14
- PDF, DOCX/DOC, XLSX/XLS, TXT, MD, RTF
15
-
16
- 🎯 File Templates:
17
- • general - Simple descriptive names (default)
18
- • document - Personal docs with name/date: contract-john-20241205.pdf
19
- • movie - Movies with year: the-matrix-1999.mkv
20
- • series - TV shows: breaking-bad-s01e01.mkv
21
- • music - Music with artist: the-beatles-hey-jude.mp3
22
- • photo - Photos with context: vacation-paris-john-20241205.jpg
23
- • book - Books with author: george-orwell-1984.pdf
24
- • auto - AI auto-detects best template
25
-
26
- 🔧 Naming Conventions:
27
- kebab-case, snake_case, camelCase, PascalCase, lowercase, UPPERCASE
28
-
29
- 💡 Quick Examples:
30
- # Basic usage (dry run first - recommended!)
31
- namewise rename ./documents --dry-run
32
-
33
- # With Claude AI and specific template
34
- namewise rename ./documents --provider claude --template document --name "john"
35
-
36
- # Movies with auto-detection
37
- namewise rename ./movies --template auto --case kebab-case
38
-
39
- # OpenAI with custom settings
40
- namewise rename ./files --provider openai --api-key your-key --max-size 20
41
-
42
- 🔑 API Keys:
43
- Set environment variables: CLAUDE_API_KEY or OPENAI_API_KEY
44
- Or provide via --api-key flag
45
-
46
- 📖 More info: https://github.com/amirdaraee/namewise#readme
47
- `);
48
-
49
- setupCommands(program);
50
-
51
- await program.parseAsync(process.argv);
52
- }
53
-
54
- main().catch(console.error);