How to send GRecaptcha V3 to WP Rest API using Nuxt js - php

i want to send the Google Recaptcha V3 to WP Rest API using Contact Form 7.
This is what i have done so far:
I just use WP as BackEnd API provider, my frontend is in Nuxt app - full static generated code
Wordpress
Install Contact Form 7 plugin
Configured the Google Recaptcha V3 Site Key and Private Key
Create a specific form form my Nuxt App
Test the form in a Wordpress test page and it works fine
Nuxt
Install #nuxtjs/recaptcha
Insert in .env the site key and api URL of contact form
in nuxt.config.js
publicRuntimeConfig: {
contactFormApi: process.env.CONTACT_FORM_API,
// other staff
},
modules: [
['#nuxtjs/recaptcha', {
hideBadge: true
,siteKey: process.env.RECAPTCHA_SITE_KEY
,version: 3
}],
// other staff
],
in layout/default.vue:
async mounted() {
try {
await this.$recaptcha.init()
} catch (e) {
console.log(e);
}
},
beforeDestroy () {
this.$recaptcha.destroy();
// other staff
}
contact form component:
<template>
<form role="form">
<v-text-field v-model="email" name="email" :label="$t('form.yourEmail')" autocomplete="email" :placeholder="$t('form.yourEmailHint')" clearable
></v-text-field>
<v-textarea v-model="message" name="message" :label="$t('form.yourMessage')" rows="3" value="" :hint="$t('form.yourMessageHint')" clearable
></v-textarea>
<v-checkbox v-model="acceptPrivacy" :label="$t('form.acceptPrivacyTerms')"></v-checkbox>
<v-btn #click="submit">{{ $t('btns.send') }}</v-btn>
</form>
</template>
<script>
export default {
data: () => ({
email: '',
message: '',
acceptPrivacy: false,
}),
methods: {
async submit() {
if (!this.acceptPrivacy || this.email == '' || this.message == '') {
return false;
}
try {
const token = await this.$recaptcha.execute('login');
console.log('ReCaptcha token:', token);
const emailBody = {
"_wpcf7_recaptcha_response" : token,
"wpcf7_recaptcha_response" : token,
"recaptcha_response" : token,
"recaptcha" : token,
"token" : token,
"email": this.email,
"message" : this.message,
"privacy_terms" : this.acceptPrivacy? 1 : 0
};
const form = new FormData();
for (const field in emailBody) {
form.append(field, emailBody[field]);
};
const headers = {
'Content-Type': 'multipart/form-data',
};
const data = await this.$axios.$post(
this.$config.contactFormApi,
form,
{ headers: headers }
);
if (data == null || data == undefined || data.status !== 'spam') {
console.log('Email has NOT been sent');
console.log(data);
return;
}
console.log('Email has been sent');
console.log(data);
} catch (error) {
console.log('Login error:', error)
}
}
}
}
</script>
I try to send the email from my localhost:3000, the other API of WP in order to get pages, post, customPostTypes work as expected.
After every request to WPCF7 i get this response:
{
"into": "#",
"status": "spam",
"message": "There was an error trying to send your message. Please try again later.",
"posted_data_hash": ""
}
As you can see in the request i don't know the proper way to send the gRecaptcha token that i correctly get from google service response:
"_wpcf7_recaptcha_response" : token,
"wpcf7_recaptcha_response" : token,
"recaptcha_response" : token,
"recaptcha" : token,
"token" : token,
Can you help me for this issue?
Thanks in advance

Related

Getting 409 error when calling php from my React application

I am trying to call a simple php file from my React application which will send an email with the details from a contact form. For some reason when the React code executes the fetch of the PHP file, it returns a 409. However, if I manually post the URL into another tab it works as expected, and subsequent calls from my React application then work as expected!
This is my React code:
var url = '/backend/sendmail.php?subject=New Website Enquiry&to=info#site.co.uk&msg=' + msg
console.log(url)
console.log('sending')
fetch(url,
{
'headers': {
'Accept': 'text/html',
'Content-Type': 'text/html'
},
'method': 'GET',
})
.then(
(result) => {
console.log(result.status)
if (result.status === 200) {
console.log('success')
this.togglePop();
this.setState({
name: "",
email: "",
phone: "",
message: "",
terms: false,
})
} else {
console.log('failed')
this.setState({ openError: true })
}
},
(error) => {
console.log('ERROR')
console.log(error)
this.setState({ openError: true })
}
)
And this is my PHP file:
<?php
//header("Access-Control-Allow-Origin: *");
header('Content-Type: text/html');
// error handler function
function customError($errno, $errstr) {
error_log($errstr);
http_response_code(500);
}
// set error handler
set_error_handler("customError");
http_response_code(200);
// send email
mail($_GET["to"],$_GET["subject"],$_GET["msg"],"From: donot.reply#site.co.uk","-f donot.reply#site.co.uk");
error_log($_GET["subject"].":\n".$_GET["msg"], 0);
echo 'OK';
?>
I have spent several days trying to figure out why this is happening. My htaccess file seems OK as once I have made one succesful call to the PHP file it works after that!
It's not a CORS issue as the file is on the same domain.
Anyone got any ideas?
You are sending the wrong request to the server, and that's why you get a 409 error. You should encode the URL params before sending a request
const url = '/backend/sendmail.php?subject=New Website Enquiry&to=info#site.co.uk&msg=' + msg;
const encoded = encodeURI(url);
console.log(encoded)
// expected correct URI: "/backend/sendmail.php?subject=New%20Website%20Enquiry&to=info#site.co.uk&msg="
You can read more about it here

Angular php-jwt token cleared on page navigation

I'm having issues with my application, I used php-jwt JSON Web Token Authentication in my angular 9 apps and the token works fine when I'm not redirecting to successful page after login. when redirecting to the dashboard after login the token is set and immediately remove from localStorage. How can I allow token even after redirection to new page? Any help will be highly appreciated.
My auth.service.ts file
// Sign-in
signIn(user: Usermodule) {
return this.http
.post<any>(`${this.endpoint}/signin.php`, user)
.subscribe((res: any) => {
localStorage.setItem('ACCESS_TOKEN', res.jwt);
this.getUserProfile(res.id).subscribe((res) => {
this.router.navigate(['app/dashboard']);
});
});
}
// User profile
getUserProfile(id): Observable<any> {
let api = `${this.endpoint}/user_profile.php`;
return this.http.get(api, { headers: this.headers }).pipe(
map((res: Response) => {
return res || {};
}),
catchError(this.handleError)
);
}
auth.interceptors.ts file
export class AuthInterceptor implements HttpInterceptor {
constructor(private authService: AuthService) {}
intercept(request: HttpRequest<any>, next: HttpHandler) {
const access_Token = this.authService.getToken();
request = request.clone({
setHeaders: {
Authorization: 'Bearer ' + access_Token,
},
});
return next.handle(request);
}
}
app.module.ts file
JwtModule.forRoot({
config: {
tokenGetter: () => {
return localStorage.getItem('ACCESS_TOKEN');
}
// whitelistedDomains: ['localhost'],
// blacklistedRoutes: ['localhost/auth/login']
}
})
],
providers: [
AuthService,
{ provide: HTTP_INTERCEPTORS, useClass: AuthInterceptor, multi:true}
],
bootstrap: [AppComponent]
Once I comment out //this.router.navigate(['app/dashboard']); the token stays in localstorage without been killed and I can even access restricted area when I type the address manually.

ListenWhisper doesn't receive an client event (Larave-echo & Vue.jsl)

I'm working in a realtime chat website using Laravel, laravel-echo,laravel-echo-server, and redis. My chat is able to receive and send messages, but I want to add a message when a user start to typing ('User x is typing...'). But the client event is typing triggered
I have diferent vue.js components in this chat,
ChatApp.vue <- Main component
...
mounted() {
Echo.private(`message.${this.user.id}`)
.listenForWhisper('.typing', (e) => { // This is listening for client event named typing
console.log(e);
setTimeout(function() {
console.log('works');
}, 900);
})
Echo.private(`messages.${this.user.id}`)
.listen('.NewMessage', (e) => { //This is listening for a backend event named New Message
this.handleIncoming(e.message);
this.playSoundNotification();
});
axios.get('/user/contacts')
.then((response) => {
console.log(response.data);
this.contacts = response.data;
});
},
....
MessageComposer.vue component
<template>
<div class="composer">
<span #typing="typing_handler" v-show="typing" class="help-block" style="font-style: italic;">
TĂș amigo esta escribiendo...
</span>
<textarea v-model="message" #keydown="isTyping" #keydown.enter="send" placeholder="Message..."></textarea>
</div>
</template>
<script >
export default {
data(){
return {
message: '',
typing:false,
};
},
methods: {
send(e){
e.preventDefault();
if(this.message == ''){
return;
}
this.$emit('send', this.message);
this.message = '';
},
typing_handler(trigger){
this.typing = trigger;
},
isTyping() {
let self_user_id = parseInt($('#self_user_id').val());
var channel = Echo.private(`message.${self_user_id}`); //Client auth
setTimeout(function() {
channel.whisper('typing', {
typing: true
});
}, 300);
},
}
}
</script>
I don't get any error in my laravel-echo-server so I don't know what the problem is?
What I'm doing wrong?
Sometimes you may wish to broadcast an event to other connected clients without hitting your Laravel application at all. This can be particularly useful for things like "typing" notifications, where you want to alert users of your application that another user is typing a message on a given screen.
To broadcast client events, you may use Echo's whisper method:
Echo.private('chat')
.whisper('typing', {
name: this.user.name
});

PAYPAL PAYMENT Client Side REST SCRIPT

I have integerated PayPal Client Side REST to my website. I have used the sample code provided from link below:
https://developer.paypal.com/demo/checkout/#/pattern/client
This code below worked over a month, however today it shows below error
Error: Request to post https://www.sandbox.paypal.com/v1/payments/payment
failed with 400 error
{
"name": "MALFORMED_REQUEST",
"message": "Incoming JSON request does not map to API request",
"information_link": "https://developer.paypal.com/webapps/developer/docs/api/#MALFORMED_REQUEST",
"debug_id": "a26904ff6211a"
}
my code follows:
<div id="paypal-button-container" class="info"></div><script src="https://www.paypalobjects.com/api/checkout.js"></script>
<script>
// Render the PayPal button
paypal.Button.render({
// Set your environment
env: 'production', // sandbox | production
// PayPal Client IDs - replace with your own
// Create a PayPal app: https://developer.paypal.com/developer/applications/create
client: {
sandbox: '<?=SANDBOXPAYPAL?>',
production: '<?=PAYPAL_TOKEN?>'
},
// Set to 'Pay Now'
commit: true,
// Wait for the PayPal button to be clicked
payment: function() {
$('#card').attr('checked',true);
// Make a client-side call to the REST api to create the payment
return paypal.rest.payment.create(this.props.env, this.props.client, {
transactions: [
{
amount: { total: '12.99', currency: 'GBP' }
}
]
});
},
// Wait for the payment to be authorized by the customer
onAuthorize: function(data, actions) {
jQuery.ajax({
type: "POST",
url: "ipn.php",
data: data,
success: function(data){
}
});
return actions.payment.execute().then(function() {
document.querySelector('#paypal-button-container').innerText = 'Payment Complete!';
});
}
}, '#paypal-button-container');
</script>
Your code does not quite match the example, but I am also using the client-sdie API from a Laravel Shoping Cart I am building, I use AJAX to push the payment data back to my system this way:
onAuthorize:function(data, actions)
{
console.log("onAuthorize()");
console.log("Dumping DATA");
console.log(data);
console.log("Dumping ACTIONS");
console.log(actions);
return actions.payment.execute().then(function(payment)
{
console.log("payment.execute called");
document.querySelector('#paypal-button-container').innerText = 'Payment Complete!';
console.log("Dumping payment:");
console.log("CART: "+payment['cart']);
console.log(payment);
var values = encodeURIComponent(JSON.stringify(payment));
$.ajaxSetup({headers:{'X-CSRF-TOKEN':'{{ $token }}' } } );
ajaxRequest= $.ajax({ url: "/ajax/payment", type: "post",data:values });
ajaxRequest.done(function(response, textStatus, jqXHR)
{
var result = $.parseJSON(response);
console.log(result);
});
});
},
/ajax/payment is my capture script i'm developing at present but it does record all the data from the purchase.. hope it helps.

Facebook iframe Graph App Requests

function sendRequest(c_id,page_id,user,g_id) {
// alert(c_id);
// alert(page_id);
FB.ui({
method: 'apprequests',
message: 'Custom messae!',
title: 'Enter in this contest!',
data: +id+','+puid+','+n_id,
},
function (response) {
if (response && response.request_ids) {
var requests = response.request_ids.join(',');
window.location.href = "mysiteurlhere";
} else {
alert('canceled');
}
});
return false;
}
The above code works for multiuser but not single user even after adding TO field,
I changed the code and used to field
method: 'apprequests',
to: sendto,
sendto has uid of user to whom i want to send the app request, I do get the invitation id but
$request_content = json_decode(file_get_contents("https://graph.facebook.com/$request_id?$app_token"), TRUE);
// returns false when i access the url
Am i missing something Multi User is working as smooth as it can be.

Categories