Invalid amount with Braintree, why? - laravel

The amount I'm passing seems correct, but I got always an error.
As I checkout the amount is invalid, even if I'm passing a float, and this error is shown on the page after submit:
The payment function is as following:
public function payment(Request $request) {
$data = $request->all();
// dd($data['price']);
$gateway = new Braintree\Gateway([
'environment' => config('services.braintree.environment'),
'merchantId' => config('services.braintree.merchantId'),
'publicKey' => config('services.braintree.publicKey'),
'privateKey' => config('services.braintree.privateKey')
]);
$amount = Sponsorship::where('price', $data['price'])->first();
// dd($amount);c
$nonce = $request->payment_method_nonce;
$result = $gateway->transaction()->sale([
'amount' => $amount,
'paymentMethodNonce' => $nonce,
'customer' => [
'firstName' => 'Tony',
'lastName' => 'Stark',
'email' => 'tony#avengers.com',
],
'options' => [
'submitForSettlement' => true
]
]);
if ($result->success) {
$transaction = $result->transaction;
// header("Location: transaction.php?id=" . $transaction->id);
return back()->with('success_message', 'Transaction successful. The ID is:'. $transaction->id);
} else {
$errorString = "";
foreach ($result->errors->deepAll() as $error) {
$errorString .= 'Error: ' . $error->code . ": " . $error->message . "\n";
}
// $_SESSION["errors"] = $errorString;
// header("Location: index.php");
return back()->withErrors('An error occurred with the message: '.$result->message);
}
}

Related

Capture stripe payment

I am using the stripe/stripe package to capture payment for single product. Everything is working as expected however when the user is returned to the order-confirmation page, I would like to get the stripe payment id. How would i achieve this?
Im not sure if i need a webhook and if i would, how would i use this?
public function onCharge() {
$user = Auth::getUser();
$course = CourseMeta::where('id', $this->param('id'))->first();
$stripe = new \Stripe\StripeClient(env('STRIPE_SECRET'));
$product = $stripe->products->create([
'name' => $course->course->name . ' - ' . $course->date,
]);
$price = $stripe->prices->create([
'unit_amount' => $course->price * 120,
'currency' => 'gbp',
'product' => $product->id,
]);
$validator = Validator::make(
[
'user_id' => $user->id,
'coursemeta_id' => $course->id,
'course_id' => $course->course->id,
'stripe_id' => '1',
],
[
'user_id' => 'required',
'coursemeta_id' => 'required',
'course_id' => 'required',
'stripe_id' => 'required'
]
);
if ($validator->fails()) {
return Redirect::back()->withErrors($validator);
} else {
$order = new Order();
$order->user_id = $user->id;
$order->coursemeta_id = $course->id;
$order->stripe_id = '1';
$order->company = request()->get('company');
$order->company_firstname = request()->get('company_firstname');
$order->company_lastname = request()->get('company_lastname');
$order->company_email = request()->get('company_email');
$order->company_phone = request()->get('company_phone');
$order->citb_levy = request()->get('citb_levy');
$order->d_firstname = request()->get('d_firstname');
$order->d_lastname = request()->get('d_lastname');
$order->d_email = request()->get('d_email');
$order->d_phone = request()->get('d_phone');
$order->d_dob = request()->get('d_dob');
$order->d_ninumber = request()->get('d_ninumber');
$order->save();
}
$portal = $stripe->checkout->sessions->create([
'success_url' => env('APP_URL') . '/order-confirmation'.'?' . 'user=' . $user->id . '&' . 'course=' . $course->id,
'cancel_url' => env('APP_URL') . '/cancel',
'line_items' => [
[
'price' => $price->id,
'quantity' => 1
],
],
'mode' => 'payment',
]);
return redirect($portal->url);
}
You need to use the checkout session ID.
when you create success_url and cancel_url you can also pass {CHECKOUT_SESSION_ID} param with curly braces. when payment gateway will redirect to one of those URLs it will automatically replace {CHECKOUT_SESSION_ID} with the actual session ID.
In your case
$portal = $stripe->checkout->sessions->create([
// HERE ---------------------------------------------------\/----------\/
'success_url' => env('APP_URL') . '/order-confirmation'.'?session_id={CHECKOUT_SESSION_ID}&' . 'user='. $user->id . '&' . 'course=' . $course->id,
'cancel_url' => env('APP_URL') . '/cancel',
'line_items' => [
[
'price' => $price->id,
'quantity' => 1
],
],
'mode' => 'payment',
]);
Now when this page is called you can have session ID and you can retrieve all stuff from it.
// on success or cancel page you can use this code to get infos
$stripe = new \Stripe\StripeClient(env('STRIPE_SECRET'));
$session = \Stripe\Checkout\Session::retrieve(get('session_id'));
$customer = \Stripe\Customer::retrieve($session->customer);
$paymentIntent = \Stripe\PaymentIntent::retrieve($session->payment_intent);
// from this $session you can get customer/items/paymentIntent etc..
ref : https://stripe.com/docs/payments/checkout/custom-success-page
if any doubt please comment.

How to Create Multiple input with laravel API?

I want to make an report API with the option of being able to do multiple inputs for violators data, crime scene photo data and personnel data.
I've tried to code like below, but still can't do multiple input. What is the correct way to create multiple inputs in laravel API (with file upload) ?
Controller
public function store(ReportRequest $request)
{
try {
$report = Report::create([
'category_id' => $request->category_id,
'user_id' => Auth::user()->id,
'title' => $request->title,
'description' => $request->description,
'incident_date' => $request->incident_date,
'injured_victims' => $request->injured_victims,
'survivors' => $request->survivors,
'dead_victims' => $request->dead_victims,
'location' => $request->location,
'latitude' => $request->latitude,
'longitude' => $request->longitude
]);
if ($request->category_id !== 4 && $request->violator_photo) {
$violators = $request->file('violator_photo');
$violators = [];
foreach($violators as $key => $value) {
if($request->hasFile('violator_photo')) {
$violator_photo = $request->hasFile('violator_photo');
$fileName = time().'_'.$violator_photo[$key]->getClientOriginalName();
$filePath = $violator_photo[$key]->storeAs('images/pelanggar', $fileName, 'public');
}
$data = new Violator();
$data->report_id = $report->id;
$data->name = $request->violator_name[$key];
$data->photo = $filePath[$key];
$data->age = $request->violator_age[$key];
$data->phone = $request->violator_phone[$key];
$data->save();
}
}
$files = $request->file('crime_scene_photo');
$files = [];
foreach($files as $key => $value) {
if($request->hasFile('crime_scene_photo')) {
$crime_scene_photo = $request->hasFile('crime_scene_photo');
$name = time().'_'.$crime_scene_photo[$key]->getClientOriginalName();
$path = $crime_scene_photo[$key]->storeAs('images/tkp', $name, 'public');
}
$data = new CrimeScenePhoto();
$data->report_id = $report->id;
$data->path = $path[$key];
$data->caption = $request->caption[$key];
$data->save();
}
if (\Auth::user()->unit_id == 2 && $request->personel) {
foreach ($request->personel as $key => $value) {
$report->members()->sync($request->personel[$key]);
}
}
return response()->json([
'status' => '200',
'message' => 'success',
'data' => [
$report,
$request->all()
],
]);
} catch (\Exception$err) {
return $this->respondInternalError([$err->getMessage(), $request->all()]);
}
}
And here is how I tested in postman.
Solved. i changed my code to like this and it work.
public function store(ReportRequest $request)
{
try {
$report = Report::create([
'category_id' => $request->category_id,
'user_id' => Auth::user()->id,
'title' => $request->title,
'description' => $request->description,
'incident_date' => $request->incident_date,
'injured_victims' => $request->injured_victims,
'survivors' => $request->survivors,
'dead_victims' => $request->dead_victims,
'location' => $request->location,
'latitude' => $request->latitude,
'longitude' => $request->longitude
]);
if ($request->hasFile('violator_photo')) {
foreach($request->file('violator_photo') as $key => $value) {
$vio_photo = $request->file('crime_scene_photo');
$fileName = time().'_'.$vio_photo[$key]->getClientOriginalName();
$filePath = $vio_photo[$key]->storeAs('images/pelanggar', $fileName, 'public');
Violator::create([
'report_id' => $report->id,
'name' => $request->violator_name[$key] ?? null,
'photo' => $filePath ?? null,
'age' => $request->violator_age[$key] ?? null,
'phone' => $request->violator_phone[$key] ?? null
]);
}
}
if ($request->hasFile('crime_scene_photo')) {
foreach($request->file('crime_scene_photo') as $key => $value) {
$crime_scene_photo = $request->file('crime_scene_photo');
$name = time().'_'.$crime_scene_photo[$key]->getClientOriginalName();
$path = $crime_scene_photo[$key]->storeAs('images/tkp', $name, 'public');
CrimeScenePhoto::create([
'report_id' => $report->id,
'path' => $path ?? null,
'caption' => $request->caption[$key] ?? null
]);
}
}
if (\Auth::user()->unit_id == 2 && $request->personel_id) {
foreach ($request->personel_id as $key => $value) {
$report->members()->attach($request->personel_id[$key]);
}
}
return response()->json([
'status' => '200',
'message' => 'success',
'data' => [
$report, $report->members, $report->violators, $report->photos
],
]);
} catch (\Exception$err) {
return $this->respondInternalError([$err->getMessage(), $request->all()]);
}
}

Only updating image if something else is updated, not if only updating image

I'm trying to update an item that could have an image or change the one that is already there, when I only change the image or add one it doesn't update, but if I change or add an image along with something else like the name or description then it does update both things. I'm not sure why this is happening.
I'm sending it to the controller like this
submit(item) {
let data = new FormData();
data.append('file', this.imagen);
data.append('name', this.ruleForm.name);
data.append('summary', this.ruleForm.summary);
data.append('description', this.ruleForm.description);
data.append('price', this.ruleForm.price);
data.append('hours', this.ruleForm.hours);
data.append('min_grade', this.ruleForm.min_grade);
data.append('matery', this.matery);
data.append('remover', this.remover);
data.append('strict', this.strict);
this.$refs.ruleForm.validate((valid) => {
if (valid) {
this.loading = true;
this.$inertia.post('/courses/' + item.id, data)
.then(
() => {
this.$message({
type: 'success',
message: 'Guardado correctamente.'
});
this.loading = false
},
(res) => {
this.$message.error(parseError(res)[0]);
this.loading = false;
})
} else {
return false;
}
});
},
This is the full update function in the controller
public function update(CourseSaveRequest $request, $id)
{
Log::info($request);
$editCourse = Course::find($id);
$editCourse->name = $request->name;
$editCourse->summary = $request->summary;
$editCourse->description = $request->description;
$editCourse->price = $request->price;
$editCourse->hours = $request->hours;
$editCourse->min_grade = $request->min_grade;
if ($request->hasFile('file')) {
$this->removeImage($editCourse);
$image = $request->file('file');
$imageName = Uuid::generate(4)->string . '.' . $image->getClientOriginalExtension();
$editCourse->image = '/' . 'img/courses' . '/' . $imageName;
$request->file('file')->move('img/courses', $imageName);
}
$editCourse->save();
return back();
}
private function removeImage(Course $course){
if (!empty($course->image) && file_exists(public_path($course->image))) {
unlink(public_path($course->image));
}
}
Not sure if this is relevant but this is the CourseSaveRequest
public function rules()
{
$rules = [
'name' => 'required|unique:courses',
'summary' => 'required',
'price' => 'required|numeric|min:0',
'hours' => 'required|numeric|min:0',
'min_grade' => 'required|numeric|min:0'
];
if ($this->has('id')) {
$rules['name'] .= ',id,'.$this->get('id');
}
return $rules;
}
I suspect it's the unique rule on the name, you can ignore the current model instance on unique with the following
use Illuminate\Validation\Rule;
...
public function rules()
{
$rules = [
'name' => [
'required',
Rule::unique('courses')->ignore($this->id)
],
'summary' => 'required',
'price' => 'required|numeric|min:0',
'hours' => 'required|numeric|min:0',
'min_grade' => 'required|numeric|min:0'
];
return $rules;
}

How to access property of an object in Laravel PHP?

I am having 2 methods. In one of the method I am making a call to database, a pure and simple one Document::findOrFail($data->id). But this is always returning me null although a record is already persisted. Any idea how to get this simple thing sorted?
public function lockExport(Request $request){
$document = Document::create([
'user_id' => $this->userId(),
'extension' => $extension,
'name' => $filename,
'file_path' => $filepath,
'size' => File::size($filepath . $filename),
'received_at' => Carbon::now()->format('Y-m-d')
]);
$isAttachment = false;
Cache::put($token, ['file' => $document->file_path . $document->name . '.' . $document->extension, 'is_attachment' => $isAttachment, 'id' => $document->id], 3);
return $this->downloadlockExport($token);
}
public function downloadlockExport($token)
{
try {
$data = (object) Cache::get($token);
// dd I get the full $data as object
$document = Document::findOrFail($data->id);
// undefined. Above query did not execute.
// Thus, below query failed
$document->update(['downloads' => $document->downloads + 1]);
$content = Crypt::decrypt(File::get($data->file));
return response()->make($content, 200, array(
'Content-Disposition' => 'attachment; filename="' . basename($data->file) . '"'
));
} catch (\Exception $e) {
\App::abort(404);
}
}
What you probably would like to do is:
public function lockExport(Request $request){
$document = Document::create([
'user_id' => $this->userId(),
'extension' => $extension,
'name' => $filename,
'file_path' => $filepath,
'size' => File::size($filepath . $filename),
'received_at' => Carbon::now()->format('Y-m-d')
]);
$isAttachment = false;
$token = 'mytoken';
Cache::put($token, ['file' => $document->file_path . $document->name . '.' . $document->extension, 'is_attachment' => $isAttachment, 'id' => $document->id], 3);
return $this->downloadlockExport($token);
}
This way you will get your $token in your called function and you will get the $data correctly as I see.
And in the downloadlockExport() function you will have the ID like this:
$document = Document::findOrFail($data->mytoken['id']);
or you can use:
$document = Document::findOrFail($data->$token['id']);
similar with getting the File value:
$content = Crypt::decrypt(File::get($data->$token['file']));

Throw error message if user is not active using Laravel

I have field status in my users table and O want to check if status is 0 then user should not login and if 1 user should be able to login.
Here is my login code (controller is lengthy, please avoid some irrelevant code):
public function fdLogin(Request $request)
{
$credentials = $request->only('email', 'password');
$rules = [
'email' => 'required|email',
'password' => 'required',
];
$validator = Validator::make($credentials, $rules);
if ($validator->fails()) {
return response()->json([
'status' => false,
'message' => __('messages.validation_errors'),
'errors' => $validator->messages()
]);
}
$token = "";
try {
// if Request has latitude and longitude
$latFrom = $longFrom = $givenSpeciality = "";
$locationTag = false;
if ($request->has('lat') && $request->has('long') && $request->has('specialityKey') && !empty($request->lat) && !empty($request->long) && !empty($request->specialityKey)) {
$latFrom = $request->lat;
$longFrom = $request->long;
$givenSpeciality = $request->specialityKey;
$locationTag = true;
}
if (!Auth::attempt($credentials)) {
return response()->json(array('status' => false, 'message' => 'Invalid username or password', 'errors' => array('Invalid username or password')));
}
$speciality = DB::table('specialities')
->join('user_facility', 'specialities.id', 'user_facility.speciality_id')
->where('user_facility.user_id', Auth::user()->id)
->select('specialities.name', 'specialities.id')->first();
$types = [];
if (!empty($speciality)) {
$types = $speciality;
}
$customClaims = ['exp' => Carbon::now()->addYear()->timestamp, 'specialityType' => $types];
if (!$token = JWTAuth::claims($customClaims)->attempt($credentials)) {
return response()->json([
'status' => false,
'message' => 'We can`t find an account with this credentials.'
], 401);
}
} catch (JWTException $e) {
// Something went wrong with JWT Auth.
return response()->json([
'status' => false,
'message' => 'Failed to login, please try again.'
], 500);
}
$withInFacility['logged_in_facility'] = array();
$currentUser = Auth::user();
$user_id = $currentUser->id;
if ($locationTag) {
$userWithFacilities = $currentUser->load('facilities.facilityLocation', 'facilities.speciality.avaliableSpeciality');
$locations = array();
if (isset($userWithFacilities['facilities']) && count($userWithFacilities['facilities'])) {
foreach ($userWithFacilities['facilities'] as $facility) {
$faci = $facility->toArray();
if (!empty($faci['facility_location']) && $faci['facility_location'] > 0) {
$demo = $faci['facility_location'];
}
if (isset($faci['speciality']) && count($faci['speciality']) > 0) {
$speciality = $faci['speciality'];
if (isset($speciality['avaliable_speciality']) && count($speciality['avaliable_speciality']) > 0) {
$avaliable_speciality = $speciality['avaliable_speciality'];
$demo['avaliable'] = $avaliable_speciality['specialty_key'];
}
}
$locations[] = $demo;
}
if (count($locations)) {
foreach ($locations as $location) {
$distance = self::distance($latFrom, $longFrom, $location['lat'], $location['long']);
// if distance is less than 100 meter ''ll eligible to login else Log him out
if ($distance < config('constants.facility_radius')) {
if ($location['avaliable'] == $givenSpeciality) {
$withInFacility['logged_in_facility'] = $location;
$withInFacility['logged_in_facility']['radius'] = config('constants.facility_radius');
}
}
}
// if distance is less than 100 meter ''ll eligible to login else Log him out
if (empty($withInFacility['logged_in_facility'])) {
JWTAuth::setToken($token)->invalidate();
return response()->json(['status' => false, 'message' => 'Your are not in facility OR Your speciality did not matched with facility', 'errors' => '']);
}
} else {
return response(['status' => false, 'message' => 'Your Facility did not have any location , please ask for administrator', 'data' => null]);
}
} else {
return response(['status' => false, 'message' => 'You did not have any facility , please ask for administrator', 'data' => null]);
}
}
$currentUser->basicInfo = $this->userBasicInfo->where('user_id', $user_id)->first();
$is_super_admin = DB::table('users')->select('users.is_super_admin')->where('id', $user_id)->first();
$specialitiesAndRoles = DB::table('user_facility')
->leftjoin('roles', 'user_facility.role_id', 'roles.id')
->leftjoin('specialities', 'user_facility.speciality_id', '=', 'specialities.id')
->leftjoin('available_specialties', 'specialities.available_specialties_id', '=', 'available_specialties.id')
->where('user_facility.user_id', $user_id)
->select('user_facility.facility_id', 'user_facility.speciality_id', 'user_facility.is_facility_supervisor', 'user_facility.priv_key', 'user_facility.role_id', 'specialities.name', 'available_specialties.id', 'available_specialties.specialty_key')
->get();
$superadmin = $is_super_admin->is_super_admin;
$specialities = (object)$specialitiesAndRoles;
$sp = $specialitiesAndRoles->toArray();
$specialty_key = "";
if (!empty($sp)) {
$specialty_key = $sp[0]->specialty_key;
}
$fac_privs = array();
if (!empty($sp)) {
foreach ($sp as $s) {
$s = (array)$s;
$s['priv_list'] = Helpers::get_checked_privs($s);
$fac_privs[] = $s;
}
}
if (count($withInFacility['logged_in_facility'])) {
$withInFacilityObj = (object)$withInFacility['logged_in_facility'];
} else {
$withInFacilityObj = NULL;
}
$response = ['is_super_admin' => $superadmin, 'facilities' => $fac_privs, 'logged_in_facility' => $withInFacilityObj];
if ($superadmin == 1) {
$response['priv_ist'] = Helpers::get_priv_list();
}
$speciality = $this->speciality;
if ($speciality) {
$user = DB::table('verify_users')->where('user_id', $user_id)->first();
DB::table('verify_users')->insert([
'token' => $token,
'user_id' => $user_id,
]);
if ($specialty_key == 'medical_doctor') {
$md_db = DB::connection('doctorDB');
$user = $md_db->table('auth_token')->where('user_id', $user_id)->first();
if ($user) {
$md_db->table('auth_token')->where('id', $user->id)->update([
'token' => $token,
'isValid' => 1,
]);
} else {
$md_db->table('auth_token')->insert([
'token' => $token,
'isValid' => 1,
'user_id' => $user_id
]);
}
}
}
$user_data = $this->GetUserInfo();
unset($currentUser['facilities']);
return response()->json([
'status' => true,
'message' => 'Login successfully',
'data' => [
'token' => $token,
'userData' => $currentUser,
'userInfo' => $user_data,
'privileges' => $response,
]
]);
}
This is my whole controller of login I am not using Laravel built-in authentication, I have created my own login based on my project requirement, and I want to implement this functionality.
I don't know why you are not checking when you get the user info. I am not sure what is your purpose but may be this code will help you.
$currentUser = Auth::user();
if($currentUser->status == 0){
Auth::logout();
return response()->json([
'status' => false,
'message' => 'Failed to login, Access forbidden.',
], 403);
}

Resources