Merge pull request #8469 from ErikOwen/feat/headless-tech-js-detect-template

Add "js-detect" headless tech template
patch-1
Prince Chaddha 2023-10-28 13:20:54 +05:30 committed by GitHub
commit e931a0a8c2
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 346 additions and 0 deletions

View File

@ -0,0 +1,346 @@
id: js-libraries-detect
info:
name: Common JS Libraries - Detection
author: adamparsons,cbadke,ChetGan,ErikOwen,jacalynli
severity: info
description: Checks a target web app for inclusion of common JavaScript libraries
metadata:
max-request: 1
tags: headless,tech,js
headless:
- steps:
- action: navigate
args:
url: "{{BaseURL}}"
- action: waitload
- action: script
name: fingerprintAxios
args:
code: |
() => {
//check for axios
if (!window.axios) {
return ""
}
try {
// check for version
// only works on some websites
return window.axios.VERSION
} catch (e) {}
return "Version not found"
}
- action: script
name: fingerprintBootstrap
args:
code: |
() => {
try {
// if not using jQuery
return bootstrap.Tooltip.VERSION || ""
} catch (e) {}
try {
// if using jQuery
return $.fn.tooltip.Constructor.VERSION || ""
} catch (e) {}
return ""
}
- action: script
name: fingerprintJQuery
args:
code: |
() => {
let version = "";
try {
if(window.jQuery) {
version = jQuery.fn.jquery;
}
if(window.$) {
version = $.fn.jquery;
}
version = version.replace(".min", "");
version = version.replace(".slim", "");
return version;
} catch (e) {}
return "";
}
- action: script
name: fingerprintLodash
args:
code: |
() => {
try {
return _.VERSION || "";
} catch (e) {}
return "";
}
- action: script
name: fingerprintMomentJs
args:
code: |
() => {
try {
return moment.version || "";
} catch (e) {}
return "";
}
- action: script
name: fingerprintReact
args:
code: |
() => {
try {
return window.React.version || "";
} catch (e) {}
return "";
}
- action: script
name: fingerprintReactDOM
args:
code: |
() => {
try {
if (window.ReactDOM) {
return window.React.version || "";
}
} catch (e) {}
return "";
}
- action: script
name: fingerprintAngular
args:
code: |
() => {
try {
// Angular Version 1
return angular.version.full
} catch (e) {}
try {
// Angular Version 2+
return getAllAngularRootElements()[0].attributes["ng-version"].value
} catch (e) {}
return ""
}
- action: script
name: fingerprintBackboneJs
args:
code: |
() => {
try {
return window.Backbone.VERSION || ""
} catch (e) {}
return ""
}
- action: script
name: fingerprintEmberJs
args:
code: |
() => {
try {
return Ember.VERSION || ""
} catch (e) {}
return "";
}
- action: script
name: fingerprintVue
args:
code: |
() => {
//method 1 (simple)
try {
return Vue.version
} catch (e) {}
//method 2 (checks if Nuxt exists)
try {
const nuxtDetected = Boolean(window.__NUXT__ || window.$nuxt)
if (nuxtDetected) {
let Vue
}
if (window.$nuxt) {
Vue = window.$nuxt.$root.constructor
}
return Vue.version
} catch (e) {}
//method 3 (go through all elements)
try {
const all = document.querySelectorAll('*')
let flag
for (let i = 0; i < all.length; i++) {
if (all[i].__vue__) {
flag = all[i]
break
}
}
if (flag) {
let Vue = Object.getPrototypeOf(flag.__vue__).constructor
while (Vue.super) {
Vue = Vue.super
}
return Vue.version
}
return ""
} catch (e) {}
return ""
}
- action: script
name: fingerprintDojoJs
args:
code: |
() => {
try {
return ([dojo.version.major, dojo.version.minor, dojo.version.patch].join("."))
} catch (e) {}
return ""
}
- action: script
name: fingerprintDomPurify
args:
code: |
() => {
try {
return DOMPurify.version || ""
} catch (e) {}
return ""
}
- action: script
name: fingerprintModernizr
args:
code: |
() => {
try {
return Modernizr._version || ""
} catch (e) {}
return ""
}
matchers-condition: or
matchers:
- type: dsl
dsl:
- len(fingerprintAxios) > 0
- len(fingerprintBootstrap) > 0
- len(fingerprintJQuery) > 0
- len(fingerprintLodash) > 0
- len(fingerprintMomentJs) > 0
- len(fingerprintReact) > 0
- len(fingerprintReactDOM) > 0
- len(fingerprintAngular) > 0
- len(fingerprintBackboneJs) > 0
- len(fingerprintEmberJs) > 0
- len(fingerprintVue) > 0
- len(fingerprintDojoJs) > 0
- len(fingerprintDomPurify) > 0
- len(fingerprintModernizr) > 0
extractors:
- name: axios
type: regex
part: fingerprintAxios
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: bootstrap
type: regex
part: fingerprintBootstrap
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: jquery
type: regex
part: fingerprintJQuery
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: lodash
type: regex
part: fingerprintLodash
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: moment
type: regex
part: fingerprintMomentJs
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: react
type: regex
part: fingerprintReact
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: reactdom
type: regex
part: fingerprintReactDOM
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: angular
type: regex
part: fingerprintAngular
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: backbone
type: regex
part: fingerprintBackboneJs
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: emberjs
type: regex
part: fingerprintEmberJs
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: vuejs
type: regex
part: fingerprintVue
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: dojo
type: regex
part: fingerprintDojoJs
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: dompurify
type: regex
part: fingerprintDomPurify
regex:
- ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
- name: modernizr
type: regex
part: fingerprintModernizr
regex:
- ^(0|[1-9]\d*)(?:\.(0|[1-9]\d*))?(?:\.(0|[1-9]\d*))?(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$