PayPal을 Vue 애플리케이션과 통합
Slack Payment는 훌륭하지만 아프리카 신생 기업에게는 이것이 도전이 될 것이며 Paypal은 훌륭한 출발점이 될 것입니다. 질문은 왜? PayPal을 사용하면 초기 수수료가 필요하지 않고 비즈니스 계정만 있으면 애플리케이션을 통합할 수 있습니다. 여기에 비즈니스 계정을 등록하려면 링크https://www.paypal.com/ke/webapps/mpp/country-worldwide가 있습니다.
해당 지역 내에서 비즈니스를 등록할 수 있는 국가를 선택하십시오. 비즈니스 계정이 있으면 바로 사용할 수 있습니다.
먼저 Vue 프로젝트를 설정합시다.
vue create paypal-app > Manually select features > Babel, Router, Linter, (Vuex, CSS Pre-processors, Unit Testing and E2E testing are always ideal according to your preference) > Eslint + Prettier
With that, we will have two things in place that we need to integrate a Vue project and Paypal. Now let's have some components to separate our application. We will have the following components and assemble everything once we are done.
(Views Directory) Views/ Home.vue Profile.vue (Components Directory) Components/ Payment.vue Header.vue Upgrade.vue Cancel.vue Suspend.vue Activate.vue // This will hold our environmental variables. Our secret and client ID .env
In our application, we need a user to be able to make the following events:
- Select a subscription
- Make payment
- Cancel or Suspend subscription
- Re-Activate a subscription
- Upgrade subscription
With the above events, we will have a complete circle for a user in our application. For CSS purposes will be using https://vuetifyjs.com/.
vue add vuetify > Default (recommended) // we will be using the following in our application yarn add sweetalert2 // alert us when payment is successful yarn add axios // to fetch user information
Let's create our application then get our client id and secret id from Paypal thereafter. We'll code each step
홈뷰
This will display all our subscription:
<template>
<!-- Home Component-->
<div class="home">
<Header />
<v-container>
<!--Snackbar-->
<v-snackbar color="info" text v-model="snackbar">
You have selected <span>{{ selected.title }}</span>
</v-snackbar>
<v-row>
<v-col cols="12" md="4" v-for="(item, index) in items" :key="index">
<v-radio-group v-model="selected" row @change="selectedsubscription">
<v-card elevation="5" tile>
<v-card-text>
<div class="mb-2 primary--text body-1">{{ item.title }}</div>
<div class="title black--text">
<span>USD</span> {{ item.amount }}
</div>
<div>{{ item.text }}</div>
<v-radio class="mt-4" :value="item"></v-radio>
</v-card-text>
</v-card>
</v-radio-group>
</v-col>
</v-row>
</v-container>
</div>
</template>
<script>
import Header from "../components/Header";
export default {
name: "Home",
components: { Header },
data() {
return {
snackbar: false,
selected: {},
items: [
{
title: "Basic",
amount: "5.50",
text:
"Lorem ipsum dolor sit amet consectetur adipisicing elit. Odio nam quasi doloremque eos iure iste, quo nostrum ipsum, hic adipisci soluta cum voluptate perspiciatis accusamus quidem non error ratione temporibus.",
plan_id: "" // plan id
},
{
title: "Essential",
amount: "6.50",
text:
"Lorem ipsum dolor sit amet consectetur adipisicing elit. Odio nam quasi doloremque eos iure iste, quo nostrum ipsum, hic adipisci soluta cum voluptate perspiciatis accusamus quidem non error ratione temporibus.",
plan_id: "" // plan id
},
{
title: "Premium",
amount: "7.50",
text:
"Lorem ipsum dolor sit amet consectetur adipisicing elit. Odio nam quasi doloremque eos iure iste, quo nostrum ipsum, hic adipisci soluta cum voluptate perspiciatis accusamus quidem non error ratione temporibus.",
plan_id: "" // plan id
}
]
};
},
methods: {
// selected subscription function
selectedsubscription() {
// check if we are creating a new subscrption or upgrading
const response = localStorage.getItem("@upgradesubscrption");
// temporarily save your plan on local storage or use vuex
// you only need the plan id
// lets use local storage for beginer purposes
localStorage.setItem("@selectedpackage", JSON.stringify(this.selected));
// From here redirect for payment
// set a timeout so user can see the package they hase selected
// we can add a snackbar
this.snackbar = true;
// You can use one component and write the logic for both upgrade and payment. In my case I have separated them to two components (Payment and Upgrade)
// Both payment and upgrade requires the user consent
setTimeout(() => {
if (response === true) {
// upgrade
this.$router.push("/upgrade-payment");
} else {
// new subscription
this.$router.push("/subscription-payment");
}
}, 1000);
// end
}
}
};
</script>
플랜 ID를 Paypal 비즈니스 계정의 구독 플랜 ID로 바꾸십시오. 샌드박스에서 테스트하고 라이브로 전환하기 전에 해당 기능을 켜야 합니다.
프로필.vue
이것은 사용자 샘플 프로필 페이지입니다. Paypal에서 가져와 결제 세부 정보를 표시할 수 있습니다.
<template>
<div class="profile">
<Header />
<div class="content">
<v-navigation-drawer app v-model="drawer">
<v-card-text class="text-center">
<v-avatar color="indigo" size="100" class="mb-3"> </v-avatar>
<Cancel class="mb-2" />
<Suspend class="mb-2" />
<Activate class="mb-2" />
<v-btn
color="secondary"
dark
block
tile
@click="upgradesubscription"
class="pl-5 pr-5"
>
<span style="text-transform: capitalize">Upgrade</span>
</v-btn>
</v-card-text>
</v-navigation-drawer>
</div>
</div>
</template>
<script>
import Header from "../components/Header";
import Cancel from "../components/Cancel";
import Suspend from "../components/Suspend";
import Activate from "../components/Activate";
export default {
name: "Profile",
components: { Header, Suspend, Cancel, Activate },
data() {
return {
drawer: true,
saving: false
};
},
methods: {
// upgrade subscrption
upgradesubscription() {
// 1. Let's save an upgrade request and subscription id
let subscription_id = "" // user subscription id
localStorage.setItem("@upgradesubscrption", true);
localStorage.setItem("@subscriptionid", JSON.stringify(subscription_id)
// 2. Send back to select a new package
this.$router.push("/");
// end
}
}
};
</script>
아래와 같이 프로필 페이지에 사용자 옵션이 표시되었습니다.
헤더.vue
<template>
<div class="header">
<v-app-bar app color="grey lighten-5" flat>
<v-card-title>
PAYPAL APP
</v-card-title>
</v-app-bar>
<v-divider></v-divider>
</div>
</template>
활성화.vue
사용자 구독 활성화
<template>
<div class="activate">
<v-btn
:loading="saving"
color="primary"
dark
block
tile
@click="activatesubscription"
class="pl-5 pr-5 mb-2"
>
<span style="text-transform: capitalize">Activate</span>
</v-btn>
</div>
</template>
<script>
import { activateusersubscription } from "./script";
export default {
name: "Activate",
data() {
return {
saving: false
};
},
methods: {
// activate subscription
async activatesubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
activateusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
이 함수를 호출하는 동안 사용자 구독 ID를 제공해야 합니다.
Suspend.vue
사용자 가입 정지
<template>
<!-- Suspend Component-->
<div class="suspend-subscription">
<v-btn
:loading="saving"
color="warning"
dark
tile
block
@click="suspendsubscription"
class="pl-5 pr-5"
>
<span style="text-transform: capitalize">suspend</span>
</v-btn>
</div>
</template>
<script>
import { suspendusersubscription } from "./script";
export default {
name: "Suspend",
data() {
return {
saving: false
};
},
methods: {
// suspend subscription
async suspendsubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
await suspendusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
이 함수를 호출하는 동안 사용자 구독 ID를 제공해야 합니다.
취소.vue
사용자 구독 취소
<template>
<!-- Cancel Component-->
<div class="cancel-subscription">
<v-btn
:loading="saving"
color="red darken-1"
dark
tile
block
@click="cancelsubscription"
class="pl-5 pr-5"
>
<span style="text-transform: capitalize">Cancel</span>
</v-btn>
</div>
</template>
<script>
import { cancelusersubscription } from "./script";
export default {
name: "Cancel",
data() {
return {
saving: false
};
},
methods: {
// cancel subscription
async cancelsubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
await cancelusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
이 함수를 호출하는 동안 사용자 구독 ID를 제공해야 합니다.
결제.vue
이 구성 요소를 통해 사용자는 새 구독을 구입할 수 있습니다. 결제/구매 및 업그레이드를 위해 둘 다 사용자가 로그인하고 동의해야 합니다.
<template>
<!-- Payment Component-->
<div class="payment">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Payment",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "blue",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
let plan_ID = package_results.plan_id; // user plan id
// 2. Create a subscription
return actions.subscription.create({
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
/**
* NOTE
* - Save the subscription id in your Database
* - This is important to ensure you can always
* - Check on the status when user logs in or wants
* - to make payment
*/
// 2. Save payment subscription id
//let subscrption_id = data.subscriptionID;
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your payment has successfully been proccessed!",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
업그레이드.vue
업그레이드 또는 다운그레이드 구독은 사용자가 업그레이드 또는 다운그레이드에 동의해야 합니다. 새로운 변경 사항은 다음 결제 시 적용됩니다.
<template>
<!-- Upgrade Component-->
<div class="upgrade">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Upgrade",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "gold",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
// 2. get subscription id
const subscription_response = await localStorage.getItem(
"@subscriptionid"
);
let subscription_id = JSON.parse(subscription_response)
let plan_ID = package_results.plan_id;
// 2. Revise a subscription
return actions.subscription.revise(subscription_id,{
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your upgrade was succesfull",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
노트
동일한 제품 내에서 구독을 통해서만 업그레이드할 수 있으므로 계획을 만들 때 모든 계획이 동일한 제품에 있는지 확인하십시오.
Script.js
Paypal에서 사용자 정보를 취소, 일시 중단, 활성화 및 검색하는 기능입니다.
import axios from "axios";
const client_id = process.env.VUE_APP_PAYPAL_CLIENT_ID;
const client_secret = process.env.VUE_APP_PAYPAL_CLIENT_SECRET_ID;
/**
* If you find challege then concat the url with + instead of html integral
* "https://api-m.sandbox.paypal.com/v1/billing/subscriptions/" + subscriptionID + "/suspend"
* =========================================================================================
*/
// retirive user subscription details
export async function retriveuserinformation(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}`,
method: "get",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function suspendusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/suspend`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function cancelusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/cancel`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// activate user subscription
export async function activateusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/activate`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Reactivating on customer request"
}
});
return user_subscription_details;
// end
}
이를 통해 모든 섹션을 준비하고 실행할 수 있습니다. 사용하려는 경우 Github 저장소가 있습니다https://github.com/kevinodongo/paypal-app.git.
이제 Paypal로 돌아가서 통합을 완료하고 애플리케이션을 테스트하는 데 필요한 것을 가져오겠습니다. 여기에서 로그인할 수 있는 Paypal의 개발자 섹션에서 앱을 생성해야 합니다https://developer.paypal.com/developer/applications/.
앱을 만든 후 앱을 클릭하면 자격 증명이 검색됩니다. 다음이 필요합니다.
<template>
<div class="header">
<v-app-bar app color="grey lighten-5" flat>
<v-card-title>
PAYPAL APP
</v-card-title>
</v-app-bar>
<v-divider></v-divider>
</div>
</template>
사용자 구독 활성화
<template>
<div class="activate">
<v-btn
:loading="saving"
color="primary"
dark
block
tile
@click="activatesubscription"
class="pl-5 pr-5 mb-2"
>
<span style="text-transform: capitalize">Activate</span>
</v-btn>
</div>
</template>
<script>
import { activateusersubscription } from "./script";
export default {
name: "Activate",
data() {
return {
saving: false
};
},
methods: {
// activate subscription
async activatesubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
activateusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
이 함수를 호출하는 동안 사용자 구독 ID를 제공해야 합니다.
Suspend.vue
사용자 가입 정지
<template>
<!-- Suspend Component-->
<div class="suspend-subscription">
<v-btn
:loading="saving"
color="warning"
dark
tile
block
@click="suspendsubscription"
class="pl-5 pr-5"
>
<span style="text-transform: capitalize">suspend</span>
</v-btn>
</div>
</template>
<script>
import { suspendusersubscription } from "./script";
export default {
name: "Suspend",
data() {
return {
saving: false
};
},
methods: {
// suspend subscription
async suspendsubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
await suspendusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
이 함수를 호출하는 동안 사용자 구독 ID를 제공해야 합니다.
취소.vue
사용자 구독 취소
<template>
<!-- Cancel Component-->
<div class="cancel-subscription">
<v-btn
:loading="saving"
color="red darken-1"
dark
tile
block
@click="cancelsubscription"
class="pl-5 pr-5"
>
<span style="text-transform: capitalize">Cancel</span>
</v-btn>
</div>
</template>
<script>
import { cancelusersubscription } from "./script";
export default {
name: "Cancel",
data() {
return {
saving: false
};
},
methods: {
// cancel subscription
async cancelsubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
await cancelusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
이 함수를 호출하는 동안 사용자 구독 ID를 제공해야 합니다.
결제.vue
이 구성 요소를 통해 사용자는 새 구독을 구입할 수 있습니다. 결제/구매 및 업그레이드를 위해 둘 다 사용자가 로그인하고 동의해야 합니다.
<template>
<!-- Payment Component-->
<div class="payment">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Payment",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "blue",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
let plan_ID = package_results.plan_id; // user plan id
// 2. Create a subscription
return actions.subscription.create({
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
/**
* NOTE
* - Save the subscription id in your Database
* - This is important to ensure you can always
* - Check on the status when user logs in or wants
* - to make payment
*/
// 2. Save payment subscription id
//let subscrption_id = data.subscriptionID;
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your payment has successfully been proccessed!",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
업그레이드.vue
업그레이드 또는 다운그레이드 구독은 사용자가 업그레이드 또는 다운그레이드에 동의해야 합니다. 새로운 변경 사항은 다음 결제 시 적용됩니다.
<template>
<!-- Upgrade Component-->
<div class="upgrade">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Upgrade",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "gold",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
// 2. get subscription id
const subscription_response = await localStorage.getItem(
"@subscriptionid"
);
let subscription_id = JSON.parse(subscription_response)
let plan_ID = package_results.plan_id;
// 2. Revise a subscription
return actions.subscription.revise(subscription_id,{
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your upgrade was succesfull",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
노트
동일한 제품 내에서 구독을 통해서만 업그레이드할 수 있으므로 계획을 만들 때 모든 계획이 동일한 제품에 있는지 확인하십시오.
Script.js
Paypal에서 사용자 정보를 취소, 일시 중단, 활성화 및 검색하는 기능입니다.
import axios from "axios";
const client_id = process.env.VUE_APP_PAYPAL_CLIENT_ID;
const client_secret = process.env.VUE_APP_PAYPAL_CLIENT_SECRET_ID;
/**
* If you find challege then concat the url with + instead of html integral
* "https://api-m.sandbox.paypal.com/v1/billing/subscriptions/" + subscriptionID + "/suspend"
* =========================================================================================
*/
// retirive user subscription details
export async function retriveuserinformation(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}`,
method: "get",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function suspendusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/suspend`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function cancelusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/cancel`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// activate user subscription
export async function activateusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/activate`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Reactivating on customer request"
}
});
return user_subscription_details;
// end
}
이를 통해 모든 섹션을 준비하고 실행할 수 있습니다. 사용하려는 경우 Github 저장소가 있습니다https://github.com/kevinodongo/paypal-app.git.
이제 Paypal로 돌아가서 통합을 완료하고 애플리케이션을 테스트하는 데 필요한 것을 가져오겠습니다. 여기에서 로그인할 수 있는 Paypal의 개발자 섹션에서 앱을 생성해야 합니다https://developer.paypal.com/developer/applications/.
앱을 만든 후 앱을 클릭하면 자격 증명이 검색됩니다. 다음이 필요합니다.
<template>
<!-- Suspend Component-->
<div class="suspend-subscription">
<v-btn
:loading="saving"
color="warning"
dark
tile
block
@click="suspendsubscription"
class="pl-5 pr-5"
>
<span style="text-transform: capitalize">suspend</span>
</v-btn>
</div>
</template>
<script>
import { suspendusersubscription } from "./script";
export default {
name: "Suspend",
data() {
return {
saving: false
};
},
methods: {
// suspend subscription
async suspendsubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
await suspendusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
사용자 구독 취소
<template>
<!-- Cancel Component-->
<div class="cancel-subscription">
<v-btn
:loading="saving"
color="red darken-1"
dark
tile
block
@click="cancelsubscription"
class="pl-5 pr-5"
>
<span style="text-transform: capitalize">Cancel</span>
</v-btn>
</div>
</template>
<script>
import { cancelusersubscription } from "./script";
export default {
name: "Cancel",
data() {
return {
saving: false
};
},
methods: {
// cancel subscription
async cancelsubscription() {
this.saving = true;
let subscription_id = ""; // user subscription id
await cancelusersubscription(subscription_id);
setTimeout(() => {
this.saving = false;
}, 1000);
// end
}
}
};
</script>
이 함수를 호출하는 동안 사용자 구독 ID를 제공해야 합니다.
결제.vue
이 구성 요소를 통해 사용자는 새 구독을 구입할 수 있습니다. 결제/구매 및 업그레이드를 위해 둘 다 사용자가 로그인하고 동의해야 합니다.
<template>
<!-- Payment Component-->
<div class="payment">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Payment",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "blue",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
let plan_ID = package_results.plan_id; // user plan id
// 2. Create a subscription
return actions.subscription.create({
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
/**
* NOTE
* - Save the subscription id in your Database
* - This is important to ensure you can always
* - Check on the status when user logs in or wants
* - to make payment
*/
// 2. Save payment subscription id
//let subscrption_id = data.subscriptionID;
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your payment has successfully been proccessed!",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
업그레이드.vue
업그레이드 또는 다운그레이드 구독은 사용자가 업그레이드 또는 다운그레이드에 동의해야 합니다. 새로운 변경 사항은 다음 결제 시 적용됩니다.
<template>
<!-- Upgrade Component-->
<div class="upgrade">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Upgrade",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "gold",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
// 2. get subscription id
const subscription_response = await localStorage.getItem(
"@subscriptionid"
);
let subscription_id = JSON.parse(subscription_response)
let plan_ID = package_results.plan_id;
// 2. Revise a subscription
return actions.subscription.revise(subscription_id,{
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your upgrade was succesfull",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
노트
동일한 제품 내에서 구독을 통해서만 업그레이드할 수 있으므로 계획을 만들 때 모든 계획이 동일한 제품에 있는지 확인하십시오.
Script.js
Paypal에서 사용자 정보를 취소, 일시 중단, 활성화 및 검색하는 기능입니다.
import axios from "axios";
const client_id = process.env.VUE_APP_PAYPAL_CLIENT_ID;
const client_secret = process.env.VUE_APP_PAYPAL_CLIENT_SECRET_ID;
/**
* If you find challege then concat the url with + instead of html integral
* "https://api-m.sandbox.paypal.com/v1/billing/subscriptions/" + subscriptionID + "/suspend"
* =========================================================================================
*/
// retirive user subscription details
export async function retriveuserinformation(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}`,
method: "get",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function suspendusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/suspend`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function cancelusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/cancel`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// activate user subscription
export async function activateusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/activate`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Reactivating on customer request"
}
});
return user_subscription_details;
// end
}
이를 통해 모든 섹션을 준비하고 실행할 수 있습니다. 사용하려는 경우 Github 저장소가 있습니다https://github.com/kevinodongo/paypal-app.git.
이제 Paypal로 돌아가서 통합을 완료하고 애플리케이션을 테스트하는 데 필요한 것을 가져오겠습니다. 여기에서 로그인할 수 있는 Paypal의 개발자 섹션에서 앱을 생성해야 합니다https://developer.paypal.com/developer/applications/.
앱을 만든 후 앱을 클릭하면 자격 증명이 검색됩니다. 다음이 필요합니다.
<template>
<!-- Payment Component-->
<div class="payment">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Payment",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "blue",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
let plan_ID = package_results.plan_id; // user plan id
// 2. Create a subscription
return actions.subscription.create({
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
/**
* NOTE
* - Save the subscription id in your Database
* - This is important to ensure you can always
* - Check on the status when user logs in or wants
* - to make payment
*/
// 2. Save payment subscription id
//let subscrption_id = data.subscriptionID;
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your payment has successfully been proccessed!",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
업그레이드 또는 다운그레이드 구독은 사용자가 업그레이드 또는 다운그레이드에 동의해야 합니다. 새로운 변경 사항은 다음 결제 시 적용됩니다.
<template>
<!-- Upgrade Component-->
<div class="upgrade">
<v-sheet height="100vh">
<v-row justify="center" align="center" class="fill-height">
<v-col cols="12">
<div style="display: flex; justify-content: center">
<div class="sheet-container">
<v-card-text>
<div class="paypal-title">{{ packageselect.title }}</div>
<div class="paypal-text">
<span>Total Amount (USD) </span>
<span>${{ packageselect.amount }}</span>
</div>
<v-divider class="mt-4 mb-4"></v-divider>
<div id="paypal-button-container"></div>
</v-card-text>
</div>
</div>
</v-col>
</v-row>
</v-sheet>
</div>
</template>
<script>
import Swal from "sweetalert2";
export default {
name: "Upgrade",
data() {
return {
item: {},
packageselect: ""
};
},
// mounted
async mounted() {
// 1. get the selected package
const package_response = localStorage.getItem("@selectedpackage");
const package_results = JSON.parse(package_response);
// 2. Mount paypal button
if (package_results) {
this.packageselect = package_results;
await this.mountpaypalbutton();
}
// end
},
// methods
methods: {
// Mount paypal button
mountpaypalbutton() {
// eslint-disable-next-line no-undef
paypal
.Buttons({
style: {
shape: "rect",
color: "gold",
layout: "vertical",
label: "paypal",
size: "medium"
},
createSubscription: async function(data, actions) {
// 1. get the selected package
const package_response = await localStorage.getItem(
"@selectedpackage"
);
const package_results = JSON.parse(package_response);
// 2. get subscription id
const subscription_response = await localStorage.getItem(
"@subscriptionid"
);
let subscription_id = JSON.parse(subscription_response)
let plan_ID = package_results.plan_id;
// 2. Revise a subscription
return actions.subscription.revise(subscription_id,{
plan_id: plan_ID
});
},
// eslint-disable-next-line no-unused-vars
onApprove: async function(data, actions) {
// 4. Remove the selected package from the local storage
localStorage.removeItem("@selectedpackage");
// 5. Lets use swal to give us an alert once transcation is completed
Swal.fire({
icon: "success",
title: "Congratulations",
text: "Your upgrade was succesfull",
confirmButtonText: "Complete",
showLoaderOnConfirm: true,
preConfirm: () => {
// redirect user to dashboard or login
location.assign("http://localhost:8080/profile");
},
allowOutsideClick: false
});
}
})
.render("#paypal-button-container");
}
}
};
</script>
<style scooped lang="css">
@media only screen and (max-width: 600px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 300px;
border-radius: 5px;
}
}
@media only screen and (min-width: 600px) and (max-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 350px;
border-radius: 5px;
}
}
@media only screen and (min-width: 960px) {
.sheet-container {
border: 1px solid #e0e0e0;
width: 400px;
border-radius: 5px;
}
}
.paypal-title {
-webkit-font-smoothing: antialiased;
color: black;
text-transform: uppercase;
font-size: 1.1em;
margin-bottom: 5px;
}
.paypal-text {
-webkit-font-smoothing: antialiased;
color: black;
font-size: 1.2em;
margin-bottom: 15px;
display: flex;
justify-content: space-between;
align-items: center;
}
</style>
노트
동일한 제품 내에서 구독을 통해서만 업그레이드할 수 있으므로 계획을 만들 때 모든 계획이 동일한 제품에 있는지 확인하십시오.
Script.js
Paypal에서 사용자 정보를 취소, 일시 중단, 활성화 및 검색하는 기능입니다.
import axios from "axios";
const client_id = process.env.VUE_APP_PAYPAL_CLIENT_ID;
const client_secret = process.env.VUE_APP_PAYPAL_CLIENT_SECRET_ID;
/**
* If you find challege then concat the url with + instead of html integral
* "https://api-m.sandbox.paypal.com/v1/billing/subscriptions/" + subscriptionID + "/suspend"
* =========================================================================================
*/
// retirive user subscription details
export async function retriveuserinformation(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}`,
method: "get",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function suspendusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/suspend`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function cancelusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/cancel`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// activate user subscription
export async function activateusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/activate`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Reactivating on customer request"
}
});
return user_subscription_details;
// end
}
이를 통해 모든 섹션을 준비하고 실행할 수 있습니다. 사용하려는 경우 Github 저장소가 있습니다https://github.com/kevinodongo/paypal-app.git.
이제 Paypal로 돌아가서 통합을 완료하고 애플리케이션을 테스트하는 데 필요한 것을 가져오겠습니다. 여기에서 로그인할 수 있는 Paypal의 개발자 섹션에서 앱을 생성해야 합니다https://developer.paypal.com/developer/applications/.
앱을 만든 후 앱을 클릭하면 자격 증명이 검색됩니다. 다음이 필요합니다.
import axios from "axios";
const client_id = process.env.VUE_APP_PAYPAL_CLIENT_ID;
const client_secret = process.env.VUE_APP_PAYPAL_CLIENT_SECRET_ID;
/**
* If you find challege then concat the url with + instead of html integral
* "https://api-m.sandbox.paypal.com/v1/billing/subscriptions/" + subscriptionID + "/suspend"
* =========================================================================================
*/
// retirive user subscription details
export async function retriveuserinformation(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}`,
method: "get",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function suspendusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/suspend`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// suspend user subscription
export async function cancelusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/cancel`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Customer-requested pause" // reason
}
});
return user_subscription_details;
// end
}
// activate user subscription
export async function activateusersubscription(subscriptionID) {
// 1. Call PayPal to get a token
const auth = await axios({
url: "https://api-m.sandbox.paypal.com/v1/oauth2/token",
method: "post",
headers: {
Accept: "application/json",
"Accept-Language": "en_US",
"content-type": "application/x-www-form-urlencoded"
},
auth: {
username: client_id,
password: client_secret
},
params: {
grant_type: "client_credentials"
}
});
// 2. Call PayPal to get the subscription details
const user_subscription_details = await axios({
url: `https://api-m.sandbox.paypal.com/v1/billing/subscriptions/${subscriptionID}/activate`,
method: "post",
headers: {
Accept: "application/json",
Authorization: `Bearer ${auth.data.access_token}`
},
data: {
reason: "Reactivating on customer request"
}
});
return user_subscription_details;
// end
}
그런 다음에는 public 폴더에 있는 index.html에 있는 애플리케이션으로 돌아가야 합니다.
// Replace the client id with your app client id.
<script
src="https://www.paypal.com/sdk/js?client-id=${CLIENT ID}"
data-sdk-integration-source="button-factory"
></script>
이제 애플리케이션을 실행할 수 있습니다.
yarn serve || yarn run serve
다음 단계
통합을 테스트하여 올바른 통신이 이루어지고 있는지 확인합니다. 샌드박스 URL을 실제 URL로 교체하기 전에 샌드박스에서 테스트합니다.
Paypal 개발자 대시보드에서 내 계정으로 이동하여 비즈니스 및 개인 계정을 만듭니다.
비즈니스를 사용하여 샌드박스 계획을 만들고 테스트 중에 해당 구독 계획 ID를 사용합니다.
거기에 PayPal과 Vue의 통합이 있습니다. 위의 다음 기사는 Lambda AWS 및 Paypal webhook를 사용하는 것입니다.
Reference
이 문제에 관하여(PayPal을 Vue 애플리케이션과 통합), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/kevin_odongo35/integrate-paypal-with-vue-application-42ih텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)