I'm using laravel Omni plugin for transactions. Once payment has been done , I'm getting error for success url.
public function checkOut(Request $request)
{
$params = array(
'cancelUrl' => 'http://localhost/vis/public/cancel_order',
'returnUrl' => 'http://localhost/vis/public/payment_success',
'name' => 'Meal',
'description' => 'Casper',
'amount' => '1.00',
'currency' => 'USD'
);
Session::put('params', $params);
Session::save();
$gateway = Omnipay::create('PayPal_Express');
$gateway->setUsername('un');
$gateway->setPassword('pwd');
$gateway->setSignature('signature');
$gateway->setTestMode(true);
$response = $gateway->purchase($params)->send();
if ($response->isSuccessful()) {
print_r($params);
redirect('payment_success/' . $this->orderNo);
// payment was successful: update database
print_r($response);
} elseif ($response->isRedirect()) {
// redirect to offsite payment gateway
$response->redirect();
} else {
// payment failed: display message to customer
echo $response->getMessage();
}
}
public function getSuccessPayment()
{
$gateway = Omnipay::create('PayPal_Express');
$gateway->setUsername('un');
$gateway->setPassword('pwd');
$gateway->setSignature('signature');
$gateway->setTestMode(true);
$params = Session::get('params');
$response = $gateway->completePurchase($params)->send();
$paypalResponse = $response->getData(); // this is the raw response object
if(isset($paypalResponse['PAYMENTINFO_0_ACK']) && $paypalResponse['PAYMENTINFO_0_ACK'] === 'Success') {
// Response
print_r($params);
// print_r($paypalResponse);
} else {
//Failed transaction
}
// return View('result');
print_r($params);
print_r($paypalResponse);
}
I'm getting following error
Not Found
HTTP Error 404. The requested resource is not found.
http://localhost/vis/public/payment_success?token=EC-1R845179Asss493N&PayerID=swdw3BS9REA4AN
It looks like you may have forgotten to add that route in the routes.php, Make sure you have something like this in routes.php
Route::get('/payment_success', 'StoreController#getSuccessPayment');
Change StoreController to the name of the controller this function is in.
Related
I'm using the mollie developer setup to simulate payment offers. I've followed a tutorial by my teacher and he hasn't any problems. So what is going on?
Because Mollie is an online service, I'm using Ngrok to create a tunnel for the webhook and my localhost. I'll post my code below but know that I wrote a Log which gave as response:
[2022-07-26 18:22:54] local.ERROR: Method App\Http\Controllers\webHookController::handle does not exist. {"exception":"[object] (BadMethodCallException(code: 0): Method App\Http\Controllers\webHookController::handle does not exist. at C:\Users\stefv\SCHOOL\GENT\NMD\WEBDEV2\werkstuk---geboortelijst-Stef-Verniers\vendor\laravel\framework\src\Illuminate\Routing\Controller.php:68)
I have no clue what exact error this log is targeting so if anyone can point this out, it's much appreciated!
Because the webhook can't get to mollie my status inside my database can't be changed so it's on 'pending' forever...
So I'm looking for a way to fix the error so my webhook can reach Mollie and my payment is accepted so the payment status in my database can change to 'paid'.
This is my code:
My Controller which sets up Mollie:
public function additional(Request $r)
{
$articles = Article::all();
$categories = Category::all();
$websites = Website::all();
$session_id = request()->session()->getId();
$cartItems = Cart::session($session_id)->getContent();
$cartTotal = Cart::session($session_id)->getTotal();
$r->session()->put('cusnaam', 'Cas');
$r->session()->put('tel', 'Tel');
$r->session()->put('email', 'Email');
$r->session()->put('pb', 'pb');
return view('customer-info', compact('articles', 'categories', 'websites', 'cartItems', 'cartTotal'));
}
public function checkout(Request $r)
{
$session_id = request()->session()->getId();
$cartTotal = Cart::session($session_id)->getTotal();
$order = new Order();
$order->name = $r->input('Cus');
$order->note = $r->input('pb');
$order->total = $cartTotal;
$order->status = 'pending';
$order->save();
$mollie = new \Mollie\Api\MollieApiClient();
$mollie->setApiKey("test_6vGchNb62gynePtcsNsbm8dartsmjU");
$mollie->methods->allAvailable();
$session_id = request()->session()->getId();
$cartItems = Cart::session($session_id)->getContent();
$valuta = number_format($cartTotal, 2);
$webhookUrl = route('webhooks.mollie');
if(App::environment('local')) {
$webhookUrl = 'https://5d25-84-199-205-243.eu.ngrok.io/webhooks/mollie';
};
$payment = Mollie::api()->payments->create([
"amount" => [
"currency" => "EUR",
"value" => $valuta // You must send the correct number of decimals, thus we enforce the use of strings
],
"description" => "Bestelling op dag " . date('d-m-Y h:i'),
"redirectUrl" => route('success'),
"webhookUrl" => $webhookUrl,
"metadata" => [
"order_id" => $order->id,
"order_name" => $order->name
],
]);
return redirect($payment->getCheckoutUrl(), 303);
}
public function success()
{
return view('succes');
}
And this is the controller that handles the webhook:
public function handleWebhookNotification(Request $request)
{
$payment = Mollie::api()->payments->get($request->id);
$orderId = $payment->metadata->order_id;
if ($payment->isPaid() && ! $payment->hasRefunds() && ! $payment->hasChargebacks()) {
$order = Order::findOrFail($orderId);
$order->status = 'paid';
$order->save();
Log::alert('tis in de cachoche');
} elseif ($payment->isOpen()) {
/*
* The payment is open.
*/
} elseif ($payment->isPending()) {
/*
* The payment is pending.
*/
} elseif ($payment->isFailed()) {
/*
* The payment has failed.
*/
} elseif ($payment->isExpired()) {
/*
* The payment is expired.
*/
} elseif ($payment->isCanceled()) {
/*
* The payment has been canceled.
*/
} elseif ($payment->hasRefunds()) {
/*
* The payment has been (partially) refunded.
* The status of the payment is still "paid"
*/
} elseif ($payment->hasChargebacks()) {
/*
* The payment has been (partially) charged back.
* The status of the payment is still "paid"
*/
}
}
I have created a custom payment plugin now I need to set up an endpoint that will receive webhook callbacks from the payment gateway. My code for the endpoint is as seen below:
add_action('rest_api_init', function () {
register_rest_route(
'namespace/v1/', 'endpoint',
array (
'methods' => 'POST',
'callback' => 'return_payment_status'
)
);
});
function return_payment_status (WP_REST_Request $request_data) {
$pay_resp = array();
$params = $request_data->get_params();
if ( isset($params['result']) ) {
$pay_resp['result'] = $params['result'];
$pay_resp['message'] = $params['message'];
}
else {
$pay_resp['result'] = 'Payment failed';
$pay_resp['message'] = $params['message'];
}
return $pay_resp;
}
Now when I try the endpoint in POSTMAN and send data I get the following response:
{ "result":"Payment failed", "message":null }
Which seems that no data is being sent to the endpoint. What can I do to fix it?
I cannot get a URL varible in my stripe checkout PHP slim app.
I need to be able to get a price varible from the URL to echo out into the session for the price of stripe payment. However it is just not working, I can use $_GET['price']; to echo out before it becomes a SLIM APP however when it becomes a SLIM APP it just wont work...
use Slim\Http\Request;
use Slim\Http\Response;
use Stripe\Stripe;
require 'vendor/autoload.php';
$dotenv = Dotenv\Dotenv::create(realpath('../../'));
$dotenv->load();
Stripe::setApiKey(getenv('STRIPE_SECRET_KEY'));
$db = new SQLite3('./store.db');
$db->exec("CREATE TABLE IF NOT EXISTS sessions(id INTEGER PRIMARY KEY, stripe_id TEXT, status TEXT)");
// createSession
function createSession($sessionId) {
global $db;
$stmt = $db->prepare("INSERT INTO sessions(stripe_id, status) VALUES (:id, 'pending')");
$stmt->bindValue(':id', $sessionId, SQLITE3_TEXT);
return $stmt->execute();
}
// markSessionPaid
function markSessionPaid($sessionId) {
global $db;
$stmt = $db->prepare("UPDATE sessions SET status='paid' WHERE :id = stripe_id");
$stmt->bindValue(':id', $sessionId, SQLITE3_TEXT);
return $stmt->execute();
}
// getSessionStatus
function getSessionStatus($sessionId) {
global $db;
$stmt = $db->prepare("SELECT status FROM sessions WHERE :id = stripe_id");
$stmt->bindValue(':id', $sessionId, SQLITE3_TEXT);
$result = $stmt->execute();
return $result->fetchArray()[0];
}
$app = new Slim\App;
$app->get('/', function (Request $request, Response $response, $args) {
$response->getBody()->write(file_get_contents("../../client/index.html"));
return $response;
});
$app->get('/success', function (Request $request, Response $response, $args) {
$response->getBody()->write(file_get_contents("../../client/success.html"));
return $response;
});
$app->get('/cancel', function (Request $request, Response $response, $args) {
$response->getBody()->write(file_get_contents("../../client/cancel.html"));
return $response;
});
function middleware1() {
$price = $app->request()->get('price');
};
$app->post('/create-session', 'middleware1', function(Request $request, Response $response) use ($app) {
try {
// One time payments
$session = \Stripe\Checkout\Session::create([
'payment_method_types' => ['card'],
'line_items' => [[
'name' => 'Order',
'description' => 'ORDER ID: 123456789A',
'images' => ['testimage'],
'amount' => $price,
'currency' => 'aud',
'quantity' => 1,
]],
'success_url' => 'http://localhost:4242/success?session_id={CHECKOUT_SESSION_ID}',
'cancel_url' => 'http://localhost:4242/cancel',
]);
// Subscription recurring payments
// $session = \Stripe\Checkout\Session::create([
// // 'customer' => 'cus_123',
// 'payment_method_types' => ['card'],
// 'subscription_data' => [
// 'items' => [[
// 'plan' => 'starter',
// 'quantity' => 1,
// ]],
// ],
// 'success_url' => 'http://localhost:4242/success?session_id={CHECKOUT_SESSION_ID}',
// 'cancel_url' => 'http://localhost:4242/cancel',
// ]);
createSession($session->id);
} catch (Exception $e) {
return $response->withJson($e->getJsonBody(), 400);
}
return $response->withJson($session);
});
$app->post('/webhook', function(Request $request, Response $response) use ($app) {
// You can find your endpoint's secret in your webhook settings
$endpoint_secret = getenv('STRIPE_WEBHOOK_SECRET');
$payload = $request->getBody();
$sig_header = $_SERVER['HTTP_STRIPE_SIGNATURE'];
$event = null;
try {
$event = \Stripe\Webhook::constructEvent(
$payload, $sig_header, $endpoint_secret
);
} catch(\UnexpectedValueException $e) {
// Invalid payload
http_response_code(400);
exit();
} catch(\Stripe\Exception\SignatureVerificationException $e) {
// Invalid signature
http_response_code(400);
exit();
}
// Handle the checkout.session.completed event
if ($event->type == 'checkout.session.completed') {
$session = $event->data->object;
// Fulfill the purchase...
handle_checkout_session($session);
}
return $response->withJson(['message' => 'success']);
});
$app->get('/session-status', function (Request $request, Response $response, array $args) {
$status = getSessionStatus($request->getQueryParam('session_id'));
return $response->withJson($status);
});
function handle_checkout_session($session) {
// Call out to inventory management system
// Ding in Slack
// send an email
markSessionPaid($session->id);
}
$app->run();
I've tried everything
$app->request()->get('price');
And more!
The URL looks like this www.example.com/server/php/?price=5770&orderid=y2INOqCUrEzrua1XwBMg
Any help would be greatly appreciated!
You cannot use $_GET in Slim since it wont work. One way to do it is since the parameters are passed in query I think you mean it like this checkout/?price=200. If so, then you can access it using this:
$queryParams = $app->request()->getQueryParams();
$price = $queryParams["price"];
This would probably work
I am developing rest web services using zend 2.
For error handling I am using below mentioned code in Module.php
public function onBootstrap(MvcEvent $e)
{
$eventManager = $e->getApplication()->getEventManager();
$moduleRouteListener = new ModuleRouteListener();
$moduleRouteListener->attach($eventManager);
$eventManager->attach(MvcEvent::EVENT_DISPATCH_ERROR, array(
$this,
'onDispatchError'
), 0);
$eventManager->attach(MvcEvent::EVENT_RENDER_ERROR, array(
$this,
'onRenderError'
), 0);
}
public function onDispatchError($e)
{
return $this->getJsonModelError($e);
}
public function onRenderError($e)
{
return $this->getJsonModelError($e);
}
/*
* Manages error's and return response_code and error message
*
* #return Zend\View\Model\JsonModel
*/
public function getJsonModelError($e)
{
$error = $e->getError();
if (! $error) {
return;
}
$response = $e->getResponse();
$sm = StaticServiceManager::getDefaultServiceManager();
$config = $sm->get('config');
$err_code = $response->getStatusCode();
$err_msg = $response->getReasonPhrase();
$response_code = $config['HTTP_ERROR'][$err_code]['response_code'];
$errorJson = array(
'response_code' => $response_code,
// 'status' => $err_code,
'message' => $err_msg
);
$model = new JsonModel($errorJson);
$e->setResult($model);
return $model;
}
However there are still cases which are not tracked by this approach. For e.g. Invalid HTTP method passed. Does there any way I can check final response and manipulate it e.g. I can check final response content-type & http status code to finally change the response to send some meaning full json message.
I'm using Socialite to get user information from facebook. All is going well but my redirect isn't working
Sub-routes
I read that it's not possible to do a redirect from a submethod, or
any method that's not in your routes.
But how else can i redirect the user after I logged them in?
My URL looks like this after the successfull facebook handshake
http://tmdb.app/auth/login/facebook?code=AQBTKNZIxbfdBruAJBqZ8xx9Qnz...
Code
class SocialController extends Controller {
public function login(Authenticate $authenticate, Request $request)
{
return $authenticate->execute($request->has('code'), $this);
}
public function userHasLoggedIn($data)
{
$user = User::where('provider_id', $data->id)->first();
if( !$user )
{
$user = User::create([
'name' => $data->name,
'email' => $data->email,
'provider' => 'facebook',
'provider_id' => $data->id
]);
}
// NOT WORKING!
return redirect('test');
}
}
Your login function should be handling the redirect.
I'm guessing execute returns $data if the user is sucessfully logged in and false if not.
class SocialController extends Controller {
public function login(Authenticate $authenticate, Request $request)
{
if($data = $authenticate->execute($request->has('code'), $this))
{
$user = User::where('provider_id', $data->id)->first();
// maybe delegate the user creation to another class/service?
if( !$user )
{
$user = User::create([
'name' => $data->name,
'email' => $data->email,
'provider' => 'facebook',
'provider_id' => $data->id
]);
}
return redirect('test');
}
return redirect('fail_view');
}
}
You can do it using PHP header function in Laravel sub method. I try it and works properly. Hope it can help you.
// You can using the following code
$url= url("about-laravel");
header("Location:" . $url);
exit;
// Or using the following code to redirect and keep set flash message
$result= $this->yourMethod(); // return redirect($this->route)->with('flash_message', 'I\'m Flash Message'); for TRUE or NULL for false
if( $result ){
return $result;
}