Door
Frits van Leeuwen
op 20-04-2020 00:22
gewijzigd op 20-04-2020 00:36
8.069 views
Hallo allemaal,
Ik doe ergens iets niet goed. Ik heb geen idee wat.
De regel "alert("record_id = " + id); " in de onderstaande code geeft aan dat id is gevuld met bijvoorbeeld 36.
Maar als ik daarna verder ga met de code wordt de code niet naar menu_tabel_update.php overgebracht te worden.
Een submit button heeft geen submit event, een formulier heeft een submit event.
Een button heeft wel een click event, maar je wilt niet de button-click afvangen, maar een formulier-submit.
Dit kun/kon je heel simpel testen, simpelweg door te kijken, en visueel terug te koppelen, welke events "vuren":
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Click test</title>
<script
src="https://code.jquery.com/jquery-1.12.4.min.js"
integrity="sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ="
crossorigin="anonymous"></script>
</head>
<body>
<form id="testForm" action="" method="POST">
<button id="testButton" type="submit">submit</button>
</form>
<script type="text/javascript">
//<![CDATA[
$().ready(function() {
// vuurt niet - submit event bestaat niet voor (submit) buttons
$('#testButton').submit(function(e) {
e.preventDefault();
alert('button firing submit');
});
// vuurt wel - simpele klik
$('#testButton').click(function(e) {
// als je hier geen e.preventDefault() gebruikt gaat het submitten van het formulier door
// maar beter is dus om op de plek dat je een event wilt tegenhouden deze te stoppen
alert('button firing click, but not preventing other events from trickling through');
});
$('#testForm').submit(function(e) {
e.preventDefault(); // hier vangen we het daadwerkelijk submitten van het formulier af
alert('form firing submit, and preventing submit itself');
});
});
//]]>
</script>
</body>
</html>
Zet anders eens tijdelijk de historie aan in je netwerktab, dan zie je ook vorige pagerequests. Waarschijnlijk wordt de pagina waar je het formulier op hebt staan gewoon meerdere keren aangeroepen omdat je dus form submits gewoon doorlaat...
Zoveel stond ook al in mijn vorige reactie:
Thomas van den Heuvel op 26/04/2020 17:23:33
Ik zou dus in plaats van een functie eerder een submit event bij $('[color=#ff0000]#Add_Row[/color]').[color=#ff0000]submit[/color](...) verwachten, waarbij je dus het default gedrag van een formulier (verzending) voorkomt...
Hierbij is #Add_Row het id van het formulier, niet van een button.
En dan al die meldingen van je JavaScript over allemaal vage velden?
Dat levert wat mij betreft nogal wat bagger op. Dus dan is het toch misschien beter om terug te gaan naar de eerdere opzet waarbij je button-clicks afvangt (en daarmee de form submit).
Je geeft zelf al functioneel aan wat er moet gebeuren: je moet op een of andere manier de geklikte button (en daarmee dus de uit te voeren actie) identificeren. Dit is weer een apart vraagstuk, en kan -op legio manieren- in afzondering worden opgelost. En deze actie moet vervolgens op een of andere manier worden overgeheveld naar de AJAX-call.
Dit is in het algemeen hoe je (of in ieder geval, hoe ik) dingen in jQuery maar ook in PHP opbouw: deel het op in deelproblemen en tackle deze problemen stuk voor stuk. Maar hierbij moet je dus wel via een plan te werk gaan en ook weten hoe je data voor debugging/ontwikkeling boven water kunt halen. Anders ben je in wezen niets anders aan het doen dan trekken en duwen aan een of andere black box.
Het is (nogmaals) niet nodig om al die formulier-variabelen te kopiëren. Het enige wat je moet doen is op een of andere manier een referentie verkrijgen naar het formulier ( bijvoorbeeld var $form = $('#Add_Row'); ) binnen de AJAX-callback, en vervolgens kun je gewoon in één ruk alle data serialiseren ( 'data': $form.serialize(); ). Het verwerkende script moet verder maak uitzoeken welke informatie die hiervan kan gebruiken, dat is niet echt de taak noch de verantwoordelijkheid van het stukje JavaScript. Deze zet enkel alles op de lopende band om verder door het PHP-script verwerkt te worden.
Wederom een voorbeeld van een aanpak. Kost misschien wat moeite, maar dit kun je allemaal bij elkaar Googlen:
<?php
// https://www.phphulp.nl/php/forum/topic/met-ajax-variabele-naar-php-overbrengen/103477
if ($_SERVER['REQUEST_METHOD'] == 'POST') {
header('Content-Type: application/json; charset=UTF-8');
echo json_encode($_POST); // dump simpelweg $_POST als test om te zien wat je ontvangen hebt
exit;
}
?>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>AJAX test</title>
<script
src="https://code.jquery.com/jquery-1.12.4.min.js"
integrity="sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ="
crossorigin="anonymous"></script>
</head>
<body>
<form id="testForm" action="" method="POST">
field: <input type="text" name="field" value=""><br>
another: <input type="text" name="another" value=""><br>
<button class="js-action" data-action="one" type="submit">een</button>
<button class="js-action" data-action="two" type="submit">twee</button>
</form>
<script type="text/javascript">
//<![CDATA[
$().ready(function() {
// hang een event op aan alle buttons met class js-action binnen het formulier
$('#testForm button.js-action').click(function(e) {
e.preventDefault(); // hiermee wordt effectief de form submit afgevangen
var $theForm = $('#testForm'); // maak referentie naar formulier
var action = $(this).data('action'); // bepaal actie, deze zit in een data-XXX attribuut, waar XXX in dit geval 'action' is
var data = $theForm.serializeArray(); // serialiseer formulier als array
data.push({'name': 'action', 'value': action}); // voeg actie toe, zorg ervoor dat je geen bestaand veld overschrijft...
console.log('This is the data I am going to send:');
console.log(data); // controleer eventueel wat je gaat versturen
$.ajax({
'url': '<?php echo $_SERVER['SCRIPT_NAME']; ?>',
'method': 'POST',
'data': $.param(data), // maak een geserialiseerde string van dit array
'dataType': 'JSON', // return type of d
'success': function(d) {
// dump alles naar je console bij wijze van test
console.log('I got this data back from the processing script:');
console.log(d);
}
});
});
});
//]]>
</script>
</body>
</html>
Bij het eerste karakter dat ik in een veld in geef volgt deze melding:
0: Unable to get property 'isPersonal' of undefined or null reference
Autoformfill_ContentScript.js (1,168)
ALs ik de submit wil doen verschijnen deze meldingen:
0: Unable to get property 'SavePersonalAndPaymentData' of undefined or null reference
Autoformfill_ContentScript.js (1,20660)
Heeft dat uberhaupt met de vraagstelling te maken?
Daar komt nergens een script Autoformfill_ContentScript.js ter sprake, noch "isPersonal" noch "SavePersonalAndPaymentData" dus geen idee wat dat allemaal voor troep is?
Het stoort in ieder geval wat je probeert te doen enorm, dus als je meer JavaScript in dat ding hebt zitten zul je dit of compatibel moeten maken of moeten verwijderen.
< 1 minuut Googlen: Foutmeldingen komen van je Edge Password Manager Extension van Norton. Tijd om je virusscanner te updaten? Of gewoon de PME uit te zetten.
Die code hierboven, ik kan mij wel een paar leuke SQL-injecties voorstellen.
DELETE FROM users WHERE id = 1 OR 1=1? :/
Hoe kan ik een tabel een refresh geven anders een pagina reset zodra ik ajax z'n werk heb laten doen.
Je bedoelt met "tabel" waarschijnlijk hier de HTML-tabel?
Ok, je hebt nu weliswaar dus alle backend code geschreven (vatbaar voor verbetering, met name qua security), maar je hebt waarschijnlijk nog niet nagedacht over hoe je de visuele zaken regelt. Zo zou het bijvoorbeeld wel handig zijn dat je een soort routine had voor het (visueel) toevoegen of verwijderen van een tabelrij, of een routine voor het verversen van de volledig lijst.
Op het moment dat je met jQuery dit soort functionaliteit in elkaar gaat zetten dan wordt zo'n lijst met AJAX-aansturing een soort van levend ding met "gedrag", dit omdat het niet langer het traditionele request-response schaakspel is wat je van webpagina's gewend bent. Je zult dus dit gedrag op een of andere manier moeten vastleggen en handig moeten bundelen zodat je ook alle visuele dingen makkelijk kunt verwezenlijken.
Als je hier nu pas over begint na te denken dan zul je mogelijk code moeten omgooien om e.e.a. te stroomlijnen.
In het callback gedeelte van de ajax-aanroep ('success': function(data) { ... } ) zou je een status kunnen teruggeven die aangeeft of het INSERTen was gelukt, en zoja, de data kunnen retourneren om de nieuwe tabelrij in te voegen. Wat je ook zou kunnen doen is een refresh-call doen op de tabel, zodat alle informatie, wederom via AJAX, opnieuw wordt binnengetrokken en de lijst wordt ververst.
Oftewel, in het 'success'-deel kun je het verwerkende PHP-script een seintje terug laten geven (deze belt terug: callback) naar de jQuery/JavaScript op het moment dat de INSERT/andere databasebewerking is afgerond. In mijn voorbeeld hierboven gebeurt dat ook, PHP dumpt alles in JSON-formaat terug naar de success-functie.
Ik zou je ook zeker aanraden om jezelf ervan te overtuigen dat je ook snapt wat er allemaal op de achtergrond gebeurt tussen webbrowser en webserver, hiertoe kan de netwerktab (onder de F12 toets) inzicht verschaffen.
Visueel heb ik wel over nagedacht. Ik heb een layout met een html tabel. Daaronder heb ik een toevoegknop.
Klik ik op de toevoegknop, dan verschijnt er boven de html tabel een formulier om toe te voegen. De toevoeg knop verdwijnt ook. Met behulp van jquery en ajax kan ik na een druk op de opslaan knop de mysql tabel aanvullen. en verdwijnt het toevoegformulier. De toevoegknop verschijnt ook weer.
klik ik op een regel, dan krijg ik een mutatie formulier boven de html tabel. De toevoegknop verdwijnt. Dan is er de mogelijkheid om te muteren, of de knop om te verwijderen te gebruiken. Ook hier klik je op de opslaan knop om de mysql tabel te muteren.
In beide situaties is er ook een annuleer knop. Deze moet het toevoeg- of muteer-formulier weer sluiten zonder verder iets te doen.
Zodra de opslaan- of verwijder-knop is gebruikt, wil ik de html tabel opnieuw opbouwen.
Dit alles het liefst zonder het scherm te verversen.
Ik heb nu een PHP code die zorgt voor de opbouw van de html tabel.
Als ik je goed volg, moet ik deze code omzetten naar jquery om het makkelijker te maken voor mezelf.
Dat is een mogelijkheid ja.
Al meteen een "gotcha": <tr id="regel"> in een loop. Waarom verwerk je niet gewoon het menu_id in een data-veld?
En als je dan toch gebruik maakt van jQuery: verwijder onclick uit de HTML-code, hier hoeft helemaal geen JavaScript meer in voor te komen. Het koppelen van events aan HTML/de DOM regel je via jQuery zelf.
De regel hoeft niet eens een class-regel te hebben. Als je een id toekent aan de tabel-tag zelf kun je elk element daarvandaan benaderen. Op eenzelfde wijze kun je ook alle opmaak regelen.