@ardrive/turbo-sdk 1.13.0 → 1.14.0-alpha.2
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 +34 -0
- package/bundles/web.bundle.min.js +1 -1
- package/lib/cjs/cli/cli.js +13 -43
- package/lib/cjs/cli/commands.js +48 -19
- package/lib/cjs/cli/options.js +119 -0
- package/lib/cjs/cli/types.js +16 -0
- package/lib/cjs/cli/utils.js +67 -72
- package/lib/cjs/node/upload.js +3 -0
- package/lib/cjs/version.js +1 -1
- package/lib/esm/cli/cli.js +11 -41
- package/lib/esm/cli/commands.js +45 -17
- package/lib/esm/cli/options.js +116 -0
- package/lib/esm/cli/types.js +16 -0
- package/lib/esm/cli/utils.js +63 -73
- package/lib/esm/node/upload.js +3 -0
- package/lib/esm/version.js +1 -1
- package/lib/types/cli/commands.d.ts +4 -13
- package/lib/types/cli/commands.d.ts.map +1 -1
- package/lib/types/cli/options.d.ts +164 -0
- package/lib/types/cli/options.d.ts.map +1 -0
- package/lib/types/cli/types.d.ts +14 -2
- package/lib/types/cli/types.d.ts.map +1 -1
- package/lib/types/cli/utils.d.ts +19 -87
- package/lib/types/cli/utils.d.ts.map +1 -1
- package/lib/types/node/upload.d.ts.map +1 -1
- package/lib/types/version.d.ts +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
@@ -69,6 +69,8 @@ Welcome to the `@ardrive/turbo-sdk`! This SDK provides functionality for interac
|
|
69
69
|
- [`balance`](#balance)
|
70
70
|
- [`top-up`](#top-up)
|
71
71
|
- [`crypto-fund`](#crypto-fund)
|
72
|
+
- [`upload-folder`](#upload-folder)
|
73
|
+
- [`upload-file`](#upload-file)
|
72
74
|
- [Developers](#developers)
|
73
75
|
- [Requirements](#requirements)
|
74
76
|
- [Setup & Build](#setup--build)
|
@@ -737,6 +739,38 @@ e.g:
|
|
737
739
|
turbo crypto-fund --value 0.0001 --token kyve --private-key 'b27...45c'
|
738
740
|
```
|
739
741
|
|
742
|
+
##### `upload-folder`
|
743
|
+
|
744
|
+
Upload a folder of files and create and upload a manifest file for the folder upload to the Turbo Upload Service.
|
745
|
+
|
746
|
+
Command Options:
|
747
|
+
|
748
|
+
- `-f, --folder-path <folderPath>` - Path to the folder to upload
|
749
|
+
- `--index-file <indexFile>` - File to use for the "index" path in the resulting manifest
|
750
|
+
- `--fallback-file <fallbackFile>` - File to use for the "fallback" path in the resulting manifest
|
751
|
+
- `--no-manifest` - Disable manifest creation
|
752
|
+
- `--max-concurrency <maxConcurrency>` - Maximum number of concurrent uploads
|
753
|
+
|
754
|
+
e.g:
|
755
|
+
|
756
|
+
```shell
|
757
|
+
turbo upload-folder --folder-path '../path/to/my/folder' --token solana --wallet-file ../path/to/sol/sec/key.json
|
758
|
+
```
|
759
|
+
|
760
|
+
##### `upload-file`
|
761
|
+
|
762
|
+
Upload a file to the Turbo Upload Service.
|
763
|
+
|
764
|
+
Command Options:
|
765
|
+
|
766
|
+
- `-f, --file-path <filePath>` - Path to the file to upload
|
767
|
+
|
768
|
+
e.g:
|
769
|
+
|
770
|
+
```shell
|
771
|
+
turbo upload-file --file-path '../path/to/my/file.txt' --token ethereum --wallet-file ../path/to/eth/private/key.txt
|
772
|
+
```
|
773
|
+
|
740
774
|
## Developers
|
741
775
|
|
742
776
|
### Requirements
|
@@ -312251,7 +312251,7 @@ var import_winston = __toESM(require_winston(), 1);
|
|
312251
312251
|
init_dirname();
|
312252
312252
|
init_buffer2();
|
312253
312253
|
init_process2();
|
312254
|
-
var version16 = "1.
|
312254
|
+
var version16 = "1.14.0-alpha.1";
|
312255
312255
|
|
312256
312256
|
// src/common/logger.ts
|
312257
312257
|
var TurboWinstonLogger = class _TurboWinstonLogger {
|
package/lib/cjs/cli/cli.js
CHANGED
@@ -21,57 +21,27 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
21
21
|
const commander_1 = require("commander");
|
22
22
|
const version_js_1 = require("../version.js");
|
23
23
|
const commands_js_1 = require("./commands.js");
|
24
|
+
const options_js_1 = require("./options.js");
|
24
25
|
const utils_js_1 = require("./utils.js");
|
25
26
|
(0, utils_js_1.applyOptions)(commander_1.program
|
26
27
|
.name('turbo')
|
27
28
|
.version(version_js_1.version)
|
28
29
|
.description('Turbo CLI')
|
29
|
-
.helpCommand(true),
|
30
|
-
|
31
|
-
|
32
|
-
process.exit(1);
|
33
|
-
}
|
34
|
-
(0, utils_js_1.applyOptions)(commander_1.program.command('balance').description('Get balance of a Turbo address'), [utils_js_1.optionMap.address, ...utils_js_1.walletOptions]).action(async (_commandOptions, command) => {
|
35
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
36
|
-
const options = command.optsWithGlobals();
|
37
|
-
try {
|
38
|
-
await (0, commands_js_1.getBalance)(options);
|
39
|
-
process.exit(0);
|
40
|
-
}
|
41
|
-
catch (error) {
|
42
|
-
exitWithErrorLog(error);
|
43
|
-
}
|
30
|
+
.helpCommand(true), options_js_1.globalOptions);
|
31
|
+
(0, utils_js_1.applyOptions)(commander_1.program.command('balance').description('Get balance of a Turbo address'), [options_js_1.optionMap.address, ...options_js_1.walletOptions]).action(async (_commandOptions, command) => {
|
32
|
+
await (0, utils_js_1.runCommand)(command, commands_js_1.getBalance);
|
44
33
|
});
|
45
|
-
(0, utils_js_1.applyOptions)(commander_1.program.command('top-up').description('Top up a Turbo address with Fiat'), [...
|
46
|
-
|
47
|
-
try {
|
48
|
-
await (0, commands_js_1.topUp)(options);
|
49
|
-
process.exit(0);
|
50
|
-
}
|
51
|
-
catch (error) {
|
52
|
-
exitWithErrorLog(error);
|
53
|
-
}
|
34
|
+
(0, utils_js_1.applyOptions)(commander_1.program.command('top-up').description('Top up a Turbo address with Fiat'), [...options_js_1.walletOptions, options_js_1.optionMap.address, options_js_1.optionMap.value, options_js_1.optionMap.currency]).action(async (_commandOptions, command) => {
|
35
|
+
await (0, utils_js_1.runCommand)(command, commands_js_1.topUp);
|
54
36
|
});
|
55
|
-
(0, utils_js_1.applyOptions)(commander_1.program.command('crypto-fund').description('Top up a wallet with crypto'), [...
|
56
|
-
|
57
|
-
const options = command.optsWithGlobals();
|
58
|
-
const token = (0, utils_js_1.tokenFromOptions)(options);
|
59
|
-
const value = (0, utils_js_1.valueFromOptions)(options);
|
60
|
-
const privateKey = await (0, utils_js_1.privateKeyFromOptions)(options);
|
61
|
-
const config = (0, utils_js_1.configFromOptions)(options);
|
62
|
-
try {
|
63
|
-
await (0, commands_js_1.cryptoFund)({ privateKey, value, token, config });
|
64
|
-
process.exit(0);
|
65
|
-
}
|
66
|
-
catch (error) {
|
67
|
-
exitWithErrorLog(error);
|
68
|
-
}
|
37
|
+
(0, utils_js_1.applyOptions)(commander_1.program.command('crypto-fund').description('Top up a wallet with crypto'), [...options_js_1.walletOptions, options_js_1.optionMap.value]).action(async (_commandOptions, command) => {
|
38
|
+
await (0, utils_js_1.runCommand)(command, commands_js_1.cryptoFund);
|
69
39
|
});
|
70
|
-
(0, utils_js_1.applyOptions)(commander_1.program
|
71
|
-
.command
|
72
|
-
|
73
|
-
|
74
|
-
|
40
|
+
(0, utils_js_1.applyOptions)(commander_1.program.command('upload-folder').description('Upload a folder using Turbo'), options_js_1.uploadFolderOptions).action(async (_commandOptions, command) => {
|
41
|
+
await (0, utils_js_1.runCommand)(command, commands_js_1.uploadFolder);
|
42
|
+
});
|
43
|
+
(0, utils_js_1.applyOptions)(commander_1.program.command('upload-file').description('Upload a file using Turbo'), options_js_1.uploadFileOptions).action(async (_commandOptions, command) => {
|
44
|
+
await (0, utils_js_1.runCommand)(command, commands_js_1.uploadFile);
|
75
45
|
});
|
76
46
|
if (process.argv[1].includes('bin/turbo') || // Running from global .bin
|
77
47
|
process.argv[1].includes('cli/cli') // Running from source
|
package/lib/cjs/cli/commands.js
CHANGED
@@ -1,10 +1,11 @@
|
|
1
1
|
"use strict";
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
3
|
-
exports.addressOrPrivateKeyFromOptions = addressOrPrivateKeyFromOptions;
|
4
3
|
exports.getBalance = getBalance;
|
5
4
|
exports.cryptoFund = cryptoFund;
|
6
5
|
exports.topUp = topUp;
|
7
6
|
exports.openUrl = openUrl;
|
7
|
+
exports.uploadFolder = uploadFolder;
|
8
|
+
exports.uploadFile = uploadFile;
|
8
9
|
/**
|
9
10
|
* Copyright (C) 2022-2024 Permanent Data Solutions, Inc. All Rights Reserved.
|
10
11
|
*
|
@@ -22,21 +23,14 @@ exports.openUrl = openUrl;
|
|
22
23
|
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
23
24
|
*/
|
24
25
|
const node_child_process_1 = require("node:child_process");
|
26
|
+
const node_fs_1 = require("node:fs");
|
25
27
|
const index_js_1 = require("../node/index.js");
|
26
28
|
const common_js_1 = require("../utils/common.js");
|
29
|
+
const version_js_1 = require("../version.js");
|
27
30
|
const utils_js_1 = require("./utils.js");
|
28
|
-
async function addressOrPrivateKeyFromOptions(options) {
|
29
|
-
if (options.address !== undefined) {
|
30
|
-
return { address: options.address, privateKey: undefined };
|
31
|
-
}
|
32
|
-
return {
|
33
|
-
address: undefined,
|
34
|
-
privateKey: await (0, utils_js_1.optionalPrivateKeyFromOptions)(options),
|
35
|
-
};
|
36
|
-
}
|
37
31
|
async function getBalance(options) {
|
38
32
|
const config = (0, utils_js_1.configFromOptions)(options);
|
39
|
-
const { address, privateKey } = await addressOrPrivateKeyFromOptions(options);
|
33
|
+
const { address, privateKey } = await (0, utils_js_1.addressOrPrivateKeyFromOptions)(options);
|
40
34
|
if (address !== undefined) {
|
41
35
|
const turbo = index_js_1.TurboFactory.unauthenticated(config);
|
42
36
|
const { winc } = await turbo.getBalance(address);
|
@@ -54,20 +48,21 @@ async function getBalance(options) {
|
|
54
48
|
console.log(`Turbo Balance for Wallet Address "${await turbo.signer.getNativeAddress()}"\nCredits: ${+winc / 1_000_000_000_000}`);
|
55
49
|
}
|
56
50
|
/** Fund the connected signer with crypto */
|
57
|
-
async function cryptoFund(
|
58
|
-
const
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
const
|
51
|
+
async function cryptoFund(options) {
|
52
|
+
const value = options.value;
|
53
|
+
if (value === undefined) {
|
54
|
+
throw new Error('Must provide a --value to top up');
|
55
|
+
}
|
56
|
+
const turbo = await (0, utils_js_1.turboFromOptions)(options);
|
57
|
+
const token = (0, utils_js_1.tokenFromOptions)(options);
|
58
|
+
const result = await turbo.topUpWithTokens({
|
64
59
|
tokenAmount: index_js_1.tokenToBaseMap[token](value),
|
65
60
|
});
|
66
61
|
console.log('Sent crypto fund transaction: \n', JSON.stringify(result, null, 2));
|
67
62
|
}
|
68
63
|
async function topUp(options) {
|
69
64
|
const config = (0, utils_js_1.configFromOptions)(options);
|
70
|
-
const { address, privateKey } = await addressOrPrivateKeyFromOptions(options);
|
65
|
+
const { address, privateKey } = await (0, utils_js_1.addressOrPrivateKeyFromOptions)(options);
|
71
66
|
const value = options.value;
|
72
67
|
if (value === undefined) {
|
73
68
|
throw new Error('Must provide a --value to top up');
|
@@ -120,3 +115,37 @@ function openUrl(url) {
|
|
120
115
|
open(url);
|
121
116
|
}
|
122
117
|
}
|
118
|
+
const turboCliTags = [
|
119
|
+
{ name: 'App-Name', value: 'Turbo-CLI' },
|
120
|
+
{ name: 'App-Version', value: version_js_1.version },
|
121
|
+
{ name: 'App-Platform', value: process.platform },
|
122
|
+
];
|
123
|
+
async function uploadFolder(options) {
|
124
|
+
const turbo = await (0, utils_js_1.turboFromOptions)(options);
|
125
|
+
const { disableManifest, fallbackFile, folderPath, indexFile, maxConcurrentUploads, } = (0, utils_js_1.getUploadFolderOptions)(options);
|
126
|
+
const result = await turbo.uploadFolder({
|
127
|
+
folderPath: folderPath,
|
128
|
+
dataItemOpts: { tags: [...turboCliTags] }, // TODO: Inject user tags
|
129
|
+
manifestOptions: {
|
130
|
+
disableManifest,
|
131
|
+
indexFile,
|
132
|
+
fallbackFile,
|
133
|
+
},
|
134
|
+
maxConcurrentUploads,
|
135
|
+
});
|
136
|
+
console.log('Uploaded folder:', JSON.stringify(result, null, 2));
|
137
|
+
}
|
138
|
+
async function uploadFile(options) {
|
139
|
+
const { filePath } = options;
|
140
|
+
if (filePath === undefined) {
|
141
|
+
throw new Error('Must provide a --file-path to upload');
|
142
|
+
}
|
143
|
+
const turbo = await (0, utils_js_1.turboFromOptions)(options);
|
144
|
+
const fileSize = (0, node_fs_1.statSync)(filePath).size;
|
145
|
+
const result = await turbo.uploadFile({
|
146
|
+
fileStreamFactory: () => (0, node_fs_1.createReadStream)(filePath),
|
147
|
+
fileSizeFactory: () => fileSize,
|
148
|
+
dataItemOpts: { tags: [...turboCliTags] }, // TODO: Inject user tags
|
149
|
+
});
|
150
|
+
console.log('Uploaded file:', JSON.stringify(result, null, 2));
|
151
|
+
}
|
@@ -0,0 +1,119 @@
|
|
1
|
+
"use strict";
|
2
|
+
/**
|
3
|
+
* Copyright (C) 2022-2024 Permanent Data Solutions, Inc. All Rights Reserved.
|
4
|
+
*
|
5
|
+
* This program is free software: you can redistribute it and/or modify
|
6
|
+
* it under the terms of the GNU Affero General Public License as published by
|
7
|
+
* the Free Software Foundation, either version 3 of the License, or
|
8
|
+
* (at your option) any later version.
|
9
|
+
*
|
10
|
+
* This program is distributed in the hope that it will be useful,
|
11
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
13
|
+
* GNU Affero General Public License for more details.
|
14
|
+
*
|
15
|
+
* You should have received a copy of the GNU Affero General Public License
|
16
|
+
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
17
|
+
*/
|
18
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
19
|
+
exports.uploadFileOptions = exports.uploadFolderOptions = exports.globalOptions = exports.walletOptions = exports.optionMap = void 0;
|
20
|
+
exports.optionMap = {
|
21
|
+
token: {
|
22
|
+
alias: '-t, --token <type>',
|
23
|
+
description: 'Crypto token type for wallet or action',
|
24
|
+
default: 'arweave',
|
25
|
+
},
|
26
|
+
currency: {
|
27
|
+
alias: '-c, --currency <currency>',
|
28
|
+
description: 'Fiat currency type to use for the action',
|
29
|
+
default: 'usd',
|
30
|
+
},
|
31
|
+
address: {
|
32
|
+
alias: '-a, --address <nativeAddress>',
|
33
|
+
description: 'Native address to use for action',
|
34
|
+
},
|
35
|
+
value: {
|
36
|
+
alias: '-v, --value <value>',
|
37
|
+
description: 'Value of fiat currency or crypto token for action. e.g: 10.50 for $10.50 USD or 0.0001 for 0.0001 AR',
|
38
|
+
},
|
39
|
+
walletFile: {
|
40
|
+
alias: '-w, --wallet-file <filePath>',
|
41
|
+
description: 'Wallet file to use with the action. Formats accepted: JWK.json, KYVE or ETH private key as a string, or SOL Secret Key as a Uint8Array',
|
42
|
+
},
|
43
|
+
mnemonic: {
|
44
|
+
alias: '-m, --mnemonic <phrase>',
|
45
|
+
description: 'Mnemonic to use with the action',
|
46
|
+
},
|
47
|
+
privateKey: {
|
48
|
+
alias: '-p, --private-key <key>',
|
49
|
+
description: 'Private key to use with the action',
|
50
|
+
},
|
51
|
+
gateway: {
|
52
|
+
alias: '-g, --gateway <url>',
|
53
|
+
description: 'Set a custom crypto gateway URL',
|
54
|
+
default: undefined,
|
55
|
+
},
|
56
|
+
dev: {
|
57
|
+
alias: '--dev',
|
58
|
+
description: 'Enable development endpoints',
|
59
|
+
default: false,
|
60
|
+
},
|
61
|
+
debug: {
|
62
|
+
// TODO: Implement
|
63
|
+
alias: '--debug',
|
64
|
+
description: 'Enable verbose logging',
|
65
|
+
default: false,
|
66
|
+
},
|
67
|
+
quiet: {
|
68
|
+
// TODO: Implement
|
69
|
+
alias: '--quiet',
|
70
|
+
description: 'Disable logging',
|
71
|
+
default: false,
|
72
|
+
},
|
73
|
+
folderPath: {
|
74
|
+
alias: '-f, --folder-path <folderPath>',
|
75
|
+
description: 'Directory to upload',
|
76
|
+
},
|
77
|
+
filePath: {
|
78
|
+
alias: '-f, --file-path <filePath>',
|
79
|
+
description: 'File to upload',
|
80
|
+
},
|
81
|
+
indexFile: {
|
82
|
+
alias: '--index-file <indexFile>',
|
83
|
+
description: 'Index file to use in the manifest created for folder upload',
|
84
|
+
},
|
85
|
+
fallbackFile: {
|
86
|
+
alias: '--fallback-file <fallbackFile>',
|
87
|
+
description: 'Fallback file to use in the manifest created for folder upload',
|
88
|
+
},
|
89
|
+
manifest: {
|
90
|
+
alias: '--no-manifest',
|
91
|
+
description: 'Disable manifest creation with --no-manifest',
|
92
|
+
default: true,
|
93
|
+
},
|
94
|
+
maxConcurrency: {
|
95
|
+
alias: '--max-concurrency <maxConcurrency>',
|
96
|
+
description: 'Maximum number of concurrent uploads',
|
97
|
+
},
|
98
|
+
};
|
99
|
+
exports.walletOptions = [
|
100
|
+
exports.optionMap.walletFile,
|
101
|
+
exports.optionMap.mnemonic,
|
102
|
+
exports.optionMap.privateKey,
|
103
|
+
];
|
104
|
+
exports.globalOptions = [
|
105
|
+
exports.optionMap.dev,
|
106
|
+
exports.optionMap.gateway,
|
107
|
+
exports.optionMap.debug,
|
108
|
+
exports.optionMap.quiet,
|
109
|
+
exports.optionMap.token,
|
110
|
+
];
|
111
|
+
exports.uploadFolderOptions = [
|
112
|
+
...exports.walletOptions,
|
113
|
+
exports.optionMap.folderPath,
|
114
|
+
exports.optionMap.indexFile,
|
115
|
+
exports.optionMap.fallbackFile,
|
116
|
+
exports.optionMap.manifest,
|
117
|
+
exports.optionMap.maxConcurrency,
|
118
|
+
];
|
119
|
+
exports.uploadFileOptions = [...exports.walletOptions, exports.optionMap.filePath];
|
package/lib/cjs/cli/types.js
CHANGED
@@ -1,2 +1,18 @@
|
|
1
1
|
"use strict";
|
2
|
+
/**
|
3
|
+
* Copyright (C) 2022-2024 Permanent Data Solutions, Inc. All Rights Reserved.
|
4
|
+
*
|
5
|
+
* This program is free software: you can redistribute it and/or modify
|
6
|
+
* it under the terms of the GNU Affero General Public License as published by
|
7
|
+
* the Free Software Foundation, either version 3 of the License, or
|
8
|
+
* (at your option) any later version.
|
9
|
+
*
|
10
|
+
* This program is distributed in the hope that it will be useful,
|
11
|
+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
13
|
+
* GNU Affero General Public License for more details.
|
14
|
+
*
|
15
|
+
* You should have received a copy of the GNU Affero General Public License
|
16
|
+
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
17
|
+
*/
|
2
18
|
Object.defineProperty(exports, "__esModule", { value: true });
|
package/lib/cjs/cli/utils.js
CHANGED
@@ -3,13 +3,18 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
3
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
4
4
|
};
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
6
|
-
exports.
|
6
|
+
exports.exitWithErrorLog = exitWithErrorLog;
|
7
|
+
exports.runCommand = runCommand;
|
7
8
|
exports.applyOptions = applyOptions;
|
8
9
|
exports.tokenFromOptions = tokenFromOptions;
|
9
10
|
exports.valueFromOptions = valueFromOptions;
|
11
|
+
exports.getFolderPathFromOptions = getFolderPathFromOptions;
|
12
|
+
exports.addressOrPrivateKeyFromOptions = addressOrPrivateKeyFromOptions;
|
10
13
|
exports.optionalPrivateKeyFromOptions = optionalPrivateKeyFromOptions;
|
11
14
|
exports.privateKeyFromOptions = privateKeyFromOptions;
|
12
15
|
exports.configFromOptions = configFromOptions;
|
16
|
+
exports.turboFromOptions = turboFromOptions;
|
17
|
+
exports.getUploadFolderOptions = getUploadFolderOptions;
|
13
18
|
/**
|
14
19
|
* Copyright (C) 2022-2024 Permanent Data Solutions, Inc. All Rights Reserved.
|
15
20
|
*
|
@@ -30,72 +35,20 @@ const bs58_1 = __importDefault(require("bs58"));
|
|
30
35
|
const fs_1 = require("fs");
|
31
36
|
const index_js_1 = require("../node/index.js");
|
32
37
|
const errors_js_1 = require("./errors.js");
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
},
|
48
|
-
value: {
|
49
|
-
alias: '-v, --value <value>',
|
50
|
-
description: 'Value of fiat currency or crypto token for action. e.g: 10.50 for $10.50 USD or 0.0001 for 0.0001 AR',
|
51
|
-
},
|
52
|
-
walletFile: {
|
53
|
-
alias: '-w, --wallet-file <filePath>',
|
54
|
-
description: 'Wallet file to use with the action. Formats accepted: JWK.json, KYVE or ETH private key as a string, or SOL Secret Key as a Uint8Array',
|
55
|
-
},
|
56
|
-
mnemonic: {
|
57
|
-
alias: '-m, --mnemonic <phrase>',
|
58
|
-
description: 'Mnemonic to use with the action',
|
59
|
-
},
|
60
|
-
privateKey: {
|
61
|
-
alias: '-p, --private-key <key>',
|
62
|
-
description: 'Private key to use with the action',
|
63
|
-
},
|
64
|
-
gateway: {
|
65
|
-
alias: '-g, --gateway <url>',
|
66
|
-
description: 'Set a custom crypto gateway URL',
|
67
|
-
default: undefined,
|
68
|
-
},
|
69
|
-
dev: {
|
70
|
-
alias: '--dev',
|
71
|
-
description: 'Enable development endpoints',
|
72
|
-
default: false,
|
73
|
-
},
|
74
|
-
debug: {
|
75
|
-
// TODO: Implement
|
76
|
-
alias: '--debug',
|
77
|
-
description: 'Enable verbose logging',
|
78
|
-
default: false,
|
79
|
-
},
|
80
|
-
quiet: {
|
81
|
-
// TODO: Implement
|
82
|
-
alias: '--quiet',
|
83
|
-
description: 'Disable logging',
|
84
|
-
default: false,
|
85
|
-
},
|
86
|
-
};
|
87
|
-
exports.walletOptions = [
|
88
|
-
exports.optionMap.walletFile,
|
89
|
-
exports.optionMap.mnemonic,
|
90
|
-
exports.optionMap.privateKey,
|
91
|
-
];
|
92
|
-
exports.globalOptions = [
|
93
|
-
exports.optionMap.dev,
|
94
|
-
exports.optionMap.gateway,
|
95
|
-
exports.optionMap.debug,
|
96
|
-
exports.optionMap.quiet,
|
97
|
-
exports.optionMap.token,
|
98
|
-
];
|
38
|
+
function exitWithErrorLog(error) {
|
39
|
+
console.error(error instanceof Error ? error.message : error);
|
40
|
+
process.exit(1);
|
41
|
+
}
|
42
|
+
async function runCommand(command, action) {
|
43
|
+
const options = command.optsWithGlobals();
|
44
|
+
try {
|
45
|
+
await action(options);
|
46
|
+
process.exit(0);
|
47
|
+
}
|
48
|
+
catch (error) {
|
49
|
+
exitWithErrorLog(error);
|
50
|
+
}
|
51
|
+
}
|
99
52
|
function applyOptions(command, options) {
|
100
53
|
[...options].forEach((option) => {
|
101
54
|
command.option(option.alias, option.description, option.default);
|
@@ -119,6 +72,27 @@ function valueFromOptions(options) {
|
|
119
72
|
}
|
120
73
|
return value;
|
121
74
|
}
|
75
|
+
function getFolderPathFromOptions(options) {
|
76
|
+
const folderPath = options.folderPath;
|
77
|
+
if (folderPath === undefined) {
|
78
|
+
throw new Error('Folder path is required. Use --folderPath <path>');
|
79
|
+
}
|
80
|
+
// Check if path exists and is a directory
|
81
|
+
const stats = (0, fs_1.statSync)(folderPath);
|
82
|
+
if (!stats.isDirectory()) {
|
83
|
+
throw new Error('Folder path is not a directory');
|
84
|
+
}
|
85
|
+
return folderPath;
|
86
|
+
}
|
87
|
+
async function addressOrPrivateKeyFromOptions(options) {
|
88
|
+
if (options.address !== undefined) {
|
89
|
+
return { address: options.address, privateKey: undefined };
|
90
|
+
}
|
91
|
+
return {
|
92
|
+
address: undefined,
|
93
|
+
privateKey: await optionalPrivateKeyFromOptions(options),
|
94
|
+
};
|
95
|
+
}
|
122
96
|
async function optionalPrivateKeyFromOptions(options) {
|
123
97
|
try {
|
124
98
|
const key = await privateKeyFromOptions(options);
|
@@ -157,10 +131,13 @@ const tokenToDevGatewayMap = {
|
|
157
131
|
solana: 'https://api.devnet.solana.com',
|
158
132
|
ethereum: 'https://ethereum-holesky-rpc.publicnode.com',
|
159
133
|
kyve: 'https://api.korellia.kyve.network',
|
134
|
+
// matic: 'https://rpc-amoy.polygon.technology',
|
160
135
|
};
|
161
|
-
function configFromOptions(
|
136
|
+
function configFromOptions(options) {
|
162
137
|
let config = {};
|
163
|
-
|
138
|
+
const token = tokenFromOptions(options);
|
139
|
+
config.token = token;
|
140
|
+
if (options.dev) {
|
164
141
|
config = index_js_1.developmentTurboConfiguration;
|
165
142
|
config.gatewayUrl = tokenToDevGatewayMap[token];
|
166
143
|
}
|
@@ -168,9 +145,27 @@ function configFromOptions({ gateway, dev, token, }) {
|
|
168
145
|
config = index_js_1.defaultTurboConfiguration;
|
169
146
|
}
|
170
147
|
// If gateway is provided, override the default or dev gateway
|
171
|
-
if (gateway !== undefined) {
|
172
|
-
config.gatewayUrl = gateway;
|
148
|
+
if (options.gateway !== undefined) {
|
149
|
+
config.gatewayUrl = options.gateway;
|
173
150
|
}
|
174
|
-
config.token = token;
|
175
151
|
return config;
|
176
152
|
}
|
153
|
+
async function turboFromOptions(options) {
|
154
|
+
const privateKey = await privateKeyFromOptions(options);
|
155
|
+
return index_js_1.TurboFactory.authenticated({
|
156
|
+
...configFromOptions(options),
|
157
|
+
privateKey,
|
158
|
+
});
|
159
|
+
}
|
160
|
+
function getUploadFolderOptions(options) {
|
161
|
+
if (options.folderPath === undefined) {
|
162
|
+
throw new Error('--folder-path is required');
|
163
|
+
}
|
164
|
+
return {
|
165
|
+
folderPath: options.folderPath,
|
166
|
+
indexFile: options.indexFile,
|
167
|
+
fallbackFile: options.fallbackFile,
|
168
|
+
disableManifest: !options.manifest,
|
169
|
+
maxConcurrentUploads: +(options.maxConcurrency ?? 1),
|
170
|
+
};
|
171
|
+
}
|
package/lib/cjs/node/upload.js
CHANGED
@@ -32,6 +32,9 @@ class TurboAuthenticatedUploadService extends upload_js_1.TurboAuthenticatedBase
|
|
32
32
|
// Walk the directory and add all file paths to the array
|
33
33
|
const files = await fs_1.promises.readdir(folderPath);
|
34
34
|
for (const file of files) {
|
35
|
+
if (file === '.DS_Store') {
|
36
|
+
continue;
|
37
|
+
}
|
35
38
|
const absoluteFilePath = (0, path_1.join)(folderPath, file);
|
36
39
|
const stat = await fs_1.promises.stat(absoluteFilePath);
|
37
40
|
if (stat.isDirectory()) {
|
package/lib/cjs/version.js
CHANGED
package/lib/esm/cli/cli.js
CHANGED
@@ -18,58 +18,28 @@
|
|
18
18
|
// eslint-disable-next-line header/header -- This is a CLI file
|
19
19
|
import { program } from 'commander';
|
20
20
|
import { version } from '../version.js';
|
21
|
-
import { cryptoFund, getBalance, topUp } from './commands.js';
|
22
|
-
import {
|
21
|
+
import { cryptoFund, getBalance, topUp, uploadFile, uploadFolder, } from './commands.js';
|
22
|
+
import { globalOptions, optionMap, uploadFileOptions, uploadFolderOptions, walletOptions, } from './options.js';
|
23
|
+
import { applyOptions, runCommand } from './utils.js';
|
23
24
|
applyOptions(program
|
24
25
|
.name('turbo')
|
25
26
|
.version(version)
|
26
27
|
.description('Turbo CLI')
|
27
28
|
.helpCommand(true), globalOptions);
|
28
|
-
function exitWithErrorLog(error) {
|
29
|
-
console.error(error instanceof Error ? error.message : error);
|
30
|
-
process.exit(1);
|
31
|
-
}
|
32
29
|
applyOptions(program.command('balance').description('Get balance of a Turbo address'), [optionMap.address, ...walletOptions]).action(async (_commandOptions, command) => {
|
33
|
-
|
34
|
-
const options = command.optsWithGlobals();
|
35
|
-
try {
|
36
|
-
await getBalance(options);
|
37
|
-
process.exit(0);
|
38
|
-
}
|
39
|
-
catch (error) {
|
40
|
-
exitWithErrorLog(error);
|
41
|
-
}
|
30
|
+
await runCommand(command, getBalance);
|
42
31
|
});
|
43
32
|
applyOptions(program.command('top-up').description('Top up a Turbo address with Fiat'), [...walletOptions, optionMap.address, optionMap.value, optionMap.currency]).action(async (_commandOptions, command) => {
|
44
|
-
|
45
|
-
try {
|
46
|
-
await topUp(options);
|
47
|
-
process.exit(0);
|
48
|
-
}
|
49
|
-
catch (error) {
|
50
|
-
exitWithErrorLog(error);
|
51
|
-
}
|
33
|
+
await runCommand(command, topUp);
|
52
34
|
});
|
53
35
|
applyOptions(program.command('crypto-fund').description('Top up a wallet with crypto'), [...walletOptions, optionMap.value]).action(async (_commandOptions, command) => {
|
54
|
-
|
55
|
-
const options = command.optsWithGlobals();
|
56
|
-
const token = tokenFromOptions(options);
|
57
|
-
const value = valueFromOptions(options);
|
58
|
-
const privateKey = await privateKeyFromOptions(options);
|
59
|
-
const config = configFromOptions(options);
|
60
|
-
try {
|
61
|
-
await cryptoFund({ privateKey, value, token, config });
|
62
|
-
process.exit(0);
|
63
|
-
}
|
64
|
-
catch (error) {
|
65
|
-
exitWithErrorLog(error);
|
66
|
-
}
|
36
|
+
await runCommand(command, cryptoFund);
|
67
37
|
});
|
68
|
-
applyOptions(program
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
38
|
+
applyOptions(program.command('upload-folder').description('Upload a folder using Turbo'), uploadFolderOptions).action(async (_commandOptions, command) => {
|
39
|
+
await runCommand(command, uploadFolder);
|
40
|
+
});
|
41
|
+
applyOptions(program.command('upload-file').description('Upload a file using Turbo'), uploadFileOptions).action(async (_commandOptions, command) => {
|
42
|
+
await runCommand(command, uploadFile);
|
73
43
|
});
|
74
44
|
if (process.argv[1].includes('bin/turbo') || // Running from global .bin
|
75
45
|
process.argv[1].includes('cli/cli') // Running from source
|