Is the submit button the only way to execute a php file? - php

Suppose you wished to create a HTML/php script which produced a webpage containing 2 buttons which, when clicked, told you which button had been clicked. The only way of doing this using php that I know of, is to create the index file
<? include('buttons.php'); ?>
<? include('clicked.php'); ?>
Where buttons.php is saved in the same directory and contains
<form method="post">
<input type="submit" name="button1" value="button1">
<input type="submit" name="button2" value="button2">
</form>
And the php script clicked.php contains
<?php
if($_POST['button1']){
echo "You have clicked button1";
}
elseif($_POST['button2']){
echo "You have clicked button2";
}
?>
This method works, but I suspect that it's not the best way of using php to get this result.
Is there a better way of doing this?

This is a server-side solution to executing PHP file however, you can approach this using client-side code and a generic handler for real-time executing and page-loading.
jQuery is free, world-wide used framework for JavaScript extensions and is easy to use.
$("#btn-one").click(function() {
$.get("clicked.php", { button: 1})
.done(function (data) {
body.innerHTML = data;
});
});
Your PHP (clicked.php) would look like this:
if(isset($_GET['button'])):
switch($_GET['button'])
{
case 1:
echo "You pressed button 1";
break;
case 2:
echo "You pressed button 2";
break;
default:
break;
}
endif;
And finally, your HTML would look like this!
<button type="button" id="btn-one">Button 1</button>

You could create your own wrapper
class Input
{
public static function fetch($key, $rules=[])
{
// ctype_alnum is used to check if the $key is alphanumeric
if (ctype_alnum($key) && isset($_POST[$key])) {
return $_POST[$key];
}
return false; // or ''
}
}
// practical use
// If string
$option = (string) Input::fetch('option');
Change the name to button[]
Then use the switch function.
you could use the rules argument to add validation rules and check for expected response types.

Related

How to access name and value pair of <button type="submit"> with php using Fetch API?

I need the name and value of a button (Not an input type = submit) when a form is submitted with the button of type submit.
I know everyone always asks why, even though the "why" is not a part of the answer to the question so I will answer the why to save time. I want a form to direct a person to choose to login, register or submit email verification. So having buttons that I can set the label for, with each have a unique value for a given name would solve this need but the name and values are not included in the POST with the rest of the input data when BUTTON type = submit is used.
Given the information in HTML5 Spec as shown on this site https://www.htmlquick.com/reference/tags/button-submit.html it seems like it's supposed to work. But short of adding javascript to manually add the key value pair to the post on click it doesn't seem to work.
Now, I want to ask why? If only inputs can be added to the data list then why isn't there an option to change the label of the submit inputs?
*EDIT
So far everyone agrees that what I've done should work, so lets get to the specific case and see if we can find where the problem is then.
Using this form:
<form data-targetblock="accountBlock" class="fetchForm" action="<?=ADDRESS ?>/MAINhubs/accountBlockHub.php" method="post">
<fieldset>
<legend>Member Login</legend>
<input type="hidden" name="formTarget1" value="test">
<button type="submit" name="formTarget" value="login">Log In</button>
<button type="submit" name="formTarget" value="register">Register</button>
<button type="submit" name="formTarget" value="verify">Verify Your Email</button>
</fieldset>
</form>
Sent with this:
function addFetch(event, targetBlock, domain)
{
event.preventDefault();
const form = new FormData(event.target);
const request = new Request(event.target.action,
{
method: event.target.method,
body: form,
mode: 'same-origin',
credentials: 'same-origin'
});
fetch(request)
.then(response => {
if(response.ok)
{
return response.text();
}
else
{
document.getElementById(targetBlock).innerHTML = 'ERROR! ERROR! There has been an ERROR!'
}
})
.then(function(text){document.getElementById(targetBlock).innerHTML = text;})
.catch(error => console.log('There was an error:', error))
}
Going to this:
<?php
session_start();
if ($_SERVER['REQUEST_METHOD'] === "POST")
{
var_dump($_POST);
}
?>
Gets me this when I click Log In:
formTarget1 = test
I'm gonna guess it has to do with this line in the Fetch:
const form = new FormData(event.target);
To answer the question of how the function is called, this JS is run to add the function to all applicable forms:
function fetchFormCallback(mutations)
{
mutations.forEach(function(mutation)
{
for (const thisForm of Array.from(document.getElementsByClassName('fetchForm')))
{
addFormListener(thisForm, thisForm.dataset.targetblock)
}
});
}
function generalCallback(mutations)
{
mutations.forEach(function(mutation)
{
// Take alertBlocks and move them to bottom of ID outerFrame because of IOS bug
if (newAlertBlock = document.getElementById('alertMessageBlock'))
{
if (newAlertBlock.dataset.relocated !== 'true')
{
var destinationBlock = document.getElementById('outerFrame');
destinationBlock.appendChild(newAlertBlock);
newAlertBlock.dataset.relocated = 'true';
}
}
// Get getElementsByClassName closeButton
for (var closeButton of Array.from(document.getElementsByClassName('closeButton')))
{
if (closeButton.dataset.closeButton !== 'true')
{
closeButton.dataset.closeButton = 'true';
closeButton.addEventListener('click', function(){this.parentNode.parentNode.removeChild(this.parentNode);});
}
}
// Potentially auto close based on a closeButton class of AUTO
});
}
document.addEventListener("DOMContentLoaded", function()
{
var config = {childList: true};
for (const thisForm of Array.from(document.getElementsByClassName('fetchForm')))
{ // setup all fetchforms
addFormListener(thisForm, thisForm.dataset.targetblock);
var thisTargetBlock = document.getElementById(thisForm.dataset.targetblock);
// if notset dataset.mutationobserver OR
if (thisTargetBlock.dataset.mutationobserver !== 'true')
{
thisTargetBlock.dataset.mutationobserver = 'true';
var observer = new MutationObserver(fetchFormCallback);
observer.observe(thisTargetBlock, config);
}
}
config = {childList: true, subtree: true};
var generalObserver = new MutationObserver(generalCallback);
generalObserver.observe(document, config);
});
function addFormListener(form, targetBlock)
{ // first check if element has attribute set for eventListeners
if (form.dataset.submitlistener !== 'true')
{
form.dataset.submitlistener = 'true';
form.addEventListener('submit', function()
{
addFetch(event, targetBlock);
});
}
}
EDIT:
We've confirmed that the issue here is that FormData is for some reason not supposed to include the submit value. Why a value should be excluded just because it may not be present/needed in the use case is beyond me. I do have a reason why it should be included and have documented it above. I developed this structure to be as universally applicable as possible without the addition of code for special case uses.
So now my evolving question has become this:
How; using the above functions, can I get the value of the clicked submit button, and include that name value pair in the FormData without changing the fundamental structure of these functions that otherwise do exactly what I want them to do in every other case.
This discussion illustrates that it's possible but has been reworked based on the spec to no longer do exactly what I'm trying to do:
FormData() object does not add submit-type inputs from form, while on Firefox
If I can't access the name and value of the button at the point of submition, then I might as well make another eventlistener to all BUTTON elements in forms that adds a hidden input with it's values on click... Before I go and do that, I can already see hurdles like the event.preventDefault(); line in the addFetch function might prevent the on click from happening? I guess it's back to trial and error unless someone has a better thought.
In your PHP:
$_POST['formTarget'];
Will have the value of the submit button. Either login, register, etc.
However I would not use a form for this, there is no need. I would just simply use links and style them as buttons if you wanted them to look like a button.
Edit: Based on your additions to the post. I offer an alternative way to accomplish this using data attributes.
HTML:
<fieldset>
<legend>Member Login</legend>
<button id="loginButton" data-url="getForm.php" data-target-block="#showForm" data-form-type="login">Log In</button>
<button id="registerButton" data-url="getForm.php" data-target-block="#showForm" data-form-type="register">Register</button>
<button id="verifyButton" data-url="getForm.php" data-target-block="#showForm" data-form-type="verify">Verify Your Email</button>
</fieldset>
<div id="showForm"></div>
<script>
document.querySelector("#loginButton").addEventListener("click", addFetch);
document.querySelector("#registerButton").addEventListener("click", addFetch);
document.querySelector("#verifyButton").addEventListener("click", addFetch);
function addFetch() {
const data = new FormData;
const targetBlock = this.dataset.targetBlock;
for(element in this.dataset) {
data.append(element, this.dataset[element]);
}
const request = new Request(this.dataset.url,
{
method: "POST",
body: data,
mode: 'same-origin',
credentials: 'same-origin',
});
fetch(request).then(response => {
if(response.ok) {
return response.text();
} else {
document.querySelector(targetBlock).innerHTML = 'ERROR! ERROR! There has been an ERROR!'
}
}).then(function(text){document.querySelector(targetBlock).innerHTML = text;})
.catch(error => console.log('There was an error:', error))
}
</script>
PHP:
<?php
if ($_SERVER['REQUEST_METHOD'] === "POST") {
switch($_POST['formType']) {
case 'verify':
echo "verify Form";
break;
case 'register':
echo "Register Form";
break;
case 'login':
echo "Login Form";
break;
default:
echo "Not valid";
break;
}
}

my external php doesn't understand input's name attribute value which is declared in ReactJS's render()

I am trying to make a ReactJS application which needs to communicate to PHP.
I could to use nodeJS but I chose PHP because I learned it some years ago and don't want to forget it.
So, what should happen in my app:
When user submits submit button(which is also rendered in render() ),instead of redirecting to php file, app will send ajax request to the external php file. PHP file should get input's value.
but php shows such warnings in console when I remove if(isset()) from the file.
Notice: Undefined index: search in C:\xampp\htdocs\ReactStudy\travelReduxApp\public\server\itemList.php on line 13
These are my codes
index.js
import ajaxRequest from './ajax';
console.log(store);
setTimeout(function(){
document.getElementById('AppName').classList.add('visible');
},300);
class App extends React.Component{
submitForm = (e)=>{
e.preventDefault();
//console.log(this.refs.search.value);
const value= this.refs.search.value;
ajaxRequest(e,value);
}
render(){
return(
<div>
<section id="Search">
<form id="Search" data-object="form" method="GET" onSubmit={this.submitForm}>
<input ref={'search'} placeholder="search country, attraction names" type="text" name="search"/>
<button type="submit">SEARCH</button>
</form>
</section>
<ItemList/>
</div>
)
}
}
ReactDOM.render(
<App/>,
document.getElementById('App')
)
ajax.js
export default function ajaxRequest(e,value){
let xhr = new XMLHttpRequest();
switch(e.type){
case 'submit':
xhr.open('get','//localhost:80/ReactStudy/travelReduxApp/public/server/search.php?'+value,true);
xhr.onreadystatechange = function(data){
switch(xhr.status){
case 200:
const text = xhr.responseText;
console.log(text);
}
}
}
xhr.send();
}
search.php
<?php
header('Access-Control-Allow-Origin:* ');
/*shows warning without isset*/
/*$form = $_GET["search"];
echo $form;*/
/*with isset shows not found*/
if(isset($_GET["search"])){
$form = $_GET["search"];
echo $form;
}else{
echo "not found";
}
?>
could please someone find or teach me why my php can't find input tag with name attribute's value search?
the input tag is already rendered into the document when php is called. What am I missing?
I am using webpack and bundle.js is included on the bottom of the tag.
edited my code. I am using GET in my code and I don't know why I wrote POST here. So, forget it. I am using $_GET in my php code. Pardon me.
The only thing your Ajax is sending is this.refs.search.value - not the name "search" / not url encoded / not multi-part encoded. Indeed, you seem to have invented your own encoding system.
Try:
xhr.open('get','//localhost:80/ReactStudy/travelReduxApp/public/server/search.php?search=' + value,true);
in Ajax.js
<?php
header('Access-Control-Allow-Origin:* ');
/*shows warning without isset*/
/*$form = $_GET["search"];
echo $form;*/
/*with isset shows not found*/
if(isset($_POST["search"])){
$form = $_GET["search"];
echo $form;
}else{
echo "not found";`ghd`
}
?>

ajax load different php pages

How can I call functions on different pages?
For example if I click on the start button, it will run the code necessary to start the tomcat server.
Here is the code for the main page:
<input name="submit" class= "green" id ="start" type="submit" value=" Start ">
<input name="submit" id = "stop" class='red' type="submit" value=" Stop ">
Here's the second page that executes the program.
function (tomcatstart){
$ssh->exec('service tomcat start');}
There are a couple of different approaches you can take to accomplish this sort of task. Here's how I would do it:
Firstly, I'd replace the <input> tags with <button> tags. This is more personal preference than a real change in functionality, but since you're sending the request via AJAX, you don't need a form or inputs.
Secondly, I'd create the JS functions to make the AJAX request, something like this:
function start() {
$.post('urlToStart.php', {
data : 'Some data'
}, function(returnedData) {
//Optionally do something with the returned data, like alert 'Success' or 'Failed'
alert(returnedData);
});
}
Finally, you need a php page to handle the request. You can either have one page that handles both the start and stop requests, or you can have different pages for each one.
Example urlToStart.php:
<?php
$data = $_POST['data'];
if($data !== null) {
tomcatstart();
echo "Success";
}
else {
echo "Failed: " . print_r(error_get_last()); //Get the error message so you know what happened
}
function tomcatstart(){
$ssh->exec('service tomcat start');
}
And that should set you on your way
What you can do is
Add data-task attribute, so we can write single ajax to for
all
Add an additional class, trigger-ajax
change inputs to button or change the input type to button
make a jquery call on click event, using class we added
jQuery(".trigger-ajax").on('click', function(){
var _context = jQuery(this);
jQuery.ajax({
url: 'ajaxrequest.php',
type: "post",
data:{
task: _context.attr('data-task')
},
success:function(response){
console.log(response)
}
})
});
handle it in php
if(!empty($_POST['task'])){
switch(trim(strtotlower($_POST['task']))){
case "start-tomcat":
$ssh->exec('service tomcat start');
break;
case "stop-tomcat":
$ssh->exec('service tomcat stop');
break;
}
}

Make a jQuery $.post() to a PHP Controller, and then in the middle of it back to View, and then use $.get() to continue with the Controller

I am dealing with a View and Controller for a webpage, and I am trying to figure out how this would work:
Controller will initially define variables used in view upon page-load.
Once a user submits a form, it does an onclick jQuery function, which posts back to the controller.
The controller returns back to the View true or false, depending on whether the vote was successfully inserted into the database.
The View's jquery function continues, determining what to do next: if it was successful, perform another jQuery function.
the next jQuery function performs a $.get back to the controller, which determines the relevant variables to be used in the view.
Right now, mine works in terms of submitting the vote. However, I never see the alert pop-up when i'm running it, which leads me to worry that the set-up I have isn't working the way it should be.
Here is code from my PHP website controller:
if(!isset($_POST['poll'])) //UPON PAGE LOAD
{
//define relevant variables to be put into the view
}
if(isset($_POST['poll'])) //UPON jQuery $.Post() back to controller
{
if($_POST['poll']=='done')
$vote = 2;
if($_POST['poll']=='no')
$vote = 1;
$id = $_POST['id'];
$result = vote($user_id, $id, $vote); //inserts vote into Database
if( !$res )
echo json_encode(array('success'=>true, 'text'=>'success'));
else
echo json_encode(array('success'=>false, 'text'=>'fail'));
//I want ^this json data to be sent back to the jQuery of my view
}
if(isset($_GET['newListing']))
{
//code that would redifine relevant variables to be put into view
}
if(isset($_GET['newListing']) || !isset($_POST['poll']))
{
//code that does something--both upon page load and when needing to retrieve
//and define variables to put into view.
}
include('view.php');
Here is code from my HTML/jQuery website view:
<html>
<body>
<form name='poll' id='poll' >
<INPUT TYPE="radio" name='poll' value='done'checked/>Done it.<br/>
<INPUT TYPE="radio" name='poll' value='no'/>No.</br>
<button id='submit-vote' onclick="postVote();">Submit</button>
<INPUT TYPE='hidden' name='id' value='<?php echo $id; ?>'/>
</form>
</body>
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript">
function loadListing(){
$.get('controller.php?newListing=yes',function(data){
if(data.response == 'success'){
//something}
else{
return false;}
});
}
function postVote(){
$.post('controller.php', { poll: $('input:radio[name=poll]:checked').val(), id: $('input:hidden[name=id]').val()} , function(data){
if(data.success){
alert('data.text');
loadListing();
return true;}
else{
alert(data.text);
return false;}
},
"json");
}
</script>
</html>
Any help/suggestions appreciated!
EDIT:
From my View code:
the HTML:
<fieldset id='poll'>
<INPUT TYPE="radio" name='poll' value='yes' checked/>Yes!<br/>
<INPUT TYPE="radio" name='poll' value='done'/>Done it.<br/>
<INPUT TYPE="radio" name='poll' value='no'/>No.</br>
<button id='submit-vote'>Submit</button>
<INPUT TYPE='hidden' name='id' value='<?php echo $id; ?>'/>
</fieldset>
the jquery:
jQuery(function($){
$("#submit-vote").click(
function(){
alert("HELLO");
$.post('controller.php', { poll: $('input:radio[name=poll]:checked').val(), id: $('input:hidden[name=id]').val()} ,
function(data)
{
alert("THIS FUNCTION WORKS");
}, "json");
}
);
});
The controller is pretty much the same. When I click on the submit button now, the alert("HELLO"); is executed, and according to the Firefox's Firebug the $.post() does take place. However, the alert("THIS FUNCTION WORKS"); does NOT get executed.
I need help figuring out why that may be....
Thanks!
The problem is that json_encode creates a string. In your Javascript, however, you're trying to access it as if it's an object (data.success). You'd need to first use window.JSON.parse() to turn it into an object:
var dataObj = window.JSON.parse(data);
After doing that, you should be able to access dataObj.success.
To be honest though, I'm not sure why you're making it that complicated. Why not just return a simple string, such as "success" or "failure"? Then you don't need to encode the object in php or decode it in JavaScript. You'd simply do:
PHP
if( !$res )
echo 'success';
else
echo 'failure';
JavaScript
if(data === 'success'){
//do your stuff
}else{
//do other stuff
}
Edit in response to OP's first comment on this answer
Your JavaScript will regain control once the PHP script ends. In the code you posted, you include a view.php file at the end of the PHP script. I don't know what's inside view.php, and it's quite possible that including this file will cause your JS alert() to still not fire even if you make the changes I described above. That's because if there is any output (i.e. echo, print, etc.) that runs in the view.php file, that will get appended to the string created by json_encode. The result will be a string that can not be parsed by window.JSON.parse().
If you want the script to end after echoing "success" or "failure" (or your json_encoded version), simply put return; after the echo statement:
if( !$res ){
echo 'success';
else
echo 'failure';
}
return;
the include('view.php'); should ONLY to be put into the if(!isset($_POST['poll'])) //UPON PAGE LOADcode.

Check if user input matches array of values. PHP

I have one field (for zip code), if user enters zip code that matches one in my array and click "go" - they are redirected to the next step, if not - display "out of our service area" message. Form and php script are on the same page. How Do I do redirection inside That's what I have so far.
<form>
<input type="text" id="zipcode" name="zipcode" />
<input type="submit" id="submit" value="GO" />
</form>
<?php
$allowedzips = array("10051", "10061", "10071", "10081");
$input = echo $_POST["zipcode"];
$input = str_split($input);
$message = "Out of our service area";
foreach($input as $zip) {
if (in_array($zip, $allowedzips)) {
$message //redirect goes here
break;
}
}
echo $message;
?>
A PHP redirect is quite easy to do:
header('Location: www.example.com');
exit;
Make sure to exit;, as that will stop the script from executing any further.
I think it would be better to use javascript instead of PHP for how you are looking to do this.
What I would do is add this into the head of your html
<script type="test/javascript">
function checkZipCode(zip) {
var myZipCodes=new Array("10051", "10061", "10071", "10081");
for(i=0;i<myZipCodes.length;i++) {
if (zip = myZipCodes[i]) {
form.submit;
}
else
window.location = "redirectpage";
}
}
</script>
And then on submit call and pass the zip code to checkZipCode.
I would do this in PHP to ensure that you're not tricked on the client side
Use the in_array() function to determine if the element you're looking for is within you list of valid zip codes, and redirect accordingly.

Categories