From a4d216b7864159990d01411a3062c249493e4453 Mon Sep 17 00:00:00 2001 From: elsapet Date: Mon, 26 Feb 2024 18:52:07 +0200 Subject: [PATCH] feat(java): third parties ElasticSearch (CWE-201) (#261) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Cédric Fabianski --- rules/java/third_parties/elasticsearch.yml | 64 +++++++++++++++++++ .../java/third_parties/elasticsearch/test.js | 17 +++++ .../elasticsearch/testdata/main.java | 55 ++++++++++++++++ 3 files changed, 136 insertions(+) create mode 100644 rules/java/third_parties/elasticsearch.yml create mode 100644 tests/java/third_parties/elasticsearch/test.js create mode 100644 tests/java/third_parties/elasticsearch/testdata/main.java diff --git a/rules/java/third_parties/elasticsearch.yml b/rules/java/third_parties/elasticsearch.yml new file mode 100644 index 000000000..87a973039 --- /dev/null +++ b/rules/java/third_parties/elasticsearch.yml @@ -0,0 +1,64 @@ +imports: + - java_shared_lang_datatype + - java_shared_lang_instance +patterns: + - pattern: | + $.index($<_> -> $<_>.index().id().document($)); + filters: + - variable: ES_CLIENT + values: + - esClient + - variable: OBJECT_WITH_DATATYPES + detection: java_third_parties_elasticsearch_object_with_datatypes + - pattern: | + $.update($<_> -> $<_>.index().id().upsert($)$<...>); + filters: + - variable: ES_CLIENT + values: + - esClient + - variable: OBJECT_WITH_DATATYPES + detection: java_third_parties_elasticsearch_object_with_datatypes + - pattern: | + $.document($); + filters: + - variable: BUILDER + detection: java_third_parties_elasticsearch_index_request_builder + - variable: OBJECT_WITH_DATATYPES + detection: java_third_parties_elasticsearch_object_with_datatypes +auxiliary: + - id: java_third_parties_elasticsearch_object_with_datatypes + patterns: + - pattern: $<_> $ = new $<_>($<...>$$<...>); + focus: OBJ + filters: + - variable: DATA_TYPE + detection: java_shared_lang_datatype + - id: java_third_parties_elasticsearch_index_request_builder + patterns: + - pattern: $.Builder<$<_>> $ = new $.Builder<>(); + focus: BUILDER + filters: + - variable: INDEX_REQUEST + regex: \A(org\.elasticsearch\.action\.index\.)?IndexRequest\z +languages: + - java +skip_data_types: + - "Unique Identifier" +metadata: + description: Leakage of sensitive data to ElasticSearch + remediation_message: | + ## Description + Leaking sensitive data to third-party data tools is a common cause of data + leaks and can lead to data breaches. This rule looks for instances of + sensitive data sent to Elasticsearch. + + ## Remediations + When sending data to third-party services, ensure all sensitive data is removed. + + ## Resources + - [Elasticsearch docs](https://www.elastic.co/guide/en/elasticsearch/client/java-api-client/current/index.html) + cwe_id: + - 201 + associated_recipe: Elasticsearch + id: java_third_parties_elasticsearch + documentation_url: https://docs.bearer.com/reference/rules/java_third_parties_elasticsearch diff --git a/tests/java/third_parties/elasticsearch/test.js b/tests/java/third_parties/elasticsearch/test.js new file mode 100644 index 000000000..a6de62055 --- /dev/null +++ b/tests/java/third_parties/elasticsearch/test.js @@ -0,0 +1,17 @@ +const { createNewInvoker, getEnvironment } = require("../../../helper.js") +const { ruleId, ruleFile, testBase } = getEnvironment(__dirname) + +describe(ruleId, () => { + const invoke = createNewInvoker(ruleId, ruleFile, testBase) + + test("elasticsearch", () => { + const testCase = "main.java" + + const results = invoke(testCase) + + expect(results).toEqual({ + Missing: [], + Extra: [], + }) + }) +}) diff --git a/tests/java/third_parties/elasticsearch/testdata/main.java b/tests/java/third_parties/elasticsearch/testdata/main.java new file mode 100644 index 000000000..5bed863bd --- /dev/null +++ b/tests/java/third_parties/elasticsearch/testdata/main.java @@ -0,0 +1,55 @@ +// Use bearer:expected java_third_parties_elasticsearch to flag expected findings + +public class Foo { + public void bad(User user) { + // ... + ElasticsearchClient esClient = new ElasticsearchClient(transport); + Customer customer = new Customer("cust-1", user.email, user.name); + + esClient.indices().create(c -> c + .index("customers")); + // bearer:expected java_third_parties_elasticsearch + IndexResponse response = esClient.index(i -> i + .index("customers") + .id(customer.getSku()) + .document(customer)); + } + + public void bad2(User user) { + // ... + ElasticsearchClient esClient = new ElasticsearchClient(transport); + User esUser = new User("usr-1", user.email, user.name); + + // bearer:expected java_third_parties_elasticsearch + esClient.update(u -> u + .index("users") + .id("usr-1") + .upsert(esUser), + User.class); + } + + public void bad3(User user) { + Customer customer = new Customer("cust-1", user.email, user.name); + + IndexRequest.Builder indexReqBuilder = new IndexRequest.Builder<>(); + indexReqBuilder.index("cust-1"); + indexReqBuilder.id(customer.getSku()); + // bearer:expected java_third_parties_elasticsearch + indexReqBuilder.document(customer); + + IndexResponse response = esClient.index(indexReqBuilder.build()); + } + + public void good() { + // ... + ElasticsearchClient esClient = new ElasticsearchClient(transport); + Product product = new Product("prod-1", "item", 256); + + esClient.update(u -> u + .index("products") + .id("prod-1") + .upsert(product), + Product.class); + } + +} \ No newline at end of file