Skip to content

Commit

Permalink
feat: gitlab improvements part 2 (#46)
Browse files Browse the repository at this point in the history
  • Loading branch information
didroe authored May 10, 2023
1 parent 655b6d4 commit 327b90d
Show file tree
Hide file tree
Showing 80 changed files with 1,640 additions and 82 deletions.
4 changes: 2 additions & 2 deletions javascript/aws_lambda/code_injection.yml
Original file line number Diff line number Diff line change
Expand Up @@ -39,8 +39,8 @@ patterns:
auxiliary:
- id: javascript_aws_lambda_code_injection_user_input
patterns:
- event.$<_>
- event[$<_>]
- async function ($<!>event, $<_>) {}
- async ($<!>event, $<_>) => {}
languages:
- javascript
severity: high
Expand Down
3 changes: 2 additions & 1 deletion javascript/aws_lambda/os_command_injection.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ patterns:
auxiliary:
- id: javascript_aws_lambda_cross_site_scripting_event
patterns:
- event
- async function ($<!>event, $<_>) {}
- async ($<!>event, $<_>) => {}
languages:
- javascript
severity: high
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
const { exec, execSync, spawn, spawnSync } = require('node:child_process');

exports.handler = async (event) => {
exports.handler = async (event, _context) => {
exec("ls "+event["user_dir"]+"| wc -l", (err, stdout, stderr) => {
// do something
});
Expand All @@ -12,4 +12,4 @@ exports.handler = async (event) => {
spawn(event["query"]);

spawnSync("grep " + event["tmp"])
};
};
4 changes: 2 additions & 2 deletions javascript/aws_lambda/query_injection.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@ patterns:
auxiliary:
- id: javascript_aws_lambda_query_injection_user_input
patterns:
- event.$<_>
- event[$<_>]
- async function ($<!>event, $<_>) {}
- async ($<!>event, $<_>) => {}
- id: javascript_aws_lambda_query_injection_hash
patterns:
- |
Expand Down
3 changes: 2 additions & 1 deletion javascript/aws_lambda/sql_injection.yml
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,8 @@ patterns:
auxiliary:
- id: javascript_aws_lambda_sql_injection_event
patterns:
- event.$<_>
- async function ($<!>event, $<_>) {}
- async ($<!>event, $<_>) => {}
- id: javascript_aws_lambda_sql_injection_pg_client
patterns:
- new Client()
Expand Down
4 changes: 2 additions & 2 deletions javascript/lang/format_string_using_user_input.yml
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,8 @@ auxiliary:
- req.cookies
- req.headers
# AWS
- event.$<_>
- event[$<_>]
- async function ($<!>event, $<_>) {}
- async ($<!>event, $<_>) => {}
severity: low
metadata:
description: "User input in format string detected."
Expand Down
35 changes: 23 additions & 12 deletions javascript/lang/hardcoded_secret.yml
Original file line number Diff line number Diff line change
@@ -1,26 +1,37 @@
patterns:
- pattern: |
{ $<KEY>: $<STRING_LITERAL> }
const $<NAME> = $<STRING_LITERAL>
filters:
- variable: KEY
values:
- clientSecret
- secretOrKey
- consumerSecret
- variable: NAME
regex: (?i)(password|api_?key|secret)\b
- variable: STRING_LITERAL
detection: string_literal
contains: false
- not:
variable: STRING_LITERAL
string_regex: \A[*•]+\z
- pattern: |
$<_>.$<KEY> = $<STRING_LITERAL>
$<_>.$<NAME> = $<STRING_LITERAL>
filters:
- variable: KEY
values:
- clientSecret
- secretOrKey
- consumerSecret
- variable: NAME
regex: (?i)(password|api_?key|secret)\b
- variable: STRING_LITERAL
detection: string_literal
contains: false
- not:
variable: STRING_LITERAL
string_regex: \A[*•]+\z
- pattern: |
{ $<!>$<NAME>: $<STRING_LITERAL> }
filters:
- variable: NAME
regex: (?i)(password|api_?key|secret)\b
- variable: STRING_LITERAL
detection: string_literal
contains: false
- not:
variable: STRING_LITERAL
string_regex: \A[*•]+\z
- pattern: crypto.$<METHOD>($<_>, $<STRING_LITERAL>$<...>)
filters:
- variable: METHOD
Expand Down
35 changes: 35 additions & 0 deletions javascript/lang/hardcoded_secret/.snapshots/unsecure_assigment.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,4 +34,39 @@ high:
parent_line_number: 2
snippet: config.clientSecret = "secretHardcodedString"
fingerprint: 33f4ae54bd29e69c4afb8971fe2b4c1c_0
- rule:
cwe_ids:
- "798"
id: javascript_lang_hardcoded_secret
title: Hardcoded secret detected
description: |
## Description
Code is not a safe place to store secrets, use environment variables instead.
## Remediations
```javascript
passport.use(new OAuth2Strategy({
authorizationURL: 'https://www.example.com/oauth2/authorize',
tokenURL: 'https://www.example.com/oauth2/token',
clientID: process.env.CLIENT_ID,
clientSecret: process.env.CLIENT_SECRET,
callbackURL: "http://localhost:3000/auth/example/callback"
},
function(accessToken, refreshToken, profile, cb) {
User.findOrCreate({ exampleId: profile.id }, function (err, user) {
return cb(err, user);
});
}
));
```
## Resources
- [OWASP hardcoded passwords](https://owasp.org/www-community/vulnerabilities/Use_of_hard-coded_password)
documentation_url: https://docs.bearer.com/reference/rules/javascript_lang_hardcoded_secret
line_number: 4
filename: /tmp/scan/unsecure_assigment.js
parent_line_number: 4
snippet: const apiKey = "oops"
fingerprint: 33f4ae54bd29e69c4afb8971fe2b4c1c_1

12 changes: 3 additions & 9 deletions javascript/lang/hardcoded_secret/.snapshots/unsecure_object.yml
Original file line number Diff line number Diff line change
Expand Up @@ -29,18 +29,12 @@ high:
## Resources
- [OWASP hardcoded passwords](https://owasp.org/www-community/vulnerabilities/Use_of_hard-coded_password)
documentation_url: https://docs.bearer.com/reference/rules/javascript_lang_hardcoded_secret
line_number: 1
line_number: 3
filename: /tmp/scan/unsecure_object.js
category_groups:
- PII
- Personal Data
parent_line_number: 1
snippet: |-
{
clientID: process.env["GOOGLE_CLIENT_ID"],
clientSecret: "secretHardcodedString",
callbackURL: "/oauth2/redirect/google",
scope: ["profile"],
}
parent_line_number: 3
snippet: 'clientSecret: "secretHardcodedString"'
fingerprint: 08b891215f23b5f7082f674966366927_0

4 changes: 4 additions & 0 deletions javascript/lang/hardcoded_secret/testdata/secure.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,3 +13,7 @@ crypto.privateEncrypt({ passphrase: process.env["SECRET"] }, buffer)

const s = crypto.createSign('RSA-SHA256')
s.sign(process.env["SECRET"], "utf-8")

const apiKey = "**"
o.password = "***"
const foo = { password: "••" }
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
const config = {};
config.clientSecret = "secretHardcodedString";

const apiKey = "oops"
4 changes: 2 additions & 2 deletions javascript/lang/http_url_using_user_input.yml
Original file line number Diff line number Diff line change
Expand Up @@ -72,8 +72,8 @@ auxiliary:
- req.cookies
- req.headers
# AWS
- event.$<_>
- event[$<_>]
- async function ($<!>event, $<_>) {}
- async ($<!>event, $<_>) => {}
severity: high
metadata:
description: "HTTP communication with user-controlled destination detected."
Expand Down
72 changes: 72 additions & 0 deletions javascript/lang/http_url_using_user_input/.snapshots/bad.yml
Original file line number Diff line number Diff line change
Expand Up @@ -215,4 +215,76 @@ high:
parent_line_number: 27
snippet: request(url, function () {})
fingerprint: 62309be37a26b5016cdbcb3c143da49f_5
- rule:
cwe_ids:
- "918"
id: javascript_lang_http_url_using_user_input
title: HTTP communication with user-controlled destination detected.
description: |
## Description
Applications should not connect to locations formed from user input.
This rule checks for URLs containing user-supplied data.
## Remediations
❌ Avoid using user input in HTTP URLs:
```javascript
const response = axios.get(`https://${req.params.host}`)
```
✅ Use user input indirectly to form a URL:
```javascript
const hosts = new Map([
["option1", "api1.com"],
["option2", "api2.com"]
])
const host = hosts.get(req.params.host)
const response = axois.get(`https://${host}`)
```
documentation_url: https://docs.bearer.com/reference/rules/javascript_lang_http_url_using_user_input
line_number: 31
filename: /tmp/scan/bad.js
parent_line_number: 31
snippet: axios.get(event.url)
fingerprint: 62309be37a26b5016cdbcb3c143da49f_6
- rule:
cwe_ids:
- "918"
id: javascript_lang_http_url_using_user_input
title: HTTP communication with user-controlled destination detected.
description: |
## Description
Applications should not connect to locations formed from user input.
This rule checks for URLs containing user-supplied data.
## Remediations
❌ Avoid using user input in HTTP URLs:
```javascript
const response = axios.get(`https://${req.params.host}`)
```
✅ Use user input indirectly to form a URL:
```javascript
const hosts = new Map([
["option1", "api1.com"],
["option2", "api2.com"]
])
const host = hosts.get(req.params.host)
const response = axois.get(`https://${host}`)
```
documentation_url: https://docs.bearer.com/reference/rules/javascript_lang_http_url_using_user_input
line_number: 35
filename: /tmp/scan/bad.js
parent_line_number: 35
snippet: axios.get(event["url"])
fingerprint: 62309be37a26b5016cdbcb3c143da49f_7

9 changes: 9 additions & 0 deletions javascript/lang/http_url_using_user_input/testdata/bad.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,3 +25,12 @@ const request = require('request')
const imageRequest = request.get(url)

request(url, function () {})


export const handler = async (event, context) => {
axios.get(event.url)
}

exports.handler = async function (event, context) {
axios.get(event["url"])
}
8 changes: 8 additions & 0 deletions javascript/lang/http_url_using_user_input/testdata/ok.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,3 +25,11 @@ const request = require('request')
const imageRequest = request.get(url)

request(url, function () {})

export const handler = async (event, context) => {
axios.get(url)
}

exports.handler = async function (event, context) {
axios.get(url)
}
71 changes: 71 additions & 0 deletions javascript/lang/raw_html_using_user_input.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
languages:
- javascript
patterns:
- pattern: $<STRING>
filters:
- variable: STRING
string_regex: <\w+(\s[^>]*)?>
- variable: STRING
detection: javascript_lang_raw_html_using_user_input_user_input
- not:
variable: STRING
detection: javascript_lang_raw_html_using_user_input_sanitized
auxiliary:
- id: javascript_lang_raw_html_using_user_input_user_input_source
patterns:
# Express
- req.params
- req.query
- req.body
- req.cookies
- req.headers
# AWS
- async function ($<!>event, $<_>) {}
- async ($<!>event, $<_>) => {}
- id: javascript_lang_raw_html_using_user_input_user_input
patterns:
- pattern: $<USER_INPUT>
filters:
- variable: USER_INPUT
detection: javascript_lang_raw_html_using_user_input_user_input_source
contains: false
- id: javascript_lang_raw_html_using_user_input_sanitized
patterns:
- pattern: sanitizeHtml($<SANITIZED_USER_INPUT>$<...>)
filters:
- variable: SANITIZED_USER_INPUT
detection: javascript_lang_raw_html_using_user_input_user_input
severity: high
metadata:
description: "Unsanitized user input detected in raw HTML string."
remediation_message: |
## Description
Applications should not include unsanitized user input in HTML. This
can allow cross-site scripting (XSS) attacks.
## Remediations
❌ Avoid including user input directly in HTML strings:
```javascript
const html = `<h1>${req.params.title}</h1>`
```
✅ Use a framework or templating language to construct the HTML.
✅ When HTML strings must be used, sanitize user input:
```javascript
import sanitizeHtml from 'sanitize-html'
const sanitizedTitle = sanitizeHtml(req.params.title)
const html = `<h1>${sanitizedTitle}</h1>`
```
## Resources
- [OWASP Cross-Site Scripting (XSS) Cheatsheet](https://cheatsheetseries.owasp.org/cheatsheets/Cross_Site_Scripting_Prevention_Cheat_Sheet.html)
cwe_id:
- 79
id: javascript_lang_raw_html_using_user_input
documentation_url: https://docs.bearer.com/reference/rules/javascript_lang_raw_html_using_user_input
Loading

0 comments on commit 327b90d

Please sign in to comment.