@irfanshadikrishad/anilist 1.0.0-forbidden.1 → 1.0.0-forbidden.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 +32 -26
- package/bin/helpers/auth.d.ts +36 -6
- package/bin/helpers/auth.js +139 -95
- package/bin/helpers/fetcher.d.ts +3 -2
- package/bin/helpers/fetcher.js +29 -24
- package/bin/helpers/lists.d.ts +4 -1
- package/bin/helpers/lists.js +357 -268
- package/bin/helpers/queries.d.ts +6 -4
- package/bin/helpers/queries.js +19 -4
- package/bin/helpers/types.d.ts +304 -8
- package/bin/helpers/workers.d.ts +9 -5
- package/bin/helpers/workers.js +155 -69
- package/bin/index.js +13 -9
- package/package.json +18 -10
- package/assets/binance.jpg +0 -0
- /package/{LICENSE → LICENSE.md} +0 -0
package/bin/helpers/workers.js
CHANGED
|
@@ -11,12 +11,15 @@ import fs from "fs";
|
|
|
11
11
|
import { readdir, writeFile } from "fs/promises";
|
|
12
12
|
import inquirer from "inquirer";
|
|
13
13
|
import { parse } from "json2csv";
|
|
14
|
+
import { createRequire } from "module";
|
|
14
15
|
import open from "open";
|
|
15
16
|
import { homedir } from "os";
|
|
16
17
|
import { join } from "path";
|
|
17
18
|
import process from "process";
|
|
18
19
|
import { Auth } from "./auth.js";
|
|
19
|
-
import {
|
|
20
|
+
import { fetcher } from "./fetcher.js";
|
|
21
|
+
import { animeSearchQuery } from "./queries.js";
|
|
22
|
+
import { MALAnimeStatus, MALMangaStatus, } from "./types.js";
|
|
20
23
|
const aniListEndpoint = `https://graphql.anilist.co`;
|
|
21
24
|
const redirectUri = "https://anilist.co/api/v2/oauth/pin";
|
|
22
25
|
function getTitle(title) {
|
|
@@ -140,9 +143,10 @@ function selectFile(fileType) {
|
|
|
140
143
|
return __awaiter(this, void 0, void 0, function* () {
|
|
141
144
|
try {
|
|
142
145
|
const files = yield listFilesInDownloadFolder();
|
|
146
|
+
console.log(getDownloadFolderPath());
|
|
143
147
|
// Filter to include only files, not directories, with the specified extension
|
|
144
148
|
const onlyFiles = files.filter((file) => {
|
|
145
|
-
const filePath =
|
|
149
|
+
const filePath = `${getDownloadFolderPath()}/${file}`; // Adjust this to the correct path
|
|
146
150
|
const isFile = fs.lstatSync(filePath).isFile(); // Check if it's a file
|
|
147
151
|
return isFile && file.endsWith(fileType);
|
|
148
152
|
});
|
|
@@ -168,49 +172,49 @@ function selectFile(fileType) {
|
|
|
168
172
|
});
|
|
169
173
|
}
|
|
170
174
|
function createAnimeXML(malId, progress, status, episodes, title) {
|
|
171
|
-
return `
|
|
172
|
-
<anime>
|
|
173
|
-
<series_animedb_id>${malId}</series_animedb_id>
|
|
174
|
-
<series_title><![CDATA[${title}]]></series_title>
|
|
175
|
-
<series_type>""</series_type>
|
|
176
|
-
<series_episodes>${episodes}</series_episodes>
|
|
177
|
-
<my_id>0</my_id>
|
|
178
|
-
<my_watched_episodes>${progress}</my_watched_episodes>
|
|
179
|
-
<my_start_date>0000-00-00</my_start_date>
|
|
180
|
-
<my_finish_date>0000-00-00</my_finish_date>
|
|
181
|
-
<my_score>0</my_score>
|
|
182
|
-
<my_storage_value>0.00</my_storage_value>
|
|
183
|
-
<my_status>${status}</my_status>
|
|
184
|
-
<my_comments><![CDATA[]]></my_comments>
|
|
185
|
-
<my_times_watched>0</my_times_watched>
|
|
186
|
-
<my_rewatch_value></my_rewatch_value>
|
|
187
|
-
<my_priority>LOW</my_priority>
|
|
188
|
-
<my_tags><![CDATA[]]></my_tags>
|
|
189
|
-
<my_rewatching>0</my_rewatching>
|
|
190
|
-
<my_rewatching_ep>0</my_rewatching_ep>
|
|
191
|
-
<my_discuss>0</my_discuss>
|
|
192
|
-
<my_sns>default</my_sns>
|
|
193
|
-
<update_on_import>1</update_on_import>
|
|
175
|
+
return `
|
|
176
|
+
<anime>
|
|
177
|
+
<series_animedb_id>${malId}</series_animedb_id>
|
|
178
|
+
<series_title><![CDATA[${title}]]></series_title>
|
|
179
|
+
<series_type>""</series_type>
|
|
180
|
+
<series_episodes>${episodes}</series_episodes>
|
|
181
|
+
<my_id>0</my_id>
|
|
182
|
+
<my_watched_episodes>${progress}</my_watched_episodes>
|
|
183
|
+
<my_start_date>0000-00-00</my_start_date>
|
|
184
|
+
<my_finish_date>0000-00-00</my_finish_date>
|
|
185
|
+
<my_score>0</my_score>
|
|
186
|
+
<my_storage_value>0.00</my_storage_value>
|
|
187
|
+
<my_status>${status}</my_status>
|
|
188
|
+
<my_comments><![CDATA[]]></my_comments>
|
|
189
|
+
<my_times_watched>0</my_times_watched>
|
|
190
|
+
<my_rewatch_value></my_rewatch_value>
|
|
191
|
+
<my_priority>LOW</my_priority>
|
|
192
|
+
<my_tags><![CDATA[]]></my_tags>
|
|
193
|
+
<my_rewatching>0</my_rewatching>
|
|
194
|
+
<my_rewatching_ep>0</my_rewatching_ep>
|
|
195
|
+
<my_discuss>0</my_discuss>
|
|
196
|
+
<my_sns>default</my_sns>
|
|
197
|
+
<update_on_import>1</update_on_import>
|
|
194
198
|
</anime>`;
|
|
195
199
|
}
|
|
196
200
|
function createMangaXML(malId, progress, status, chapters, title) {
|
|
197
|
-
return `
|
|
198
|
-
<manga>
|
|
199
|
-
<manga_mangadb_id>${malId}</manga_mangadb_id>
|
|
200
|
-
<manga_title><![CDATA[${title ? title : "unknown"}]]></manga_title>
|
|
201
|
-
<manga_volumes>0</manga_volumes>
|
|
202
|
-
<manga_chapters>${chapters ? chapters : 0}</manga_chapters>
|
|
203
|
-
<my_id>0</my_id>
|
|
204
|
-
<my_read_chapters>${progress}</my_read_chapters>
|
|
205
|
-
<my_start_date>0000-00-00</my_start_date>
|
|
206
|
-
<my_finish_date>0000-00-00</my_finish_date>
|
|
207
|
-
<my_score>0</my_score>
|
|
208
|
-
<my_status>${status}</my_status>
|
|
209
|
-
<my_reread_value></my_reread_value>
|
|
210
|
-
<my_priority>LOW</my_priority>
|
|
211
|
-
<my_rereading>0</my_rereading>
|
|
212
|
-
<my_discuss>0</my_discuss>
|
|
213
|
-
<update_on_import>1</update_on_import>
|
|
201
|
+
return `
|
|
202
|
+
<manga>
|
|
203
|
+
<manga_mangadb_id>${malId}</manga_mangadb_id>
|
|
204
|
+
<manga_title><![CDATA[${title ? title : "unknown"}]]></manga_title>
|
|
205
|
+
<manga_volumes>0</manga_volumes>
|
|
206
|
+
<manga_chapters>${chapters ? chapters : 0}</manga_chapters>
|
|
207
|
+
<my_id>0</my_id>
|
|
208
|
+
<my_read_chapters>${progress}</my_read_chapters>
|
|
209
|
+
<my_start_date>0000-00-00</my_start_date>
|
|
210
|
+
<my_finish_date>0000-00-00</my_finish_date>
|
|
211
|
+
<my_score>0</my_score>
|
|
212
|
+
<my_status>${status}</my_status>
|
|
213
|
+
<my_reread_value></my_reread_value>
|
|
214
|
+
<my_priority>LOW</my_priority>
|
|
215
|
+
<my_rereading>0</my_rereading>
|
|
216
|
+
<my_discuss>0</my_discuss>
|
|
217
|
+
<update_on_import>1</update_on_import>
|
|
214
218
|
</manga>`;
|
|
215
219
|
}
|
|
216
220
|
function createAnimeListXML(mediaWithProgress) {
|
|
@@ -230,19 +234,19 @@ function createAnimeListXML(mediaWithProgress) {
|
|
|
230
234
|
const status = statusMap[anime.status];
|
|
231
235
|
return createAnimeXML(malId, progress, status, episodes, title);
|
|
232
236
|
});
|
|
233
|
-
return `<myanimelist>
|
|
234
|
-
<myinfo>
|
|
235
|
-
<user_id/>
|
|
236
|
-
<user_name>${yield Auth.MyUserName()}</user_name>
|
|
237
|
-
<user_export_type>1</user_export_type>
|
|
238
|
-
<user_total_anime>0</user_total_anime>
|
|
239
|
-
<user_total_watching>0</user_total_watching>
|
|
240
|
-
<user_total_completed>0</user_total_completed>
|
|
241
|
-
<user_total_onhold>0</user_total_onhold>
|
|
242
|
-
<user_total_dropped>0</user_total_dropped>
|
|
243
|
-
<user_total_plantowatch>0</user_total_plantowatch>
|
|
244
|
-
</myinfo>
|
|
245
|
-
\n${xmlEntries.join("\n")}\n
|
|
237
|
+
return `<myanimelist>
|
|
238
|
+
<myinfo>
|
|
239
|
+
<user_id/>
|
|
240
|
+
<user_name>${yield Auth.MyUserName()}</user_name>
|
|
241
|
+
<user_export_type>1</user_export_type>
|
|
242
|
+
<user_total_anime>0</user_total_anime>
|
|
243
|
+
<user_total_watching>0</user_total_watching>
|
|
244
|
+
<user_total_completed>0</user_total_completed>
|
|
245
|
+
<user_total_onhold>0</user_total_onhold>
|
|
246
|
+
<user_total_dropped>0</user_total_dropped>
|
|
247
|
+
<user_total_plantowatch>0</user_total_plantowatch>
|
|
248
|
+
</myinfo>
|
|
249
|
+
\n${xmlEntries.join("\n")}\n
|
|
246
250
|
</myanimelist>`;
|
|
247
251
|
});
|
|
248
252
|
}
|
|
@@ -263,20 +267,102 @@ function createMangaListXML(mediaWithProgress) {
|
|
|
263
267
|
const status = statusMap[manga.status];
|
|
264
268
|
return createMangaXML(malId, progress, status, chapters, title);
|
|
265
269
|
});
|
|
266
|
-
return `<myanimelist>
|
|
267
|
-
<myinfo>
|
|
268
|
-
<user_id/>
|
|
269
|
-
<user_name>${yield Auth.MyUserName()}</user_name>
|
|
270
|
-
<user_export_type>2</user_export_type>
|
|
271
|
-
<user_total_manga>5</user_total_manga>
|
|
272
|
-
<user_total_reading>1</user_total_reading>
|
|
273
|
-
<user_total_completed>1</user_total_completed>
|
|
274
|
-
<user_total_onhold>1</user_total_onhold>
|
|
275
|
-
<user_total_dropped>1</user_total_dropped>
|
|
276
|
-
<user_total_plantoread>1</user_total_plantoread>
|
|
277
|
-
</myinfo>
|
|
278
|
-
\n${xmlEntries.join("\n")}\n
|
|
270
|
+
return `<myanimelist>
|
|
271
|
+
<myinfo>
|
|
272
|
+
<user_id/>
|
|
273
|
+
<user_name>${yield Auth.MyUserName()}</user_name>
|
|
274
|
+
<user_export_type>2</user_export_type>
|
|
275
|
+
<user_total_manga>5</user_total_manga>
|
|
276
|
+
<user_total_reading>1</user_total_reading>
|
|
277
|
+
<user_total_completed>1</user_total_completed>
|
|
278
|
+
<user_total_onhold>1</user_total_onhold>
|
|
279
|
+
<user_total_dropped>1</user_total_dropped>
|
|
280
|
+
<user_total_plantoread>1</user_total_plantoread>
|
|
281
|
+
</myinfo>
|
|
282
|
+
\n${xmlEntries.join("\n")}\n
|
|
279
283
|
</myanimelist>`;
|
|
280
284
|
});
|
|
281
285
|
}
|
|
282
|
-
|
|
286
|
+
function getCurrentPackageVersion() {
|
|
287
|
+
const require = createRequire(import.meta.url);
|
|
288
|
+
const packageJson = require("../../package.json");
|
|
289
|
+
const version = packageJson.version;
|
|
290
|
+
return version || null;
|
|
291
|
+
}
|
|
292
|
+
function timestampToTimeAgo(timestamp) {
|
|
293
|
+
const now = Math.floor(Date.now() / 1000);
|
|
294
|
+
const elapsed = now - timestamp;
|
|
295
|
+
if (elapsed < 60) {
|
|
296
|
+
return `${elapsed} second${elapsed === 1 ? "" : "s"} ago`;
|
|
297
|
+
}
|
|
298
|
+
else if (elapsed < 3600) {
|
|
299
|
+
const minutes = Math.floor(elapsed / 60);
|
|
300
|
+
return `${minutes} minute${minutes === 1 ? "" : "s"} ago`;
|
|
301
|
+
}
|
|
302
|
+
else if (elapsed < 86400) {
|
|
303
|
+
const hours = Math.floor(elapsed / 3600);
|
|
304
|
+
return `${hours} hour${hours === 1 ? "" : "s"} ago`;
|
|
305
|
+
}
|
|
306
|
+
else if (elapsed < 2592000) {
|
|
307
|
+
const days = Math.floor(elapsed / 86400);
|
|
308
|
+
return `${days} day${days === 1 ? "" : "s"} ago`;
|
|
309
|
+
}
|
|
310
|
+
else if (elapsed < 31536000) {
|
|
311
|
+
const months = Math.floor(elapsed / 2592000);
|
|
312
|
+
return `${months} month${months === 1 ? "" : "s"} ago`;
|
|
313
|
+
}
|
|
314
|
+
else {
|
|
315
|
+
const years = Math.floor(elapsed / 31536000);
|
|
316
|
+
return `${years} year${years === 1 ? "" : "s"} ago`;
|
|
317
|
+
}
|
|
318
|
+
}
|
|
319
|
+
function activityBy(activity) {
|
|
320
|
+
var _a, _b, _c, _d;
|
|
321
|
+
if ((_a = activity === null || activity === void 0 ? void 0 : activity.messenger) === null || _a === void 0 ? void 0 : _a.name) {
|
|
322
|
+
return `[${activity.id}]\t${activity.messenger.name} messaged ${activity.recipient.name}`;
|
|
323
|
+
}
|
|
324
|
+
else if ((_c = (_b = activity === null || activity === void 0 ? void 0 : activity.media) === null || _b === void 0 ? void 0 : _b.title) === null || _c === void 0 ? void 0 : _c.userPreferred) {
|
|
325
|
+
if (activity.progress) {
|
|
326
|
+
return `[${activity.id}]\t${activity.user.name} ${activity.status} ${activity.progress} of ${activity.media.title.userPreferred}`;
|
|
327
|
+
}
|
|
328
|
+
else {
|
|
329
|
+
return `[${activity.id}]\t${activity.user.name} ${activity.status} ${activity.media.title.userPreferred}`;
|
|
330
|
+
}
|
|
331
|
+
}
|
|
332
|
+
else if ((_d = activity === null || activity === void 0 ? void 0 : activity.user) === null || _d === void 0 ? void 0 : _d.name) {
|
|
333
|
+
return `[${activity.id}]\t${activity.user.name}`;
|
|
334
|
+
}
|
|
335
|
+
else {
|
|
336
|
+
return `[${activity === null || activity === void 0 ? void 0 : activity.id}] ???`;
|
|
337
|
+
}
|
|
338
|
+
}
|
|
339
|
+
const anidbToanilistMapper = (romanjiName, year, englishName) => __awaiter(void 0, void 0, void 0, function* () {
|
|
340
|
+
const fetchAnime = (search) => __awaiter(void 0, void 0, void 0, function* () {
|
|
341
|
+
var _a;
|
|
342
|
+
try {
|
|
343
|
+
const response = yield fetcher(animeSearchQuery, {
|
|
344
|
+
search,
|
|
345
|
+
perPage: 50,
|
|
346
|
+
});
|
|
347
|
+
return ((_a = response.data) === null || _a === void 0 ? void 0 : _a.Page.media) || [];
|
|
348
|
+
}
|
|
349
|
+
catch (error) {
|
|
350
|
+
console.error("Error fetching AniList data:", error);
|
|
351
|
+
return [];
|
|
352
|
+
}
|
|
353
|
+
});
|
|
354
|
+
// Search using romanjiName first
|
|
355
|
+
let results = yield fetchAnime(romanjiName);
|
|
356
|
+
// If no results, fallback to englishName
|
|
357
|
+
if (!results.length && englishName) {
|
|
358
|
+
results = yield fetchAnime(englishName);
|
|
359
|
+
}
|
|
360
|
+
// Match using year
|
|
361
|
+
for (const anime of results) {
|
|
362
|
+
if (anime.startDate.year === year) {
|
|
363
|
+
return anime.id;
|
|
364
|
+
}
|
|
365
|
+
}
|
|
366
|
+
return null;
|
|
367
|
+
});
|
|
368
|
+
export { activityBy, anidbToanilistMapper, aniListEndpoint, createAnimeListXML, createAnimeXML, createMangaListXML, createMangaXML, formatDateObject, getCurrentPackageVersion, getDownloadFolderPath, getFormattedDate, getNextSeasonAndYear, getTitle, redirectUri, removeHtmlAndMarkdown, saveJSONasCSV, saveJSONasJSON, selectFile, timestampToTimeAgo, };
|
package/bin/index.js
CHANGED
|
@@ -9,18 +9,15 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
|
|
|
9
9
|
});
|
|
10
10
|
};
|
|
11
11
|
import { Command } from "commander";
|
|
12
|
-
import { createRequire } from "module";
|
|
13
12
|
import process from "process";
|
|
14
13
|
import { Auth } from "./helpers/auth.js";
|
|
15
14
|
import { AniList } from "./helpers/lists.js";
|
|
16
|
-
|
|
17
|
-
const packageJson = require("../package.json");
|
|
18
|
-
const version = packageJson.version;
|
|
15
|
+
import { getCurrentPackageVersion } from "./helpers/workers.js";
|
|
19
16
|
const cli = new Command();
|
|
20
17
|
cli
|
|
21
18
|
.name("anilist")
|
|
22
19
|
.description("Minimalist unofficial AniList CLI for Anime and Manga Enthusiasts.")
|
|
23
|
-
.version(
|
|
20
|
+
.version(getCurrentPackageVersion());
|
|
24
21
|
cli
|
|
25
22
|
.command("login")
|
|
26
23
|
.description("Login with AniList")
|
|
@@ -35,7 +32,7 @@ cli
|
|
|
35
32
|
}
|
|
36
33
|
}));
|
|
37
34
|
cli
|
|
38
|
-
.command("
|
|
35
|
+
.command("whoami")
|
|
39
36
|
.description("Get details of the logged in user")
|
|
40
37
|
.action(() => __awaiter(void 0, void 0, void 0, function* () {
|
|
41
38
|
yield Auth.Myself();
|
|
@@ -91,7 +88,7 @@ cli
|
|
|
91
88
|
.description("Delete entire collections of anime or manga")
|
|
92
89
|
.option("-a, --anime", "For anime list of authenticated user", false)
|
|
93
90
|
.option("-m, --manga", "For manga list of authenticated user", false)
|
|
94
|
-
.option("-
|
|
91
|
+
.option("-s, --activity", "For activity of authenticated user", false)
|
|
95
92
|
.action((_a) => __awaiter(void 0, [_a], void 0, function* ({ anime, manga, activity }) {
|
|
96
93
|
const selectedOptions = [anime, manga, activity].filter(Boolean).length;
|
|
97
94
|
if (selectedOptions === 0) {
|
|
@@ -209,8 +206,15 @@ cli
|
|
|
209
206
|
cli
|
|
210
207
|
.command("autolike")
|
|
211
208
|
.alias("al")
|
|
209
|
+
.option("-2, --v2", "Like the activities", false)
|
|
210
|
+
.option("-c, --count <number>", "Number of activities to like", "25")
|
|
212
211
|
.description("Autolike following or global activities.")
|
|
213
|
-
.action(() => __awaiter(void 0,
|
|
214
|
-
|
|
212
|
+
.action((_a) => __awaiter(void 0, [_a], void 0, function* ({ v2, count }) {
|
|
213
|
+
if (v2) {
|
|
214
|
+
yield Auth.LikeFollowingActivityV2(count);
|
|
215
|
+
}
|
|
216
|
+
else {
|
|
217
|
+
yield Auth.AutoLike();
|
|
218
|
+
}
|
|
215
219
|
}));
|
|
216
220
|
cli.parse(process.argv);
|
package/package.json
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"name": "@irfanshadikrishad/anilist",
|
|
3
3
|
"description": "Minimalist unofficial AniList CLI for Anime and Manga Enthusiasts",
|
|
4
4
|
"author": "Irfan Shadik Rishad",
|
|
5
|
-
"version": "1.0.0-forbidden.
|
|
5
|
+
"version": "1.0.0-forbidden.2",
|
|
6
6
|
"main": "./bin/index.js",
|
|
7
7
|
"type": "module",
|
|
8
8
|
"types": "./bin/index.d.ts",
|
|
@@ -13,12 +13,14 @@
|
|
|
13
13
|
"access": "public"
|
|
14
14
|
},
|
|
15
15
|
"scripts": {
|
|
16
|
-
"build": "rm -rf ./bin && tsc
|
|
16
|
+
"build": "rm -rf ./bin && tsc",
|
|
17
|
+
"buildw": "rm -rf ./bin && tsc -w",
|
|
17
18
|
"format": "prettier . --write",
|
|
18
19
|
"format:check": "prettier . --check",
|
|
19
20
|
"lint": "eslint ./dist",
|
|
20
21
|
"lint:fix": "eslint ./dist --fix",
|
|
21
|
-
"all": "npm run lint && npm run lint:fix && npm run format"
|
|
22
|
+
"all": "npm run build && npm run lint && npm run lint:fix && npm run format && npm test",
|
|
23
|
+
"test": "jest ./tests"
|
|
22
24
|
},
|
|
23
25
|
"keywords": [
|
|
24
26
|
"anilist",
|
|
@@ -52,21 +54,27 @@
|
|
|
52
54
|
},
|
|
53
55
|
"license": "MPL-2.0",
|
|
54
56
|
"devDependencies": {
|
|
55
|
-
"@
|
|
57
|
+
"@babel/preset-env": "^7.26.0",
|
|
58
|
+
"@eslint/js": "^9.18.0",
|
|
59
|
+
"@types/jest": "^29.5.14",
|
|
56
60
|
"@types/json2csv": "^5.0.7",
|
|
57
|
-
"@types/node": "^22.10.
|
|
58
|
-
"eslint": "^
|
|
61
|
+
"@types/node": "^22.10.7",
|
|
62
|
+
"@typescript-eslint/eslint-plugin": "^8.20.0",
|
|
63
|
+
"eslint": "^9.18.0",
|
|
59
64
|
"globals": "^15.14.0",
|
|
65
|
+
"jest": "^29.7.0",
|
|
60
66
|
"prettier": "^3.4.2",
|
|
61
67
|
"prettier-plugin-organize-imports": "^4.1.0",
|
|
62
|
-
"
|
|
63
|
-
"
|
|
68
|
+
"ts-jest": "^29.2.5",
|
|
69
|
+
"ts-node": "^10.9.2",
|
|
70
|
+
"typescript": "^5.7.3"
|
|
64
71
|
},
|
|
65
72
|
"dependencies": {
|
|
66
|
-
"commander": "^
|
|
73
|
+
"commander": "^13.0.0",
|
|
67
74
|
"fast-xml-parser": "^4.5.1",
|
|
68
|
-
"inquirer": "^12.2
|
|
75
|
+
"inquirer": "^12.3.2",
|
|
69
76
|
"json2csv": "^6.0.0-alpha.2",
|
|
77
|
+
"jsonrepair": "^3.11.2",
|
|
70
78
|
"node-fetch": "^3.3.2",
|
|
71
79
|
"open": "^10.1.0"
|
|
72
80
|
}
|
package/assets/binance.jpg
DELETED
|
Binary file
|
/package/{LICENSE → LICENSE.md}
RENAMED
|
File without changes
|