I want to store more customer information from my Paystack form such as first name, last name and shipping address, but only email and amount is stored. I discovered this can be done using metadata but I really don't know how to go about it. I'd be glad if anyone can help.
The HTML payment form
<form class="container" id="paymentForm">
<h3>Please fill the form below</h3>
<div class="form-group">
<label for="first_name">First Name</label>
<input class="form-control" type="text" id="first-name" required />
</div>
<div class="form-group">
<label for="last_name">Last Name</label>
<input class="form-control" type="text" id="last-name" required />
</div>
<input type="text" class="amount" id="amount" value="" hidden>
<div class="form-group">
<label for="email">Email Address</label>
<input class="form-control" type="email" id="email-address" required />
</div>
<div class="form-group">
<label for="address">Shipping Address</label>
<input class="form-control" type="text" id="shipping-address" required />
</div>
<div class="form-submit">
<button type="submit" class="btn btn-primary btn-lg" onclick="payWithPaystack()"> Pay </button>
</div>
</form>
Here's Paystack Js code
const paymentForm = document.getElementById('paymentForm');
paymentForm.addEventListener("submit", payWithPaystack, false);
function payWithPaystack(e) {
e.preventDefault();
let handler = PaystackPop.setup({
key: 'pk_test_xxxxxxxxxx', // Replace with your public key
email: document.getElementById("email-address").value,
amount: document.getElementById("amount").value * 100,
//these three values (first_name, last_name and address) aren't retrieved
first_name: document.getElementById("first-name").value,
last_name: document.getElementById("last-name").value,
address: document.getElementById("shipping-address").value,
ref: 'CLE-BPS' + Math.floor((Math.random() * 1000000000) + 1), // generates a pseudo-unique reference. Please replace with a reference you generated. Or remove the line entirely so our API will generate one for you
// label: "Optional string that replaces customer email"
onClose: function() {
window.location = "https://my-url/?transaction=cancelled";
alert('Transaction cancelled.');
},
callback: function(response) {
let message = 'Payment complete! Reference: ' + response.reference;
alert(message);
window.location = "https://my-url/verify_transaction.php?reference=" + response.reference;
}
});
handler.openIframe();
}
verify_transaction.php
<?php
$ref = $_GET['reference'];
if ($ref == "") {
header("Location: javascript://history.go(-1)");
exit();
}
$curl = curl_init();
curl_setopt_array($curl, array(
CURLOPT_URL => "https://api.paystack.co/transaction/verify/" . rawurlencode($ref),
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "GET",
CURLOPT_HTTPHEADER => array(
"Authorization: Bearer SECRET_KEY",
"Cache-Control: no-cache",
),
));
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
//echo $response;
$result = json_decode($response);
}
if ($result->data->status == 'success') {
$status = $result->data->status;
$reference = $result->data->reference;
$amount = $result->data->amount;
$l_name = $result->data->customer->last_name;
$f_name = $result->data->customer->first_name;
$fullname = $f_name . " " . $l_name;
$customer_email = $result->data->customer->email;
$shipping_address = $result->data->customer->address;
$customer_id = $result->data->customer->id;
$date = date('d-m-Y H:i:s');
include "config.php";
$stmt = $link->prepare("INSERT INTO transactions (status, reference, fullname, amount, customer_email, shipping_address, customer_id, date_purchased) VALUES (?, ?, ?, ?, ?, ?, ?, ?)");
$stmt->bind_param("ssssssss", $status, $reference, $fullname, $amount, $customer_email, $shipping_address, $customer_id, $date);
$stmt->execute();
if (!$stmt) {
echo "Oops...Something went wrong";
} else {
header("Location: https://my-url/success.php?status=success");
exit();
}
$stmt->close();
$link->close();
} else {
header("Location: error.php");
exit();
}
modify your paystack js code to look like this:
metadata:{
custom_field:[
{
first_name: document.getElementById("first-name").value,
last_name: document.getElementById("last-name").value,
address: document.getElementById("shipping-address").value,
}
]
}
so from the code above, I am creating a property, metadata and value is an object, and inside of the object, I am creating another property, custom_field and the value is an array. Place the additional fields you want to add in an object and place it inside of the custom_field property defined. You can place an many object as you want inside the custom_field array defined.
modify your verify_transaction.php to get the values;
After $result = json_decode($response);
$first_name = $result->data->metadata->custom_field[0]->first_name,
$last_name = $result->data->metadata->custom_field[0]->last_name,
$address = $result->data->metadata->custom_field[0]->address,
However, you can echo $response to see where the defined metadata is.
Related
I am making a newsletter integration with external api , and it works fine but on submit my entire page redirects to admin post php , i have tried to use it without action and adding ajax script to footer but don't exactly know how to use my wp_remote method to send data without refreshing or redirecting my page
<?php
namespace SalesManago;
if (!defined('ABSPATH')) {
die;
}
/**
* Class ZH_SalesmanagoNewsletter
*/
class ZH_SalesmanagoNewsletter extends ZH_Salesmanago {
public function __construct() {
add_shortcode( 'sm_newsletter', array($this, 'newsletter_form' ));
add_action('admin_post_nopriv_newsletter', array($this, 'saveDataNewsletter'));
add_action('admin_post_newsletter', array($this, 'saveDataNewsletter'));
}
public function newsletter_form() {
return "
<div style='height: 300px; display: block; position: relative'></div>
<form id='ajax-newsletter-form' action='". esc_url( admin_url('admin-post.php') ) . "' method='post'>
<label for='email'>Email</label>
<input type='email' name='email' id='email' required>
<input type='hidden' name='action' value='newsletter'>
<input type='submit' name='sm-submit' value='>'>
</form>";
}
public function prepareDefaultNewsletterData()
{
$clientId = SALESMANAGO_CLIENTID;
$apiKey = SALESMANAGO_APIKEY;
$apiSecret = SALESMANAGO_APISECRET;
$data = [
'clientId' => $clientId,
'apiKey' => $apiKey,
'requestTime' => time(),
'sha' => sha1($apiKey . $clientId . $apiSecret),
];
return $data;
}
public function parseNewsletterData(){
$email = $_POST['email'];
$set[0]['contact'] = array(
'email' => $email,
);
return $set;
}
public function saveDataNewsletter(){
if (isset($_POST['sm-submit'])) {
$set = $this->parseNewsletterData();
$params = array(
"upsertDetails" => $set,
"owner" => SALESMANAGO_OWNER,
);
$data = array_merge($this->prepareDefaultSalesData(), $params);
$headers = [
'Content-Type' => 'application/json'
];
$result = wp_remote_post( SALESMANAGO_ENDPOINT .'/api/contact/batchupsertv2',
array(
'method' => 'POST',
'headers' => $headers,
'sslverify' => false,
'body' => json_encode($data)
)
);
}
}
}
This implementation of dropzone.js works on my local host, but when I move it to live the files don't end up on the server:
Here's the form:
<form action="submit.php" enctype="multipart/form-data" method="POST">
<label for="fname">First name: </label>
<input type="text" name="fname" id="fname" required />
<label for="lname">Surname:</label>
<input type="text" name="lname" id="lname" required />
<div class="dropzone" id="file-upload"></div>
<button type="submit" id="submit-all">Submit</button>
</form>
I am using AJAX to submit the form:
$(document).ready(function() {
Dropzone.options.fileUpload = {
url: '/submit.php',
autoProcessQueue: false,
paramName: 'file',
uploadMultiple: true,
parallelUploads: 1,
maxFiles: 1,
maxFilesize: 10,
acceptedFiles: 'image/*,.mp4,.mkv,.avi',
addRemoveLinks: true,
init: function() {
dzClosure = this;
document.getElementById("submit-all").addEventListener("click", function(e) {
e.preventDefault();
e.stopPropagation();
dzClosure.processQueue();
});
this.on("sendingmultiple", function(data, xhr, formData) {
formData.append("fname", jQuery("#fname").val());
formData.append("lname", jQuery("#lname").val());
});
}
}
});
});
submit.php
<?php
require_once "db.php";
$target_dir = "uploads/";
echo '<pre>';
if (move_uploaded_file($_FILES["file"]["tmp_name"][0], $target_dir.$_FILES['file']['name'][0])) {
$status = 1;
echo 'uploaded, ';
}
else {
echo 'not uploaded, ';
}
echo 'Here is some more debugging info:';
print_r($_FILES);
print "</pre>";
$fname = mysqli_real_escape_string($conn, $_POST['fname']);
$lname = mysqli_real_escape_string($conn, $_POST['lname']);
if(mysqli_query($conn, "INSERT INTO CF_form(fname, lname
) VALUES('" . $fname . "', '" . $lname . "')")) {
echo 'sent';
} else {
echo "Error: " . $sql . "" . mysqli_error($conn);
}
mysqli_close($conn);
As I said, this all works on my local host but on the live site the file doesn't appear. I get the 'sent' message and the debugging info is like this:
uploaded, Here is some more debugging info:
Array
(
[file] => Array
(
[name] => Array
(
[0] => IMG_1129.JPG
)
[type] => Array
(
[0] => image/jpeg
)
[tmp_name] => Array
(
[0] => /tmp/phpriOyPQ
)
[error] => Array
(
[0] => 0
)
[size] => Array
(
[0] => 2181000
)
)
)
sent
The uploads directory is set to 777. Just can't figure out why I'm not getting the files.
I'm unable to see the "message sent successfully" after clicking on the Send button even though it's mentioned here on php: if( $sendEmail == true ):
echo '{ "alert": "success", "message": "' . $message_success . '" }';
The code is from a template, here is the HTML, PHP and JS code bellow:
HTML:
<div class="contact-form">
<form class="text-white mb-0" id="cf" name="cf" action="include/sendemail.php" method="post">
<div class="row">
<div class="form-process"></div>
<div class="col-12 col-md-6">
<div class="form-group error-text-white">
<input type="text" id="cf-name" name="cf-name" placeholder="Nom" class="form-control fc-bordered fc-light required">
</div>
</div>
<div class="col-12 col-md-6">
<div class="form-group error-text-white">
<input type="email" id="cf-email" name="cf-email" placeholder="Adresse E-mail" class="form-control fc-bordered fc-light required">
</div>
</div>
<div class="col-12 mb-4">
<div class="form-group error-text-white">
<textarea name="cf-message" id="cf-message" placeholder="Message" class="form-control fc-bordered fc-light required" rows="7"></textarea>
</div>
</div>
<div class="col-12 d-none">
<input type="text" id="cf-botcheck" name="cf-botcheck" value="" class="form-control fc-bordered fc-light" />
</div>
<div class="col-12">
<button class="btn btn-white" type="submit" id="cf-submit" name="cf-submit">Send Message</button>
</div>
</div>
</form>
<div class="contact-form-result pt-1"></div>
</div>
PHP:
<?php
use PHPMailer\PHPMailer\PHPMailer;
require 'phpmailer/src/PHPMailer.php';
// If you intend you use SMTP, uncomment next line
//require 'phpmailer/src/SMTP.php';
$toemails = array();
$toemails[] = array(
'email' => 'xxxx', // Your Email Address
'name' => 'xxxx' // Your Name
);
// Form Processing Messages
$message_success = 'We have successfully received your Message and
will get Back to you as soon as possible.';
$mail = new PHPMailer();
// If you intend you use SMTP, add your SMTP Code after this Line-
if( $_SERVER['REQUEST_METHOD'] == 'POST' ) {
if( $_POST['cf-email'] != '' ) {
$name = isset( $_POST['cf-name'] ) ? $_POST['cf-name'] : '';
$email = isset( $_POST['cf-email'] ) ? $_POST['cf-email'] : '';
$subject = isset( $_POST['cf-subject'] ) ? $_POST['cf-subject'] : '';
$message = isset( $_POST['cf-message'] ) ? $_POST['cf-message'] : '';
$subject = isset($subject) ? $subject : 'New Message From Contact Form';
$botcheck = $_POST['cf-botcheck'];
if( $botcheck == '' ) {
$mail->CharSet = 'UTF-8';
$mail->SetFrom( $email , $name );
$mail->AddReplyTo( $email , $name );
foreach( $toemails as $toemail ) {
$mail->AddAddress( $toemail['email'] , $toemail['name'] );
}
$mail->Subject = $subject;
$name = isset($name) ? "Name: $name<br><br>" : '';
$email = isset($email) ? "Email: $email<br><br>" : '';
$message = isset($message) ? "Message: $message<br><br>" : '';
$referrer = $_SERVER['HTTP_REFERER'] ? '<br><br><br>This Form was submitted from: ' . $_SERVER['HTTP_REFERER'] : '';
$body = "$name $email $message $referrer";
$mail->MsgHTML( $body );
$sendEmail = $mail->Send();
if( $sendEmail == true ):
echo '{ "alert": "success", "message": "' . $message_success . '" }';
else
echo '{ "alert": "error", "message": "Email could not be sent due to some Unexpected Error. Please Try Again later.<br /><br />Reason:<br />' . $mail->ErrorInfo . '" }';
endif;
} else {
echo '{ "alert": "error", "message": "Bot Detected.! Clean yourself Botster.!" }';
}
} else {
echo '{ "alert": "error", "message": "Please Fill up all the Fields and Try Again." }';
}
} else {
echo '{ "alert": "error", "message": "An unexpected error occured.
Please Try Again later." }';
}
?>
JS:
function ln_contactForm() {
var contactForm = $('.contact-form');
if( contactForm.length < 1 ){ return true; }
contactForm.each( function(){
var el = $(this),
elResult = el.find('.contact-form-result');
el.find('form').validate({
submitHandler: function(form) {
elResult.fadeOut( 500 );
$(form).ajaxSubmit({
target: elResult,
dataType: 'json',
success: function( data ) {
elResult.html( data.message ).fadeIn( 500 );
if( data.alert != 'error' ) {
$(form).clearForm();
setTimeout(function(){
elResult.fadeOut( 500 );
}, 5000);
};
}
});
}
});
});
}
There might be a syntax error in your below code
if( $sendEmail == true ):
echo '{ "alert": "success", "message": "' . $message_success . '" }';
<b>else</b>
echo '{ "alert": "error", "message": "Email could not be sent due to some Unexpected Error. Please Try Again later. Reason:' . $mail->ErrorInfo . '" }';
endif;
Correct syntax of if else statement is
if( $sendEmail == true ):
else :
endif;
Please fix it in your code, and then try.
I'm trying to implement Google Invisible Recaptcha on a website online after the domain registration on google recaptcha site, I followed the documentation, but not works. When send the form, show the alert error:
Cannot contact reCAPTCHA. Check your connection and try again.
This is my code (only the interesting points), HTML/JS:
<script src='https://www.google.com/recaptcha/api.js?
onload=onloadCallback&render=explicit&hl=it' async defer></script>
</head>
<body>
<form method="post" action="contact.php" name="contactform" id="contactform">
<fieldset>
<input name="email" type="text" id="email" required/>
<input type="submit" class="submit" id="submit" value="Contact!" />
</fieldset>
</form>
<script type="text/javascript">
var onSubmit = function(token) {
// ajax call
};
var onloadCallback = function() {
grecaptcha.render('submit', {
'sitekey' : 'PUBLIC_KEY',
'callback' : onSubmit
});
};
</script>
and the contact.php file:
class Captcha
{
private $key = 'PRIVATE_KEY';
public $goo;
public function verify()
{
$postData = http_build_query(
array(
'secret' => $this->key,
'response' => $this->goo,
'remoteip' => $_SERVER['REMOTE_ADDR']
)
);
$options = array('http' =>
array(
'method' => 'POST',
'header' => 'Content-type: application/x-www-form-urlencoded',
'content' => $postData
)
);
$context = stream_context_create($options);
$response = file_get_contents('https://www.google.com/recaptcha/api/siteverify', false, $context);
return json_decode($response);
}
}
$captcha = new Captcha();
$captcha->goo = $_POST['g-recaptcha-response'];
$response = $captcha->verify();
if (!$response->success) {
// not works
}
else {
// works
}
I don't understand what is incorrect.
Thanks for help!
I want to check to see if an email already exists in a table or not.
I am using bootstrap formValidator library, with remote method,
but its not making any proper result.
It always shows the same message, whether its wrong or right, dont know whats wrong.
remote.php
<?php
include("dbcontroller");
$dbhandle=new DBcontroller();
header('Content-type: application/json');
include("connect.php");
$sql="select * from members";
$temp=array();
$result=$db_handle->runQuery($sql);
foreach($result as $row)
{
$temp[]=$row['email'];
}
$valid = true;
if (isset($_POST['email'])) {
$email = $_POST['email'][0];
foreach ($temp as $k => $v) {
if ($email == $v) {
$valid = false;
break;
}
}
}
echo json_encode(array(
'valid' => $valid,
));
?>
Form.php
<div class="form-group">
<label class="col-lg-2 control-label">Email</label>
<div class="col-lg-8">
<input type="text" placeholder="Email" id="e_mail" class="form-control" name="email[]" autocomplete="off"/>
</div>
</div>
Javascript file
'emaill[]': {
validators: {
notEmpty: {
message: 'The email address is required and can\'t be empty'
},
emailAddress: {
message: 'The input is not a valid email address'
},
remote: {
message: 'The email is already exist. you are already a registered user. please try to login?',
url: 'remote.php',
data:{
type:'email'
},
type: 'POST',
delay: 2000
}
}
}
Why don't you do the check in your SQL query?
$sql = "SELECT email FROM members WHERE email = '".$_POST['email']."'";
Now you only have to check if it returns more than 0 results:
$valid = false;
$result=$db_handle->runQuery($sql);
if(sizeOf($results) > 0) {
$valid = true;
}
Although you probably should escape the $_POST the avoid SQL injection ;-)