s3db.js 19.2.2-next.ab202d14 → 19.2.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -2,7 +2,7 @@
2
2
  "version": "1.0",
3
3
  "model": "BGESmallENV15",
4
4
  "dimensions": 384,
5
- "generatedAt": "2026-01-07T22:04:56.478Z",
5
+ "generatedAt": "2026-01-13T14:50:38.155Z",
6
6
  "documents": [
7
7
  {
8
8
  "id": "plugin-0",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "s3db.js",
3
- "version": "19.2.2-next.ab202d14",
3
+ "version": "19.2.3",
4
4
  "description": "Use AWS S3, the world's most reliable document storage, as a database with this ORM.",
5
5
  "main": "dist/s3db.cjs",
6
6
  "module": "dist/s3db.es.js",
@@ -74,13 +74,6 @@ export interface DnsdumpsterFeatures {
74
74
  enabled: boolean;
75
75
  }
76
76
 
77
- export interface MassdnsFeatures {
78
- enabled: boolean;
79
- wordlist?: string | null;
80
- rate?: number;
81
- maxSubdomains?: number;
82
- }
83
-
84
77
  export interface ReconFeatures {
85
78
  dns: boolean;
86
79
  certificate: boolean;
@@ -99,7 +92,6 @@ export interface ReconFeatures {
99
92
  secrets: SecretsFeatures;
100
93
  asn: AsnFeatures;
101
94
  dnsdumpster: DnsdumpsterFeatures;
102
- massdns: MassdnsFeatures;
103
95
  }
104
96
 
105
97
  export interface RateLimitConfig {
@@ -227,12 +219,6 @@ export const DEFAULT_FEATURES: ReconFeatures = {
227
219
  },
228
220
  dnsdumpster: {
229
221
  enabled: true
230
- },
231
- massdns: {
232
- enabled: false,
233
- wordlist: null,
234
- rate: 1000,
235
- maxSubdomains: 1000
236
222
  }
237
223
  };
238
224
 
@@ -256,7 +242,6 @@ export const BEHAVIOR_PRESETS: Record<string, BehaviorPreset> = {
256
242
  secrets: { enabled: false },
257
243
  asn: { enabled: true },
258
244
  dnsdumpster: { enabled: true },
259
- massdns: { enabled: false, wordlist: null, rate: 1000, maxSubdomains: 1000 }
260
245
  },
261
246
  concurrency: 2,
262
247
  timeout: { default: 30000 },
@@ -281,7 +266,6 @@ export const BEHAVIOR_PRESETS: Record<string, BehaviorPreset> = {
281
266
  secrets: { enabled: false },
282
267
  asn: { enabled: true },
283
268
  dnsdumpster: { enabled: true },
284
- massdns: { enabled: false, wordlist: null, rate: 1000, maxSubdomains: 1000 }
285
269
  },
286
270
  concurrency: 1,
287
271
  timeout: { default: 60000 },
@@ -306,7 +290,6 @@ export const BEHAVIOR_PRESETS: Record<string, BehaviorPreset> = {
306
290
  secrets: { enabled: false },
307
291
  asn: { enabled: true },
308
292
  dnsdumpster: { enabled: true },
309
- massdns: { enabled: true, wordlist: null, rate: 5000, maxSubdomains: 5000 }
310
293
  },
311
294
  concurrency: 8,
312
295
  timeout: { default: 120000 },
@@ -35,7 +35,6 @@ import { WhoisStage } from './stages/whois-stage.js';
35
35
  import { SecretsStage } from './stages/secrets-stage.js';
36
36
  import { ASNStage } from './stages/asn-stage.js';
37
37
  import { DNSDumpsterStage } from './stages/dnsdumpster-stage.js';
38
- import { MassDNSStage } from './stages/massdns-stage.js';
39
38
  import { GoogleDorksStage } from './stages/google-dorks-stage.js';
40
39
 
41
40
  // Concerns
@@ -78,7 +77,6 @@ export interface ScanFeatures {
78
77
  secrets?: boolean | Record<string, any>;
79
78
  asn?: boolean | Record<string, any>;
80
79
  dnsdumpster?: boolean | Record<string, any>;
81
- massdns?: boolean | Record<string, any>;
82
80
  googleDorks?: boolean | Record<string, any>;
83
81
  }
84
82
 
@@ -157,7 +155,6 @@ interface Stages {
157
155
  secrets: SecretsStage;
158
156
  asn: ASNStage;
159
157
  dnsdumpster: DNSDumpsterStage;
160
- massdns: MassDNSStage;
161
158
  googleDorks: GoogleDorksStage;
162
159
  }
163
160
 
@@ -264,7 +261,6 @@ export class ReconPlugin extends Plugin {
264
261
  secrets: new SecretsStage(this as any),
265
262
  asn: new ASNStage(this as any),
266
263
  dnsdumpster: new DNSDumpsterStage(this as any),
267
- massdns: new MassDNSStage(this as any),
268
264
  googleDorks: new GoogleDorksStage(this as any)
269
265
  };
270
266
  }
@@ -400,10 +396,6 @@ export class ReconPlugin extends Plugin {
400
396
  results.dnsdumpster = await this.stages.dnsdumpster.execute(normalizedTarget, scanConfig.dnsdumpster as any);
401
397
  }
402
398
 
403
- if (scanConfig.massdns !== false) {
404
- results.massdns = await this.stages.massdns.execute(normalizedTarget, scanConfig.massdns as any);
405
- }
406
-
407
399
  if (scanConfig.googleDorks !== false) {
408
400
  results.googleDorks = await this.stages.googleDorks.execute(normalizedTarget, scanConfig.googleDorks as any);
409
401
  }
@@ -68,14 +68,6 @@ export type {
68
68
  LatencyResult
69
69
  } from './latency-stage.js';
70
70
 
71
- export { MassDNSStage } from './massdns-stage.js';
72
- export type {
73
- MassDNSFeatureConfig,
74
- ResolvedSubdomain,
75
- MassDNSData,
76
- MassDNSResult
77
- } from './massdns-stage.js';
78
-
79
71
  export { OsintStage } from './osint-stage.js';
80
72
  export type {
81
73
  OsintFeatureConfig,
@@ -1,209 +0,0 @@
1
- /**
2
- * MassDNSStage
3
- *
4
- * High-performance DNS resolution using RedBlue:
5
- * - Mass subdomain resolution
6
- * - Wordlist-based brute force
7
- * - Fast parallel queries
8
- */
9
-
10
- import type { CommandRunner } from '../concerns/command-runner.js';
11
-
12
- export interface ReconPlugin {
13
- commandRunner: CommandRunner;
14
- config: {
15
- massdns?: {
16
- wordlist?: string;
17
- };
18
- };
19
- }
20
-
21
- export interface Target {
22
- host: string;
23
- protocol?: string;
24
- port?: number;
25
- path?: string;
26
- }
27
-
28
- export interface MassDNSFeatureConfig {
29
- timeout?: number;
30
- wordlist?: string;
31
- rate?: number;
32
- resolvers?: string;
33
- }
34
-
35
- export interface ResolvedSubdomain {
36
- subdomain: string;
37
- ip: string | null;
38
- ips?: string[] | null;
39
- cname?: string | null;
40
- }
41
-
42
- export interface MassDNSData {
43
- subdomains: ResolvedSubdomain[];
44
- resolvedCount: number;
45
- totalAttempts: number | null;
46
- }
47
-
48
- export interface MassDNSResult {
49
- status: 'ok' | 'empty' | 'error' | 'unavailable';
50
- message?: string;
51
- host: string;
52
- subdomains: ResolvedSubdomain[];
53
- resolvedCount: number;
54
- totalAttempts?: number | null;
55
- metadata?: Record<string, any>;
56
- }
57
-
58
- export class MassDNSStage {
59
- private plugin: ReconPlugin;
60
- private commandRunner: CommandRunner;
61
- private config: ReconPlugin['config'];
62
-
63
- constructor(plugin: ReconPlugin) {
64
- this.plugin = plugin;
65
- this.commandRunner = plugin.commandRunner;
66
- this.config = plugin.config;
67
- }
68
-
69
- async execute(target: Target, featureConfig: MassDNSFeatureConfig = {}): Promise<MassDNSResult> {
70
- const wordlist = featureConfig.wordlist || this.config.massdns?.wordlist;
71
-
72
- if (!wordlist) {
73
- return {
74
- status: 'error',
75
- message: 'No wordlist provided for mass DNS resolution',
76
- host: target.host,
77
- subdomains: [],
78
- resolvedCount: 0
79
- };
80
- }
81
-
82
- const flags: string[] = ['--wordlist', wordlist];
83
-
84
- if (featureConfig.rate) {
85
- flags.push('--rate', String(featureConfig.rate));
86
- }
87
-
88
- if (featureConfig.resolvers) {
89
- flags.push('--resolvers', featureConfig.resolvers);
90
- }
91
-
92
- const result = await this.commandRunner.runRedBlue(
93
- 'dns',
94
- 'record',
95
- 'bruteforce',
96
- target.host,
97
- {
98
- timeout: featureConfig.timeout || 120000,
99
- flags
100
- }
101
- );
102
-
103
- if (result.status === 'unavailable') {
104
- return {
105
- status: 'unavailable',
106
- message: 'RedBlue (rb) is not available',
107
- host: target.host,
108
- subdomains: [],
109
- resolvedCount: 0,
110
- metadata: result.metadata
111
- };
112
- }
113
-
114
- if (result.status === 'error') {
115
- return {
116
- status: 'error',
117
- message: result.error,
118
- host: target.host,
119
- subdomains: [],
120
- resolvedCount: 0,
121
- metadata: result.metadata
122
- };
123
- }
124
-
125
- const resolved = this._normalizeResolved(result.data, target.host);
126
-
127
- return {
128
- status: resolved.subdomains.length > 0 ? 'ok' : 'empty',
129
- host: target.host,
130
- ...resolved,
131
- metadata: result.metadata
132
- };
133
- }
134
-
135
- private _normalizeResolved(data: any, baseDomain: string): MassDNSData {
136
- if (!data || typeof data !== 'object') {
137
- return { subdomains: [], resolvedCount: 0, totalAttempts: null };
138
- }
139
-
140
- if (data.raw) {
141
- return this._parseRawResolved(data.raw, baseDomain);
142
- }
143
-
144
- const subdomains: ResolvedSubdomain[] = [];
145
-
146
- if (Array.isArray(data.subdomains)) {
147
- subdomains.push(...data.subdomains.map((s: any) => this._normalizeSubdomain(s)).filter(Boolean));
148
- } else if (Array.isArray(data.results)) {
149
- subdomains.push(...data.results.map((s: any) => this._normalizeSubdomain(s)).filter(Boolean));
150
- } else if (Array.isArray(data.resolved)) {
151
- subdomains.push(...data.resolved.map((s: any) => this._normalizeSubdomain(s)).filter(Boolean));
152
- } else if (Array.isArray(data)) {
153
- subdomains.push(...data.map((s: any) => this._normalizeSubdomain(s)).filter((s): s is ResolvedSubdomain => s !== null));
154
- }
155
-
156
- return {
157
- subdomains: subdomains.filter((s): s is ResolvedSubdomain => s !== null),
158
- resolvedCount: subdomains.length,
159
- totalAttempts: data.totalAttempts || data.attempts || null
160
- };
161
- }
162
-
163
- private _normalizeSubdomain(subdomain: any): ResolvedSubdomain | null {
164
- if (!subdomain) return null;
165
-
166
- if (typeof subdomain === 'string') {
167
- return { subdomain, ip: null };
168
- }
169
-
170
- return {
171
- subdomain: subdomain.subdomain || subdomain.name || subdomain.host || subdomain.domain,
172
- ip: subdomain.ip || subdomain.address || subdomain.a || null,
173
- ips: subdomain.ips || subdomain.addresses || null,
174
- cname: subdomain.cname || null
175
- };
176
- }
177
-
178
- private _parseRawResolved(raw: string, baseDomain: string): MassDNSData {
179
- const subdomains: ResolvedSubdomain[] = [];
180
- const lines = raw.split('\n').filter(Boolean);
181
-
182
- for (const line of lines) {
183
- const match = line.match(/^([\w\-\.]+)\.\s+A\s+([\d\.]+)$/);
184
- if (match) {
185
- const subdomain = match[1]!.replace(/\.$/, '');
186
- const ip = match[2]!;
187
-
188
- if (subdomain && ip && subdomain.endsWith(baseDomain)) {
189
- subdomains.push({ subdomain, ip });
190
- }
191
- continue;
192
- }
193
-
194
- const simpleMatch = line.match(/^([\w\-\.]+)\s+([\d\.]+)$/);
195
- if (simpleMatch) {
196
- subdomains.push({
197
- subdomain: simpleMatch[1]!,
198
- ip: simpleMatch[2] ?? null
199
- });
200
- }
201
- }
202
-
203
- return {
204
- subdomains,
205
- resolvedCount: subdomains.length,
206
- totalAttempts: null
207
- };
208
- }
209
- }