В Інтернеті є багато застарілої інформації, яка вводить в оману нових користувачів PHP, поширення поганих практик і небезпечного коду. PHP: The Right Way легко читати, короткий довідник для популярних стандартів кодування PHP, посилання на авторитетні посібники в Інтернеті та те, що учасники вважають найкращими практиками на даний момент.
Немає канонічного способу використання PHP. Цей веб-сайт має на меті представити новий PHP розробників до деяких тем, які вони можуть не відкрити, доки не стануть надто пізно, і цілей щоб дати досвідченим професіоналам свіжі ідеї щодо тих тем, якими вони займаються роками ніколи не переглядаючи. Цей веб-сайт також не підкаже вам, які інструменти використовують, але натомість запропонуйте кілька варіантів, по можливості пояснюючи відмінності у підході та варіанті використання.
Це живий документ, який буде оновлюватися більш корисною інформацією і приклади, коли вони стануть доступними.
PHP: The Right Way перекладається багатьма різними мовами:
Найновіша версія PHP: The Right Way також доступна у форматах PDF, EPUB і MOBI. [Перейти до Leanpub][1]
Допоможіть зробити цей веб-сайт найкращим ресурсом для початківців PHP-програмістів! [Зробити внесок на GitHub][2] [1]: https://leanpub.com/phptherightway [2]: https://github.com/codeguy/php-the-right-way/tree/gh-pages
Якщо ви починаєте працювати з PHP, почніть із поточної стабільної версії PHP 8.5. PHP 8.x дає багато нових функцій разом зі старішими версіями 7.x і 5.x. Двігун був значною мірою переписаний, і тепер PHP ще більш швидкий, ніж попередні версії. PHP 8 — це велике оновлення мови, яке містить багато нових функцій і оптимізацій.
Вам слідувати спробувати швидко оновити до останньої стабільної версії - PHP 7.4 [вже закінчився термін служби] [підтримати PHP]. Оновити легко, існує небагато пошкодження зворотної сумісності PHP 8.0, PHP 8.1, PHP 8.2, PHP 8.3, PHP 8.4, PHP 8.5. Якщо ви не впевнені, в якій версії є функція чи функція, ви можете перевірити документацію PHP на веб-сайті php.net.
З PHP 5.4 або новішої версії ви можете розпочати роботу над PHP без встановлення та налаштування повноцінного веб-сервера. Щоб запустити сервер, запустіть таку команду з вашого терміналу в кореневій веб-версії проекту:
> php -S localhost:8000macOS 12 (Monterey) і пізніші версії не постачаються раніше запакованими з PHP. Попередні версії macOS включають PHP, але відстають від останнього стабільного випуску. Є кілька способів встановити останню версію PHP на macOS.
Homebrew — це менеджер пакунків для macOS, який допоможе легко інсталювати різні PHP і розширення. Базовий репозиторій Homebrew містить «формули» для PHP 8.1, 8.2, 8.3, 8.4 і 8.5. Встановіть останню версію за допомогою цієї команди:
brew install php
Ви можете переключатися між версіями PHP Homebrew, змінюючи свою змінну PATH. Крім того, ви можете використовувати brew-php-switcher для автоматичного перемикання версій PHP.
Ви також можете перемикати між версіями PHP вручну, об’єднавши та зв’язавши потрібну версію:
brew unlink php
brew link --overwrite php@8.2
brew unlink php
brew link --overwrite php@8.3
Проект MacPorts — це ініціатива спільноти з відкритим кодом для розробки проста у використанні система для компіляції, встановлення та оновлення командний рядок, програмне забезпечення з відкритим вихідним кодом на базі X11 або Aqua під керуванням macOS система.
MacPorts підтримує попередньо скомпільовані двійкові файли, тому вам не потрібно перекомпілювати кожен залежність від вихідних файлів tarball, це врятує ваше життя, якщо ви цього не зробите встановити будь-який пакет у вашій системі.
На цьому етапі можна встановити php54, php55, php56, php70, php71, php72, php73, php74, php80, php81, php82, php83 або php84 за допомогою команди port install, наприклад:
sudo port встановити php74 порт sudo інсталювати php83
І ви можете запустити команду select, щоб переключити ваш активний PHP:
sudo port select –set php php83
phpbrew — це інструмент для встановлення кількох версій PHP і керування ними. Це може бути дуже корисно, якщо два інших програми/проекти вимагають різні версії PHP, і ви не використовуєте віртуальні машини.
Іншим популярним варіантом є php-osx.liip.ch, який надає один метод встановлення вкладки для версій від 5.3 до 7.3. Він не перезаписує двійкові файли PHP, встановлені Apple, але інсталює всі в окремому місці (/usr/local/php5).
Ще один варіант, який дає вам контроль над версією PHP, яку ви встановлюєте, це компілювати його самостійно. У цьому випадку переконайтеся, що встановлено Xcode або замінник Apple [“Інструменти командного рядка для XCode”] можна завантажити з Центру розробників Apple.
Рішення, перелічені вище, в основному обробляють сам PHP і не надають такі речі, як Apache, Nginx або сервер SQL. Комплексні рішення, такі як MAMP і XAMPP встановлюють ці інші частини програмного забезпечення для ви та зв’яжете їх усі разом, але легкість налаштування приходить із компромісом гнучкості.
Ви можете завантажити двійкові файли зі [сторінки завантаження php.net][php-завантаження]. Після вилучення PHP це так рекомендовано встановити [PATH][шлях до windows] у кореневу папку PHP (де знаходиться php.exe), щоб можна було виконувати PHP з будь-якого місця.
Для навчання та локального розвитку ви можете використовувати вбудований веб-сервер із PHP 5.4+, тому вам не потрібно турбуватися про його налаштування. Якщо ви потрібен «все-в-одному», який включає повноцінний веб-сервер і MySQL також, тоді такі інструменти, як [EasyPHP][easyphp], [OpenServer][openserver] або [WampServer][wamp] отримати результат Середовище розробки Windows працює швидко. Проте ці інструменти будуть дещо відрізнятися від виробництво, тому будьте обережні з відмінностями середовища, якщо ви працюєте в Windows і розгортаєтеся в Linux.
Як правило, запуск вашої програми в різних середовищах розробки та виробництва може призвести до дивних помилок з’являється, коли ви йдете в прямому ефірі. Якщо ви розгортаєте в Windows і розгортаєте в Linux (або будь-якому іншому, що не є Windows), тоді ви варто відшкодувати можливість використання віртуальної машини або [підсистеми Windows для Linux (WSL)][wsl].
Кріс Танкерслі має дуже корисну публікацію в блозі про те, які інструменти він використовує для [розробки PHP за допомогою Windows][windows-tools]. [easyphp]: https://www.easyphp.org/ [openserver]: https://ospanel.io/en/ [php-downloads]: https://www.php.net/downloads.php?os=windows [wamp]: https://wampserver.aviatechno.net/?lang=en [windows-path]: https://www.windows-commandline.com/set-path-command-line/ [windows-tools]: https://ctankersley.com/2016/11/13/developing-on-windows-2016/ [wsl]: https://learn.microsoft.com/en-us/windows/wsl/
Більшість дистрибутивів GNU/Linux постачаються з PHP, доступними з офіційних сховищ, але ці пакети зазвичай трохи відстають від поточної стабільної версії. Є кілька способів отримати нові версії PHP для таких дистрибутивів.
Наприклад, у дистрибутивах GNU/Linux на базі Ubuntu та Debian найкращі альтернативи для нативних пакетів надає та підтримує [Ондржей Сурі][Блог Ондрея Сурі] через його особистий пакет архівів (PPA) на Ubuntu та DPA/bikeshed на Debian. Знайдіть інструкції для кожного з них нижче.
Для дистрибутивів Ubuntu [PPA від Ondřej Surý][Ondrej Sury PPA] надає підтримувані версії PHP разом із багатьма розширеннями PECL. Щоб додати цей PPA до вашої системи, виконайте наступні кроки у ваших терміналах:
bash
sudo add-apt-repository ppa:ondrej/php
2. Після додавання PPA оновіть список пакетів вашої системи:
bash
sudo apt update
Пакет гарантує, що ваша система зможе отримати доступ і встановити цей останній PHP, доступний у PPA.Для дистрибутивів на основі Debian Ондржей Сурі також надає [bikeshed]bikeshed. Щоб додати навіс для велосипедів у свою систему та оновити його, виконайте такі дії:
Переконайтеся, що у вас є root-доступ. Якщо ні, ви можете використовувати sudo для наступних команд.
Оновіть список пакетів вашої системи:
bash
sudo apt-get update
3. Встановіть lsb-release, ca-certificates і curl:
bash
sudo apt-get -y install lsb-release ca-certificates curl
4. Завантажте ключ підпису для репозиторію:
bash
sudo curl -sSLo /usr/share/keyrings/deb.sury.org-php.gpg https://packages.sury.org/php/apt.gpg
5. Додайте репозиторій до джерел програмного забезпечення вашої системи:
bash
sudo sh -c 'echo "deb [signed-by=/usr/share/keyrings/deb.sury.org-php.gpg] https://packages.sury.org/php/ $(lsb_release -sc) main" > /etc/apt/sources.list.d/php.list'
6. Нарешті, знову оновіть список пакетів вашої системи:
bash
sudo apt-get update
Завдяки цим крокам ваша система зможе інсталювати найновіші PHP-пакети з велосипедного сараю.
У дистрибутивах на базі версії RPM (CentOS, Fedora, RHEL тощо) ви можете використовувати [репозиторій RPM Remi][remi-repo], щоб одночасно інсталювати останню PHP або мати кілька доступних версій PHP.
Існує [майстер конфігурації][remi-wizard], доступний для налаштування дистрибутива на основі RPM.
Зрештою, ви завжди можете використовувати контейнери або скомпіювати вихідний код PHP з нуля. [Ondrej Sury Blog]: https://deb.sury.org/ [Ondrej Sury PPA]: https://launchpad.net/~ondrej/+archive/ubuntu/php [bikeshed]: https://packages.sury.org/php/ [remi-repo]: https://rpms.remirepo.net/ [remi-wizard]: https://rpms.remirepo.net/wizard/
Поширеним питанням серед тих, хто хоче писати програми для Інтернету, є: “куди мені роздрукувати свої речі?” протягом багатьох років ця відповідь незмінно була «де DocumentRoot». Хоча ця відповідь не є повною, це чудове місце для початку.
З міркувань безпеки файли конфігурації не повинні бути доступні для відвідувачів сайту; тому загальнодоступні сценарії зберігаються в загальнодоступному каталозі, а приватні конфігурації та дані зберігаються за межами цього каталогу.
Для кожної команди, у якій працює CMS або фреймворка, кожна з цих сутностей використовує стандартну структуру каталогу. Однак, якщо хтось працює над проектом, знати, яка структура файлової системи використовується, може бути складно.
[Пол М. Джонс] пров фантастичне дослідження розширених практик десятків тисяч проектів github у сфері PHP. На основі цього він склав стандартну структуру файлів і каталогів [Стандартний скелет пакета PHP]. У цьому структурному каталозі DocumentRoot необхідно вказати в public/, модульні тести мають бути в каталозі tests/, а сторонні бібліотеки, встановлені [компонент], належать до каталогу vendor/. Для інших файлів і каталогів [Стандартного скелета збереження пакета PHP] буде найбільш доцільним для учасників проекту.
[Paul M. Jones]: https://paul-m-jones.com/
[Standard PHP Package Skeleton]: https://github.com/php-pds/skeleton
[Composer]: /#composer_and_packagist
Спільнота PHP велика й різноманітна, складається з незлічених бібліотек, фреймворків і компонентів. Воно розширене для Розробники PHP можна вибрати кілька з них і об’єднати їх в один проект. Важливо, щоб код PHP дотримувався (якомога ближче) до загального стилю коду, щоб розробникам було легко змішувати та поєднувати різні бібліотеки їхні проекти.
[Framework Interop Group][рис] запропонувала та схвалила серію рекомендацій щодо стилю. Не всі вони стосуються до стилю кодування, але ті, що мають, це PSR-1, PSR-12, PSR-4 і PER Coding Style. ці рекомендації — це лише набір правил, які застосовуються для багатьох проектів, таких як Drupal, Zend, Symfony, Laravel, CakePHP, phpBB, AWS SDK, Застосовуються FuelPHP, Lithium тощо. Ви можете використовувати їх для власних проектів або продовжувати використовувати власні особистий стиль.
В ідеалі ви повинні написати код PHP, який відповідає відомому стандарту. Це може бути будь-яка комбінація PSR або один стандартів кодування PEAR або Zend. Це означає, що інші розробники можуть легко читати ваш код і працювати з ним Програми, які реалізують компоненти, можуть мати послідовність навіть при роботі з великою кількістю коду сторонніх розробників.
Ви можете використовувати PHP_CodeSniffer, щоб перевірити код на відповідність будь-якому із цих рекомендацій, а також плагіни для тексту такі редактори, як Sublime Text, отримувати відгуки в реальному часі.
Ви можете автоматично виправити структуру коду за допомогою одного з таких інструментів:
І ви можете запустити phpcs вручну з сайту:
phpcs -sw –standard=PSR1 file.php
Він покаже помилки та опише, як їх виправити.
Також можна використовувати команду phpcs у гіт-хуку перед фіксацією з аргументом CLI --filter=GitStaged.
Таким чином, код, який містить порушення вибраного стандарту, не може потрапити до сховища, доки вони не будуть
порушення усунуто.
Якщо у вас є PHP_CodeSniffer, ви можете автоматично виправити проблеми з компонуванням коду, про які він повідомляє, за допомогою Прикрашання та виправлення коду PHP.
phpcbf -w –standard=PSR1 file.php
Іншим варіантом є використання PHP Coding Standards Fixer. Він покаже, які помилки були в структурі коду до їх виправлення.
php-cs-fixer fix -v –rules=@PSR1 file.php
Англійська мова є переважною для всіх назв символів та кодової інфраструктури. Коментарі можна легко написати будь-якою мовою доступний для читання всіма поточними та майбутніми сторонами, які можуть працювати над кодовою базою.
Нарешті, гарним додатковим ресурсом для написання чистого PHP-коду є Clean Code PHP.
PHP — це гнучка динамічна мова, яка підтримує різні техніки програмування. Воно різко еволюціонувало років, зокрема, додавши надійну об’єктно-орієнтовану модель у PHP 5.0 (2004), анонімні функції та простори імен у PHP 5.3 (2009) і особливості в PHP 5.4 (2012).
PHP має дуже повний набір функцій об’єктно-орієнтованого програмування, включаючи підтримку класів, абстрактних класів, інтерфейси, успадкування, конструктори, клонування, інші тощо.
PHP підтримує функцію першого класу, яку функцію можна призначити змінною. Як визначені користувачем, так і на складові функції можна посилатися за допомогою змінної та виявляти їх динамічно. Функції можна передавати як аргументи інші функції (функція під назвою Функції вищого порядку) і функції можуть повертати інші функції.
Рекурсія, функція, яка дозволяє функції виключати саму себе, підтримуватися мовою, але більшою мірою коду PHP орієнтована на ітерацію.
Нові анонімні функції (з підтримкою закриття) присутні з PHP 5.3 (2009).
У PHP 5.4 додано можливість прив’язувати замикання до області видимості об’єкта, а також покращено підтримку викликів, щоб вони можна використовувати як взаємозамінні з анонімними функціями майже у всіх випадках.
call_user_func_array()PHP підтримує різні форми метапрограмування за допомогою таких механізмів, як Reflection API і Magic Methods. Є
доступних магічних методів, таких як __get(), __set(), __clone(), __toString(), __invoke() тощо, які вважаються
розробникам підключитися до поведінки класу. Розробники Ruby часто кажуть, що PHP не має method_missing, але це так
доступні як __call() і __callStatic().
Як згадувалося вище, спільна PHP має багато розробників, які створюють багато коду. Це означає, що одна бібліотека PHP код може використовувати ту саму назву класу, що й інший. Коли обидві бібліотеки конструюються в одному просторі імен, вони стикаються і завдавати біди.
Просторі імені вирішують цю проблему. Як описано в довідковому посібнику PHP, простори імен можна порівняти з операційними системні каталоги, що файли _простір імені; два файли з однаковою назвою можна співіснувати в окремих каталогах. так само два класи PHP з однаковою назвою можуть співіснувати в окремих просторах імен PHP. Це так просто.
Для вас важливо створити простір імен для свого коду, щоб його могли використовувати інші розробники, не боячись конфліктів з іншими бібліотеками.
Один із рекомендованих способів використання простору з іменем, викладеним у PSR-4, який надається за стандартним файлом, класом та угода про простір імен, щоб дозволити код plug-and-play.
У жовтні 2014 року PHP-FIG скасував попередній стандарт автозавантаження: PSR-0. І PSR-0, і PSR-4 досить придатні для використання. Останній вимагає PHP 5.3, тому багато проектів для PHP 5.2 реалізують PSR-0.
Якщо ви збираєтеся використовувати стандартний автозавантажувач для нової програми чи пакета, подівіться на PSR-4.
Стандартна бібліотека PHP (SPL) укомплектована PHP і надає набір класів та інтерфейсів. Це вигадане головним чином розширених класів структури даних (стек, черга, купа тощо) та ітераторів, які можуть проходити над цими структурами даних або вашими власними класами, які реалізують інтерфейси SPL.
PHP був створений для створення веб-додатків, але також корисний для створення сценаріїв програмного інтерфейсу командного рядка (CLI). Програми командного рядка PHP можуть допомогти автоматизувати типові завдання, такі як тестування, розгортання та адміністрування додатків.
Програми CLI PHP є потужними, тому ви можете використовувати свою програму одночасно без необхідності створювати та захищати Інтернет GUI для нього. Просто переконайтеся, що не розміщуєте ваші сценарії CLI PHP у загальнодоступному веб-корені!
Спробуйте запустити PHP з командного рядка:
> php -iОпція -i друкує вашу конфігурацію PHP так само, як функція [phpinfo()][phpinfo].
Параметр -a забезпечує інтерактивне насіння, подібне до інтерактивного вірусу Ruby IRB або Python. Є ряд
інших корисних [параметрів командного рядка][cli-options] також.
Давайте напишемо просту програму CLI “Hello, $name”. Щоб спробувати, створіть файл під назвою hello.php, як показано нижче.
<?php
if ($argc !== 2) {
echo "Використання: php hello.php <ім'я>" . PHP_EOL;
вихід (1);
}
$name = $argv[1];
echo "Привіт, $name" . PHP_EOL;PHP встановлює дві спеціальні зміни на основі аргументів, з якими виконується ваш сценарій. [$argc][argc] є цілим числом
змінна, що містить аргумент count, а [$argv][argv] — це змінний масив, що містить значення кожного аргументу.
Першим аргументом завжди є ім’я вашого файлу сценарію PHP, у цьому випадку hello.php.
Вираз exit() використовується з ненульовим числом, щоб повідомити людині, що команда не виконана. загальні використання
коди виходу можна знайти [here][коди виходу].
Щоб запустити наш сценарій, наведений вище, з командного рядка:
> php привіт.php
Використання: php hello.php <ім'я>
> php hello.php world
Привіт, світеОдним із найбільш корисних інструментів у розробці програмного забезпечення є належний відладчик. Це дозволяє відстежити виконання ваших код і стежити за вмістом стека. Xdebug, налагоджувач PHP, може використовуватися серед IDE для забезпечення Перевірка точок зупинки та стека. Це також можна дозволити таким інструментам, як PHPUnit і KCacheGrind, виконати охоплення коду аналіз і профілювання коду.
Якщо ви опинились у безвиході, бажаючи вдатися до var_dump()/print_r(), але все ще не можете знайти рішення -
можливо, вам потрібно використовувати налагоджувач.
Встановлення Xdebug може бути складним, але єдиним з його важливими функціями є “Віддалене налагодження” - ви розробляєте код локально, а потім тестуєте його у віртуальній внутрішній машині або на іншому сервері, віддалене накладання — це функція, яку ви вибрали захочуть увімкнути відразу.
Традиційно ви змінюєте файл Apache VHost або .htaccess із такими значеннями:
php_value xdebug.remote_host 192.168.?.?
php_value xdebug.remote_port 9000«Віддалений хост» і «віддалений порт» відповідають вашому локальному комп’ютеру та порту, на який ви шукаєте IDE слухай далі. Тоді потрібно лише перевести IDE в режим «прослуховування з’єднання» і завантажити URL-адресу:
http://your-website.example.com/index.php?XDEBUG_SESSION_START=1
Ваша IDE тепер перехоплює поточний стан під час виконання сценарію, дозволяючи встановлювати точки зупинки та перевірки значення в пам’яті.
Графічні налагоджувачі можуть дуже легко проходити код, змінювати та оцінювати код у порівнянні з живим середовищем перевірки виконання. Багато IDE мають вбудовану підтримку або підтримку графічного налагодження за допомогою Xdebug. MacGDBp — безкоштовна програма з відкритим кодом, автономний графічний інтерфейс Xdebug для macOS.
Існує маса бібліотек PHP, фреймворків і компонентів на вибір. Ваш проект, швидше за все, використовуйте кілька з них — це залежність від проекту. PHP не мав хорошого способу керування ці щодо проекту. Крім того, якщо ви керували ними вручну, вам все одно доводилося турбуватися про автозавантажувачі. Це вже не проблема.
Зараз існують дві основні системи керування пакетами для PHP - [Композитор] і [PEAR]. Композитор в даний час найпопулярніший менеджер пакетів для PHP, однак протягом тривалого часу PEAR був основним менеджером пакетів у використанні. Знати історію PEAR — гарна ідея, після чого ви все одно можете знайти посилання на неї, навіть якщо ніколи не користуєтеся. [Composer]: /#composer_and_packagist [PEAR]: /#pear
Composer — рекомендований менеджер залежностей для PHP. Перелічіть залежності вашого проекту у файлі composer.json і,
за допомогою кількох простих команд Composer автоматично завантажить залежності вашого проекту та налаштує автозавантаження для
ти. Composer аналогічний NPM у світі node.js або Bundler у світі Ruby.
Існує безліч бібліотек PHP, які сумісні з Composer і готові до використання у вашому проекті. Ці “пакети” перераховані в Packagist, офіційному репозиторії бібліотек PHP, сумісних із Composer.
Найбезпечніший спосіб завантажити композитор — дотримуючись офіційних інструкцій.
Це дозволить переконатися, що програму встановлення не пошкоджено чи не змінено.
Програма встановлення встановлює двійковий файл composer.phar у ваш поточний робочий каталог.
Ми рекомендуємо інсталювати Composer глобально (наприклад, одну копію в /usr/local/bin). Для цього виконайте наступну команду:
mv composer.phar /usr/local/bin/composerПримітка. Якщо вищевказане не вдається через дозволи, додайте префікс sudo.
Щоб запустити локально встановлений Composer, ви б використовували php composer.phar, глобально це просто composer.
Для користувачів Windows найпростішим способом почати роботу є використання інсталятора ComposerSetup, який
виконує глобальне встановлення та налаштовує ваш $PATH так, щоб ви могли просто викликати composer з будь-якого
у вашому командному рядку.
Composer відстежує залежності вашого проекту у файлі під назвою composer.json. Ви можете керувати цим
вручну, якщо хочете, або скористайтеся самим Composer. Команда composer require додає залежність проекту
і якщо у вас немає файлу composer.json, він буде створений. Ось приклад, який додає Twig
як залежність від вашого проекту.
композитор вимагає twig/twig:^2.0Крім того, команда composer init допоможе вам створити повний файл composer.json
для вашого проекту. У будь-якому випадку, коли ви створите свій файл composer.json, ви можете вказати Composer
завантажте та встановіть ваші залежності в каталог vendor/. Це стосується і проектів
ви завантажили, які вже містять файл composer.json:
встановлення композитораДалі додайте цей рядок до основного файлу PHP вашої програми; це вкаже PHP використовувати Composer автозавантажувач для залежностей вашого проекту.
<?php
вимагати 'vendor/autoload.php';Тепер ви можете використовувати ваші залежності проекту, і вони будуть автоматично завантажуватися на вимогу.
Composer створює файл під назвою composer.lock, у якому зберігається точна версія кожного пакета
завантажено під час першого запуску composer install. Якщо ви ділитеся своїм проектом з іншими,
переконайтеся, що файл composer.lock включено, щоб під час запуску composer install вони
отримати такі ж версії, як і ви. Щоб оновити свої залежності, запустіть composer update. Не використовуйте
composer update під час розгортання лише composer install, інакше ви можете отримати інші
пакетні версії на виробництві.
Це найбільш корисно, коли ви гнучко визначаєте вимоги до версії. Наприклад, версія
Вимога ~1.8 означає «все, що нове, ніж 1.8.0, але менше, ніж 2.0.x-dev». Ви також можете використовувати
символ підстановки *, як у 1.8.*. Тепер команда Composer composer update оновить усі ваші
залежності до найновішої версії, яка відповідає встановленим вами обмеженням.
Щоб отримувати сповіщення про випуск нових версій, ви можете зареєструватися на веб-службі libraries.io. який може контролювати залежності та надсилати вам сповіщення про оновлення.
Local PHP Security Checker — це інструмент командного рядка, який перевірить ваш composer.lock
файл і повідомить вам, чи потрібно оновити будь-які ваші залежності.
Composer також може обробляти глобальні залежності та їхні двійкові файли. Використання просте, все, що вам потрібно
До вашої команди потрібно додати префікс global. Якщо, наприклад, ви хочете встановити PHPUnit і мати його
доступний глобально, потрібно виконати таку команду:
composer global вимагає phpunit/phpunitБуде створено папку ~/.composer, у якій зберігаються ваші глобальні залежності. Для встановлення
двійкові файли пакетів, доступні скрізь, ви повинні додати папку ~/.composer/vendor/bin до свого
Змінна $PATH.
Ветеран пакетного менеджера, який подобається деяким розробникам PHP, це PEAR. Він поводиться подібно до Composer, але має деякі помітні відмінності.
PEAR вимагає, щоб кожен пакет мав певну структуру, що означає, що авторський пакет повинен її підготувати використання з PEAR. Використання проекту, який не був підготовлений для роботи з PEAR, неможливо.
PEAR встановлює пакети глобально, що означає, що після їх інсталяції вони залишаються доступними для всіх проектів на цьому місці сервер. Це може бути добре, якщо багато проектів складаються на той самий пакет з тією самою версією, але може звести до проблеми, якщо отримати конфлікти версій між двома проектами.
Ви можете встановити PEAR, завантаживши інсталятор .phar і запустивши його. У документації PEAR є
докладні інструкції зі встановлення для кожної операційної системи.
Якщо ви можете використовувати Linux, ви також перегляньте менеджер пакунків дистрибутива. Debian і Ubuntu,
наприклад, мати відповідний пакет php-pear.
Якщо пакет указано в списку пакетів PEAR, ви можете встановити його, вказавши офіційну назву:
pear встановити fooЯкщо пакет є на іншому каналі, вам потрібно спочатку канал discover, а також вказати його, коли
встановлення. Див. Використання каналу документів для отримання додаткової інформації на цю тему.
Якщо ви вже використовуєте Composer і бажаєте встановити певний код PEAR, ви можете використовувати Composer, обробляти ваші відносини PEAR. Репозиторії PEAR більше не підтримують Composer версії 2, тому вам потрібно вручну додати репозиторій для встановлення пакетів PEAR:
{
"сховища": [
{
"type": "пакет",
"пакет": {
"ім'я": "pear2/pear2-http-запит",
"версія": "2.5.1",
"dist": {
"url": "https://github.com/pear2/HTTP_Request/archive/refs/heads/master.zip",
"type": "zip"
}
}
}
],
"вимагати": {
"pear2/pear2-http-запит": "*"
},
"автозавантаження": {
"psr-4": {"PEAR2\\HTTP\\": "vendor/pear2/pear2-http-request/src/HTTP/"}
}
}Перший розділ "repositories" використовуйте, щоб повідомити Composer, що його слід «ініціалізувати» (або «викрити» у PEAR
термінологія) the pear repo. Тоді розділ require матиме префікс імені пакета таким чином:
груша-канал/пакет
Префікс “груша” жорстко закодований, щоб уникнути будь-яких конфліктів, пропуск грушевого каналу може бути таким же, як і інший постачальник пакетів наприклад, ім’я, а потім коротку назву каналу (або повну URL-адресу) можна використовувати для посилання на канал, у якому знаходиться пакет.
Коли цей код буде встановлено, він буде доступний у вашому каталозі постачальника та автоматично доступний через Автозавантажувач композитора:
vendor/pear2/pear2-http-request/pear2/HTTP/Request.php
Щоб скористатися цим пакетом PEAR, просто скористайтеся ним так:
<?php
вимагати __DIR__. '/vendor/autoload.php';
використовувати PEAR2\HTTP\Request;
$request = новий запит();PHP — це велика мова, яка дозволяє програмістам усіх рівнів створювати код не тільки швидко, але й ефективно. Однак, просуваючись у мові, ми часто забуваємо ці основи, які спочатку вивчили (або пропустили) на спробу коротких шляхів і/або шкідливих звичок. Щоб допомогти впоратися з цією розширеною проблемою, цей розділ має на меті нагадати програмістам про основні методи кодування в PHP.
У PHP є клас під назвою DateTime, який допоможе вам читати, записувати, порівнювати або обчислювати дату й час. там Крім DateTime, в PHP є багато функцій, пов’язаних із датою та часом, але він забезпечує гарний об’єктно-орієнтований інтерфейс для найпоширеніші використання. DateTime може обробляти часові пояси, але це виходить за рамки цього короткого вступу.
Щоб почати роботу з DateTime, перетворіть необроблений рядок дати й часу на об’єкт за допомогою фабричного методу createFromFormat()
або виконайте new DateTime, щоб отримати поточну дату та час. Використовуйте метод format(), щоб перетворити DateTime назад на рядок для
вихід.
<?php
$raw = '22. 11. 1968';
$start = DateTime::createFromFormat('d. m. Y', $raw);
echo 'Початок даних: ' . $start->format('Y-m-d') . PHP_EOL;Обчислення за допомогою DateTime можливо за допомогою класу DateInterval. DateTime має такі методи, як add() і sub(), які
візьміть DateInterval як аргумент. Не пиши код, який очікує однакову кількість секунд щодня. Обидва денне світло
збереження та зміни часового поясу порушити це припущення. Натомість використовуйте інтервалі дат. Щоб розрахувати різницю дат
використовуйте метод diff(). Він поверне новий DateInterval, який дуже легко відобразити.
<?php
// створити копію $start і додати один місяць і 6 днів
$end = клон $start;
$end->add(new DateInterval('P1M6D'));
$diff = $end->diff($start);
echo 'Різниця: ' . $diff->format('%m місяць, %d днів (загалом: %a днів)') . PHP_EOL;
// Різниця: 1 місяць, 6 днів (загалом: 37 днів)Ви можете використовувати стандартні порівняння об’єктів DateTime:
<?php
if ($start < $end) {
echo "Початок перед кінцем!" . PHP_EOL;}Останній приклад для демонстрації класу DatePeriod. Він використовується для повторення подій, що повторюєте. Це може зайняти два Об’єкти DateTime, початок і кінець, інтервал, течія якого повертаються також усі події між ними.
<?php
// вивести всі четверги між $start і $end
$periodInterval = DateInterval::createFromDateString('перший четвер');
$periodIterator = новий DatePeriod($start, $periodInterval, $end, DatePeriod::EXCLUDE_START_DATE);
foreach ($periodIterator як $date) {
// виведення кожного дати в періоді
echo $date->format('Y-m-d') . ' ';
}Популярним розширенням PHP API є Carbon. Він успадковує все в класі DateTime, тому забезпечує мінімальні зміни коду, але додатково включає функції підтримки локалізації, додаткові способи додавання, віднімання та форматування об’єкта DateTime, а також засоби для тестування вашого коду шляхом імітації дати та часу за вашим вибором.
Коли ви створюєте свою програму, корисно використовувати загальні шаблони у вашому коді та загальні шаблони для загальна структура вашого проекту. Використання загальних шаблонів є корисним, оскільки це значно полегшує керування кодом і дозволяє іншим розробникам швидко зрозуміти, як все поєднується.
Якщо ви використовуєте фреймворк, то більша частина коду вищого рівня та структура проекту базуватимуться на цьому фреймворку, тому a багато рішень про шаблони приймаються за вас. Але ви все одно повинні вибрати найкращі шаблони для наслідування код, який ви створюєте поверх фреймворку. Якщо, з іншого боку, ви не використовуєте фреймворк для створення своєї програми тоді ви повинні знайти шаблони, які найкраще відповідають типу та розміру програми, яку ви створюєте.
Ви можете дізнатися більше про шаблони проектування PHP і переглянути робочі приклади за адресою:
Цей розділ спочатку був написаний Alex Cabal о Найкращі практики PHP і було використано як основа для наших власних порад щодо UTF-8.
Зараз PHP не підтримує Unicode на низькому рівні. Є способи переконатися, що рядки UTF-8 обробляються нормально, але це нелегко, і вимагає вивчення майже всіх рівнів веб-програм, від HTML до SQL і PHP. Ми будемо цілитися для короткого практичного резюме.
Базові операції над рядками, такі як об’єднання двох рядків і призначення рядків змінним, нічого не потребують
спеціально для UTF-8. Однак деякі рядки функцій, такі як strpos() і strlen(), потребують особливої уваги. ці
функції часто мають відповідник mb_*: наприклад, mb_strpos() і mb_strlen(). Ці рядки mb_* зроблені
доступні через [Multibyte String Extension] і спеціально розроблені для роботи з рядками Unicode.
Ви повинні використовувати функції mb_* щоразу, якщо працюєте з рядком Unicode. Наприклад, якщо ви використовуєте substr() на a
Рядок UTF-8, є хороша ймовірність, що результат наповнює деякі спотворені напівсимволі. Правильна функція для використання
буде багатобайтовим аналогом mb_substr().
Важко пам’ятати, що функції mb_* потрібно використовувати завжди. Якщо ви забудете хоча б один раз, ваш Unicode
рядок може бути спотворений під час подальшої обробки.
Не всі рядкові функції мають відповідник mb_*. Якщо немає такого для того, що ви хочете зробити, то ви можете бути поза
удачі.
Ви повинні використовувати функцію mb_internal_encoding() у верхній частині кожного сценарію PHP, який ви пишете (або у верхній частині вашої
global include script) і функція mb_http_output() відразу після нього, якщо ваш сценарій виведе в браузер.
Явне визначення кодування ваших рядків у кожному сценарії позбавить вас від багатьох головних болів у майбутньому.
Крім того, багато функцій PHP, які працюють із рядками, мають додатковий параметр, який дозволяє вказати символ
кодування. Ви завжди повинні явно вказувати UTF-8, коли надається така опція. Наприклад, htmlentities() має
параметр для кодування символів, і ви завжди повинні вказувати UTF-8, якщо маєте справу з такими рядками. Зверніть увагу, що починаючи з PHP 5.4.0, UTF-8 є кодуванням для замовчувань для htmlentities() і htmlspecialchars().
Нарешті, якщо ви створите розподілену програму і не можете бути впевнені, що розширення mbstring буде
увімкнено, тоді розгляньте можливість використання пакета [symfony/polyfill-mbstring] Composer. Цеме використовувати mbstring, якщо він доступний, і
залежить від функцій, відмінних від UTF-8, якщо ні.
[Multibyte String Extension]: https://www.php.net/book.mbstring
[symfony/polyfill-mbstring]: https://packagist.org/packages/symfony/polyfill-mbstring
Якщо ваш сценарій PHP отримує доступ до MySQL, існує ймовірність того, що ваші рядки можуть зберігатися в базі даних як рядки, відмінні від UTF-8 навіть якщо ви дотримуєтесь усіх наведених вище заходів безпеки.
Щоб переконатися, що ваші рядки переходять із PHP на MySQL як UTF-8, переконайтеся, що ваша база даних і таблиці налаштовані на
набір символів utf8mb4 і сортування, а також використання набору символів utf8mb4 у рядку з’єднання PDO. див
приклад коду нижче. Це критично важливо.
Зауважте, що ви повинні використовувати набір символів utf8mb4 для повної підтримки UTF-8, а не набір символів utf8! див
Подальше читання, чому.
Використовуйте функцію mb_http_output(), щоб переконатися, що ваш сценарій PHP виводить рядки UTF-8 у ваш браузер.
Відповідь HTTP має повідомити веб-переглядачу, що цю сторінку слід вважати UTF-8. Сьогодні прийнято встановлювати набір символів у заголовку відповіді HTTP таким чином:
<?php
header('Content-Type: text/html; charset=UTF-8')Історичним підходом до цього було додавання тегу набору символів <meta> до тегу <head> вашої сторінки.
<?php
// Повідомте PHP, що ми використовуємо рядки UTF-8 до кінця сценарію
mb_internal_encoding('UTF-8');
$utf_set = ini_set('default_charset', 'utf-8');
if (!$utf_set) {
throw new Exception('не вдалося встановити default_charset на utf-8, переконайтеся, що його встановлено у вашій системі!');
}
// Повідомте PHP, що ми будемо виводити UTF-8 у браузер
mb_http_output('UTF-8');
// Наш тестовий рядок UTF-8
$string = 'El síla erin lû e-govaned vîn.';
// Певним чином трансформувати рядок за допомогою багатобайтової функції
// Зверніть увагу на те, як ми скоротили рядок на символі, відмінному від Ascii, для демонстраційних цілей
$string = mb_substr($string, 0, 15);
// Підключення до бази даних для збереження перетвореного рядка
// Для отримання додаткової інформації дивіться приклад PDO в цьому документі
// Зверніть увагу на `charset=utf8mb4` в назві джерела даних (DSN)
$link = новий PDO(
'mysql:host=ваше ім'я хоста;dbname=ваша база даних;charset=utf8mb4',
'ваше ім'я користувача',
'ваш-пароль',
масив(
PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
PDO::ATTR_PERSISTENT => false
)
);
// Зберігаємо наш перетворений рядок як UTF-8 у нашій базі даних
// Ваша БД і таблиці мають набір символів і сортування utf8mb4, вірно?
$handle = $link->prepare('вставити в ElvishSentences (Id, Body, Priority) значення (за замовчуванням, :body, :priority)');
$handle->bindParam(':body', $string, PDO::PARAM_STR);
$пріоритет = 45;
$handle->bindParam(':priority', $priority, PDO::PARAM_INT); // явно вказуємо pdo очікувати int
$handle->execute();
// Отримати рядок, який ми щойно зберегли, щоб підтвердити, що він був збережений правильно
$handle = $link->prepare('вибрати * з ElvishSentences, де Id = :id');
$id = 7;
$handle->bindParam(':id', $id, PDO::PARAM_INT);
$handle->execute();
// Зберігаємо результат в об’єкт, який ми виведемо пізніше в нашому HTML
// Цей об’єкт не вб’є вашу пам’ять, оскільки він своєчасно отримує дані
$результат = $handle->fetchAll(\PDO::FETCH_OBJ);
// Приклад оболонки, яка дозволяє вам передавати дані в html
функція escape_to_html($dirty){
echo htmlspecialchars($dirty, ENT_QUOTES, 'UTF-8');
}
header('Content-Type: text/html; charset=UTF-8'); // Немає потреби, якщо для вашого default_charset уже встановлено значення utf-8
?><!doctype html>
<html>
<голова>
<meta charset="UTF-8">
<title>Тестова сторінка UTF-8</title>
</head>
<тіло>
<?php
foreach($result as $row){
escape_to_html($row->Body); // Це має правильно вивести наш трансформований рядок UTF-8 у браузер
}
?>
</body>
</html>Застереження для новачків: i18n і l10n є нумеронімами, свого роду абревіатурою, де цифри використовуються для скорочення слова - у нашому випадку інтернаціоналізація стає i18n, а локалізація - l10n.
Перш за все, нам потрібно визначити ці два схожі поняття та інші пов’язані речі:
Найпростіший спосіб інтернаціоналізації програмного забезпечення PHP — використання масивів файлів і використання цих рядків у шаблонах, таких як
<h1><?=$TRANS['title_about_page']?></h1>. Однак цей спосіб навряд рекомендований для серйозних проектів, як він представляє
Деякі проблеми з техобслуговуванням уздовж дороги - деякі можуть виникнути на самому початку, наприклад, множинність. Тож будь ласка,
не пробуйте це, якщо ваш проект надрукуйте більше двох сторінок.
Найбільш класичним способом, який часто виконується як посилання для i18n і l10n, є [інструмент Unix під назвою gettext][gettext]. Це дати
повертається до 1995 року і досягає повної реалізації для перекладу програмного забезпечення. Досить легко почати працювати, поки
все ще має потужні інструменти підтримки. Саме про Gettext ми тут і будемо говорити. Крім того, щоб допомогти вам не заплутатися
через командний рядок ми представляємо чудову програму з графічним інтерфейсом користувача, яку можна використовувати для легкого оновлення джерела l10n.
Використовуються загальні бібліотеки, які підтримують Gettext та інші реалізації i18n. Деякі з них можуть здатися легшими
інсталювати або використовувати додаткові функції або формати файлів i18n. В цьому документі ми зосереджуємося на інструментах, які надаються разом з
Ядро PHP, але тут ми перераховуємо інші для доповнення:- [aura/intl][aura-intl]: Надає інструменти інтернаціоналізації (I18N), зокрема пакетно-орієнтоване повідомлення для всіх мов
переклад. Він використовує формати масивів для повідомлень. Не надає екстрактора повідомляє, але надає розширені можливості
форматування повідомлень за допомогою розширення intl (включно з повідомленнями в загальному множині).
gettext), а також можуть експортувати
в інших форматах, крім файлів .mo/.po. Може бути корисним, якщо вам потрібно інтегрувати ваші файли перекладу в інші
частини системи, наприклад інтерфейс JavaScript.strtr().Інші фреймворки також включають модулі i18n, але вони недоступні за межами їхніх кодових баз:
— [Laravel] підтримує базові масиви файлів, не має автоматичного екстрактора, але містить помічник @lang для файлів шаблонів.
Intl][intl], доступне з PHP 5.3 і засноване на [проекті ICU]; це дозволяє Yii працювати потужно
заміни, як-от написання чисел, форматування дат, часу, інтервалів, валюти та порядкових номерів.Якщо ви вирішите вибрати одну з бібліотек, які не містять екстрактори, ви можете використовувати формат gettext, тому ви можете використовувати оригінальний інструментарій gettext (включаючи Poedit), як описано в останньому розділі.
Можливо, вам знадобиться інсталювати Gettext і відповідну бібліотеку PHP за допомогою пакетів менеджера, наприклад apt-get або yum.
Після встановлення увімкніть його, додавши extension=gettext.so (Linux/Unix) або extension=php_gettext.dll (Windows) до
ваш php.ini.
Тут ми також будемо використовувати [Poedit] для створення файлів перекладу. Ймовірно, ви знайдете його в пакеті вашої системи менеджер; він доступний для Unix, macOS і Windows, і його можна [завантажити безкоштовно на веб-сайті][poedit_download] також.
Під час роботи з gettext ви зазвичай маєте роботу з трьома файлами. Основними з них є PO (Portable Object) і Файли MO (Machine Object), перший з яких є списком доступних для читання «перекладених об’єктів», інших — відповідний. двійковий файл, який буде інтерпретовано gettext під час локалізації. Існує також файл POT (шаблон), який просто містить всі наявні ключі з ваших вихідних файлів і можуть використовуватися як посібник для створення та оновлення всіх PO-файлів. Ті шаблони файли не є обов’язковими: залежно від інструменту, який ви використовуєте для виконання l10n, ви можете добре працювати лише з файлами PO/MO. У вас завжди буде одна пара файлів PO/MO для кожної мови та регіону, але лише один POT для кожного домену.### Домени Бувають випадки у великих проектах, коли ви можете знадобитися розділити переклади, коли передаються однакові слова різне значення в контексті. У таких випадках ви розділяєте їх на інші домени. Вони, в основному, названі групи файлів POT/PO/MO, де ім’я файлу є зібраним доменом перекладу. Малі та середні проекти, як правило, для спрощення використовуйте лише один домен; назва є вільною, але ми будемо використовувати його “main” для наших зразків коду. У проектах [Symfony], наприклад, домени сайту для розділення перекладу повідомлень перевірки.
Локаль — це просто код, який ідентифікує одну версію мови. Це визначено відповідно до [ISO 639-1][639-1] і Специфікації [ISO 3166-1 alpha-2][3166-1]: дві малі літери для мови, необов’язково після підкреслення двох великі літери, що ідентифікують код країни або регіону. Для [рідкісних мов][рідкісних] є три літери.
Деяким мовцям частина країни може здатися зайвою. Насправді деякі мови мають різні діалекти
таких країнах, як австрійська німецька (de_AT) або бразильська португальська (pt_BR). Друга частина використовується для розрізнення
між цими діалектами - коли його немає, його сприймають як “загальну” або “гібридну” версію мови.
Щоб використовувати Gettext, нам потрібно буде виконувати певну структуру папок. Спочатку вам потрібно буде вибрати довільний
root для ваших файлів l10n у вашому вихідному сховищі. Усередині нього ви матимете папку для кожної необхідної мови та a
виправлено папку LC_MESSAGES, яка наповнює всі ваші пари PO/MO. приклад:
<корінь проекту>
├─ src/
├─ шаблони/
└─ локалі/
├─ форум.пот
├─ site.pot
├─ de/
│ └─ LC_MESSAGES/
│ ├─ forum.mo
│ ├─ forum.po
│ ├─ site.mo
│ └─ site.po
├─ es_ES/
│ └─ LC_MESSAGES/
│ └─ ...
├─ пт/
│ └─ ...
├─ pt_BR/
│ └─ ...
└─ pt_PT/
└─ ...Як ми вже говорили у вступі, інші мови можуть використовувати різні правила множини. Однак gettext рятує нас від
знову ця біда. Під час створення нового файлу .po вам цікаво оцінити [правила множини][множина] для цього
мову, і перекладені частини, які чутливі до множини, мають різну форму для кожного з цих правил. Коли
Викликаючи Gettext у коді, вам зовсім вказати число, пов’язане з реченнями, і воно буде правильним
форма для використання - навіть використовуючи підстановку рядка, якщо потрібно.
Правила множини включають кількість доступних форм множини та логічний тест із n, який визначає, у якому правилі
дане число випадає (починаючи відлік з 0). Наприклад:
nplurals=1; plural=0 - лише одне правило
– Англійська: nplurals=2; plural=(n != 1); – два правила, перше, якщо N дорівнює одиниці, друге правило – іншеnplurals=2; plural=(n > 1); - два правила, друге, якщо N більше за одиницю, перше в іншому випадкуТепер, коли ви зрозуміли, як працюють правила множини, а ні, перегляньте глибше пояснення у [підручнику LingoHub][lingohub_plurals] - ви можете замість цього скопіювати ті, які вам потрібні, із [list][множина] написання їх від рук.
Викликаючи Gettext для локалізації речей із лічильниками, ви повинні надати йому значення
також відповідний номер. Gettext визначте, яке правило має діяти, і використовує правильну локалізовану версію.
Вам потрібно буде включити у файл .po інше речення для кожного визначеного правила множини.### Приклад реалізації
Після цієї теорії дайте трохи практики. Ось уривок файлу .po – не зважайте на його формат,
але натомість із загальним змістом; пізніше ви дізнаєтеся, як це легко редагувати:
msgstr ""
msgstr ""
"Мова: pt_BR\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Форми множини: nplurals=2; множина=(n > 1);\n"
msgstr "Зараз ми перекладаємо деякі рядки"
msgstr "Наш переклад агори рядків"
msgstr "Вітаємо, %1$s! Ваш останній візит був %2$s"
msgstr "Ой, %1$s! Останнє відвідування для %2$s"
msgstr "Вище одне непрочитане повідомлення"
msgid_plural "%d непрочитаних повідомлень"
msgstr[0] "Немає повідомлення"
msgstr[1] "%d повідомлень немає"Перший розділ працює як заголовок, після msgid і msgstr особливо порожні. Він описує кодування файлу,
форми множини та інші речі, які менш актуальні.
Другий розділ перекладає простий рядок з англійської мови
бразильською португальською, а третій робить те саме, але використовуючи заміну рядка з sprintf, тому
переклад може надрукувати ім’я користувача та дату відвідування.
Останній розділ — зразок форм множини, відображення
версії одні та множини як msgid англійською мовою та їхні відповідні переклади як msgstr 0 та 1
(за номером, заданим правилом множини). Там також використовується заміна рядка, щоб число було видно
один у реченні, використовуючи %d. У формі множини завжди є два msgid (однина та множина), тому це
радимо не використовувати складну мову як джерело перекладу.
Як ви могли помітити, ми використовуємо як ідентифікатор джерела фактичне речення англійською мовою. msgid використовується так само
у всіх ваших файлах .po, які інші мови мають той самий формат і однакові поля msgid, але
перекладені рядки msgstr.
Якщо говорити про ключі перекладу, то тут є дві основні «школи»:
msgid як реальне речення.
Основні переваги:
msgid;msgid
у кількох мовних файлах.2. msgid як унікальний структурований ключ.
Він структуровано описує роль речення в додатку, включаючи шаблон або частину, де
рядок знаходиться замість його вмісту.en.po
перекладачі читали б, щоб зрозуміти, що писати, наприклад, fr.po.top_menu.welcome замість Hello there, User!
на згаданій неперекладеній французькій сторінці). Це добре, такий переклад має бути завершеним перед публікацією -
однак проблеми з перекладом були надзвичайно жахливими в інтерфейсі. Однак деякі бібліотеки відповідають an
можливість вказати цю мову як “резервну”, маючи поведінку, подібну до іншого підходу.[Посібник Gettext][посібник] надає перевагу першому підходу, після, загалом, перекладачам і користувачам легше випадок біди. Так ми будемо працювати і тут. Однак [документація Symfony][symfony-keys] дає перевагу переклад на основі ключових слів, щоб дозволити незалежні зміни всіх перекладів, не впливаючи також на шаблони.
У типових програмах ви використовували деякі функції Gettext під час написання статичного тексту на своїх сторінках. Ті речення
потім з’явиться у файлі .po, буде перекладено, скомпільовано у файлі .mo, а потім Gettext під час використання візуалізації
фактичний інтерфейс. Враховуючи це, давайте об’єднаємо те, що ми обговорювали досі, у покроковому прикладі:
<?php include 'i18n_setup.php' ?>
<div id="header">
<h1><?=sprintf(gettext('Ласкаво просимо, %s!'), $name)?></h1>
<!-- код із таким відступом лише для розбірливості -->
<?php if ($unread): ?>
<h2><?=sprintf(
ngettext('Ще одне непрочитане повідомлення',
'%d непрочитаних повідомлень',
$непрочитане),
$непрочитане)?>
</h2>
<?php endif ?>
</div>
<h1><?=gettext('Introduction')?></h1>
<p><?=gettext('Ми зараз перекладаємо деякі рядки')?></p>gettext() просто перекладає msgid на відповідний msgstr для даної мови. Є також
скорочена функція _(), яка працює так само;ngettext() робить те саме, але з правилами множини;dgettext() і dngettext(), які замінити домен для одного
виклик. Докладніше про налаштування домену в наступному прикладі.i18n_setup.php, як використовується вище), правильний вибір мови та налаштування Gettext<?php
/**
* Перевіряє, чи даний $locale підтримується проектом
* @param рядок $locale
* @return bool
*/
функція valid($locale) {
return in_array($locale, ['en_US', 'en', 'pt_BR', 'pt', 'es_ES', 'es']);
}
//встановлення вихідної/замовної мови для інформаційних цілей
$lang = 'en_US';if (isset($_GET['lang']) && valid($_GET['lang'])) {
// локаль можна змінити за допомогою рядка запиту
$lang = $_GET['lang']; //ви повинні продезінфікувати це!
setcookie('lang', $lang); //зберігається у файлі cookie, тому його можна використовувати повторно
} elseif (isset($_COOKIE['lang']) && valid($_COOKIE['lang'])) {
// якщо присутній файл cookie, давайте просто збережемо його
$lang = $_COOKIE['lang']; //ви повинні продезінфікувати це!
} elseif (isset($_SERVER['HTTP_ACCEPT_LANGUAGE'])) {
// замовчуванням: пошук мов, які, за словами браузера, користувача користувача
$langs = explode(',', $_SERVER['HTTP_ACCEPT_LANGUAGE']);
array_walk($langs, функція (&$lang) { $lang = strtr(strtok($lang, ';'), ['-' => '_']); });
foreach ($langs як $browser_lang) {
if (valid($browser_lang)) {
$lang = $browser_lang;
розрив;
}
}
}
// тут ми шукаємо глобальну системну локаль з урахуванням знайденої мови
putenv("LANG=$lang");
// це може бути корисним для функції дати (LC_TIME) або форматування грошей (LC_MONETARY), наприклад
setlocale(LC_ALL, $lang);
// це змусити Gettext шукати ../locales/<lang>/LC_MESSAGES/main.mo
bindtextdomain('main', '../locales');
// вказує, у якому кодуванні має бути прочитаний файл
bind_textdomain_codeset('main', 'UTF-8');
// якщо ваша програма має додаткові домени, як уже згадувалося раніше, вам також слід зв’язати їх тут
bindtextdomain('форум', '../локалі');
bind_textdomain_codeset('форум', 'UTF-8');
// тут ми вказуємо домен за замовчуванням, на який відповідають виклики gettext().
textdomain('main');
// це буде шукати рядок у forum.mo замість main.mo
// echo dgettext('forum', 'Ласкаво просимо назад!');
?>Однією з великих переваг Gettext над спеціальними пакетами фреймворка i18n є його широкий і потужний формат файлів. “О, чувак, це досить важко зрозуміти та редагувати вручну, простий масив був би легшим!” Не помилитися, такі програми, як [Poedit] тут, щоб допомогти - багато. Ви можете отримати програму з [їхнього веб-сайту][poedit_download], це безкоштовно та доступно для всіх платформ. Це досить простий інструмент, до якого можна звикнути, і водночас дуже потужний час – використання всіх доступних функцій Gettext. Цей посібник базується на PoEdit 1.8.
Під час першого запуску вам слід вибрати в меню «Файл > Створити…». Вас одразу запитають про мову:
тут ви можете вибрати/відфільтрувати мову, якою ви хочете перекласти, або використати формат, який ми згадували раніше, наприклад
en_US або pt_BR.
Збережіть файл, використовуючи цю структуру каталогів, яку ми також згадували. Потім слід натиснути «Витягти з джерела»,
і тут ви налаштовуєте різні параметри для завдань вилучення та перекладу. Ви можете знайти все це
Пізніше через «Каталог > Властивості»:- Вихідні шляхи: тут ви повинні включити всі папки з проекту, де викликаються gettext() (і братів і сестер) - це
зазвичай це папка(и) шаблонів/переглядів. Це єдине обов’язкове налаштування;
gettext() і подібні функції у кількох
мови програмування, але ви також можете створити власні функції перекладу. Ви їх додасте тут
інші методи. Про це йтиметься пізніше в розділі «Поради».Після встановлення цих точок він запустить сканування ваших вихідних файлів, щоб знайти всі виклики локалізації. Після кожного сканування PoEdit відобразити підсумок того, що було знайдено та що було видалено з вихідних файлів. Нові записи будуть подані пусті в таблицю перекладу, і ви почнете вводити локалізовані версії цих рядків. Збережіть його та .mo файл буде (повторно) скомпільовано в ту саму папку, і так: ваш проект інтернаціоналізовано.
Як ви могли помітити, раніше існують два основних типи локалізованих рядків: прості та рядки з множиною. форми. Перші просто мають два поля: джерело та локалізований рядок. Вихідний рядок не можна змінити як Gettext/Poedit не відповідає повноважень змінювати ваші вихідні файли - вам слід змінити вихідний код і повторно відсканувати файли. Порада: ви можете клацнути правою кнопкою миші рядок перекладу, і він підкаже вам вихідні файли та рядки, де це рядок використання. З іншого боку рядки форми множини включають два поля для відображення двох вихідних рядків і вкладок, щоб ви могли налаштувати різні різні форми.
Щоразу, коли ви змінюєте свої джерела та потребуєте оновити переклади, просто натисніть «Оновити», і Poedit повторно відсканує код, видалення неісних записів, об’єднання змінених і додавання нових. Він також може спробувати вгадати деякі перекладів на основі інших ваших перекладів. Ці відгадки та змінені записи отримують маркер «Нечіткість», вказуючи, що його потрібно переглянути, у списку відображуватися золотим кольором. Це також корисно, якщо у вас є команда перекладачів і хтось намагається написати щось, у чому вони не впевнені: просто позначте Fuzzy, і хтось інший перегляне пізніше.
Нарешті, радимо залишити позначку «Перегляд > Спочатку неперекладені записи», оскільки це допоможе вам багато не забути будь-який запис. У цьому меню ви також можете відкрити частини інтерфейсу користувача, які дозволяють залишити контекстну інформацію для перекладачі, якщо потрібно.
Якщо ви використовуєте PHP як модуль Apache (mod_php), ви можете виявити проблеми з кешуванням файлу .mo. Це
відбувається під час першого читання, а потім, щоб оновити його, вам можна знадобитися перезапустити сервер. На Nginx і PHP5 це
потрібно лише кілька оновлень сторінок, щоб оновити кеш перекладу, а на PHP7 це потрібно.#### Додаткові допоміжні функції
На думку багатьох людей, простіше використовувати _() замість gettext(). Багато спеціальних бібліотек i18n з
Фреймворки також потрібно щось подібне до t(), щоб зробити перекладений код коротшим. Однак це єдина функція
що спортивний ярлик. Ви можете додати до свого проекту деякі інші, наприклад __() або _n() для ngettext(),
або, можливо, вигадливий _r(), який приєднався до викликів gettext() і sprintf(). Інші бібліотеки, як напр
Gettext [php-gettext] [php-gettext] також надає такі допоміжні функції.
У таких випадках вам потрібно буде вказати утиліту Gettext, як витягнути рядки з цих нових функцій.
Не бійся; це дуже легко. Це лише поле у файлі .po або налаштування екрану в Poedit. У редакторі
ця опція знаходиться в середині «Каталог > Властивості > Вихідні ключові слова». Пам’ятайте: Gettext вже знає стандартні функції
для багатьох мов, тому не бійтеся, якщо цей список здасться порожнім. Ви повинні включити туди їх характеристики
нові функції в [певному форматі][func_format]:
t(), що просто повертає переклад для рядка, ви можете вказати його як t.
Gettext знаєте, що єдиним аргументом функції є рядок, який потрібно перекласти;__('one user', '%d users', $number),
специфікація буде __:1,2, яка перша форма є першим аргументом, а друга форма – іншим
аргумент. Якщо натомість вашого числа є першим аргументом, специфікація буде __:2,3, що вказує на те, що перша форма є
другий аргумент і так далі.Після включення цих нових правил у файл .po нове сканування введе ваші нові рядки так само легко, як і раніше.
З Вікіпедії:
Ін’єкція залежностей — це шаблон розробки програмного забезпечення, який дозволяє видалити жорстко закодовані залежності та робить можна змінити їх під час виконання чи під час компіляції.
Ця цитата робить концепцію досить складною, ніж вона є насправді. Ін’єкція залежностей забезпечує a компонент із його залежностями впровадження через конструктора, виклики методів або налаштування влади. Це так так просто.
Ми можемо продемонструвати концепцію простим, але наївним прикладом.
Тут ми маємо клас Database, який потрібен адаптер для спілкування з базою даних. Ми створюємо екземпляр адаптера в
конструктор і створити жорстку залежність. Це ускладнює тестування та означає, що клас Database дуже високий
підключений до адаптера.
<?php
простір імен База даних;
клас База даних
{
захищений $адаптер;
публічна функція __construct()
{
$this->adapter = новий MySqlAdapter;
}
}
клас MysqlAdapter {}Цей код можна переробити для використання Dependency Injection і таким чином послабити залежність. Тут ми вставляємо залежність у конструктор і використовуємо [promotion властивості конструктора][php-constructor-promotion], щоб він був доступний як владність у всьому класі:
<?php
простір імен База даних;
клас База даних
{
публічна функція __construct(protected MySqlAdapter $adapter)
{
}
}
клас MysqlAdapter {}Тепер ми надаємо класу Database його залежність, а не створюємо його самого. Ми навіть могли б створити метод
який би прийняв аргумент відносно та встановив його таким чином, або якщо владність $adapter була public, ми
можна встановити разом.
[php-constructor-promotion]: https://www.php.net/manual/en/language.oop5.decon.php#language.oop5.decon.constructor.promotion
Якщо ви коли-небудь читали про впровадження захворювань, то, напевно, бачили терміни «Інверсія контролю» або “Принцип інверсії залежностей”. Це складні проблеми, які вирішує Dependency Injection.
Інверсія контролю – це, як там сказано, «інвертування контролю» системи шляхом повного збереження організаційного контролю окремо від наших об’єктів. З точки зору впровадження залежностей, це означає послаблення наших залежностей шляхом контролю та створюючи їх в іншому місці системи.
Протягом багатьох років фреймворки PHP досягли інверсії керування, однак постало питання, яка частина контролю ми інвертуємо і куди? Наприклад, фреймворки MVC фактично надають супероб’єкт або базовий контролер що інші контролери повинні розширити, щоб отримати доступ до його залежностей. Однак це є інверсія контролю, замість того, щоб послабити відносини, цей метод просто перемістив їх.
Впровадження залежностей дозволяє нам більш елегантно вирішити цю проблему, вставляючи лише потрібні нам залежності, коли ми вони потрібні, без жодних жорстко закодованих залежностей взагалі.
Принцип єдиної відповідальності стосується акторів і архітектури високого рівня. У ньому сказано, що «клас повинен мати лише одна причина змінитися». Це означає, що кожен клас повинен лише відповідати за одну частину функціональні можливості, які надає програмне забезпечення. Найбільша перевага цього підходу полягає в тому, що він дозволяє покращити код повторне використання. Спроектувавши наш клас для виконання лише однієї речі, ми можемо використовувати (або повторно використовувати) його в будь-якій іншій програмі без цього змінюючи його.
Принцип відкритості/закритості стосується дизайну класу та розширення функцій. У ньому зазначено, що «програмні сутності (класи, модулі, функції тощо) мають бути відкритими для розширення, але закритими для модифікації». Це означає, що ми повинні проектувати наші модулі, класи та функції таким чином, що коли потрібна нова функціональність, ми не повинні змінювати існуючу коду, а замість того, щоб написати новий код, який використовуватиметься існуючим кодом. Практично це означає, що ми повинні писати класи, які реалізують і дотримуються інтерфейсів, потім введіть підказку проти цих інтерфейсів замість конкретних класів.
Найбільшою перевагою цього підходу є те, що ми можемо дуже легко розширити наш код підтримкою чогось нового без нього необхідно змінити існуючий код, що означає, що ми можемо скоротити час перевірки якості та ризик негативного впливу на програму суттєво зменшується. Ми можемо розгорнути новий код швидше та з більшою впевненістю.
Принцип заміни Ліскова стосується підтипу та успадкування. У ній зазначено, що «Дитячі заняття ніколи не повинні перериватися визначення типу батьківського класу». Або, за словами Роберта С. Мартіна, «Підтипи повинні бути замінними на свою базу типи».
Наприклад, якщо у нас є інтерфейс FileInterface, який використовує метод embed(), і ми маємо Audio і Video
класів, які зловживають реалізацією інтерфейсу FileInterface, то ми можемо очікувати, що використання методу embed() завжди
зробити те, що ми маємо намір. Якщо пізніше ми створимо клас PDF або клас Gist, які реалізують FileInterface
інтерфейсу, ми вже будемо знати та розуміти, що робитиме метод embed(). Найбільша перевага цього підходу
існує в тому, що ми маємо можливість створювати гнучки та легко налаштовані програми, після чого ми змінюємо один об’єкт
тип (наприклад, FileInterface) на інший, нам не потрібно нічого змінювати в нашій програмі.
має бути зобов’язаний залежати від методів, які він не використовує». Це означає, що замість єдиного монолітного інтерфейсу які повинні реалізувати відповідні класи, замість цього ми повинні надати набір менших, специфічних для концепції інтерфейсів що відповідний клас реалізує один або більше з.
Наприклад, клас Car або Bus буде цікавим у методі steeringWheel(), але Motorcycle або Tricycle
клас не буде. І навпаки, клас Motorcycle або Tricycle буде цікавий у методі handlebars(), але
Клас Car або Bus не буде. Немає необхідності, щоб усі ці типи транспортних засобів підтримували обидва
steeringWheel(), а також handlebars(), тому ми повинні розбити вихідний інтерфейс.
Принцип інверсії залежностей стосується усунення жорстких зв’язків між окремими класами, щоб нові функції могли використовувати, пройшовши інший клас. У ньому сказано, що слід «Залежити від абстракцій. Не залежати від конкременти».. Простіше кажучи, це означає, що наші залежності повинні бути інтерфейсами/контрактами або абстрактними класами, а не конкретні реалізації. Ми можемо легко змінити наведений вище приклад, щоб слідувати цьому принципу.
<?php
простір імен База даних;
клас База даних
{
публічна функція __construct(protected AdapterInterface $adapter)
{
}
}
інтерфейс AdapterInterface {}
клас MysqlAdapter реалізує AdapterInterface {}Існує кілька переваг класу Database, які тепер залежать від інтерфейсу, а не конкреції.
Вважайте, що ми працюємо в команді, а над адаптером працює колега. У нашому першому прикладі ми довелося б зачекати, поки згаданий колега закінчить адаптер, перш ніж ми зможемо належним чином познущатися над ним для наших модульних тестів. Зараз що залежність – це інтерфейс/контракт, ми можемо радісно висміювати цей інтерфейс, знаючи, що наш колега створить адаптер на основі цього договору.
Ще більшою перевагою цього методу є те, що наш код тепер набагато більш масштабований. Якщо через рік ми вирішимо що ми хочемо перейти до іншого типу бази даних, ми можемо написати адаптер, який реалізує оригінальний інтерфейс і вводить, що натомість більше не буде потрібно рефакторинг, оскільки ми можемо гарантувати, що адаптер дотримується контракту встановлюється інтерфейсом.
Перше, що вам слід зрозуміти про контейнери ін’єкцій залежностей, це те, що це не те саме Ін’єкція незалежності. Контейнер — це зручна утиліта, яка допоможе нам реалізувати ін’єкцію залежностей, однак вони можуть бути та часто неправильно використані для реалізації антишаблону, Service Location. Впровадження контейнера DI як служби Можливо, локатор у ваших класах створює більш жорстку залежність від контейнера, ніж залежність, яку ви замінюєте. Це також робить ваш код менш прозорим і, зрештою, важчим для тестування.
Більшість сучасних фреймворків мають власний контейнер ін’єкції залежностей, який дозволяє об’єднувати ваші залежності разом через конфігурацію. На практиці це означає, що ви можете написати максимально чистий код програми відокремлений як каркас, на якому він побудований.
Багато разів ваш код PHP використовує базу даних для збереження інформації. У вас є кілька варіантів підключення та взаємодії з вашою базою даних. Рекомендованим варіантом до PHP 5.1.0 було використано власні драйвери, такі як mysqli, pgsql, mssql тощо.
Рідні драйвери чудові, якщо ви використовуєте лише одну базу даних у своїй програмі, але якщо, наприклад, ви використовуєте MySQL і трохи MSSQL, або вам потрібно підключитися до бази даних Oracle, тоді ви не зможете використовувати однакові драйвери. Вам потрібно буде вивчити абсолютно новий API для кожної бази даних — і це може стати безглуздим.
Розширення [mysql] для PHP неймовірно старе, його замінили два інших розширення:
Розробка [mysql] не тільки минула давно, але й було [офіційно видалено в PHP 7.0][mysql_removed].
Щоб не копіюватись у своїх налаштуваннях php.ini, щоб побачити, який модуль ви використовуєте, одним із варіантів є пошук mysql_*
у обраному вами редакторі. Якщо з’явилися такі функції, як mysql_connect() і mysql_query(), то mysql є
у використанні.
Крім того, якщо ви не використовуєте PHP 7.x або новішу версію, якщо не вважаєте це оновлення найвищим, це призведе до більшої труднощі, коли все-таки відбудеться оновлення PHP. Найкращий варіант – замінити використання mysql на [mysqli] або [PDO]. ваші додатки в рамках ваших власних розробок графіків, щоб потім вас не поспішали.
Якщо ви оновлюєте [mysql] до [mysqli], слідкуйте за оновленнями ледачих посібників, які пропонують просто знайти та замінити mysql_* на mysqli_*. Мало того, що це посилене спрощення, воно втрачає переваги, які дає mysqli, наприклад зв’язування параметрів, яке також пропонується в [PDO][pdo].
PDO — це бібліотека абстракцій підключення до бази даних — вбудована в PHP версії 5.1.0 — забезпечує загальний интерфейс для общения с большим количеством баз данных. Наприклад, ви можете використовувати в основному ідентичний код для взаємодії MySQL або SQLite:
<?php
// PDO + MySQL
$pdo = new PDO('mysql:host=example.com;dbname=database', 'user', 'password');
$statement = $pdo->query("SELECT some_field FROM some_table");
$row = $statement->fetch(PDO::FETCH_ASSOC);
echo htmlentities($row['some_field']);
// PDO + SQLite
$pdo = новий PDO('sqlite:/path/db/foo.sqlite');
$statement = $pdo->query("SELECT some_field FROM some_table");
$row = $statement->fetch(PDO::FETCH_ASSOC);
echo htmlentities($row['some_field']);PDO не перекладаємо ваші запити SQL або емулюємо відсутні функції; це спеціально для підключення до кількох типів бази даних з тим самим API.
Що ще важливо, PDO дозволяє безпечно вводити сторонні дані (наприклад, ідентифікатори) у ваші запити SQL, не турбуючись
про атаки SQL-ін’єкції бази даних.
Це можливо за допомогою операторів PDO та зв’язаних параметрів.
Припустимо, скрипт PHP отримує числовий ідентифікатор як параметр запиту. Цей ідентифікатор слід використовувати для отримання запису користувача
з бази даних. Це wrong спосіб зробити це:
<?php
$pdo = новий PDO('sqlite:/path/db/users.db');
$pdo->query("ВИБРАТИ ім'я FROM користувача WHERE id = ". $_GET['id']); // <-- НІ!Це жахливий код. Ви вставляєте необроблений параметр запиту в запит SQL. Це дозволяє вам зламати a
heartbeat, використовуючи практику під назвою SQL Injection. Тільки уявіть, якщо хакер передає винахідливий параметр id через
виклик URL-адреси на зразок http://domain.com/?id=1%3BDELETE+FROM+users. Установіть змінну $_GET['id'] на 1;DELETE
FROM users, яка видалить усіх ваших користувачів! Натомість вам слід очистити введений ідентифікатор за допомогою параметрів, пов’язаних із PDO.
<?php
$pdo = новий PDO('sqlite:/path/db/users.db');
$stmt = $pdo->prepare('ВИБРАТИ ім'я FROM користувача WHERE id = :id');
$id = filter_input(INPUT_GET, 'id', FILTER_SANITIZE_NUMBER_INT); // <-- спочатку фільтруйте дані (див. [Фільтрування даних](#data_filtering)), особливо важливо для ВСТАВЛЕННЯ, ОНОВЛЕННЯ тощо.
$stmt->bindParam(':id', $id, PDO::PARAM_INT); // <-- Автоматично очищається для SQL PDO
$stmt->виконати();Це правильний код. Він використовує зв’язаний параметр у заяві PDO. Це екранує іноземний ідентифікатор, введений перед ним введено в базу даних, запобігаючи атакам SQL-ін’єкцій.
Для записів, таких як INSERT або UPDATE, особливо важливо спочатку фільтрувати свої дані і очистити їх для інших речей (видалення тегів HTML, JavaScript тощо). PDO очистити його лише для SQL, а не для вашої програми.
Вам також слід пам’ятати, що з’єднання з базою даних виробляють ресурси, і наявність ресурсів не була чимось нечуваним. вичерпується, якщо зв’язки не були явно закриті, однак це було більш поширеним на інших мовах. Використовуючи PDO, ви можете неявно закрити з’єднання, знищивши об’єкт, переконавшись, що всі решта посилань на нього видалено, тобто. встановити значення NULL. Якщо ви не зробите це явно, PHP автоматично закриє з’єднання, коли ваш сценарій завершиться - якщо, звичайно, ви не використовуєте постійні підключення.
Коли розробники вперше починають вивчати PHP, вони часто змішують його взаємодію з базою даних логіка представлення, використовуючи код, який можна виглядати так:
<ul>
<?php
foreach ($db->query('SELECT * FROM table') as $row) {
echo "<li>".$row['field1']." - ".$row['field1']."</li>";
}
?>
</ul>Це погана практика з багатьох причин, головним чином через те, що її важко налагодити, важко перевірити, важко прочитати, і це виводитиме багато полів, якщо ви не обмежите їх.
існує хоча багато інших рішень для цього – залежно від того, чи ви віддаєте перевагу ООП чи функціональне програмування - має бути якийсь елемент розділення.
Розглянемо найпростіший крок:
<?php
функція getAllFoos($db) {
return $db->query('SELECT * FROM table');
}
$результати = getAllFoos($db);
foreach ($results as $row) {
echo "<li>".$row['field1']." - ".$row['field1']."</li>"; // ПОГАНО!!
}Це хороший початок. Помістіть ці два елементи в два різні файли, і ви отримаєте чітке розділення.
Створіть клас, щоб розповісти цей метод, і у вас буде «Модель». Створіть простий файл .php, щоб розмістити презентацію
логіка, і ви маєте “Вид”, який дуже схожий на MVC - звичайну ООП-архітектуру для незалежної
frameworks.
foo.php
<?php
$db = new PDO('mysql:host=localhost;dbname=testdb;charset=utf8mb4', 'ім'я користувача', 'пароль');
// Зробити свою модель доступною
include 'models/FooModel.php';
// Створення екземпляра
$fooModel = новий FooModel($db);
// Отримати список Foos
$fooList = $fooModel->getAllFoos();
// Показати вигляд
включати 'views/foo-list.php';models/FooModel.php
<?php
клас FooModel
{
публічна функція __construct(захищений PDO $db)
{
}
публічна функція getAllFoos() {
return $this->db->query('SELECT * FROM table');
}
}views/foo-list.php
<?php foreach ($fooList як $row): ?>
<li><?= $row['field1'] ?> - <?= $row['field1'] ?></li>
<?php endforeach ?>По суті, це те саме, що роблять більшість сучасних фреймворків, хоча й трохи більше вручну. Ви можете ні потрібно робити все це щоразу, але змішування надто великої кількості логіки презентації та взаємодії з базою даних може бути а справжня проблема, якщо ви коли-небудь захочете модульне тестування вашої програми.
Багато фреймворків дають власний рівень абстракції, який може розміщуватися поверх PDO, а може й ні. Це часто емулювати функції для однієї системи бази даних, яких немає в інших, загортаючи ваші запити в методі PHP, даючи ви фактичну абстракцію бази даних, а не просто абстракцію з’єднання, яку надає PDO. Це, звичайно, додасть a невеликі витрати, але якщо ви створите портативну програму, яка повинна працювати з MySQL, PostgreSQL і SQLite тоді невеликі накладні витрати будуть того варті заради чистоти коду.
Деякі рівні абстракції були створені з використанням стандартів простору з іменем PSR-0 або PSR-4, тому їх можна встановіть в будь-якій програмі, яка вам подобається:
Шаблони забезпечують зручний спосіб відокремлення контролера та логіки домену від логіки презентації. Шаблони традиційно відрізняються від HTML вашої програми, але також можуть використовуватися для інших форматів, наприклад XML. Шаблони часто називають «представленнями», які складають частину другого компонента model–view–controller (MVC) шаблон архітектури програмного забезпечення.
Основна перевага використання шаблонів полягає в тому, що вони створюють чіткий розподіл між логікою презентації та рештою ваша заявка. Шаблони несуть виключну відповідальність за відображення форматованого вмісту. Вони не відповідають за пошук даних, збереження або інші складніші завдання. Це веде до більш чистого та читабельного коду, що особливо важливо корисно в командному середовищі, де розробники працюють над кодом на стороні сервера (контролери, моделі), а дизайнери працюють над клієнтський код (розмітка).
Шаблони також покращують організацію коду презентації. Кожен шаблон постійно розміщується в папці “views”. визначені в одному файлі. Цей підхід заохочує повторне використання коду, якщо більші блоки коду розбиваються на менші, шматки багаторазового використання, які часто називають частковими. Наприклад, верхній і нижній колонтитул вашого сайту можна використовувати як шаблони, які потім включаються перед і після кожного шаблону сторінки.
Нарешті, залежно від бібліотеки, яку ви використовуєте, шаблони можуть запропонувати більший захист, автоматично виходячи з створеного користувачем вміст. Деякі бібліотеки навіть пропонують пісочницю, де дизайнери шаблонів мають доступ лише до білого списку змінні та функції.
Звичайні шаблони PHP — це просто шаблони, які забирають рідний код PHP. Вони є природним вибором, після чого PHP насправді є сама мова шаблону. Це просто означає, що ви можете підключити код PHP до іншого коду, наприклад HTML. Це є корисно для розробників PHP, немає нового синтаксису для вивчення, вони знають доступні їм функції та їхні редактори коду вже мають підсвічування синтаксису PHP і вбудоване автозавершення. Крім того, звичайні шаблони PHP, як правило, є дуже швидко, після не потрібен етап компіляції.
Кожен сучасний фреймворк PHP використовує певну систему шаблонів, серед яких для замовчування використовується звичайний PHP. За межами фреймворки, бібліотеки, такі як Plates або Aura.View полегшують роботу з простими шаблонами PHP, пропонує такі сучасні функції шаблонів, як успадкування, макети та розширення.
Використання бібліотеки [Plates][пластини].
<?php // user_profile.php ?>
<?php $this->insert('header', ['title' => 'Профіль користувача']) ?>
<h1>Профіль користувача</h1>
<p>Вітаємо, <?=$this->escape($name)?></p>
<?php $this->insert('footer') ?>Використання бібліотеки [Plates][пластини].
<?php // template.php ?>
<html>
<голова>
<title><?=$title?></title>
</head>
<тіло>
<головний>
<?=$this->section('content')?>
</main>
</body>
</html><?php // user_profile.php ?>
<?php $this->layout('template', ['title' => 'Профіль користувача']) ?>
<h1>Профіль користувача</h1>
<p>Вітаємо, <?=$this->escape($name)?></p>на те, що PHP перетворився на зрілу об’єктно-орієнтовану мову, він не значно покращився як мова шаблонів. Зкомпільовані шаблони, такі як Twig, Brainy або Smarty*, заповнюють цю породу, пропонуючи новий синтаксис, який розроблено спеціально для створення шаблонів. Від автоматичного екранування до успадкування та спрощених структур керування, скомпільовані шаблони розроблено таким чином, щоб їх було легше писати, чистіше читати та безпечніше використовувати. Скомпільовані шаблони можуть бути навіть поширені іншими мовами, Mustache є хорошим прикладом цього. Так як ці шаблони повинні бути скомпільовані є невелике зниження продуктивності, однак воно дуже мінімальне, якщо використовується належне кешування.
*Хоча Smarty пропонує автоматичний вихід, ця функція НЕ ввімкнена за умовчанням.
Використання бібліотеки Twig.
{% include 'header.html' with {'title': 'User Profile'} %}
<h1>Профіль користувача</h1>
<p>Вітаємо, {{ name }}</p>
{% include 'footer.html' %}Використання бібліотеки Twig.
// template.html
<html>
<голова>
<title>{% block title %}{% endblock %}</title>
</head>
<тіло>
<головний>
{% block content %}{% endblock %}
</main>
</body>
</html>// user_profile.html
{% extends "template.html" %}
{% block title %}Профіль користувача{% endblock %}
{% block content %}
<h1>Профіль користувача</h1>
<p>Вітаю, {{ name }}</p>
{% endblock %}У багатьох мовах програмування, які складаються з великої кількості, щоразу, коли щось йде не так, створюється виняток. Це є безумовно, це життєздатний спосіб робити речі, але PHP — це мова програмування з “виключеннями”. Поки має підсумки та більша частина ядра намагається використовувати їх під час роботи з об’єктами, більша частина самого PHP намагається зберегти обробка незалежно від того, що відбувається, якщо не виникає фатальна помилка.
Наприклад:
$ php -a
php > echo $foo;
Примітка: невизначена змінна: foo у коді клітини php у рядку 1Це лише повідомлення про помилку, і PHP із задоволенням продовжить роботу. Це може заплутати тих, хто приїжджає з Мови зі «значним числом видів», тому що посилання на відсутню зміну в Python, наприклад, призведе до виключення:
$ python
>>> надрукувати foo
Traceback (останній останній виклик):
Файл "<stdin>", рядок 1, у <module>
NameError: ім'я 'foo' не визначеноЄдина справжня різниця виникає в тому, що Python злякається через будь-яку дрібницю, тому розробники можуть бути дуже впевнені, що виявлено певну проблему або крайній випадок, тоді як PHP продовжить обробку, якщо не стане щось екстремальне, вказати, що він видасть помилку та повідомити про це.
PHP має кілька рівнів серйозності помилок. Три найпоширеніші типи повідомлень: помилки, повідомлення та попередження.
Вони мають різні рівні тяжкості; E_ERROR, E_NOTICE і E_WARNING. Помилки — це фатальні помилки під час виконання та
зазвичай викликані помилками у вашому коді, і їх потрібно виправити, після чого вони призведуть до припинення виконання PHP. Повідомлення є
консультаційні повідомлення, викликані кодом, який може або не може викликати проблеми під час виконання сценарію, виконання
не зупинено. Попередження — це нефатальні помилки, виконання сценарію не буде зупинено.
Іншим типом повідомлень про помилки, які виникають під час компіляції, є повідомлення E_STRICT. Ці повідомлення використано для пропозицій
зміни у вашому коді, щоб забезпечити найкращу взаємодію та пряму сумісність із майбутніми версіями PHP.
Повідомлення про помилки можна змінити за допомогою налаштувань PHP та/або викликів функцій PHP. Використання вбудованої функції PHP
error_reporting() ви можете встановити рівень помилок протягом тривалості виконання сценарію, передавши один із
визначені постійні рівні помилок, тобто якщо ви хочете побачити лише помилки та попередження, але не сповіщення, тоді ви можете
на вибір це:
<?php
error_reporting(E_ERROR | E_WARNING);Ви також можете контролювати, чи помилки відображаються на екрані (добре для розробки), чи приховуються, і реєструються (придатний для виробництва). Щоб дізнатися більше про це, перегляньте розділ [Звіт про помилку][звіт про помилку].
Ви також можете наказати PHP придушувати певні помилки за допомогою оператора керування помилками @. Ви ставите цього оператора на
початок виразу, а будь-яка помилка, яка є прямим результатом виразу, мовчиться.
<?php
echo @$foo['bar'];Це виведе $foo['bar'], якщо він існує, але просто поверне нуль і нічого не виведе, якщо змінено $foo або
Ключ 'bar' не існує. Без оператора керування помилками цей вираз міг би створити повідомлення «PHP Notice: Undefined».
змінна: foo or PHP Примітка: невизначений індекс: помилка рядка.Це може здатися гарною ідеєю, але є кілька небажаних компромісів. PHP обробляє вирази за допомогою @ в a
менш продуктивний спосіб, ніж вирази без @. Передчасна оптимізація може бути основою всього програмування
аргументи, але якщо продуктивність особливо важлива для вашої програми/бібліотеки, важливо зрозуміти
слідки роботи оператора контролю помилок.
По-друге, оператор контролю помилок повністю ковтає помилку. Помилка не відображається, а помилка є не відправлено в журнал помилок. Крім того, стандартні/виробничі системи PHP не мають можливості вимкнути оператор контролю помилок. Поки Можливо, ви праві, що помилка, яку ви бачите, є нешкідливою, іншою, нешкідлива помилка буде так само мовчазною.
Якщо є спосіб уникнути оператора придушення помилок, вам слід його розглянути. Наприклад, наш код вище може бути таким переписано так:
<?php
// Нульовий оператор об'єднання
echo $foo['bar'] ?? '';Один із відвідувачів, коли придушення помилок може мати сенс, якщо fopen() не може знайти файл для завантаження. Ви можете перевірити
для перегляду файлу до того, як ви намагаєтеся його завантажити, але файл буде видалено після перевірки та перед
fopen() (що може здатися неможливим, але це може трапитися), тоді fopen() поверне false і видасть помилку. Це
це показано те, що PHP повинен вирішувати, але це один випадок, коли придушення помилок може здатися єдиним дійсним
рішення.
Раніше ми згадували, що в базовій системі PHP немає можливості вивести оператор контролю помилок. Однак Xdebug має
параметр xdebug.scream ini, який вимкне оператор контролю помилок. Ви можете встановити це за допомогою файлу php.ini
з наступним.
xdebug.scream = УвімкВи також можете встановити це значення під час виконання за допомогою функції ini_set
<?php
ini_set('xdebug.scream', '1')Це найбільше корисно, коли ви налагоджуєте код і відчуваєте, що інформаційна помилка прихована. Використовуйте крик обережно, і як тимчасовий інструмент налагодження. Є багато бібліотечного коду PHP, який не може працювати з оператором контролю помилок вимкнено.
PHP здатний успішно програмувати зі «значною кількістю» і потребує лише кілька рядків коду, щоб
зробити перемикач. По суті ви можете видавати свої «помілки» як «винятки», використовуючи клас ErrorException, який розширює
клас Exception.
Це звичайна практика, реалізована великою кількістю сучасних фреймворків, таких як Symfony і Laravel. У налагодженні режим (або режим розробника) обидва ці фреймворки відображають гарну та чисту трасування стека.
Також доступні деякі пакети для кращого лікування помилок і випадків, а також звітування. Як [Ой!], який постачається разом із інсталяцією Laravel для замовчування, а також може використовуватися в будь-якому фреймворку.
Викидаючи помилки як є в розробці, ви можете впоратися з ними краще, ніж звичайний результат, і якщо ви бачите іншим під час розробки ви можете загорнути його в операторі catch із конкретними інструкціями щодо обробки місце. Кожен виключений випадок, який ви миттєво перехоплюєте, робить вашу програму трохи надійнішою.
Додаткову інформацію про це та детальну інформацію про те, як використовувати ErrorException із обробкою помилок можна знайти на
ErrorException Клас.
error_reporting()][повідомлення про помилку]Вінятки є стандартною частиною необхідних популярних мов програмування, але програми PHP їх часто не помічають. Такі мови, як Ruby, надзвичайно важкі для видів, тому щоразу, коли щось піде не так, як-от помилка запиту HTTP або запит БД пішов не так, або навіть якщо зображення ресурсу не вдалося знайти, Ruby (або дорогоцінні камені, що використовують) видасть виняток на екрані означає, що ви миттєво бачите, що є помилка.
Сам PHP досить слабкий із цим, і виклик file_get_contents() зазвичай просто принесе вам FALSE і
попередження.
Багато старших фреймворків PHP, як-от CodeIgniter, просто повертають false, реєструють повідомлення до своїх власних журналів і, можливо,
дозволити вам використовувати такий метод, як $this->upload->get_error(), щоб побачити, що пішло не так. Проблема тут у тому, що ви повинні піти
шукайте помилку та перевіряйте документи, щоб побачити, який метод його помилки для цього класу, замість того, щоб зробити
надзвичайно очевидно.
Інша проблема полягає в тому, що класи автоматично видають помилку на екран і виходять з процесу. Коли ви робите це ви заборонити іншому розробнику динамічно виправляти цю помилку. Слід робити винятки, щоб зробити a розробник знає про помилку; потім вони можуть вибрати, як це зробити. наприклад:
<?php
$email = новий Fuel\Email;
$email->subject('Моя тема');
$email->body('Як ти, біса?');
$email->to('guy@example.com', 'Some Guy');
пробувати
{
$email->send();
}
catch(Fuel\Email\ValidationFailedException $e)
{
// Помилка перевірки
}
catch(Fuel\Email\SendingFailedException $e)
{
// Драйвер не зміг надіслати електронний лист
}
нарешті
{
// Виконується незалежно від того, чи був викинутий виняток, і до відновлення нормального виконання
}Загальний клас Exception надає дуже мало контексту накладання для розробника; однак, щоб виправити це, це
можна створити спеціалізований тип Exception за підкласом загального класу Exception:
<?php
class ValidationException extends Exception {}Це означає, що ви можете додати кілька блоків catch і по-різному обробляти різні. Це може призвести до створення багатьох окремих спеціалістів, деяких з яких можна було б уникнути за допомогою деяких SPL надається в розширенні SPL.
Якщо, наприклад, ви використовуєте магічний метод __call() і запитуєте недійсний метод, замість того, щоб кинути
стандартний віняток, який є розливчастим, або створити спеціальний віняток саме для цього, ви можете просто
throw new BadMethodCallException;.
Найкращий ресурс із безпеки PHP, який я знайшов, — це [Посібник зі створення безпечного програмного забезпечення PHP за 2018 рік] (https://paragonie.com/blog/2017/12/2018-guide-building-secure-php-software) [Ініціатива Paragon] (https://paragonie.com/).
Для кожного розробника PHP дуже важливо вивчити основи безпеки веб-додатків, які можуть бути зламані на декілька широких тем:
Є погані люди, готові та готові використовувати вашу веб-програму. Важливо, щоб ви взяли необхідне запобіжні заходи для посилення безпеки вашої веб-програми. На щастя, хороші люди в Проект відкритих веб-додатків безпеки(OWASP) склав вичерпний список відомих проблем безпеки та методи захисту від них. Це обов’язковий для читання розробник, який пікселиться про безпеку. Survive The Deep End: PHP Security Padraic Brady також є ще одним хорошим посібником із безпеки веб-додатків для PHP.
Зрештою кожен створює програму PHP, яка розміщується при вході користувача. Ім’я користувача і паролі зберігаються в a бази даних і пізніше використовувався для автентифікації користувачів під час входу.
Важливо, щоб ви правильно hash паролі перед їх збереженням. Хешування та шифрування — це дві дуже різні речі які часто плутають.
Хешування є необоротною односторонньою функцією. Це створює рядок фіксованої довжини, який не можна реально повернути. Це означає, що ви можете порівняти хеш з іншим, щоб визначити, чи вони обидва походять з одного вихідного рядка, крім вас не може визначити вихідний рядок. Якщо паролі не хешуються і ваша база даних отримує неавторизований доступ третіх сторін, усі облікові записи користувачів тепер зламано.
На відміну від хешування, шифрування є оборотним (за умови, що у вас є ключ). Шифрування корисне в інших сферах, але погане стратегія безпечного зберігання паролів.
Паролі також мають індивідуальні salted, додаючи випадковий рядок до кожного пароля перед хешуванням. Це запобігає словниковим атакам і використовує «нню райдужну таблицю» (зворотний список криптографічних хешів для типових паролів).
Хешування та солізація є життєво важливими, оскільки часто користувачі використовують той самий пароль для кількох служб, і якість пароля може бути низькою.
Крім того, вам слід використовувати спеціалізований алгоритм хешування паролів, а не швидкий, універсальний криптографічна хеш-функція (наприклад, SHA256). Короткий список прийнятих алгоритмів хешування паролів (станом на червень 2018 р.) бути:
На щастя, сьогодні PHP робить це легко.
Хешування паролів за допомогою password_hash
У PHP 5.5 було представлено password_hash(). Зараз він використовує BCrypt, найпотужніший на даний момент алгоритму
підтримуватися PHP. У майбутньому його буде оновлено, якщо підтримувати більше алгоритмів, це необхідно. password_compat
бібліотеку було створено для забезпечення прямої сумісності для PHP >= 5.3.7.
Нижче ми хешуємо рядок, а потім перевіряємо хеш на новий рядок. Тому що наші дві вихідні рядки інші (‘secret-password’ проти ‘bad-password’) цей вхід не вдасться.
<?php
вимагати 'password.php';
$passwordHash = password_hash('секретний-пароль', PASSWORD_DEFAULT);
if (password_verify('bad-password', $passwordHash)) {
// Правильний пароль
} ще {
// Неправильний пароль
}password_hash() підбає про підбір пароля для вас. Сіль зберігається разом з алгоритмом і «вартістю» як частина хешу. password_verify() витягує це, щоб застосувати, як перевірити пароль, тому вам не окреме поле бази даних для зберігання ваших солей.
Ніколи (ніколи) не довіряйте іноземним введенням у ваш код PHP. Завжди дезінфікуйте та перевіряйте іноземні введення перед тим
використовуючи його в коді. Функції filter_var() і filter_input() можуть дезінфікувати текст і перевіряти текстові формати (наприклад,
адреси електронної пошти).
Зовнішнім введенням може бути будь-що: $_GET і $_POST формують вхідні дані, деякі значення в суперглобалі $_SERVER і
Тіло запиту HTTP через fopen('php://input', 'r'). Пам’ятайте, що зовнішній вхід не обмежується даними формами, наданими
користувача. Завантажені та завантажені файли, значення сеансу, даний файл cookie та даний сторінкових веб-сервісів є сторонніми
введення тяжк.
Незважаючи на те, що сторонні дані можна зберігати, комбінувати та отримувати доступ пізніше, вони все одно є зовнішніми введеннями. Щоразу, коли ви обробляєте, вивести, об’єднати або включити дані у свій код, запитайте себе, чи дані відфільтровано належним чином і чи можна їм довіряти.
Дані можуть бути фільтровані по-різному залежно від їх призначення. Наприклад, коли невідфільтрований зовнішній вхід передається в HTML
виводячи сторінки, він може підтримувати HTML і JavaScript на вашому сайті! Це відомо як міжсайтовий сценарій (XSS) і може бути a
дуже небезпечний напад. Один із способів уникнути XSS — очистити всі створені користувачем дані перед виведенням їх на вашу сторінку
видалення тегів HTML за допомогою функції strip_tags() або екранування символів зі спеціальним значенням у відповідних
Сутності HTML із функціями htmlentities() або htmlspecialchars().
Іншим прикладом є передача параметрів для виконання в командному рядку. Це може бути надзвичайно небезпечно (і традиційно
погана ідея), але ви можете використати вбудовану функцію escapeshellarg(), щоб очистити аргументи виконаної команди.
Останній приклад — прийняття стороннього введення для визначення файлу для завантаження з файлової системи. Цим можна скористатися
зміна назви файла на шлях до файла. Вам потрібно видалити "/", "../", null bytes або інші символи з
шлях до файлу, щоб він не міг завантажити закриті, закриті або конфіденційні файли.
filter_varfilter_inputОчищення видаляє (або усуває) недозволені або небезпечні символи з іноземного введення.
Наприклад, вам слід очистити іноземні дані, перш ніж включити їх у HTML або вставити в необроблений SQL-запит. Якщо ви використовуєте зв’язані параметри з PDO, очищайте вхідні дані.
Іноді потрібно дозволити певні безпечні HTML-теги у вхідних даних під час підключення їх до HTML-сторінок. Це дуже важко зробити, і багато хто уникає це, використовуючи інше більш обмежене форматування, наприклад Markdown або BBCode, хоча білий список Бібліотеки на зразок HTML Purifier саме з цієї причини.
Це небезпечно для даних unserialize() від користувачів або інших ненадійних джерел. Це може дозволити зловмісникам створювати екземпляри об’єктів (із визначеними користувачами властивостями), чиї деструктори будуть виконані, навіть, якщо самі об’єкти не використані. Тому слід уникати десеріалізації ненадійних даних.
Використовуйте безпечний стандартний формат обміну даними, наприклад JSON (через json_decode і json_encode), якщо вам потрібно передати серіалізовані дані користувачів.
Перевірка гарантує, що іноземні дані відповідають вашим очікуванням. Наприклад, ви можете перевірити електронну адресу, a номер телефону або вік під час обробки реєстраційного подання.
Під час створення конфігураційних файлів для ваших додатків передові практики рекомендують використовувати один із наведених нижче методів слідував:
.php. Це забезпечення
що, навіть якщо доступ до сценарію прямий, він не буде виведений як простий текст.ПРИМІТКА: Починаючи з PHP 5.4.0, параметр register_globals видалено, і його більше не можна використовувати. Це тільки
включено як попередження для будь-якого в процесі оновлення застарілої програми.
Якщо ввімкнено, параметр конфігурації register_globals створює кілька типів змінених (включно з
$_POST, $_GET і $_REQUEST), доступні в глобальній області вашої програми. Це можна легко привести до безпеки
проблеми, далі ваша програма не може ефективно працювати, звідки надходять на дані.
Наприклад: $_GET['foo'] буде доступним через $foo, який може перевизначати зміни, які були оголошені.
Якщо ви використовуєте PHP < 5.4.0 переконайтеся, що register_globals вимкнено.
Реєстрація помилок може бути корисною для пошуку проблемних місць у вашій програмі, але вона також може відкрити інформацію про структуру вашої програми для зовнішнього світу. Щоб ефективно захистити свою програму від проблем, які можуть бути спричиненим виводом цих повідомлень, вам потрібно налаштувати свій сервер по-різному під час розробки та виробництво (наживо).
Щоб відобразити всі можливості помилки під час розробки, налаштуйте такі параметри у своєму php.ini:
display_errors = Увімк
display_startup_errors = Увімк
error_reporting = -1
log_errors = УвімкненоПередача значення
-1показує всі можливі помилки, навіть нові, якщо рівні та постійні будуть додані в наступний PHP версії. КонстантаE_ALLтакож ведеться таким чином, починаючи з PHP 5.4. - php.net
Помилка постійного рівня E_STRICT була введена в 5.3.0 і не є частиною E_ALL, проте вона стала частиною
E_ALL у 5.4.0. Що це означає? З точки зору повідомлення про всі можливі помилки у версії 5.3 це означає, що ви повинні
використовуйте -1 або E_ALL | E_STRICT.
Повідомлення про можливість усіх помилок за версією PHP
-1 або E_ALL-1 або E_ALL | E_STRICT5.3
-1абоE_ALL
Щоб приховати помилки у вашому виробничому середовищі, налаштуйте php.ini як:
display_errors = Вимк
display_startup_errors = Вимк
error_reporting = E_ALL
log_errors = УвімкненоЗ цими налаштуваннями у виробництві помилки все одно реєструватимуться в журналах помилок веб-сервера, але не будуть показано користувачеві. Щоб отримати додаткові відомості про ці параметри, перегляньте посібник PHP:
Написання автоматизованих тестів для вашого PHP-коду є найкращою практичною та може призвести до створення добре створених програм. Автоматичні тести є чудовим інструментом для того, щоб переконатися, що ваша програма не ламається під час внесення змін або додавання. нові функції, і не слід ігнорувати.
Існує кілька різних типів інструментів тестування (або фреймворків), доступних для PHP, які вибирають різні підходи - всі вони намагаються уникнути ручного тестування та потреби у великих групах забезпечення якості, щоб просто переконатися останні зміни не порушили наявні функції.
З Вікіпедії:
Тестована розробка (TDD) — це процес розробки програмного забезпечення, який обґрунтовується на повторенні дуже короткого цикл розробки: спочатку розробник пише невдалий автоматизований тестовий приклад, який хоче бажане вдосконалення або нове , потім створює код для проходження цього тесту та, нарешті, рефакторює новий код відповідно до прийнятих стандартів. Кент Бек, кому приписують розробку або «перевідкриття» техніки, зазначеної в 2003 році, що TDD заохочує прості створює дизайн і вселяє довіру.
Є кілька різних типів тестування, які ви можете виконати для своєї програми:
Модульне тестування — це підхід до програмування, який забезпечує належну роботу функцій, класів і методів ви створюєте їх протягом усього циклу розробки. Перевіряючи значення, що надходять і виходять з різних функцій і Ви можете переконатися, що внутрішня логіка працює правильно. Використовуючи ін’єкцію залежностей і створюючи “макет” класи та заглушки, ви можете перевірити, чи правильно використовуються залежності для ще кращого покриття тесту.
Якщо ви створите клас або функцію, ви повинні створити модульний тест для кожної поведінки, яку він повинен мати. На дуже базовому рівні
ви повинні переконатися, що він помиляється, якщо ви надсилаєте йому неправильні аргументи, і переконайтеся, що він працює, якщо ви надсилаєте йому правильні аргументи. Це
допоможе переконатися, що коли ви вносите зміни в цей клас або функцію пізніше в циклі розробки, старі
функціональність продовжує працювати як очікувалося. Єдиною альтернативою буде var_dump() у test.php, який є
немає способу створити додаток - великий чи малий.
Інше використання модульних тестів - це внесок у відкритий код. Якщо ви можете написати тест, який показує несправну функціональність (тобто зазнає невдачі), потім виправте це та покажіть, що тест пройдено, виправлення, швидше за все, будуть прийняті. Якщо ви запускаєте проект який приймає запити на вилучення, то вам слід запропонувати це як вимогу.
PHPUnit — це фактична платформа тестування для написання модульних тестів для додатків PHP, але є декілька альтернатив:
З Вікіпедії:
Інтеграційне тестування (іноді його називають інтеграцією та тестуванням, скорочено «I&T») — це етап тестування програмного забезпечення в які окремі модулі програмного забезпечення поєднуються та тестуються як група. Це відбувається після модульного тестування та до нього валідаційне тестування. Інтеграційне тестування приймає як вхідні модулі, які пройшли модульне тестування, групує їх у великі групи агрегатів, застосовує до цих агрегатів тести, визначені в плані тестування інтеграції, і надає як результат інтегрована система готова до тестування системи.
Багато тих самих інструментів, які можна використовувати для модульного тестування, можна використовувати для інтеграційного тестування використовуються принципи.
Іноді також відоме як приймальне тестування, функціональне тестування складається з використання інструментів для створення автоматизованих тестів, які фактично використовувати вашу програму замість того, щоб просто перевіряти, чи окремі одиниці коду поводяться правильно окремі підрозділи можуть правильно спілкуватися один з одним. Ці інструменти зазвичай працюють, використовуючи реальні дані та імітуючи фактичні дані користувачів програми.
Існує два різних типи розробки, керованої поведінкою (BDD): SpecBDD і StoryBDD. SpecBDD зосереджується на техніці поведінка коду, тоді як StoryBDD зосереджується на поведінці чи взаємодії бізнесу чи функцій. PHP має рамки для обох види БДД.
За допомогою StoryBDD ви пишете зрозумілі для історії людини, які описують поведінку вашої програми. Ці історії можуть потім виконувати як фактичні тести вашої програми. Фреймворк, який використовується в додатках PHP для StoryBDD, — це Behat. натхненний проект Ruby Cucumber і реалізує Gherkin DSL для опису поведінки функцій.
За допомогою SpecBDD ви пишете специфікації, які описують, як має поводитися ваш фактичний код. Замість тестування функцій або метод, ви описуєте, як ця функція або метод має поводитися. Для цього PHP пропонує структуру PHPSpec. мета. Цей фреймворк натхненний проектом RSpec для Ruby.
Окрім індивідуальних фреймворків тестування та поведінки, існує також низка загальних фреймворків і допоміжних засобів бібліотеки, корисні для будь-якого обраного підходу.
Програми PHP можна розгортати та запускати на робочих веб-серверах ключовими способами.
PaaS забезпечує системну та мережеву архітектуру, необхідну для запуску програми PHP в Інтернеті. Це майже ні конфігурація для запуску програм PHP або фреймворків PHP.
Нещодавно PaaS став популярним методом розгортання, розміщення та масштабування PHP-додатків будь-якого розміру. Ви можете знайдіть список постачальників платформи як послуги PHP PaaS у нашому розділі ресурсів.
Якщо ви добре знаєте системне адміністрування або хочете навчитися цьому, віртуальні або виділені сервери допоможуть Ви повністю контролюєте робоче середовище своєї програми.
PHP, через вбудований у PHP FastCGI Process Manager (FPM), дуже добре поєднується з nginx, який є легким, високопродуктивний веб-сервер. Він використовує менше пам’яті, ніж Apache, і може краще обробляти більше одночасних запитів. Це є особливо важливо на віртуальних серверах, які не мають багато вільної пам’яті.
PHP і Apache мають довгу спільну історію. Apache легко налаштовується і має багато доступних modules для розширення функціональності. Це популярний вибір для спільних серверів і легке налаштування для PHP фреймворки та програми з відкритим кодом, такі як WordPress. На жаль, за замовчуванням Apache використовує більше ресурсів, ніж nginx не може обслуговувати стільки відвідувачів одночасно.
Apache має кілька можливих конфігурацій для запуску PHP. Найпоширенішим і найпростішим у налаштуванні є prefork MPM
з mod_php. Хоча він не є найбільш ефективним для використання пам’яті, він найпростіший для роботи та використання. Це ймовірно
найкращий вибір, якщо ви не хочете надто глибоко копатися в аспектах адміністрування сервера. Зауважте, що якщо ви використовуєте
mod_php ви ПОВИННІ використовувати prefork MPM.
Крім того, якщо ви хочете вичавити більше продуктивності та стабільності з Apache, ви можете скористатися перевагами та сама система FPM, що й nginx, і запустіть worker MPM або event MPM за допомогою mod_fastcgi або mod_fcgid. Ця конфігурація буде бути значно ефективнішим для пам’яті та набагато швидшим, але це більше роботи для налаштування.
Якщо ви використовуєте Apache 2.4 або новішу версію, ви можете використовувати mod_proxy_fcgi, щоб отримати чудову продуктивність, яку легко налаштувати.
Якщо ви бачите, що вручну змінюєте схему бази даних або виконуєте тести вручну перед оновленням файлів (вручну), подумайте двічі! З кожним додатковим ручним завданням, необхідним для розгортання нової версії програми, шанси на збільшується кількість потенційно фатальних помилок. Незалежно від того, чи маєте ви справу з простим оновленням, комплексним процесом збирання чи навіть стратегія безперервної інтеграції, [build automation][buildautomation] — ваш друг.
Серед завдань, які ви можете автоматизувати, є:
Інструменти розгортання можна описати як набір сценаріїв, які виконують типові завдання розгортання програмного забезпечення. Інструмент розгортання не є частиною вашого програмного забезпечення, він впливає на ваше програмне забезпечення «зовні».
Існує багато доступних інструментів з відкритим кодом, які допоможуть вам з автоматизацією створення та розгортанням, деякі з них написані на PHP, інші – ні. Це не повинно утримувати вас від їх використання, якщо вони краще підходять для конкретної роботи. Ось кілька прикладів:
[Phing] може керувати процесом упакування, розгортання або тестування з файлу збірки XML. Phing (який базується на [Apache Ant]) надає багатий набір завдань, які зазвичай потрібні для встановлення або оновлення веб-програми, і може бути розширений додатковими спеціальними завданнями, написаними на PHP. Це надійний і надійний інструмент, який існує вже давно, однак його можна було б сприйняти як трохи старомодний через те, як він працює з конфігурацією (файли XML).
[Capistrano] — це система для програмістів середнього та просунутого рівня для виконання команд у структурований, повторюваний спосіб на одній або кількох віддалених машинах. Він попередньо налаштований для розгортання програм Ruby on Rails, однак ви можете успішно розгортати системи PHP з ним. Успішне використання Capistrano залежить від робочого знання Ruby та Rake.
[Ansistrano] — це кілька ролей Ansible для легкого керування процесом розгортання (розгортання та відкат) для програм сценаріїв, таких як PHP, Python і Ruby. Це порт Ansible для [Capistrano]. Його вже використовувало досить багато компаній PHP.
[Deployer] — це інструмент розгортання, написаний на PHP. Це просто і функціонально. Функції включають паралельне виконання завдань, атомарне розгортання та підтримку узгодженості між серверами. Доступні рецепти типових завдань для Symfony, Laravel, Zend Framework і Yii. Стаття Юнеса Рафі [Просте розгортання PHP-додатків за допомогою Deployer][phpdeploy_deployer] є чудовим посібником із розгортання вашої програми за допомогою інструменту.
[Magallanes] — ще один інструмент, написаний на PHP із простою конфігурацією у файлах YAML. Він підтримує кілька серверів і середовищ, атомарне розгортання та має деякі вбудовані завдання, які можна використовувати для звичайних інструментів і фреймворків.
Управління та налаштування серверів може бути складним завданням, якщо стикатися з великою кількістю серверів. Існують інструменти для вирішення цієї проблеми, щоб ви могли автоматизувати свою інфраструктуру, щоб переконатися, що у вас є правильні сервери та що вони правильно налаштовані. Вони часто інтегруються з великими провайдерами хмарного хостингу (Amazon Web Services, Heroku, DigitalOcean тощо) для керування примірниками, що значно полегшує масштабування програми.[Ansible] — це інструмент, який керує вашою інфраструктурою за допомогою файлів YAML. Почати роботу з ним просто, і він може керувати складними та великомасштабними програмами. Існує API для керування хмарними примірниками, і він може керувати ними за допомогою динамічної інвентаризації за допомогою певних інструментів.
[Puppet] — це інструмент, який має власну мову та типи файлів для керування серверами та конфігураціями. Його можна використовувати в налаштуваннях головний/клієнт або в режимі «без головного». У режимі головний/клієнт клієнти опитуватимуть центрального головного(-их) нову конфігурацію через встановлені проміжки часу та оновлюватимуться за потреби. У режимі без майстра ви можете надсилати зміни до своїх вузлів.
[Chef] — це потужна система системної інтеграції на основі Ruby, за допомогою якої ви можете створити все серверне середовище або віртуальні коробки. Він добре інтегрується з Amazon Web Services через їхню службу OpsWorks.
Безперервна інтеграція – це практика розробки програмного забезпечення, де члени команди часто інтегрують свою роботу, зазвичай кожна особа інтегрується щонайменше щодня, що призводить до кількох інтеграцій на день. Багато команд вважають це підхід значно зменшує проблеми інтеграції та дозволяє команді більше розробляти згуртоване програмне забезпечення швидко.
– Мартін Фаулер
Існують різні способи реалізації постійної інтеграції для PHP. [Travis CI] зробив чудову роботу роблячи постійну інтеграцію реальністю навіть для невеликих проектів. Travis CI — це служба постійної інтеграції. Його можна інтегрувати з GitHub і пропонує підтримку багатьох мов, включаючи PHP. GitHub має постійні робочі процеси інтеграції з [GitHub Actions][github_actions].
Запуск вашої програми в різних середовищах під час розробки та виробництва може призвести до появи дивних помилок коли ви йдете в прямому ефірі. Також складно підтримувати різні середовища розробки в актуальному стані з однаковою версією для всіх бібліотеки, які використовуються при роботі з командою розробників.
Якщо ви розробляєте в Windows і розгортаєте в Linux (або будь-якому іншому, що не є Windows) або розробляєте в команді, ви варто розглянути можливість використання віртуальної машини. Це звучить складно, але крім широко відомих середовищ віртуалізації наприклад VMware або VirtualBox, є додаткові інструменти, які можуть допомогти вам налаштувати віртуальне середовище в декілька простих завдань кроки.
Vagrant допоможе вам створити ваші віртуальні ящики на основі відомих віртуальних середовищ і налаштує їх середовища на основі одного файлу конфігурації. Ці скриньки можна налаштувати вручну або за допомогою «ініціалізації» програмне забезпечення, наприклад Puppet або Chef, щоб зробити це за вас. Ініціалізація базової коробки є чудовим способом забезпечити це кілька ящиків налаштовані однаковим чином, і вам не потрібно підтримувати складне “налаштування” списки команд. Ви також можете «знищити» свою базову коробку та відтворити її без численних ручних дій, що полегшить її створення «свіжа» установка.
Vagrant створює папки для обміну кодом між вашим хостом і вашою віртуальною машиною, що означає, що ви можете створюйте та редагуйте свої файли на хост-машині, а потім запускайте код у своїй віртуальній машині.
[Docker] — легка альтернатива повноцінній віртуальній машині — називається так тому, що це все про «контейнери». Контейнер — це будівельний блок, який, у найпростішому випадку, виконує одну певну роботу, напр. запуск веб-сервера. «Зображення» — це пакет, який ви використовуєте для створення контейнера — у Docker є повний репозиторій.
Типова програма LAMP може мати три контейнери: веб-сервер, процес PHP-FPM і MySQL. Як і у випадку зі спільними папками у Vagrant, ви можете залишити файли програми там, де вони є, і вказати Docker, де їх знайти.
Ви можете генерувати контейнери з командного рядка (див. приклад нижче) або, для зручності обслуговування, створіть файл docker-compose.yml для свого проекту, вказавши, які контейнери потрібно створити та як вони взаємодіють один з одним.
Docker може допомогти, якщо ви розробляєте кілька веб-сайтів і бажаєте відокремити їх від встановлення кожного на окремій віртуальній машині, але не маєте необхідного дискового простору чи часу, щоб підтримувати все в актуальному стані. Це ефективно: інсталяція та завантаження відбуваються швидше, вам потрібно лише зберігати одну копію кожного образу, незважаючи на те, що часто він використовується, контейнерам потрібно менше оперативної пам’яті та спільно використовувати те саме ядро ОС, тож ви можете мати більше серверів, що працюють одночасно, а їх зупинка та запуск займає лічені секунди, не потрібно чекати повного завантаження сервера.
Після [встановлення докера][docker-install] на вашому комп’ютері ви можете запустити веб-сервер за допомогою однієї команди.
Далі буде завантажено повнофункціональну інсталяцію Apache з останньою версією PHP, зіставляючи /path/to/your/php/files з коренем документа, який ви можете переглянути на http://localhost:8080:
docker run -d --name my-php-webserver -p 8080:80 -v /path/to/your/php/files:/var/www/html/ php:apacheЦе ініціалізує та запустить ваш контейнер. -d дозволяє працювати у фоновому режимі. Щоб зупинити та запустити його, просто запустіть docker stop my-php-webserver і docker start my-php-webserver (інші параметри знову не потрібні).
Наведена вище команда показує швидкий спосіб запуску базового сервера. Ви можете зробити багато іншого (і тисячі попередньо створених образів у [Docker Hub][docker-hub]). Знайдіть час, щоб вивчити термінологію та прочитати [Посібник користувача Docker][docker-doc], щоб отримати від нього максимальну користь, і не запускайте випадковий код, який ви завантажили, не перевіривши його безпечність – неофіційні зображення можуть не мати останніх патчів безпеки. Якщо сумніваєтеся, дотримуйтеся [офіційних сховищ][docker-hub-official].
Сайт [PHPDocker.io] автоматично створить усі файли, необхідні для повнофункціонального стеку LAMP/LEMP, включно з обраною вами версією PHP і розширеннями.
PHP досить швидкий сам по собі, але вузькі місця можуть виникати під час встановлення віддалених з’єднань, завантаження файлів тощо. На щастя, існують різні інструменти, які дозволяють пришвидшити певні частини вашої програми або зменшити кількість виконання цих різноманітних трудомістких завдань.
Коли PHP-файл виконується, його потрібно спочатку скомпілювати в opcodes (інструкції машинної мови для ЦП). Якщо вихідний код не змінено, коди операцій залишаться тими самими, тому цей крок компіляції стає марною тратою ресурсів ЦП.
Кеш кодів операцій запобігає надлишковій компіляції, зберігаючи коди операцій у пам’яті та повторно використовуючи їх під час послідовних викликів. Як правило, спочатку перевіряється підпис або час модифікації файлу на випадок, якщо були якісь зміни.
Цілком ймовірно, що кеш коду операції значно покращить швидкість вашої програми. Починаючи з PHP 5.5, є один вбудований - Zend OPcache. Залежно від вашого пакета/дистрибутива PHP, зазвичай його ввімкнено за умовчанням. Щоб переконатися, перевірте opcache.enable і вихід phpinfo(). Для попередніх версій є розширення PECL.
Докладніше про кеші кодів операцій:
Бувають випадки, коли може бути корисним кешувати окремі об’єкти у вашому коді, наприклад, з даними, які є дорогими отримати або звернення до бази даних, коли результат навряд чи зміниться. Ви можете використовувати програмне забезпечення для кешування об’єктів, щоб зберегти їх частини даних у пам’яті для надзвичайно швидкого доступу пізніше. Якщо ви збережете ці елементи в сховищі даних після отримання їх, а потім витягніть їх безпосередньо з кешу для наступних запитів, ви можете отримати значне покращення продуктивність, а також зменшити навантаження на сервери бази даних.
Багато популярних рішень для кешування байт-коду також дозволяють кешувати власні дані, тому є ще більше причин для перевага їх. APCu та WinCache надають API для збереження даних із вашого PHP-коду в кеш пам’яті.
Найпоширенішими системами кешування об’єктів пам’яті є APCu та memcached. APCu - відмінний вибір для об’єкта кешування, він містить простий API для додавання ваших власних даних до кешу пам’яті, його дуже легко налаштувати та використовувати. The одне реальне обмеження APCu полягає в тому, що він прив’язаний до сервера, на якому його встановлено. З іншого боку, Memcached є інстальовано як окрему службу, і до неї можна отримати доступ через мережу, тобто ви можете зберігати об’єкти в a надшвидке сховище даних у центральному місці, з якого може отримувати багато різних систем.
Зауважте, що спільний доступ до кешу між процесами PHP залежить від того, як використовується PHP. Під час запуску PHP через PHP-FPM, кеш використовується для всіх процесів усіх пулів. Під час запуску PHP як (швидкої) програми CGI у вашому веб-сервер, кеш не є спільним, тобто кожен процес PHP матиме власні дані APCu. Під час запуску PHP за командою рядок, кеш не є спільним і існуватиме лише протягом дії команди, тому вам слід пам’ятати про ситуація і цілі. Натомість ви можете розглянути можливість використання memcached, оскільки він не прив’язаний до процесів PHP.
У мережевій конфігурації APCu зазвичай перевершує memcached з точки зору швидкості доступу, але memcached буде здатність розширюватися швидше та далі. Якщо ви не очікуєте, що ваша програма буде працювати на кількох серверах, або ні потрібні додаткові функції, які пропонує memcached, тоді APCu, мабуть, найкращий вибір для кешування об’єктів.
Приклад логіки використання APCu:
<?php
// перевірити, чи є дані, збережені як 'expensive_data' в кеші
$data = apcu_fetch('expensive_data');
if ($data === false) {
// даних немає в кеші; зберегти результат дорогого дзвінка для подальшого використання
apcu_add('expensive_data', $data = get_expensive_data());
}
print_r($дані);PHPDoc — це неформальний стандарт для коментування коду PHP. Доступно багато різних [тегів]. Повний список тегів і приклади можна знайти в [посібнику PHPDoc].
Нижче наведено приклад того, як ви можете документувати клас за допомогою кількох методів;
<?php
/**
* @author A Name <a.name@example.com>
* @link https://docs.phpdoc.org/
*/
клас DateTimeHelper
{
/**
* @param змішав $anything Все, що ми можемо перетворити на об’єкт \DateTime
*
* @throws \InvalidArgumentException
*
* @return \DateTime
*/
публічна функція dateTimeFromAnything($anything)
{
$type = gettype($anything);
перемикач ($type) {
// Деякий код, який намагається повернути об'єкт \DateTime
}
створити новий \InvalidArgumentException(
«Помилка перетворення параметра типу '{$type}' в об'єкт DateTime»
);
}
/**
* @param mixed $date Усе, що ми можемо перетворити на об’єкт \DateTime
*
* @return void
*/
публічна функція printISO8601Date($date)
{
echo $this->dateTimeFromAnything($date)->format('c');
}
/**
* @param mixed $date Усе, що ми можемо перетворити на об’єкт \DateTime
*/
публічна функція printRFC2822Date($date)
{
echo $this->dateTimeFromAnything($date)->format('r');
}
}Документація для класу в цілому має теги @author і @link. Тег @author використовується для задокументувати автора коду та може бути повторений для документування кількох авторів. Тег @link використовується для посилання на веб-сайт, що вказує на зв’язок між веб-сайтом і кодом.
Усередині класу перший метод має тег @param, що документує тип, назву та опис параметра передається в метод. Крім того, він має теги @return і @throws для документування типу повернення та будь-яких винятків, які можуть бути створені відповідно.
Другий і третій методи дуже схожі й мають єдиний тег @param, як і перший метод. Важливе
Різниця між блоком документів другого та третього методів полягає у включенні/виключенні тегу @return.
@return void чітко повідомляє нам, що повернення неможливе; історичне пропускання оператора @return void також призводить до тієї самої дії (без повернення).
Важко знайти цікавий та обізнаний PHP членів спільноти, коли ви тільки починаєте. Ви можете знайдіть скорочений список членів PHP-спільноти для початку:
Замість того, щоб заново винаходити велосипед, багато розробників PHP використовують фреймворки для створення веб-додатків. Анотація фреймворків усунути багато проблем низького рівня та надати корисні, прості у використанні інтерфейси для виконання типових завдань.
Вам не потрібно використовувати фреймворк для кожного проекту. Іноді простий PHP є правильним шляхом, але якщо вам потрібен то існує три основні типи:
Мікрофреймворки, по суті, є оболонкою для маршрутизації HTTP-запиту до зворотного виклику, контролера, методу тощо так швидко, як можливо, і іноді постачається з кількома додатковими бібліотеками для допомоги в розробці, такими як базові оболонки бази даних і подобається. Вони широко використовуються для створення віддалених HTTP-служб.
Багато фреймворків додають значну кількість функцій на додаток до того, що доступно в мікрофреймворку; це називається Full-Stack Frameworks. Вони часто постачаються в комплекті з ORM, пакетами автентифікації тощо.
Компонентні фреймворки — це колекції спеціалізованих і одноцільових бібліотек. На основі різнорідних компонентів фреймворки можна використовувати разом для створення мікро- або повного стеку.
Як згадувалося вище, «Компоненти» є іншим підходом до спільної мети створення, розповсюдження та впровадження спільний код. Існують різні сховища компонентів, два основних з яких:
Обидва ці репозиторії мають інструменти командного рядка, пов’язані з ними, щоб допомогти процесам встановлення та оновлення, і були пояснені більш детально в розділі [Керування залежностями].
Існують також фреймворки на основі компонентів і постачальники компонентів, які взагалі не пропонують фреймворків. Ці проекти забезпечують інше джерело пакунків, які в ідеалі майже не залежать від інших пакунків або певних фреймворків.
Наприклад, ви можете використовувати [пакет перевірки FuelPHP] без необхідності використовувати саму структуру FuelPHP.
Laravel [компоненти Illuminate] стануть краще відокремлені від фреймворку Laravel. Наразі лише Компоненти, найкраще відокремлені від інфраструктури Laravel, перераховані вище.
Ви можете підписатися на щотижневі інформаційні бюлетені, щоб бути в курсі нових бібліотек, останніх новин, подій та загального оголошення, а також додаткові ресурси, що час від часу публікуються:
Є також тижневики на інших платформах, які можуть вас зацікавити; ось список деяких.
Існує багато книг про PHP; на жаль, деякі з них зараз досить старі та вже не точні. Зокрема, уникайте книг про “PHP 6”, версію, яка тепер ніколи не існуватиме. Наступним великим випуском PHP після 5.6 був «PHP 7», частково через це.
Цей розділ має бути живим документом для рекомендованих книг про розробку PHP загалом. Якщо ви хочете, щоб ваш книгу, яка буде додана, надішліть PR, і вона буде перевірена на відповідність.
Спільнота PHP така ж різноманітна, як і велика, і її учасники готові та бажають підтримати нових PHP-програмістів. Спробуйте приєднатися до місцевої групи користувачів PHP (PUG) або відвідати більші конференції PHP, щоб дізнатися більше про найкращі показані тут практики. Ви можете спілкуватися на IRC у каналі #phpc на irc.libera.chat і стежити за @phpc, на Discord, на X або Mastodon. Виходьте туди, знайомтеся з новими розробниками, вивчайте нові теми та, перш за все, створюйте нове друзі! Інші ресурси спільноти включають StackOverflow.
[Читати офіційний календар подій PHP][php-календар]
Якщо ви живете у великому місті, швидше за все, поблизу є група користувачів PHP. Ви можете легко знайти свого місцевого МОПСА за адресою
[PHP.ug][php-ug]. Альтернативними джерелами можуть бути [Meetup.com][meetup] або пошук php user group near me
за допомогою вашої улюбленої пошукової системи (наприклад, [Google][google]). Якщо ви живете в меншому місті, його може не бути
місцевий МОПС; якщо це так, почніть один!
Окремо варто відзначити дві глобальні групи користувачів: [NomadPHP] і [PHPWomen]. [NomadPHP] пропонує двічі на місяць онлайн-зустрічі груп користувачів із презентаціями деяких найкращих доповідачів спільноти PHP. [PHPWomen] — це неексклюзивна група користувачів, спочатку орієнтована на жінок у світі PHP. Членство відкрито для кожен, хто підтримує більш різноманітну спільноту. PHPWomen надають мережу підтримки, наставництва та навчання, а також загалом сприяти створенню «жіночої» та професійної атмосфери.
[Прочитайте про групи користувачів у PHP Wiki][php-wiki] [google]: https://www.google.com/search?q=php+user+group+near+me [meetup]: https://www.meetup.com/find/ [php-ug]: https://php.ug/ [NomadPHP]: https://nomadphp.com/ [PHPWomen]: https://x.com/PHPWomen [php-wiki]: https://wiki.php.net/usergroups
Спільнота PHP також проводить більші регіональні та національні конференції в багатьох країнах світу. Добре відомий члени PHP-спільноти зазвичай виступають на цих великих заходах, тож це чудова можливість навчитися безпосередньо лідери галузі.
ElePHPant — це чудовий талісман проекту PHP із зображенням слона. Спочатку він був розроблений для проекту PHP у 1998 році Вінсентом Понт’є – духовним батьком тисяч elePHPants у всьому світі – і через десять років також з’явилися чарівні плюшеві іграшки-слони. Тепер elePHPants присутні на багатьох PHP-конференціях і разом із багатьма PHP-розробниками за комп’ютерами для розваги та натхнення.
[Інтерв’ю з Вінсентом Понт’є][інтерв’ю-вінсента-понтьє]