Beispiel #1
0
    def test_multiple_sensitive_data_fields_get_marked_when_added(self):
        cased.add_sensitive_field("email")
        cased.add_sensitive_field("phone")
        processor = SensitiveDataProcessor(event_with_email_and_phone_field)

        assert processor.process() == {
            ".cased": {
                "pii": {
                    "email": [{
                        "begin": 0,
                        "end": 19,
                        "label": "email"
                    }],
                    "phone": [{
                        "begin": 0,
                        "end": 12,
                        "label": "phone"
                    }],
                }
            },
            "action": "user.create",
            "actor": "some-actor",
            "email": "*****@*****.**",
            "phone": "555-555-5555",
        }
Beispiel #2
0
 def test_process_does_everything_needed(self):
     handler = SensitiveDataHandler("username", username_regex)
     processor = SensitiveDataProcessor(
         event_with_multiple_keys_matching.copy(), [handler])
     assert processor.process() == {
         ".cased": {
             "pii": {
                 "friend_username": [{
                     "begin": 0,
                     "end": 15,
                     "label": "username"
                 }],
                 "new_username": [
                     {
                         "begin": 0,
                         "end": 13,
                         "label": "username"
                     },
                     {
                         "begin": 23,
                         "end": 39,
                         "label": "username"
                     },
                 ],
             }
         },
         "action": "user.create",
         "actor": "some-actor",
         "friend_username": "******",
         "new_username": "******",
     }
Beispiel #3
0
 def test_process_does_everything_needed_with_redact_configured(self):
     cased.redact_before_publishing = True
     handler = SensitiveDataHandler("username", username_regex)
     processor = SensitiveDataProcessor(
         event_with_multiple_keys_matching.copy(), [handler])
     assert processor.process() == {
         ".cased": {
             "pii": {
                 "friend_username": [{
                     "begin": 0,
                     "end": 15,
                     "label": "username"
                 }],
                 "new_username": [
                     {
                         "begin": 0,
                         "end": 13,
                         "label": "username"
                     },
                     {
                         "begin": 23,
                         "end": 39,
                         "label": "username"
                     },
                 ],
             }
         },
         "action": "user.create",
         "actor": "some-actor",
         "friend_username": "******",
         "new_username": "******",
     }
Beispiel #4
0
    def test_redact_data_with_multiple_key_matches(self):
        handler = SensitiveDataHandler("username", username_regex)
        processor = SensitiveDataProcessor(
            event_with_multiple_keys_matching.copy(), [handler])

        ranges = {
            "friend_username": [{
                "begin": 0,
                "end": 15,
                "label": "username"
            }],
            "new_username": [
                {
                    "begin": 0,
                    "end": 13,
                    "label": "username"
                },
                {
                    "begin": 23,
                    "end": 39,
                    "label": "username"
                },
            ],
        }

        assert processor.redact_data(ranges) == {
            "action": "user.create",
            "actor": "some-actor",
            "friend_username": "******",
            "new_username": "******",
        }
Beispiel #5
0
    def test_redact_data_with_multiple_handlers(self):
        cased.redact_before_publishing = True

        handler1 = SensitiveDataHandler("username", username_regex)
        handler2 = SensitiveDataHandler("name", name_regex)

        processor = SensitiveDataProcessor(
            event_with_multiple_keys_of_different_matches.copy(),
            [handler1, handler2])

        assert processor.process() == {
            ".cased": {
                "pii": {
                    "new_username": [{
                        "begin": 0,
                        "end": 13,
                        "label": "username"
                    }],
                    "name": [{
                        "begin": 5,
                        "end": 10,
                        "label": "name"
                    }],
                }
            },
            "name": "Jane XXXXX",
            "action": "user.create",
            "actor": "some-actor",
            "phone": "555-555-5555",
            "new_username": "******",
        }
Beispiel #6
0
    def test_ranges_from_event_works_with_multiple_key_matches(self):
        handler = SensitiveDataHandler("username", username_regex)
        processor = SensitiveDataProcessor(
            event_with_multiple_keys_matching.copy(), [handler])

        assert processor.ranges_from_event(
            event_with_multiple_keys_matching.copy(), handler) == {
                "friend_username": [{
                    "begin": 0,
                    "end": 15,
                    "label": "username"
                }],
                "new_username": [
                    {
                        "begin": 0,
                        "end": 13,
                        "label": "username"
                    },
                    {
                        "begin": 23,
                        "end": 39,
                        "label": "username"
                    },
                ],
            }
Beispiel #7
0
    def test_add_ranges_to_events(self):
        handler = SensitiveDataHandler("username", username_regex)
        processor = SensitiveDataProcessor(event.copy(), [handler])
        ranges = {
            "new_username": [{
                "begin": 0,
                "end": 13,
                "label": "username"
            }]
        }

        assert processor.add_ranges_to_event(ranges) == {
            ".cased": {
                "pii": {
                    "new_username": [{
                        "begin": 0,
                        "end": 13,
                        "label": "username"
                    }],
                },
            },
            "action": "user.create",
            "actor": "some-actor",
            "new_username": "******",
        }
Beispiel #8
0
    def test_ranges_from_event_works_with_multiple_handlers_and_field_setting(
            self):
        handler1 = SensitiveDataHandler("username", username_regex)
        handler2 = SensitiveDataHandler("name", name_regex)
        cased.add_sensitive_field("phone")

        processor = SensitiveDataProcessor(
            event_with_multiple_keys_of_different_matches.copy(),
            [handler1, handler2])

        assert processor.process()[".cased"]["pii"] == {
            "new_username": [{
                "begin": 0,
                "end": 13,
                "label": "username"
            }],
            "name": [{
                "begin": 5,
                "end": 10,
                "label": "name"
            }],
            "phone": [{
                "begin": 0,
                "end": 12,
                "label": "phone"
            }],
        }

        cased.sensitive_fields = set()
Beispiel #9
0
    def test_ranges_from_event(self):
        handler = SensitiveDataHandler("username", username_regex)
        processor = SensitiveDataProcessor(event, [handler])

        assert processor.ranges_from_event(event, handler) == {
            "new_username": [{
                "begin": 0,
                "end": 13,
                "label": "username"
            }]
        }
Beispiel #10
0
    def test_sensitive_data_processor_has_default_handlers_if_set(self):
        handler = SensitiveDataHandler("username", username_regex)
        cased.add_handler(handler)

        processor = SensitiveDataProcessor(event)
        assert processor.data_handlers[0].label == handler.label

        cased.clear_handlers()
Beispiel #11
0
    def test_sensitive_data_processor_can_be_created_with_mutiple_handlers(
            self):
        handler1 = SensitiveDataHandler("username", username_regex)
        handler2 = SensitiveDataHandler("name", name_regex)

        processor = SensitiveDataProcessor(event, [handler1, handler2])
        assert processor.audit_event == event
        assert processor.data_handlers == [handler1, handler2]
Beispiel #12
0
    def test_ranges_from_event_works_with_multiple_matches(self):
        handler = SensitiveDataHandler("username", username_regex)
        processor = SensitiveDataProcessor(event_with_two_usernames, [handler])

        assert processor.ranges_from_event(event_with_two_usernames,
                                           handler) == {
                                               "new_username": [
                                                   {
                                                       "begin": 0,
                                                       "end": 13,
                                                       "label": "username"
                                                   },
                                                   {
                                                       "begin": 23,
                                                       "end": 39,
                                                       "label": "username"
                                                   },
                                               ]
                                           }
Beispiel #13
0
    def test_sensitive_data_fields_get_marked_when_added(self):
        cased.add_sensitive_field("email")
        processor = SensitiveDataProcessor(event_with_email_field)

        assert processor.process() == {
            ".cased": {
                "pii": {
                    "email": [{
                        "begin": 0,
                        "end": 19,
                        "label": "email"
                    }]
                },
            },
            "action": "user.create",
            "actor": "some-actor",
            "email": "*****@*****.**",
        }

        assert len(event_with_email_field["email"]) == 19
Beispiel #14
0
    def test_sensitive_data_fields_get_marked_with_explicit_setting(self):
        cased.clear_sensitive_fields()
        cased.sensitive_fields = {"email"}
        processor = SensitiveDataProcessor(event_with_email_field)

        assert processor.process() == {
            ".cased": {
                "pii": {
                    "email": [{
                        "begin": 0,
                        "end": 19,
                        "label": "email"
                    }]
                },
            },
            "action": "user.create",
            "actor": "some-actor",
            "email": "*****@*****.**",
        }

        assert (len(event_with_email_field["email"]) == 19
                )  # to confirm a match with the "end" parameter in pii
Beispiel #15
0
    def publish(cls, data, **params):
        if cased.disable_publishing:
            return None

        requestor = Requestor.publish_requestor(**params)
        publish_data = data.copy()

        # Using the plugin system, add any data from plugins that have been configured
        data_plugins = getattr(cased, "data_plugins", [])
        for plugin in data_plugins:
            instance = plugin(publish_data)
            additions = instance.additions()
            publish_data.update(additions)

        # Include context data, overriding it with any local publish data
        current_context = cased.context.current()
        always_merger.merge(current_context, publish_data)

        # Update the .cased with any PII ranges
        processor = SensitiveDataProcessor(current_context)
        final_publish_data = processor.process()

        # Add the item to a ReliabilityEngine backend. The backend can be configured
        # with a "backend" keyword arg passed to publish(), or with the global config.
        # By default, we try/except just in case the user misconfigured their ReliabilityEngine:
        # we'd rather still send the audit data then fail here. But we do log a message.
        # Additionally, if a ReliabilityBackend is not set, we will (optionally) log a warning.
        try:
            if "backend" in params:
                engine = ReliabilityEngine(backend=params["backend"])
                engine.add(publish_data)
            elif cased.reliability_backend:
                engine = ReliabilityEngine(backend=cased.reliability_backend)
                engine.add(publish_data)
            else:
                if cased.warn_if_no_reliability_backend:
                    log_info("No reliability backend has been set")
        except ReliabilityEngineError as e:
            log_info("""Reliability backend is misconfigured.
                Please check configuration. Client will still
                send audit data to Cased. Error: {}""".format(e))

        try:
            # Send to Cased
            response = requestor.request("post", "/", final_publish_data)
            log_info("Sent to Cased: " + str(final_publish_data))

            # Publish the item to any additional publishers
            additional_publishers = cased.additional_publishers
            for publisher in additional_publishers:
                try:
                    publisher.publish(final_publish_data)
                except AttributeError:
                    raise PublisherException(
                        "Publisher must implement publish()")

        except Exception as e:
            log_error(e)
            if cased.raise_on_publish_errors:
                raise
        finally:
            if cased.clear_context_after_publishing:
                cased.context.clear()

        return response
Beispiel #16
0
 def test_sensitive_data_processor_can_be_created(self):
     processor = SensitiveDataProcessor(event)
     assert processor.audit_event == event