I am creating a new subscription in Stripe, using Laravel 6 and Cashier 10.7, but the default card is not storing in the Stripe customer profile. The subscription is creating fine and no errors, but the card is not storing.
My payment page controller looks like this
public function payment() {
$user = Auth::user();
if ($user->stripe_id == null) {
$user->createAsStripeCustomer();
}
return view('auth.payment', [
'intent' => $user->createSetupIntent()
]);
}
my payment blade like this
#extends('layouts.app')
#section('content')
<div class="container">
<div class="row justify-content-center">
<div class="col-12 col-md-6 mt-5 mb-2">
#if (session('status'))
<div class="alert alert-success" role="alert">
{{ session('status') }}
</div>
#endif
#if ($errors->any())
<div class="alert alert-danger">
<strong>Whoops!</strong> There was a problem.
<ul>
#foreach ($errors->all() as $error)
<li>{{ $error }}</li>
#endforeach
</ul>
</div>
#endif
<div class="h2 text-center">
{{ __('Please enter your card details') }}
</div>
<div class="card">
<div class="card-body">
<form method="post" action="{{ route('startSubscription') }}" id="payment-form">
#csrf
<div class="group">
<label class="stripe-label">
<span class="mr-1 p-2">{{ __('Cardholder Name') }}</span>
<input id="card-holder-name" class="field" placeholder="Jordan Jones" />
</label>
</div>
<!-- Stripe Elements Placeholder -->
<div class="group">
<label class="stripe-label">
<span class="mr-1 p-2">{{ __('Card') }}</span>
<div id="card-element" class="field p-3"></div>
</label>
</div>
<!-- Used to display form errors. -->
<div id="card-errors" role="alert"></div>
<button id="card-button" class="btn btn-lg btn-block btn-success" data-secret="{{ $intent->client_secret }}">
<i class="fas fa-credit-card mr-1"></i>{{ __('Add Payment Method') }}
</button>
</form>
</div>
</div>
</div>
</div>
</div>
#endsection
#section('javascript')
<script>
const stripe = Stripe('pk_********');
const elements = stripe.elements();
const cardElement = elements.create('card', {hidePostalCode: true});
cardElement.mount('#card-element');
const cardHolderName = document.getElementById('card-holder-name');
const cardButton = document.getElementById('card-button');
const clientSecret = cardButton.dataset.secret;
// Handle form submission.
var form = document.getElementById('payment-form');
form.addEventListener('submit', function(event) {
event.preventDefault();
stripe.handleCardSetup(clientSecret, cardElement).then(function(result) {
if (result.error) {
var errorElement = document.getElementById('card-errors');
errorElement.textContent = result.error.message;
} else {
stripePaymentHandler(result.setupIntent);
}
});
});
// Submit the form with the token ID.
function stripePaymentHandler(setupIntent) {
// Insert the token ID into the form so it gets submitted to the server
var form = document.getElementById('payment-form');
var hiddenInput = document.createElement('input');
hiddenInput.setAttribute('type', 'hidden');
hiddenInput.setAttribute('name', 'stripePaymentMethod');
hiddenInput.setAttribute('value', setupIntent.payment_method);
form.appendChild(hiddenInput);
// Submit the form
form.submit();
}
</script>
#endsection
and my create subscription controller like this
public function subscriptionPayment(Request $request) {
$user = Auth::user();
$paymentMethod = $request->stripePaymentMethod;
try {
$newSubscription = $user->newSubscription('Author', 'plan_HGvJkewD0eaX5Y')->trialDays(60)->create($paymentMethod, ['email' => $user->email]);
} catch ( IncompletePayment $exception ){
return redirect()->route(
'payment',
[$exception->payment->id, 'redirect' => route('home')]
);
}
return redirect()->route('home')
->with('status', 'Great! Your payment has been processed and your subscription is now active.');
}
I have tried including
if ($user->hasPaymentMethod()) {
$user->updateDefaultPaymentMethod($paymentMethod);
} else {
$user->addPaymentMethod($paymentMethod);
}
but this throws and error and I'm not sure I should need it anyway.
Any pointers would be great. Thanks.
Related
I have code I am working on. I will list the page, the route, and the controller code. When I inspect and click on the add to cart button I get 500 internal server error and I cannot figure out what I did. It should be giving a message checking to see if the item is already in the cart and if not send a message saying item is in the cart but I can't get past the 500 internal server error.
Page
#extends('layouts.frontend.frontend')
#section('title')
Distinctly Mine - {{$products->name}}
#endsection
#section('content')
<div class="py-3 mb-4 shadow-sm babyblue border-top">
<div class="container">
<h6 class="mb-0">Collections / {{$products->category->name}} / {{$products->name}}</h6>
</div>
</div>
<div class="container">
<div class="card-shadow shadow-sm product_data">
<div class="card-body">
<div class="row">
<div class="col-md-4 border-right">
<div class="img-hover-zoom img-hover-zoom--xyz card-img-top">
<img src="{{ asset('backend/uploads/products/'.$products->image) }}" class="w-100 h-100" alt="{{$products->name}}">
</div>
</div>
<div class="col-md-8">
<h2 class="mb-0">{{ $products->name}}</h2>
<hr>
<label for="" class="me-3">Price: ${{$products->original_price}}</label>
<p class="mt-3">{!! $products->small_description !!}</p>
<hr>
#if($products->qty > 0)
<label for="" class="badge bg-success text-dark fw-bold">In Stock</label>
#else
<label for="" class="badge bg-danger text dark fw-bold">Out of Stock</label>
#endif
<div class="row mt-2">
<div class="col-md-2">
<input type="hidden" value="{{$products->id}}" class="prod_id">
<label for="Quantity">Quantity</label>
<div class="input-group text-center mb-3" style="width:130px">
<button type="button" class="input-group-text decrement-btn">-</button>
<input type="text" name="quantity" value="1" class="form-control qty-input" />
<button type="button" class="input-group-text increment-btn">+</button>
</div>
</div>
<div class="col-md-10">
<br />
<button type="button" class="btn btn-warning text-dark fw-bold ms-3 float-start"><i class=" me-1 fa fa-heart text-danger me-1"></i>Add To Wishlist</button>
<button type="button" class="btn btn-success ms-3 float-start text-dark fw-bold addToCartBtn"><i class="me-1 fa fa-shopping-cart text-dark me-1"></i>Add to Cart</button>
</div>
<hr>
<h2>Description</h2>
{{$products->description}}
</div>
</div>
</div>
</div>
</div>
</div>
#endsection
#section('scripts')
<script>
$(document).ready(function (){
$('.addToCartBtn').click(function (e){
e.preventDefault();
var product_id = $(this).closest('.product_data').find('.prod_id').val();
var product_qty = $(this).closest('.product_data').find('.qty-input').val();
$.ajaxSetup({
headers: {
'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
}
});
$.ajax({
method: "POST",
url: "/add-to-cart",
data: {
'product_id': product_id,
'product_qty': product_qty,
},
dataType: "dataType",
success: function (response){
alert(response.status);
}
});
});
$('.increment-btn').click(function (e){
e.preventDefault();
var inc_value = $('.qty-input').val();
var value = parseInt(inc_value,10);
value = isNaN(value) ? 0 :value;
if(value < 10)
{
value++;
$('.qty-input').val(value);
}
});
$('.decrement-btn').click(function (e){
e.preventDefault();
var dec_value = $('.qty-input').val();
var value = parseInt(dec_value,10);
value = isNaN(value) ? 0 :value;
if(value > 1)
{
value--;
$('.qty-input').val(value);
}
});
});
</script>
#endsection
Route
Route::middleware(['auth'])->group(function (){
Route::post('/add-to-cart',[CartController::class,'addProduct']);
});
Controller
<?php
namespace App\Http\Controllers\Frontend;
use App\Models\Product;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
use Illuminate\Support\Facades\Auth;
class CartController extends Controller
{
public function addProduct(Request $request)
{
$product_id = $request->input('product_id');
$product_qty = $request->input('product_qty');
if(Auth::check())
{
$prod_check = Product::where('id',$product_id)->first();
if($prod_check)
{
if(Cart::where('prod_id',$product_id)->where('user_id',Auth::id())->exists())
{
return response()->json(['status' => $prod_check->name." Already Added to cart"]);
}else{
$cartItem = new Cart();
$cartItem->prod_id = $product_id;
$cartItem->user_id = Auth::id();
$cartItem->prod_qty = $product_qty;
$cartItem->save();
return response()->json(['status'=>$prod_check->name." Added to cart"]);
}
}
}
else{
return response()->json(['status'=> "Login To Continue"]);
}
}
}
I am getting a continuous validation error despite the data being valid. I originally had this forming working, at the time I was only storing one email at a time. When I added the "addNewRow" function, I was unable to post the data. Each time I get a validation error, I am quite new to Vue, and I'm not sure where I am going wrong with either the post method or my validation.
Here is my controller:
public function notifyTeam(Request $request, Agency $id)
{
$request->validate([
'email' => 'unique:users|required|email|max:255|unique:agency_emails',
]);
$user = Auth::user();
$agency = Agency::where('id', $user->agency_id)->first();
$subdomain = $agency->subdomain;
$emails = json_decode($request->getContent('emailArray'), true);
foreach($emails as $email){
$authorizedEmails = new AgencyEmail;
$authorizedEmails->email = $request->email;
$authorizedEmails->agency_id = $agency->id;
$authorizedEmails->save();
}
// Generate Link
// /{subdomain}/register
// Email the link to specified users
// vue component
return redirect()->route('dashboard');
}
And here is my Vue Component:
<template>
<div class="row justify-content-center">
<div class="col-md-4">
<div class="row justify-content-center">
</div>
<h1 class="agency_h1 mt-5 mb-5">ASSEMBLE THE TROOPS</h1>
<form method="POST" #submit.prevent="submit">
<input type="hidden" name="_token" :value="csrf">
<label for="email">E-mail Address</label>
<div class="form-group row" v-for="(field, k) in fields" :key="k">
<div class="input-group">
<input id="email" type="email" class="form-control" name="email[]" v-model="field.email"
required placeholder="Add An Email Address">
</div>
<div class="col">
<div class="alert alert-success alert-dismissible fade show sticky-top mt-2" role="alert"
v-show="success">
Emails Have Been Seent
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
<div class="alert alert-danger alert-dismissible fade show sticky-top mt-2" role="alert"
v-if="errors && errors.email">
{{ errors.email[0] }}
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
</div>
</div>
<button type="submit" class="btn btn-success mb-2" #click="addNewRow">Add Row +</button>
<button type="submit" class="btn btn-primary btn-block mb-5" >Create Your Agency</button>
</form>
</div>
</div>
</template>
<script>
export default {
data() {
return {
fields: [{
email: '',
}],
errors: {},
success: false,
csrf: document.querySelector('meta[name="csrf-token"]').getAttribute('content')
}
},
methods: {
addNewRow() {
this.fields.push({
email: '',
});
},
submit() {
axios.post('/create-team', {
emailArray: this.fields
})
.then(response => {
this.fields = {};
this.success = true;
this.errors = {};
})
.catch(error => {
if (error.response.status === 422) {
this.errors = error.response.data.errors || {};
}
console.log('Still not saved');
});
},
},
}
</script>
Im using laravel cashier for stripe, im creating a subscription with no card up front and 15 days trial when user registration, im following laravel cashier tutorial to add payment method for user so card can be charged when trial is over but i keep getting error
below is my controller
class BillingController extends Controller {
public function getBilling()
{
return view('dashboard.billing', [
'intent' => Auth::user()->createSetupIntent()
]);
}
}
this is my view and script
#extends('layouts.app')
#section('content')
<div class="container">
<div class="row">
<div class="col-3">
#include('dashboard.partial.menu')
</div>
<div class="col-9">
<div class="card">
<div class="card-header">
Update Card Info
</div>
<div class="card-body">
#if(Auth::user()->subscribed() && Auth::user()->subscription('monthly')->onTrial())
<h6 class="card-title">Trial ends at: <span class="badge badge-primary">{{$diff = Carbon\Carbon::parse(Auth::user()->subscription('monthly')->trial_ends_at)->diffForHumans()}}</span></h6>
#endif
<h5>Subscription Details</h5>
<p>Monthly Membership - .99 <small>(Renews every month)</small></p>
#if (Auth::user()->hasPaymentMethod())
<h6>Card on file</h6>
<p>{{Auth::user()->card_brand}}: ending in <span class="badge badge-primary">{{Auth::user()->card_last_four}}</span></p>
#endif
<div class="form-group">
<input class="form-control" id="card-holder-name" type="text" placeholder="Cardholder name">
</div>
<!-- Stripe Elements Placeholder -->
<div id="card-element" class="form-control" style='margin-bottom: 1.5em;height: 2.4em; padding-top: .7em;'></div>
<div class="form-group">
<button class="btn btn-primary" id="card-button" data-secret="{{ $intent->client_secret }}">
Update Payment Method
</button>
</div>
</div>
</div>
</div>
</div>
</div>
#endsection #push('scripts')
window.addEventListener('load',function() { const stripe = Stripe('pk_test_xxxxxxxxxxxxxxxxxxxxxxx');
const elements = stripe.elements();
const cardElement = elements.create('card');
cardElement.mount('#card-element');
const cardHolderName = document.getElementById('card-holder-name');
const cardButton = document.getElementById('card-button');
const clientSecret = cardButton.dataset.secret;
cardButton.addEventListener('click', async (e) => {
const { setupIntent, error } = await stripe.handleCardSetup(
clientSecret, cardElement, {
payment_method_data: {
billing_details: { name: cardHolderName.value }
}
}
);
if (error) {
console.log(error);
} else {
stripePaymentHandler(setupIntent);
}
});
});
#endpush
and i get this error
Object { type: "invalid_request_error", code: "resource_missing", doc_url: "https://stripe.com/docs/error-codes/resource-missing", message: "No such setupintent: seti_1FjTcII7sKb0v4gBuFe9ZZ5f", param: "intent" }
I'm looping through user table. And each user table has a button that toggle(update:Boolean type) user status on user table. And I want the button for each user to have red color when the status value for the user is 0 and green when the status is 1. Also I want the button to change the color(LIVE) based on the status value each time it clicked.
component: ToggleStatus.vue
<template>
<div>
<button type="button" v-bind:class="buttonStatus" #click="goOnline">
<span class="ion-ios-wifi" ></span>
</button>
</div>
</template>
<script>
export default {
props: ['userId', 'onlinestat'],
mounted() {
console.log('Component mounted.')
},
data: function() {
return {
status: this.onlinestat,
}
},
methods: {
goOnline() {
axios.post('/reservation/online/' + this.userId )
.then(response => {
this.status =! this.status;
console.log(response.data);
})
.catch(errors => {
if (errors.response.status == 401){
window.location = '/login';
}
});
}
},
computed: {
buttonStatus() {
return(this.status) ? 'btn btn-outline-danger text-danger' : 'btn btn-success ';
}
}
}
</script>
Controller:
$authUser = Auth::user()->business_id;
$employee = User::where('business_id', $authUser)->get()->sortBy('name');
return view('backend.reservation.index', compact('employee'));
View/Blade
<div class="container-fluid flex-grow-1 container-p-y">
<div class="uikit-example">
<div class="row">
#foreach ($employee as $key => $emp)
<div class="col-lg-4 col-md-4 col-sm-12">
<div class="card mb-4">
<div class="card-body">
<div class="media align-items-center">
<img src="{{ asset('Upload/Images/Media/Avatar/Thumb/'.$emp->image) }}" alt class="ui-w-60 rounded-circle">
<div class="media-body pt-2 ml-3">
<h5 class="mb-2">{{ $emp->name }}</h5>
<div class="text-muted small mb-2">{{ $emp->phone }}</div>
<div class="text-muted small mb-2">{{ $emp->email }}</div>
<div class="text-muted small mb-2"><span>ID: </span>{{ $emp->user_code }}</div>
</div>
<div class="">
<toggleonline user-id="{{ $emp->id }}" onlinestat="{{ $emp->onlinestatus }}"></toggleonline>
</div>
</div>
</div>
<div class="card-footer text-center py-3">
{{-- + Go Online --}}
{{-- <span class="ion ion-md-mail"></span> --}}
{{-- <div class="float-right"> --}}
My Reservations
{{-- </div> --}}
</div>
</div>
</div>
#endforeach
</div>
</div>
</div>
The result I'm getting is that the button does toggle but the toggle button of all the user come red after on refresh page or when the page loads.
try
buttonStatus() {
return(this.status==0) ? 'btn btn-outline-danger text-danger' : 'btn btn-success ';
}
Hello I want to make a loop to iterate an array of data retrieve from a controller but I have an error message in vue js I can not find where is my error help me please I start with a vue js
here is my code
controller.php
public function index(){
$post= Posts::with('likes','comments', 'user')->orderBy('created_at','DESC')->get();
return $post ;
}
vue.js
const root = new Vue({
el: '#root',
data: {
msg: 'Update New Post:',
content: '',
posts: []
},
ready: function ready() {
this.created();
},
created: function created() {
var _this = this;
axios.get('http://localhost:8000/mur/posts')
.then(response => {
_this.posts = response.data;
//we are putting data into our posts array
console.log(response.data);
// show if success
Vue.filter('myOwnTime', function(value){
return moment(value).fromNow();
});
})
.catch(function (error) {
console.log(error); // run if we have error
});
}
},
view
<div v-for="post, key in posts">
<div class="col-md-12 col-sm-12 col-xs-12 all_posts">
<div class="col-md-1 pull-left">
<img :src="'{{asset('storage/avatar')}}/' + post.avatar"
style="width:50px;">
</div>
<div class="col-md-10" style="margin-left:10px">
<div class="row">
<div class="col-md-11">
<p><a :href="'{{url('profile')}}/' + post.slug" class="user_name"> #{{post.user.name}}</a> <br>
<span style="color:#AAADB3"> #{{ post.created_at }}
<i class="fa fa-globe"></i></span></p>
</div>
<div class="col-md-1 pull-right">
#if(Auth::check())
<!-- delete button goes here -->
<a href="#" data-toggle="dropdown" aria-haspopup="true">
{{--<img src="{{Config::get('app.url')}}/public/img/settings.png" width="20">--}}
</a>
<div class="dropdown-menu">
<li><a>some action here</a></li>
<li><a>some more action</a></li>
<div class="dropdown-divider"></div>
<li v-if="post.user_id == '{{Auth::user()->id}}'">
<a #click="deletePost(post.id)">
<i class="fa fa-trash"></i> Delete </a>
</li>
</div>
#endif
</div>
</div>
</div>
<p class="col-md-12" style="color:#000; margin-top:15px; font-family:inherit" >
#{{post.content}}
</p>
<div style="padding:10px; border-top:1px solid #ddd" class="col-md-12">
<!-- like button goes here -->
#if(Auth::check())
<div v-for="">
<div v-if="">
<p class="likeBtn" #click="likePost(post.id)">
<i class="fa fa-heart-o"></i>
</p>
</div>
</div>
data : #{{ post.likes.length }}
#endif
</div>
</div>
</div>
web.php
Route::get('mur/posts', 'PostController#index');
posts [ ] return this
[{"id":8,
"user_id":3,
"content":"content 1",
"status":0,
"created_at":"2017-12-27 22:43:20",
"updated_at":"2017-12-27 22:43:20",
"likes":[{"id":2,"posts_id":7,"user_id":3,"created_at":"2017-12-27 16:38:33","updated_at":null}],
"comments":[],
"user":{
"id":3,"name":"toto","sulg":"toto","email":"toto#hotmail.fr","avatar":"215563.jpg","is_actif":"activ\u00e9","created_at":"2017-12-06 15:30:42","updated_at":"2017-12-06 17:04:41"}
},
{"id":7,
"user_id":9,
"content":"coucou",
"status":0,
"created_at":"2017-12-27 16:07:01",
"updated_at":"2017-12-27 16:07:01",
"likes":[{"id":2,"posts_id":7,"user_id":4,"created_at":"2017-12-27 16:38:33","updated_at":null}],
"comments":[],
"user":{"id":9,"name":"blop","sulg":"blop","email":"blop#gmail.com","avatar":"logoBee.png","is_actif":"activ\u00e9","created_at":"2017-12-17 14:37:29","updated_at":"2017-12-17 14:37:29"}}
error in console