fix(core): update
This commit is contained in:
parent
461ec9d6b6
commit
429df4c0d1
@ -36,5 +36,11 @@
|
||||
"cli.js",
|
||||
"npmextra.json",
|
||||
"readme.md"
|
||||
]
|
||||
],
|
||||
"dependencies": {
|
||||
"@push.rocks/smartfile": "^10.0.28",
|
||||
"@push.rocks/smartpath": "^5.0.5",
|
||||
"csv-parser": "^3.0.0",
|
||||
"unzipper": "^0.10.14"
|
||||
}
|
||||
}
|
||||
|
262
pnpm-lock.yaml
generated
262
pnpm-lock.yaml
generated
File diff suppressed because it is too large
Load Diff
12
test/test.ts
12
test/test.ts
@ -1,8 +1,16 @@
|
||||
import { expect, expectAsync, tap } from '@push.rocks/tapbundle';
|
||||
import * as abuseCh from '../ts/index.js';
|
||||
|
||||
tap.test('first test', async () => {
|
||||
console.log(abuseCh);
|
||||
tap.test('should deal with UrlHouse data', async () => {
|
||||
const urlHouse = new abuseCh.UrlHouse();
|
||||
const data = await urlHouse.getData();
|
||||
console.log(data);
|
||||
});
|
||||
|
||||
tap.test('should deal with UrlHouse data', async () => {
|
||||
const threatFox = new abuseCh.ThreatFox();
|
||||
const data = await threatFox.getData();
|
||||
console.log(data);
|
||||
});
|
||||
|
||||
tap.start();
|
||||
|
@ -3,6 +3,6 @@
|
||||
*/
|
||||
export const commitinfo = {
|
||||
name: '@apiclient.xyz/abuse.ch',
|
||||
version: '1.0.2',
|
||||
version: '1.0.3',
|
||||
description: 'an unofficial client to retrieve abuse.ch data'
|
||||
}
|
||||
|
76
ts/abuse.ch.classes.threatfox.ts
Normal file
76
ts/abuse.ch.classes.threatfox.ts
Normal file
@ -0,0 +1,76 @@
|
||||
import * as plugins from './plugins.js';
|
||||
import * as paths from './paths.js';
|
||||
|
||||
export interface IThreatFoxData {
|
||||
ID: string;
|
||||
Dateadded: string;
|
||||
URL: string;
|
||||
URLStatus: string;
|
||||
Threat: string;
|
||||
AssociatedTags: string;
|
||||
ThreatFoxLink: string;
|
||||
Reporter: string;
|
||||
}
|
||||
|
||||
export class ThreatFox {
|
||||
private static readonly THREATFOX_API_URL: string = 'https://threatfox.abuse.ch/export/csv/full'; // Replace with actual API endpoint
|
||||
|
||||
public async getData(): Promise<IThreatFoxData[]> {
|
||||
plugins.smartfile.fs.ensureDirSync(paths.threatFoxTmp);
|
||||
const zipPath = plugins.path.join(paths.threatFoxTmp, 'threatfox.zip');
|
||||
const csvPath = plugins.path.join(paths.threatFoxTmp, 'full.csv');
|
||||
|
||||
const response = await fetch(ThreatFox.THREATFOX_API_URL);
|
||||
if (!response.ok) {
|
||||
throw new Error(`HTTP error! status: ${response.status}`);
|
||||
}
|
||||
|
||||
await new Promise((resolve, reject) => {
|
||||
const fileStream = plugins.fs.createWriteStream(zipPath);
|
||||
// @ts-ignore
|
||||
const readable = plugins.stream.Readable.from(response.body);
|
||||
plugins.stream.pipeline(readable, fileStream, (err) => {
|
||||
if (err) reject(err);
|
||||
else resolve(null);
|
||||
});
|
||||
});
|
||||
|
||||
await new Promise((resolve, reject) => {
|
||||
plugins.stream.pipeline(
|
||||
plugins.fs.createReadStream(zipPath),
|
||||
plugins.unzipper.Extract({ path: paths.threatFoxTmp }),
|
||||
(err) => {
|
||||
if (err) reject(err);
|
||||
else resolve(null);
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
let data: IThreatFoxData[] = [];
|
||||
await new Promise((resolve, reject) => {
|
||||
plugins.stream.pipeline(
|
||||
plugins.fs.createReadStream(csvPath),
|
||||
plugins.csv({
|
||||
headers: ['ID', 'Dateadded', 'URL', 'URLStatus', 'Threat', 'AssociatedTags', 'ThreatFoxLink', 'Reporter'],
|
||||
mapValues: ({ header, value }) => value.trim()
|
||||
}),
|
||||
(err) => {
|
||||
if (err) reject(err);
|
||||
}
|
||||
)
|
||||
.on('data', (row) => {
|
||||
data.push(row);
|
||||
})
|
||||
.on('end', resolve)
|
||||
.on('error', reject);
|
||||
});
|
||||
data = data.map((item) => {
|
||||
return {
|
||||
...item,
|
||||
URL: item.URL?.replace('http', 'ht-NOCLICK-NOLINK-tp'),
|
||||
}
|
||||
});
|
||||
plugins.smartfile.fs.removeSync(paths.threatFoxTmp);
|
||||
return data;
|
||||
}
|
||||
}
|
76
ts/abuse.ch.classes.urlhouse.ts
Normal file
76
ts/abuse.ch.classes.urlhouse.ts
Normal file
@ -0,0 +1,76 @@
|
||||
import * as plugins from './plugins.js';
|
||||
import * as paths from './paths.js';
|
||||
|
||||
export interface IUrlHouseData {
|
||||
ID: string;
|
||||
Dateadded: string;
|
||||
URL: string;
|
||||
URLStatus: string;
|
||||
Threat: string;
|
||||
AssociatedTags: string;
|
||||
UrlHausLink: string;
|
||||
Reporter: string;
|
||||
}
|
||||
|
||||
export class UrlHouse {
|
||||
private static readonly URLHOUSE_API_URL: string = 'https://urlhaus.abuse.ch/downloads/csv/';
|
||||
|
||||
public async getData(): Promise<IUrlHouseData[]> {
|
||||
plugins.smartfile.fs.ensureDirSync(paths.urlHouseTmp);
|
||||
const zipPath = plugins.path.join(paths.urlHouseTmp, 'urlhaus.zip');
|
||||
const csvPath = plugins.path.join(paths.urlHouseTmp, 'csv.txt');
|
||||
|
||||
const response = await fetch(UrlHouse.URLHOUSE_API_URL);
|
||||
if (!response.ok) {
|
||||
throw new Error(`HTTP error! status: ${response.status}`);
|
||||
}
|
||||
|
||||
await new Promise((resolve, reject) => {
|
||||
const fileStream = plugins.fs.createWriteStream(zipPath);
|
||||
// @ts-ignore
|
||||
const readable = plugins.stream.Readable.from(response.body);
|
||||
plugins.stream.pipeline(readable, fileStream, (err) => {
|
||||
if (err) reject(err);
|
||||
else resolve(null);
|
||||
});
|
||||
});
|
||||
|
||||
await new Promise((resolve, reject) => {
|
||||
plugins.stream.pipeline(
|
||||
plugins.fs.createReadStream(zipPath),
|
||||
plugins.unzipper.Extract({ path: paths.urlHouseTmp }),
|
||||
(err) => {
|
||||
if (err) reject(err);
|
||||
else resolve(null);
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
let data: IUrlHouseData[] = [];
|
||||
await new Promise((resolve, reject) => {
|
||||
plugins.stream.pipeline(
|
||||
plugins.fs.createReadStream(csvPath),
|
||||
plugins.csv({
|
||||
headers: ['ID', 'Dateadded', 'URL', 'URLStatus', 'Threat', 'AssociatedTags', 'UrlHausLink', 'Reporter'],
|
||||
mapValues: ({ header, value }) => value.trim()
|
||||
}),
|
||||
(err) => {
|
||||
if (err) reject(err);
|
||||
}
|
||||
)
|
||||
.on('data', (row) => {
|
||||
data.push(row);
|
||||
})
|
||||
.on('end', resolve)
|
||||
.on('error', reject);
|
||||
});
|
||||
data = data.map((item) => {
|
||||
return {
|
||||
...item,
|
||||
URL: item.URL?.replace('http', 'ht-NOCLICK-NOLINK-tp'),
|
||||
}
|
||||
});
|
||||
plugins.smartfile.fs.removeSync(paths.urlHouseTmp);
|
||||
return data;
|
||||
}
|
||||
}
|
@ -1,3 +1,2 @@
|
||||
import * as plugins from './abuse.ch.plugins.js';
|
||||
|
||||
export let demoExport = 'Hi there! :) This is an exported string';
|
||||
export * from './abuse.ch.classes.urlhouse.js';
|
||||
export * from './abuse.ch.classes.threatfox.js';
|
||||
|
7
ts/paths.ts
Normal file
7
ts/paths.ts
Normal file
@ -0,0 +1,7 @@
|
||||
import * as plugins from './plugins.js';
|
||||
|
||||
export const packageDir = plugins.path.join(plugins.smartpath.get.dirnameFromImportMetaUrl(import.meta.url), '../');
|
||||
export const nogitDir = plugins.path.join(packageDir, '.nogit');
|
||||
|
||||
export const urlHouseTmp = plugins.path.join(nogitDir, 'tmp.urlhaus');
|
||||
export const threatFoxTmp = plugins.path.join(nogitDir, 'tmp.threatfox');
|
25
ts/plugins.ts
Normal file
25
ts/plugins.ts
Normal file
@ -0,0 +1,25 @@
|
||||
// node native
|
||||
import * as stream from 'stream';
|
||||
import * as util from 'util';
|
||||
import unzipper from 'unzipper';
|
||||
import csv from 'csv-parser';
|
||||
import * as fs from 'fs';
|
||||
import * as path from 'path';
|
||||
|
||||
export {
|
||||
stream,
|
||||
util,
|
||||
unzipper,
|
||||
csv,
|
||||
fs,
|
||||
path,
|
||||
}
|
||||
|
||||
// @push.rocks scope
|
||||
import * as smartfile from '@push.rocks/smartfile';
|
||||
import * as smartpath from '@push.rocks/smartpath';
|
||||
|
||||
export {
|
||||
smartfile,
|
||||
smartpath,
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user