Каков наиболее эффективный способ внесения в белый список символов utf-8 в PHP? - PullRequest
1 голос
/ 22 февраля 2011

Моя цель - защитить свой веб-сайт от атак, создав строгий белый список разрешенных символов для всех и всех POST-данных, получаемых со стороны клиента.

Это очень удобно при использовании символов ASCII.,Что-то вроде:

if(preg_match('/[^aA-zZ0-9]/', $stringToTest))
{
   // Battle stations!!
}

Однако мне нужно разрешить любые и все символы utf-8, особенно азиатские наборы символов, такие как японский, китайский и корейский.Но я не хочу исключать кого-либо с дурацкими персонажами, такими как арабский, русский или что-то еще.Один мир, одна любовь!.

Ответы [ 4 ]

4 голосов
/ 22 февраля 2011

\w даст вам буквенные символы (буквы, цифры и символы подчеркивания), что, вероятно, то, что вам нужно после \s для пробела.

, например

if(preg_match('/[\w\s]/', $stringToTest))
{
   // Battle stations!!
}

Regular-expressions.info является отличным справочником для этого материала - здесь и здесь пара соответствующих страниц:)

edit: нужны дополнительные разъяснения, извините!

вот что я обычно использую для CJK:

function get_CJK_ranges() {

    return array(
                "[\x{2E80}-\x{2EFF}]",      # CJK Radicals Supplement
                "[\x{2F00}-\x{2FDF}]",      # Kangxi Radicals
                "[\x{2FF0}-\x{2FFF}]",      # Ideographic Description Characters
                "[\x{3000}-\x{303F}]",      # CJK Symbols and Punctuation
                "[\x{3040}-\x{309F}]",      # Hiragana
                "[\x{30A0}-\x{30FF}]",      # Katakana
                "[\x{3100}-\x{312F}]",      # Bopomofo
                "[\x{3130}-\x{318F}]",      # Hangul Compatibility Jamo
                "[\x{3190}-\x{319F}]",      # Kanbun
                "[\x{31A0}-\x{31BF}]",      # Bopomofo Extended
                "[\x{31F0}-\x{31FF}]",      # Katakana Phonetic Extensions
                "[\x{3200}-\x{32FF}]",      # Enclosed CJK Letters and Months
                "[\x{3300}-\x{33FF}]",      # CJK Compatibility
                "[\x{3400}-\x{4DBF}]",      # CJK Unified Ideographs Extension A
                "[\x{4DC0}-\x{4DFF}]",      # Yijing Hexagram Symbols
                "[\x{4E00}-\x{9FFF}]",      # CJK Unified Ideographs
                "[\x{A000}-\x{A48F}]",      # Yi Syllables
                "[\x{A490}-\x{A4CF}]",      # Yi Radicals
                "[\x{AC00}-\x{D7AF}]",      # Hangul Syllables
                "[\x{F900}-\x{FAFF}]",      # CJK Compatibility Ideographs
                "[\x{FE30}-\x{FE4F}]",      # CJK Compatibility Forms
                "[\x{1D300}-\x{1D35F}]",    # Tai Xuan Jing Symbols
                "[\x{20000}-\x{2A6DF}]",    # CJK Unified Ideographs Extension B
                "[\x{2F800}-\x{2FA1F}]"     # CJK Compatibility Ideographs Supplement
    );

}

function contains_CJK($string) {
    $regex = '/'.implode('|',get_CJK_ranges()).'/u';
    return preg_match($regex,$string);
}

Чтобы получить все, что может быть проблемой для побега и других вещей в черной шляпе, используйте:

/[^\p{Punctuation}]/ (== /[^\p{P}]/)

или

/[^\32-\151]/ (== /[^!-~]/)

еще одна хорошая ссылка

2 голосов
/ 02 апреля 2011

Для некоторых вещей вы можете кодировать с помощью base64, но мне пришлось убрать чуть-чуть функциональности, когда это невозможно, поскольку сохранение всех символов кажется более важным и, безусловно, сейчас не стоит больше времени.

...

Сказав, что я сталкивался с этим, но, похоже, проблема становится эффективной из-за большого количества символов, если вы хотите использовать универсальную функцию, но это не является большой проблемой (китайский, русский и греческий языки могут иметь отдельные веб-страницы и т. Д.) .

http://www.php.net/manual/en/regexp.reference.unicode.php.

0 голосов
/ 22 февраля 2011

Я сомневаюсь, что вы можете защитить что-либо таким образом.
Вы просто усложните ситуацию для честных пользователей, но не остановите злонамеренного.

Я бы просто покинул сайт, на котором не было бы возможности ввести знак вопроса, цитату или электронную почту.
Простая точка наверняка входит в число «мерзких приманок, используемых в злых сценариях».Но любое сообщение без него будет выглядеть ужасно.

В то время как SQL-инъекция может быть выполнена только с использованием букв алфавита.

Не вижу смысла в такой «защите».

0 голосов
/ 22 февраля 2011

Попробуйте инвертировать тест - используйте черный список вместо белого.например,

if(preg_match('/[\*\?<>]/', $stringToTest))
{
    // Battle stations!!
}

Регулярное выражение может быть не совсем правильным, но вы поняли.

...