@riavzon/shield-base 1.3.2 → 1.4.0
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 +5 -5
- package/dist/{chunk-MZE5OD6T.js → chunk-BYQ3CUVE.js} +33 -33
- package/dist/chunk-BYQ3CUVE.js.map +1 -0
- package/dist/cli.js +1 -1
- package/dist/main.d.ts +207 -1
- package/dist/main.js +1 -1
- package/package.json +1 -1
- package/dist/chunk-MZE5OD6T.js.map +0 -1
package/README.md
CHANGED
|
@@ -100,10 +100,10 @@ npm install @riavzon/shield-base
|
|
|
100
100
|
npm link
|
|
101
101
|
|
|
102
102
|
# Or
|
|
103
|
-
npx shield-base <args>
|
|
103
|
+
npx @riavzon/shield-base <args>
|
|
104
104
|
|
|
105
105
|
# Or to start the wizard
|
|
106
|
-
npx shield-base
|
|
106
|
+
npx @riavzon/shield-base
|
|
107
107
|
```
|
|
108
108
|
|
|
109
109
|
|
|
@@ -119,7 +119,7 @@ Simply run the command without arguments to start the wizard:
|
|
|
119
119
|
shield-base
|
|
120
120
|
|
|
121
121
|
# Or
|
|
122
|
-
npx shield-base
|
|
122
|
+
npx @riavzon/shield-base
|
|
123
123
|
```
|
|
124
124
|
### Programmatic
|
|
125
125
|
|
|
@@ -150,7 +150,7 @@ const ids = [
|
|
|
150
150
|
"firehol_l4"
|
|
151
151
|
]
|
|
152
152
|
|
|
153
|
-
const selectedSources = true
|
|
153
|
+
const selectedSources = true; // or use ids array.
|
|
154
154
|
|
|
155
155
|
const results = await Promise.allSettled([
|
|
156
156
|
getBGPAndASN(contactInfo, outputDirectory, mmdbPath),
|
|
@@ -163,7 +163,7 @@ const results = await Promise.allSettled([
|
|
|
163
163
|
]);
|
|
164
164
|
const restartAllData = true;
|
|
165
165
|
|
|
166
|
-
const restart = restartData(outputDirectory, restartAllData)
|
|
166
|
+
const restart = await restartData(outputDirectory, restartAllData)
|
|
167
167
|
|
|
168
168
|
// A utility to run shell commands
|
|
169
169
|
await run('ls')
|
|
@@ -1,43 +1,43 @@
|
|
|
1
|
-
import {anyOf,exactly,charIn,digit,letter,createRegExp,oneOrMore,charNotIn}from'magic-regexp';import*as
|
|
2
|
-
Fetching ASN Dictionary from BGP.tools...`);let
|
|
3
|
-
`).slice(1),y=createRegExp(exactly("AS").and(oneOrMore(digit).groupedAs("asnNumber"))),t=charNotIn('"').times.any(),d=t.and(exactly('"')).times(2),
|
|
4
|
-
`),u=[];for(let b of O){if(!b)continue;let _=JSON.parse(b);if(_.Hits<10)continue;let
|
|
5
|
-
`),"utf-8"),k.info(`Compiling MMDB with mmdbctl to ${n}...`);let w=`${a} import --in ${c} --out ${n}`,
|
|
1
|
+
import {anyOf,exactly,charIn,digit,letter,createRegExp,oneOrMore,charNotIn}from'magic-regexp';import*as M from'fs';import M__default,{existsSync}from'fs';import Ht from'child_process';import qt from'util';import*as G from'path';import G__default from'path';import U,{consola}from'consola';import {fileURLToPath}from'url';import et from'ipaddr.js';import {IpRange,IpAddress}from'cidr-calc';import ve from'os';import {readFile}from'fs/promises';var Vt=qt.promisify(Ht.exec),R=async(o,s={})=>{try{let{stdout:a,stderr:e}=await Vt(o,{...s,maxBuffer:s.maxBuffer??10485760}),n={stdout:typeof a=="string"?a.trim():a,stderr:typeof e=="string"?e.trim():e};return s.silent||(console.log(`[run]: ${o}`),n.stdout&&console.log("stdout:",n.stdout),n.stderr&&console.error("stderr:",n.stderr)),n}catch(a){if(console.error(`Execution failed for command: "${o}"`),typeof a=="object"&&a!==null){let e=a;e.stderr&&console.error("Error Output:",e.stderr);}throw a}};var k=consola.withTag("[ASN/BGP]");async function rt(o,s,a){let e=["https://bgp.tools/asns.csv","https://bgp.tools/table.jsonl"],n=G__default.resolve(s,"asn.mmdb"),c=G__default.resolve(s,"temp_asn_data.json");try{k.info(`
|
|
2
|
+
Fetching ASN Dictionary from BGP.tools...`);let p=await(await fetch(e[0],{method:"GET",headers:{"User-Agent":o}})).text(),i=new Map,l=p.split(`
|
|
3
|
+
`).slice(1),y=createRegExp(exactly("AS").and(oneOrMore(digit).groupedAs("asnNumber"))),t=charNotIn('"').times.any(),d=t.and(exactly('"')).times(2),S=createRegExp(exactly(",").before(d.times.any().and(t).at.lineEnd()));for(let b of l){if(!b)continue;let _=b.split(S),T=_[0].match(y),h=T?.groups.asnNumber?parseInt(T.groups.asnNumber,10):null,$=createRegExp(exactly('"').at.lineStart().or(exactly('"').at.lineEnd()),["g"]),E=_[1]?.replace($,"").trim()||"Unknown",f=_[2]?.trim()||"Unknown";h!==null&&i.set(h,{name:E,type:f});}k.success(`SUCCESS: Loaded ${String(i.size)} ASN definitions.`),k.info("Fetching Routing Table...");let x=await(await fetch(e[1],{method:"GET",headers:{"User-Agent":o}})).text();k.info("Mapping CIDR to ASN data...");let O=x.split(`
|
|
4
|
+
`),u=[];for(let b of O){if(!b)continue;let _=JSON.parse(b);if(_.Hits<10)continue;let T=i.get(_.ASN)??{name:"Unknown",type:"Unknown"},h={range:_.CIDR,asn_id:String(_.ASN),asn_name:T.name,classification:T.type,hits:String(_.Hits)};u.push(JSON.stringify(h));}u.length>0&&k.log("SAMPLE:",u[0]),k.info(`Writing ${String(u.length)} enriched entries to temporary JSON...`),M.writeFileSync(c,u.join(`
|
|
5
|
+
`),"utf-8"),k.info(`Compiling MMDB with mmdbctl to ${n}...`);let w=`${a} import --in ${c} --out ${n}`,m=await R(w);m.stdout&&k.log(`mmdbctl: ${m.stdout.toString().trim()}`),k.success(`COMPLETED: Successfully compiled ASN MMDB to ${n}
|
|
6
6
|
`);}catch(r){k.error(`
|
|
7
|
-
ERROR during processing:`,r),process.exit(1);}finally{
|
|
8
|
-
Building global geographic index from hierarchical database...`);let a=G.resolve(o,"city.mmdb"),e=G.resolve(o,"temp_city_data.json"),n=
|
|
9
|
-
`),y=createRegExp(exactly("#").at.lineStart());B.success(`SUCCESS: Received ${String(l.length)} IP ranges. Mapping to geographic index...`);let t=[];for(let g of l){if(!g.trim()||y.test(g))continue;let
|
|
10
|
-
`),"utf-8"),B.start("Compiling MMDB with mmdbctl...");let d=`${s} import --in ${e} --out ${a}`,
|
|
11
|
-
`);}catch(
|
|
12
|
-
ERROR during processing:`,
|
|
13
|
-
Fetching node data from Onionoo API...`);let c=await fetch(a,{method:"GET",headers:{"Accept-Encoding":"gzip",Accept:"application/json"}});if(!c.ok){A.error(`ERROR: API fetch failed with status ${String(c.status)}`);return}let r=await c.json();A.success("SUCCESS: Data received, mapping relay nodes...");let i=(r.relays||[]).filter(t=>{let d=t.flags?.map(
|
|
14
|
-
`);
|
|
15
|
-
`);}catch(t){A.error("ERROR: MMDB compilation failed:",t);return}}catch(c){A.error("ERROR: Unexpected failure while fetching node list:",c);return}finally{
|
|
16
|
-
Building country index from local database...`);let a=G.resolve(o,"country.mmdb"),e=G.resolve(o,"temp_country_data.json"),n=
|
|
17
|
-
`);F.success(`SUCCESS: Received ${String(y.length)} global IP ranges. Enriching data...`);let t=[];for(let g of y){if(!g.trim())continue;let
|
|
18
|
-
`),"utf-8"),F.start("Compiling MMDB with mmdbctl...");let d=`${s} import --in ${e} --out ${a}`,
|
|
7
|
+
ERROR during processing:`,r),process.exit(1);}finally{M.existsSync(c)&&M.unlinkSync(c);}}var gt=G.dirname(fileURLToPath(import.meta.url)),re=[G.resolve(gt,"./countries+states+cities.json"),G.resolve(gt,"../../public/countries+states+cities.json")].find(o=>M.existsSync(o))??G.resolve(gt,"./countries+states+cities.json"),B=consola.withTag("[CITY/GEO]");async function st(o,s){B.info(`
|
|
8
|
+
Building global geographic index from hierarchical database...`);let a=G.resolve(o,"city.mmdb"),e=G.resolve(o,"temp_city_data.json"),n=M.readFileSync(re,"utf8"),c=JSON.parse(n),r=new Map;for(let p of c){let i=new Map;if(p.states)for(let l of p.states){let y=new Map;if(l.cities)for(let t of l.cities)y.set(t.name.toLowerCase(),t);i.set(l.state_code,{meta:l,cities:y});}r.set(p.iso2.toUpperCase(),{meta:p,states:i});}try{B.info("Fetching validated geofeed CSV...");let l=(await(await fetch("https://geolocatemuch.com/geofeeds/validated-all.csv")).text()).split(`
|
|
9
|
+
`),y=createRegExp(exactly("#").at.lineStart());B.success(`SUCCESS: Received ${String(l.length)} IP ranges. Mapping to geographic index...`);let t=[];for(let g of l){if(!g.trim()||y.test(g))continue;let x=g.split(","),O=x[0]?.trim()||"",u=x[1]?.trim()||"",w=x[2]?.trim()||"",m=x[3]?.trim()||"",b=x[4]?.trim()||"";if(!u&&!m&&!b)continue;let _=u.toUpperCase()||"",T="",h="",$="",E="",f={},W=r.get(_);if(W){if(f=W.meta,T=W.meta.emoji||"",w){let Y=w.includes("-")?w.split("-").pop():w,P=W.states.get(Y);if(P){if(E=P.meta.name||P.meta.state_code||"",m){let dt=P.cities.get(m.toLowerCase());dt&&(h=dt.latitude||"",$=dt.longitude||"");}!h&&P.meta.latitude&&P.meta.longitude&&(h=P.meta.latitude||"",$=P.meta.longitude||"");}}if(!h&&m)for(let[,Y]of W.states){let P=Y.cities.get(m.toLowerCase());if(P){h=P.latitude||"",$=P.longitude||"",E||(E=Y.meta.name||Y.meta.state_code||"");break}}!h&&f.latitude&&f.longitude&&(h=f.latitude||"",$=f.longitude||"");}let Wt={range:O,country_code:u,region:w||(f.region??""),subregion:f.subregion??"",city:m,zip_code:b,latitude:h,longitude:$,state:E,name:f.name??"Unknown",native:f.native??"",phone:f.phonecode??"",numericCode:f.numeric_code??"",continent:f.region??"",capital:f.capital??"",currency:f.currency??"",currency_name:f.currency_name??"",languages:f.translations?Object.values(f.translations)[0]??"":"",emoji:T,timezone:f.timezones?.[0]?.zoneName??"",utc_offset:f.timezones?.[0]?.gmtOffsetName??"",timeZoneName:f.timezones?.[0]?.tzName??"",tld:f.tld??"",nationality:f.nationality??""};t.push(JSON.stringify(Wt));}B.info(`Writing ${String(t.length)} enriched entries to temporary JSON...`),M.writeFileSync(e,t.join(`
|
|
10
|
+
`),"utf-8"),B.start("Compiling MMDB with mmdbctl...");let d=`${s} import --in ${e} --out ${a}`,S=await R(d);S.stdout&&B.log(`mmdbctl: ${S.stdout.toString().trim()}`),B.success(`COMPLETED: Successfully compiled City MMDB to ${a}
|
|
11
|
+
`);}catch(p){B.error(`
|
|
12
|
+
ERROR during processing:`,p),process.exit(1);}finally{M.existsSync(e)&&M.unlinkSync(e);}}var A=U.withTag("[TOR]");async function nt(o,s){let a="https://onionoo.torproject.org/details",e=G__default.resolve(o,"tor.mmdb"),n=G__default.resolve(o,"temp_tor_nodes.json");try{A.info(`
|
|
13
|
+
Fetching node data from Onionoo API...`);let c=await fetch(a,{method:"GET",headers:{"Accept-Encoding":"gzip",Accept:"application/json"}});if(!c.ok){A.error(`ERROR: API fetch failed with status ${String(c.status)}`);return}let r=await c.json();A.success("SUCCESS: Data received, mapping relay nodes...");let i=(r.relays||[]).filter(t=>{let d=t.flags?.map(S=>S.toLowerCase())??[];return d.includes("exit")||d.includes("valid")||d.includes("running")||d.includes("stable")||d.includes("hsdir")&&t.exit_addresses&&t.or_addresses});if(i.length===0){A.warn("WARNING: No relay nodes found matching criteria.");return}let l=[];for(let t of i){let d=[...t.exit_addresses??[],...t.or_addresses??[]];if(d)for(let S of d){let g=S;g.startsWith("[")?g=g.split("]:")[0].substring(1):g=g.split(":")[0];let x=et.parse(g),O;if(x.kind()==="ipv4"){let u=x;O=`${et.IPv4.networkAddressFromCIDR(`${u.toString()}/24`).toString()}/24`;}else if(x.kind()==="ipv6"){let u=x;O=`${et.IPv6.networkAddressFromCIDR(`${u.toString()}/64`).toString()}/64`;}else continue;l.push({range:O,or_addresses:t.or_addresses?.join(",")??"",exit_addresses:t.exit_addresses?.join(",")??"",last_seen:t.last_seen??"",last_changed_address_or_port:t.last_changed_address_or_port??"",first_seen:t.first_seen??"",running:t.running??!1,flags:t.flags?.join(",")??"",country:t.country??"",country_name:t.country_name??"",as:t.as??"",as_name:t.as_name??"",last_restarted:t.last_restarted??"",exit_policy:t.exit_policy?.join(",")??"",exit_policy_summary:JSON.stringify(t.exit_policy_summary)||"",exit_policy_v6_summary:t.exit_policy_v6_summary?JSON.stringify(t.exit_policy_v6_summary):void 0,contact:t.contact??"Unknown",version_status:t.version_status??"",guard_probability:t.guard_probability??0,middle_probability:t.middle_probability??0,exit_probability:t.exit_probability??0,recommended_version:t.recommended_version??!1,measured:t.measured??!1});}}A.info("SAMPLE:",l[0]);let y=l.map(t=>JSON.stringify(t)).join(`
|
|
14
|
+
`);M.writeFileSync(n,y,"utf-8");try{A.info("Compiling MMDB with mmdbctl...");let t=await R(`${s} import -j -i ${n} -o ${e}`);t.stdout&&A.info(`mmdbctl: ${t.stdout.toString().trim()}`),A.success(`COMPLETED: Successfully compiled Tor MMDB to ${e}
|
|
15
|
+
`);}catch(t){A.error("ERROR: MMDB compilation failed:",t);return}}catch(c){A.error("ERROR: Unexpected failure while fetching node list:",c);return}finally{M.existsSync(n)&&M.unlinkSync(n);}}var yt=G.dirname(fileURLToPath(import.meta.url)),ae=[G.resolve(yt,"./countries+states+cities.json"),G.resolve(yt,"../../public/countries+states+cities.json")].find(o=>M.existsSync(o))??G.resolve(yt,"./countries+states+cities.json"),F=U.withTag("[GEO/COUNTRY]");async function it(o,s){F.info(`
|
|
16
|
+
Building country index from local database...`);let a=G.resolve(o,"country.mmdb"),e=G.resolve(o,"temp_country_data.json"),n=M.readFileSync(ae,"utf8"),c=JSON.parse(n),r=new Map;for(let i of c)r.set(i.iso2.toUpperCase(),i);F.info("Fetching global IPv4 Country mapping from Sapics...");let p="https://raw.githubusercontent.com/sapics/ip-location-db/refs/heads/main/geo-asn-country/geo-asn-country-ipv4.csv";try{let i=await fetch(p);if(!i.ok)throw new Error(`ERROR: Failed to fetch country data: ${i.statusText}`);let y=(await i.text()).split(`
|
|
17
|
+
`);F.success(`SUCCESS: Received ${String(y.length)} global IP ranges. Enriching data...`);let t=[];for(let g of y){if(!g.trim())continue;let x=g.split(","),O=x[0]?.trim(),u=x[1]?.trim(),w=x[2]?.trim().toUpperCase();if(!O||!u||!w)continue;let m=r.get(w),b={range:`${O}-${u}`,country_code:w,region:m?.region??"",numericCode:m?.numeric_code??"",name:m?.name??"",native:m?.native??"",phone:m?.phonecode??"",capital:m?.capital??"",currency:m?.currency??"",currency_name:m?.currency_name??"",currency_symbol:m?.currency_symbol??"",languages:m?.translations?Object.values(m.translations)[0]??"":"",emoji:m?.emoji??"",timezone:m?.timezones?.[0]?.zoneName??"",utc_offset:m?.timezones?.[0]?.gmtOffsetName??"",timeZoneName:m?.timezones?.[0]?.tzName??"",tld:m?.tld??"",nationality:m?.nationality??"",subregion:m?.subregion??""};t.push(JSON.stringify(b));}F.info(`Writing ${String(t.length)} enriched entries to temporary JSON...`),M.writeFileSync(e,t.join(`
|
|
18
|
+
`),"utf-8"),F.start("Compiling MMDB with mmdbctl...");let d=`${s} import --in ${e} --out ${a}`,S=await R(d);S.stdout&&F.log(`mmdbctl: ${S.stdout.toString().trim()}`),F.success(`COMPLETED: Successfully compiled Country MMDB to ${a}
|
|
19
19
|
`);}catch(i){F.error(`
|
|
20
|
-
ERROR during processing:`,i),process.exit(1);}finally{
|
|
21
|
-
Fetching initial Proxy list from Awesome-lists...`);let a=G__default.resolve(o,"proxy.mmdb"),e=G__default.resolve(o,"temp_proxy_data.json"),n=new Set,c=[],r=["https://raw.githubusercontent.com/mthcht/awesome-lists/refs/heads/main/Lists/PROXY/ALL_PROXY_Lists.csv","https://raw.githubusercontent.com/firehol/blocklist-ipsets/refs/heads/master/firehol_proxies.netset"],
|
|
22
|
-
`).slice(1),t=charNotIn('"').times.any(),d=t.and(exactly('"')).times(2),
|
|
23
|
-
`),w=createRegExp(exactly("#").at.lineStart()),
|
|
24
|
-
`),"utf-8"),
|
|
25
|
-
`);}catch(i){
|
|
26
|
-
ERROR during processing:`,i),process.exit(1);}finally{
|
|
27
|
-
`);for(let u of O){let w=u.trim();if(!w||c.test(w))continue;let
|
|
20
|
+
ERROR during processing:`,i),process.exit(1);}finally{M.existsSync(e)&&M.unlinkSync(e);}}var j=U.withTag("[PROXY]");async function ct(o,s){j.log(`
|
|
21
|
+
Fetching initial Proxy list from Awesome-lists...`);let a=G__default.resolve(o,"proxy.mmdb"),e=G__default.resolve(o,"temp_proxy_data.json"),n=new Set,c=[],r=["https://raw.githubusercontent.com/mthcht/awesome-lists/refs/heads/main/Lists/PROXY/ALL_PROXY_Lists.csv","https://raw.githubusercontent.com/firehol/blocklist-ipsets/refs/heads/master/firehol_proxies.netset"],p=createRegExp(exactly(oneOrMore(digit),".",oneOrMore(digit),".",oneOrMore(digit),".",oneOrMore(digit)).and(exactly("/",oneOrMore(digit)).optionally()).at.lineStart().at.lineEnd());try{let i=await fetch(r[0]);if(!i.ok)throw new Error(`ERROR: Failed to fetch awesome list: ${i.statusText}`);let y=(await i.text()).split(`
|
|
22
|
+
`).slice(1),t=charNotIn('"').times.any(),d=t.and(exactly('"')).times(2),S=createRegExp(exactly(",").before(d.times.any().and(t).at.lineEnd())),g=createRegExp(anyOf(exactly("PROXY_ALL_"),exactly("_list.csv"),exactly('"')),["g","i"]);for(let T of y){if(!T.trim())continue;let[h,$,E]=T.split(S);if(!h||!p.test(h)||n.has(h))continue;n.add(h);let f=E.replace(g,"").trim(),W={range:`${h}/32`,port:$,comment:f};c.push(JSON.stringify(W));}j.success(`SUCCESS: Finished Awesome-list. Discovered ${String(c.length)} unique IPs.`),j.log("Fetching secondary data from FireHOL proxy list...");let x=await fetch(r[1]);if(!x.ok)throw new Error(`ERROR: Failed to fetch FireHOL list: ${x.statusText}`);let u=(await x.text()).split(`
|
|
23
|
+
`),w=createRegExp(exactly("#").at.lineStart()),m=0;for(let T of u){let h=T.trim();if(!h||w.test(h))continue;let $=h;if(!p.test($)||n.has($))continue;n.add($);let E={range:$,port:"unknown",comment:"Ip from Firehol"};c.push(JSON.stringify(E)),m++;}j.success(`SUCCESS: Finished FireHOL. Added ${String(m)} NEW unique proxies. Total unique: ${String(c.length)}`),c.length>0&&j.log("SAMPLE:",c[0]),j.log(`Writing ${String(c.length)} unique proxies to temporary JSON...`),M__default.writeFileSync(e,c.join(`
|
|
24
|
+
`),"utf-8"),j.log("Compiling MMDB with mmdbctl...");let b=`${s} import --in ${e} --out ${a}`,_=await R(b);_.stdout&&j.log(`mmdbctl: ${_.stdout.toString().trim()}`),j.success(`COMPLETED: Successfully compiled Proxy MMDB to ${a}
|
|
25
|
+
`);}catch(i){j.error(`
|
|
26
|
+
ERROR during processing:`,i),process.exit(1);}finally{M__default.existsSync(e)&&M__default.unlinkSync(e);}}var Tt={firehol_anonymous:"https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_anonymous.netset",firehol_l1:"https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level1.netset",firehol_l2:"https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level2.netset",firehol_l3:"https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level3.netset",firehol_l4:"https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level4.netset"},C=U.withTag("[THREATS]");async function lt(o,s,a){let e=" Maintainer: http://iplists.firehol.org/",n=createRegExp(exactly(oneOrMore(digit),".",oneOrMore(digit),".",oneOrMore(digit),".",oneOrMore(digit)).and(exactly("/",oneOrMore(digit)).optionally()).at.lineStart().at.lineEnd()),c=createRegExp(exactly("#").at.lineStart()),r=[];if(Array.isArray(a)?r=Object.entries(Tt).filter(([p])=>a.includes(p)).map(([p,i])=>({id:p,url:i})):a&&(r=Object.entries(Tt).map(([p,i])=>({id:p,url:i}))),r.length===0){C.info("No valid FireHOL data sources selected. Skipping.");return}try{C.start(`Initializing fetch for ${String(r.length)} FireHOL stream(s)...`);let p=r.map(async y=>{let t=await fetch(y.url);return {id:y.id,res:t}}),i=await Promise.allSettled(p);C.success(`SUCCESS: Fetched ${String(i.length)} data streams from FireHOL.`);let l=0;for(let y of i){if(y.status==="rejected"){C.error("Promise rejected:",y.reason);continue}let{id:t,res:d}=y.value,S=`${t} ${e}`,g=[];if(C.info(`Processing stream: ${t}...`),!d.ok){C.error(`Failed fetching ${t}: ${d.statusText}`);continue}let O=(await d.text()).split(`
|
|
27
|
+
`);for(let u of O){let w=u.trim();if(!w||c.test(w))continue;let m=w;if(!n.test(m))continue;let b={range:m,comment:S};l++,g.push(JSON.stringify(b));}if(C.info(`${t} summary:
|
|
28
28
|
|
|
29
29
|
\u2192 IPs Discovered: ${String(g.length)}
|
|
30
30
|
|
|
31
31
|
\u2192 Rolling Total: ${String(l)}
|
|
32
|
-
`),g.length>0){C.info(`SAMPLE: ${g[0]}`),C.info(`Writing entries to temporary JSON: temp_${t}.json`);let u=G__default.resolve(o,`temp_${t}.json`),w=G__default.resolve(o,`${t}.mmdb`);
|
|
33
|
-
`),"utf-8"),console.log(`Compiling MMDB with mmdbctl to ${w}...`);let
|
|
32
|
+
`),g.length>0){C.info(`SAMPLE: ${g[0]}`),C.info(`Writing entries to temporary JSON: temp_${t}.json`);let u=G__default.resolve(o,`temp_${t}.json`),w=G__default.resolve(o,`${t}.mmdb`);M__default.writeFileSync(u,g.join(`
|
|
33
|
+
`),"utf-8"),console.log(`Compiling MMDB with mmdbctl to ${w}...`);let m=`${s} import --in ${u} --out ${w}`,b=await R(m);b.stdout&&C.box(`mmdbctl: ${b.stdout.toString().trim()}`),M__default.existsSync(u)&&M__default.unlinkSync(u),C.success(`SUCCESS: Compiled ${t}.mmdb
|
|
34
34
|
`);}else C.warn(`WARNING: No valid IPs found for ${t}. Skipping.
|
|
35
35
|
`);}C.success(`COMPLETED: All threat intelligence sources processed successfully.
|
|
36
|
-
`);}catch(
|
|
37
|
-
FATAL ERROR during processing:`,
|
|
36
|
+
`);}catch(p){C.error(`
|
|
37
|
+
FATAL ERROR during processing:`,p),process.exit(1);}}var Pt=[{name:"google",type:"JSON",urls:["https://developers.google.com/static/search/apis/ipranges/googlebot.json","https://developers.google.com/static/search/apis/ipranges/special-crawlers.json","https://developers.google.com/static/search/apis/ipranges/user-triggered-fetchers.json","https://developers.google.com/static/search/apis/ipranges/user-triggered-fetchers-google.json","https://www.gstatic.com/ipranges/goog.json"]},{name:"bing",type:"JSON",urls:["https://www.bing.com/toolbox/bingbot.json"]},{name:"openai",type:"JSON",urls:["https://openai.com/gptbot.json","https://openai.com/chatgpt-user.json","https://openai.com/searchbot.json"]},{name:"apple",type:"JSON",urls:["https://search.developer.apple.com/applebot.json"]},{name:"ahrefs",type:"JSON",urls:["https://api.ahrefs.com/v3/public/crawler-ip-ranges"]},{name:"duckDuckGo",type:"HTML",urls:["https://duckduckgo.com/duckduckgo-help-pages/results/duckassistbot","https://duckduckgo.com/duckduckgo-help-pages/results/duckduckbot"]},{name:"commonCrawler",type:"HTML",urls:["https://commoncrawl.org/faq"]},{name:"xAndTwitter",type:"HTML",urls:["https://developer.x.com/en/docs/x-for-websites/cards/guides/troubleshooting-cards"]},{name:"facebook",type:"CSV",urls:["https://www.facebook.com/peering/geofeed"]},{name:"pinterest",type:"HTML",urls:["https://help.pinterest.com/en/business/article/pinterestbot"]},{name:"telegram",type:"HTML",urls:["https://core.telegram.org/bots/webhooks"]},{name:"semrush",type:"HTML",urls:["https://www.semrush.com/kb/1149-issues-with-crawling-a-domain"]}];var ot=o=>{if(!o)throw new Error("Empty IP string");if(o.includes("/")){let[s,a]=o.split("/");if(!et.isValidCIDR(o))throw new Error("Invalid CIDR");return `${et.parse(s).toString()}/${a}`}if(!et.isValid(o))throw new Error("Invalid Ip address");return et.parse(o).toString()},kt=(o,s,a)=>{let e=ot(o);if(s&&!a){let n=ot(s);return new IpRange(IpAddress.of(e),IpAddress.of(n)).toCidrs().map(r=>r.toString())}if(a){let n=`${e}/${a}`;if(!et.isValidCIDR(n))throw new Error("Invalid Extracted CIDR");return n}return e};var ue=U.withTag("GOOD-BOT-CRAWLER");async function At(o,s){ue.start(`Processing provider: ${o}...`);let a=s.map(async n=>{let c=await fetch(n);if(!c.ok)throw new Error(`fetch ${o} ${n} -> ${String(c.status)}`);let r=await c.json();return Array.isArray(r)?r:[r]});return (await Promise.all(a)).flat()}var bt=U.withTag("GOOD-BOT-CRAWLER"),jt=false;async function he(o){if(!jt)try{await R("command -v curl",{silent:!0}),jt=!0;}catch{throw bt.error("curl needed to be installed to run goodBots scrapper in order to avoid being blocked."),new Error("Fatal: curl is required for fallback scraping.")}try{let{stdout:s}=await R(`curl -sL ${o}`,{silent:!0});return typeof s=="string"?s:s.toString("utf-8")}catch(s){return bt.warn(`curl failed for ${o}: ${String(s)}`),""}}async function Dt(o){try{let s=await fetch(o,{headers:{"User-Agent":"Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",Accept:"text/html,text/csv,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8"}});if(!s.ok)throw new Error(`Failed to fetch ${o}: ${s.statusText} - ${String(s.status)}`);return await s.text()}catch(s){return bt.warn(`Fetch failed for ${o}:
|
|
38
38
|
${String(s)},
|
|
39
|
-
Using curl instead...`),await he(o)}}var
|
|
40
|
-
`);
|
|
39
|
+
Using curl instead...`),await he(o)}}var pt=anyOf(exactly("25",charIn("012345")),exactly("2",charIn("01234"),digit),exactly(charIn("01"),digit,digit),exactly(digit,digit),digit),It=anyOf(exactly(pt,".",pt,".",pt,".",pt)),D=anyOf(digit,charIn("abcdefABCDEF")).times.between(1,4),xe=anyOf(exactly(D,":").times(7).and(D),exactly(exactly(D,":").times.between(3,7),":"),exactly(D,":").times.between(1,5).and("::").and(exactly(D,":").times.any()).and(D),exactly("::").and(anyOf(D,It,exactly(D,":").times.any().and(D))),exactly(D,":").times.between(1,7).and(":")),Mt=anyOf(It,xe).notAfter(anyOf(letter,digit,":")),Nt=createRegExp(Mt.groupedAs("ip1"),anyOf(exactly("/",digit.times.between(1,3).groupedAs("mask")),exactly(anyOf(" to "," - ","-"," and "),Mt.groupedAs("ip2"))).optionally(),["g","i"]);var Lt=U.withTag("GOOD-BOT-CRAWLER");async function Bt(o,s){Lt.start(`Processing provider: ${s}...`);let e=(await Promise.all(o.map(Dt))).flatMap(n=>Array.from(n.matchAll(Nt)).flatMap(r=>{if(!r.groups?.ip1)return [];try{let p=kt(r.groups.ip1,r.groups.ip2,r.groups.mask);return Array.isArray(p)?p:[p]}catch(p){return Lt.warn(`Failed to normalize extracted IP match from ${s}:`,r[0],`Message: ${String(p)}`),[]}}));return [{creationTime:new Date().toISOString(),prefixes:Array.from(new Set(e)).map(n=>({ipv4Prefix:n}))}]}var H=U.withTag("GOOD-BOT-CRAWLER");async function Jt(o,s,a){H.start("Starting Good Bots IP scraper...");let e=G__default.resolve(o,"./goodBots.mmdb"),n=[...Pt,...a??[]];a&&a.length>0&&a.forEach(l=>{if(!l.name||!l.type||!l.urls)throw new Error(`Provider ${l.name||"unknown"} is missing required fields.`)});let c={};for(let l of n)l.type==="JSON"?c[l.name]=await At(l.name,l.urls):c[l.name]=await Bt(l.urls,l.name);U.info("Building data...");let r=Object.entries(c).flatMap(([l,y])=>y.flatMap(t=>{if(typeof t=="string")try{return [{range:ot(t),provider:l,syncToken:"unknown",creationTime:new Date().toISOString()}]}catch(d){return H.warn(`Invalid ip format skipping: ${t} -> ${String(d)}`),null}return t.prefixes.map(d=>{let S=d.ipv4Prefix??d.ipv6Prefix??"";if(!S)return null;try{return {range:ot(S),provider:l,syncToken:t.syncToken,creationTime:t.creationTime}}catch(g){return H.warn(`Invalid ip format skipping from prefix: ${S} -> ${String(g)}`),null}}).filter(Boolean)}));H.info(`Total records to import: ${String(r.length)}`);let p=G__default.resolve(o,"temp_bots.json"),i=r.map(l=>JSON.stringify(l)).join(`
|
|
40
|
+
`);M__default.writeFileSync(p,i,"utf-8");try{H.info("Compiling MMDB...");let l=`${s} import --in ${p} --out ${e}`;await R(l),H.success(`Successfully generated ${e}`);}catch(l){throw H.error(`Failed to compile MMDB: ${String(l)}`),l}finally{M__default.existsSync(p)&&M__default.unlinkSync(p);}}var ft=U.withTag("Shield Base");async function zt(o,s,a,e){ft.box(`
|
|
41
41
|
=========================================
|
|
42
42
|
=== Starting data generation pipeline ===
|
|
43
43
|
=========================================
|
|
@@ -49,5 +49,5 @@ Pipeline execution finished.
|
|
|
49
49
|
====================================
|
|
50
50
|
Fatal error in pipeline: ${String(n)}
|
|
51
51
|
====================================
|
|
52
|
-
`);}}var Ut=G__default.join(ve.homedir(),".shield-base",".cache.json");async function qo(o,s){existsSync(Ut)||(U.error("No cache found. Cannot restart. Please run a standard compilation first."),process.exit(1));let a=await readFile(Ut,"utf-8"),e=JSON.parse(a);if(!e.selectedDataTypes||e.selectedDataTypes.length===0){U.warn("Cache is empty. No data sources to restart.");return}if(s){U.info("Restarting ALL data sources..."),await zt(o,e.useragent,true,e.mmdbctlPath),U.success("\u2728 All data successfully refreshed!");return}U.info(`Restarting data compilation from cache: ${e.selectedDataTypes.join(", ")}`);let n=e.selectedDataTypes.filter(i=>i.startsWith("firehol_")||i==="anonymous"),c=e.selectedDataTypes.filter(i=>!i.startsWith("firehol_")&&i!=="anonymous"),r=[];c.includes("BGP")&&r.push({name:"BGP & ASN",task:()=>rt(e.useragent||"",o,e.mmdbctlPath)}),c.includes("City")&&r.push({name:"City",task:()=>st(e.outPutPath,e.mmdbctlPath)}),c.includes("Geography")&&r.push({name:"Geography",task:()=>it(e.outPutPath,e.mmdbctlPath)}),c.includes("Proxy")&&r.push({name:"Proxy",task:()=>ct(e.outPutPath,e.mmdbctlPath)}),c.includes("Tor")&&r.push({name:"Tor",task:()=>nt(e.outPutPath,e.mmdbctlPath)}),n.length>0&&r.push({name:"Threats",task:()=>lt(e.outPutPath,e.mmdbctlPath,n)}),U.start(`Running ${String(r.length)} restart jobs...`),(await Promise.allSettled(r.map(i=>i.task()))).forEach((i,l)=>{i.status==="rejected"&&U.error(`[${r[l].name}] Failed:`,i.reason);}),U.success("\u2728 Cached data successfully refreshed!");}export{R as a,rt as b,st as c,nt as d,it as e,ct as f,lt as g,ot as h,kt as i,
|
|
53
|
-
//# sourceMappingURL=chunk-
|
|
52
|
+
`);}}var Ut=G__default.join(ve.homedir(),".shield-base",".cache.json");async function qo(o,s){existsSync(Ut)||(U.error("No cache found. Cannot restart. Please run a standard compilation first."),process.exit(1));let a=await readFile(Ut,"utf-8"),e=JSON.parse(a);if(!e.selectedDataTypes||e.selectedDataTypes.length===0){U.warn("Cache is empty. No data sources to restart.");return}if(s){U.info("Restarting ALL data sources..."),await zt(o,e.useragent,true,e.mmdbctlPath),U.success("\u2728 All data successfully refreshed!");return}U.info(`Restarting data compilation from cache: ${e.selectedDataTypes.join(", ")}`);let n=e.selectedDataTypes.filter(i=>i.startsWith("firehol_")||i==="anonymous"),c=e.selectedDataTypes.filter(i=>!i.startsWith("firehol_")&&i!=="anonymous"),r=[];c.includes("BGP")&&r.push({name:"BGP & ASN",task:()=>rt(e.useragent||"",o,e.mmdbctlPath)}),c.includes("City")&&r.push({name:"City",task:()=>st(e.outPutPath,e.mmdbctlPath)}),c.includes("Geography")&&r.push({name:"Geography",task:()=>it(e.outPutPath,e.mmdbctlPath)}),c.includes("Proxy")&&r.push({name:"Proxy",task:()=>ct(e.outPutPath,e.mmdbctlPath)}),c.includes("Tor")&&r.push({name:"Tor",task:()=>nt(e.outPutPath,e.mmdbctlPath)}),n.length>0&&r.push({name:"Threats",task:()=>lt(e.outPutPath,e.mmdbctlPath,n)}),U.start(`Running ${String(r.length)} restart jobs...`),(await Promise.allSettled(r.map(i=>i.task()))).forEach((i,l)=>{i.status==="rejected"&&U.error(`[${r[l].name}] Failed:`,i.reason);}),U.success("\u2728 Cached data successfully refreshed!");}export{R as a,rt as b,st as c,nt as d,it as e,ct as f,lt as g,ot as h,kt as i,Mt as j,Nt as k,Jt as l,zt as m,qo as n};//# sourceMappingURL=chunk-BYQ3CUVE.js.map
|
|
53
|
+
//# sourceMappingURL=chunk-BYQ3CUVE.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/utils/run.ts","../src/scripts/bgp.ts","../src/scripts/city.ts","../src/scripts/tor.ts","../src/scripts/geo.ts","../src/scripts/proxy.ts","../src/scripts/threats.ts","../src/scripts/goodBotsScrapper/urls.ts","../src/scripts/goodBotsScrapper/ipNormalizers.ts","../src/scripts/goodBotsScrapper/scrappers/jsonScrapper.ts","../src/scripts/goodBotsScrapper/scrappers/fetchers.ts","../src/scripts/goodBotsScrapper/regex.ts","../src/scripts/goodBotsScrapper/scrappers/htmlScrapper.ts","../src/scripts/goodBotsScrapper/scrapper.ts","../src/scripts/executeAll.ts","../src/utils/restart.ts"],"names":["execAsync","util","child","run","command","options","stdout","stderr","result","error","logger","consola","getBGPAndASN","userAgent","outputPath","mmdbPath","urls","output","path","tempASNJson","rawAsnCsv","asnDictionary","asnLines","regex","createRegExp","exactly","oneOrMore","digit","nonQuotes","charNotIn","quotePair","splitRegex","line","parts","match","asnNumber","quoteStripRegex","asnName","asnClass","rawTable","routes","results","route","parsed","dictionaryLookup","record","q","cmd","convert","currentDir","fileURLToPath","dbPath","p","buildCitiesData","tempGeoJson","rawData","dbJson","countryIndex","country","stateMap","state","cityMap","city","lines","commentRegex","prefix","region","zip","cc","emoji","lat","lon","stateName","countryMeta","countryData","regionCode","stateData","cityData","geoRecord","getTorLists","url","tempFileName","response","data","toMap","flags","fl","f","node","ipsToProcess","ip","cleanIp","parsedIp","ipaddr","finalNetworkAddress","ipv4","ipv6","ndjsonOutput","V","J","I","getGeoDatas","res","start","end","getListOfProxies","tempProxyJson","seenIps","ipv4Regex","resAwesome","splitAwesomeListRegex","stripAwesomeListRegex","anyOf","dest_ip","dest_port","metadata_comment","cleanComment","resFirehol","fireholLines","fireholCount","trimmed","fs","THREAT_CONFIG","getThreatLists","selectedSources","maintainerUrl","tasks","id","promises","task","resultsSettled","ipsCount","finalMsg","jsonName","normalizeIp","baseIp","mask","normalizeExtractedMatch","ip1","ip2","cleanIp1","cleanIp2","IpRange","IpAddress","c","cidr","jsonScrapper","name","isCurlVerified","fetchWithCurl","err","downloadHtml","octet","charIn","ipv4Base","hexWord","ipv6Base","ipBase","letter","botIpExtractor","htmlScrapper","allMatches","txt","m","normalized","getCrawlersIps","customUrls","databasePath","providers","prov","ipDb","provider","mmdbRecords","snapshots","snap","rawIp","tempJsonPath","jsonLines","r","generateData","index","cacheOutput","os","restartData","all","existsSync","cachedFile","readFile","cache","fireholSources","s","standardSources","executionRestartQueue"],"mappings":"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","file":"chunk-BYQ3CUVE.js","sourcesContent":["import child from 'node:child_process';\nimport util from 'node:util';\nimport type { ExecOptions } from 'node:child_process';\n\nexport interface RunResult {\n stdout: string | Buffer;\n stderr: string | Buffer;\n}\n\nconst execAsync = util.promisify(child.exec);\n\nexport interface RunOptions extends ExecOptions {\n silent?: boolean;\n}\n\nexport const run = async (command: string, options: RunOptions = {}): Promise<RunResult> => {\n try {\n const { stdout, stderr } = await execAsync(command, {\n ...options,\n maxBuffer: options.maxBuffer ?? 1024 * 1024 * 10, \n });\n\n const result: RunResult = {\n stdout: typeof stdout === 'string' ? stdout.trim() : stdout,\n stderr: typeof stderr === 'string' ? stderr.trim() : stderr,\n };\n\n if (!options.silent) {\n console.log(`[run]: ${command}`);\n if (result.stdout) console.log('stdout:', result.stdout);\n if (result.stderr) console.error('stderr:', result.stderr);\n }\n\n return result;\n } catch (error: unknown) {\n\n console.error(`Execution failed for command: \"${command}\"`);\n \n if (typeof error === 'object' && error !== null) {\n const e = error as { stderr?: string; stdout?: string };\n if (e.stderr) console.error('Error Output:', e.stderr);\n }\n \n throw error;\n }\n};","import { createRegExp, exactly, digit, oneOrMore, charNotIn } from \"magic-regexp\";\nimport * as fs from 'fs';\nimport { run } from \"../utils/run.js\";\nimport path from \"path\";\nimport { AsnDictionaryEntry, BGPRouteRaw, BgpRecord } from \"../types/bgp.js\";\nimport { consola } from \"consola\";\n\nconst logger = consola.withTag('[ASN/BGP]');\nexport async function getBGPAndASN(userAgent: string, outputPath: string, mmdbPath: string) {\n const urls = ['https://bgp.tools/asns.csv', 'https://bgp.tools/table.jsonl'];\n const output = path.resolve(outputPath, 'asn.mmdb');\n const tempASNJson = path.resolve(outputPath, 'temp_asn_data.json');\n try {\n logger.info(\"\\nFetching ASN Dictionary from BGP.tools...\");\n const ansRes = await fetch(urls[0], {\n method: 'GET',\n headers: {\n 'User-Agent': userAgent\n }\n });\n\n // AS1,\"Level 3 Parent, LLC\",Unknown\n // AS10,CSNET Coordination and Information Center,Unknown\n\n const rawAsnCsv = await ansRes.text();\n const asnDictionary = new Map<number, AsnDictionaryEntry>();\n const asnLines = rawAsnCsv.split('\\n').slice(1);\n \n const regex = createRegExp(exactly('AS').and(oneOrMore(digit).groupedAs('asnNumber')));\n \n const nonQuotes = charNotIn('\"').times.any();\n const quotePair = nonQuotes.and(exactly('\"')).times(2);\n const splitRegex = createRegExp(\n exactly(',').before(quotePair.times.any().and(nonQuotes).at.lineEnd())\n );\n\n for (const line of asnLines) {\n if (!line) continue;\n const parts = line.split(splitRegex);\n\n const match = parts[0].match(regex);\n const asnNumber = match?.groups.asnNumber ? parseInt(match.groups.asnNumber, 10) : null;\n \n const quoteStripRegex = createRegExp(exactly('\"').at.lineStart().or(exactly('\"').at.lineEnd()), ['g']);\n const asnName = parts[1]?.replace(quoteStripRegex, '').trim() || 'Unknown';\n const asnClass = parts[2]?.trim() || 'Unknown';\n \n if (asnNumber !== null) {\n asnDictionary.set(asnNumber, { name: asnName, type: asnClass });\n }\n }\n logger.success(`SUCCESS: Loaded ${String(asnDictionary.size)} ASN definitions.`);\n logger.info(\"Fetching Routing Table...\");\n const tableRes = await fetch(urls[1], {\n method: 'GET',\n headers: {\n 'User-Agent': userAgent\n }\n });\n\n const rawTable = await tableRes.text();\n logger.info(\"Mapping CIDR to ASN data...\");\n const routes = rawTable.split('\\n');\n const results = [];\n\n for (const route of routes) {\n if (!route) continue;\n // {\"CIDR\":\"1.1.1.0/24\",\"ASN\":13335,\"Hits\":509}\n const parsed = JSON.parse(route) as BGPRouteRaw;\n if (parsed.Hits < 10) continue; \n \n const dictionaryLookup = asnDictionary.get(parsed.ASN) ?? { name: 'Unknown', type: 'Unknown' };\n\n const record: BgpRecord = {\n range: parsed.CIDR,\n asn_id: String(parsed.ASN),\n asn_name: dictionaryLookup.name,\n classification: dictionaryLookup.type,\n hits: String(parsed.Hits)\n };\n results.push(JSON.stringify(record));\n }\n\n if (results.length > 0) {\n logger.log('SAMPLE:', results[0]);\n }\n\n logger.info(`Writing ${String(results.length)} enriched entries to temporary JSON...`);\n fs.writeFileSync(tempASNJson, results.join('\\n'), 'utf-8');\n logger.info(`Compiling MMDB with mmdbctl to ${output}...`);\n \n const cmd = `${mmdbPath} import --in ${tempASNJson} --out ${output}`;\n const convert = await run(cmd);\n\n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled ASN MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error(`\\nERROR during processing:`, error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempASNJson)) {\n fs.unlinkSync(tempASNJson);\n }\n }\n}\n","import { run } from \"../utils/run.js\";\nimport * as fs from 'fs';\nimport type { GlobalCountry, GlobalState, GlobalCity, CityGeoRecord } from \"../types/geography.js\";\nimport * as path from \"path\";\nimport { fileURLToPath } from \"url\";\nimport { createRegExp, exactly } from \"magic-regexp\";\nimport { consola } from \"consola\";\n\nconst currentDir = path.dirname(fileURLToPath(import.meta.url));\nconst dbPath = [\n path.resolve(currentDir, './countries+states+cities.json'),\n path.resolve(currentDir, '../../public/countries+states+cities.json')\n].find(p => fs.existsSync(p)) ?? path.resolve(currentDir, './countries+states+cities.json');\n\nconst logger = consola.withTag('[CITY/GEO]');\n\nexport async function buildCitiesData(outputPath: string, mmdbPath: string) {\n logger.info('\\nBuilding global geographic index from hierarchical database...');\n const output = path.resolve(outputPath, 'city.mmdb');\n const tempGeoJson = path.resolve(outputPath, 'temp_city_data.json');\n \n\n const rawData = fs.readFileSync(dbPath, 'utf8');\n const dbJson = JSON.parse(rawData) as GlobalCountry[];\n\n const countryIndex = new Map<string, { meta: GlobalCountry, states: Map<string, { meta: GlobalState, cities: Map<string, GlobalCity> }> }>();\n \n for (const country of dbJson) {\n const stateMap = new Map<string, { meta: GlobalState, cities: Map<string, GlobalCity> }>();\n \n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (country.states) {\n for (const state of country.states) {\n const cityMap = new Map<string, GlobalCity>();\n \n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (state.cities) {\n for (const city of state.cities) {\n cityMap.set(city.name.toLowerCase(), city);\n }\n }\n \n stateMap.set(state.state_code, { meta: state, cities: cityMap });\n }\n }\n \n countryIndex.set(country.iso2.toUpperCase(), { meta: country, states: stateMap });\n }\n\n try {\n logger.info('Fetching validated geofeed CSV...');\n\n const res = await fetch('https://geolocatemuch.com/geofeeds/validated-all.csv');\n const csvText = await res.text();\n const lines = csvText.split('\\n');\n const commentRegex = createRegExp(exactly('#').at.lineStart());\n \n logger.success(`SUCCESS: Received ${String(lines.length)} IP ranges. Mapping to geographic index...`);\n const results: string[] = [];\n\n for (const line of lines) {\n if (!line.trim() || commentRegex.test(line)) continue;\n\n const parts = line.split(',');\n const prefix = parts[0]?.trim() || \"\";\n const country = parts[1]?.trim() || \"\";\n const region = parts[2]?.trim() || \"\";\n const city = parts[3]?.trim() || \"\";\n const zip = parts[4]?.trim() || \"\";\n\n if (!country && !city && !zip) continue;\n\n const cc = country.toUpperCase() || \"\";\n\n let emoji = \"\";\n let lat = '';\n let lon = '';\n let stateName = '';\n let countryMeta: Partial<GlobalCountry> = {};\n \n const countryData = countryIndex.get(cc);\n if (countryData) {\n countryMeta = countryData.meta;\n emoji = countryData.meta.emoji || \"\";\n \n \n if (region) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n const regionCode = region.includes('-') ? region.split('-').pop()! : region;\n const stateData = countryData.states.get(regionCode);\n \n if (stateData) {\n stateName = stateData.meta.name || stateData.meta.state_code || \"\";\n \n if (city) {\n const cityData = stateData.cities.get(city.toLowerCase());\n if (cityData) {\n lat = cityData.latitude || \"\";\n lon = cityData.longitude || \"\";\n }\n }\n\n if (!lat && stateData.meta.latitude && stateData.meta.longitude) {\n lat = stateData.meta.latitude || \"\";\n lon = stateData.meta.longitude || \"\";\n }\n }\n }\n \n\n if (!lat && city) {\n for (const [, stateData] of countryData.states) {\n const cityData = stateData.cities.get(city.toLowerCase());\n if (cityData) {\n lat = cityData.latitude || \"\";\n lon = cityData.longitude || \"\";\n if (!stateName) stateName = stateData.meta.name || stateData.meta.state_code || \"\";\n break;\n }\n }\n }\n\n if (!lat && countryMeta.latitude && countryMeta.longitude) {\n lat = countryMeta.latitude || \"\";\n lon = countryMeta.longitude || \"\";\n }\n }\n\n const geoRecord: CityGeoRecord = {\n range: prefix,\n country_code: country,\n region: region || (countryMeta.region ?? \"\"),\n subregion: countryMeta.subregion ?? \"\",\n city: city,\n zip_code: zip,\n latitude: lat,\n longitude: lon,\n state: stateName,\n name: countryMeta.name ?? \"Unknown\",\n native: countryMeta.native ?? \"\",\n phone: countryMeta.phonecode ?? '',\n numericCode: countryMeta.numeric_code ?? \"\",\n continent: countryMeta.region ?? \"\",\n capital: countryMeta.capital ?? \"\",\n currency: countryMeta.currency ?? '',\n currency_name: countryMeta.currency_name ?? \"\",\n languages: countryMeta.translations ? Object.values(countryMeta.translations)[0] ?? \"\" : \"\",\n emoji: emoji,\n timezone: countryMeta.timezones?.[0]?.zoneName ?? \"\",\n utc_offset: countryMeta.timezones?.[0]?.gmtOffsetName ?? \"\",\n timeZoneName: countryMeta.timezones?.[0]?.tzName ?? \"\",\n tld: countryMeta.tld ?? \"\",\n nationality: countryMeta.nationality ?? \"\",\n };\n \n results.push(JSON.stringify(geoRecord));\n }\n \n logger.info(`Writing ${String(results.length)} enriched entries to temporary JSON...`);\n fs.writeFileSync(tempGeoJson, results.join('\\n'), 'utf-8');\n\n logger.start('Compiling MMDB with mmdbctl...');\n \n const cmd = `${mmdbPath} import --in ${tempGeoJson} --out ${output}`;\n const convert = await run(cmd);\n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled City MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error('\\nERROR during processing:', error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempGeoJson)) {\n fs.unlinkSync(tempGeoJson);\n }\n }\n}\n","/* eslint-disable @typescript-eslint/ban-ts-comment */\nimport { run } from \"../utils/run.js\";\nimport * as fs from 'fs';\nimport ipaddr from 'ipaddr.js';\nimport path from \"path\";\nimport type { OnionooPayload, TorRecord } from \"../types/tor.js\";\nimport consola from \"consola\";\n\n\nconst logger = consola.withTag('[TOR]');\n\nexport async function getTorLists(outputPath: string, mmdbPath: string): Promise<void> {\n const url = 'https://onionoo.torproject.org/details';\n const output = path.resolve(outputPath, 'tor.mmdb');\n const tempFileName = path.resolve(outputPath, 'temp_tor_nodes.json');\n\ntry {\n\n logger.info(\"\\nFetching node data from Onionoo API...\");\n const response = await fetch(url, {\n method: 'GET',\n headers: {\n 'Accept-Encoding': 'gzip',\n 'Accept': 'application/json'\n }\n\n });\n\n\n\n if (!response.ok) {\n logger.error(`ERROR: API fetch failed with status ${String(response.status)}`);\n return;\n }\n\n const data = await response.json() as OnionooPayload;\n logger.success('SUCCESS: Data received, mapping relay nodes...');\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n const rawNodes = data.relays || [];\n const toMap = rawNodes.filter((flags) => {\n\n const fl = flags.flags?.map(f => f.toLowerCase()) ?? [];\n return fl.includes(\"exit\") ||\n fl.includes(\"valid\") ||\n fl.includes(\"running\") ||\n fl.includes(\"stable\") ||\n fl.includes(\"hsdir\") &&\n flags.exit_addresses &&\n flags.or_addresses;\n });\n\n\n\n if (toMap.length === 0) {\n logger.warn(\"WARNING: No relay nodes found matching criteria.\");\n return;\n }\n\n const results: TorRecord[] = [];\n\n for (const node of toMap) {\n const ipsToProcess = [\n // eslint-disable-next-line @typescript-eslint/no-misused-spread\n ...(node.exit_addresses ?? []),\n ...(node.or_addresses ?? [])\n ];\n\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (!ipsToProcess) continue;\n\n for (const ip of ipsToProcess) {\n\n let cleanIp = ip;\n if (cleanIp.startsWith('[')) {\n cleanIp = cleanIp.split(']:')[0].substring(1);\n } else {\n cleanIp = cleanIp.split(':')[0];\n }\n\n const parsedIp = ipaddr.parse(cleanIp);\n let finalNetworkAddress: string;\n\n if (parsedIp.kind() === 'ipv4') {\n const ipv4 = parsedIp as ipaddr.IPv4;\n const networkAddress = ipaddr.IPv4.networkAddressFromCIDR(`${ipv4.toString()}/24`);\n finalNetworkAddress = `${networkAddress.toString()}/24`;\n } else if (parsedIp.kind() === 'ipv6') {\n const ipv6 = parsedIp as ipaddr.IPv6;\n const networkAddress = ipaddr.IPv6.networkAddressFromCIDR(`${ipv6.toString()}/64`);\n finalNetworkAddress = `${networkAddress.toString()}/64`;\n } else {\n continue;\n }\n\n results.push({\n range: finalNetworkAddress,\n or_addresses: node.or_addresses?.join(',') ?? '',\n // @ts-ignore\n // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment, @typescript-eslint/no-unsafe-call\n exit_addresses: node.exit_addresses?.join(',') ?? '',\n last_seen: node.last_seen ?? \"\",\n last_changed_address_or_port: node.last_changed_address_or_port ?? \"\",\n first_seen: node.first_seen ?? \"\",\n running: node.running ?? false,\n flags: node.flags?.join(',') ?? \"\",\n country: node.country ?? \"\",\n country_name: node.country_name ?? \"\",\n as: node.as ?? \"\",\n as_name: node.as_name ?? \"\",\n last_restarted: node.last_restarted ?? \"\",\n exit_policy: node.exit_policy?.join(',') ?? '',\n exit_policy_summary: JSON.stringify(node.exit_policy_summary) || '',\n exit_policy_v6_summary: node.exit_policy_v6_summary ? JSON.stringify(node.exit_policy_v6_summary) : undefined,\n contact: node.contact ?? \"Unknown\",\n version_status: node.version_status ?? \"\",\n guard_probability: node.guard_probability ?? 0,\n middle_probability: node.middle_probability ?? 0,\n exit_probability: node.exit_probability ?? 0,\n recommended_version: node.recommended_version ?? false,\n measured: node.measured ?? false,\n });\n }\n\n }\n\n logger.info('SAMPLE:', results[0]);\n const ndjsonOutput = results.map(record => JSON.stringify(record)).join('\\n');\n fs.writeFileSync(tempFileName, ndjsonOutput, 'utf-8');\n try {\n logger.info('Compiling MMDB with mmdbctl...');\n const convert = await run(`${mmdbPath} import -j -i ${tempFileName} -o ${output}`);\n if (convert.stdout) logger.info(`mmdbctl: ${convert.stdout.toString().trim()}`);\n\n logger.success(`COMPLETED: Successfully compiled Tor MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error(\"ERROR: MMDB compilation failed:\", error);\n return;\n }\n\n } catch (error: unknown) {\n logger.error(\"ERROR: Unexpected failure while fetching node list:\", error);\n return;\n } finally {\n if (fs.existsSync(tempFileName)) {\n fs.unlinkSync(tempFileName);\n }\n \n }\n\n} ","import { run } from \"../utils/run.js\";\nimport * as fs from 'fs';\nimport * as path from \"path\";\nimport { fileURLToPath } from \"url\";\nimport type { GlobalCountry, GeoRecord } from \"../types/geography.js\";\nimport consola from \"consola\";\n\nconst currentDir = path.dirname(fileURLToPath(import.meta.url));\nconst dbPath = [\n path.resolve(currentDir, './countries+states+cities.json'),\n path.resolve(currentDir, '../../public/countries+states+cities.json')\n].find(p => fs.existsSync(p)) ?? path.resolve(currentDir, './countries+states+cities.json');\n\nconst logger = consola.withTag('[GEO/COUNTRY]');\n\nexport async function getGeoDatas(outputPath: string, mmdbPath: string) {\n logger.info(\"\\nBuilding country index from local database...\");\n\n const output = path.resolve(outputPath, 'country.mmdb');\n const tempGeoJson = path.resolve(outputPath, 'temp_country_data.json');\n const rawData = fs.readFileSync(dbPath, 'utf8');\n const dbJson = JSON.parse(rawData) as GlobalCountry[];\n\n const countryIndex = new Map<string, GlobalCountry>();\n for (const country of dbJson) {\n countryIndex.set(country.iso2.toUpperCase(), country);\n }\n\n logger.info('Fetching global IPv4 Country mapping from Sapics...');\n const url = 'https://raw.githubusercontent.com/sapics/ip-location-db/refs/heads/main/geo-asn-country/geo-asn-country-ipv4.csv';\n\n try {\n const res = await fetch(url);\n if (!res.ok) {\n throw new Error(`ERROR: Failed to fetch country data: ${res.statusText}`);\n }\n\n const csvText = await res.text();\n const lines = csvText.split('\\n');\n \n logger.success(`SUCCESS: Received ${String(lines.length)} global IP ranges. Enriching data...`);\n const results: string[] = [];\n\n for (const line of lines) {\n if (!line.trim()) continue;\n \n const parts = line.split(',');\n const start = parts[0]?.trim();\n const end = parts[1]?.trim();\n const cc = parts[2]?.trim().toUpperCase();\n \n if (!start || !end || !cc) continue;\n\n const countryMeta = countryIndex.get(cc);\n\n const record: GeoRecord = {\n range: `${start}-${end}`,\n country_code: cc,\n region: countryMeta?.region ?? '',\n numericCode: countryMeta?.numeric_code ?? \"\",\n name: countryMeta?.name ?? \"\",\n native: countryMeta?.native ?? \"\",\n phone: countryMeta?.phonecode ?? \"\",\n capital: countryMeta?.capital ?? \"\",\n currency: countryMeta?.currency ?? \"\",\n currency_name: countryMeta?.currency_name ?? \"\",\n currency_symbol: countryMeta?.currency_symbol ?? \"\",\n languages: countryMeta?.translations ? Object.values(countryMeta.translations)[0] ?? \"\" : \"\",\n emoji: countryMeta?.emoji ?? \"\",\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n timezone: countryMeta?.timezones?.[0]?.zoneName ?? \"\",\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n utc_offset: countryMeta?.timezones?.[0]?.gmtOffsetName ?? \"\",\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n timeZoneName: countryMeta?.timezones?.[0]?.tzName ?? \"\",\n tld: countryMeta?.tld ?? \"\",\n nationality: countryMeta?.nationality ?? \"\",\n subregion: countryMeta?.subregion ?? \"\"\n };\n\n results.push(JSON.stringify(record));\n }\n\n logger.info(`Writing ${String(results.length)} enriched entries to temporary JSON...`);\n fs.writeFileSync(tempGeoJson, results.join('\\n'), 'utf-8');\n\n logger.start('Compiling MMDB with mmdbctl...');\n\n const cmd = `${mmdbPath} import --in ${tempGeoJson} --out ${output}`;\n const convert = await run(cmd);\n \n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled Country MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error('\\nERROR during processing:', error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempGeoJson)) {\n fs.unlinkSync(tempGeoJson);\n }\n }\n}\n","import fs from 'node:fs';\nimport { run } from \"../utils/run.js\";\nimport { createRegExp, exactly, charNotIn, anyOf, digit, oneOrMore } from 'magic-regexp';\nimport path from 'node:path';\nimport consola from 'consola';\nimport type { ProxyRecord } from '../types/proxy.js';\n\nconst logger = consola.withTag('[PROXY]');\n\nexport async function getListOfProxies(outputPath: string, mmdbPath: string) {\n logger.log(\"\\nFetching initial Proxy list from Awesome-lists...\");\n const output = path.resolve(outputPath, 'proxy.mmdb');\n const tempProxyJson = path.resolve(outputPath, 'temp_proxy_data.json');\n\n const seenIps = new Set<string>();\n const results: string[] = [];\n const urls = ['https://raw.githubusercontent.com/mthcht/awesome-lists/refs/heads/main/Lists/PROXY/ALL_PROXY_Lists.csv', 'https://raw.githubusercontent.com/firehol/blocklist-ipsets/refs/heads/master/firehol_proxies.netset'];\n \n const ipv4Regex = createRegExp(\n exactly(oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit))\n .and(exactly('/', oneOrMore(digit)).optionally()) \n .at.lineStart().at.lineEnd()\n );\n\n try {\n const resAwesome = await fetch(urls[0]);\n if (!resAwesome.ok) throw new Error(`ERROR: Failed to fetch awesome list: ${resAwesome.statusText}`);\n\n const csvText = await resAwesome.text();\n const lines = csvText.split('\\n').slice(1);\n\n const nonQuotes = charNotIn('\"').times.any();\n const quotePair = nonQuotes.and(exactly('\"')).times(2);\n const splitAwesomeListRegex = createRegExp(\n exactly(',').before(quotePair.times.any().and(nonQuotes).at.lineEnd())\n );\n\n const stripAwesomeListRegex = createRegExp(\n anyOf(exactly('PROXY_ALL_'), exactly('_list.csv'), exactly('\"')), \n ['g', 'i']\n );\n\n\n\n for (const line of lines) {\n if (!line.trim()) continue;\n \n const [dest_ip, dest_port, metadata_comment] = line.split(splitAwesomeListRegex);\n\n if (!dest_ip || !ipv4Regex.test(dest_ip)) continue;\n \n if (seenIps.has(dest_ip)) continue;\n seenIps.add(dest_ip);\n\n const cleanComment = metadata_comment.replace(stripAwesomeListRegex, '').trim();\n\n const record: ProxyRecord = {\n range: `${dest_ip}/32`, \n port: dest_port,\n comment: cleanComment\n };\n \n results.push(JSON.stringify(record));\n }\n \n logger.success(`SUCCESS: Finished Awesome-list. Discovered ${String(results.length)} unique IPs.`);\n logger.log('Fetching secondary data from FireHOL proxy list...');\n const resFirehol = await fetch(urls[1]);\n\n if (!resFirehol.ok) throw new Error(`ERROR: Failed to fetch FireHOL list: ${resFirehol.statusText}`);\n const textFirehol = await resFirehol.text();\n const fireholLines = textFirehol.split('\\n');\n const commentRegex = createRegExp(exactly('#').at.lineStart());\n let fireholCount = 0;\n\n\n for (const line of fireholLines) {\n const trimmed = line.trim();\n if (!trimmed || commentRegex.test(trimmed)) continue;\n\n const ip = trimmed;\n \n if (!ipv4Regex.test(ip)) continue;\n \n if (seenIps.has(ip)) continue;\n seenIps.add(ip);\n\n const record: ProxyRecord = {\n range: ip,\n port: 'unknown',\n comment: `Ip from Firehol`\n };\n\n results.push(JSON.stringify(record));\n fireholCount++;\n }\n\n logger.success(`SUCCESS: Finished FireHOL. Added ${String(fireholCount)} NEW unique proxies. Total unique: ${String(results.length)}`);\n\n if (results.length > 0) {\n logger.log('SAMPLE:', results[0]);\n }\n\n logger.log(`Writing ${String(results.length)} unique proxies to temporary JSON...`);\n fs.writeFileSync(tempProxyJson, results.join('\\n'), 'utf-8');\n logger.log('Compiling MMDB with mmdbctl...');\n\n const cmd = `${mmdbPath} import --in ${tempProxyJson} --out ${output}`;\n const convert = await run(cmd);\n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled Proxy MMDB to ${output}\\n`);\n\n\n } catch (error) {\n logger.error('\\nERROR during processing:', error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempProxyJson)) {\n fs.unlinkSync(tempProxyJson);\n }\n } \n}\n","import fs from 'node:fs';\nimport { run } from \"../utils/run.js\";\nimport { createRegExp, exactly, digit, oneOrMore } from 'magic-regexp';\nimport path from 'node:path';\nimport consola from 'consola';\nimport type { ThreatRecord } from '../types/threats.js';\n\n\n\n\nconst THREAT_CONFIG = {\n firehol_anonymous: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_anonymous.netset',\n firehol_l1: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level1.netset',\n firehol_l2: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level2.netset',\n firehol_l3: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level3.netset',\n firehol_l4: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level4.netset',\n} as const;\n\n\nconst logger = consola.withTag('[THREATS]');\n\nexport async function getThreatLists(outputPath: string, mmdbPath: string, selectedSources?: string[] | boolean) {\n\n const maintainerUrl = ' Maintainer: http://iplists.firehol.org/';\n const ipv4Regex = createRegExp(\n exactly(oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit))\n .and(exactly('/', oneOrMore(digit)).optionally()) \n .at.lineStart().at.lineEnd()\n );\n const commentRegex = createRegExp(exactly('#').at.lineStart());\n let tasks: { id: string, url: string }[] = [];\n\n if (Array.isArray(selectedSources)) {\n tasks = Object.entries(THREAT_CONFIG)\n .filter(([id]) => selectedSources.includes(id))\n .map(([id, url]) => ({ id, url }));\n } else if (Boolean(selectedSources)) {\n tasks = Object.entries(THREAT_CONFIG).map(([id, url]) => ({ id, url }));\n }\n \n if (tasks.length === 0) {\n logger.info('No valid FireHOL data sources selected. Skipping.');\n return;\n }\n try {\n logger.start(`Initializing fetch for ${String(tasks.length)} FireHOL stream(s)...`);\n\n const promises = tasks.map(async (task) => {\n const res = await fetch(task.url);\n return { id: task.id, res };\n });\n\n const resultsSettled = await Promise.allSettled(promises);\n logger.success(`SUCCESS: Fetched ${String(resultsSettled.length)} data streams from FireHOL.`);\n\n let ipsCount = 0;\n\n\n for (const result of resultsSettled) {\n\n if (result.status === 'rejected') {\n logger.error(`Promise rejected:`, result.reason);\n continue;\n }\n const { id, res } = result.value;\n const finalMsg = `${id} ${maintainerUrl}`;\n const results: string[] = [];\n logger.info(`Processing stream: ${id}...`);\n \n if (!res.ok) {\n logger.error(`Failed fetching ${id}: ${res.statusText}`);\n continue;\n }\n\n const rawTextData = await res.text();\n const lines = rawTextData.split('\\n');\n\n for (const line of lines) {\n const trimmed = line.trim();\n if (!trimmed || commentRegex.test(trimmed)) continue;\n\n const ip = trimmed;\n if (!ipv4Regex.test(ip)) continue;\n\n const record: ThreatRecord = {\n range: ip,\n comment: finalMsg\n };\n\n ipsCount++;\n results.push(JSON.stringify(record));\n }\n\n logger.info(`${id} summary:\\n\n → IPs Discovered: ${String(results.length)}\\n\n → Rolling Total: ${String(ipsCount)}\\n`);\n \n if (results.length > 0) {\n logger.info(`SAMPLE: ${results[0]}`);\n logger.info(`Writing entries to temporary JSON: temp_${id}.json`);\n const jsonName = path.resolve(outputPath, `temp_${id}.json`);\n const output = path.resolve(outputPath, `${id}.mmdb`);\n\n fs.writeFileSync(jsonName, results.join('\\n'), 'utf-8');\n console.log(`Compiling MMDB with mmdbctl to ${output}...`);\n\n const cmd = `${mmdbPath} import --in ${jsonName} --out ${output}`;\n const convert = await run(cmd);\n if (convert.stdout) logger.box(`mmdbctl: ${convert.stdout.toString().trim()}`);\n\n if (fs.existsSync(jsonName)) {\n fs.unlinkSync(jsonName);\n }\n logger.success(`SUCCESS: Compiled ${id}.mmdb\\n`);\n } else {\n logger.warn(`WARNING: No valid IPs found for ${id}. Skipping.\\n`);\n }\n }\n \n logger.success(\"COMPLETED: All threat intelligence sources processed successfully.\\n\");\n\n } catch (error) {\n logger.error('\\nFATAL ERROR during processing:', error);\n process.exit(1);\n }\n}","// This file contains a list of URLs for various web crawlers and bots.\n// The URLs are used to fetch the IP ranges of the respective crawlers and bots.\n// Please note that the list is not exhaustive and may not include all available crawlers and bots.\n// feel free to add more URLs as needed.\n\nimport { ProvidersLists } from \"../../types/botsIps.js\";\n\nexport const urls: ProvidersLists[] = [\n {\n name: 'google',\n type: 'JSON',\n urls: [\n //DOCS : https://developers.google.com/search/docs/crawling-indexing/verifying-googlebot\n 'https://developers.google.com/static/search/apis/ipranges/googlebot.json', \n 'https://developers.google.com/static/search/apis/ipranges/special-crawlers.json', \n 'https://developers.google.com/static/search/apis/ipranges/user-triggered-fetchers.json', \n 'https://developers.google.com/static/search/apis/ipranges/user-triggered-fetchers-google.json',\n 'https://www.gstatic.com/ipranges/goog.json',\n ]\n },\n { \n name: 'bing',\n type: 'JSON',\n urls: [\n // DOCS : https://www.bing.com/webmasters/help/how-to-verify-bingbot-3905dc26\n 'https://www.bing.com/toolbox/bingbot.json',\n ]\n },\n {\n name: 'openai',\n type: 'JSON',\n urls: [\n // DOCS : https://platform.openai.com/docs/bots/\n 'https://openai.com/gptbot.json',\n 'https://openai.com/chatgpt-user.json',\n 'https://openai.com/searchbot.json',\n ]\n },\n {\n name: 'apple',\n type: 'JSON',\n urls: [\n // DOCS : https://support.apple.com/en-us/119829\n 'https://search.developer.apple.com/applebot.json',\n ]\n },\n {\n name: 'ahrefs',\n type: 'JSON',\n urls: [\n // DOCS : https://help.ahrefs.com/en/articles/78658-what-is-the-list-of-your-ip-ranges\n 'https://api.ahrefs.com/v3/public/crawler-ip-ranges'\n ]\n },\n {\n name: 'duckDuckGo',\n type: 'HTML',\n urls: [\n // DOCS : https://duckduckgo.com/duckduckgo-help-pages/results/duckassistbot\n // DOCS : https://duckduckgo.com/duckduckgo-help-pages/results/duckduckbot\n 'https://duckduckgo.com/duckduckgo-help-pages/results/duckassistbot',\n 'https://duckduckgo.com/duckduckgo-help-pages/results/duckduckbot'\n ]\n },\n {\n name: 'commonCrawler',\n type: 'HTML',\n urls: [\n // DOCS : https://commoncrawl.org/faq\n 'https://commoncrawl.org/faq',\n ]\n },\n {\n name: 'xAndTwitter',\n type: 'HTML',\n urls: [\n // DOCS : https://developer.x.com/en/docs/x-for-websites/cards/guides/troubleshooting-cards\n 'https://developer.x.com/en/docs/x-for-websites/cards/guides/troubleshooting-cards'\n ]\n },\n {\n name: 'facebook',\n type: 'CSV',\n urls: [\n // DOCS : https://developers.facebook.com/docs/sharing/webmasters/web-crawlers/\n 'https://www.facebook.com/peering/geofeed'\n ]\n },\n {\n name: 'pinterest',\n type: 'HTML',\n urls: [\n // DOCS : https://help.pinterest.com/en/business/article/pinterestbot\n 'https://help.pinterest.com/en/business/article/pinterestbot'\n ]\n },\n {\n name: 'telegram',\n type: 'HTML',\n urls: [\n // DOCS : https://core.telegram.org/bots/webhooks\n 'https://core.telegram.org/bots/webhooks'\n ]\n },\n {\n name: 'semrush',\n type: 'HTML',\n urls: [\n // DOCS : https://www.semrush.com/kb/1149-issues-with-crawling-a-domain\n 'https://www.semrush.com/kb/1149-issues-with-crawling-a-domain'\n ]\n }\n];\n\n\n","import ipaddr from 'ipaddr.js';\nimport { IpRange, IpAddress } from 'cidr-calc';\n\n\nexport const normalizeIp = (ip: string): string => {\n if (!ip) throw new Error('Empty IP string');\n\n \n if (ip.includes('/')) {\n const [baseIp, mask] = ip.split('/');\n if (!ipaddr.isValidCIDR(ip)) throw new Error('Invalid CIDR');\n return `${ipaddr.parse(baseIp).toString()}/${mask}`;\n }\n\n if (!ipaddr.isValid(ip)) throw new Error('Invalid Ip address');\n return ipaddr.parse(ip).toString();\n};\n\nexport const normalizeExtractedMatch = (ip1: string, ip2?: string, mask?: string): string | string[] => {\n const cleanIp1 = normalizeIp(ip1);\n\n if (ip2 && !mask) {\n const cleanIp2 = normalizeIp(ip2);\n \n const ipRange = new IpRange(IpAddress.of(cleanIp1), IpAddress.of(cleanIp2));\n return ipRange.toCidrs().map(c => c.toString());\n }\n \n if (mask) {\n const cidr = `${cleanIp1}/${mask}`;\n if (!ipaddr.isValidCIDR(cidr)) throw new Error('Invalid Extracted CIDR');\n return cidr;\n }\n\n return cleanIp1;\n};","import consola from 'consola';\nimport { BotIpData } from '../../../types/botsIps.js';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nexport async function jsonScrapper(name: string, urls: string[]): Promise<(BotIpData | string)[]> {\n logger.start(`Processing provider: ${name}...`);\n\n const promises = urls.map(async (url) => {\n const res = await fetch(url);\n if (!res.ok) throw new Error(`fetch ${name} ${url} -> ${String(res.status)}`); \n const data = await res.json() as BotIpData | BotIpData[];\n\n return Array.isArray(data) ? data : [data];\n });\n \n const results = await Promise.all(promises);\n return results.flat();\n}","import consola from 'consola';\nimport { run } from '../../../utils/run.js';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nlet isCurlVerified = false;\nexport async function fetchWithCurl(url: string): Promise<string> {\n if (!isCurlVerified) {\n try {\n await run('command -v curl', { silent: true });\n isCurlVerified = true;\n } catch {\n logger.error('curl needed to be installed to run goodBots scrapper in order to avoid being blocked.');\n throw new Error('Fatal: curl is required for fallback scraping.');\n }\n }\n\n try {\n const { stdout } = await run(`curl -sL ${url}`, { silent: true });\n return typeof stdout === 'string' ? stdout : stdout.toString('utf-8');\n } catch (err) {\n logger.warn(`curl failed for ${url}: ${String(err)}`);\n return '';\n }\n}\n\nexport async function downloadHtml(url: string): Promise<string> {\n try {\n const response = await fetch(url, {\n headers: {\n 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36',\n 'Accept': 'text/html,text/csv,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8'\n }\n });\n\n if (!response.ok) {\n throw new Error(`Failed to fetch ${url}: ${response.statusText} - ${String(response.status)}`);\n }\n\n const html = await response.text();\n return html;\n } catch (err) {\n logger.warn(`Fetch failed for ${url}:\\n ${String(err)},\\n Using curl instead...`);\n return await fetchWithCurl(url);\n }\n}\n","import { createRegExp, exactly, anyOf, charIn, digit, letter } from 'magic-regexp';\n\nconst octet = anyOf(\n exactly('25', charIn('012345')),\n exactly('2', charIn('01234'), digit),\n exactly(charIn('01'), digit, digit),\n exactly(digit, digit),\n digit\n);\n\nconst ipv4Base = anyOf(exactly(octet, '.', octet, '.', octet, '.', octet));\nconst hexWord = anyOf(digit, charIn('abcdefABCDEF')).times.between(1, 4);\n\n\nconst ipv6Base = anyOf( \n exactly(hexWord, ':').times(7).and(hexWord),\n exactly( exactly(hexWord, ':').times.between(3, 7), ':' ),\n exactly(hexWord, ':').times.between(1, 5).and('::').and(exactly(hexWord, ':').times.any()).and(hexWord),\n exactly('::').and(anyOf(hexWord, ipv4Base, exactly(hexWord, ':').times.any().and(hexWord))),\n exactly(hexWord, ':').times.between(1, 7).and(':')\n);\n\n\nexport const ipBase = anyOf(ipv4Base, ipv6Base).notAfter(anyOf(letter, digit, ':'));\n\nexport const botIpExtractor = createRegExp(\n ipBase.groupedAs('ip1'),\n anyOf(\n // CIDR\n exactly(\n '/', \n digit.times.between(1, 3).groupedAs('mask')\n ),\n \n // ranges\n exactly(\n anyOf(' to ', ' - ', '-', ' and '),\n ipBase.groupedAs('ip2')\n )\n ).optionally(),\n \n ['g', 'i'] \n);","import { downloadHtml } from './fetchers.js';\nimport { BotIpData } from '../../../types/botsIps.js';\nimport { normalizeExtractedMatch } from '../ipNormalizers.js';\nimport { botIpExtractor } from '../regex.js';\nimport consola from 'consola';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nexport async function htmlScrapper(urls: string[], name: string): Promise<(BotIpData | string)[]> {\n logger.start(`Processing provider: ${name}...`);\n const texts = (await Promise.all(urls.map(downloadHtml)));\n\n const allMatches = texts.flatMap((txt: string) => {\n const matches = Array.from(txt.matchAll(botIpExtractor));\n \n return matches.flatMap((m) => {\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (!m.groups?.ip1) return [];\n \n try {\n const normalized = normalizeExtractedMatch(\n m.groups.ip1, \n m.groups.ip2, \n m.groups.mask\n );\n \n return Array.isArray(normalized) ? normalized : [normalized];\n } catch (err) {\n logger.warn(`Failed to normalize extracted IP match from ${name}:`, m[0], `Message: ${String(err)}`);\n return [];\n }\n });\n });\n \n return [{\n creationTime: new Date().toISOString(),\n prefixes: Array.from(new Set(allMatches)).map((ip: string) => ({ ipv4Prefix: ip }))\n }];\n}","import path from 'path';\nimport fs from 'node:fs';\nimport consola from 'consola';\nimport { urls } from './urls.js';\nimport { BotIpsLists, BotIpPrefix } from '../../types/botsIps.js';\nimport { run } from '../../utils/run.js';\nimport { normalizeIp } from './ipNormalizers.js';\nimport { jsonScrapper } from './scrappers/jsonScrapper.js';\nimport { htmlScrapper } from './scrappers/htmlScrapper.js';\nimport {ProvidersLists} from '../../types/botsIps.js';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nexport async function getCrawlersIps(outputPath: string, mmdbPath: string, customUrls?: ProvidersLists[]) {\n\n logger.start('Starting Good Bots IP scraper...');\n const databasePath = path.resolve(outputPath, './goodBots.mmdb');\n const providers = [...urls, ...(customUrls ?? [])];\n\n \n if (customUrls && customUrls.length > 0) {\n customUrls.forEach((prov) => {\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (!prov.name || !prov.type || !prov.urls) {\n throw new Error(`Provider ${prov.name || 'unknown'} is missing required fields.`);\n }\n });\n } \n\n const ipDb: BotIpsLists = {};\n\n\n for (const provider of providers) {\n if (provider.type === 'JSON') {\n ipDb[provider.name] = await jsonScrapper(provider.name, provider.urls);\n } else {\n ipDb[provider.name] = await htmlScrapper(provider.urls, provider.name);\n }\n }\n\n consola.info(`Building data...`);\n\n const mmdbRecords = Object.entries(ipDb).flatMap(([provider, snapshots]) => {\n return snapshots.flatMap((snap) => {\n if (typeof snap === 'string') {\n try {\n return [{\n range: normalizeIp(snap),\n provider: provider,\n syncToken: 'unknown',\n creationTime: new Date().toISOString()\n }];\n } catch (err) {\n logger.warn(`Invalid ip format skipping: ${snap} -> ${String(err)}`);\n return null;\n }\n }\n return snap.prefixes.map((p: BotIpPrefix) => {\n const rawIp = p.ipv4Prefix ?? p.ipv6Prefix ?? '';\n if (!rawIp) return null;\n\n try {\n return {\n range: normalizeIp(rawIp),\n provider: provider,\n syncToken: snap.syncToken,\n creationTime: snap.creationTime\n };\n } catch (err) {\n logger.warn(`Invalid ip format skipping from prefix: ${rawIp} -> ${String(err)}`);\n return null;\n }\n }).filter(Boolean);\n });\n });\n\n logger.info(`Total records to import: ${String(mmdbRecords.length)}`);\n\n const tempJsonPath = path.resolve(outputPath, 'temp_bots.json');\n\n const jsonLines = mmdbRecords.map(r => JSON.stringify(r)).join('\\n');\n\n fs.writeFileSync(tempJsonPath, jsonLines, 'utf-8');\n\n try {\n logger.info('Compiling MMDB...');\n const cmd = `${mmdbPath} import --in ${tempJsonPath} --out ${databasePath}`;\n await run(cmd);\n logger.success(`Successfully generated ${databasePath}`);\n } catch (err) {\n logger.error(`Failed to compile MMDB: ${String(err)}`);\n throw err;\n } finally {\n if (fs.existsSync(tempJsonPath)) {\n fs.unlinkSync(tempJsonPath);\n }\n }\n}","import { getBGPAndASN } from \"./bgp.js\";\nimport { buildCitiesData } from \"./city.js\";\nimport { getTorLists } from \"./tor.js\";\nimport { getGeoDatas } from \"./geo.js\";\nimport { getListOfProxies } from \"./proxy.js\";\nimport { getThreatLists } from \"./threats.js\";\nimport consola from \"consola\";\nimport { getCrawlersIps } from \"./goodBotsScrapper/scrapper.js\";\n\nconst logger = consola.withTag('Shield Base');\n\nexport async function generateData(outputPath: string, userAgent: string, selectedSources: string[] | boolean, mmdbPath: string) {\n logger.box(\"\\n=========================================\\n\" +\n \" === Starting data generation pipeline === \" +\n \"\\n=========================================\\n\");\n \n try {\n\n const results = await Promise.allSettled([\n getBGPAndASN(userAgent, outputPath, mmdbPath),\n buildCitiesData(outputPath, mmdbPath),\n getTorLists(outputPath, mmdbPath),\n getGeoDatas(outputPath, mmdbPath),\n getListOfProxies(outputPath, mmdbPath),\n getThreatLists(outputPath, mmdbPath, selectedSources),\n getCrawlersIps(outputPath, mmdbPath)\n ]);\n \n results.forEach((result, index) => {\n if (result.status === 'rejected') {\n logger.error(`Script cluster [${String(index)}] failed:`, String(result.reason));\n }\n });\n logger.info(\"\\n====================================\\n\" +\n \"Pipeline execution finished.\" +\n \"\\n====================================\\n\");\n } catch (error) {\n logger.error(\"\\n====================================\\n\" +\n `Fatal error in pipeline: ${String(error)}` +\n \"\\n====================================\\n\");\n }\n}","/* eslint-disable @typescript-eslint/no-unnecessary-condition */\nimport consola from 'consola';\nimport path from 'node:path';\nimport os from 'node:os';\nimport { readFile } from 'node:fs/promises';\nimport { existsSync } from 'node:fs';\nimport { InputCache } from '../types/input.js';\nimport { \n getBGPAndASN,\n buildCitiesData,\n generateData as executeAll,\n getGeoDatas,\n getListOfProxies,\n getThreatLists,\n getTorLists\n} from '../scripts/index.js';\n\nconst cacheOutput = path.join(os.homedir(), '.shield-base', '.cache.json');\n\nexport async function restartData(outputPath: string, all: boolean): Promise<void> {\n \n if (!existsSync(cacheOutput)) { \n consola.error('No cache found. Cannot restart. Please run a standard compilation first.');\n process.exit(1);\n }\n \n const cachedFile = await readFile(cacheOutput, 'utf-8');\n const cache = JSON.parse(cachedFile) as InputCache;\n \n if (!cache.selectedDataTypes || cache.selectedDataTypes.length === 0) {\n consola.warn('Cache is empty. No data sources to restart.');\n return;\n }\n\n if (all) {\n consola.info('Restarting ALL data sources...');\n await executeAll(outputPath, cache.useragent, true, cache.mmdbctlPath);\n consola.success('✨ All data successfully refreshed!');\n return;\n }\n\n consola.info(`Restarting data compilation from cache: ${cache.selectedDataTypes.join(', ')}`);\n\n const fireholSources = cache.selectedDataTypes.filter(s => s.startsWith('firehol_') || s === 'anonymous');\n const standardSources = cache.selectedDataTypes.filter(s => !s.startsWith('firehol_') && s !== 'anonymous');\n const executionRestartQueue: { name: string, task: () => Promise<void> }[] = [];\n\n if (standardSources.includes('BGP')) {\n executionRestartQueue.push({ name: 'BGP & ASN', task: () => getBGPAndASN(cache.useragent || '', outputPath, cache.mmdbctlPath) });\n }\n\n if (standardSources.includes('City')) {\n executionRestartQueue.push({\n name: 'City',\n task: () => buildCitiesData(cache.outPutPath, cache.mmdbctlPath),\n });\n }\n if (standardSources.includes('Geography')) {\n executionRestartQueue.push({\n name: 'Geography',\n task: () => getGeoDatas(cache.outPutPath, cache.mmdbctlPath)\n });\n }\n\n if (standardSources.includes('Proxy')) {\n executionRestartQueue.push({\n name: 'Proxy',\n task: () => getListOfProxies(cache.outPutPath, cache.mmdbctlPath)\n });\n }\n\n if (standardSources.includes('Tor')) {\n executionRestartQueue.push({\n name: 'Tor',\n task: () => getTorLists(cache.outPutPath, cache.mmdbctlPath)\n });\n }\n \n if (fireholSources.length > 0) {\n executionRestartQueue.push({\n name: 'Threats',\n task: () => getThreatLists(cache.outPutPath, cache.mmdbctlPath, fireholSources)\n });\n }\n consola.start(`Running ${String(executionRestartQueue.length)} restart jobs...`);\n const results = await Promise.allSettled(executionRestartQueue.map(q => q.task()));\n \n results.forEach((res, index) => {\n if (res.status === 'rejected') {\n consola.error(`[${executionRestartQueue[index].name}] Failed:`, res.reason);\n }\n });\n\n consola.success('✨ Cached data successfully refreshed!');\n return;\n}"]}
|
package/dist/cli.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import {n,m,b as b$1,c,e,f,d,l,g}from'./chunk-
|
|
2
|
+
import {n,m,b as b$1,c,e,f,d,l,g}from'./chunk-BYQ3CUVE.js';import {parseArgs}from'util';import B,{consola}from'consola';import {charNotIn,oneOrMore,exactly,createRegExp}from'magic-regexp';import {performance}from'perf_hooks';import I from'path';import C from'fs';import H from'os';import {pipeline}from'stream/promises';import {execSync}from'child_process';import*as le from'tar';import Ee from'extract-zip';import {readFile,writeFile}from'fs/promises';var me=/\d/,de=["-","_","/","."];function he(e=""){if(!me.test(e))return e!==e.toLowerCase()}function X(e,i){let o=de,a=[];if(!e||typeof e!="string")return a;let n="",s,m;for(let t of e){let c=o.includes(t);if(c===true){a.push(n),n="",s=void 0;continue}let f=he(t);if(m===false){if(s===false&&f===true){a.push(n),n=t,s=f;continue}if(s===true&&f===false&&n.length>1){let p=n.at(-1);a.push(n.slice(0,Math.max(0,n.length-1))),n=p+t,s=f;continue}}n+=t,s=f,m=c;}return a.push(n),a}function ge(e){return e?e[0].toUpperCase()+e.slice(1):""}function ye(e){return e?e[0].toLowerCase()+e.slice(1):""}function be(e,i){return e?(Array.isArray(e)?e:X(e)).map(o=>ge(o)).join(""):""}function _(e,i){return ye(be(e||""))}function R(e,i){return e?(Array.isArray(e)?e:X(e)).map(o=>o.toLowerCase()).join("-"):""}function ee(e){return Array.isArray(e)?e:e===void 0?[]:[e]}function F(e,i=""){let o=[];for(let a of e)for(let[n,s]of a.entries())o[n]=Math.max(o[n]||0,s.length);return e.map(a=>a.map((n,s)=>i+n[s===0?"padStart":"padEnd"](o[s])).join(" ")).join(`
|
|
3
3
|
`)}function b(e){return typeof e=="function"?e():e}var A=class extends Error{code;constructor(e,i){super(e),this.name="CLIError",this.code=i;}};function ve(e=[],i={}){let o=new Set(i.boolean||[]),a=new Set(i.string||[]),n=i.alias||{},s=i.default||{},m=new Map,t=new Map;for(let[u,r]of Object.entries(n)){let d=r;for(let y of d)m.set(u,y),t.has(y)||t.set(y,[]),t.get(y).push(u),m.set(y,u),t.has(u)||t.set(u,[]),t.get(u).push(y);}let c={};function f(u){if(o.has(u))return "boolean";let r=t.get(u)||[];for(let d of r)if(o.has(d))return "boolean";return "string"}let p=new Set([...o,...a,...Object.keys(n),...Object.values(n).flat(),...Object.keys(s)]);for(let u of p)c[u]||(c[u]={type:f(u),default:s[u]});for(let[u,r]of m.entries())u.length===1&&c[r]&&!c[r].short&&(c[r].short=u);let w=[],v={};for(let u=0;u<e.length;u++){let r=e[u];if(r==="--"){w.push(...e.slice(u));break}if(r.startsWith("--no-")){let d=r.slice(5);v[d]=true;continue}w.push(r);}let l;try{l=parseArgs({args:w,options:Object.keys(c).length>0?c:void 0,allowPositionals:!0,strict:!1});}catch{l={values:{},positionals:w};}let g={_:[]};g._=l.positionals;for(let[u,r]of Object.entries(l.values))g[u]=r;for(let[u]of Object.entries(v)){g[u]=false;let r=m.get(u);r&&(g[r]=false);let d=t.get(u);if(d)for(let y of d)g[y]=false;}for(let[u,r]of m.entries())g[u]!==void 0&&g[r]===void 0&&(g[r]=g[u]),g[r]!==void 0&&g[u]===void 0&&(g[u]=g[r]);return g}var xe=(()=>{let e=globalThis.process?.env??{};return e.NO_COLOR==="1"||e.TERM==="dumb"||e.TEST||e.CI})(),T=(e,i=39)=>o=>xe?o:`\x1B[${e}m${o}\x1B[${i}m`,E=T(1,22),x=T(36),Se=T(90),N=T(4,24);function Ae(e,i){let o={boolean:[],string:[],alias:{},default:{}},a=te(i);for(let t of a){if(t.type==="positional")continue;t.type==="string"||t.type==="enum"?o.string.push(t.name):t.type==="boolean"&&o.boolean.push(t.name),t.default!==void 0&&(o.default[t.name]=t.default),t.alias&&(o.alias[t.name]=t.alias);let c=_(t.name),f=R(t.name);if(c!==t.name||f!==t.name){let p=ee(o.alias[t.name]||[]);c!==t.name&&!p.includes(c)&&p.push(c),f!==t.name&&!p.includes(f)&&p.push(f),p.length>0&&(o.alias[t.name]=p);}}let n=ve(e,o),[...s]=n._,m=new Proxy(n,{get(t,c){return t[c]??t[_(c)]??t[R(c)]}});for(let[,t]of a.entries())if(t.type==="positional"){let c=s.shift();if(c!==void 0)m[t.name]=c;else {if(t.default===void 0&&t.required!==false)throw new A(`Missing required positional argument: ${t.name.toUpperCase()}`,"EARG");m[t.name]=t.default;}}else if(t.type==="enum"){let c=m[t.name],f=t.options||[];if(c!==void 0&&f.length>0&&!f.includes(c))throw new A(`Invalid value for argument: ${x(`--${t.name}`)} (${x(c)}). Expected one of: ${f.map(p=>x(p)).join(", ")}.`,"EARG")}else if(t.required&&m[t.name]===void 0)throw new A(`Missing required argument: --${t.name}`,"EARG");return m}function te(e){let i=[];for(let[o,a]of Object.entries(e||{}))i.push({...a,name:o,alias:ee(a.alias)});return i}async function oe(e,i){let o=await b(e.args||{}),a=Ae(i.rawArgs,o),n={rawArgs:i.rawArgs,args:a,data:i.data,cmd:e};typeof e.setup=="function"&&await e.setup(n);let s;try{let m=await b(e.subCommands);if(m&&Object.keys(m).length>0){let t=i.rawArgs.findIndex(f=>!f.startsWith("-")),c=i.rawArgs[t];if(c){if(!m[c])throw new A(`Unknown command ${x(c)}`,"E_UNKNOWN_COMMAND");let f=await b(m[c]);f&&await oe(f,{rawArgs:i.rawArgs.slice(t+1)});}else if(!e.run)throw new A("No command specified.","E_NO_COMMAND")}typeof e.run=="function"&&(s=await e.run(n));}finally{typeof e.cleanup=="function"&&await e.cleanup(n);}return {result:s}}async function M(e,i,o){let a=await b(e.subCommands);if(a&&Object.keys(a).length>0){let n=i.findIndex(t=>!t.startsWith("-")),s=i[n],m=await b(a[s]);if(m)return M(m,i.slice(n+1),e)}return [e,o]}async function Ce(e,i){try{console.log(await Pe(e,i)+`
|
|
4
4
|
`);}catch(o){console.error(o);}}var $e=/^no[-A-Z]/;async function Pe(e,i){let o=await b(e.meta||{}),a=te(await b(e.args||{})),n=await b(i?.meta||{}),s=`${n.name?`${n.name} `:""}`+(o.name||process.argv[1]),m=[],t=[],c=[],f=[];for(let l of a)if(l.type==="positional"){let g=l.name.toUpperCase(),u=l.required!==false&&l.default===void 0,r=l.default?`="${l.default}"`:"";t.push([x(g+r),l.description||"",l.valueHint?`<${l.valueHint}>`:""]),f.push(u?`<${g}>`:`[${g}]`);}else {let g=l.required===true&&l.default===void 0,u=[...(l.alias||[]).map(r=>`-${r}`),`--${l.name}`].join(", ")+(l.type==="string"&&(l.valueHint||l.default)?`=${l.valueHint?`<${l.valueHint}>`:`"${l.default||""}"`}`:"")+(l.type==="enum"&&l.options?`=<${l.options.join("|")}>`:"");if(m.push([x(u+(g?" (required)":"")),l.description||""]),l.type==="boolean"&&(l.default===true||l.negativeDescription)&&!$e.test(l.name)){let r=[...(l.alias||[]).map(d=>`--no-${d}`),`--no-${l.name}`].join(", ");m.push([x(r+(g?" (required)":"")),l.negativeDescription||""]);}g&&f.push(u);}if(e.subCommands){let l=[],g=await b(e.subCommands);for(let[u,r]of Object.entries(g)){let d=await b((await b(r))?.meta);d?.hidden||(c.push([x(u),d?.description||""]),l.push(u));}f.push(l.join("|"));}let p=[],w=o.version||n.version;p.push(Se(`${o.description} (${s+(w?` v${w}`:"")})`),"");let v=m.length>0||t.length>0;return p.push(`${N(E("USAGE"))} ${x(`${s}${v?" [OPTIONS]":""} ${f.join(" ")}`)}`,""),t.length>0&&(p.push(N(E("ARGUMENTS")),""),p.push(F(t," ")),p.push("")),m.length>0&&(p.push(N(E("OPTIONS")),""),p.push(F(m," ")),p.push("")),c.length>0&&(p.push(N(E("COMMANDS")),""),p.push(F(c," ")),p.push("",`Use ${x(`${s} <command> --help`)} for more information about a command.`)),p.filter(l=>typeof l=="string").join(`
|
|
5
5
|
`)}async function ne(e,i={}){let o=i.rawArgs||process.argv.slice(2),a=i.showUsage||Ce;try{if(o.includes("--help")||o.includes("-h"))await a(...await M(e,o)),process.exit(0);else if(o.length===1&&o[0]==="--version"){let n=typeof e.meta=="function"?await e.meta():await e.meta;if(!n?.version)throw new A("No version specified","E_NO_VERSION");console.log(n.version);}else await oe(e,{rawArgs:o});}catch(n){n instanceof A?(await a(...await M(e,o)),console.error(n.message)):console.error(n,`
|
package/dist/main.d.ts
CHANGED
|
@@ -32,12 +32,218 @@ declare const botIpExtractor: magic_regexp.MagicRegExp<"/(?<ip1>(?<!(?:[a-zA-Z]|
|
|
|
32
32
|
declare const normalizeIp: (ip: string) => string;
|
|
33
33
|
declare const normalizeExtractedMatch: (ip1: string, ip2?: string, mask?: string) => string | string[];
|
|
34
34
|
|
|
35
|
+
interface BotIpPrefix {
|
|
36
|
+
ipv4Prefix?: string;
|
|
37
|
+
ipv6Prefix?: string;
|
|
38
|
+
}
|
|
39
|
+
interface BotIpData {
|
|
40
|
+
creationTime?: string;
|
|
41
|
+
syncToken?: string;
|
|
42
|
+
prefixes: BotIpPrefix[];
|
|
43
|
+
}
|
|
44
|
+
type BotIpsLists = Record<string, (BotIpData | string)[]>;
|
|
35
45
|
interface ProvidersLists {
|
|
36
46
|
name: string;
|
|
37
47
|
type: 'HTML' | 'JSON' | 'CSV';
|
|
38
48
|
urls: string[];
|
|
39
49
|
}
|
|
50
|
+
interface CrawlersRecord {
|
|
51
|
+
range: string;
|
|
52
|
+
provider: string;
|
|
53
|
+
syncToken: string;
|
|
54
|
+
creationTime: string;
|
|
55
|
+
}
|
|
40
56
|
|
|
41
57
|
declare function getCrawlersIps(outputPath: string, mmdbPath: string, customUrls?: ProvidersLists[]): Promise<void>;
|
|
42
58
|
|
|
43
|
-
|
|
59
|
+
interface AsnDictionaryEntry {
|
|
60
|
+
name: string;
|
|
61
|
+
type: string;
|
|
62
|
+
}
|
|
63
|
+
interface BGPRouteRaw {
|
|
64
|
+
CIDR: string;
|
|
65
|
+
ASN: number;
|
|
66
|
+
Hits: number;
|
|
67
|
+
}
|
|
68
|
+
interface BgpRecord {
|
|
69
|
+
range: string;
|
|
70
|
+
asn_id: string;
|
|
71
|
+
asn_name: string;
|
|
72
|
+
classification: string;
|
|
73
|
+
hits: string;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
interface GlobalCity {
|
|
77
|
+
id: number;
|
|
78
|
+
name: string;
|
|
79
|
+
latitude: string;
|
|
80
|
+
longitude: string;
|
|
81
|
+
}
|
|
82
|
+
interface GlobalState {
|
|
83
|
+
id: number;
|
|
84
|
+
name: string;
|
|
85
|
+
state_code: string;
|
|
86
|
+
latitude: string;
|
|
87
|
+
longitude: string;
|
|
88
|
+
type: string | null;
|
|
89
|
+
cities: GlobalCity[];
|
|
90
|
+
}
|
|
91
|
+
interface GlobalCountry {
|
|
92
|
+
id: number;
|
|
93
|
+
name: string;
|
|
94
|
+
iso2: string;
|
|
95
|
+
iso3: string;
|
|
96
|
+
numeric_code: string;
|
|
97
|
+
phonecode: string;
|
|
98
|
+
capital: string;
|
|
99
|
+
currency: string;
|
|
100
|
+
currency_name: string;
|
|
101
|
+
currency_symbol: string;
|
|
102
|
+
tld: string;
|
|
103
|
+
native: string | null;
|
|
104
|
+
region: string;
|
|
105
|
+
region_id: number;
|
|
106
|
+
subregion: string;
|
|
107
|
+
subregion_id: number;
|
|
108
|
+
nationality: string;
|
|
109
|
+
timezones: {
|
|
110
|
+
zoneName: string;
|
|
111
|
+
gmtOffset: number;
|
|
112
|
+
gmtOffsetName: string;
|
|
113
|
+
abbreviation: string;
|
|
114
|
+
tzName: string;
|
|
115
|
+
}[];
|
|
116
|
+
translations: Record<string, string>;
|
|
117
|
+
latitude: string;
|
|
118
|
+
longitude: string;
|
|
119
|
+
emoji: string;
|
|
120
|
+
emojiU: string;
|
|
121
|
+
states: GlobalState[];
|
|
122
|
+
}
|
|
123
|
+
interface CityGeoRecord {
|
|
124
|
+
range: string;
|
|
125
|
+
country_code: string;
|
|
126
|
+
region: string;
|
|
127
|
+
city: string;
|
|
128
|
+
zip_code: string;
|
|
129
|
+
numericCode: string;
|
|
130
|
+
latitude: string;
|
|
131
|
+
longitude: string;
|
|
132
|
+
state: string;
|
|
133
|
+
name: string;
|
|
134
|
+
native: string;
|
|
135
|
+
phone: string;
|
|
136
|
+
continent: string;
|
|
137
|
+
capital: string;
|
|
138
|
+
currency: string;
|
|
139
|
+
currency_name: string;
|
|
140
|
+
languages: string;
|
|
141
|
+
emoji: string;
|
|
142
|
+
timezone: string;
|
|
143
|
+
utc_offset: string;
|
|
144
|
+
tld: string;
|
|
145
|
+
nationality: string;
|
|
146
|
+
subregion: string;
|
|
147
|
+
timeZoneName: string;
|
|
148
|
+
}
|
|
149
|
+
interface GeoRecord {
|
|
150
|
+
range: string;
|
|
151
|
+
country_code: string;
|
|
152
|
+
region: string;
|
|
153
|
+
numericCode: string;
|
|
154
|
+
name: string;
|
|
155
|
+
native: string;
|
|
156
|
+
phone: string;
|
|
157
|
+
capital: string;
|
|
158
|
+
currency: string;
|
|
159
|
+
currency_name: string;
|
|
160
|
+
currency_symbol: string;
|
|
161
|
+
languages: string;
|
|
162
|
+
emoji: string;
|
|
163
|
+
tld: string;
|
|
164
|
+
nationality: string;
|
|
165
|
+
subregion: string;
|
|
166
|
+
timezone: string;
|
|
167
|
+
timeZoneName: string;
|
|
168
|
+
utc_offset: string;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
interface ExitPolicySummary {
|
|
172
|
+
accept?: string[];
|
|
173
|
+
reject?: string[];
|
|
174
|
+
}
|
|
175
|
+
interface OnionooPayload {
|
|
176
|
+
version: string;
|
|
177
|
+
relays: Partial<RelayNode>[];
|
|
178
|
+
bridges: Partial<RelayNode>[];
|
|
179
|
+
}
|
|
180
|
+
interface RelayNode {
|
|
181
|
+
or_addresses: string[];
|
|
182
|
+
exit_addresses?: string[] | string;
|
|
183
|
+
last_seen: string;
|
|
184
|
+
last_changed_address_or_port: string;
|
|
185
|
+
first_seen: string;
|
|
186
|
+
running: boolean;
|
|
187
|
+
flags: string[];
|
|
188
|
+
country: string;
|
|
189
|
+
country_name: string;
|
|
190
|
+
as: string;
|
|
191
|
+
as_name: string;
|
|
192
|
+
last_restarted: string;
|
|
193
|
+
exit_policy: string[];
|
|
194
|
+
exit_policy_summary: ExitPolicySummary;
|
|
195
|
+
exit_policy_v6_summary?: ExitPolicySummary;
|
|
196
|
+
contact: string;
|
|
197
|
+
version_status: string;
|
|
198
|
+
guard_probability: number;
|
|
199
|
+
middle_probability: number;
|
|
200
|
+
exit_probability: number;
|
|
201
|
+
recommended_version: boolean;
|
|
202
|
+
measured: boolean;
|
|
203
|
+
}
|
|
204
|
+
interface TorRecord {
|
|
205
|
+
range: string;
|
|
206
|
+
or_addresses: string;
|
|
207
|
+
exit_addresses: string;
|
|
208
|
+
last_seen: string;
|
|
209
|
+
last_changed_address_or_port: string;
|
|
210
|
+
first_seen: string;
|
|
211
|
+
running: boolean;
|
|
212
|
+
flags: string;
|
|
213
|
+
country: string;
|
|
214
|
+
country_name: string;
|
|
215
|
+
as: string;
|
|
216
|
+
as_name: string;
|
|
217
|
+
last_restarted: string;
|
|
218
|
+
exit_policy: string;
|
|
219
|
+
exit_policy_summary: string;
|
|
220
|
+
exit_policy_v6_summary?: string;
|
|
221
|
+
contact: string;
|
|
222
|
+
version_status: string;
|
|
223
|
+
guard_probability: number;
|
|
224
|
+
middle_probability: number;
|
|
225
|
+
exit_probability: number;
|
|
226
|
+
recommended_version: boolean;
|
|
227
|
+
measured: boolean;
|
|
228
|
+
}
|
|
229
|
+
|
|
230
|
+
interface InputCache {
|
|
231
|
+
selectedDataTypes: string[];
|
|
232
|
+
useragent: string;
|
|
233
|
+
license: boolean;
|
|
234
|
+
mmdbctlPath: string;
|
|
235
|
+
outPutPath: string;
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
interface ProxyRecord {
|
|
239
|
+
range: string;
|
|
240
|
+
port: string;
|
|
241
|
+
comment: string;
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
interface ThreatRecord {
|
|
245
|
+
range: string;
|
|
246
|
+
comment: string;
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
export { type AsnDictionaryEntry, type BGPRouteRaw, type BgpRecord, type BotIpData, type BotIpPrefix, type BotIpsLists, type CityGeoRecord, type CrawlersRecord, type ExitPolicySummary, type GeoRecord, type GlobalCity, type GlobalCountry, type GlobalState, type InputCache, type OnionooPayload, type ProvidersLists, type ProxyRecord, type RelayNode, type RunOptions, type RunResult, type ThreatRecord, type TorRecord, botIpExtractor, buildCitiesData, generateData, getBGPAndASN, getCrawlersIps, getGeoDatas, getListOfProxies, getThreatLists, getTorLists, ipBase, normalizeExtractedMatch, normalizeIp, restartData, run };
|
package/dist/main.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export{k as botIpExtractor,c as buildCitiesData,m as generateData,b as getBGPAndASN,l as getCrawlersIps,e as getGeoDatas,f as getListOfProxies,g as getThreatLists,d as getTorLists,j as ipBase,i as normalizeExtractedMatch,h as normalizeIp,n as restartData,a as run}from'./chunk-
|
|
1
|
+
export{k as botIpExtractor,c as buildCitiesData,m as generateData,b as getBGPAndASN,l as getCrawlersIps,e as getGeoDatas,f as getListOfProxies,g as getThreatLists,d as getTorLists,j as ipBase,i as normalizeExtractedMatch,h as normalizeIp,n as restartData,a as run}from'./chunk-BYQ3CUVE.js';//# sourceMappingURL=main.js.map
|
|
2
2
|
//# sourceMappingURL=main.js.map
|
package/package.json
CHANGED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/utils/run.ts","../src/scripts/bgp.ts","../src/scripts/city.ts","../src/scripts/tor.ts","../src/scripts/geo.ts","../src/scripts/proxy.ts","../src/scripts/threats.ts","../src/scripts/goodBotsScrapper/urls.ts","../src/scripts/goodBotsScrapper/ipNormalizers.ts","../src/scripts/goodBotsScrapper/scrappers/jsonScrapper.ts","../src/scripts/goodBotsScrapper/scrappers/fetchers.ts","../src/scripts/goodBotsScrapper/regex.ts","../src/scripts/goodBotsScrapper/scrappers/htmlScrapper.ts","../src/scripts/goodBotsScrapper/scrapper.ts","../src/scripts/executeAll.ts","../src/utils/restart.ts"],"names":["execAsync","util","child","run","command","options","stdout","stderr","result","error","logger","consola","getBGPAndASN","userAgent","outputPath","mmdbPath","urls","output","path","tempASNJson","rawAsnCsv","asnDictionary","asnLines","regex","createRegExp","exactly","oneOrMore","digit","nonQuotes","charNotIn","quotePair","splitRegex","line","parts","match","asnNumber","quoteStripRegex","asnName","asnClass","rawTable","routes","results","route","parsed","dictionaryLookup","record","q","cmd","convert","currentDir","fileURLToPath","dbPath","p","buildCitiesData","tempGeoJson","rawData","dbJson","countryIndex","country","stateMap","state","cityMap","city","lines","commentRegex","prefix","region","zip","cc","emoji","lat","lon","stateName","countryMeta","countryData","regionCode","stateData","cityData","geoRecord","getTorLists","url","tempFileName","response","data","toMap","flags","fl","f","node","ipsToProcess","ip","cleanIp","parsedIp","ipaddr","finalNetworkAddress","ipv4","ipv6","ndjsonOutput","V","J","I","getGeoDatas","res","start","end","getListOfProxies","tempProxyJson","seenIps","ipv4Regex","resAwesome","splitAwesomeListRegex","stripAwesomeListRegex","anyOf","dest_ip","dest_port","metadata_comment","cleanComment","resFirehol","fireholLines","fireholCount","trimmed","fs","THREAT_CONFIG","getThreatLists","selectedSources","maintainerUrl","tasks","id","promises","task","resultsSettled","ipsCount","finalMsg","jsonName","normalizeIp","baseIp","mask","normalizeExtractedMatch","ip1","ip2","cleanIp1","cleanIp2","IpRange","IpAddress","c","cidr","jsonScrapper","name","isCurlVerified","fetchWithCurl","err","downloadHtml","octet","charIn","ipv4Base","hexWord","ipv6Base","ipBase","letter","botIpExtractor","htmlScrapper","allMatches","txt","m","normalized","getCrawlersIps","customUrls","databasePath","providers","prov","ipDb","provider","mmdbRecords","snapshots","snap","rawIp","tempJsonPath","jsonLines","r","generateData","index","cacheOutput","os","restartData","all","existsSync","cachedFile","readFile","cache","fireholSources","s","standardSources","executionRestartQueue"],"mappings":"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","file":"chunk-MZE5OD6T.js","sourcesContent":["import child from 'node:child_process';\nimport util from 'node:util';\nimport type { ExecOptions } from 'node:child_process';\n\nexport interface RunResult {\n stdout: string | Buffer;\n stderr: string | Buffer;\n}\n\nconst execAsync = util.promisify(child.exec);\n\nexport interface RunOptions extends ExecOptions {\n silent?: boolean;\n}\n\nexport const run = async (command: string, options: RunOptions = {}): Promise<RunResult> => {\n try {\n const { stdout, stderr } = await execAsync(command, {\n ...options,\n maxBuffer: options.maxBuffer ?? 1024 * 1024 * 10, \n });\n\n const result: RunResult = {\n stdout: typeof stdout === 'string' ? stdout.trim() : stdout,\n stderr: typeof stderr === 'string' ? stderr.trim() : stderr,\n };\n\n if (!options.silent) {\n console.log(`[run]: ${command}`);\n if (result.stdout) console.log('stdout:', result.stdout);\n if (result.stderr) console.error('stderr:', result.stderr);\n }\n\n return result;\n } catch (error: unknown) {\n\n console.error(`Execution failed for command: \"${command}\"`);\n \n if (typeof error === 'object' && error !== null) {\n const e = error as { stderr?: string; stdout?: string };\n if (e.stderr) console.error('Error Output:', e.stderr);\n }\n \n throw error;\n }\n};","import { createRegExp, exactly, digit, oneOrMore, charNotIn } from \"magic-regexp\";\nimport * as fs from 'fs';\nimport { run } from \"../utils/run.js\";\nimport path from \"path\";\nimport { AsnDictionaryEntry, BGPRouteRaw, BgpRecord } from \"../types/bgp.js\";\nimport { consola } from \"consola\";\n\nconst logger = consola.withTag('[ASN/BGP]');\nexport async function getBGPAndASN(userAgent: string, outputPath: string, mmdbPath: string) {\n const urls = ['https://bgp.tools/asns.csv', 'https://bgp.tools/table.jsonl'];\n const output = path.resolve(outputPath, 'asn.mmdb');\n const tempASNJson = path.resolve(outputPath, 'temp_asn_data.json');\n try {\n logger.info(\"\\nFetching ASN Dictionary from BGP.tools...\");\n const ansRes = await fetch(urls[0], {\n method: 'GET',\n headers: {\n 'User-Agent': userAgent\n }\n });\n\n // AS1,\"Level 3 Parent, LLC\",Unknown\n // AS10,CSNET Coordination and Information Center,Unknown\n\n const rawAsnCsv = await ansRes.text();\n const asnDictionary = new Map<number, AsnDictionaryEntry>();\n const asnLines = rawAsnCsv.split('\\n').slice(1);\n \n const regex = createRegExp(exactly('AS').and(oneOrMore(digit).groupedAs('asnNumber')));\n \n const nonQuotes = charNotIn('\"').times.any();\n const quotePair = nonQuotes.and(exactly('\"')).times(2);\n const splitRegex = createRegExp(\n exactly(',').before(quotePair.times.any().and(nonQuotes).at.lineEnd())\n );\n\n for (const line of asnLines) {\n if (!line) continue;\n const parts = line.split(splitRegex);\n\n const match = parts[0].match(regex);\n const asnNumber = match?.groups.asnNumber ? parseInt(match.groups.asnNumber, 10) : null;\n \n const quoteStripRegex = createRegExp(exactly('\"').at.lineStart().or(exactly('\"').at.lineEnd()), ['g']);\n const asnName = parts[1]?.replace(quoteStripRegex, '').trim() || 'Unknown';\n const asnClass = parts[2]?.trim() || 'Unknown';\n \n if (asnNumber !== null) {\n asnDictionary.set(asnNumber, { name: asnName, type: asnClass });\n }\n }\n logger.success(`SUCCESS: Loaded ${String(asnDictionary.size)} ASN definitions.`);\n logger.info(\"Fetching Routing Table...\");\n const tableRes = await fetch(urls[1], {\n method: 'GET',\n headers: {\n 'User-Agent': userAgent\n }\n });\n\n const rawTable = await tableRes.text();\n logger.info(\"Mapping CIDR to ASN data...\");\n const routes = rawTable.split('\\n');\n const results = [];\n\n for (const route of routes) {\n if (!route) continue;\n // {\"CIDR\":\"1.1.1.0/24\",\"ASN\":13335,\"Hits\":509}\n const parsed = JSON.parse(route) as BGPRouteRaw;\n if (parsed.Hits < 10) continue; \n \n const dictionaryLookup = asnDictionary.get(parsed.ASN) ?? { name: 'Unknown', type: 'Unknown' };\n\n const record: BgpRecord = {\n range: parsed.CIDR,\n asn_id: String(parsed.ASN),\n asn_name: dictionaryLookup.name,\n classification: dictionaryLookup.type,\n hits: String(parsed.Hits)\n };\n results.push(JSON.stringify(record));\n }\n\n if (results.length > 0) {\n logger.log('SAMPLE:', results[0]);\n }\n\n logger.info(`Writing ${String(results.length)} enriched entries to temporary JSON...`);\n fs.writeFileSync(tempASNJson, results.join('\\n'), 'utf-8');\n logger.info(`Compiling MMDB with mmdbctl to ${output}...`);\n \n const cmd = `${mmdbPath} import --in ${tempASNJson} --out ${output}`;\n const convert = await run(cmd);\n\n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled ASN MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error(`\\nERROR during processing:`, error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempASNJson)) {\n fs.unlinkSync(tempASNJson);\n }\n }\n}\n","import { run } from \"../utils/run.js\";\nimport * as fs from 'fs';\nimport type { GlobalCountry, GlobalState, GlobalCity, CityGeoRecord } from \"../types/geography.js\";\nimport * as path from \"path\";\nimport { fileURLToPath } from \"url\";\nimport { createRegExp, exactly } from \"magic-regexp\";\nimport { consola } from \"consola\";\n\nconst currentDir = path.dirname(fileURLToPath(import.meta.url));\nconst dbPath = [\n path.resolve(currentDir, './countries+states+cities.json'),\n path.resolve(currentDir, '../../public/countries+states+cities.json')\n].find(p => fs.existsSync(p)) ?? path.resolve(currentDir, './countries+states+cities.json');\n\nconst logger = consola.withTag('[CITY/GEO]');\n\nexport async function buildCitiesData(outputPath: string, mmdbPath: string) {\n logger.info('\\nBuilding global geographic index from hierarchical database...');\n const output = path.resolve(outputPath, 'city.mmdb');\n const tempGeoJson = path.resolve(outputPath, 'temp_city_data.json');\n \n\n const rawData = fs.readFileSync(dbPath, 'utf8');\n const dbJson = JSON.parse(rawData) as GlobalCountry[];\n\n const countryIndex = new Map<string, { meta: GlobalCountry, states: Map<string, { meta: GlobalState, cities: Map<string, GlobalCity> }> }>();\n \n for (const country of dbJson) {\n const stateMap = new Map<string, { meta: GlobalState, cities: Map<string, GlobalCity> }>();\n \n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (country.states) {\n for (const state of country.states) {\n const cityMap = new Map<string, GlobalCity>();\n \n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (state.cities) {\n for (const city of state.cities) {\n cityMap.set(city.name.toLowerCase(), city);\n }\n }\n \n stateMap.set(state.state_code, { meta: state, cities: cityMap });\n }\n }\n \n countryIndex.set(country.iso2.toUpperCase(), { meta: country, states: stateMap });\n }\n\n try {\n logger.info('Fetching validated geofeed CSV...');\n\n const res = await fetch('https://geolocatemuch.com/geofeeds/validated-all.csv');\n const csvText = await res.text();\n const lines = csvText.split('\\n');\n const commentRegex = createRegExp(exactly('#').at.lineStart());\n \n logger.success(`SUCCESS: Received ${String(lines.length)} IP ranges. Mapping to geographic index...`);\n const results: string[] = [];\n\n for (const line of lines) {\n if (!line.trim() || commentRegex.test(line)) continue;\n\n const parts = line.split(',');\n const prefix = parts[0]?.trim() || \"\";\n const country = parts[1]?.trim() || \"\";\n const region = parts[2]?.trim() || \"\";\n const city = parts[3]?.trim() || \"\";\n const zip = parts[4]?.trim() || \"\";\n\n if (!country && !city && !zip) continue;\n\n const cc = country.toUpperCase() || \"\";\n\n let emoji = \"\";\n let lat = '';\n let lon = '';\n let stateName = '';\n let countryMeta: Partial<GlobalCountry> = {};\n \n const countryData = countryIndex.get(cc);\n if (countryData) {\n countryMeta = countryData.meta;\n emoji = countryData.meta.emoji || \"\";\n \n \n if (region) {\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n const regionCode = region.includes('-') ? region.split('-').pop()! : region;\n const stateData = countryData.states.get(regionCode);\n \n if (stateData) {\n stateName = stateData.meta.name || stateData.meta.state_code || \"\";\n \n if (city) {\n const cityData = stateData.cities.get(city.toLowerCase());\n if (cityData) {\n lat = cityData.latitude || \"\";\n lon = cityData.longitude || \"\";\n }\n }\n\n if (!lat && stateData.meta.latitude && stateData.meta.longitude) {\n lat = stateData.meta.latitude || \"\";\n lon = stateData.meta.longitude || \"\";\n }\n }\n }\n \n\n if (!lat && city) {\n for (const [, stateData] of countryData.states) {\n const cityData = stateData.cities.get(city.toLowerCase());\n if (cityData) {\n lat = cityData.latitude || \"\";\n lon = cityData.longitude || \"\";\n if (!stateName) stateName = stateData.meta.name || stateData.meta.state_code || \"\";\n break;\n }\n }\n }\n\n if (!lat && countryMeta.latitude && countryMeta.longitude) {\n lat = countryMeta.latitude || \"\";\n lon = countryMeta.longitude || \"\";\n }\n }\n\n const geoRecord: CityGeoRecord = {\n range: prefix,\n country_code: country,\n region: region || (countryMeta.region ?? \"\"),\n subregion: countryMeta.subregion ?? \"\",\n city: city,\n zip_code: zip,\n latitude: lat,\n longitude: lon,\n state: stateName,\n name: countryMeta.name ?? \"Unknown\",\n native: countryMeta.native ?? \"\",\n phone: countryMeta.phonecode ?? '',\n numericCode: countryMeta.numeric_code ?? \"\",\n continent: countryMeta.region ?? \"\",\n capital: countryMeta.capital ?? \"\",\n currency: countryMeta.currency ?? '',\n currency_name: countryMeta.currency_name ?? \"\",\n languages: countryMeta.translations ? Object.values(countryMeta.translations)[0] ?? \"\" : \"\",\n emoji: emoji,\n timezone: countryMeta.timezones?.[0]?.zoneName ?? \"\",\n utc_offset: countryMeta.timezones?.[0]?.gmtOffsetName ?? \"\",\n timeZoneName: countryMeta.timezones?.[0]?.tzName ?? \"\",\n tld: countryMeta.tld ?? \"\",\n nationality: countryMeta.nationality ?? \"\",\n };\n \n results.push(JSON.stringify(geoRecord));\n }\n \n logger.info(`Writing ${String(results.length)} enriched entries to temporary JSON...`);\n fs.writeFileSync(tempGeoJson, results.join('\\n'), 'utf-8');\n\n logger.start('Compiling MMDB with mmdbctl...');\n \n const cmd = `${mmdbPath} import --in ${tempGeoJson} --out ${output}`;\n const convert = await run(cmd);\n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled City MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error('\\nERROR during processing:', error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempGeoJson)) {\n fs.unlinkSync(tempGeoJson);\n }\n }\n}\n","/* eslint-disable @typescript-eslint/ban-ts-comment */\nimport { run } from \"../utils/run.js\";\nimport * as fs from 'fs';\nimport ipaddr from 'ipaddr.js';\nimport path from \"path\";\nimport type { OnionooPayload, TorRecord } from \"../types/tor.js\";\nimport consola from \"consola\";\n\n\nconst logger = consola.withTag('[TOR]');\n\nexport async function getTorLists(outputPath: string, mmdbPath: string): Promise<void> {\n const url = 'https://onionoo.torproject.org/details';\n const output = path.resolve(outputPath, 'tor.mmdb');\n const tempFileName = path.resolve(outputPath, 'temp_tor_nodes.json');\n\ntry {\n\n logger.info(\"\\nFetching node data from Onionoo API...\");\n const response = await fetch(url, {\n method: 'GET',\n headers: {\n 'Accept-Encoding': 'gzip',\n 'Accept': 'application/json'\n }\n\n });\n\n\n\n if (!response.ok) {\n logger.error(`ERROR: API fetch failed with status ${String(response.status)}`);\n return;\n }\n\n const data = await response.json() as OnionooPayload;\n logger.success('SUCCESS: Data received, mapping relay nodes...');\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n const rawNodes = data.relays || [];\n const toMap = rawNodes.filter((flags) => {\n\n const fl = flags.flags?.map(f => f.toLowerCase()) ?? [];\n return fl.includes(\"exit\") ||\n fl.includes(\"valid\") ||\n fl.includes(\"running\") ||\n fl.includes(\"stable\") ||\n fl.includes(\"hsdir\") &&\n flags.exit_addresses &&\n flags.or_addresses;\n });\n\n\n\n if (toMap.length === 0) {\n logger.warn(\"WARNING: No relay nodes found matching criteria.\");\n return;\n }\n\n const results: TorRecord[] = [];\n\n for (const node of toMap) {\n const ipsToProcess = [\n // eslint-disable-next-line @typescript-eslint/no-misused-spread\n ...(node.exit_addresses ?? []),\n ...(node.or_addresses ?? [])\n ];\n\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (!ipsToProcess) continue;\n\n for (const ip of ipsToProcess) {\n\n let cleanIp = ip;\n if (cleanIp.startsWith('[')) {\n cleanIp = cleanIp.split(']:')[0].substring(1);\n } else {\n cleanIp = cleanIp.split(':')[0];\n }\n\n const parsedIp = ipaddr.parse(cleanIp);\n let finalNetworkAddress: string;\n\n if (parsedIp.kind() === 'ipv4') {\n const ipv4 = parsedIp as ipaddr.IPv4;\n const networkAddress = ipaddr.IPv4.networkAddressFromCIDR(`${ipv4.toString()}/24`);\n finalNetworkAddress = `${networkAddress.toString()}/24`;\n } else if (parsedIp.kind() === 'ipv6') {\n const ipv6 = parsedIp as ipaddr.IPv6;\n const networkAddress = ipaddr.IPv6.networkAddressFromCIDR(`${ipv6.toString()}/64`);\n finalNetworkAddress = `${networkAddress.toString()}/64`;\n } else {\n continue;\n }\n\n results.push({\n range: finalNetworkAddress,\n or_addresses: node.or_addresses?.join(',') ?? '',\n // @ts-ignore\n // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment, @typescript-eslint/no-unsafe-call\n exit_addresses: node.exit_addresses?.join(',') ?? '',\n last_seen: node.last_seen ?? \"\",\n last_changed_address_or_port: node.last_changed_address_or_port ?? \"\",\n first_seen: node.first_seen ?? \"\",\n running: node.running ?? false,\n flags: node.flags?.join(',') ?? \"\",\n country: node.country ?? \"\",\n country_name: node.country_name ?? \"\",\n as: node.as ?? \"\",\n as_name: node.as_name ?? \"\",\n last_restarted: node.last_restarted ?? \"\",\n exit_policy: node.exit_policy?.join(',') ?? '',\n exit_policy_summary: JSON.stringify(node.exit_policy_summary) || '',\n exit_policy_v6_summary: node.exit_policy_v6_summary ? JSON.stringify(node.exit_policy_v6_summary) : undefined,\n contact: node.contact ?? \"Unknown\",\n version_status: node.version_status ?? \"\",\n guard_probability: node.guard_probability ?? 0,\n middle_probability: node.middle_probability ?? 0,\n exit_probability: node.exit_probability ?? 0,\n recommended_version: node.recommended_version ?? false,\n measured: node.measured ?? false,\n });\n }\n\n }\n\n logger.info('SAMPLE:', results[0]);\n const ndjsonOutput = results.map(record => JSON.stringify(record)).join('\\n');\n fs.writeFileSync(tempFileName, ndjsonOutput, 'utf-8');\n try {\n logger.info('Compiling MMDB with mmdbctl...');\n const convert = await run(`${mmdbPath} import -j -i ${tempFileName} -o ${output}`);\n if (convert.stdout) logger.info(`mmdbctl: ${convert.stdout.toString().trim()}`);\n\n logger.success(`COMPLETED: Successfully compiled Tor MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error(\"ERROR: MMDB compilation failed:\", error);\n return;\n }\n\n } catch (error: unknown) {\n logger.error(\"ERROR: Unexpected failure while fetching node list:\", error);\n return;\n } finally {\n if (fs.existsSync(tempFileName)) {\n fs.unlinkSync(tempFileName);\n }\n \n }\n\n} ","import { run } from \"../utils/run.js\";\nimport * as fs from 'fs';\nimport * as path from \"path\";\nimport { fileURLToPath } from \"url\";\nimport type { GlobalCountry, GeoRecord } from \"../types/geography.js\";\nimport consola from \"consola\";\n\nconst currentDir = path.dirname(fileURLToPath(import.meta.url));\nconst dbPath = [\n path.resolve(currentDir, './countries+states+cities.json'),\n path.resolve(currentDir, '../../public/countries+states+cities.json')\n].find(p => fs.existsSync(p)) ?? path.resolve(currentDir, './countries+states+cities.json');\n\nconst logger = consola.withTag('[GEO/COUNTRY]');\n\nexport async function getGeoDatas(outputPath: string, mmdbPath: string) {\n logger.info(\"\\nBuilding country index from local database...\");\n\n const output = path.resolve(outputPath, 'country.mmdb');\n const tempGeoJson = path.resolve(outputPath, 'temp_country_data.json');\n const rawData = fs.readFileSync(dbPath, 'utf8');\n const dbJson = JSON.parse(rawData) as GlobalCountry[];\n\n const countryIndex = new Map<string, GlobalCountry>();\n for (const country of dbJson) {\n countryIndex.set(country.iso2.toUpperCase(), country);\n }\n\n logger.info('Fetching global IPv4 Country mapping from Sapics...');\n const url = 'https://raw.githubusercontent.com/sapics/ip-location-db/refs/heads/main/geo-asn-country/geo-asn-country-ipv4.csv';\n\n try {\n const res = await fetch(url);\n if (!res.ok) {\n throw new Error(`ERROR: Failed to fetch country data: ${res.statusText}`);\n }\n\n const csvText = await res.text();\n const lines = csvText.split('\\n');\n \n logger.success(`SUCCESS: Received ${String(lines.length)} global IP ranges. Enriching data...`);\n const results: string[] = [];\n\n for (const line of lines) {\n if (!line.trim()) continue;\n \n const parts = line.split(',');\n const start = parts[0]?.trim();\n const end = parts[1]?.trim();\n const cc = parts[2]?.trim().toUpperCase();\n \n if (!start || !end || !cc) continue;\n\n const countryMeta = countryIndex.get(cc);\n\n const record: GeoRecord = {\n range: `${start}-${end}`,\n country_code: cc,\n region: countryMeta?.region ?? '',\n numericCode: countryMeta?.numeric_code ?? \"\",\n name: countryMeta?.name ?? \"\",\n native: countryMeta?.native ?? \"\",\n phone: countryMeta?.phonecode ?? \"\",\n capital: countryMeta?.capital ?? \"\",\n currency: countryMeta?.currency ?? \"\",\n currency_name: countryMeta?.currency_name ?? \"\",\n currency_symbol: countryMeta?.currency_symbol ?? \"\",\n languages: countryMeta?.translations ? Object.values(countryMeta.translations)[0] ?? \"\" : \"\",\n emoji: countryMeta?.emoji ?? \"\",\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n timezone: countryMeta?.timezones?.[0]?.zoneName ?? \"\",\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n utc_offset: countryMeta?.timezones?.[0]?.gmtOffsetName ?? \"\",\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n timeZoneName: countryMeta?.timezones?.[0]?.tzName ?? \"\",\n tld: countryMeta?.tld ?? \"\",\n nationality: countryMeta?.nationality ?? \"\",\n subregion: countryMeta?.subregion ?? \"\"\n };\n\n results.push(JSON.stringify(record));\n }\n\n logger.info(`Writing ${String(results.length)} enriched entries to temporary JSON...`);\n fs.writeFileSync(tempGeoJson, results.join('\\n'), 'utf-8');\n\n logger.start('Compiling MMDB with mmdbctl...');\n\n const cmd = `${mmdbPath} import --in ${tempGeoJson} --out ${output}`;\n const convert = await run(cmd);\n \n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled Country MMDB to ${output}\\n`);\n\n } catch (error) {\n logger.error('\\nERROR during processing:', error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempGeoJson)) {\n fs.unlinkSync(tempGeoJson);\n }\n }\n}\n","import fs from 'node:fs';\nimport { run } from \"../utils/run.js\";\nimport { createRegExp, exactly, charNotIn, anyOf, digit, oneOrMore } from 'magic-regexp';\nimport path from 'node:path';\nimport consola from 'consola';\n\nconst logger = consola.withTag('[PROXY]');\n\nexport async function getListOfProxies(outputPath: string, mmdbPath: string) {\n logger.log(\"\\nFetching initial Proxy list from Awesome-lists...\");\n const output = path.resolve(outputPath, 'proxy.mmdb');\n const tempProxyJson = path.resolve(outputPath, 'temp_proxy_data.json');\n\n const seenIps = new Set<string>();\n const results: string[] = [];\n const urls = ['https://raw.githubusercontent.com/mthcht/awesome-lists/refs/heads/main/Lists/PROXY/ALL_PROXY_Lists.csv', 'https://raw.githubusercontent.com/firehol/blocklist-ipsets/refs/heads/master/firehol_proxies.netset'];\n \n const ipv4Regex = createRegExp(\n exactly(oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit))\n .and(exactly('/', oneOrMore(digit)).optionally()) \n .at.lineStart().at.lineEnd()\n );\n\n try {\n const resAwesome = await fetch(urls[0]);\n if (!resAwesome.ok) throw new Error(`ERROR: Failed to fetch awesome list: ${resAwesome.statusText}`);\n\n const csvText = await resAwesome.text();\n const lines = csvText.split('\\n').slice(1);\n\n const nonQuotes = charNotIn('\"').times.any();\n const quotePair = nonQuotes.and(exactly('\"')).times(2);\n const splitAwesomeListRegex = createRegExp(\n exactly(',').before(quotePair.times.any().and(nonQuotes).at.lineEnd())\n );\n\n const stripAwesomeListRegex = createRegExp(\n anyOf(exactly('PROXY_ALL_'), exactly('_list.csv'), exactly('\"')), \n ['g', 'i']\n );\n\n\n\n for (const line of lines) {\n if (!line.trim()) continue;\n \n const [dest_ip, dest_port, metadata_comment] = line.split(splitAwesomeListRegex);\n\n if (!dest_ip || !ipv4Regex.test(dest_ip)) continue;\n \n if (seenIps.has(dest_ip)) continue;\n seenIps.add(dest_ip);\n\n const cleanComment = metadata_comment.replace(stripAwesomeListRegex, '').trim();\n\n const record = {\n range: `${dest_ip}/32`, \n port: dest_port,\n comment: cleanComment\n };\n \n results.push(JSON.stringify(record));\n }\n \n logger.success(`SUCCESS: Finished Awesome-list. Discovered ${String(results.length)} unique IPs.`);\n logger.log('Fetching secondary data from FireHOL proxy list...');\n const resFirehol = await fetch(urls[1]);\n\n if (!resFirehol.ok) throw new Error(`ERROR: Failed to fetch FireHOL list: ${resFirehol.statusText}`);\n const textFirehol = await resFirehol.text();\n const fireholLines = textFirehol.split('\\n');\n const commentRegex = createRegExp(exactly('#').at.lineStart());\n let fireholCount = 0;\n\n\n for (const line of fireholLines) {\n const trimmed = line.trim();\n if (!trimmed || commentRegex.test(trimmed)) continue;\n\n const ip = trimmed;\n \n if (!ipv4Regex.test(ip)) continue;\n \n if (seenIps.has(ip)) continue;\n seenIps.add(ip);\n\n const record = {\n range: ip,\n port: 'unknown',\n comment: `Ip from Firehol`\n };\n\n results.push(JSON.stringify(record));\n fireholCount++;\n }\n\n logger.success(`SUCCESS: Finished FireHOL. Added ${String(fireholCount)} NEW unique proxies. Total unique: ${String(results.length)}`);\n\n if (results.length > 0) {\n logger.log('SAMPLE:', results[0]);\n }\n\n logger.log(`Writing ${String(results.length)} unique proxies to temporary JSON...`);\n fs.writeFileSync(tempProxyJson, results.join('\\n'), 'utf-8');\n logger.log('Compiling MMDB with mmdbctl...');\n\n const cmd = `${mmdbPath} import --in ${tempProxyJson} --out ${output}`;\n const convert = await run(cmd);\n if (convert.stdout) logger.log(`mmdbctl: ${convert.stdout.toString().trim()}`);\n logger.success(`COMPLETED: Successfully compiled Proxy MMDB to ${output}\\n`);\n\n\n } catch (error) {\n logger.error('\\nERROR during processing:', error);\n process.exit(1);\n } finally {\n if (fs.existsSync(tempProxyJson)) {\n fs.unlinkSync(tempProxyJson);\n }\n } \n}\n","import fs from 'node:fs';\nimport { run } from \"../utils/run.js\";\nimport { createRegExp, exactly, digit, oneOrMore } from 'magic-regexp';\nimport path from 'node:path';\nimport consola from 'consola';\n\n\n\n\nconst THREAT_CONFIG = {\n firehol_anonymous: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_anonymous.netset',\n firehol_l1: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level1.netset',\n firehol_l2: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level2.netset',\n firehol_l3: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level3.netset',\n firehol_l4: 'https://github.com/firehol/blocklist-ipsets/raw/refs/heads/master/firehol_level4.netset',\n} as const;\n\n\nconst logger = consola.withTag('[THREATS]');\n\nexport async function getThreatLists(outputPath: string, mmdbPath: string, selectedSources?: string[] | boolean) {\n\n const maintainerUrl = ' Maintainer: http://iplists.firehol.org/';\n const ipv4Regex = createRegExp(\n exactly(oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit), '.', oneOrMore(digit))\n .and(exactly('/', oneOrMore(digit)).optionally()) \n .at.lineStart().at.lineEnd()\n );\n const commentRegex = createRegExp(exactly('#').at.lineStart());\n let tasks: { id: string, url: string }[] = [];\n\n if (Array.isArray(selectedSources)) {\n tasks = Object.entries(THREAT_CONFIG)\n .filter(([id]) => selectedSources.includes(id))\n .map(([id, url]) => ({ id, url }));\n } else if (Boolean(selectedSources)) {\n tasks = Object.entries(THREAT_CONFIG).map(([id, url]) => ({ id, url }));\n }\n \n if (tasks.length === 0) {\n logger.info('No valid FireHOL data sources selected. Skipping.');\n return;\n }\n try {\n logger.start(`Initializing fetch for ${String(tasks.length)} FireHOL stream(s)...`);\n\n const promises = tasks.map(async (task) => {\n const res = await fetch(task.url);\n return { id: task.id, res };\n });\n\n const resultsSettled = await Promise.allSettled(promises);\n logger.success(`SUCCESS: Fetched ${String(resultsSettled.length)} data streams from FireHOL.`);\n\n let ipsCount = 0;\n\n\n for (const result of resultsSettled) {\n\n if (result.status === 'rejected') {\n logger.error(`Promise rejected:`, result.reason);\n continue;\n }\n const { id, res } = result.value;\n const finalMsg = `${id} ${maintainerUrl}`;\n const results: string[] = [];\n logger.info(`Processing stream: ${id}...`);\n \n if (!res.ok) {\n logger.error(`Failed fetching ${id}: ${res.statusText}`);\n continue;\n }\n\n const rawTextData = await res.text();\n const lines = rawTextData.split('\\n');\n\n for (const line of lines) {\n const trimmed = line.trim();\n if (!trimmed || commentRegex.test(trimmed)) continue;\n\n const ip = trimmed;\n if (!ipv4Regex.test(ip)) continue;\n\n const record = {\n range: ip,\n comment: finalMsg\n };\n\n ipsCount++;\n results.push(JSON.stringify(record));\n }\n\n logger.info(`${id} summary:\\n\n → IPs Discovered: ${String(results.length)}\\n\n → Rolling Total: ${String(ipsCount)}\\n`);\n \n if (results.length > 0) {\n logger.info(`SAMPLE: ${results[0]}`);\n logger.info(`Writing entries to temporary JSON: temp_${id}.json`);\n const jsonName = path.resolve(outputPath, `temp_${id}.json`);\n const output = path.resolve(outputPath, `${id}.mmdb`);\n\n fs.writeFileSync(jsonName, results.join('\\n'), 'utf-8');\n console.log(`Compiling MMDB with mmdbctl to ${output}...`);\n\n const cmd = `${mmdbPath} import --in ${jsonName} --out ${output}`;\n const convert = await run(cmd);\n if (convert.stdout) logger.box(`mmdbctl: ${convert.stdout.toString().trim()}`);\n\n if (fs.existsSync(jsonName)) {\n fs.unlinkSync(jsonName);\n }\n logger.success(`SUCCESS: Compiled ${id}.mmdb\\n`);\n } else {\n logger.warn(`WARNING: No valid IPs found for ${id}. Skipping.\\n`);\n }\n }\n \n logger.success(\"COMPLETED: All threat intelligence sources processed successfully.\\n\");\n\n } catch (error) {\n logger.error('\\nFATAL ERROR during processing:', error);\n process.exit(1);\n }\n}","// This file contains a list of URLs for various web crawlers and bots.\n// The URLs are used to fetch the IP ranges of the respective crawlers and bots.\n// Please note that the list is not exhaustive and may not include all available crawlers and bots.\n// feel free to add more URLs as needed.\n\nimport { ProvidersLists } from \"../../types/botsIps.js\";\n\nexport const urls: ProvidersLists[] = [\n {\n name: 'google',\n type: 'JSON',\n urls: [\n //DOCS : https://developers.google.com/search/docs/crawling-indexing/verifying-googlebot\n 'https://developers.google.com/static/search/apis/ipranges/googlebot.json', \n 'https://developers.google.com/static/search/apis/ipranges/special-crawlers.json', \n 'https://developers.google.com/static/search/apis/ipranges/user-triggered-fetchers.json', \n 'https://developers.google.com/static/search/apis/ipranges/user-triggered-fetchers-google.json',\n 'https://www.gstatic.com/ipranges/goog.json',\n ]\n },\n { \n name: 'bing',\n type: 'JSON',\n urls: [\n // DOCS : https://www.bing.com/webmasters/help/how-to-verify-bingbot-3905dc26\n 'https://www.bing.com/toolbox/bingbot.json',\n ]\n },\n {\n name: 'openai',\n type: 'JSON',\n urls: [\n // DOCS : https://platform.openai.com/docs/bots/\n 'https://openai.com/gptbot.json',\n 'https://openai.com/chatgpt-user.json',\n 'https://openai.com/searchbot.json',\n ]\n },\n {\n name: 'apple',\n type: 'JSON',\n urls: [\n // DOCS : https://support.apple.com/en-us/119829\n 'https://search.developer.apple.com/applebot.json',\n ]\n },\n {\n name: 'ahrefs',\n type: 'JSON',\n urls: [\n // DOCS : https://help.ahrefs.com/en/articles/78658-what-is-the-list-of-your-ip-ranges\n 'https://api.ahrefs.com/v3/public/crawler-ip-ranges'\n ]\n },\n {\n name: 'duckDuckGo',\n type: 'HTML',\n urls: [\n // DOCS : https://duckduckgo.com/duckduckgo-help-pages/results/duckassistbot\n // DOCS : https://duckduckgo.com/duckduckgo-help-pages/results/duckduckbot\n 'https://duckduckgo.com/duckduckgo-help-pages/results/duckassistbot',\n 'https://duckduckgo.com/duckduckgo-help-pages/results/duckduckbot'\n ]\n },\n {\n name: 'commonCrawler',\n type: 'HTML',\n urls: [\n // DOCS : https://commoncrawl.org/faq\n 'https://commoncrawl.org/faq',\n ]\n },\n {\n name: 'xAndTwitter',\n type: 'HTML',\n urls: [\n // DOCS : https://developer.x.com/en/docs/x-for-websites/cards/guides/troubleshooting-cards\n 'https://developer.x.com/en/docs/x-for-websites/cards/guides/troubleshooting-cards'\n ]\n },\n {\n name: 'facebook',\n type: 'CSV',\n urls: [\n // DOCS : https://developers.facebook.com/docs/sharing/webmasters/web-crawlers/\n 'https://www.facebook.com/peering/geofeed'\n ]\n },\n {\n name: 'pinterest',\n type: 'HTML',\n urls: [\n // DOCS : https://help.pinterest.com/en/business/article/pinterestbot\n 'https://help.pinterest.com/en/business/article/pinterestbot'\n ]\n },\n {\n name: 'telegram',\n type: 'HTML',\n urls: [\n // DOCS : https://core.telegram.org/bots/webhooks\n 'https://core.telegram.org/bots/webhooks'\n ]\n },\n {\n name: 'semrush',\n type: 'HTML',\n urls: [\n // DOCS : https://www.semrush.com/kb/1149-issues-with-crawling-a-domain\n 'https://www.semrush.com/kb/1149-issues-with-crawling-a-domain'\n ]\n }\n];\n\n\n","import ipaddr from 'ipaddr.js';\nimport { IpRange, IpAddress } from 'cidr-calc';\n\n\nexport const normalizeIp = (ip: string): string => {\n if (!ip) throw new Error('Empty IP string');\n\n \n if (ip.includes('/')) {\n const [baseIp, mask] = ip.split('/');\n if (!ipaddr.isValidCIDR(ip)) throw new Error('Invalid CIDR');\n return `${ipaddr.parse(baseIp).toString()}/${mask}`;\n }\n\n if (!ipaddr.isValid(ip)) throw new Error('Invalid Ip address');\n return ipaddr.parse(ip).toString();\n};\n\nexport const normalizeExtractedMatch = (ip1: string, ip2?: string, mask?: string): string | string[] => {\n const cleanIp1 = normalizeIp(ip1);\n\n if (ip2 && !mask) {\n const cleanIp2 = normalizeIp(ip2);\n \n const ipRange = new IpRange(IpAddress.of(cleanIp1), IpAddress.of(cleanIp2));\n return ipRange.toCidrs().map(c => c.toString());\n }\n \n if (mask) {\n const cidr = `${cleanIp1}/${mask}`;\n if (!ipaddr.isValidCIDR(cidr)) throw new Error('Invalid Extracted CIDR');\n return cidr;\n }\n\n return cleanIp1;\n};","import consola from 'consola';\nimport { BotIpData } from '../../../types/botsIps.js';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nexport async function jsonScrapper(name: string, urls: string[]): Promise<(BotIpData | string)[]> {\n logger.start(`Processing provider: ${name}...`);\n\n const promises = urls.map(async (url) => {\n const res = await fetch(url);\n if (!res.ok) throw new Error(`fetch ${name} ${url} -> ${String(res.status)}`); \n const data = await res.json() as BotIpData | BotIpData[];\n\n return Array.isArray(data) ? data : [data];\n });\n \n const results = await Promise.all(promises);\n return results.flat();\n}","import consola from 'consola';\nimport { run } from '../../../utils/run.js';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nlet isCurlVerified = false;\nexport async function fetchWithCurl(url: string): Promise<string> {\n if (!isCurlVerified) {\n try {\n await run('command -v curl', { silent: true });\n isCurlVerified = true;\n } catch {\n logger.error('curl needed to be installed to run goodBots scrapper in order to avoid being blocked.');\n throw new Error('Fatal: curl is required for fallback scraping.');\n }\n }\n\n try {\n const { stdout } = await run(`curl -sL ${url}`, { silent: true });\n return typeof stdout === 'string' ? stdout : stdout.toString('utf-8');\n } catch (err) {\n logger.warn(`curl failed for ${url}: ${String(err)}`);\n return '';\n }\n}\n\nexport async function downloadHtml(url: string): Promise<string> {\n try {\n const response = await fetch(url, {\n headers: {\n 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36',\n 'Accept': 'text/html,text/csv,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8'\n }\n });\n\n if (!response.ok) {\n throw new Error(`Failed to fetch ${url}: ${response.statusText} - ${String(response.status)}`);\n }\n\n const html = await response.text();\n return html;\n } catch (err) {\n logger.warn(`Fetch failed for ${url}:\\n ${String(err)},\\n Using curl instead...`);\n return await fetchWithCurl(url);\n }\n}\n","import { createRegExp, exactly, anyOf, charIn, digit, letter } from 'magic-regexp';\n\nconst octet = anyOf(\n exactly('25', charIn('012345')),\n exactly('2', charIn('01234'), digit),\n exactly(charIn('01'), digit, digit),\n exactly(digit, digit),\n digit\n);\n\nconst ipv4Base = anyOf(exactly(octet, '.', octet, '.', octet, '.', octet));\nconst hexWord = anyOf(digit, charIn('abcdefABCDEF')).times.between(1, 4);\n\n\nconst ipv6Base = anyOf( \n exactly(hexWord, ':').times(7).and(hexWord),\n exactly( exactly(hexWord, ':').times.between(3, 7), ':' ),\n exactly(hexWord, ':').times.between(1, 5).and('::').and(exactly(hexWord, ':').times.any()).and(hexWord),\n exactly('::').and(anyOf(hexWord, ipv4Base, exactly(hexWord, ':').times.any().and(hexWord))),\n exactly(hexWord, ':').times.between(1, 7).and(':')\n);\n\n\nexport const ipBase = anyOf(ipv4Base, ipv6Base).notAfter(anyOf(letter, digit, ':'));\n\nexport const botIpExtractor = createRegExp(\n ipBase.groupedAs('ip1'),\n anyOf(\n // CIDR\n exactly(\n '/', \n digit.times.between(1, 3).groupedAs('mask')\n ),\n \n // ranges\n exactly(\n anyOf(' to ', ' - ', '-', ' and '),\n ipBase.groupedAs('ip2')\n )\n ).optionally(),\n \n ['g', 'i'] \n);","import { downloadHtml } from './fetchers.js';\nimport { BotIpData } from '../../../types/botsIps.js';\nimport { normalizeExtractedMatch } from '../ipNormalizers.js';\nimport { botIpExtractor } from '../regex.js';\nimport consola from 'consola';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nexport async function htmlScrapper(urls: string[], name: string): Promise<(BotIpData | string)[]> {\n logger.start(`Processing provider: ${name}...`);\n const texts = (await Promise.all(urls.map(downloadHtml)));\n\n const allMatches = texts.flatMap((txt: string) => {\n const matches = Array.from(txt.matchAll(botIpExtractor));\n \n return matches.flatMap((m) => {\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (!m.groups?.ip1) return [];\n \n try {\n const normalized = normalizeExtractedMatch(\n m.groups.ip1, \n m.groups.ip2, \n m.groups.mask\n );\n \n return Array.isArray(normalized) ? normalized : [normalized];\n } catch (err) {\n logger.warn(`Failed to normalize extracted IP match from ${name}:`, m[0], `Message: ${String(err)}`);\n return [];\n }\n });\n });\n \n return [{\n creationTime: new Date().toISOString(),\n prefixes: Array.from(new Set(allMatches)).map((ip: string) => ({ ipv4Prefix: ip }))\n }];\n}","import path from 'path';\nimport fs from 'node:fs';\nimport consola from 'consola';\nimport { urls } from './urls.js';\nimport { BotIpsLists, BotIpPrefix } from '../../types/botsIps.js';\nimport { run } from '../../utils/run.js';\nimport { normalizeIp } from './ipNormalizers.js';\nimport { jsonScrapper } from './scrappers/jsonScrapper.js';\nimport { htmlScrapper } from './scrappers/htmlScrapper.js';\nimport {ProvidersLists} from '../../types/botsIps.js';\n\nconst logger = consola.withTag('GOOD-BOT-CRAWLER');\n\nexport async function getCrawlersIps(outputPath: string, mmdbPath: string, customUrls?: ProvidersLists[]) {\n\n logger.start('Starting Good Bots IP scraper...');\n const databasePath = path.resolve(outputPath, './goodBots.mmdb');\n const providers = [...urls, ...(customUrls ?? [])];\n\n \n if (customUrls && customUrls.length > 0) {\n customUrls.forEach((prov) => {\n // eslint-disable-next-line @typescript-eslint/no-unnecessary-condition\n if (!prov.name || !prov.type || !prov.urls) {\n throw new Error(`Provider ${prov.name || 'unknown'} is missing required fields.`);\n }\n });\n } \n\n const ipDb: BotIpsLists = {};\n\n\n for (const provider of providers) {\n if (provider.type === 'JSON') {\n ipDb[provider.name] = await jsonScrapper(provider.name, provider.urls);\n } else {\n ipDb[provider.name] = await htmlScrapper(provider.urls, provider.name);\n }\n }\n\n consola.info(`Building data...`);\n\n const mmdbRecords = Object.entries(ipDb).flatMap(([provider, snapshots]) => {\n return snapshots.flatMap((snap) => {\n if (typeof snap === 'string') {\n try {\n return [{\n range: normalizeIp(snap),\n provider: provider,\n syncToken: 'unknown',\n creationTime: new Date().toISOString()\n }];\n } catch (err) {\n logger.warn(`Invalid ip format skipping: ${snap} -> ${String(err)}`);\n return null;\n }\n }\n return snap.prefixes.map((p: BotIpPrefix) => {\n const rawIp = p.ipv4Prefix ?? p.ipv6Prefix ?? '';\n if (!rawIp) return null;\n\n try {\n return {\n range: normalizeIp(rawIp),\n provider: provider,\n syncToken: snap.syncToken,\n creationTime: snap.creationTime\n };\n } catch (err) {\n logger.warn(`Invalid ip format skipping from prefix: ${rawIp} -> ${String(err)}`);\n return null;\n }\n }).filter(Boolean);\n });\n });\n\n logger.info(`Total records to import: ${String(mmdbRecords.length)}`);\n\n const tempJsonPath = path.resolve(outputPath, 'temp_bots.json');\n\n const jsonLines = mmdbRecords.map(r => JSON.stringify(r)).join('\\n');\n\n fs.writeFileSync(tempJsonPath, jsonLines, 'utf-8');\n\n try {\n logger.info('Compiling MMDB...');\n const cmd = `${mmdbPath} import --in ${tempJsonPath} --out ${databasePath}`;\n await run(cmd);\n logger.success(`Successfully generated ${databasePath}`);\n } catch (err) {\n logger.error(`Failed to compile MMDB: ${String(err)}`);\n throw err;\n } finally {\n if (fs.existsSync(tempJsonPath)) {\n fs.unlinkSync(tempJsonPath);\n }\n }\n}","import { getBGPAndASN } from \"./bgp.js\";\nimport { buildCitiesData } from \"./city.js\";\nimport { getTorLists } from \"./tor.js\";\nimport { getGeoDatas } from \"./geo.js\";\nimport { getListOfProxies } from \"./proxy.js\";\nimport { getThreatLists } from \"./threats.js\";\nimport consola from \"consola\";\nimport { getCrawlersIps } from \"./goodBotsScrapper/scrapper.js\";\n\nconst logger = consola.withTag('Shield Base');\n\nexport async function generateData(outputPath: string, userAgent: string, selectedSources: string[] | boolean, mmdbPath: string) {\n logger.box(\"\\n=========================================\\n\" +\n \" === Starting data generation pipeline === \" +\n \"\\n=========================================\\n\");\n \n try {\n\n const results = await Promise.allSettled([\n getBGPAndASN(userAgent, outputPath, mmdbPath),\n buildCitiesData(outputPath, mmdbPath),\n getTorLists(outputPath, mmdbPath),\n getGeoDatas(outputPath, mmdbPath),\n getListOfProxies(outputPath, mmdbPath),\n getThreatLists(outputPath, mmdbPath, selectedSources),\n getCrawlersIps(outputPath, mmdbPath)\n ]);\n \n results.forEach((result, index) => {\n if (result.status === 'rejected') {\n logger.error(`Script cluster [${String(index)}] failed:`, String(result.reason));\n }\n });\n logger.info(\"\\n====================================\\n\" +\n \"Pipeline execution finished.\" +\n \"\\n====================================\\n\");\n } catch (error) {\n logger.error(\"\\n====================================\\n\" +\n `Fatal error in pipeline: ${String(error)}` +\n \"\\n====================================\\n\");\n }\n}","/* eslint-disable @typescript-eslint/no-unnecessary-condition */\nimport consola from 'consola';\nimport path from 'node:path';\nimport os from 'node:os';\nimport { readFile } from 'node:fs/promises';\nimport { existsSync } from 'node:fs';\nimport { InputCache } from '../types/input.js';\nimport { \n getBGPAndASN,\n buildCitiesData,\n generateData as executeAll,\n getGeoDatas,\n getListOfProxies,\n getThreatLists,\n getTorLists\n} from '../scripts/index.js';\n\nconst cacheOutput = path.join(os.homedir(), '.shield-base', '.cache.json');\n\nexport async function restartData(outputPath: string, all: boolean): Promise<void> {\n \n if (!existsSync(cacheOutput)) { \n consola.error('No cache found. Cannot restart. Please run a standard compilation first.');\n process.exit(1);\n }\n \n const cachedFile = await readFile(cacheOutput, 'utf-8');\n const cache = JSON.parse(cachedFile) as InputCache;\n \n if (!cache.selectedDataTypes || cache.selectedDataTypes.length === 0) {\n consola.warn('Cache is empty. No data sources to restart.');\n return;\n }\n\n if (all) {\n consola.info('Restarting ALL data sources...');\n await executeAll(outputPath, cache.useragent, true, cache.mmdbctlPath);\n consola.success('✨ All data successfully refreshed!');\n return;\n }\n\n consola.info(`Restarting data compilation from cache: ${cache.selectedDataTypes.join(', ')}`);\n\n const fireholSources = cache.selectedDataTypes.filter(s => s.startsWith('firehol_') || s === 'anonymous');\n const standardSources = cache.selectedDataTypes.filter(s => !s.startsWith('firehol_') && s !== 'anonymous');\n const executionRestartQueue: { name: string, task: () => Promise<void> }[] = [];\n\n if (standardSources.includes('BGP')) {\n executionRestartQueue.push({ name: 'BGP & ASN', task: () => getBGPAndASN(cache.useragent || '', outputPath, cache.mmdbctlPath) });\n }\n\n if (standardSources.includes('City')) {\n executionRestartQueue.push({\n name: 'City',\n task: () => buildCitiesData(cache.outPutPath, cache.mmdbctlPath),\n });\n }\n if (standardSources.includes('Geography')) {\n executionRestartQueue.push({\n name: 'Geography',\n task: () => getGeoDatas(cache.outPutPath, cache.mmdbctlPath)\n });\n }\n\n if (standardSources.includes('Proxy')) {\n executionRestartQueue.push({\n name: 'Proxy',\n task: () => getListOfProxies(cache.outPutPath, cache.mmdbctlPath)\n });\n }\n\n if (standardSources.includes('Tor')) {\n executionRestartQueue.push({\n name: 'Tor',\n task: () => getTorLists(cache.outPutPath, cache.mmdbctlPath)\n });\n }\n \n if (fireholSources.length > 0) {\n executionRestartQueue.push({\n name: 'Threats',\n task: () => getThreatLists(cache.outPutPath, cache.mmdbctlPath, fireholSources)\n });\n }\n consola.start(`Running ${String(executionRestartQueue.length)} restart jobs...`);\n const results = await Promise.allSettled(executionRestartQueue.map(q => q.task()));\n \n results.forEach((res, index) => {\n if (res.status === 'rejected') {\n consola.error(`[${executionRestartQueue[index].name}] Failed:`, res.reason);\n }\n });\n\n consola.success('✨ Cached data successfully refreshed!');\n return;\n}"]}
|