Exemplo n.º 1
0
    def post(self):
        url = request.get_json()["request_url"]
        host, path = self.parse_url(url)

        # Init managers and sessions
        hs_manager = HsManager()
        db_session = DatabaseManager().get_session()

        # Search
        try:
            start_search_time = time()
            search_data = hs_manager.search(domain=host,
                                            path=path,
                                            is_test=True)
            end_search_time = time()
        except AssertionError as e:
            Logger() \
                .event(category="hyperscan", action="hyperscan search") \
                .error(message=str(e)) \
                .out(severity=Severity.ERROR)
            DatabaseManager().return_session(db_session)
            return api_error(
                message="Something went wrong during Hyperscan search!",
                errors=str(e),
                status_code=400)

        # Convert ids into models
        domain_rules_data = {}
        redirect_rules_data = {}
        d_r_map = search_data["domain_rule_map"]

        for domain_id in d_r_map.keys():
            domain_rule = get_model_by_id(db_session, DomainRule, domain_id)
            domain_rules_data[domain_id] = db_encode_model(domain_rule)

            for rule_id in d_r_map[domain_id]:
                redirect_rule = get_model_by_id(db_session, RedirectRule,
                                                rule_id)
                redirect_rules_data[rule_id] = db_encode_model(redirect_rule,
                                                               expand=True)

        # Get final result
        final_redirect_rule, is_ambiguous = HsManager.pick_result(
            db_session, list(redirect_rules_data.keys()))

        # Fill in test data
        search_data[
            "final_result_id"] = final_redirect_rule.id if final_redirect_rule is not None else None
        search_data["is_ambiguous"] = is_ambiguous
        search_data["time"] = str(end_search_time - start_search_time)

        DatabaseManager().return_session(db_session)
        return make_response(
            jsonify({
                "domain_rules": domain_rules_data,
                "redirect_rules": redirect_rules_data,
                "search_data": search_data
            }), 200)
Exemplo n.º 2
0
    def get(self, content=None):
        del content
        host = request.host.split(":")[0]
        path = request.path

        # Stop spamming for favicon pls
        if path == "/favicon.ico":
            self.page_404()

        # Init managers and sessions
        hs_manager = HsManager()
        db_session = DatabaseManager().get_session()

        # Search
        try:
            matching_ids = None
            with HYPERSCAN_REQUESTS_REDIRECTED_DURATION_SECONDS.time(
            ):  # Metric
                matching_ids = hs_manager.search(domain=host, path=path)

            is_404 = matching_ids is None
        except AssertionError as e:
            Logger() \
                .event(category="hyperscan", action="hyperscan search failed") \
                .error(message=str(e)) \
                .out(severity=Severity.ERROR)
            DatabaseManager().return_session(db_session)
            is_404 = True

        if is_404:
            REQUESTS_REDIRECTED_TOTAL.labels("worker", "404",
                                             "not_found").inc()
            self.page_404()

        # Get final result
        with DB_LOOKUP_REQUESTS_REDIRECTED_DURATION_SECONDS.time():  # Metric
            final_redirect_rule, is_ambiguous = HsManager.pick_result(
                db_session, list(matching_ids))
            final_destination_url = final_redirect_rule.destination_rule.destination_url
            is_back_ref: bool = final_redirect_rule.destination_rule.is_rewrite

        # Do back reference
        if is_back_ref:
            final_destination_url = self.apply_back_reference(
                path, final_redirect_rule)

        # Add ambiguous request to db if needed
        if is_ambiguous or final_destination_url is None:
            from redirectory.libs_int.kubernetes import K8sManager, ManagementPod

            try:
                management_pod: ManagementPod = K8sManager(
                ).get_management_pod()
                management_pod.add_ambiguous_request(request.url)
            except AssertionError as e:
                Logger() \
                    .event(category="sync", action="sync ambiguous request",
                           dataset="Unable to sync ambiguous request with the management pod") \
                    .error(message=str(e)) \
                    .out(severity=Severity.ERROR)

            if final_destination_url is None:
                self.page_404()

        # Sanitize final redirect url
        final_destination_url = self.sanitize_outgoing_redirect(
            final_destination_url)

        DatabaseManager().return_session(db_session)

        if is_ambiguous:
            REQUESTS_REDIRECTED_TOTAL.labels("worker", "301",
                                             "ambiguous").inc()
        elif is_back_ref:
            REQUESTS_REDIRECTED_TOTAL.labels("worker", "301", "back_ref").inc()
        else:
            REQUESTS_REDIRECTED_TOTAL.labels("worker", "301", "normal").inc()

        return redirect(final_destination_url, 301)