Risk Evaluation

    Access Stripe's machine learning system judgments in the Dashboard and the API.

    At Stripe Radar’s core is an adaptive machine learning system that evaluates each payment’s risk level in real time. It uses hundreds of signals about each payment, and taps into data across our network of millions of businesses, to predict whether a payment is likely to be fraudulent.

    Our machine learning system is flexible and responsive, continuously learns from new customer purchase patterns and transaction features, and incorporates feedback from you whenever payments are indicated as fraudulent.

    Risk outcomes

    Stripe’s machine learning models evaluate how likely it is that a payment might be fraudulent. This judgment can take one of three values:

    Each payment includes information on the outcome of our risk evaluation. Payments with an elevated or high risk level include details of the primary risk factor that we identified. If a payment is declined, Stripe also includes any information we receive from the card issuer as part of the outcome.

    Stripe’s risk outcome (and risk score for users of Radar for Fraud Teams) in the Dashboard.

    The outcome for each payment is available when viewing a payment in the Dashboard or through the API as part of the Charge object’s Outcome attribute.

    High risk payments

    Stripe reports payments as high risk when we believe they are likely to be fraudulent. Payments of this risk level are blocked by default.

    A high risk payment in the Dashboard.

    On the Charge object of a high risk payment, the risk_level is set to highest.

    ...
    "outcome":
    {
      "network_status": "not_sent_to_network",
      "reason": "highest_risk_level",
      "risk_level": "highest",
      "risk_score": "92", // Provided only with Stripe Radar for Fraud Teams
      "seller_message": "Stripe blocked this charge as too risky.",
      "type": "blocked",
    }
    ...
    

    If Stripe Radar ever blocks a payment that you know is legitimate, you can remove the block using the Dashboard. To do this, view the payment in the Dashboard and click the Mark as safe button. Marking a payment as safe doesn’t retry the payment, but it does prevent Stripe Radar from blocking future payment attempts with that card or email address.

    Elevated risk payments

    Elevated risk payments have an increased chance of being fraudulent. Payments of this risk level are allowed by default. If you are using Stripe Radar for Fraud Teams, elevated risk payments are automatically placed into your review queue for you to take a closer look.

    An elevated risk payment in the Dashboard.

    On the Charge object of an elevated risk payment, the risk_level is set to elevated.

    ...
    "outcome": {
      "network_status": "approved_by_network",
      "reason": "elevated_risk_level",
      "risk_level": "elevated",
      "risk_score"": "56", // Provided only with Stripe Radar for Fraud Teams
      "seller_message": "Stripe evaluated this charge as having elevated risk, and placed it in your manual review queue.",
      "type": "manual_review"
    }
    ...
    

    Normal risk payments

    Payments with a normal risk evaluation have fewer characteristics that are strongly indicative of fraud than payments with elevated or high risk levels. However, we recommend that you continue to be vigilant when fulfilling these orders. Payments that have normal risk can still turn out to be fraudulent and there are other possible types of fraud that can be committed later on in the order process.

    A normal risk payment in the Dashboard.

    On the Charge object of a successful payment with normal risk, the risk_level is set to normal.

    ...
    "outcome":
    {
      "network_status": "approved_by_network",
      "reason": null,
      "seller_message": "The charge was authorized.",
      "risk_level": "normal",
      "risk_score": "23", // Provided only with Stripe Radar for Fraud Teams
      "type": "authorized",
    }
    ...
    

    Searching for a specific risk level in the Dashboard

    You can search for payments of a specific risk level using the risk_level search term and the desired risk level. For example, a search for risk_level:highest returns a list of all payments with a high risk level. Likewise, a search for risk_level:elevated returns a list of all payments with an elevated risk level.

    Searching for elevated risk payments in the Dashboard.

    Feedback on risk evaluations

    While we utilize information across our network to evaluate a payment, you may have additional information about a payment as a result of a customer interaction. Stripe’s machine learning models respond to feedback you share with us, and you can help improve our fraud detection algorithms by refunding and reporting payments that you believe are fraudulent.

    Refunding fraudulent payments helps improve our fraud detection algorithms and the accuracy of our risk evaluations for this payment, and similar ones in the future.

    To refund a payment and mark it as fraudulent using the Dashboard:

    1. Click Refund
    2. Select Fraudulent from the list of refunds
    3. Provide a brief explanation

    You can also indicate that a payment is fraudulent when you create a refund using the API by providing fraudulent as the value for reason. This adds the email address and card fingerprint associated with the payment to the default email address and card fingerprint block lists.

    # Set your secret key: remember to change this to your live secret key in production
    # See your keys here: https://dashboard.stripe.com/account/apikeys
    Stripe.api_key = "sk_test_4eC39HqLyjWDarjtT1zdp7dc"
    
    # If you haven't refunded the charge, you can do so and let Stripe
    # know it was fraudulent in one step.
    charge = Stripe::Charge.retrieve(charge_id)
    charge.refunds.create(reason: 'fraudulent')
    
    # If you already refunded the charge (without specifying the
    # 'fraudulent' reason), you can still let us know it was fraudulent.
    refunded_charge = Stripe::Charge.retrieve(refunded_charge_id)
    refunded_charge.mark_as_fraudulent
    
    # Set your secret key: remember to change this to your live secret key in production
    # See your keys here: https://dashboard.stripe.com/account/apikeys
    stripe.api_key = "sk_test_4eC39HqLyjWDarjtT1zdp7dc"
    
    # If you haven't refunded the charge, you can do so and let Stripe
    # know it was fraudulent in one step.
    charge = stripe.Charge.retrieve(charge_id)
    charge.refunds.create(reason='fraudulent')
    
    # If you already refunded the charge (without specifying the
    # 'fraudulent' reason), you can still let us know it was fraudulent.
    refunded_charge = stripe.Charge.retrieve(refunded_charge_id)
    refunded_charge.mark_as_fraudulent()
    
    // Set your secret key: remember to change this to your live secret key in production
    // See your keys here: https://dashboard.stripe.com/account/apikeys
    \Stripe\Stripe::setApiKey("sk_test_4eC39HqLyjWDarjtT1zdp7dc");
    
    // If you haven't refunded the charge, you can do so and let Stripe
    // know it was fraudulent in one step.
    $charge = \Stripe\Charge::retrieve($charge_id);
    $charge->refunds->create(array("reason" => "fraudulent"));
    
    // If you already refunded the charge (without specifying the
    // 'fraudulent' reason), you can still let us know it was fraudulent.
    $refunded_charge = \Stripe\Charge::retrieve($refunded_charge_id);
    $refunded_charge->markAsFraudulent();
    
    // Set your secret key: remember to change this to your live secret key in production
    // See your keys here: https://dashboard.stripe.com/account/apikeys
    Stripe.apiKey = "sk_test_4eC39HqLyjWDarjtT1zdp7dc";
    
    // If you haven't refunded the charge, you can do so and let Stripe
    // know it was fraudulent in one step.
    Charge charge = Charge.retrieve(chargeId);
    
    Map<String, Object> refundParams = new HashMap<String, Object>();
    refundParams.put("reason", "fraudulent");
    
    charge.refund(refundParams);
    
    // If you already refunded the charge (without specifying the
    // 'fraudulent' reason), you can still let us know it was fraudulent.
    Charge refundedCharge = Charge.retrieve(refundedChargeId);
    refundedCharge.markFraudulent((RequestOptions) null);
    
    // Set your secret key: remember to change this to your live secret key in production
    // See your keys here: https://dashboard.stripe.com/account/apikeys
    var stripe = require("stripe")("sk_test_4eC39HqLyjWDarjtT1zdp7dc");
    
    // If you haven't refunded the charge, you can do so and let Stripe
    // know it was fraudulent in one step.
    stripe.charges.createRefund(
      charge_id, {"reason": "fraudulent"})
    
    // If you already refunded the charge (without specifying the
    // 'fraudulent' reason), you can still let us know it was fraudulent.
    stripe.charges.markAsFraudulent(charge_id);
    

    For a small subset of charges, Stripe modifies the reported risk score so we can measure the performance of our models and obtain data for subsequent model development. This allows Stripe to ensure key metrics like false positive rate and recall remain within desirable bounds, and that model performance continues to improve.

    If you would not like the protection of Stripe Radar’s machine learning models, you can opt out by contacting our Support team.

    Next steps

    Now that you know more about Stripe Radar's risk evaluations, read on to learn about using reviews.

    Questions?

    We're always happy to help with code or other questions you might have! Search our documentation, contact support, or connect with our sales team. You can also chat live with other developers in #stripe on freenode.

    Was this page helpful? Yes No

    Send

    Thank you for helping improve Stripe's documentation. If you need help or have any questions, please consider contacting support.