Voor het maximaal toegestane aantal getypte karakters in een textarea gebruik ik een counter die het aantal getypte karakters weergeeft en de waarde van die counter stuur ik via ajax naar een php file die dit serverside checkt.

Dit is de funcite van de counter:

// counting characters textarea
function CountCharacters() {
	var body = tinymce.activeEditor.getBody();
	var content = tinymce.trim(body.innerText || body.textContent);
	return content.length;
};


In de ajax stuur ik hem op deze manier naar de php file:


// count chars input
var countchars = CountCharacters();
$.ajax({
	url: 'comment.php',
	type: 'POST',
	data: {
               .......
               countchars:countchars
              }

De check in php:

<?php
$countchars = $_POST['countchars']; // countchars
$max_chars_allowed = 200;
if( $countchars > $max_chars_allowed ) {
    echo 'maximale toegestane aantal karakters overschreden';
    ......
?>

Mijn vraag is nu: is het mogelijk dat iemand (via de browserinspector) de waarde van de javascript var var countchars kan manipuleren zodat ajax een ander aantal karkaters naar de php file stuurt dan dat er in werkelijkheid getypt is in de textarea? en zodoende dus een comment kan plaatsen dat boven het toegestane aantal karakters ligt?
Niet als deze nog eens in PHP beperkt wordt.
1) Ja, deze is manipuleerbaar. Dus zoals Ariën hierboven al aangeeft zul je bij het daadwerkelijk versturen van de tekst deze nogmaals op lengte moeten controleren.

2) Waarom doe je deze check niet gewoon helemaal client-side (in javascript)? Scheelt je weer een round-trip naar de server. Minder belasting op je server & snellere response voor de gebruiker.
Rob Doemaarwat op 27/06/2020 14:59:41
2) Waarom doe je deze check niet gewoon helemaal client-side (in javascript)? Scheelt je weer een round-trip naar de server. Minder belasting op je server & snellere response voor de gebruiker.


Ik begrijp waarschijnlijk verkeerd met wat je met "helemaal client-side" bedoelt, maar is dit niet juist het probleem, dat de topicstarter (data die afkomstig is van) de gebruiker niet kan vertrouwen (en dit zou je ook nooit moeten doen), en daarom genoodzaakt is om (ook) een server-side controle uit te voeren, wat overigens altijd aan te bevelen is.

De huidige controle in PHP is ook niet goed, want zoals je zelf al aangaf kan countchars gemanipuleerd worden. Vervolgens accepteer je aan de PHP-zijde blindelings dat dit ook het daadwerkelijk aantal ingevoerde karakters is. Een betere controle is dus om het aantal karakters opnieuw te tellen aan de PHP-zijde.

Functies zoals strlen() tellen echter het aantal bytes en niet het aantal karakters, dus het is waarschijnlijk veiliger om een "multi byte aware" functie te gebruiken zoals mb_strlen().

Misschien is dit ook een uitgelezen moment om je (verder) te verdiepen in multibyte-karakters en character encoding en hoe je dit correct integreert in je site en database.
Voor zover ik het zie wordt client-side het aantal karakters al geteld, en wordt server-side dit aantal alleen nog met de $max_chars_allowed vergeleken + evt. foutmelding. Die foutmelding zal client-side dan wel weer getoond worden.

Dan is dus alleen het *aantal karakters* naar de server gegaan. Ik heb even aangenomen dat de tekst zelf uiteindelijk ook naar de server gaat, en dan doe je uiteraard nogmaals (server-side) de lengte check.

De check tussendoor (+ evt. melding) is dus puur "een stukje informatie" naar de gebruiker toe (en niet het "eindoordeel"). Het lijkt me dus niet echt nodig om hiervoor de server lastig te vallen.
Ik neem aan dat je dit alleen serverside checkt als je daadwerkelijk klaar bent met typen en het bericht hebt vestuurd, niet dat je dit telkens opnieuw controleert tijdens het typen.

Je kunt alles aan de clientzijde manipuleren, dus op die informatie zou ik gewoon niet bouwen.

Op het moment dat iemand besluit om de JavaScript zo te manipuleren dat het maximaal aantal karakters overschreden kan worden, dan moet hij/zij dit zelf weten, maar de consequentie is dan wel dat als 'ie dit probeert te versturen dat de server het dan niet accepteert, mits de controles hiervoor niet corrumpeerbaar zijn :).

Hier tussendoor allerlei checks voor uitvoeren (die mogelijk niet betrouwbaar zijn en dus ook op een veilige manier moeten plaatsvinden) lijkt mij overbodige overhead, vooral als dit alles via AJAX loopt, zelfs al heb je dan een uiteindelijke "round-trip naar de server" dan merkt een gebruiker hier mogelijk niets van omdat deze de huidige pagina toch niet verlaat.
Ja wat ik bedoel: Ik kan de input serverside testen met strlen. En dit is ook het veiligste. Maar het probleem wat zich voordoet is dat de javascript length niet exact overeenkomt met de strlen van php. Er zit soms meer dan 10 karakters verschil tussen. Overigens, ik heb str_tags al gebruikt en ook str_replace voor karakters als &nbsp; etc. Daaroverheen ipv strlen mb_strlen gebruikt. En nog een verschil tussen js lenght en php mb_strlen. Dus toen dacht ik: gebruik 1 variable, die van js, en stuur die mee met ajax naar de php. Want wat is het geval: de counter telt af als je begint te typen. Er komt een moment dat ie aangeeft bijv: "2 karakters nog over, van de 100". Dan stop je met typen om er niet overheen te gaan en submit je. Vervolgens test php de input en zegt dat de string 103 karakters bevat. Want strlen is niet hetzelfdee als de length van javascript. Das dus lullig.
Als ik dus 1 variable gebruik, die van de js en die naar php stuur heb ik geen verschil meer. Maar...alles wat er meegestuurd wordt via ajax kan gemanipuleerd worden. Maw: manipuleer via de browserinspector dat er 50 karkaters getypt zijn, (terwijl erin werkelijkheid 150 karakters in de textarea getypt zijn) en de php loop wordt gebypassed omdat hij 50 aangeleverd krijgt om te checken.
Jack Maessen op 27/06/2020 22:27:22
Ja wat ik bedoel: Ik kan de input serverside testen met strlen. En dit is ook het veiligste.

Het veiligste? Je bedoelt dat je dit aan de serverkant opnieuw controleert? Ja, dat is altijd het verstandigste.

Jack Maessen op 27/06/2020 22:27:22
Want wat is het geval: de counter telt af als je begint te typen.

Uhm, dat zijn dus toetsaanslagen, dat hoeft toch niet overeen te stemmen met het daadwerkelijk aantal ingetypte karakters?

Jack Maessen op 27/06/2020 22:27:22
Er komt een moment dat ie aangeeft bijv: "2 karakters nog over, van de 100". Dan stop je met typen om er niet overheen te gaan en submit je. Vervolgens test php de input en zegt dat de string 103 karakters bevat. Want strlen is niet hetzelfdee als de length van javascript. Das dus lullig.

Een betere vraag zou dan dus zijn: hoe telt JavaScript precies (bytes of karakters) en hoe is dit verschil te verklaren?

En strlen() in PHP is dus niet de juiste functie om karakters te tellen.
Klopt @Thomas. Ik heb een issue tussen de length van js en de mb_strlen van php. die zijn niet hetzelfde.
Overigens, js counter heb ik nu zo gemaakt:

 // counting characters textarea
function CountCharacters() {
    var body = tinymce.activeEditor.getBody();
    var content = tinymce.trim(body.innerText || body.textContent);
    content = content.replace(/\r\n|\r|\n/g, "\n");
    return content.length;
};


En de lengte van de userinput serverside test ik zo:

$count_chars_comment = mb_strlen(strip_tags(preg_replace("/&#?[a-z0-9]+;/i"," ",$_POST['comment']))); // length of string

Maar er blijft een verschil in lengte tussen die 2...
En heb je ook getest waar het verschil in zit?
ik ben bang dat het verschil het gevolg is van de tinymce textarea die ik gebruik. Geen idee hoe ik ze synchroon krijg...

Reageren