Cloud Code Functions
Integrations
การใช้งาน Stripe API ผ่าน Cloud Functions บน Back4App
13 นาที
การรวม stripe โดยใช้ cloud functions บทนำ ในคู่มือนี้ เราจะแสดงให้คุณเห็นว่าคุณจะรวม backend ที่โฮสต์ใน back4app กับ stripe api ได้อย่างไร ตัวเลือกสถาปัตยกรรมที่ดีที่สุดในการสร้างมันบน back4app คือการใช้ฟีเจอร์ที่ทรงพลังมากที่เรียกว่า cloud functions เมื่อคุณเสร็จสิ้นการรวมฟังก์ชันคลาวด์กับ stripe คุณจะสามารถใช้การรวมนี้สำหรับโครงการ front end ทั้งหมดของคุณ (web, ios, android) คู่มือนี้นำเสนอการรวม stripe ที่สมบูรณ์โดยใช้ตัวอย่างเว็บ ข้อกำหนดเบื้องต้น ในการทำตามบทเรียนนี้ คุณจะต้อง แอปที่สร้างขึ้นที่ back4app ติดตาม บทเรียนการสร้างแอปใหม่ เพื่อเรียนรู้วิธีการสร้างแอปที่ back4app บัญชีที่สร้างขึ้นใน stripe เป้าหมาย รวม stripe ในโครงการเว็บโดยใช้ back4app cloud functions stripe คืออะไร? stripe เป็นบริษัทเทคโนโลยีที่ดำเนินงานในกว่า 25 ประเทศ ซึ่งอนุญาตให้ทั้งบุคคลและธุรกิจสามารถรับชำระเงินผ่านทางอินเทอร์เน็ตได้ stripe มุ่งเน้นการให้บริการโครงสร้างพื้นฐานทางเทคนิค การป้องกันการฉ้อโกง และการธนาคารที่จำเป็นสำหรับการดำเนินการระบบการชำระเงินออนไลน์ บทแนะนำนี้จะพาคุณผ่านขั้นตอนการสร้างฟังก์ชันและการรวม stripe api เข้ากับ parse server ในแอปเว็บของคุณ โดยเฉพาะในคู่มือนี้ เราจะสร้างสภาพแวดล้อมที่ผู้ใช้สามารถเข้าสู่ระบบหรือสมัครสมาชิก ลงทะเบียนบัตรเครดิต และสร้างการซื้อที่เป็นตัวอย่างด้วยพวกเขาผ่าน stripe payments นอกจากนี้ คุณจะได้รับคำแนะนำเกี่ยวกับวิธีการตั้งค่าทั้งกระบวนการรวมถึงการทดสอบว่าการเชื่อมต่อกับเซิร์ฟเวอร์และ stripe api ทำงานได้อย่างถูกต้อง 1 สร้างบัญชี stripe ไปที่ stripe และคลิกที่ลงทะเบียนเพื่อ สร้างบัญชี ที่นั่น คุณเพียงแค่ต้องให้ข้อมูลส่วนบุคคลของคุณและประเทศที่บัญชีของคุณอยู่ ถัดไป ยืนยันบัญชี stripe ของคุณ (คุณจะได้รับอีเมลที่มีลิงก์การยืนยันจาก stripe) คลิกที่ลิงก์นั้น จากนั้นทำตามขั้นตอนเพื่อยืนยันที่อยู่อีเมล stripe ของคุณ 2 การตั้งค่าชั้นข้อมูลฐานข้อมูลของคุณ หลังจากกำหนดค่าบริการ stripe สำหรับขั้นตอนที่ 1 แล้ว ให้ไปที่แดชบอร์ดแอป back4app ของคุณเพื่อที่คุณจะได้ตั้งค่าฐานข้อมูลของคุณ ขั้นตอนนี้ไม่จำเป็น เนื่องจาก parse จะสร้างชั้นข้อมูลโดยอัตโนมัติในขณะที่ฟังก์ชันคลาวด์พยายามสร้างวัตถุใหม่ แต่เราจะผ่านขั้นตอนเหล่านี้เพื่ออธิบายว่าฟิลด์ใดจะถูกสร้างขึ้นและทำไม จะมีสองชั้นข้อมูลที่จะเก็บข้อมูลที่เกี่ยวข้องกับ stripe ของแอปของคุณ paymentmethod paymentmethod และ payment payment นี่คือวิธีการจัดเรียงคลาส paymentmethod paymentmethod type type (string) ค่าของมันจะเป็น “card” เสมอ; card card (object) จะเก็บข้อมูล stripe ที่สมบูรณ์เกี่ยวกับบัตรที่ลงทะเบียน; stripeid stripeid (string) id ที่อ้างอิงถึง paymentmethod นี้ใน backend ของ stripe; user user (pointer to parse user) การอ้างอิงโดยตรงถึงผู้ใช้ที่ paymentmethod นี้เป็นของ payment payment data data (object) จะเก็บข้อมูล stripe ที่สมบูรณ์เกี่ยวกับการชำระเงิน; user user (pointer to parse user) การอ้างอิงโดยตรงถึงผู้ใช้ที่การชำระเงินนี้เป็นของ เราจะเพิ่มคอลัมน์ค่าใหม่สองคอลัมน์ในแอปของคุณที่เรียกว่า string string ในคลาสเริ่มต้นของ user user ที่เรียกว่า setupsecret setupsecret และ customerid customerid ที่จะเก็บ stripe ids ที่เชื่อมโยง user user กับคู่ของมันใน stripe 3 การนำ cloud code ไปใช้ มาคอนฟิก ฟังก์ชัน cloud code https //docs parseplatform org/cloudcode/guide/#cloud functions ในแอป โดยการติดตั้งโมดูล stripe และปรับใช้โค้ด หากคุณต้องการเข้าใจสภาพแวดล้อมของ cloud code ให้ดีขึ้น ให้ตรวจสอบ คู่มือนี้ 3 1 รับคีย์ stripe ของคุณ ตอนนี้ เปิดแดชบอร์ด stripe ของคุณ ไปที่ นักพัฒนา นักพัฒนา ที่ด้านบน จากนั้นเลือก คีย์ api คีย์ api ในเมนูด้านซ้าย ในส่วนนี้ คุณจะสามารถเห็น คีย์ที่เผยแพร่ คีย์ที่เผยแพร่ และ คีย์ลับ คีย์ลับ ของคุณ จดบันทึกคีย์เหล่านี้ไว้ เพราะคุณจะต้องใช้มันในภายหลัง 3 2 ไฟล์ cloud code บนคอมพิวเตอร์ของคุณ ให้สร้างไฟล์ต่อไปนี้ ซึ่งจะรับผิดชอบในการติดตั้งโมดูลและเพิ่มฟังก์ชัน cloud code ของคุณไปยัง back4app 1 { 2 "dependencies" { 3 "stripe" " " 4 } 5 } เพิ่มโค้ดด้านล่างลงในไฟล์ใหม่และอย่าลืมวางคีย์ลับของ stripe ของคุณที่ด้านบน main js 1 const stripe secret key = 2 "your stripe secret key"; 3 const stripe = require("stripe")(stripe secret key); 4 5 // stripe needs an unique customer id to create payments, so after 6 // signing up, this function should be called to do this operation 7 parse cloud define("createstripecustomer", async (request) => { 8 // get parse user object 9 const userquery = new parse query(parse user); 10 userquery equalto("objectid", request params userid); 11 let user = await userquery first(); 12 13 const customer = await stripe customers create({ email user get("email") }); 14 // creates an stripe setupintent, that will enable the stripe lib to perform 15 // a singel operation related to payments 16 const intent = await stripe setupintents create({ 17 customer customer id, 18 }); 19 // set and save the stripe ids to the parse user object 20 user set({ 21 customerid customer id, 22 setupsecret intent client secret, 23 }); 24 return await user save(null, { usemasterkey true }); 25 }); 26 27 // creates new payment method for a registered customer 28 parse cloud define("addnewpaymentmethod", async (request) => { 29 // get parse user object 30 const userquery = new parse query(parse user); 31 userquery equalto("objectid", request params userid); 32 let user = await userquery first(); 33 34 // retrieve complete stripe payment method by its id 35 const stripepaymentmethod = await stripe paymentmethods retrieve( 36 request params paymentmethodid 37 ); 38 39 // create a new setupintent so the customer can add a new method next time 40 const intent = await stripe setupintents create({ 41 customer `${stripepaymentmethod customer}`, 42 }); 43 user set("setupsecret", intent client secret); 44 user = await user save(null, { usemasterkey true }); 45 46 // creates a new parse object in the paymentmethod class 47 let paymentmethod = new parse object("paymentmethod"); 48 paymentmethod set({ 49 user user, 50 type "card", 51 stripeid stripepaymentmethod id, 52 card stripepaymentmethod card, 53 }); 54 paymentmethod save(); 55 return true; 56 }); 57 58 // creates a new payment using a valid payment method 59 parse cloud define("createnewpayment", async (request) => { 60 // get parse user object 61 const userquery = new parse query(parse user); 62 userquery equalto("objectid", request params userid); 63 let user = await userquery first(); 64 65 const { amount, currency, payment method } = request params paymentdata; 66 67 // look up the stripe customer id 68 const customer = user get("customerid"); 69 70 // create a charge using an unique idempotency key 71 // to protect against double charges 72 const idempotencykey = new date() gettime(); 73 const payment = await stripe paymentintents create( 74 { 75 amount, 76 currency, 77 customer, 78 payment method, 79 off session false, 80 confirm true, 81 confirmation method "manual", 82 }, 83 { idempotencykey } 84 ); 85 // if the result is successful, write it back to the database 86 let payment = new parse object("payment"); 87 payment set({ 88 user user, 89 data payment, 90 }); 91 await payment save(); 92 93 return true; 94 }); 4 อัปโหลดฟังก์ชันไปยัง cloud code ไปที่เว็บไซต์ back4app, ลงชื่อเข้าใช้และจากนั้นค้นหาแอปของคุณ หลังจากนั้น คลิกที่ แดชบอร์ด แดชบอร์ด ลิงก์และคุณจะไปยังหน้าที่แสดงด้านล่าง เพื่อปรับใช้ cloud code ของคุณ คลิกที่ + เพิ่ม + เพิ่ม ปุ่มและค้นหา main js main js และ package json package json ไฟล์ที่คุณสร้างในขั้นตอนก่อนหน้า จากนั้นคลิกที่ ปรับใช้ ปรับใช้ ปุ่ม คุณเพิ่งตั้งค่าฟังก์ชัน cloud code ที่คุณสามารถใช้ได้ในทุกแพลตฟอร์ม! ตรวจสอบ คู่มือการปรับใช้และเรียกฟังก์ชัน เพื่อเรียนรู้วิธีการเรียกใช้พวกเขา ในขั้นตอนถัดไป คุณจะทำงานกับโปรเจกต์ javascript ที่เรียกใช้พวกเขา 5 การรวมแอป javascript กับ cloud code ตอนนี้คุณจะเห็นตัวอย่างของหน้า html ที่เรียบง่ายพร้อม javascript ที่มีฟีเจอร์หลักสามอย่าง การลงชื่อเข้าใช้หรือสมัครสมาชิกผู้ใช้บน parse, การสร้างวิธีการชำระเงินที่ถูกต้อง (บัตรเครดิต), และการสร้างการชำระเงินใหม่ โดยเรียกเก็บเงินจากวิธีการเหล่านี้ที่เป็นของผู้ใช้ ไปข้างหน้าและสร้างไดเรกทอรีใหม่ในคอมพิวเตอร์ของคุณและไฟล์ html ใหม่ที่มีโค้ดต่อไปนี้ภายใน index html 1 2 3 4 5 6 7 back4app stripe payments 8 9 10 11 12 13 15 react on back4app 16 back4app stripe payments 17 18 19 20 21 22 sign in 23 24 25 26 sign in 27 28 don't have an account yet? sign up instead 29 30 31 sign up 32 33 34 35 sign up 36 37 already have an account? sign in instead 38 39 40 41 42 43 44 45 add new payment method 46 47 use any of the 48 stripe test cards 49 for this demo! 50 51 52 53 54 55 56 save card 57 58 59 60 create new payment 61 62 63 card (payment method) 64 65 66 68 69 currency 70 usd 71 brl 72 eur 73 74 75 charge selected card 76 77 78 79 payments 80 81 82 83 sign out 84 85 86 87 88 89 90 91 92 ในไฟล์นี้คุณจะพบสองส่วนหลัก ส่วนแรกคือส่วนการตรวจสอบสิทธิ์ ซึ่งจะแสดงโดยอัตโนมัติหากผู้ใช้ยังไม่ได้เข้าสู่ระบบ หลังจากเข้าสู่ระบบแล้ว ส่วนการชำระเงินจะปรากฏขึ้น ซึ่งประกอบด้วยแบบฟอร์มทั้งหมดที่รับผิดชอบในการสร้างข้อมูลบน stripe และยังสื่อสารกับฟังก์ชัน cloud code บน back4app เราต้องสร้างฟังก์ชัน javascript ที่มีโค้ดที่เชื่อมโยงทุกอย่างเข้าด้วยกัน ซึ่งเรียกว่า index js index js index js 1 // define and initialize parse and stripe libs 2 const parse app id = "your parse id"; 3 const parse js key = "your parse js key"; 4 parse initialize(parse app id, parse js key); 5 parse serverurl = "https //parseapi back4app com/"; 6 7 const stripe publishable key = "your stripe publishable key"; 8 const stripe = stripe(stripe publishable key); 9 10 // holds the currentuser complete parse object 11 let currentuser = null; 12 const setcompletecurrentuser = async () => { 13 // called when user is already signed in, completing 14 // the currentuser object with the full one 15 currentuser = await new parse query(parse user) 16 equalto("objectid", parse user current() id) 17 first(); 18 // retrieve and render user cards and payments 19 retrievecurrentuserpaymentmethods(); 20 retrievecurrentuserpayments(); 21 }; 22 23 const retrievecurrentuserpaymentmethods = async () => { 24 // query and render user paymentmethods 25 const pmquery = new parse query("paymentmethod"); 26 pmquery equalto("user", parse user current()); 27 paymentmethods = await pmquery find(); 28 renderpaymentmethodoptions(paymentmethods); 29 }; 30 31 const retrievecurrentuserpayments = async () => { 32 // query and render user payments 33 const paymentsquery = new parse query("payment"); 34 paymentsquery equalto("user", parse user current()); 35 payments = await paymentsquery find(); 36 renderpayments(payments); 37 }; 38 39 const renderpaymentmethodoptions = async (paymentmethods) => { 40 for (let paymentmethod of paymentmethods) { 41 const optionid = `card ${paymentmethod get("stripeid")}`; 42 let optionelement = document getelementbyid(optionid); 43 44 // add a new option if one doesn't exist yet 45 if (!optionelement) { 46 optionelement = document createelement("option"); 47 optionelement id = optionid; 48 document 49 queryselector("select\[name=payment method]") 50 appendchild(optionelement); 51 } 52 53 optionelement value = paymentmethod get("stripeid"); 54 optionelement text = `${paymentmethod get("card") brand} •••• ${ 55 paymentmethod get("card") last4 56 } | expires ${paymentmethod get("card") exp month}/${ 57 paymentmethod get("card") exp year 58 }`; 59 } 60 }; 61 62 const renderpayments = (payments) => { 63 for (let payment of payments) { 64 let lielement = document getelementbyid(`payment ${payment id}`); 65 if (!lielement) { 66 lielement = document createelement("li"); 67 lielement id = `payment ${payment id}`; 68 } 69 70 const paymentdata = payment get("data"); 71 let content = ""; 72 if ( 73 paymentdata status === "new" || 74 paymentdata status === "requires confirmation" 75 ) { 76 content = `creating payment for ${formatamount( 77 paymentdata amount, 78 paymentdata currency 79 )}`; 80 } else if (paymentdata status === "succeeded") { 81 const card = paymentdata charges data\[0] payment method details card; 82 content = `payment for ${formatamount( 83 paymentdata amount, 84 paymentdata currency 85 )} on ${card brand} card •••• ${card last4} ${paymentdata status}!`; 86 } else { 87 content = `payment for ${formatamount( 88 paymentdata amount, 89 paymentdata currency 90 )} ${paymentdata status}`; 91 } 92 lielement innertext = content; 93 document queryselector("#payments list") appendchild(lielement); 94 } 95 }; 96 97 // checks if user is already signed in on parse 98 if (parse user current() !== null) { 99 setcompletecurrentuser(); 100 // hide auth screen and show payment fields 101 document getelementbyid("auth") style display = "none"; 102 document getelementbyid("content") style display = "block"; 103 } 104 105 // toggle signin and signup forms 106 document 107 queryselector("#signup toggle") 108 addeventlistener("click", async ( event) => { 109 document getelementbyid("auth signin form") style display = "none"; 110 document getelementbyid("auth signup form") style display = "block"; 111 clearauthformfields(); 112 }); 113 document 114 queryselector("#signin toggle") 115 addeventlistener("click", async ( event) => { 116 document getelementbyid("auth signup form") style display = "none"; 117 document getelementbyid("auth signin form") style display = "block"; 118 clearauthformfields(); 119 }); 120 121 // clear auth form fields 122 const clearauthformfields = () => { 123 document 124 queryselector("#auth") 125 queryselectorall("input") 126 foreach((input) => (input value = "")); 127 }; 128 129 // handle auth forms 130 document 131 queryselector("#auth signin form") 132 addeventlistener("submit", async (event) => { 133 event preventdefault(); 134 toggleallbuttonsenabled(false); 135 const form = new formdata(event target); 136 const email = form get("email"); 137 const password = form get("password"); 138 139 // try to signin on parse 140 try { 141 let user = await parse user login(email, password); 142 if (user !== null) { 143 currentuser = user; 144 // hide auth screen and show payment fields 145 document getelementbyid("auth") style display = "none"; 146 document getelementbyid("content") style display = "block"; 147 clearauthformfields(); 148 } 149 } catch (error) { 150 alert(error); 151 } 152 toggleallbuttonsenabled(true); 153 }); 154 155 document 156 queryselector("#auth signup form") 157 addeventlistener("submit", async (event) => { 158 event preventdefault(); 159 toggleallbuttonsenabled(false); 160 const form = new formdata(event target); 161 const email = form get("email"); 162 const password = form get("password"); 163 164 // try to signup on parse 165 try { 166 let user = await parse user signup(email, password, { email email }); 167 // cloud code to create stripe user and intent 168 user = await parse cloud run("createstripecustomer", { userid user id }); 169 if (user !== null) { 170 currentuser = user; 171 // hide auth screen and show payment fields 172 document getelementbyid("auth") style display = "none"; 173 document getelementbyid("content") style display = "block"; 174 clearauthformfields(); 175 } 176 } catch (error) { 177 alert(error); 178 } 179 toggleallbuttonsenabled(true); 180 }); 181 182 // signout from parse 183 document queryselector("#signout") addeventlistener("click", async ( event) => { 184 await parse user logout(); 185 currentuser = null; 186 // show auth screen and hide payment fields 187 document getelementbyid("auth") style display = "block"; 188 document getelementbyid("content") style display = "none"; 189 }); 190 191 // creates stripe card ui element 192 const elements = stripe elements(); 193 const cardelement = elements create("card"); 194 cardelement mount("#card element"); 195 196 // handle add new card form 197 document 198 queryselector("#payment method form") 199 addeventlistener("submit", async (event) => { 200 event preventdefault(); 201 toggleallbuttonsenabled(false); 202 if (!event target reportvalidity()) { 203 return; 204 } 205 const form = new formdata(event target); 206 const cardholdername = form get("name"); 207 208 const result = await stripe confirmcardsetup( 209 currentuser get("setupsecret"), 210 { 211 payment method { 212 card cardelement, 213 billing details { 214 name cardholdername, 215 }, 216 }, 217 } 218 ); 219 220 if (result error) { 221 alert(result error message); 222 toggleallbuttonsenabled(true); 223 return null; 224 } 225 226 let setupintent = result setupintent; 227 228 // cloud code to add new payment method 229 let cloudcoderesult = await parse cloud run("addnewpaymentmethod", { 230 userid currentuser id, 231 paymentmethodid setupintent payment method, 232 }); 233 234 toggleallbuttonsenabled(true); 235 alert("success on creating a new payment method!"); 236 237 // update payment method options 238 retrievecurrentuserpaymentmethods(); 239 }); 240 241 // handles new payment form 242 document 243 queryselector("#payment form") 244 addeventlistener("submit", async (event) => { 245 event preventdefault(); 246 toggleallbuttonsenabled(false); 247 const form = new formdata(event target); 248 const amount = number(form get("amount")); 249 const currency = form get("currency"); 250 // gets selected card option id 251 const paymentmethod = form get("payment method"); 252 const paymentdata = { 253 payment method paymentmethod, 254 currency, 255 amount formatamountforstripe(amount, currency), 256 status "new", 257 }; 258 // cloud code to create new payment 259 let cloudcoderesult = await parse cloud run("createnewpayment", { 260 userid currentuser id, 261 paymentdata paymentdata, 262 }); 263 264 toggleallbuttonsenabled(true); 265 alert("success on creating a new payment!"); 266 267 retrievecurrentuserpayments(); 268 }); 269 270 // helper functions 271 const toggleallbuttonsenabled = (enabledvalue) => { 272 document 273 queryselectorall("button") 274 foreach((button) => (button disabled = !enabledvalue)); 275 }; 276 277 const formatamount = (amount, currency) => { 278 amount = zerodecimalcurrency(amount, currency) 279 ? amount 280 (amount / 100) tofixed(2); 281 return new intl numberformat("en us", { 282 style "currency", 283 currency, 284 }) format(amount); 285 }; 286 287 // format amount for stripe 288 const formatamountforstripe = (amount, currency) => { 289 return zerodecimalcurrency(amount, currency) 290 ? amount 291 math round(amount 100); 292 }; 293 294 // check if we have a zero decimal currency 295 // https //stripe com/docs/currencies#zero decimal 296 const zerodecimalcurrency = (amount, currency) => { 297 let numberformat = new intl numberformat(\["en us"], { 298 style "currency", 299 currency currency, 300 currencydisplay "symbol", 301 }); 302 const parts = numberformat formattoparts(amount); 303 let zerodecimalcurrency = true; 304 for (let part of parts) { 305 if (part type === "decimal") { 306 zerodecimalcurrency = false; 307 } 308 } 309 return zerodecimalcurrency; 310 }; ตรวจสอบให้แน่ใจว่าได้เพิ่มคีย์ที่เผยแพร่ของ stripe และ id แอป parse รวมถึงคีย์ js ของคุณไปยังด้านบนของไฟล์ นี่คือบางส่วนขององค์ประกอบสำคัญที่ควรตรวจสอบและเข้าใจในสคริปต์นี้ ตรวจสอบการใช้งานของ parse user current parse user current เมื่อต้องโหลดสคริปต์เป็นครั้งแรกเพื่อแสดงส่วนที่ถูกต้องของหน้า; ตัวฟังการส่งแบบฟอร์มที่จะดำเนินการบน parse เช่น การลงชื่อเข้าใช้หรือสมัครสมาชิกและเรียกใช้ฟังก์ชัน cloud code เพื่อสร้างวัตถุที่เกี่ยวข้องกับ stripe และบันทึกในฐานข้อมูล back4app ของคุณ; วิธีการ “retrieve” และ “return” ที่ทำการค้นหาบน parse เพื่อดึงข้อมูลของผู้ใช้ปัจจุบัน payment payment และ paymentmethod paymentmethod วัตถุ ก่อนทดสอบแอป ให้เพิ่มสไตล์ชีตต่อไปนี้ในไฟล์ css ที่เรียกว่า app css app css ภายในไดเรกทอรีเดียวกัน 1 / back4app guide / 2 3 , 4 before, 5 after { 6 margin 0; 7 padding 0; 8 box sizing inherit; 9 } 10 11 html { 12 font family sans serif; 13 box sizing border box; 14 outline none; 15 overflow auto; 16 } 17 18 body { 19 margin 0; 20 background color #fff; 21 } 22 23 h1, 24 h2, 25 h3, 26 h4, 27 h5, 28 h6 { 29 margin 0; 30 } 31 32 p { 33 margin 0; 34 } 35 36 container { 37 width 100%; 38 max width 600px; 39 margin auto; 40 padding 20px 0; 41 } 42 43 wrapper { 44 width '90%'; 45 align self 'center'; 46 } 47 48 header { 49 display flex; 50 flex direction column; 51 align items center; 52 padding 25px 0; 53 background color #208aec; 54 } 55 56 header logo { 57 height 55px; 58 margin bottom 20px; 59 object fit contain; 60 } 61 62 header text bold { 63 margin bottom 3px; 64 color rgba(255, 255, 255, 0 9); 65 font size 16px; 66 font weight bold; 67 } 68 69 header text { 70 color rgba(255, 255, 255, 0 9); 71 font size 15px; 72 } 73 74 flex row { 75 display flex; 76 } 77 78 flex between { 79 display flex; 80 align items center; 81 justify content space between; 82 } 83 84 form wrapper { 85 margin top 20px; 86 margin bottom 10px; 87 } 88 89 form heading { 90 margin bottom 10px; 91 } 92 93 form { 94 padding bottom 25px; 95 margin 25px 0; 96 border bottom 1px solid rgba(0, 0, 0, 0 12); 97 } 98 99 form input { 100 display block; 101 width 100%; 102 height 46px; 103 padding 0 15px; 104 background color #e6e6e6; 105 border 1px solid #ccc; 106 border radius 999px; 107 margin bottom 20px; 108 font size 16px; 109 } 110 111 form button { 112 display block; 113 width 100%; 114 height 42px; 115 padding 0 15px; 116 background color #208aec; 117 border 1px solid #208aec; 118 border radius 999px; 119 color #fff; 120 font size 16px; 121 cursor pointer; 122 } 123 124 form hint { 125 display block; 126 margin top 20px; 127 color rgba(0, 0, 0, 0 5); 128 font size 16px; 129 text align center; 130 text decoration color rgba(0, 0, 0, 0 4); 131 } 132 133 card element wrapper { 134 padding 13px 15px; 135 margin bottom 20px; 136 background color #e6e6e6; 137 border 1px solid #ccc; 138 border radius 999px; 139 } ทดสอบแอปโดยใช้เซิร์ฟเวอร์ http ท้องถิ่นใด ๆ เช่น แพ็คเกจ node http server หลังจากลงทะเบียน แอปของคุณควรมีลักษณะดังนี้ บทสรุป จากคู่มือที่อธิบายข้างต้น คุณได้ใช้ stripe กับฟังก์ชัน cloud code ใน back4app รวมถึงการรวมการชำระเงินเข้ากับแอป javascript ที่เรียบง่าย! หากคุณพบปัญหาใด ๆ ขณะรวม stripe หรือฟังก์ชันไม่ทำงาน โปรดติดต่อทีมงานของเราผ่านการแชท!