This is for WordPress, just to make that clear. I’m asking here since I suspect that I need to provide a bounty on this question (worth 400).
I need to add AJAX to my form submit to avoid page reload / page refresh. I have tried several different versions and none of them are working.
The general idea here is to protect parts of a post whereof that part is code wrapped in <pre>
and <code>
tags.
These tags are from the prismjs
highlighter and looks like this:
<pre><code class="language-php">code here</code></pre>
These tags have four different classes;
- PHP
- HTML
- CSS
- JS
This is why the preg_replace
uses the ('/(<pre[^>]*>s*<code[^>]*>)
formatting as it needs to cover (handle) the class added.
Furthermore, a cookie is set so that once the user has provided a correct password, the password is remembered. The user should not have to re-enter the password each time they view a post with protected content.
I have an empty DIV acting as a placeholder for showing messages (success and error). The idea here is to show an error if the user submits an incorrect password. If the password match, show the content (code).
This is the code I am working on:
add_filter( 'the_content', 'wrap_code_in_shortcode' , 9 );
function wrap_code_in_shortcode( $content ) {
if ( ! in_category( 'premium' ) ) return $content;
$content = preg_replace('/(<pre[^>]*>s*<code[^>]*>)/',"[protected]$1", $content);
$content = preg_replace('/(</code>s*</pre>)/', "$1[/protected]", $content);
return $content;
}
add_shortcode( 'protected', 'protected_function' );
function protected_function($atts, $content=null){
$userpass = isset( $_REQUEST['password']) ? $_REQUEST['password'] : (isset($_COOKIE['userpass']) ? $_COOKIE['userpass'] : NULL );
if ( in_array( $userpass, array('testpw') ) ) {
$return_code = do_shortcode( $content );
} else {
$return_code = '<div style="margin-top:20px; font-size:15px">Submit password to view.</div>
<div id="errorPWdata"></div>
<form method="post" onsubmit="protectedFunction(this);">
<input required style="display: block; width: 69%; height: 50px; margin-right: 1%; float: left; border: 2px solid #333;" type="text" placeholder=" Password Here" name="password" id="userpass">
<input style="display: block; margin: 0px; width: 30%; height: 50px; background-color: #333; color: #fff;" id="protectedButton" type="submit" value="Submit">
</form>';
?>
<script>
function protectedFunction(form) {
$('#protectedButton').on( 'click', function(e) {
e.preventDefault();
$.ajax({
success: function(data) {
$("#errorPWdata").html(data);
},
error: function() {
alert("Password record error. Contact the administrator.");
}
});
document.cookie = "userpass=" + escape(form.userpass.value) + "; path=/";
}
}
</script>
<?php
}
return $return_code;
}
2
Answers
Please try with below code.
Shortcode handling part:
Ajax Request Handling Part:
Hope this code help you.
I learned to details your code snippet and notice mistakes.
Please, read everything firstly, then you could try.
Mistake 1
Shortcode has been defined with a wrong function name
Should be replaced with
Mistake 2
Script tag should be replaced by the enqueueing system to guarantee script sequences.
The snippet
Should be replaced with this one
An appropriate bio-shortcode-protected.js file should be created
path-to-your-theme/assets/js/bio-shortcode-protected.js (Content of the file in next mistake)
Mistake 3
By default WordPress loads jQuery as a global JavaScript object
jQuery
should works meanwhile$
probably won’t. The script should start withjQuery
wrapper to guarantee$
alias working.Provided Script has incorrect syntax. There should be a close
parentese symbol
)
Better to use submit handler instead of click handler. I simplified your handler by handling
submit
instead ofclick
. Clicking input button triggerssubmit
andclick
handler not required.Finally, the bio-shortcode-protected.js content should be
And appropriate little bit improved shortcode template should look like:
Mistake 4
If the form will be submitted what would heppend – is WordPress starts to build content of the page, firstly header, the content (the_content filter), then footer. And checking password inside shortcode not so good idea. This way sending unnecessary page chunks. The only thing need to fetch by AJAX is clean apropriate post content.
This is where ajax-endpoint comes into play. Endpoint should be created by placing the snippet to functions.php file:
And password validation function
Last words:
I don’t recommend set password in Cookie. It’s potential security breach.
Better to set Session password variable. But this way not much better.
There is a good answer why not to store password in Session and what to do instead.
Is it secure to store a password in a session?