简体   繁体   中英

I am getting IntegrationError: Invalid value for stripe.confirmCardPayment intent secret: value should be a client_secret string

I am following a Amazon clone guide to get me started with React JS. While being 4 days in im getting stuck after processing my Orders. I am using Stripe, Firebase, Axios and Express to do this. After clicking the Buy now button im getting the error:

Uncaught (in promise) IntegrationError: Invalid value for stripe.confirmCardPayment intent secret: value should be a client_secret string. You specified: true.

Tried every possible solution and the videoguide doesnt get this error or discuss this error in anyway.

Thanks in advance!

I wouldnt mind sharing my github so youre getting a full look at all my codes if need be.

This is my payment page code:

import React, { useEffect, useState } from "react";
import { Link, useHistory } from "react-router-dom";
import CheckoutProduct from "./CheckoutProduct";
import "./Payment.css";
import { useStateValue } from "./StateProvider";
import { CardElement, useStripe, useElements } from "@stripe/react-stripe-js";
import CurrencyFormat from "react-currency-format";
import { getBasketTotal } from "./reducer";
import axios from "./axios";
import {db} from "./firebase";

function Payment() {
  const [{ basket, user }, dispatch] = useStateValue();
  const history = useHistory();

  const stripe = useStripe();
  const elements = useElements();

  const [processing, setProcessing] = useState(false);
  const [succeeded, setSucceeded] = useState("");
  const [error, setError] = useState(null);
  const [disabled, setDisabled] = useState(true);
  const [clientSecret, setClientSecret] = useState(true);

  useEffect(() => {
    //zorgt ervoor dat ik betalingen kan aannemen
    const getClientSecret = async () => {
      const response = await axios({
        method: "post",
        url: `/payments/create?total=${getBasketTotal(basket) * 100}`
      });
      setClientSecret(response.data.clientSecret);
    };

    getClientSecret();
  }, [basket]);

  console.log("Mijn geheim is >>>>", clientSecret);

  const handleSubmit = async (event) => {
    // Stripe betalingen
    event.preventDefault();
    setProcessing(true);

    const payload = await stripe
      .confirmCardPayment(clientSecret, {
        payment_method: {
          card: elements.getElement(CardElement),
        },
      })
      .then(({ paymentIntent }) => {
        // betalingconfirmatie

        // bestelhistorie uit mijn database halen
        db.collection('users')
        .doc(user?.id)
        .collection('orders')
        .doc(paymentIntent.id)
        .set({
          basket: basket,
          amount: paymentIntent.amount,
          created: paymentIntent.created
        })


        setSucceeded(true);
        setError(null);
        setProcessing(false);

        dispatch({
          type: "EMPTY_BASKET",
        });

        history.replace("/orders");
      });
  };

  const handleChange = (event) => {
    // Kijkt naar veranderingen in de Cardelement
    // geeft errors aan wanneer de bezoeker zijn kaartgegevens niet goed intypt
    setDisabled(event.emtpy);
    setError(event.error ? event.error.message : "");
  };

  return (
    <div className="payment">
      <div className="paymentcontainer">
        <h1>
          Checkout (<Link to="/checkout">{basket?.length} items</Link>)
        </h1>

        {/* payment*/}
        <div className="paymentsection">
          <div className="paymenttitle">
            <h3>Bezorgadres</h3>
          </div>
          <div className="paymentaddress">
            <p>{user?.email}</p>
            <p>Melkdistel</p>
            <p>Almere, FL</p>
          </div>
        </div>

        {/* payment*/}
        <div className="paymentsection">
          <div className="paymenttitle">
            <h3>Artikelen</h3>
          </div>
          <div className="paymentitems">
            {basket.map((item) => (
              <CheckoutProduct
                id={item.id}
                title={item.title}
                image={item.image}
                price={item.price}
                rating={item.rating}
              />
            ))}
          </div>
        </div>

        {/* payment*/}
        <div className="paymentsection">
          <div className="paymenttitle">
            <h3>Betalingsmethode</h3>
          </div>
          <div className="paymentdetails">
            {/* Stripe */}

            <form onSubmit={handleSubmit}>
              <CardElement onChange={handleChange} />

              <div className="paymentpriceContainer">
                <CurrencyFormat
                  renderText={(value) => <h3>Order Totaal:{value}</h3>}
                  decimalScale={2}
                  value={getBasketTotal(basket)}
                  displayType={"text"}
                  thousandSeparator={true}
                  prefix={"$"}
                />
                <button disabled={processing || disabled || succeeded}>
                  <span>{processing ? <p>Processing</p> : "Buy Now"}</span>
                </button>
              </div>

              {/*Errors */}
              {error && <div>{error}</div>}
            </form>
          </div>
        </div>
      </div>
    </div>
  );
}

export default Payment;

This is my index.js code or my server:

/* eslint-disable max-len */
const functions = require("firebase-functions");
const express = require("express");
const cors = require("cors");
const stripe = require("stripe")("sk_xxx");

// API

// App config
const app = express();

// Middlewares
app.use(cors({origin: true}));
app.use(express.json());

// API Routes
app.get("/", (request, response) => response.status(200).send("hello world"));

app.post("/payments/create", async (request, response) => {
  const total = request.query.total;

  console.log("Payment request received", total);

  const paymentIntent = await stripe.paymentIntents.create({
    amount: total,
    currency: "usd",
  });

  // Good
  response.status(201).send({
    clientSecret: paymentIntent.client_secret,
  });
});

// Listen command
exports.api = functions.https.onRequest(app);

// http://localhost:5001/flowerpower-7c9f1/us-central1/api

控制台程序

Firstly, please don't share your Stripe secret keys!

The issue is that you're passing clientSecret: true to theconfirmCardPayment method, which instead expects the client_secret of a created PaymentIntent .

I note from the code you've provided that true is the default value of your clientSecret local React variable used in the confirmCardPayment call. The error you're seeing likely indicates that this value is not updated (via setClientSecret ) following your API call to /payments/create .

My recommendation to you would be verify that the /payments/create API does indeed create and return a PaymentIntent object and introduce error handling to your sever function to throw if/when that Stripe API call fails.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM