Baš malopre napisah (i testirah) jednu metodu koja proverava da li unos preko browser based js code editora (codemirror ili ace) sadrži samo one tagove koji smeju da se nađu u okviru
head taga, pa rekoh sebi da to podelim sa novajlijama koji čupaju kosu.
Postoji već rešenje za to (HTML purifier, npr.), međ'tim ja sam nekako alergičan na robusne i poznate, freeToUse klase koje doduše, rade svoj posao, pretpostavljam, jako dobro (u životu nisam koristio, lična rešenja su najbolja). Ne želim da gruvam dodatne 'require_once' (itd) i dodatni opcode ako to već može u jednoj hand-made metodi sa malo foreach, explode, itd.. da se odradi i da radi lepo. U suštini, jako, jako prosto za 'sklepati'.
Dakle, onda kada se nađete u situaciji da vam treba unos koji ostavlja traga
isključivo unutar
head taga, pa želite da vašim korisnicima ne dozvolite da osim validnih (html5 DOCTYPE,
'<!--', '-->', '<title>', '<style>', '<base>', '<link>', '<meta>', '<script>', '<noscript>') ne mogu da unesu bilo šta drugo, možete probati sa sledećom metodom/funkcijom.
Metoda ne proverava atribute i ostalo, već samo tagove. Ima li neželjenih ili nema neželjenih.
Između ostalog, metoda takođe proverava da li postoje i Server Side Code tagovi, vezani za xml i sve varijante php-a. Pa ako ima i njih - unos se takođe stopira.
Sve delove uzete u obzir je lako obrisati/izbaciti ili pak proširiti ...
Preduslov:
- Pre nego što se metoda pozove, potrebni su pravi
< i
> open/close tagovi (metoda u svom trenutnom izdanju takve uzima u obzir), ne entiteti *(konverzija se lako može dodati/dopisati samoj metodi, pa, kome treba neka dopiše).
Metoda
Code (php):
<?php
# Check for allowed head tags before writing
class someClass
extends someOtherClass
// Or extends nothing..
{
protected function NotAllowedTagsForHead
($textarea)
{
# HTML tags start
$counter = array();
$allowedTags = array (
'<!--',
'-->',
'<title',
'<style',
'<base',
'<link',
'<meta',
'<script',
'<noscript',
);
$cl=array();
$details=(explode(PHP_EOL
, $textarea));
if(count($details)>=1)
{
foreach($details as $i=>$line)
{
$checkLine=str_replace('>',' ', $details[$i]);
$checkLine=explode(' ', $checkLine);
$checkLine=$checkLine[0];
$cl[]=$checkLine;
}
unset($i, $line, $details, $checkLine);
foreach($cl as $suspect):
if(in_array($suspect, $allowedTags)):
else: $HAAAALT = true; break; endif;
endforeach;
unset($cl, $suspect);
}
else unset($cl, $details);
if(!isset($HAAAALT))
{
foreach($allowedTags as $value):
if(strpos($textarea, $value) !== false):
$counter[]=true; else: endif;
unset($value);
endforeach;
unset($allowedTags);
$HAAAALT=(
(count($counter)<1 || empty($counter)) ?
true:false
);
}
# HTML tags end
# SS/xml tags piece start
foreach( array (
'fullphp' => '<?php',
'shortphp' => '<?',
'aspphp' => '<%',
'shortecho' => '<?=',
'endasp' => '%>',
'endtag' => '?>'
) as $var=>$value):
$$var=strpos($textarea, $value);
unset($value, $var);
endforeach;
$serverSideSTOP=(
in_array(true,
array($fullphp, $shortphp, $aspphp, $shortecho, $endasp, $endtag)) ?
true:false
);
# SS/xml tags piece end
return(
(trim($textarea) !== ''
&& $HAAAALT || $serverSideSTOP ) ?
true:false
);
}
}
-------------
- Metoda se može pridodati bilo kojoj postojećoj klasi jer je 'unutra' - čista standardna php procedura.
- Ukoliko je potrebno, prepraviti
protected u
public *(u mom slučaju sve živo ide kroz instance ili abstrakciju) ...
- Ukoliko ne treba ili ne može da bude metoda u sklopu već funkcija, obrisati 'protected' pozvati istu bez '$this->'
Provera
Code (php):
<?php
/*
Somewhere inside validation script, after submit/post button is being clicked ...
*/
$headTagsArea = $_POST['myTextAreaField'];
if($this->NotAllowedTagsForHead($headTagsArea))
{
echo (
'HEY YOU! <br> You can only add tags allowed within <span class="paramID"><head></span> '.
' on this portion.<br> No scripting, no server side code. <br> '.
'Allowed tags: <span style="color: Green;"><title> <style> <base> '.
'<link> <meta> <script> <noscript></span> '
);
} else {
// No unwanted tags or value is - EMPTY.
// Proceed with validation, parsing, etc ...
}
I to bi bilo to.
:)
Ono što treba imati u vidu, jeste da svaki naredni tag koji korisnici upisuju treba biti u novom redu/liniji.
Pa ako neko džidža ručno sve u jednom redu, to se recimo u '$details' promenjivoj može promeniti/prevazići tako da ne pravi niz od PHP_EOL već od '>' karaktera, npr..
Ukoliko pre pozivanja funkcije, ta sitnica nije već rešena.
npr.
Code (php):
# Umesto
$details=(explode(PHP_EOL
, $textarea));
# Ovako nešto
$details=preg_replace('/\s+/', ' ', $textarea);
$details=str_replace('><','> <',$details);
$details=str_replace('> </','></',$details);
$details=str_replace('> <','>:*:<',$details);
$details=(explode(':*:', $details));
[Ovu poruku je menjao plus_minus dana 07.04.2015. u 20:45 GMT+1]
about:networking