Exemple #1
0
def transactions(
    request: Request,
    account: str,
    sep6: bool = False,
) -> Response:
    try:
        limit = _validate_limit(request.GET.get("limit"))
    except ValueError:
        return render_error_response("invalid limit",
                                     status_code=status.HTTP_400_BAD_REQUEST)

    protocol_filter = {
        "sep6_enabled": True
    } if sep6 else {
        "sep24_enabled": True
    }
    if not request.GET.get("asset_code"):
        return render_error_response("asset_code is required")
    elif not Asset.objects.filter(code=request.GET.get("asset_code"),
                                  **protocol_filter).exists():
        return render_error_response("invalid asset_code")

    translation_dict = {
        "asset_code": "asset__code",
        "no_older_than": "started_at__gte",
        "kind": "kind",
    }

    qset_filter = _compute_qset_filters(request.GET, translation_dict)
    qset_filter["stellar_account"] = account

    # Since the Transaction IDs are UUIDs, rather than in the chronological
    # order of their creation, we map the paging ID (if provided) to the
    # started_at field of a Transaction.
    paging_id = request.GET.get("paging_id")
    if paging_id:
        try:
            start_transaction = Transaction.objects.get(id=paging_id)
        except Transaction.DoesNotExist:
            return render_error_response(
                "invalid paging_id", status_code=status.HTTP_400_BAD_REQUEST)
        qset_filter["started_at__lt"] = start_transaction.started_at

    protocol = Transaction.PROTOCOL.sep6 if sep6 else Transaction.PROTOCOL.sep24
    transactions_qset = Transaction.objects.filter(protocol=protocol,
                                                   **qset_filter)
    if limit:
        transactions_qset = transactions_qset[:limit]

    serializer = TransactionSerializer(
        transactions_qset,
        many=True,
        context={
            "request": request,
            "same_asset": True,
            "sep6": sep6
        },
    )

    return Response({"transactions": serializer.data})
Exemple #2
0
def transaction(
    request: Request,
    account: str,
    sep6: bool = False,
) -> Response:
    try:
        request_transaction = _get_transaction_from_request(
            request,
            account=account,
            sep6=sep6,
        )
    except (AttributeError, ValidationError) as exc:
        return render_error_response(str(exc),
                                     status_code=status.HTTP_400_BAD_REQUEST)
    except Transaction.DoesNotExist:
        return render_error_response("transaction not found",
                                     status_code=status.HTTP_404_NOT_FOUND)
    serializer = TransactionSerializer(
        request_transaction,
        context={
            "request": request,
            "sep6": sep6
        },
    )
    return Response({"transaction": serializer.data})
Exemple #3
0
def more_info(request: Request, sep6: bool = False) -> Response:
    try:
        request_transaction = _get_transaction_from_request(request, sep6=sep6)
    except (AttributeError, ValidationError) as exc:
        return render_error_response(str(exc), content_type="text/html")
    except Transaction.DoesNotExist:
        return render_error_response(
            _("transaction not found"),
            status_code=status.HTTP_404_NOT_FOUND,
            content_type="text/html",
        )

    serializer = TransactionSerializer(request_transaction,
                                       context={
                                           "request": request,
                                           "sep6": sep6
                                       })
    tx_json = json.dumps({"transaction": serializer.data})
    context = {
        "tx_json": tx_json,
        "amount_in": serializer.data.get("amount_in"),
        "amount_out": serializer.data.get("amount_out"),
        "amount_fee": serializer.data.get("amount_fee"),
        "transaction": request_transaction,
        "asset_code": request_transaction.asset.code,
    }
    if request_transaction.kind == Transaction.KIND.deposit:
        content = rdi.content_for_template(Template.MORE_INFO,
                                           transaction=request_transaction)
        if request_transaction.status == Transaction.STATUS.pending_user_transfer_start:
            context.update(instructions=rdi.instructions_for_pending_deposit(
                request_transaction))
    else:
        content = rwi.content_for_template(Template.MORE_INFO,
                                           transaction=request_transaction)
    if content:
        context.update(content)

    if registered_scripts_func is not scripts:
        logger.warning(
            "DEPRECATED: the `scripts` Polaris integration function will be "
            "removed in Polaris 2.0 in favor of allowing the anchor to override "
            "and extend Polaris' Django templates. See the Template Extensions "
            "documentation for more information.")
    context["scripts"] = registered_scripts_func(content)

    # more_info.html will update the 'callback' parameter value to 'success' after
    # making the callback. If the page is then reloaded, the callback is not included
    # in the rendering context, ensuring only one successful callback request is made.
    callback = request.GET.get("callback")
    if callback and callback != "success":
        context["callback"] = callback

    return Response(context, template_name="polaris/more_info.html")
Exemple #4
0
def more_info(request: Request, sep6: bool = False) -> Response:
    try:
        request_transaction = _get_transaction_from_request(request, sep6=sep6)
    except (AttributeError, ValidationError) as exc:
        return render_error_response(str(exc), content_type="text/html")
    except Transaction.DoesNotExist:
        return render_error_response(
            _("transaction not found"),
            status_code=status.HTTP_404_NOT_FOUND,
            content_type="text/html",
        )

    serializer = TransactionSerializer(request_transaction,
                                       context={
                                           "request": request,
                                           "sep6": sep6
                                       })
    tx_json = json.dumps({"transaction": serializer.data})
    resp_data = {
        "tx_json": tx_json,
        "amount_in": serializer.data.get("amount_in"),
        "amount_out": serializer.data.get("amount_out"),
        "amount_fee": serializer.data.get("amount_fee"),
        "transaction": request_transaction,
        "asset_code": request_transaction.asset.code,
    }
    if request_transaction.kind == Transaction.KIND.deposit:
        content = rdi.content_for_template(Template.MORE_INFO,
                                           transaction=request_transaction)
        if request_transaction.status == Transaction.STATUS.pending_user_transfer_start:
            resp_data["instructions"] = rdi.instructions_for_pending_deposit(
                request_transaction)
    else:
        content = rwi.content_for_template(Template.MORE_INFO,
                                           transaction=request_transaction)

    resp_data["scripts"] = registered_scripts_func(content)
    if content:
        resp_data.update(content)

    callback = request.GET.get("callback")
    if callback:
        resp_data["callback"] = callback

    return Response(resp_data, template_name="transaction/more_info.html")
Exemple #5
0
def make_on_change_callback(transaction: Transaction,
                            timeout: Optional[int] = None) -> RequestsResponse:
    """
    Makes a POST request to `transaction.on_change_callback`, a URL
    provided by the client. The request will time out in
    ``settings.CALLBACK_REQUEST_TIMEOUT`` seconds if _timeout_ is not specified.

    The client is responsible for providing a publicly-accessible URL that
    responds within the timeout period. Polaris will continue processing
    `transaction` regardless of the result of this request.

    :raises: A ``requests.RequestException`` subclass or ``ValueError``
    :returns: The ``requests.Response`` object for the request
    """
    if (not transaction.on_change_callback
            or transaction.on_change_callback.lower() == "postmessage"):
        raise ValueError("invalid or missing on_change_callback")
    if not timeout:
        timeout = settings.CALLBACK_REQUEST_TIMEOUT
    return post(
        url=transaction.on_change_callback,
        json=TransactionSerializer(transaction).data,
        timeout=timeout,
    )