Scanning Every Push with the Soteri - Scan Commits Security Hook
Security for Bitbucket contains a pre-receive hook, which can run a scan on any code before it is pushed into Bitbucket. At the Bitbucket instance level, the Security Hook can be configured to run:
only when explicitly enabled for a repository or project,
for repositories where the hook is configured as “inherited” (the Bitbucket default) or “enabled”, or
always (cannot be disabled on the repository or project level).
When enabled, the Security Hook has two modes:
Block: reject the push if any vulnerabilities are found, and
Warn-only: print a message to the pusher notifying them of the scan failures, but allow the push to succeed.
Note: UI Edits and Warn-only mode
Warnings can’t be presented to users when they commit using the Bitbucket built-in web editor.
Bitbucket 8: Soteri recommends increasing git hook timeout
Bitbucket 8 introduced a timeout for git hooks which can prevent scans from completing successfully. Soteri recommends increasing this timeout by setting mesh.hooks.callback.timeout = 1200
in your bitbucket.properties
file. See this page for more information.
Note: using with git-submodules
Repositories included via git-submodules are treated as separate repositories. When enabling the hook, make sure to also enable it on any relevant repositories included via git-submodules.
Bypassing the hook
Sometimes the synchronous scanning of pushes is not feasible due to the size or complexity of the commits pushed. In those cases, developers can include the string **skip-soteri-security-check**
in the commit message of the commit which should not be scanned. Any commits pushed in the same push operation which do not contain the skip-string will still be scanned.
If a scan is subsequently triggered via the Branch Security Analysis page or the Soteri Global Dashboard, the contents of the commit will be scanned. The bypass directive applies to the pre-receive hook only.
When the pre-receive hook is enabled and a commit is bypassed, a warning message is displayed to the pusher:
When a commit skips the security check, a log message is printed to the Bitbucket log which looks like this:
[INFO] 2022-02-22 13:01:22,106 WARN [hook-callback:thread-1] admin @1R4HND9x781x74x0 0:0:0:0:0:0:0:1 "POST /scm/dev/rep_3.git/git-receive-pack HTTP/1.1" i.s.b.s.h.ValidationPreRepositoryHookCommitCallback 'Soteri - Scan Commits': Checks bypassed in push to DEV/rep_1 by jsecurity. Commits skipped: 24debf934a018ab840494cda536fbb5624cee12a f2ec25125a9732eb708cf175326e6065e47154af a1444c181d2d99b1bc8817799ecd4021bef2bda1
And an Auditable Event is created in Bitbucket’s Audit Log. More information on Audited Events can be found in Viewing Audited Events.
Inheritance Model
The security hook can be enabled globally, on a project level, or on the repository level. When the repository-level hook is configured as “Inherited”, it inherits settings either from the project level or from the global configuration. The following table outlines whether or not the hook runs in each of these cases.
Global hook setting | Project hook toggle | Repository hook setting | Resulting Behavior |
---|---|---|---|
ONLY WHEN ENABLED | DISABLED | DISABLED | Hook OFF |
ONLY WHEN ENABLED | DISABLED | INHERITED | Hook OFF |
ONLY WHEN ENABLED | DISABLED | ENABLED | Hook ON |
ONLY WHEN ENABLED | ENABLED | DISABLED | Hook OFF |
ONLY WHEN ENABLED | ENABLED | INHERITED | Hook ON (mode inherited from project) |
ONLY WHEN ENABLED | ENABLED | ENABLED | Hook ON |
INHERITED OR ENABLED | DISABLED | DISABLED | Hook OFF |
INHERITED OR ENABLED | DISABLED | INHERITED | Hook ON (mode inherited from global) |
INHERITED OR ENABLED | DISABLED | ENABLED | Hook ON |
INHERITED OR ENABLED | ENABLED | DISABLED | Hook OFF |
INHERITED OR ENABLED | ENABLED | INHERITED | Hook ON (mode inherited from project) |
INHERITED OR ENABLED | ENABLED | ENABLED | Hook ON |
ALWAYS | DISABLED | DISABLED | Hook ON (repo setting overridden) |
ALWAYS | DISABLED | INHERITED | Hook ON (mode inherited from global) |
ALWAYS | DISABLED | ENABLED | Hook ON |
ALWAYS | ENABLED | DISABLED | Hook ON (repo setting overridden) |
ALWAYS | ENABLED | INHERITED | Hook ON (mode inherited from project) |
ALWAYS | ENABLED | ENABLED | Hook ON |
If the global hook is set to “always (cannot be disabled)”, security checks cannot be weakened. For instance, if the global hook is set to block, even if the repository hook is set to warn, potentially vulnerable commits will be blocked. If the hook is overridden on, an additional customizable message will be displayed to developers.
Personal repositories (those with ~username in the path) do not support inheritance, since they don’t belong to a project. The only way to enable the Security Hook for all personal repositories is to enable the Global Hook “always (cannot be disabled)”.
Enabling the hook globally
To enable the hook on a global scale, Bitbucket administrator, or anyone granted access to Security for Bitbucket, can access the security settings page and then modify the Enable hook drop-down option:
When the global hook enabled is set to either “when explicitly enabled or inherited” or “always”, the global hook mode can be configured to be Block or Warn:
Enabling the hook on the project level
To enable the hook on a project level (which is great for blocking vulnerabilities for new repositories), go to the desired project, Settings → Hooks, and then enable the Soteri - Scan Commits hook. A pop-up will prompt you with the option whether to configure the hook in reject or warn-only mode.
Enabling the hook on the repository level
To enable the hook on a repository level, go to the desired repository, Settings → Hooks, and then enable the Soteri - Scan Commits hook. A pop-up will prompt you with the option whether to configure the hook in reject or warn-only mode.
Example of a blocked push
Blocked pushes contain details about each finding. For example, in the first finding:
AWS_CLIENT_ID
is the name of the rule which generated the findingsec_1.js
is the file in which the finding was detectedb7f65f0929978e3d53eab26b2f99c212cab9ebe1
is the hash of the commit in which the finding was detectedline 7
is the finding’s line number(16:36)
are the starting and ending indices of the finding withinline 11
Pushed which are blocked or warned about are logged in the Bitbucket audit log. More information on Audited Events can be found in Viewing Audited Events.