@jbrowse/cli 4.0.4 → 4.1.3
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 +269 -111
- package/bin/run +2 -1
- package/bundle/index.js +289 -538
- package/dist/base.js +1 -2
- package/dist/bin.js +2 -4
- package/dist/cliFetch.js +3 -0
- package/dist/commands/add-assembly/index.js +19 -22
- package/dist/commands/add-assembly/utils.js +75 -92
- package/dist/commands/add-connection.js +16 -22
- package/dist/commands/add-track-json.js +13 -16
- package/dist/commands/add-track-utils/adapter-utils.js +6 -13
- package/dist/commands/add-track-utils/file-operations.js +8 -14
- package/dist/commands/add-track-utils/track-config.js +10 -18
- package/dist/commands/add-track-utils/validators.js +15 -27
- package/dist/commands/add-track.js +27 -33
- package/dist/commands/admin-server/index.js +24 -30
- package/dist/commands/admin-server/utils.js +27 -38
- package/dist/commands/create.js +16 -22
- package/dist/commands/make-pif/cigar-utils.js +3 -8
- package/dist/commands/make-pif/file-utils.js +10 -18
- package/dist/commands/make-pif/index.js +13 -16
- package/dist/commands/make-pif/pif-generator.js +14 -23
- package/dist/commands/process-utils.js +1 -4
- package/dist/commands/remove-track.js +8 -11
- package/dist/commands/set-default-session.js +13 -19
- package/dist/commands/shared/config-operations.js +7 -11
- package/dist/commands/shared/sort-utils.js +7 -14
- package/dist/commands/shared/validators.js +4 -8
- package/dist/commands/sort-bed.js +14 -17
- package/dist/commands/sort-gff.js +14 -17
- package/dist/commands/text-index/adapter-utils.js +5 -10
- package/dist/commands/text-index/aggregate.js +12 -15
- package/dist/commands/text-index/command.js +9 -12
- package/dist/commands/text-index/config-utils.js +24 -38
- package/dist/commands/text-index/file-list.js +11 -17
- package/dist/commands/text-index/index.js +4 -11
- package/dist/commands/text-index/indexing-utils.js +59 -43
- package/dist/commands/text-index/per-track.js +13 -16
- package/dist/commands/text-index/validators.js +3 -8
- package/dist/commands/track-utils.js +22 -33
- package/dist/commands/upgrade.js +20 -26
- package/dist/index.js +31 -39
- package/dist/types/common.js +5 -107
- package/dist/util.js +13 -20
- package/dist/utils.js +82 -58
- package/dist/version.js +1 -0
- package/package.json +7 -6
- package/dist/fetchWithProxy.js +0 -12
- package/dist/types/gff3Adapter.js +0 -42
- package/dist/types/streamUtils.js +0 -66
- package/dist/types/vcfAdapter.js +0 -39
package/dist/commands/upgrade.js
CHANGED
|
@@ -1,15 +1,9 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
const fs_1 = __importDefault(require("fs"));
|
|
8
|
-
const path_1 = __importDefault(require("path"));
|
|
9
|
-
const util_1 = require("util");
|
|
10
|
-
const decompress_1 = __importDefault(require("decompress"));
|
|
11
|
-
const fetchWithProxy_ts_1 = __importDefault(require("../fetchWithProxy.js"));
|
|
12
|
-
const utils_ts_1 = require("../utils.js");
|
|
1
|
+
import fs from 'fs';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
import { parseArgs } from 'util';
|
|
4
|
+
import decompress from 'decompress';
|
|
5
|
+
import fetch from "../cliFetch.js";
|
|
6
|
+
import { fetchGithubVersions, getBranch, getLatest, getTag, printHelp, } from "../utils.js";
|
|
13
7
|
const description = 'Upgrades JBrowse 2 to latest version';
|
|
14
8
|
const examples = [
|
|
15
9
|
'# Upgrades current directory to latest jbrowse release',
|
|
@@ -45,7 +39,7 @@ const options = {
|
|
|
45
39
|
tag: {
|
|
46
40
|
type: 'string',
|
|
47
41
|
short: 't',
|
|
48
|
-
description: 'Version of JBrowse 2 to install. Format is v1.0.0
|
|
42
|
+
description: 'Version of JBrowse 2 to install. Format is v1.0.0. Defaults to latest',
|
|
49
43
|
},
|
|
50
44
|
branch: {
|
|
51
45
|
type: 'string',
|
|
@@ -65,8 +59,8 @@ const options = {
|
|
|
65
59
|
description: 'A direct URL to a JBrowse 2 release',
|
|
66
60
|
},
|
|
67
61
|
};
|
|
68
|
-
async function run(args) {
|
|
69
|
-
const { positionals, values: runFlags } =
|
|
62
|
+
export async function run(args) {
|
|
63
|
+
const { positionals, values: runFlags } = parseArgs({
|
|
70
64
|
options,
|
|
71
65
|
args,
|
|
72
66
|
allowPositionals: true,
|
|
@@ -74,7 +68,7 @@ async function run(args) {
|
|
|
74
68
|
const argsPath = positionals[0];
|
|
75
69
|
const { clean, listVersions, tag, url, branch, nightly } = runFlags;
|
|
76
70
|
if (runFlags.help) {
|
|
77
|
-
|
|
71
|
+
printHelp({
|
|
78
72
|
options,
|
|
79
73
|
examples,
|
|
80
74
|
usage: 'jbrowse upgrade [localPath] [options]',
|
|
@@ -83,23 +77,23 @@ async function run(args) {
|
|
|
83
77
|
return;
|
|
84
78
|
}
|
|
85
79
|
if (listVersions) {
|
|
86
|
-
const versions = (await
|
|
80
|
+
const versions = (await fetchGithubVersions()).map(v => v.tag_name);
|
|
87
81
|
console.log(`All JBrowse versions:\n${versions.join('\n')}`);
|
|
88
82
|
process.exit(0);
|
|
89
83
|
}
|
|
90
84
|
if (!argsPath) {
|
|
91
85
|
throw new Error('No directory supplied');
|
|
92
86
|
}
|
|
93
|
-
if (!
|
|
87
|
+
if (!fs.existsSync(path.join(argsPath, 'manifest.json'))) {
|
|
94
88
|
throw new Error(`No manifest.json found in this directory, are you sure it is an
|
|
95
89
|
existing jbrowse 2 installation?`);
|
|
96
90
|
}
|
|
97
91
|
const locationUrl = url ||
|
|
98
|
-
(nightly ? await
|
|
99
|
-
(branch ? await
|
|
100
|
-
(tag ? await
|
|
92
|
+
(nightly ? await getBranch('main') : '') ||
|
|
93
|
+
(branch ? await getBranch(branch) : '') ||
|
|
94
|
+
(tag ? await getTag(tag) : await getLatest());
|
|
101
95
|
console.log(`Fetching ${locationUrl}...`);
|
|
102
|
-
const response = await (
|
|
96
|
+
const response = await fetch(locationUrl);
|
|
103
97
|
if (!response.ok) {
|
|
104
98
|
throw new Error(`HTTP ${response.status} fetching ${locationUrl}: ${response.statusText}`);
|
|
105
99
|
}
|
|
@@ -110,13 +104,13 @@ async function run(args) {
|
|
|
110
104
|
throw new Error('The URL provided does not seem to be a JBrowse installation URL');
|
|
111
105
|
}
|
|
112
106
|
if (clean) {
|
|
113
|
-
|
|
114
|
-
for (const f of
|
|
107
|
+
fs.rmSync(path.join(argsPath, 'static'), { recursive: true, force: true });
|
|
108
|
+
for (const f of fs
|
|
115
109
|
.readdirSync(argsPath)
|
|
116
110
|
.filter(f => f.includes('worker.js'))) {
|
|
117
|
-
|
|
111
|
+
fs.unlinkSync(path.join(argsPath, f));
|
|
118
112
|
}
|
|
119
113
|
}
|
|
120
|
-
await (
|
|
114
|
+
await decompress(Buffer.from(await response.arrayBuffer()), argsPath);
|
|
121
115
|
console.log(`Unpacked ${locationUrl} at ${argsPath}`);
|
|
122
116
|
}
|
package/dist/index.js
CHANGED
|
@@ -1,45 +1,38 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
4
|
-
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
5
|
-
};
|
|
6
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
-
exports.main = main;
|
|
8
|
-
const fs_1 = __importDefault(require("fs"));
|
|
9
|
-
const path_1 = __importDefault(require("path"));
|
|
10
|
-
const util_1 = require("util");
|
|
2
|
+
import { parseArgs } from 'util';
|
|
11
3
|
// Command imports
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
4
|
+
import { run as addAssemblyRun } from "./commands/add-assembly/index.js";
|
|
5
|
+
import { run as addConnectionRun } from "./commands/add-connection.js";
|
|
6
|
+
import { run as addTrackJsonRun } from "./commands/add-track-json.js";
|
|
7
|
+
import { run as addTrackRun } from "./commands/add-track.js";
|
|
8
|
+
import { run as adminServerRun } from "./commands/admin-server/index.js";
|
|
9
|
+
import { run as createRun } from "./commands/create.js";
|
|
10
|
+
import { run as makePIFRun } from "./commands/make-pif/index.js";
|
|
11
|
+
import { run as removeTrackRun } from "./commands/remove-track.js";
|
|
12
|
+
import { run as setDefaultSessionRun } from "./commands/set-default-session.js";
|
|
13
|
+
import { run as sortBedRun } from "./commands/sort-bed.js";
|
|
14
|
+
import { run as sortGffRun } from "./commands/sort-gff.js";
|
|
15
|
+
import { run as textIndexRun } from "./commands/text-index/index.js";
|
|
16
|
+
import { run as upgradeRun } from "./commands/upgrade.js";
|
|
17
|
+
import { version } from "./version.js";
|
|
25
18
|
const commands = {
|
|
26
|
-
create:
|
|
27
|
-
'add-assembly':
|
|
28
|
-
'add-track':
|
|
29
|
-
'text-index':
|
|
30
|
-
'admin-server':
|
|
31
|
-
upgrade:
|
|
32
|
-
'make-pif':
|
|
33
|
-
'sort-gff':
|
|
34
|
-
'sort-bed':
|
|
35
|
-
'add-connection':
|
|
36
|
-
'add-track-json':
|
|
37
|
-
'remove-track':
|
|
38
|
-
'set-default-session':
|
|
19
|
+
create: createRun,
|
|
20
|
+
'add-assembly': addAssemblyRun,
|
|
21
|
+
'add-track': addTrackRun,
|
|
22
|
+
'text-index': textIndexRun,
|
|
23
|
+
'admin-server': adminServerRun,
|
|
24
|
+
upgrade: upgradeRun,
|
|
25
|
+
'make-pif': makePIFRun,
|
|
26
|
+
'sort-gff': sortGffRun,
|
|
27
|
+
'sort-bed': sortBedRun,
|
|
28
|
+
'add-connection': addConnectionRun,
|
|
29
|
+
'add-track-json': addTrackJsonRun,
|
|
30
|
+
'remove-track': removeTrackRun,
|
|
31
|
+
'set-default-session': setDefaultSessionRun,
|
|
39
32
|
};
|
|
40
|
-
async function main(args) {
|
|
33
|
+
export async function main(args) {
|
|
41
34
|
try {
|
|
42
|
-
const { values: flags, positionals } =
|
|
35
|
+
const { values: flags, positionals } = parseArgs({
|
|
43
36
|
args,
|
|
44
37
|
options: {
|
|
45
38
|
help: {
|
|
@@ -62,8 +55,7 @@ async function main(args) {
|
|
|
62
55
|
return;
|
|
63
56
|
}
|
|
64
57
|
if (flags.version && positionals.length === 0) {
|
|
65
|
-
|
|
66
|
-
console.log(`@jbrowse/cli version ${packageJson.version}`);
|
|
58
|
+
console.log(`@jbrowse/cli version ${version}`);
|
|
67
59
|
return;
|
|
68
60
|
}
|
|
69
61
|
const commandName = positionals[0];
|
package/dist/types/common.js
CHANGED
|
@@ -1,24 +1,12 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
};
|
|
5
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
-
exports.createRemoteStream = createRemoteStream;
|
|
7
|
-
exports.isURL = isURL;
|
|
8
|
-
exports.guessAdapterFromFileName = guessAdapterFromFileName;
|
|
9
|
-
exports.supported = supported;
|
|
10
|
-
exports.generateMeta = generateMeta;
|
|
11
|
-
const fs_1 = __importDefault(require("fs"));
|
|
12
|
-
const path_1 = __importDefault(require("path"));
|
|
13
|
-
const fetchWithProxy_ts_1 = __importDefault(require("../fetchWithProxy.js"));
|
|
14
|
-
async function createRemoteStream(urlIn) {
|
|
15
|
-
const res = await (0, fetchWithProxy_ts_1.default)(urlIn);
|
|
1
|
+
import fetch from "../cliFetch.js";
|
|
2
|
+
export async function createRemoteStream(urlIn) {
|
|
3
|
+
const res = await fetch(urlIn);
|
|
16
4
|
if (!res.ok) {
|
|
17
5
|
throw new Error(`Failed to fetch ${urlIn} status ${res.status} ${await res.text()}`);
|
|
18
6
|
}
|
|
19
7
|
return res;
|
|
20
8
|
}
|
|
21
|
-
function isURL(FileName) {
|
|
9
|
+
export function isURL(FileName) {
|
|
22
10
|
let url;
|
|
23
11
|
try {
|
|
24
12
|
url = new URL(FileName);
|
|
@@ -28,102 +16,12 @@ function isURL(FileName) {
|
|
|
28
16
|
}
|
|
29
17
|
return url.protocol === 'http:' || url.protocol === 'https:';
|
|
30
18
|
}
|
|
31
|
-
function makeLocation(location, protocol) {
|
|
32
|
-
if (protocol === 'uri') {
|
|
33
|
-
return {
|
|
34
|
-
uri: location,
|
|
35
|
-
locationType: 'UriLocation',
|
|
36
|
-
};
|
|
37
|
-
}
|
|
38
|
-
if (protocol === 'localPath') {
|
|
39
|
-
return {
|
|
40
|
-
localPath: path_1.default.resolve(location),
|
|
41
|
-
locationType: 'LocalPathLocation',
|
|
42
|
-
};
|
|
43
|
-
}
|
|
44
|
-
throw new Error(`invalid protocol ${protocol}`);
|
|
45
|
-
}
|
|
46
|
-
function guessAdapterFromFileName(filePath) {
|
|
47
|
-
const protocol = isURL(filePath) ? 'uri' : 'localPath';
|
|
48
|
-
const name = path_1.default.basename(filePath);
|
|
49
|
-
if (/\.vcf\.b?gz$/i.test(filePath)) {
|
|
50
|
-
return {
|
|
51
|
-
trackId: name,
|
|
52
|
-
name: name,
|
|
53
|
-
assemblyNames: [],
|
|
54
|
-
adapter: {
|
|
55
|
-
type: 'VcfTabixAdapter',
|
|
56
|
-
vcfGzLocation: makeLocation(filePath, protocol),
|
|
57
|
-
},
|
|
58
|
-
};
|
|
59
|
-
}
|
|
60
|
-
else if (/\.gff3?\.b?gz$/i.test(filePath)) {
|
|
61
|
-
return {
|
|
62
|
-
trackId: name,
|
|
63
|
-
name,
|
|
64
|
-
assemblyNames: [],
|
|
65
|
-
adapter: {
|
|
66
|
-
type: 'Gff3TabixAdapter',
|
|
67
|
-
gffGzLocation: makeLocation(filePath, protocol),
|
|
68
|
-
},
|
|
69
|
-
};
|
|
70
|
-
}
|
|
71
|
-
else if (/\.gtf?$/i.test(filePath)) {
|
|
72
|
-
return {
|
|
73
|
-
trackId: name,
|
|
74
|
-
name,
|
|
75
|
-
assemblyNames: [],
|
|
76
|
-
adapter: {
|
|
77
|
-
type: 'GtfAdapter',
|
|
78
|
-
gtfLocation: { uri: filePath, locationType: 'UriLocation' },
|
|
79
|
-
},
|
|
80
|
-
};
|
|
81
|
-
}
|
|
82
|
-
else if (/\.vcf$/i.test(filePath)) {
|
|
83
|
-
return {
|
|
84
|
-
trackId: name,
|
|
85
|
-
name,
|
|
86
|
-
assemblyNames: [],
|
|
87
|
-
adapter: {
|
|
88
|
-
type: 'VcfAdapter',
|
|
89
|
-
vcfLocation: makeLocation(filePath, protocol),
|
|
90
|
-
},
|
|
91
|
-
};
|
|
92
|
-
}
|
|
93
|
-
else if (/\.gff3?$/i.test(filePath)) {
|
|
94
|
-
return {
|
|
95
|
-
trackId: name,
|
|
96
|
-
name,
|
|
97
|
-
assemblyNames: [],
|
|
98
|
-
adapter: {
|
|
99
|
-
type: 'Gff3Adapter',
|
|
100
|
-
gffLocation: makeLocation(filePath, protocol),
|
|
101
|
-
},
|
|
102
|
-
};
|
|
103
|
-
}
|
|
104
|
-
else {
|
|
105
|
-
throw new Error(`Unsupported file type ${filePath}`);
|
|
106
|
-
}
|
|
107
|
-
}
|
|
108
19
|
const SUPPORTED_ADAPTERS = new Set([
|
|
109
20
|
'Gff3TabixAdapter',
|
|
110
21
|
'VcfTabixAdapter',
|
|
111
22
|
'Gff3Adapter',
|
|
112
23
|
'VcfAdapter',
|
|
113
24
|
]);
|
|
114
|
-
function supported(type = '') {
|
|
25
|
+
export function supported(type = '') {
|
|
115
26
|
return SUPPORTED_ADAPTERS.has(type);
|
|
116
27
|
}
|
|
117
|
-
async function generateMeta({ trackConfigs, attributes, outLocation, name, typesToExclude, assemblyNames, }) {
|
|
118
|
-
const tracks = trackConfigs.map(({ adapter, textSearching, trackId }) => ({
|
|
119
|
-
trackId,
|
|
120
|
-
attributesIndexed: textSearching?.indexingAttributes || attributes,
|
|
121
|
-
excludedTypes: textSearching?.indexingFeatureTypesToExclude || typesToExclude,
|
|
122
|
-
adapterConf: adapter,
|
|
123
|
-
}));
|
|
124
|
-
fs_1.default.writeFileSync(path_1.default.join(outLocation, 'trix', `${name}_meta.json`), JSON.stringify({
|
|
125
|
-
dateCreated: new Date().toISOString(),
|
|
126
|
-
tracks,
|
|
127
|
-
assemblyNames,
|
|
128
|
-
}, null, 2));
|
|
129
|
-
}
|
package/dist/util.js
CHANGED
|
@@ -1,34 +1,27 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
};
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
const
|
|
9
|
-
const promises_1 = require("fs/promises");
|
|
10
|
-
const path_1 = __importDefault(require("path"));
|
|
11
|
-
const stream_1 = require("stream");
|
|
12
|
-
const common_ts_1 = require("./types/common.js");
|
|
13
|
-
async function getLocalOrRemoteStream(uri, out) {
|
|
14
|
-
if ((0, common_ts_1.isURL)(uri)) {
|
|
15
|
-
const result = await (0, common_ts_1.createRemoteStream)(uri);
|
|
1
|
+
import { createReadStream } from 'fs';
|
|
2
|
+
import { stat } from 'fs/promises';
|
|
3
|
+
import path from 'path';
|
|
4
|
+
import { Readable } from 'stream';
|
|
5
|
+
import { createRemoteStream, isURL } from "./types/common.js";
|
|
6
|
+
export async function getLocalOrRemoteStream(uri, out) {
|
|
7
|
+
if (isURL(uri)) {
|
|
8
|
+
const result = await createRemoteStream(uri);
|
|
16
9
|
return {
|
|
17
10
|
totalBytes: +(result.headers.get('Content-Length') || 0),
|
|
18
11
|
stream: result.body,
|
|
19
12
|
};
|
|
20
13
|
}
|
|
21
14
|
else {
|
|
22
|
-
const filename =
|
|
23
|
-
const stats = await
|
|
24
|
-
const nodeStream =
|
|
15
|
+
const filename = path.isAbsolute(uri) ? uri : path.join(out, uri);
|
|
16
|
+
const stats = await stat(filename);
|
|
17
|
+
const nodeStream = createReadStream(filename);
|
|
25
18
|
return {
|
|
26
19
|
totalBytes: stats.size,
|
|
27
|
-
stream:
|
|
20
|
+
stream: Readable.toWeb(nodeStream),
|
|
28
21
|
};
|
|
29
22
|
}
|
|
30
23
|
}
|
|
31
|
-
function decodeURIComponentNoThrow(uri) {
|
|
24
|
+
export function decodeURIComponentNoThrow(uri) {
|
|
32
25
|
if (!uri.includes('%')) {
|
|
33
26
|
return uri;
|
|
34
27
|
}
|
package/dist/utils.js
CHANGED
|
@@ -1,47 +1,29 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
exports.debug = debug;
|
|
7
|
-
exports.resolveConfigPath = resolveConfigPath;
|
|
8
|
-
exports.readFile = readFile;
|
|
9
|
-
exports.readJsonFile = readJsonFile;
|
|
10
|
-
exports.writeJsonFile = writeJsonFile;
|
|
11
|
-
exports.resolveFileLocation = resolveFileLocation;
|
|
12
|
-
exports.readInlineOrFileJson = readInlineOrFileJson;
|
|
13
|
-
exports.fetchGithubVersions = fetchGithubVersions;
|
|
14
|
-
exports.getLatest = getLatest;
|
|
15
|
-
exports.fetchVersions = fetchVersions;
|
|
16
|
-
exports.getTag = getTag;
|
|
17
|
-
exports.getBranch = getBranch;
|
|
18
|
-
exports.printHelp = printHelp;
|
|
19
|
-
const fs_1 = require("fs");
|
|
20
|
-
const path_1 = __importDefault(require("path"));
|
|
21
|
-
const json_parse_better_errors_1 = __importDefault(require("json-parse-better-errors"));
|
|
22
|
-
const fetchWithProxy_ts_1 = __importDefault(require("./fetchWithProxy.js"));
|
|
23
|
-
function debug(message) {
|
|
1
|
+
import { promises as fsPromises } from 'fs';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
import parseJSON from 'json-parse-better-errors';
|
|
4
|
+
import fetch from "./cliFetch.js";
|
|
5
|
+
export function debug(message) {
|
|
24
6
|
if (process.env.DEBUG) {
|
|
25
7
|
console.log(`DEBUG: ${message}`);
|
|
26
8
|
}
|
|
27
9
|
}
|
|
28
|
-
async function resolveConfigPath(target, out) {
|
|
10
|
+
export async function resolveConfigPath(target, out) {
|
|
29
11
|
const output = target || out || '.';
|
|
30
|
-
const stat = await
|
|
12
|
+
const stat = await fsPromises.lstat(output);
|
|
31
13
|
return stat.isDirectory() ? `${output}/config.json` : output;
|
|
32
14
|
}
|
|
33
|
-
async function readFile(location) {
|
|
34
|
-
return
|
|
15
|
+
export async function readFile(location) {
|
|
16
|
+
return fsPromises.readFile(location, { encoding: 'utf8' });
|
|
35
17
|
}
|
|
36
|
-
async function readJsonFile(location) {
|
|
37
|
-
const contents = await
|
|
38
|
-
return (
|
|
18
|
+
export async function readJsonFile(location) {
|
|
19
|
+
const contents = await fsPromises.readFile(location, { encoding: 'utf8' });
|
|
20
|
+
return parseJSON(contents);
|
|
39
21
|
}
|
|
40
|
-
async function writeJsonFile(location, contents) {
|
|
22
|
+
export async function writeJsonFile(location, contents) {
|
|
41
23
|
debug(`Writing JSON file to ${process.cwd()} ${location}`);
|
|
42
|
-
return
|
|
24
|
+
return fsPromises.writeFile(location, JSON.stringify(contents, null, 2));
|
|
43
25
|
}
|
|
44
|
-
async function resolveFileLocation(location, check = true, inPlace = false) {
|
|
26
|
+
export async function resolveFileLocation(location, check = true, inPlace = false) {
|
|
45
27
|
let locationUrl;
|
|
46
28
|
try {
|
|
47
29
|
locationUrl = new URL(location);
|
|
@@ -51,7 +33,7 @@ async function resolveFileLocation(location, check = true, inPlace = false) {
|
|
|
51
33
|
}
|
|
52
34
|
if (locationUrl) {
|
|
53
35
|
if (check) {
|
|
54
|
-
const response = await (
|
|
36
|
+
const response = await fetch(locationUrl, { method: 'HEAD' });
|
|
55
37
|
if (!response.ok) {
|
|
56
38
|
throw new Error(`${locationUrl} result ${response.statusText}`);
|
|
57
39
|
}
|
|
@@ -60,13 +42,13 @@ async function resolveFileLocation(location, check = true, inPlace = false) {
|
|
|
60
42
|
}
|
|
61
43
|
let locationPath;
|
|
62
44
|
try {
|
|
63
|
-
locationPath = check ? await
|
|
45
|
+
locationPath = check ? await fsPromises.realpath(location) : location;
|
|
64
46
|
}
|
|
65
47
|
catch (e) {
|
|
66
48
|
// ignore
|
|
67
49
|
}
|
|
68
50
|
if (locationPath) {
|
|
69
|
-
const filePath =
|
|
51
|
+
const filePath = path.relative(process.cwd(), locationPath);
|
|
70
52
|
if (inPlace && filePath.startsWith('..')) {
|
|
71
53
|
console.warn(`Location ${filePath} is not in the JBrowse directory. Make sure it is still in your server directory.`);
|
|
72
54
|
}
|
|
@@ -74,11 +56,11 @@ async function resolveFileLocation(location, check = true, inPlace = false) {
|
|
|
74
56
|
}
|
|
75
57
|
throw new Error(`Could not resolve to a file or a URL: "${location}"`);
|
|
76
58
|
}
|
|
77
|
-
async function readInlineOrFileJson(inlineOrFileName) {
|
|
59
|
+
export async function readInlineOrFileJson(inlineOrFileName) {
|
|
78
60
|
let result;
|
|
79
61
|
// see if it's inline JSON
|
|
80
62
|
try {
|
|
81
|
-
result = (
|
|
63
|
+
result = parseJSON(inlineOrFileName);
|
|
82
64
|
}
|
|
83
65
|
catch (error) {
|
|
84
66
|
debug(`Not valid inline JSON, attempting to parse as filename: '${inlineOrFileName}'`);
|
|
@@ -87,23 +69,23 @@ async function readInlineOrFileJson(inlineOrFileName) {
|
|
|
87
69
|
}
|
|
88
70
|
return result;
|
|
89
71
|
}
|
|
90
|
-
async function fetchGithubVersions() {
|
|
72
|
+
export async function fetchGithubVersions() {
|
|
91
73
|
let versions = [];
|
|
92
74
|
for await (const iter of fetchVersions()) {
|
|
93
75
|
versions = [...versions, ...iter];
|
|
94
76
|
}
|
|
95
77
|
return versions;
|
|
96
78
|
}
|
|
97
|
-
async function getLatest() {
|
|
79
|
+
export async function getLatest() {
|
|
98
80
|
for await (const versions of fetchVersions()) {
|
|
99
81
|
// if a release was just uploaded, or an erroneous build was made then it
|
|
100
82
|
// might have no build asset
|
|
101
|
-
const
|
|
83
|
+
const nonprerelease = versions
|
|
102
84
|
.filter(release => !release.prerelease)
|
|
103
|
-
.
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
const file =
|
|
85
|
+
.find(release => release.assets?.length);
|
|
86
|
+
const first = nonprerelease;
|
|
87
|
+
if (first?.assets) {
|
|
88
|
+
const file = first.assets.find(f => f.name.includes('jbrowse-web'))?.browser_download_url;
|
|
107
89
|
if (!file) {
|
|
108
90
|
throw new Error('no jbrowse-web download found');
|
|
109
91
|
}
|
|
@@ -112,12 +94,12 @@ async function getLatest() {
|
|
|
112
94
|
}
|
|
113
95
|
throw new Error('no version tags found');
|
|
114
96
|
}
|
|
115
|
-
async function* fetchVersions() {
|
|
97
|
+
export async function* fetchVersions() {
|
|
116
98
|
let page = 1;
|
|
117
99
|
let result;
|
|
118
100
|
do {
|
|
119
101
|
const url = `https://api.github.com/repos/GMOD/jbrowse-components/releases?page=${page}`;
|
|
120
|
-
const response = await (
|
|
102
|
+
const response = await fetch(url);
|
|
121
103
|
if (response.ok) {
|
|
122
104
|
result = (await response.json());
|
|
123
105
|
yield result.filter(release => release.tag_name.startsWith('v'));
|
|
@@ -128,8 +110,8 @@ async function* fetchVersions() {
|
|
|
128
110
|
}
|
|
129
111
|
} while (result.length);
|
|
130
112
|
}
|
|
131
|
-
async function getTag(tag) {
|
|
132
|
-
const response = await (
|
|
113
|
+
export async function getTag(tag) {
|
|
114
|
+
const response = await fetch(`https://api.github.com/repos/GMOD/jbrowse-components/releases/tags/${tag}`);
|
|
133
115
|
if (response.ok) {
|
|
134
116
|
const result = (await response.json());
|
|
135
117
|
const file = result.assets?.find(f => f.name.includes('jbrowse-web'))?.browser_download_url;
|
|
@@ -140,20 +122,62 @@ async function getTag(tag) {
|
|
|
140
122
|
}
|
|
141
123
|
throw new Error(`Could not find version: ${response.statusText}`);
|
|
142
124
|
}
|
|
143
|
-
async function getBranch(branch) {
|
|
125
|
+
export async function getBranch(branch) {
|
|
144
126
|
return `https://s3.amazonaws.com/jbrowse.org/code/jb2/${branch}/jbrowse-web-${branch}.zip`;
|
|
145
127
|
}
|
|
146
|
-
function
|
|
128
|
+
function wrapText(text, width, indent) {
|
|
129
|
+
// Normalize: join single \n into spaces, preserve \n\n as paragraph breaks
|
|
130
|
+
const normalized = text
|
|
131
|
+
.replace(/\n\n/g, '\0')
|
|
132
|
+
.replace(/\n/g, ' ')
|
|
133
|
+
.replace(/\0/g, '\n\n');
|
|
134
|
+
const lines = [];
|
|
135
|
+
for (const line of normalized.split('\n')) {
|
|
136
|
+
if (line.length <= width) {
|
|
137
|
+
lines.push(line);
|
|
138
|
+
}
|
|
139
|
+
else {
|
|
140
|
+
const words = line.split(' ');
|
|
141
|
+
let current = '';
|
|
142
|
+
for (const word of words) {
|
|
143
|
+
if (current.length + word.length + 1 <= width) {
|
|
144
|
+
current += (current ? ' ' : '') + word;
|
|
145
|
+
}
|
|
146
|
+
else {
|
|
147
|
+
if (current) {
|
|
148
|
+
lines.push(current);
|
|
149
|
+
}
|
|
150
|
+
current = word;
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
if (current) {
|
|
154
|
+
lines.push(current);
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
return lines.join(`\n${indent}`);
|
|
159
|
+
}
|
|
160
|
+
export function printHelp({ description, options, examples, usage, }) {
|
|
161
|
+
const termWidth = process.stdout.columns || 80;
|
|
147
162
|
console.log(description);
|
|
148
163
|
console.log(`\nUsage: ${usage || 'jbrowse <command> [options]'}`);
|
|
149
164
|
console.log('\nOptions:');
|
|
150
165
|
for (const [name, option] of Object.entries(options)) {
|
|
151
|
-
const
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
const namePadded = `--${name}`.padEnd(
|
|
155
|
-
const
|
|
156
|
-
|
|
166
|
+
const opt = option;
|
|
167
|
+
const shortFlag = opt.short;
|
|
168
|
+
const prefix = shortFlag ? ` -${shortFlag}, ` : ' ';
|
|
169
|
+
const namePadded = `--${name}`.padEnd(22, ' ');
|
|
170
|
+
const indent = ' '.repeat(prefix.length + namePadded.length + 1);
|
|
171
|
+
const descWidth = termWidth - indent.length;
|
|
172
|
+
let desc = opt.description || '';
|
|
173
|
+
if (opt.choices) {
|
|
174
|
+
desc += ` [choices: ${opt.choices.join(', ')}]`;
|
|
175
|
+
}
|
|
176
|
+
if (opt.default !== undefined) {
|
|
177
|
+
desc += ` [default: ${opt.default}]`;
|
|
178
|
+
}
|
|
179
|
+
const wrapped = desc ? wrapText(desc, descWidth, indent) : '';
|
|
180
|
+
console.log(`${prefix}${namePadded} ${wrapped}\n`);
|
|
157
181
|
}
|
|
158
|
-
console.log(
|
|
182
|
+
console.log(examples.join('\n'));
|
|
159
183
|
}
|
package/dist/version.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const version = '4.1.3';
|
package/package.json
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jbrowse/cli",
|
|
3
|
-
"version": "4.
|
|
3
|
+
"version": "4.1.3",
|
|
4
|
+
"type": "module",
|
|
4
5
|
"description": "A command line tool for working with JBrowse 2",
|
|
5
6
|
"keywords": [
|
|
6
7
|
"jbrowse",
|
|
@@ -30,20 +31,20 @@
|
|
|
30
31
|
"dependencies": {
|
|
31
32
|
"cli-progress": "^3.12.0",
|
|
32
33
|
"command-exists": "^1.2.9",
|
|
33
|
-
"cors": "^2.8.
|
|
34
|
+
"cors": "^2.8.6",
|
|
34
35
|
"decompress": "^4.2.1",
|
|
35
36
|
"express": "^5.2.1",
|
|
36
|
-
"ixixx": "^3.0.
|
|
37
|
+
"ixixx": "^3.0.3",
|
|
37
38
|
"json-parse-better-errors": "^1.0.2",
|
|
38
|
-
"
|
|
39
|
-
"
|
|
39
|
+
"tmp": "^0.2.5",
|
|
40
|
+
"@jbrowse/text-indexing-core": "^4.1.3"
|
|
40
41
|
},
|
|
41
42
|
"publishConfig": {
|
|
42
43
|
"access": "public"
|
|
43
44
|
},
|
|
44
45
|
"scripts": {
|
|
45
46
|
"prebuild": "pnpm clean",
|
|
46
|
-
"build": "tsc && webpack",
|
|
47
|
+
"build": "tsc && webpack -c webpack.config.mjs",
|
|
47
48
|
"clean": "rimraf bundle",
|
|
48
49
|
"generate-readme": "./generate_readme.sh > README.md"
|
|
49
50
|
}
|
package/dist/fetchWithProxy.js
DELETED
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.default = fetchWithProxy;
|
|
4
|
-
const node_1 = require("node-fetch-native/node");
|
|
5
|
-
const proxy_1 = require("node-fetch-native/proxy");
|
|
6
|
-
const proxy = (0, proxy_1.createProxy)();
|
|
7
|
-
// The correct proxy `Agent` implementation to use will be determined
|
|
8
|
-
// via the `http_proxy` / `https_proxy` / `no_proxy` / etc. env vars
|
|
9
|
-
// https://github.com/unjs/node-fetch-native?tab=readme-ov-file#proxy-support
|
|
10
|
-
function fetchWithProxy(url, options = {}) {
|
|
11
|
-
return (0, node_1.fetch)(url, { ...options, ...proxy });
|
|
12
|
-
}
|