@contrast/common
Advanced tools
Comparing version 1.1.5 to 1.2.0
@@ -0,1 +1,2 @@ | ||
import { CommonRulesResultsMap, HardeningResultsMap, ResultMap, SemanticAnalysisResultsMap, ServerFeaturePreliminaryResultsMap } from './types'; | ||
export * from './constants'; | ||
@@ -13,3 +14,11 @@ export * from './types'; | ||
export declare function encodeString(str: string): string; | ||
export declare function simpleTraverse(obj: any, cb: TraverseCallback): void; | ||
export declare function installChildComponentsSync(parent: any, order: string[]): void; | ||
export declare function traverseKeysAndValues(obj: any, cb: TraverseCallback): void; | ||
export declare function traverseValues(obj: any, cb: TraverseCallback): void; | ||
export declare function traverseKeys(obj: any, cb: TraverseCallback): void; | ||
export declare function callChildComponentMethodsSync(parent: any, method: 'install' | 'uninstall', order?: string[]): void; | ||
export declare function groupResultsMap(resultsMap: Partial<ResultMap>): { | ||
commonResultsMap: Partial<CommonRulesResultsMap>; | ||
hardeningResultsMap: Partial<HardeningResultsMap>; | ||
semanticResultsMap: Partial<SemanticAnalysisResultsMap>; | ||
serverFeaturesResultsMap: Partial<ServerFeaturePreliminaryResultsMap>; | ||
}; |
109
lib/index.js
@@ -31,3 +31,4 @@ "use strict"; | ||
Object.defineProperty(exports, "__esModule", { value: true }); | ||
exports.installChildComponentsSync = exports.simpleTraverse = exports.encodeString = exports.isNonEmptyObject = exports.isString = void 0; | ||
exports.groupResultsMap = exports.callChildComponentMethodsSync = exports.traverseKeys = exports.traverseValues = exports.traverseKeysAndValues = exports.encodeString = exports.isNonEmptyObject = exports.isString = void 0; | ||
const constants_1 = require("./constants"); | ||
__exportStar(require("./constants"), exports); | ||
@@ -53,10 +54,9 @@ __exportStar(require("./types"), exports); | ||
exports.encodeString = encodeString; | ||
function simpleTraverse(obj, cb) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
const path = []; | ||
function traverse(obj) { | ||
function traverse(obj, cb, path, traverseValues, traverseKeys) { | ||
let shouldKeepTraversing = true; | ||
function _traverse(obj, cb, path, traverseValues, traverseKeys) { | ||
const isArray = Array.isArray(obj); | ||
for (const k in obj) { | ||
if (!shouldKeepTraversing) | ||
return; | ||
if (isArray) { | ||
@@ -68,6 +68,8 @@ const _k = Number(k); | ||
if (typeof obj[_k] === 'object' && obj[_k] !== null) { | ||
traverse(obj[_k]); | ||
_traverse(obj[_k], cb, path, traverseValues, traverseKeys); | ||
} | ||
else if (typeof obj[_k] === 'string' && isNaN(obj[_k]) && obj[_k]) { | ||
cb(path, 'Value', obj[_k], obj); | ||
else if (typeof obj[_k] === 'string' && obj[_k]) { | ||
if (traverseValues && cb(path, 'Value', obj[_k], obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
} | ||
@@ -77,13 +79,19 @@ path.pop(); | ||
else if (typeof obj[k] === 'object' && obj[k] !== null) { | ||
cb(path, 'Key', k, obj); | ||
if (traverseKeys && cb(path, 'Key', k, obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
path.push(k); | ||
traverse(obj[k]); | ||
_traverse(obj[k], cb, path, traverseValues, traverseKeys); | ||
path.pop(); | ||
} | ||
else { | ||
cb(path, 'Key', k, obj); | ||
if (traverseKeys && cb(path, 'Key', k, obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
// only callback if the value is a non-empty string | ||
if (typeof obj[k] === 'string' && isNaN(obj[k]) && obj[k]) { | ||
if (typeof obj[k] === 'string' && obj[k]) { | ||
path.push(k); | ||
cb(path, 'Value', obj[k], obj); | ||
if (traverseValues && cb(path, 'Value', obj[k], obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
path.pop(); | ||
@@ -94,15 +102,74 @@ } | ||
} | ||
traverse(obj); | ||
_traverse(obj, cb, path, traverseValues, traverseKeys); | ||
} | ||
exports.simpleTraverse = simpleTraverse; | ||
function installChildComponentsSync(parent, order) { | ||
function traverseKeysAndValues(obj, cb) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
traverse(obj, cb, [], true, true); | ||
} | ||
exports.traverseKeysAndValues = traverseKeysAndValues; | ||
function traverseValues(obj, cb) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
traverse(obj, cb, [], true, false); | ||
} | ||
exports.traverseValues = traverseValues; | ||
function traverseKeys(obj, cb) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
traverse(obj, cb, [], false, true); | ||
} | ||
exports.traverseKeys = traverseKeys; | ||
function callChildComponentMethodsSync(parent, method, order) { | ||
const keys = order || Object.keys(parent); | ||
for (const key of keys) { | ||
const component = parent[key]; | ||
if (typeof component.install === 'function') { | ||
component.install(); | ||
if (typeof component[method] === 'function') { | ||
component[method](); | ||
} | ||
} | ||
} | ||
exports.installChildComponentsSync = installChildComponentsSync; | ||
exports.callChildComponentMethodsSync = callChildComponentMethodsSync; | ||
function groupResultsMap(resultsMap) { | ||
const result = { | ||
commonResultsMap: {}, | ||
hardeningResultsMap: {}, | ||
semanticResultsMap: {}, | ||
serverFeaturesResultsMap: {}, | ||
}; | ||
Object.keys(resultsMap).reduce((acc, rule) => { | ||
switch (rule) { | ||
case constants_1.Rule.SQL_INJECTION: | ||
case constants_1.Rule.CMD_INJECTION: | ||
case constants_1.Rule.PATH_TRAVERSAL: | ||
case constants_1.Rule.REFLECTED_XSS: | ||
case constants_1.Rule.SSJS_INJECTION: | ||
case constants_1.Rule.NOSQL_INJECTION_MONGO: | ||
case constants_1.Rule.UNSAFE_FILE_UPLOAD: | ||
case constants_1.Rule.BOT_BLOCKER: | ||
case constants_1.Rule.NOSQL_INJECTION: | ||
acc.commonResultsMap[rule] = resultsMap[rule]; | ||
break; | ||
case constants_1.Rule.CMD_INJECTION_SEMANTIC_DANGEROUS_PATHS: | ||
case constants_1.Rule.CMD_INJECTION_SEMANTIC_CHAINED_COMMANDS: | ||
case constants_1.Rule.XXE: | ||
case constants_1.Rule.CMD_INJECTION_COMMAND_BACKDOORS: | ||
case constants_1.Rule.PATH_TRAVERSAL_SEMANTIC_FILE_SECURITY_BYPASS: | ||
acc.semanticResultsMap[rule] = resultsMap[rule]; | ||
break; | ||
case constants_1.Rule.VIRTUAL_PATCH: | ||
case constants_1.Rule.IP_DENYLIST: | ||
acc.serverFeaturesResultsMap[rule] = resultsMap[rule]; | ||
break; | ||
case constants_1.Rule.UNTRUSTED_DESERIALIZATION: | ||
acc.hardeningResultsMap[rule] = resultsMap[rule]; | ||
} | ||
return acc; | ||
}, result); | ||
return result; | ||
} | ||
exports.groupResultsMap = groupResultsMap; | ||
//# sourceMappingURL=index.js.map |
@@ -24,6 +24,9 @@ /// <reference types="node" /> | ||
} | ||
export declare type SemanticAnalysisRules = Rule.CMD_INJECTION_SEMANTIC_CHAINED_COMMANDS | Rule.CMD_INJECTION_COMMAND_BACKDOORS | Rule.CMD_INJECTION_SEMANTIC_DANGEROUS_PATHS; | ||
export declare type CommonRules = Rule.SQL_INJECTION | Rule.CMD_INJECTION | Rule.PATH_TRAVERSAL | Rule.REFLECTED_XSS | Rule.SSJS_INJECTION | Rule.NOSQL_INJECTION_MONGO | Rule.UNSAFE_FILE_UPLOAD | Rule.NOSQL_INJECTION | Rule.BOT_BLOCKER; | ||
export declare type SemanticAnalysisRules = Rule.CMD_INJECTION_SEMANTIC_DANGEROUS_PATHS | Rule.CMD_INJECTION_SEMANTIC_CHAINED_COMMANDS | Rule.XXE | Rule.CMD_INJECTION_COMMAND_BACKDOORS | Rule.PATH_TRAVERSAL_SEMANTIC_FILE_SECURITY_BYPASS; | ||
export declare type ServerFeaturePreliminaryRules = Rule.VIRTUAL_PATCH | Rule.IP_DENYLIST; | ||
export declare type HardeningRules = Rule.UNTRUSTED_DESERIALIZATION; | ||
export interface Result { | ||
blocked: boolean; | ||
details?: any[]; | ||
exploitMetadata?: any[] | any; | ||
idsList?: string[]; | ||
@@ -38,16 +41,18 @@ inputType: string; | ||
value: string; | ||
sinkContext?: any; | ||
} | ||
export interface SemanticAnalysisResult extends Result { | ||
findings?: { | ||
ruleId: SemanticAnalysisRules; | ||
exploitMetadata: { | ||
command?: string; | ||
prolog?: string; | ||
xml?: string; | ||
}; | ||
}[]; | ||
sinkContext?: any; | ||
} | ||
export interface HardeningResult extends Result { | ||
findings?: { | ||
exploitMetadata: { | ||
command?: boolean; | ||
deserializer?: string; | ||
}; | ||
}[]; | ||
sinkContext?: any; | ||
@@ -61,3 +66,3 @@ } | ||
export interface ServerFeatureResult extends Result { | ||
details?: ServerFeaturePreliminaryResult[]; | ||
exploitMetadata?: ServerFeaturePreliminaryResult[]; | ||
} | ||
@@ -73,11 +78,15 @@ export interface ReqData { | ||
} | ||
export interface Findings { | ||
trackRequest: boolean; | ||
securityException?: [mode: ProtectRuleMode, ruleId: string]; | ||
bodyType?: 'json' | 'urlencoded'; | ||
resultsMap: Partial<Record<Rule, Result[]>>; | ||
semanticResultsMap: Partial<Record<Rule, SemanticAnalysisResult[]>>; | ||
serverFeaturesResultsMap: Partial<Record<Rule, ServerFeaturePreliminaryResult[]>>; | ||
hardeningResultsMap: Partial<Record<Rule, HardeningResult[]>>; | ||
} | ||
export declare type CommonRulesResultsMap = { | ||
[rule in CommonRules]: Result[]; | ||
}; | ||
export declare type SemanticAnalysisResultsMap = { | ||
[rule in SemanticAnalysisRules]: SemanticAnalysisResult[]; | ||
}; | ||
export declare type ServerFeaturePreliminaryResultsMap = { | ||
[rule in ServerFeaturePreliminaryRules]: ServerFeaturePreliminaryResult[]; | ||
}; | ||
export declare type HardeningResultsMap = { | ||
[rule in HardeningRules]: HardeningResult[]; | ||
}; | ||
export declare type ResultMap = CommonRulesResultsMap & SemanticAnalysisResultsMap & ServerFeaturePreliminaryResultsMap & HardeningResultsMap; | ||
export interface ProtectMessage { | ||
@@ -89,3 +98,6 @@ reqData: ReqData; | ||
virtualPatches: any[]; | ||
findings: Findings; | ||
trackRequest: boolean; | ||
securityException?: [mode: ProtectRuleMode, ruleId: string]; | ||
bodyType?: 'json' | 'urlencoded'; | ||
resultsMap: Partial<ResultMap>; | ||
parsedBody: any; | ||
@@ -92,0 +104,0 @@ parsedCookies: any; |
{ | ||
"name": "@contrast/common", | ||
"version": "1.1.5", | ||
"version": "1.2.0", | ||
"description": "Shared constants and utilities for all Contrast Agent modules", | ||
@@ -17,2 +17,2 @@ "license": "UNLICENSED", | ||
} | ||
} | ||
} |
128
src/index.ts
@@ -16,2 +16,5 @@ /* | ||
import { Rule } from './constants'; | ||
import { CommonRulesResultsMap, HardeningResultsMap, ResultMap, SemanticAnalysisResultsMap, ServerFeaturePreliminaryResultsMap } from './types'; | ||
export * from './constants'; | ||
@@ -42,10 +45,23 @@ export * from './types'; | ||
export function simpleTraverse(obj: any, cb: TraverseCallback) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
const path: any[] = []; | ||
function traverse(obj: any) { | ||
function traverse( | ||
obj: any, | ||
cb: TraverseCallback, | ||
path: any[], | ||
traverseValues: boolean, | ||
traverseKeys: boolean | ||
) { | ||
let shouldKeepTraversing = true; | ||
function _traverse( | ||
obj: any, | ||
cb: TraverseCallback, | ||
path: any[], | ||
traverseValues: boolean, | ||
traverseKeys: boolean | ||
) { | ||
const isArray = Array.isArray(obj); | ||
for (const k in obj) { | ||
if (!shouldKeepTraversing) return; | ||
if (isArray) { | ||
@@ -57,18 +73,26 @@ const _k = Number(k); | ||
if (typeof obj[_k] === 'object' && obj[_k] !== null) { | ||
traverse(obj[_k]); | ||
} else if (typeof obj[_k] === 'string' && isNaN(obj[_k]) && obj[_k]) { | ||
cb(path, 'Value', obj[_k], obj); | ||
_traverse(obj[_k], cb, path, traverseValues, traverseKeys); | ||
} else if (typeof obj[_k] === 'string' && obj[_k]) { | ||
if (traverseValues && cb(path, 'Value', obj[_k], obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
} | ||
path.pop(); | ||
} else if (typeof obj[k] === 'object' && obj[k] !== null) { | ||
cb(path, 'Key', k, obj); | ||
if (traverseKeys && cb(path, 'Key', k, obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
path.push(k); | ||
traverse(obj[k]); | ||
_traverse(obj[k], cb, path, traverseValues, traverseKeys); | ||
path.pop(); | ||
} else { | ||
cb(path, 'Key', k, obj); | ||
if (traverseKeys && cb(path, 'Key', k, obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
// only callback if the value is a non-empty string | ||
if (typeof obj[k] === 'string' && isNaN(obj[k]) && obj[k]) { | ||
if (typeof obj[k] === 'string' && obj[k]) { | ||
path.push(k); | ||
cb(path, 'Value', obj[k], obj); | ||
if (traverseValues && cb(path, 'Value', obj[k], obj)) { | ||
return shouldKeepTraversing = false; | ||
} | ||
path.pop(); | ||
@@ -80,13 +104,81 @@ } | ||
traverse(obj); | ||
_traverse(obj, cb, path, traverseValues, traverseKeys); | ||
} | ||
export function installChildComponentsSync(parent: any, order: string[]) { | ||
export function traverseKeysAndValues(obj: any, cb: TraverseCallback) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
traverse(obj, cb, [], true, true); | ||
} | ||
export function traverseValues(obj: any, cb: TraverseCallback) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
traverse(obj, cb, [], true, false); | ||
} | ||
export function traverseKeys(obj: any, cb: TraverseCallback) { | ||
if (typeof obj !== 'object' || obj === null) { | ||
return; | ||
} | ||
traverse(obj, cb, [], false, true); | ||
} | ||
export function callChildComponentMethodsSync(parent: any, method: 'install' | 'uninstall', order?: string[]) { | ||
const keys = order || Object.keys(parent); | ||
for (const key of keys) { | ||
const component: any = parent[key]; | ||
if (typeof component.install === 'function') { | ||
component.install(); | ||
if (typeof component[method] === 'function') { | ||
component[method](); | ||
} | ||
} | ||
} | ||
export function groupResultsMap (resultsMap: Partial<ResultMap>) { | ||
const result: { | ||
commonResultsMap: Partial<CommonRulesResultsMap>; | ||
hardeningResultsMap: Partial<HardeningResultsMap>; | ||
semanticResultsMap: Partial<SemanticAnalysisResultsMap>; | ||
serverFeaturesResultsMap: Partial<ServerFeaturePreliminaryResultsMap>; | ||
} = { | ||
commonResultsMap: {}, | ||
hardeningResultsMap: {}, | ||
semanticResultsMap: {}, | ||
serverFeaturesResultsMap: {}, | ||
}; | ||
Object.keys(resultsMap).reduce((acc, rule) => { | ||
switch (rule) { | ||
case Rule.SQL_INJECTION: | ||
case Rule.CMD_INJECTION: | ||
case Rule.PATH_TRAVERSAL: | ||
case Rule.REFLECTED_XSS: | ||
case Rule.SSJS_INJECTION: | ||
case Rule.NOSQL_INJECTION_MONGO: | ||
case Rule.UNSAFE_FILE_UPLOAD: | ||
case Rule.BOT_BLOCKER: | ||
case Rule.NOSQL_INJECTION: | ||
acc.commonResultsMap[rule] = resultsMap[rule]; | ||
break; | ||
case Rule.CMD_INJECTION_SEMANTIC_DANGEROUS_PATHS: | ||
case Rule.CMD_INJECTION_SEMANTIC_CHAINED_COMMANDS: | ||
case Rule.XXE: | ||
case Rule.CMD_INJECTION_COMMAND_BACKDOORS: | ||
case Rule.PATH_TRAVERSAL_SEMANTIC_FILE_SECURITY_BYPASS: | ||
acc.semanticResultsMap[rule] = resultsMap[rule]; | ||
break; | ||
case Rule.VIRTUAL_PATCH: | ||
case Rule.IP_DENYLIST: | ||
acc.serverFeaturesResultsMap[rule] = resultsMap[rule]; | ||
break; | ||
case Rule.UNTRUSTED_DESERIALIZATION: | ||
acc.hardeningResultsMap[rule] = resultsMap[rule]; | ||
} | ||
return acc; | ||
}, result); | ||
return result; | ||
} |
@@ -40,10 +40,27 @@ /* | ||
export type CommonRules = | ||
Rule.SQL_INJECTION | | ||
Rule.CMD_INJECTION | | ||
Rule.PATH_TRAVERSAL | | ||
Rule.REFLECTED_XSS | | ||
Rule.SSJS_INJECTION | | ||
Rule.NOSQL_INJECTION_MONGO | | ||
Rule.UNSAFE_FILE_UPLOAD | | ||
Rule.NOSQL_INJECTION | | ||
Rule.BOT_BLOCKER; | ||
export type SemanticAnalysisRules = | ||
| Rule.CMD_INJECTION_SEMANTIC_CHAINED_COMMANDS | ||
| Rule.CMD_INJECTION_COMMAND_BACKDOORS | ||
| Rule.CMD_INJECTION_SEMANTIC_DANGEROUS_PATHS; | ||
Rule.CMD_INJECTION_SEMANTIC_DANGEROUS_PATHS | | ||
Rule.CMD_INJECTION_SEMANTIC_CHAINED_COMMANDS | | ||
Rule.XXE | | ||
Rule.CMD_INJECTION_COMMAND_BACKDOORS | | ||
Rule.PATH_TRAVERSAL_SEMANTIC_FILE_SECURITY_BYPASS; | ||
export type ServerFeaturePreliminaryRules = Rule.VIRTUAL_PATCH | Rule.IP_DENYLIST; | ||
export type HardeningRules = Rule.UNTRUSTED_DESERIALIZATION; | ||
export interface Result { | ||
blocked: boolean; | ||
details?: any[]; // TODO | ||
exploitMetadata?: any[] | any; // TODO | ||
idsList?: string[]; | ||
@@ -58,10 +75,12 @@ inputType: string; // TODO | ||
value: string; | ||
sinkContext?: any; | ||
} | ||
export interface SemanticAnalysisResult extends Result { | ||
findings?: { | ||
ruleId: SemanticAnalysisRules; | ||
exploitMetadata: { | ||
command?: string; | ||
prolog?: string; | ||
xml?: string; | ||
}; | ||
}[]; | ||
sinkContext?: any; | ||
@@ -71,6 +90,6 @@ } | ||
export interface HardeningResult extends Result { | ||
findings?: { | ||
exploitMetadata: { | ||
command?: boolean; | ||
deserializer?: string; | ||
}; | ||
}[]; | ||
sinkContext?: any; | ||
@@ -86,3 +105,3 @@ } | ||
export interface ServerFeatureResult extends Result { | ||
details?: ServerFeaturePreliminaryResult[]; | ||
exploitMetadata?: ServerFeaturePreliminaryResult[]; | ||
} | ||
@@ -100,12 +119,20 @@ | ||
export interface Findings { | ||
trackRequest: boolean; | ||
securityException?: [mode: ProtectRuleMode, ruleId: string]; | ||
bodyType?: 'json' | 'urlencoded'; | ||
resultsMap: Partial<Record<Rule, Result[]>>; | ||
semanticResultsMap: Partial<Record<Rule, SemanticAnalysisResult[]>>; | ||
serverFeaturesResultsMap: Partial<Record<Rule, ServerFeaturePreliminaryResult[]>>; | ||
hardeningResultsMap: Partial<Record<Rule, HardeningResult[]>>; | ||
} | ||
export type CommonRulesResultsMap = { | ||
[rule in CommonRules]: Result[]; | ||
}; | ||
export type SemanticAnalysisResultsMap = { | ||
[rule in SemanticAnalysisRules]: SemanticAnalysisResult[]; | ||
}; | ||
export type ServerFeaturePreliminaryResultsMap = { | ||
[rule in ServerFeaturePreliminaryRules]: ServerFeaturePreliminaryResult[] | ||
}; | ||
export type HardeningResultsMap = { | ||
[rule in HardeningRules]:HardeningResult[]; | ||
}; | ||
export type ResultMap = CommonRulesResultsMap & SemanticAnalysisResultsMap & ServerFeaturePreliminaryResultsMap & HardeningResultsMap; | ||
export interface ProtectMessage { | ||
@@ -117,3 +144,6 @@ reqData: ReqData; | ||
virtualPatches: any[]; // TODO | ||
findings: Findings; | ||
trackRequest: boolean; | ||
securityException?: [mode: ProtectRuleMode, ruleId: string]; | ||
bodyType?: 'json' | 'urlencoded'; | ||
resultsMap: Partial<ResultMap> | ||
parsedBody: any; | ||
@@ -120,0 +150,0 @@ parsedCookies: any; |
Sorry, the diff of this file is not supported yet
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
39812
843