puter-cli 1.1.5 → 1.2.1

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.
@@ -0,0 +1,21 @@
1
+ # This workflow will run tests using node on every push
2
+
3
+ name: Build package
4
+
5
+ on: push
6
+
7
+ jobs:
8
+ build:
9
+ runs-on: ubuntu-latest
10
+
11
+ strategy:
12
+ matrix:
13
+ node-version: ['18.x', '20.x', '23.x']
14
+
15
+ steps:
16
+ - uses: actions/checkout@v4
17
+ - uses: actions/setup-node@v4
18
+ with:
19
+ node-version: ${{ matrix.node-version }}
20
+ - run: npm ci
21
+ - run: npm test
@@ -1,11 +1,9 @@
1
1
  # This workflow will run tests using node and then publish a package to GitHub Packages when a release is created
2
2
  # For more information see: https://docs.github.com/en/actions/publishing-packages/publishing-nodejs-packages
3
3
 
4
- name: Node.js Package
4
+ name: Publish package
5
5
 
6
- on:
7
- release:
8
- types: [created]
6
+ on: push
9
7
 
10
8
  jobs:
11
9
  build:
@@ -18,19 +16,16 @@ jobs:
18
16
  - run: npm ci
19
17
  - run: npm test
20
18
 
21
- publish-gpr:
19
+ publish-npm:
22
20
  needs: build
23
21
  runs-on: ubuntu-latest
24
- permissions:
25
- contents: read
26
- packages: write
27
22
  steps:
28
23
  - uses: actions/checkout@v4
29
24
  - uses: actions/setup-node@v4
30
25
  with:
31
26
  node-version: 20
32
- registry-url: https://npm.pkg.github.com/
27
+ registry-url: https://registry.npmjs.org/
33
28
  - run: npm ci
34
29
  - run: npm publish
35
30
  env:
36
- NODE_AUTH_TOKEN: ${{secrets.GITHUB_TOKEN}}
31
+ NODE_AUTH_TOKEN: ${{secrets.npm_token}}
package/CHANGELOG.md ADDED
@@ -0,0 +1,70 @@
1
+ ### Changelog
2
+
3
+ All notable changes to this project will be documented in this file. Dates are displayed in UTC.
4
+
5
+ Generated by [`auto-changelog`](https://github.com/CookPete/auto-changelog).
6
+
7
+ #### [v1.2.1](https://github.com/bitsnaps/puter-cli/compare/v1.2.0...v1.2.1)
8
+
9
+ - feat: update changelog [`028ca0c`](https://github.com/bitsnaps/puter-cli/commit/028ca0cf72e09bb63468d2b0a0ba7602d3b870ad)
10
+ - feat: auto-update changelog [`3004bed`](https://github.com/bitsnaps/puter-cli/commit/3004beda6afcf68cc916d544a45be85fa7e658e3)
11
+
12
+ #### [v1.2.0](https://github.com/bitsnaps/puter-cli/compare/v1.1.5...v1.2.0)
13
+
14
+ > 18 January 2025
15
+
16
+ - ci: attempt to fix npm install [`32fc508`](https://github.com/bitsnaps/puter-cli/commit/32fc508c4807119de485926674274b70e034288f)
17
+ - feat: basic history command [`18da28c`](https://github.com/bitsnaps/puter-cli/commit/18da28c83aa0760128d7b18e66e6b4d2b08b48d3)
18
+ - chore: improve structure [`70b67ad`](https://github.com/bitsnaps/puter-cli/commit/70b67adad5bd5e0bad4a9276160d17538d9b4bb6)
19
+
20
+ #### [v1.1.5](https://github.com/bitsnaps/puter-cli/compare/v1.1.4...v1.1.5)
21
+
22
+ > 16 January 2025
23
+
24
+ - fix: description arg handling & improve args parsing [`45c5a8c`](https://github.com/bitsnaps/puter-cli/commit/45c5a8c19034379e3cd7f30e724b8675d98bf28f)
25
+
26
+ #### [v1.1.4](https://github.com/bitsnaps/puter-cli/compare/v1.1.3...v1.1.4)
27
+
28
+ > 16 January 2025
29
+
30
+ - improve compatibility crypto api [`b015e6f`](https://github.com/bitsnaps/puter-cli/commit/b015e6f1318a2c4994675dd7390fab09d45bf3e9)
31
+ - fix: temporary disabled description [`c7456be`](https://github.com/bitsnaps/puter-cli/commit/c7456bed1c496f1a52156801aa4c0ea0191279c7)
32
+
33
+ #### [v1.1.3](https://github.com/bitsnaps/puter-cli/compare/v1.1.2...v1.1.3)
34
+
35
+ > 14 January 2025
36
+
37
+ - fix: unavailable subdomain when update app [`2497de4`](https://github.com/bitsnaps/puter-cli/commit/2497de41b5691df4d3a141952841c08cace4703c)
38
+
39
+ #### [v1.1.2](https://github.com/bitsnaps/puter-cli/compare/v1.1.1...v1.1.2)
40
+
41
+ > 14 January 2025
42
+
43
+ - grab latest version from npm [`9c32190`](https://github.com/bitsnaps/puter-cli/commit/9c321906415dfb5baa3d2bbba7b352f2766f8b84)
44
+
45
+ #### [v1.1.1](https://github.com/bitsnaps/puter-cli/compare/v1.1.0...v1.1.1)
46
+
47
+ > 14 January 2025
48
+
49
+ - Create npm-publish action [`48d9a70`](https://github.com/bitsnaps/puter-cli/commit/48d9a709417664900681e2219ea2af5e9bf33c01)
50
+ - update README: badges [`49241d7`](https://github.com/bitsnaps/puter-cli/commit/49241d7144c8c128955891a64acb448e79e1822c)
51
+
52
+ #### [v1.1.0](https://github.com/bitsnaps/puter-cli/compare/v1.0.3...v1.1.0)
53
+
54
+ > 14 January 2025
55
+
56
+ - feat: add support for 2FA logins [`#1`](https://github.com/bitsnaps/puter-cli/pull/1)
57
+
58
+ #### [v1.0.3](https://github.com/bitsnaps/puter-cli/compare/v1.0.1...v1.0.3)
59
+
60
+ > 13 January 2025
61
+
62
+ - update README [`479b8fc`](https://github.com/bitsnaps/puter-cli/commit/479b8fc9c784061146f453bc68759dbdb417ea1e)
63
+
64
+ #### v1.0.1
65
+
66
+ > 13 January 2025
67
+
68
+ - initial commit [`604d4a4`](https://github.com/bitsnaps/puter-cli/commit/604d4a47c8b593b7e24757c115df728f09233664)
69
+ - output nicely formatted table [`a0adb75`](https://github.com/bitsnaps/puter-cli/commit/a0adb75813bcecb21878c8ae7228b0ecbfdb397f)
70
+ - remove unused packages [`925b6cb`](https://github.com/bitsnaps/puter-cli/commit/925b6cbf827e619e65eb5afaa566a4d14e919cb8)
package/README.md CHANGED
@@ -1,7 +1,7 @@
1
1
  # Puter-CLI
2
2
 
3
3
  <p align="center">
4
- <img alt="test" src="https://github.com/bitsnaps/puter-cli/actions/workflows/npm-publish-github-packages.yml/badge.svg">
4
+ <img alt="test" src="https://github.com/bitsnaps/puter-cli/actions/workflows/npm-build.yml/badge.svg">
5
5
  <img alt="GitHub repo size" src="https://img.shields.io/github/repo-size/bitsnaps/puter-cli">
6
6
  </p>
7
7
 
@@ -123,17 +123,17 @@ P.S. These commands consider the current directory as the base path for every op
123
123
  #### User Information
124
124
  - **Get User Info**: Display user information.
125
125
  ```bash
126
- puter whoami
126
+ puter> whoami
127
127
  ```
128
128
 
129
129
  #### Disk Usage
130
130
  - **Check Disk Usage**: Display disk usage information.
131
131
  ```bash
132
- puter df
132
+ puter> df
133
133
  ```
134
134
  - **Get Usage Info**: Fetch usage information for services.
135
135
  ```bash
136
- puter usage
136
+ puter> usage
137
137
  ```
138
138
 
139
139
  #### Application Management
@@ -142,25 +142,25 @@ The **Application** are sepcial type of hosted web app, they're served from the
142
142
 
143
143
  - **List Applications**: List all applications.
144
144
  ```bash
145
- puter apps [period]
145
+ puter> apps [period]
146
146
  ```
147
147
  P.S. Please check the help command `help apps` for more details about any argument.
148
148
 
149
149
  - **Create Application**: Create a new application.
150
150
  ```bash
151
- puter app:create <name> [<directory>] [--description="My App Description"] [--url=<url>]
151
+ puter> app:create <name> [<directory>] [--description="My App Description"] [--url=<url>]
152
152
  ```
153
153
  P.S. By default a new `index.html` with basic content will be created, but you can set a directory when you create a new application as follows: `app:create nameOfApp ./appDir`, so all files will be copied to the `AppData` directoy, you can then update your app using `app:update <name> <remote_dir>`. This command will attempt to create a subdomain with a random `uid` prefixed with the name of the app.
154
154
 
155
155
  - **Update Application**: Update an application.
156
156
  ```bash
157
- puter app:update <name> <remote_dir>
157
+ puter> app:update <name> <remote_dir>
158
158
  ```
159
159
  **IMPORTANT** All existing files will be overwritten, new files are copied, other files are just ignored.
160
160
 
161
161
  - **Delete Application**: Delete an application.
162
162
  ```bash
163
- puter app:delete [-f] <name>
163
+ puter> app:delete [-f] <name>
164
164
  ```
165
165
  P.S. This command will lookup for the allocated `subdomain` and attempt to delete it if it exists.
166
166
 
@@ -170,20 +170,31 @@ The static sites are served from the selected directory (or the current director
170
170
 
171
171
  - **Deploy Site**: Deploy a static website from a directory.
172
172
  ```bash
173
- puter site:create <app_name> [<dir>] [--subdomain=<name>]
173
+ puter> site:create <app_name> [<dir>] [--subdomain=<name>]
174
174
  ```
175
175
  P.S. If the subdomain already exists, it will generate a new random one can set your own subdomain using `--subdomain` argument.
176
176
 
177
177
  - **List Sites**: List all hosted sites.
178
178
  ```bash
179
- puter sites
179
+ puter> sites
180
180
  ```
181
181
  - **Delete Site**: Delete a hosted site.
182
182
  ```bash
183
- puter site:delete <uid>
183
+ puter> site:delete <uid>
184
184
  ```
185
185
  P.S. You can find the `<uid>` in the list of `sites`.
186
186
 
187
+ #### Commands history
188
+
189
+ - **Display history**: Display the history executed commands
190
+ ```bash
191
+ puter> history
192
+ ```
193
+ - **Copy command from history**: Copy a previous command from history by line number
194
+ ```bash
195
+ puter> history <line_number>
196
+ ```
197
+
187
198
  #### Interactive Shell
188
199
  - **Start Shell**: Launch an interactive shell.
189
200
  ```bash
@@ -198,10 +209,14 @@ or just type (you'll need to login):
198
209
  - **General Help**: Display a list of available commands.
199
210
  ```bash
200
211
  puter help
212
+ # or inside the interactive shell:
213
+ puter> help
201
214
  ```
202
215
  - **Command Help**: Display detailed help for a specific command.
203
216
  ```bash
204
217
  puter help <command>
218
+ # or inside the interactive shell:
219
+ puter> help <command>
205
220
  ```
206
221
 
207
222
  ---
package/bin/index.js CHANGED
@@ -1,9 +1,9 @@
1
1
  #!/usr/bin/env node
2
2
  import { Command } from 'commander';
3
- import { login, logout } from '../commands/auth.js';
4
- import { init } from '../commands/init.js';
5
- import { startShell } from '../commands/shell.js';
6
- import { PROJECT_NAME, getLatestVersion } from '../commands/commons.js';
3
+ import { login, logout } from '../src/commands/auth.js';
4
+ import { init } from '../src/commands/init.js';
5
+ import { startShell } from '../src/commands/shell.js';
6
+ import { PROJECT_NAME, getLatestVersion } from '../src/commons.js';
7
7
 
8
8
  async function main() {
9
9
  const { version } = await getLatestVersion(PROJECT_NAME);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "puter-cli",
3
- "version": "1.1.5",
3
+ "version": "1.2.1",
4
4
  "description": "Command line interface for Puter cloud platform",
5
5
  "main": "index.js",
6
6
  "bin": {
@@ -11,7 +11,8 @@
11
11
  "scripts": {
12
12
  "start": "node bin/index.js",
13
13
  "test": "vitest run tests/*",
14
- "test:watch": "vitest --watch tests/*"
14
+ "test:watch": "vitest --watch tests/*",
15
+ "version": "auto-changelog -p && git add CHANGELOG.md"
15
16
  },
16
17
  "engines": {
17
18
  "node": ">=18.0.0"
@@ -38,6 +39,7 @@
38
39
  "yargs-parser": "^21.1.1"
39
40
  },
40
41
  "devDependencies": {
42
+ "auto-changelog": "^2.5.0",
41
43
  "vitest": "^2.1.8"
42
44
  },
43
45
  "repository": {
@@ -2,13 +2,13 @@ import path from 'path';
2
2
  import chalk from 'chalk';
3
3
  import fetch from 'node-fetch';
4
4
  import Table from 'cli-table3';
5
- import { displayNonNullValues, formatDate } from './utils.js';
6
- import { API_BASE, getHeaders, getDefaultHomePage, isValidAppName, resolvePath } from './commons.js';
5
+ import { displayNonNullValues, formatDate } from '../utils.js';
6
+ import { API_BASE, getHeaders, getDefaultHomePage, isValidAppName, resolvePath } from '../commons.js';
7
7
  import { createSubdomain, getSubdomains } from './subdomains.js';
8
8
  import { deleteSite } from './sites.js';
9
9
  import { copyFile, createFile, listRemoteFiles, pathExists, removeFileOrDirectory } from './files.js';
10
10
  import { getCurrentDirectory } from './auth.js';
11
- import crypto from './crypto.js';
11
+ import crypto from '../crypto.js';
12
12
 
13
13
  /**
14
14
  * List all apps
@@ -3,7 +3,7 @@ import chalk from 'chalk';
3
3
  import Conf from 'conf';
4
4
  import ora from 'ora';
5
5
  import fetch from 'node-fetch';
6
- import { PROJECT_NAME, API_BASE, getHeaders, BASE_URL } from './commons.js'
6
+ import { PROJECT_NAME, API_BASE, getHeaders, BASE_URL } from '../commons.js'
7
7
  const config = new Conf({ projectName: PROJECT_NAME });
8
8
 
9
9
  /**
@@ -6,12 +6,12 @@ import chalk from 'chalk';
6
6
  import ora from 'ora';
7
7
  import Conf from 'conf';
8
8
  import fetch from 'node-fetch';
9
- import { API_BASE, BASE_URL, PROJECT_NAME, getHeaders, showDiskSpaceUsage, resolvePath } from './commons.js';
10
- import { formatDate, formatDateTime, formatSize } from './utils.js';
9
+ import { API_BASE, BASE_URL, PROJECT_NAME, getHeaders, showDiskSpaceUsage, resolvePath } from '../commons.js';
10
+ import { formatDate, formatDateTime, formatSize } from '../utils.js';
11
11
  import inquirer from 'inquirer';
12
12
  import { getAuthToken, getCurrentDirectory, getCurrentUserName } from './auth.js';
13
13
  import { updatePrompt } from './shell.js';
14
- import crypto from './crypto.js';
14
+ import crypto from '../crypto.js';
15
15
 
16
16
  const config = new Conf({ projectName: PROJECT_NAME });
17
17
 
@@ -3,7 +3,7 @@ import chalk from 'chalk';
3
3
  import ora from 'ora';
4
4
  import { promises as fs } from 'fs';
5
5
  import path from 'path';
6
- import { generateAppName } from './commons.js';
6
+ import { generateAppName } from '../commons.js';
7
7
 
8
8
  export async function init() {
9
9
  const answers = await inquirer.prompt([
@@ -1,13 +1,13 @@
1
1
  import readline from 'node:readline';
2
2
  import chalk from 'chalk';
3
3
  import Conf from 'conf';
4
- import { execCommand, getPrompt } from './executor.js';
4
+ import { execCommand, getPrompt } from '../executor.js';
5
5
  import { getAuthToken } from './auth.js';
6
- import { PROJECT_NAME } from './commons.js';
6
+ import { PROJECT_NAME } from '../commons.js';
7
7
 
8
8
  const config = new Conf({ projectName: PROJECT_NAME });
9
9
 
10
- const rl = readline.createInterface({
10
+ export const rl = readline.createInterface({
11
11
  input: process.stdin,
12
12
  output: process.stdout,
13
13
  prompt: null
@@ -2,8 +2,8 @@ import chalk from 'chalk';
2
2
  import fetch from 'node-fetch';
3
3
  import Table from 'cli-table3';
4
4
  import { getCurrentUserName, getCurrentDirectory } from './auth.js';
5
- import { API_BASE, getHeaders, generateAppName, resolvePath, isValidAppName } from './commons.js';
6
- import { displayNonNullValues, formatDate, formatDateTime } from './utils.js';
5
+ import { API_BASE, getHeaders, generateAppName, resolvePath, isValidAppName } from '../commons.js';
6
+ import { displayNonNullValues, formatDate, formatDateTime } from '../utils.js';
7
7
  import { getSubdomains, createSubdomain, deleteSubdomain } from './subdomains.js';
8
8
 
9
9
 
@@ -1,6 +1,6 @@
1
1
  import chalk from 'chalk';
2
2
  import fetch from 'node-fetch';
3
- import { API_BASE, getHeaders } from './commons.js';
3
+ import { API_BASE, getHeaders } from '../commons.js';
4
4
 
5
5
  /**
6
6
  * Get list of subdomains.
@@ -1,5 +1,5 @@
1
1
  import chalk from 'chalk';
2
- import { getAuthToken } from './auth.js';
2
+ import { getAuthToken } from './commands/auth.js';
3
3
 
4
4
  export const PROJECT_NAME = 'puter-cli';
5
5
  export const API_BASE = 'https://api.puter.com';
@@ -1,19 +1,23 @@
1
1
  import chalk from 'chalk';
2
2
  import Conf from 'conf';
3
- import { listApps, appInfo, createApp, updateApp, deleteApp } from './apps.js';
4
- import { listSites, createSite, deleteSite, infoSite } from './sites.js';
3
+ import { listApps, appInfo, createApp, updateApp, deleteApp } from './commands/apps.js';
4
+ import { listSites, createSite, deleteSite, infoSite } from './commands/sites.js';
5
5
  import { listFiles, makeDirectory, renameFileOrDirectory,
6
6
  removeFileOrDirectory, emptyTrash, changeDirectory, showCwd,
7
7
  getInfo, getDiskUsage, createFile, readFile, uploadFile,
8
- downloadFile, copyFile, syncDirectory } from './files.js';
9
- import { getUserInfo, getUsageInfo } from './auth.js';
8
+ downloadFile, copyFile, syncDirectory } from './commands/files.js';
9
+ import { getUserInfo, getUsageInfo } from './commands/auth.js';
10
10
  import { PROJECT_NAME, API_BASE, getHeaders } from './commons.js';
11
11
  import inquirer from 'inquirer';
12
12
  import { exec } from 'node:child_process';
13
13
  import { parseArgs } from './utils.js';
14
+ import { rl } from './commands/shell.js';
14
15
 
15
16
  const config = new Conf({ projectName: PROJECT_NAME });
16
17
 
18
+ // History of commands
19
+ const commandHistory = [];
20
+
17
21
  /**
18
22
  * Update the prompt function
19
23
  * @returns The current prompt
@@ -26,7 +30,7 @@ const commands = {
26
30
  help: showHelp,
27
31
  exit: () => process.exit(0),
28
32
  logout: async () => {
29
- await import('./auth.js').then(m => m.logout());
33
+ await import('./commands/auth.js').then(m => m.logout());
30
34
  process.exit(0);
31
35
  },
32
36
  whoami: getUserInfo,
@@ -37,6 +41,26 @@ const commands = {
37
41
  });
38
42
  },
39
43
  app: appInfo,
44
+ history: async (args) => {
45
+ const lineNumber = parseInt(args[0]);
46
+
47
+ if (isNaN(lineNumber)) {
48
+ // Display full history
49
+ commandHistory.forEach((command, index) => {
50
+ console.log(chalk.cyan(`${index + 1}: ${command}`));
51
+ });
52
+ } else {
53
+ // Copy the command at the specified line number
54
+ if (lineNumber < 1 || lineNumber > commandHistory.length) {
55
+ console.error(chalk.red(`Invalid line number. History has ${commandHistory.length} entries.`));
56
+ return;
57
+ }
58
+
59
+ const commandToCopy = commandHistory[lineNumber - 1];
60
+ // Simulate typing the command in the shell
61
+ rl.write(commandToCopy);
62
+ }
63
+ },
40
64
  'app:create': async (rawArgs) => {
41
65
  try {
42
66
  const args = parseArgs(rawArgs.join(' '));
@@ -119,7 +143,7 @@ const commands = {
119
143
  sites: listSites,
120
144
  site: infoSite,
121
145
  'site:delete': deleteSite,
122
- 'site:create': createSite
146
+ 'site:create': createSite,
123
147
  };
124
148
 
125
149
  /**
@@ -129,6 +153,12 @@ const commands = {
129
153
  export async function execCommand(input) {
130
154
  const [cmd, ...args] = input.split(' ');
131
155
 
156
+
157
+ // Add the command to history (skip the "history" command itself)
158
+ if (cmd !== 'history') {
159
+ commandHistory.push(input);
160
+ }
161
+
132
162
  if (cmd === 'help') {
133
163
  // Handle help command
134
164
  const command = args[0];
@@ -312,6 +342,11 @@ function showHelp(command) {
312
342
  Execute a command on the host machine.
313
343
  Example: !ls -la
314
344
  `,
345
+ 'history [line]': `
346
+ ${chalk.cyan('history [line]')}
347
+ Display history of commands or copy command by line number
348
+ Example: history 2
349
+ `,
315
350
  };
316
351
 
317
352
  if (command && commandHelp[command]) {
@@ -1,12 +1,12 @@
1
1
  import { describe, it, expect, vi, beforeEach } from 'vitest';
2
2
  import { login, logout, getUserInfo, isAuthenticated, getAuthToken, getCurrentUserName,
3
- getCurrentDirectory, getUsageInfo } from './commands/auth.js';
3
+ getCurrentDirectory, getUsageInfo } from '../src/commands/auth.js';
4
4
  import inquirer from 'inquirer';
5
5
  import ora from 'ora';
6
6
  import chalk from 'chalk';
7
7
  import fetch from 'node-fetch';
8
8
  import Conf from 'conf';
9
- import { BASE_URL } from '../commands/commons.js';
9
+ import { BASE_URL } from '../src/commons.js';
10
10
 
11
11
  // Mock console to prevent actual logging
12
12
  vi.spyOn(console, 'log').mockImplementation(() => {});
File without changes
File without changes