Loading...

Във форума е въведено ограничение, което позволява на потребителите единствено да разглеждат публикуваните въпроси.

Hristo_Penchev avatar Hristo_Penchev 389 Точки

[Technical Issue] PHP - Проблем със специалните символи

Специалните символи по принцип са проблем в РНР. Аз съвсем не мога да се оправя с тях. Ето ми кода на пета задача:

http://pastebin.com/cmegS92s
http://pastebin.com/fv4nCbNh

Задачата работи с различни примери, но когато въведа текста от примера в домашното, отказва да го присвои изобщо в променлива, поради символите – и ’. Това не са стандартните тире и апостроф от клавиатурата. Без тях всичк ое ОК. Опитах да ползвам кирилица - нея я присвоява, но я печата грешно. Та въпросите са ми следните?

1. Защо програмата отказва да присвои целия текст в стринг променлива при наличието на дълго тире и специален апостроф?

2. Как да я направя да работи с кирилица.

 

3. Ескейпингът на ХТМЛ символи може ли да се прави при присвояване на стойност или е само при печатане? $text = htmlspecialchars($_GET['text']);

Благодаря предварително.

 

Тагове:
1
PHP Web Development Basics 10/12/2014 00:32:44
a.angelov avatar a.angelov 1316 Точки

Здравей,

на третия ти въпрос отговора е - ескейпва се само при печатане! Може да погледнеш презентацията Working-with-Forms-in-PHP - 13-ти слайд:

Principles of HTML Escaping

How and when the HTML escape?

HTML escaping should be performed on all data printed in an HTML page, that could contain HTML special chars.

Any other behavior is incorrect!

Never escape data when you read it!

Escape the data when you print it in a HTML page.

Never store HTML-escaped data in the database!

Never perform double HTML escaping

2
Hristo_Penchev avatar Hristo_Penchev 389 Точки

Да, от там ми е била грешката. Като преместих escaping на изхода вече нямам проблем с присвояването на текста и примерът от домашното работи. Обаче ако сменим ключовата дума с it, не ни изпечатва "Isn’t it great?". Опитах да махна изцяло ескейпинга, тогава печата въпросното изречение, като заменя апострофа с питанка. Явно поради някаква причина въпросният ескейпинг блокира всичко, ако вътре има специален символ.

1
AleksandurSeferinkin avatar AleksandurSeferinkin 333 Точки

С всеки изминал ден все повече започвам да мразя това php. Неочаквано поведение във всяка 3та функция.

3
Filkolev avatar Filkolev 4482 Точки

^ Значи не съм само аз с такива сантименти към тоя език

1
RoYaL avatar RoYaL Trainer 6849 Точки

Why do people hate PHP - едно 20 минутно видео, в което се опитвам да обясня как се насажда подобно мнение у хората за РНР

Няма неочаквано поведение във функциите. Функциите са доста добре документирани и всички възможни случаи са описани.

Вашият случай го има също написан:

http://php.net/manual/en/function.htmlspecialchars.php

Какво връща функцията: Конвертирания стринг ИЛИ

If the input string contains an invalid code unit sequence within the given encoding an empty string will be returned, unless either the ENT_IGNORE or ENT_SUBSTITUTE flags are set.

И съответно решението на проблема е просто:

foreach ($matches[0] as $sentence) {
echo htmlspecialchars($sentence, ENT_QUOTES | ENT_SUBSTITUTE) . "<br/>";
}

Това ще изпиша някакъв странен символ на мястото на smart quote-а. ENT_IGNORE ще го премахне и ще изпише Isnt.

За да ползваш РНР правилно, трябва да си го научил. Съществената разлика между .NET платформата и РНР сам по себе си като фреймуърк е, че първото не ти позволява всякакви начини да се застреляш в крака, освен ако експлицитно не си го поискаш, докато в РНР това е по презумпция наложащо и експлицитно трябва да се защитиш от тези случаи, като се научиш как да работиш с езика.

В крайна сметка от повече от петилетка никой сериозен производител не използва РНР без абстракция. Винаги има някакъв много солиден набор от абстрактнати неща под апликейшън лейъра. Никъде няма да видите htmlspecialchars($string, ENT_SMTH | ENT_SMTHELSE | ENT_SMTHSMTHELSE, 'UTF-8'); Най-вероятно това ще е добре затворено във функции, които се казват Escape::charIgnore(), Escape::charPreserve() и т.н. и т.н.

Това не е проблем на езика, а е съвсем нормална еволюция на програмирането. Както и никой не използва C# без .NET (което еп рактически почти невъзможно). Представяте ли си да имате само компилатора и набор от базови функции? И сега да сетъпнете един уеб сайт на C#? Дори и да успеете да подкарате кода да върви под WEB, ще срещнете абсолютно същите трудности, каквито и тук. С рендирането на HTML, с ескейпването на аутпут. Но хората са го помислили и шипват заедно с езика и цяла една работна рамка, която знае че когато между HTML тагове вкараш променлива, тя трябва да бъде ескейпната по определени условия.

Това е така и с PHP Frameworks. Грешката на учебвната програма е, че първо ни запозна с нещата, които се случват на магия и после ни впусна в среда, в която магията я няма и трябва да намерим как става.

Трябваше да е обратното. Реално за да работиш с абстракциите, които някакъв API ти дава, е хубаво да знаеш как работят те отдолу. Т.е. да си видял някакъв много суров начин на правене на нещата, както в момента го правите с РНР и там някъде да ви щракне лампата "абе тук не може ли да си измисля някакъв механизъм който сам да свързва два файла - PHP и HTML без ръчно да пиша инклуд навсякъде?", "хм, няма ли как да си напиша една фнукцийка която да се аплайва върху всеки стринг, който изведа със short-echo в HTML-a?", "трябва ли ми въбоще addslashes за да вкарвам ескейпнати стрингове в базата, или мога да кажа на драйвъра че това е query, а не query string?" и хиляди други неща, които е хубаво сам човек да се сети, преди да се впусне в среда, в която друг вече ги е измислил и му ги е дал наготово.

На конкретния въпрос кога да се ескейпва нещо, краткият отговор е - когато ти потрябва ескейпнато. Мутирането на данните по дефиниция от самото начало не е добра идея, дори и да не става въпрос за ескейпване.

По-дългият отговор е, че най-добре е да се използва някакъв вид темплейтинг, в който РНР е наясно, че това е темплейт файл, в него нямаш никаква логика, само цикли и ифове, а всяко <?= $var; ?> е ескейпнато. Обикновено за това нещо се ползват темплейт енджини, в които примерно не се отварят въобще РНР тагове за да се дисплейне променлива, а се пишат плейсхолдъри.

От страницата с логиката, подаваш на темплейта някакви променливи примерно:

$this->template->name = $_POST['name'];

$this->template->age = $_GET['age'];

В темплейта си написал

<p> {{$name}} </p>

<b> {{$age}}</b>

 

Когато дойде време да се рендира този темплейт, минава някакъв твой къстъм парсър и почва да чете, като срещне две къдравки скобки и синтаксис за променлива вътре, намира тази променлива, котяо да кажем е пратена на темплейт обекта и той може да я достъпва с $this и казва, "ахаа, тук се принтира в темплейта, чакай да ескейпна" и замества {{$name}} с <?= htmlspecialchars($this->name); ?> например

 

 

5
Можем ли да използваме бисквитки?
Ние използваме бисквитки и подобни технологии, за да предоставим нашите услуги. Можете да се съгласите с всички или част от тях.
Назад
Функционални
Използваме бисквитки и подобни технологии, за да предоставим нашите услуги. Използваме „сесийни“ бисквитки, за да Ви идентифицираме временно. Те се пазят само по време на активната употреба на услугите ни. След излизане от приложението, затваряне на браузъра или мобилното устройство, данните се трият. Използваме бисквитки, за да предоставим опцията „Запомни Ме“, която Ви позволява да използвате нашите услуги без да предоставяте потребителско име и парола. Допълнително е възможно да използваме бисквитки за да съхраняваме различни малки настройки, като избор на езика, позиции на менюта и персонализирано съдържание. Използваме бисквитки и за измерване на маркетинговите ни усилия.
Рекламни
Използваме бисквитки, за да измерваме маркетинг ефективността ни, броене на посещения, както и за проследяването дали дадено електронно писмо е било отворено.