Skip to content

Headless

Headless Requests

Nuclei supports automation of a browser with simple DSL. Headless browser engine can be fully customized and user actions can be scripted allowing complete control over the browser. This allows for a variety of unique and custom workflows.

# Start the requests for the template right here
headless:

Actions

Action is a single piece of Task for the Nuclei Headless Engine. Each action manipulates the browser state in some way, and finally leads to the state that we are interesting in capturing.

Nuclei supports a variety of actions. A list of these Actions along with their arguments are given below -

Navigate visits a given URL. url field supports variables like {{BaseURL}}, {{Hostname}} to customize the request fully.

action: navigate
args: 
  url: "{{BaseURL}}
script

Script runs a JS code on the current browser page. At the simplest level, you can just provide a code argument with the JS snippet you want to execute and it will be run on the page.

action: script
args:
  code: alert(document.domain)

Suppose you want to run a matcher on a JS object to inspect it's value. This type of data extraction use cases are also supported with nuclei headless. As an example, let's say the application sets an object called window.random-object with a value and you want to match on that value.

- action: script
  args:
    code: window.random-object
  name: script-name
...
matchers:
  - type: word
    part: script-name
    words:
      - "some-value"

Nuclei supports running some custom Javascript, before the page load with the hook argument. This will always run the provided Javascript, before any of the pages load.

The example provided hooks window.alert so that the alerts that are generated by the application do not stop the crawler.

- action: script
  args:
    code: (function() { window.alert=function(){} })()
    hook: true

This is one use case, there are many more use cases of function hooking such as DOM XSS Detection and Javascript-Injection based testing techniques. Further examples are provided on examples page.

click

Click simulates clicking with the Left-Mouse button on an element specified by a selector.

action: click
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input

Nuclei supports a variety of selector types, including but not limited to XPath, Regex, CSS, etc. For more information about selectors, see here.

rightclick

RightClick simulates clicking with the Right-Mouse button on an element specified by a selector.

action: rightclick
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input
text

Text simulates typing something into an input with Keyboard. Selectors can be used to specify the element to type in.

action: text
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input
  value: username
screenshot

Screenshots takes the screenshots of a page and writes it to disk. It supports both full page as well as normal screenshots.

action: screenshot
args: 
  to: /root/test/screenshot-web

If you require full page screenshot, it can be achieved with fullpage: true option in the args.

action: screenshot
args: 
  to: /root/test/screenshot-web
  fullpage: true
time

Time enters values into time inputs on pages in RFC3339 format.

action: time
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input
  value: 2006-01-02T15:04:05Z07:00
select

Select performs selection on a HTML Input by a selector.

action: select
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input
  selected: true
  value: option[value=two]
  selector: regex
files

Files handles a file upload input on the webpage.

action: files
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input
  value: /root/test/payload.txt
waitload

WaitLoads waits for a page to finish loading and get in Idle state.

action: waitload

Nuclei's waitload action waits for DOM to load, and window.onload event to be received after which we wait for the page to become idle for 1 seconds.

getresource

GetResource returns the src attribute for an element.

action: getresource
name: extracted-value-src
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input
extract

Extract extracts either the Text for a HTML Node, or an attribute as specified by the user.

The below code will extract the Text for the given XPath Selector Element, which can then also be matched upon by name extracted-value with matchers and extractors.

action: extract
name: extracted-value
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input

An attribute can also be extracted for an element. For example -

action: extract
name: extracted-value-href
args: 
  by: xpath
  xpath: /html/body/div[1]/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input
  target: attribute
  attribute: href
setmethod

SetMethod overrides the method for the request.

action: setmethod
args: 
  part: request
  method: DELETE
addheader

AddHeader adds a header to the requests / responses. This does not overwrites any pre-existing headers.

action: addheader
args: 
  part: response # can be request too
  key: Content-Security-Policy
  value: "default-src * 'unsafe-inline' 'unsafe-eval' data: blob:;"
setheader

SetHeader sets a header in the requests / responses.

action: setheader
args: 
  part: response # can be request too
  key: Content-Security-Policy
  value: "default-src * 'unsafe-inline' 'unsafe-eval' data: blob:;"
deleteheader

DeleteHeader deletes a header from requests / responses.

action: deleteheader
args: 
  part: response # can be request too
  key: Content-Security-Policy
setbody

SetBody sets the body for a request / response.

action: setbody
args: 
  part: response # can be request too
  body: '{"success":"ok"}'
waitevent

WaitEvent waits for an event to trigger on the page.

action: waitevent
args: 
  event: 'Page.loadEventFired'

The list of events supported are listed here.

keyboard

Keybord simulates a single key-press on the keyboard.

action: keyboard
args: 
  keys: '\r' # this simulates pressing enter key on keyboard

keys argument accepts key-codes.

debug

Debug adds a delay of 5 seconds between each headless action and also shows a trace of all the headless events occuring in the browser.

Note: Only use this for debugging purposes, don't use this in production templates.

action: debug
sleep

Sleeps makes the browser wait for a specified duration in seconds. This is also useful for debugging purposes.

action: sleep
args:
  duration: 5

Selectors

Selectors are how nuclei headless engine identifies what element to execute an action on. Nuclei supports getting selectors by including a variety of options -

Selector Description
r / regex Element matches CSS Selector and Text Matches Regex
x / xpath Element matches XPath selector
js Return elements from a JS function
search Search for a query (can be text, XPATH, CSS)
selector (default) Element matches CSS Selector

Matchers / Extractor Parts

Valid part values supported by Headless protocol for Matchers / Extractor are -

Value Description
request Headless Request
<out_names> Action names with stored values
raw / body / data Final DOM response from browser

Example Headless Template

An example headless template to automatically login into DVWA is provided below -

id: dvwa-headless-automatic-login
info:
  name: DVWA Headless Automatic Login
  author: pdteam
  severity: high
headless:
  - steps:
      - args:
          url: "{{BaseURL}}/login.php"
        action: navigate
      - action: waitload
      - args:
          by: xpath
          xpath: /html/body/div/div[2]/form/fieldset/input
        action: click
      - action: waitload
      - args:
          by: xpath
          value: admin
          xpath: /html/body/div/div[2]/form/fieldset/input
        action: text
      - args:
          by: xpath
          xpath: /html/body/div/div[2]/form/fieldset/input[2]
        action: click
      - action: waitload
      - args:
          by: xpath
          value: password
          xpath: /html/body/div/div[2]/form/fieldset/input[2]
        action: text
      - args:
          by: xpath
          xpath: /html/body/div/div[2]/form/fieldset/p/input
        action: click
      - action: waitload
    matchers:
      - part: resp
        type: word
        words:
          - "You have logged in as"

More complete examples are provided here