Verification: a143cc29221c9be0

Optibit расширение mysql необходимое для работы wordpress

Optibit расширение mysql необходимое для работы wordpress

Предварительные требования

Для изучения этого учебника требуется опыт работы с Docker Compose.

Скачивание примера приложения

При работе с этим руководством вы будете использовать файл из Docker Compose, но измените его, добавив сведения о Базе данных Azure для MySQL, постоянном хранилище и Redis. Файл конфигурации можно найти в репозитории примеров для Azure. Поддерживаемые параметры конфигурации см. в разделе Docker Compose options (Параметры Docker Compose).

version: '3.3'

services:
   db:
     image: mysql:5.7
     volumes:
       - db_data:/var/lib/mysql
     restart: always
     environment:
       MYSQL_ROOT_PASSWORD: somewordpress
       MYSQL_DATABASE: wordpress
       MYSQL_USER: wordpress
       MYSQL_PASSWORD: wordpress

   wordpress:
     depends_on:
       - db
     image: wordpress:latest
     ports:
       - "8000:80"
     restart: always
     environment:
       WORDPRESS_DB_HOST: db:3306
       WORDPRESS_DB_USER: wordpress
       WORDPRESS_DB_PASSWORD: wordpress
volumes:
    db_data:

В Cloud Shell создайте каталог tutorial и перейдите в него.

mkdir tutorial

cd tutorial

Затем выполните следующую команду, чтобы клонировать репозиторий с примером приложения в локальный каталог tutorial. Затем перейдите в каталог multicontainerwordpress.

git clone https://github.com/Azure-Samples/multicontainerwordpress

cd multicontainerwordpress

Создание группы ресурсов

Группа ресурсов — это логический контейнер, в котором происходит развертывание ресурсов Azure (например, веб-приложений, баз данных и учетных записей хранения) и управление ими. Например, в дальнейшем можно удалить всю группу ресурсов при помощи одного простого действия.

В Cloud Shell создайте группу ресурсов с помощью команды az group create. В следующем примере создается группа ресурсов с именем myResourceGroup в расположении Центрально-южная часть США. Чтобы просмотреть все поддерживаемые расположения для службы приложений в Linux на уровне Стандартный, выполните команду az appservice list-locations --sku S1 --linux-workers-enabled.

az group create --name myResourceGroup --location "South Central US"

Обычно группа ресурсов и ресурсы создаются в ближайших регионах.

По завершении команды в выходных данных JSON будут отображаться свойства группы ресурсов.

Создание плана службы приложений Azure

В Cloud Shell создайте план службы приложений в группе ресурсов с помощью команды az appservice plan create.

В следующем примере создается план службы приложений с именем myAppServicePlan в ценовой категории Стандартный (--sku S1) в контейнере Linux (--is-linux).

az appservice plan create --name myAppServicePlan --resource-group myResourceGroup --sku S1 --is-linux

После создания плана службы приложений в Cloud Shell отображается информация следующего вида:

{
  "adminSiteName": null,
  "appServicePlanName": "myAppServicePlan",
  "geoRegion": "South Central US",
  "hostingEnvironmentProfile": null,
  "id": "/subscriptions/0000-0000/resourceGroups/myResourceGroup/providers/Microsoft.Web/serverfarms/myAppServicePlan",
  "kind": "linux",
  "location": "South Central US",
  "maximumNumberOfWorkers": 1,
  "name": "myAppServicePlan",
  
  "targetWorkerSizeId": 0,
  "type": "Microsoft.Web/serverfarms",
  "workerTierName": null
}

Docker Compose с контейнерами WordPress и MySQL

Создание приложения Docker Compose

В Cloud Shell создайте многоконтейнерное веб-приложение в рамках плана службы приложений myAppServicePlan с помощью команды az webapp create. Не забудьте указать уникальное имя приложения вместо .

az webapp create --resource-group myResourceGroup --plan myAppServicePlan --name  --multicontainer-config-type compose --multicontainer-config-file docker-compose-wordpress.yml

Когда веб-приложение будет создано, в Cloud Shell отобразится примерно следующее:

{
  "additionalProperties": {},
  "availabilityState": "Normal",
  "clientAffinityEnabled": true,
  "clientCertEnabled": false,
  "cloningInfo": null,
  "containerSize": 0,
  "dailyMemoryTimeQuota": 0,
  "defaultHostName": ".azurewebsites.net",
  "enabled": true,
  
}

Переход в приложение

Перейдите в развернутое приложение по адресу http://.azurewebsites.net. Для загрузки приложения может потребоваться несколько минут. Если произойдет ошибка, подождите несколько минут, а затем обновите страницу в браузере. Если возникнет проблема, которую нужно будет устранить, просмотрите журналы контейнера.

Пример многоконтейнерного приложения на платформе "Веб-приложение для контейнеров"

Поздравляем! Вы создали многоконтейнерное приложение на платформе "Веб-приложение для контейнеров". Далее вам предстоит настроить приложение для использования базы данных Azure для MySQL. Не устанавливайте WordPress в этом этапе.

Подключение к рабочей базе данных

Не рекомендуется использовать контейнеры базы данных в рабочей среде. Локальные контейнеры не являются масштабируемыми. Вместо этого вы будете использовать базу данных Azure для MySQL, которую можно масштабировать.

Создайте сервер базы данных Azure для MySQL.

Создайте сервер базы данных Azure для MySQL с помощью команды az mysql server create.

В следующей команде замените именем своего сервера MySQL везде, где встречается этот заполнитель. Допустимые символы: a-z, 0-9 и -. Это имя является частью имени узла сервера MySQL (.database.windows.net). Оно должно быть глобально уникальным.

az mysql server create --resource-group myResourceGroup --name   --location "South Central US" --admin-user adminuser --admin-password My5up3rStr0ngPaSw0rd! --sku-name B_Gen5_1 --version 5.7

Создание сервера может занять несколько минут. После создания сервера MySQL в Cloud Shell отображаются следующие сведения:

{
  "administratorLogin": "adminuser",
  "administratorLoginPassword": null,
  "fullyQualifiedDomainName": ".database.windows.net",
  "id": "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/myResourceGroup/providers/Microsoft.DBforMySQL/servers/",
  "location": "southcentralus",
  "name": "",
  "resourceGroup": "myResourceGroup",
  ...
}

Настройка брандмауэра сервера

Создайте правило брандмауэра для сервера MySQL, чтобы разрешить подключения клиентов, выполнив команду az mysql server firewall-rule create. Если для начального и конечного IP-адресов задано значение 0.0.0.0, брандмауэр открыт только для других ресурсов Azure.

az mysql server firewall-rule create --name allAzureIPs --server  --resource-group myResourceGroup --start-ip-address 0.0.0.0 --end-ip-address 0.0.0.0

Создание базы данных WordPress

az mysql db create --resource-group myResourceGroup --server-name  --name wordpress

После создания базы данных в Cloud Shell отображаются следующие сведения:

{
  "additionalProperties": {},
  "charset": "latin1",
  "collation": "latin1_swedish_ci",
  "id": "/subscriptions/12db1644-4b12-4cab-ba54-8ba2f2822c1f/resourceGroups/myResourceGroup/providers/Microsoft.DBforMySQL/servers//databases/wordpress",
  "name": "wordpress",
  "resourceGroup": "myResourceGroup",
  "type": "Microsoft.DBforMySQL/servers/databases"
}

Настройка переменных базы данных в WordPress

Чтобы подключить приложение WordPress к новому серверу MySQL, задайте несколько переменных среды для WordPress, включая путь к выданному центром сертификации SSL-сертификату, который определяется с помощью MYSQL_SSL_CA. Сведения о сертификате Baltimore CyberTrust Root от DigiCert см. в разделе о пользовательском образе ниже.

Чтобы внести эти изменения, выполните команду az webapp config appsettings set в Cloud Shell. Параметры приложения чувствительны к регистру и используются с разделителями-пробелами.

az webapp config appsettings set --resource-group myResourceGroup --name  --settings WORDPRESS_DB_HOST=".mysql.database.azure.com" WORDPRESS_DB_USER="adminuser@" WORDPRESS_DB_PASSWORD="My5up3rStr0ngPaSw0rd!" WORDPRESS_DB_NAME="wordpress" MYSQL_SSL_CA="BaltimoreCyberTrustroot.crt.pem"

После создания параметров приложения в Cloud Shell отображается информация следующего вида:

[
  {
    "name": "WORDPRESS_DB_HOST",
    "slotSetting": false,
    "value": ".mysql.database.azure.com"
  },
  {
    "name": "WORDPRESS_DB_USER",
    "slotSetting": false,
    "value": "adminuser@"
  },
  {
    "name": "WORDPRESS_DB_NAME",
    "slotSetting": false,
    "value": "wordpress"
  },
  {
    "name": "WORDPRESS_DB_PASSWORD",
    "slotSetting": false,
    "value": "My5up3rStr0ngPaSw0rd!"
  },
  {
    "name": "MYSQL_SSL_CA",
    "slotSetting": false,
    "value": "BaltimoreCyberTrustroot.crt.pem"
  }
]

Подробные сведения о переменных среды см. в разделе Configure environment variables (Настройка переменных среды).

Использование пользовательского образа для SSL-соединения с MySQL и других конфигураций

По умолчанию SSL-соединение используется в базе данных Azure для MySQL. Но чтобы использовать это соединение в WordPress, нужно задать дополнительную конфигурацию. "Официальный образ" WordPress не содержит таких настроек, но для удобства мы подготовили пользовательский образ. На практике требуемые изменения нужно добавлять в свой образ.

Пользовательский образ создан на основе официального образа WordPress из Docker Hub. В этот пользовательский образ внесены следующие изменения для базы данных Azure для MySQL:

  • добавлен файл сертификата Baltimore CyberTrust Root для SSL-соединения с MySQL;
  • задан параметр приложения для SSL-сертификата MySQL, предоставленного центром сертификации, в файле wp-config.php WordPress;
  • добавлено определение WordPress для MYSQL_CLIENT_FLAGS, необходимое для SSL-соединения с MySQL.

Для Redis (используется в следующем разделе) внесены следующие изменения:

  • добавлено расширение PHP для Redis версии 4.0.2;
  • добавлена команда распаковки, необходимая для извлечения файла;
  • добавлен подключаемый модуль Redis Object Cache 1.3.8 для WordPress.
  • задан параметр приложения для имени узла Redis в файле wp-config.php WordPress.

Чтобы применить пользовательский образ, нужно обновить файл docker-compose-wordpress.yml. В Cloud Shell введите nano docker-compose-wordpress.yml, чтобы открыть текстовый редактор Nano. Измените image: wordpress на image: mcr.microsoft.com/azuredocs/multicontainerwordpress. Вам больше не понадобится контейнер базы данных. Удалите разделы db, environment, depends_on и volumes из файла конфигурации. Файл должен выглядеть примерно так, как в следующем коде:

version: '3.3'

services:
   wordpress:
     image: mcr.microsoft.com/azuredocs/multicontainerwordpress
     ports:
       - "8000:80"
     restart: always

Сохраните изменения и выйдите из редактора Nano. Выполните команду ^O, чтобы сохранить файл, и ^X — чтобы выйти.

Обновление приложения с указанием новой конфигурации

В Cloud Shell измените конфигурацию многоконтейнерного веб-приложения с помощью команды az webapp config container set. Не забудьте заменить именем веб-приложения, созданного ранее.

az webapp config container set --resource-group myResourceGroup --name  --multicontainer-config-type compose --multicontainer-config-file docker-compose-wordpress.yml

После изменения настроек приложения в Cloud Shell отображаются следующие сведения:

[
  {
    "name": "DOCKER_CUSTOM_IMAGE_NAME",
    "value": "COMPOSE|dmVyc2lvbjogJzMuMycKCnNlcnZpY2VzOgogICB3b3JkcHJlc3M6CiAgICAgaW1hZ2U6IG1zYW5nYXB1L3dvcmRwcmVzcwogICAgIHBvcnRzOgogICAgICAgLSAiODAwMDo4MCIKICAgICByZXN0YXJ0OiBhbHdheXM="
  }
]

Переход в приложение

Перейдите в развернутое приложение по адресу http://.azurewebsites.net. Теперь в приложении используется база данных Azure для MySQL.

Пример многоконтейнерного приложения на платформе "Веб-приложение для контейнеров"

Добавление постоянного хранилища

Ваше многоконтейнерное приложение теперь работает на платформе "Веб-приложение для контейнеров". Но если установить WordPress сейчас и после этого перезапустить приложение, вы обнаружите, что данные установки WordPress удалены. Это происходит потому, что сейчас в конфигурации Docker Compose указано расположение для хранения в контейнере. Файлы, установленные в контейнере, исчезают после перезапуска приложения. Из этого раздела вы узнаете, как добавить постоянное хранилище в контейнер WordPress.

Настройка переменных среды

Чтобы использовать постоянное хранилище, вам нужно включить этот параметр в Службе приложений. Чтобы внести это изменение, выполните команду az webapp config appsettings set в Cloud Shell. Параметры приложения чувствительны к регистру и используются с разделителями-пробелами.

az webapp config appsettings set --resource-group myResourceGroup --name  --settings WEBSITES_ENABLE_APP_SERVICE_STORAGE=TRUE

После создания параметров приложения в Cloud Shell отображается информация следующего вида:

[
  
  {
    "name": "WORDPRESS_DB_NAME",
    "slotSetting": false,
    "value": "wordpress"
  },
  {
    "name": "WEBSITES_ENABLE_APP_SERVICE_STORAGE",
    "slotSetting": false,
    "value": "TRUE"
  }
]

Изменение файла конфигурации

В Cloud Shell введите nano docker-compose-wordpress.yml, чтобы открыть текстовый редактор Nano.

Параметр volumes сопоставляет файловую систему с каталогом в контейнере. ${WEBAPP_STORAGE_HOME} — это переменная среды в Службе приложений, которая сопоставляется с постоянным хранилищем для вашего приложения. Используйте эту переменную среды в параметре volumes, чтобы файлы WordPress устанавливались в постоянное хранилище, а не в контейнер. Внесите в файл следующие изменения:

Добавьте в раздел wordpress параметр volumes, как показано в следующем коде:

version: '3.3'

services:
   wordpress:
     image: mcr.microsoft.com/azuredocs/multicontainerwordpress
     volumes:
      - ${WEBAPP_STORAGE_HOME}/site/wwwroot:/var/www/html
     ports:
       - "8000:80"
     restart: always

Обновление приложения с указанием новой конфигурации

В Cloud Shell измените конфигурацию многоконтейнерного веб-приложения с помощью команды az webapp config container set. Не забудьте указать уникальное имя приложения вместо .

az webapp config container set --resource-group myResourceGroup --name  --multicontainer-config-type compose --multicontainer-config-file docker-compose-wordpress.yml

После выполнения команда вернет результат, аналогичный следующему примеру:

[
  {
    "name": "WEBSITES_ENABLE_APP_SERVICE_STORAGE",
    "slotSetting": false,
    "value": "TRUE"
  },
  {
    "name": "DOCKER_CUSTOM_IMAGE_NAME",
    "value": "COMPOSE|dmVyc2lvbjogJzMuMycKCnNlcnZpY2VzOgogICBteXNxbDoKICAgICBpbWFnZTogbXlzcWw6NS43CiAgICAgdm9sdW1lczoKICAgICAgIC0gZGJfZGF0YTovdmFyL2xpYi9teXNxbAogICAgIHJlc3RhcnQ6IGFsd2F5cwogICAgIGVudmlyb25tZW50OgogICAgICAgTVlTUUxfUk9PVF9QQVNTV09SRDogZXhhbXBsZXBhc3MKCiAgIHdvcmRwcmVzczoKICAgICBkZXBlbmRzX29uOgogICAgICAgLSBteXNxbAogICAgIGltYWdlOiB3b3JkcHJlc3M6bGF0ZXN0CiAgICAgcG9ydHM6CiAgICAgICAtICI4MDAwOjgwIgogICAgIHJlc3RhcnQ6IGFsd2F5cwogICAgIGVudmlyb25tZW50OgogICAgICAgV09SRFBSRVNTX0RCX1BBU1NXT1JEOiBleGFtcGxlcGFzcwp2b2x1bWVzOgogICAgZGJfZGF0YTo="
  }
]

Переход в приложение

Перейдите в развернутое приложение по адресу http://.azurewebsites.net.

Теперь контейнер WordPress использует базу данных Azure для MySQL и постоянное хранилище.

Добавление контейнера Redis

Официальный образ WordPress не содержит зависимостей для Redis. Эти зависимости и дополнительные конфигурации, необходимые для использования Redis с WordPress, подготовлены для вас в этом пользовательском образе. На практике требуемые изменения нужно добавлять в свой образ.

Пользовательский образ создан на основе официального образа WordPress из Docker Hub. В пользовательский образ для Redis внесены следующие изменения:

  • добавлено расширение PHP для Redis версии 4.0.2;
  • добавлена команда распаковки, необходимая для извлечения файла;
  • добавлен подключаемый модуль Redis Object Cache 1.3.8 для WordPress.
  • задан параметр приложения для имени узла Redis в файле wp-config.php WordPress.

Добавьте контейнер Redis в конец файла конфигурации, как показано в следующем примере:

version: '3.3'

services:
   wordpress:
     image: mcr.microsoft.com/azuredocs/multicontainerwordpress
     ports:
       - "8000:80"
     restart: always

   redis:
     image: mcr.microsoft.com/oss/bitnami/redis:6.0.8
     environment: 
      - ALLOW_EMPTY_PASSWORD=yes
     restart: always

Настройка переменных среды

Чтобы использовать Redis, включите параметр WP_REDIS_HOST в Службе приложений. Это обязательный параметр для взаимодействия WordPress с узлом Redis. Чтобы внести это изменение, выполните команду az webapp config appsettings set в Cloud Shell. Параметры приложения чувствительны к регистру и используются с разделителями-пробелами.

az webapp config appsettings set --resource-group myResourceGroup --name  --settings WP_REDIS_HOST="redis"

После создания параметров приложения в Cloud Shell отображается информация следующего вида:

[
  
  {
    "name": "WORDPRESS_DB_USER",
    "slotSetting": false,
    "value": "adminuser@"
  },
  {
    "name": "WP_REDIS_HOST",
    "slotSetting": false,
    "value": "redis"
  }
]

Обновление приложения с указанием новой конфигурации

В Cloud Shell измените конфигурацию многоконтейнерного веб-приложения с помощью команды az webapp config container set. Не забудьте указать уникальное имя приложения вместо .

az webapp config container set --resource-group myResourceGroup --name  --multicontainer-config-type compose --multicontainer-config-file compose-wordpress.yml

После выполнения команда вернет результат, аналогичный следующему примеру:

[
  {
    "name": "DOCKER_CUSTOM_IMAGE_NAME",
    "value": "COMPOSE|dmVyc2lvbjogJzMuMycKCnNlcnZpY2VzOgogICBteXNxbDoKICAgICBpbWFnZTogbXlzcWw6NS43CiAgICAgdm9sdW1lczoKICAgICAgIC0gZGJfZGF0YTovdmFyL2xpYi9teXNxbAogICAgIHJlc3RhcnQ6IGFsd2F5cwogICAgIGVudmlyb25tZW50OgogICAgICAgTVlTUUxfUk9PVF9QQVNTV09SRDogZXhhbXBsZXBhc3MKCiAgIHdvcmRwcmVzczoKICAgICBkZXBlbmRzX29uOgogICAgICAgLSBteXNxbAogICAgIGltYWdlOiB3b3JkcHJlc3M6bGF0ZXN0CiAgICAgcG9ydHM6CiAgICAgICAtICI4MDAwOjgwIgogICAgIHJlc3RhcnQ6IGFsd2F5cwogICAgIGVudmlyb25tZW50OgogICAgICAgV09SRFBSRVNTX0RCX1BBU1NXT1JEOiBleGFtcGxlcGFzcwp2b2x1bWVzOgogICAgZGJfZGF0YTo="
  }
]

Переход в приложение

Перейдите в развернутое приложение по адресу http://.azurewebsites.net.

Выполните шаги по установке WordPress.

Подключение WordPress к Redis

Войдите в WordPress, используя учетную запись администратора. В области навигации слева последовательно выберите Plugins (Подключаемые модули) и Installed Plugins (Установленные подключаемые модули).

Выбор подключаемых модулей WordPress

Отображение всех подключаемых модулей

На странице подключаемых модулей найдите Redis Object Cache (Кэш объектов Redis) и щелкните Activate (Активировать).

Активация Redis

Щелкните Параметры.

Щелкните Settings (Параметры).

Нажмите кнопку Enable Object Cache (Включить Object Cache).

Нажатие кнопки "Enable Object Cache" (Включить Object Cache)

WordPress подключится к серверу Redis. Состояние подключения отобразится на той же странице.

WordPress подключится к серверу Redis. Состояние подключения, отображаемое на той же странице

Поздравляем! Вы подключили WordPress к Redis. Сейчас в готовом для рабочей среды приложении используется база данных Azure для MySQL, постоянное хранилище и Redis. Теперь вы можете горизонтального увеличивать масштаб плана службы приложений до нескольких экземпляров.

Поиск журналов контейнера Docker

Если при использовании нескольких контейнеров возникли проблемы, вы можете перейти к журналам контейнера по адресу https://.scm.azurewebsites.net/api/logs/docker.

Результат будет выглядеть примерно так:

[
   {
      "machineName":"RD00XYZYZE567A",
      "lastUpdated":"2018-05-10T04:11:45Z",
      "size":25125,
      "href":"https://.scm.azurewebsites.net/api/vfs/LogFiles/2018_05_10_RD00XYZYZE567A_docker.log",
      "path":"/home/LogFiles/2018_05_10_RD00XYZYZE567A_docker.log"
   }
]

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

Очистка развертывания

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

az group delete --name myResourceGroup

Производительность

Производительность кода всегда имеет большое значение, особенно при разработке сложных приложений. Существуют определенные практики, позволяющие оптимизировать ваш код для работы с high-load.

Оптимизируем запросы к базе данных

При запросах в базу данных WordPress в большинстве случаев стоит использовать WP_Query. Запросы через WP_Query имеют несколько полезных аргументов, а также выполняют много полезной работы в фоновом режиме, чего не происходит при использовании других методов доступа к базе, например get_posts().

Вот некоторые ключевые моменты:

Используйте только те запросы, которые вам действительно нужны. Каждый новый объект WP_Query по-умолчанию запускает 5 запросов к базе, включая пагинацию и обновление кэшей терминов и мета-полей. Правда, количество запросов можно сократить. Каждый из приведенных ниже аргументов убирает 1 запрос к базе:

'no_found_rows' => true: используйте там, где пагинация не нужна.

'update_post_meta_cache' => false: убирает обновление кэша метаполей. Полезно, если вам не нужны мета-поля в данном запросе.

'update_post_term_cache' => false: если вам не нужно получать термины таксономии, обновление их кэша лучше отключить.

'fields' => 'ids': вместо целого объекта на каждую запись, можно оптимизировать запрос и получать только ID записей.

Не рекомендуется использовать posts_per_page => -1, так как это потенциальная дыра в производительности. Что если у вас 100 000 записей? Один такой запрос может запросто положить сервер. Старайтесь всегда указывать разумные пределы для каждой ситуации. Например, если вы разрабатываете виджет для вывода произвольных записей в сайдбаре, укажите ограничение в 500 записей. Больше вряд ли когда-либо понадобиться.

 500, )); ?>

Не используйте $wpdb или get_posts() без весомой причины. get_posts() на самом деле вызывает WP_Query, но по-умолчанию обходит некоторые фильтры. Уверены, что вам это нужно? Скорее всего, нет.

Если вы не планируете использовать пагинацию результатов запроса, обязательно передайте параметр no_found_rows => true в WP_Query. Это попросит WordPress не включать SQL_CALC_FOUND_ROWS в SQL запрос, значительно увеличивая скорость его выполнения. Команда SQL_CALC_FOUND_ROWS рассчитывает общее количество строк в запросе, необходимое для работы пагинации.

) для лучшей производительности. new WP_Query( array( 'no_found_rows' => true, )); ?>

Избегайте использования аргумента post__not_in – в большинстве случаев быстрее отфильтровать нужные посты уже потом, с помощью PHP, чем внутри SQL запроса. Также, у вас будет преимущество лучшего кэширования. Учтите, однако, что такой подход может не работать с пагинацией без дополнительных танцев с бубном.

Попробуйте так:

 'post', 'posts_per_page' => 30 + count( $posts_to_exclude ) ) ); if ( $foo_query->have_posts() ) : while ( $foo_query->have_posts() ) : $foo_query->the_post(); if ( in_array( get_the_ID(), $posts_to_exclude ) ) { continue; } the_title(); endwhile; endif; ?>

Вместо:

 'post', 'posts_per_page' => 30, 'post__not_in' => $posts_to_exclude ) ); ?>

Подробнее можно прочитать на WordPress VIP

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

Использование аргумента cache_results => false в WP_Query почти всегда является плохой идеей. Если cache_results => true (а он по умолчанию true если у вас разрешено кэширование и настроен объектный кэш), WP_Query будет кэшировать найденные записи вместе с остальными данными. В очень редких случаях использование cache_results => false оправдано (например, при разработке собственных функций для WP-CLI).

Многоуровневые запросы стоит избегать. Примеры таких запросов:

  • Выборка записей из термов разных таксономий
  • Выборка записей значениям разных мета-полей

Пример 2-х уровневого запроса:

 'cat-slug', 'tag' => 'tag-slug', )); 

?>

Каждый новый “слой” в запросе создает JOIN к дополнительной таблицы в базе данных. Старайтесь запрашивать записи с минимальным количеством параметров, а для сложных выборок и фильтраций используйте PHP

WP_Query vs. get_posts() vs. query_posts()

Как мы уже писали выше, get_posts() и WP_Query очень похожи, за исключением некоторых нюансов. Оба метода примерно одинаково “стоят” вам в плане производительности.

query_posts(), напротив, ведет себя совершенно иначе и поэтому почти никогда не должен быть использован. И вот почему:

  • создает новый экземпляр объекта WP_Query с указанными вами параметрами.
  • заменяет собой существующий главный запрос (цикл)

Как отмечалось в Кодексе, query_posts() никогда не предназначался для использования в темах и плагинах, в первую очередь из-за способности к подмене и потенциальному дублированию главного запроса, что всегда негативно сказывается на производительности.

Создавайте массивы, поощряющие выборку по ключам, а не поиск по значениям

in_array() – не самый эффективный способ определения наличия искомого значения в массиве. В худшем случае, такой подход приведет к перебору всего массива, а это может увеличить сложность запроса до бесконечности. Команда WordPress VIP помечает использование in_array() как ошибку, именно из-за невозможности масштабировать основанные на нем решения.

Лучший способ определить, есть ли нужное значение в массиве, или нет – это создавать правильные массивы. Такие, в которых можно быстро находить нужные ключи с помощью isset(). isset() имеет постоянную скорость поиска и поэтому хорошо масштабируется.

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

 true,
 'bar' => true,
);
if ( isset( $array['bar'] ) ) {
  // value is present in the array
};

В случае, если вы не контролируете процесс создания массивов и вынуждены использовать in_array(), постарайтесь немного улучшить его производительность. Это можно сделать, указав 3 параметр strict : true, что заставит функцию использовать только строгое сравнение.

Кэширование

Кэширование по сути – просто сохранение обработанных данных где-либо для дальнейшего использования. И это невероятно важный принцип работы WordPress. Существуют различные способы использования кэширования и зачастую стоит использовать сразу несколько.

Объектное кэширование

Объектное кэширование позволяет сохранять объекты (логично) для использования в будущем. В мире WordPress, объекты хранятся в оперативной памяти и поэтому могут быть извлечены очень быстро.

Для работы с объектным кэшем, WordPress использует методы класса WP_Object_Cache. В дополнение к нему, Transients API (транзиты, транзитный кэш) отлично работает при кэшировании долгих запросов к базе данных, результатов работы сложных функций и тому подобных вещей.

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

Транзитный кэш также имеет особенность “протухания” и обычно для него указывают срок действия. Конечно, можно создавать транзиты без указания 3 параметра и тогда они никогда не “протухнут”. Этого лучше избегать, так как транзиты автоматически грузятся на при каждом запросе и со временем вы можете ухудшить скорость загрузки страниц вместо того, чтобы получить прирост.

Там, где доступно использование постоянного кэширования (Memcache, Redis и т.д.) функции работы с транзитами становятся обертками для методов WP_Object_Cache. Объекты и транзиты одинаково хранятся в объектном кэше, который, в свою очередь, находится в оперативной памяти. Как следствие, получение данных из объектного кэша возможно на любой странице и происходит очень быстро.

В высоко-нагруженные проектах без постоянного кэширования следует избегать использования транзитов из-за риска заполнения таблиц wp_options большим количеством данных. См. секцию “Разумное хранение данных”.

Имейте в виду, что поскольку объекты хранятся в памяти, они могут быть удалены в любой момент (например при перезагрузке сервера или очистке объектного кэша). Проектируйте свой код таким образом, чтобы он не зависел от наличия объектов в кэше.

Проще говоря, всегда проверяйте на наличие объекта в кэше и если его там нет – создавайте его на лету. Например:

have_posts() ) {
            // Cache the whole WP_Query object in the cache and store it for 5 minutes (300 secs).
            wp_cache_set( 'prefix_top_commented_posts', $top_commented_posts->posts, 'top_posts', 5 * MINUTE_IN_SECONDS );
        }
    }
    return $top_commented_posts;
}
?>

В вышеприведенном примере есть проверка на наличие в кэше объекта с 10 самыми комментируемыми записями, которая запускает генерацию этого списка в случае, если в кэше ничего нет. Как правило, все запросы к WP_Query, кроме основного, следует кэшировать

Так как результаты запросов кэшируются на 300 секунд, обращение к базе для обновления данных происходит всего раз в 5 минут. Этим можно неплохо экономить ресурсы, особенно на слабых серверах.

Однако здесь есть нюанс. Перестройка кэша в примере выше всегда будет вызываться посетителем, попавшим на “просроченный” кэш. В этот момент для всех остальных пользователей эта страница будет грузиться дольше, причем задержка расти пропорционально количеству одновременных посетителей. Также, на высоконагруженных проектах есть риск получить “состояние гонки”, когда несколько посетителей одновременно попадают на устаревший кэш и запускают его обновление. В худшем случае (большой трафик, неоптимизированные или сложные запросы к базе) “гонка” может привести к очередям на сервере базы данных, ошибкам записи и даже падению сайта из-за нехватки ресурсов, в первую очередь – оперативной памяти.

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

В WP есть хук, который срабатывает в нужном нам случае – wp_update_comment_count, который работает следующим образом: do_action( 'wp_update_comment_count', $post_id, $new, $old ).

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

Вот как это работает:

have_posts() ) {

            // Помещаем их в кэш, без срока экспирации.
            wp_cache_set( 'prefix_top_commented_posts', $top_commented_posts->posts, 'top_posts' );
        }
    }
    return $top_commented_posts;
}
?>

Такое решение позволяет хранить кэш объекта бесконечно и не волноваться об экспирации. Новые записи в кэше будут создаваться по мере надобности. Просто имейте ввиду, что некоторые системы внешнего кэширования (такие как Memcache) могут инвалидировать и очищать объекты в кэше самостоятельно, без всякого запроса со стороны WordPress.

Иногда необходимо создавать несколько объектов в зависимости от параметров, переданных в функцию. В таких случаях, хорошей практикой является создание cache key, в котором хранится переменная с этими параметрами. Простым решением здесь может стать добавление сериализованного параметра в виде md5 хеша к названию ключа.

Полностраничное кэширование

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

Batcache – плагин для WordPress, использующий объектный кэш (часто – Memcache) для хранения и отдачи сгенерированных страниц. Он также умеет кэшировать редиректы. Он может быть не так быстр, как другие плагины кэширования, но он может быть использован в тех случаях, когда кэширование отдельных файлов нежелательно или не может быть применено. (интересно бы посмотреть на такие ситуации – прим. WordPressify).

Беткэш сделан для того, чтобы не дать потоку нового трафика положить ваш сайт. Он достигает этого тем, что отдает старые (по-умолчанию 5-минутной давности) страницы новым посетителям. Это уменьшает нагрузку на процессор и базу данных сервера. Но также это значит, что некоторые посетители вашего сайта будут получать не самые “свежие” страницы. Правда, это относится только к гостям сайта, которые никак не взаимодействуют с ним, а просто просматривают. Как только посетитель авторизуется или оставляет комментарий, он всегда будет получать свежие страницы.

Несмотря на то, что использование такого плагина в целом имеет множество преимуществ, оно также накладывает определенные ограничения по коду:

  • Поскольку весь итоговый HTML кэшируется, вы не можете полагаться на серверную логику в отношении переменных $_SERVER$_COOKIE и других, которые уникальны для каждого отдельно взятого посетителя.
  • Вы можете, тем не менее, работать с cookie и другой пользовательской логикой на фронте, используя JavaScript

Batcache не отдает кэшированные страницы авторизованным пользователям (основываясь на нативных WordPress login cookies) – имейте это ввиду при разработке сайтов с высокой степенью интерактивности, таких как BuddyPress. Плагин также считает query в URL как часть адреса, т.е. страницы /your-page/ и /your-page?tracking=on будут фактически разными страницами. Это может значительно снизить эффективность кэширования на сайтах с отслеживанием UTM-меток (обычно используется в связке с Google Analytics). И не забывайте о том, что несмотря на использование плагина BatCache командой WordPress VIP, существуют определенные правила и условия его работы, которые не распространяются на публичную версию плагина.

Есть много популярных плагинов полностраничного кэширования, таких как W3 Total Cache и WP Super Cache, но мы не используем их по разным причинам. Тем не менее, для вашей конкретной ситуации они вполне могут подойти.

AJAX ендпоинты

Аббревиатура AJAX означает Асинхронный Яваскрипт и XML. Мы часто используем javascript в браузере для отправки запросов на эндпоинты, например для получение списка постов “бесконечного” скролла.

В WordPress встроено API для регистрации собственных AJAX-ендпоинтов на базе wp-admin/admin-ajax.php. По понятным причинам, WordPress не кэширует запросы внутри панели администрирования. Это значит, что отправляя любой запрос на admin-ajax.php, вы каждый раз загружаете ядро WordPress и минуете кэширование. Если это делать правильно, все будет хорошо. Но можно и “положить” сайт, просто отправляя запросы на admin-ajax.php с фронтенда.

По этой причине все ендпоинты, предназначенные для работы с клиентской стороны, лучше писать с использованием Rewrite Rules API и встраивать в цепочку запросов WordPress как можно раньше, используя хуки.

Вот просто пример того, как можно спроектировать ендпоинт таким образом:

get( 'api_item_id' );

	if ( ! empty( $item_id ) ) {
		$response = array();

		// Do stuff with $item_id

		wp_send_json( $response );
	}
}
add_action( 'template_redirect', 'prefix_do_api' );
?>

Кэширование запросов к сторонним источникам

Все запросы к сторонним сервисам, как синхронные, так и асинхронные, должны быть кэшированы. Если этого не делать, время загрузки вашего сайта будет напрямую зависеть от скорости сторонних сервисов, на которые вы никак не можете повлиять.

Вот небольшой пример того, как можно кэшировать подобные запросы:

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

Разумное хранение данных

Встроенные API WordPress позволяют нам хранить данные разными способами. Мы можем сохранять информацию в опциях, мета-полях записей, типах записей, объектном кэше или в термах таксономий.

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

  • Опции – API, работающее с опциями – это простая система хранения данных типа ключ-значение, использующая MySQL таблицу. Это API предназначалось для хранения небольших данных, таких как настройки цвета шапки или адреса сайта. Опции не созданы для хранения больших объемов произвольных данных. Производительность всего сайта может сильно пострадать от большого размера таблицы опций. Рекомендуется регулярно проверять таблицу wp_options и следить за тем, чтобы ее размер не превышал 500 строк. Поле “autoload” следует держать включенным (со значением ‘yes’) только для тех опций, которые действительно нужны вам в памяти для каждой страницы сайта. Кэширующие плагины также могут работать хуже с большими объемами опций в базе. Например, популярный плагин Memcached имеет ограничение в 1MB на размер отдельных элементов, хранящихся в кэше. Большая таблица опций может легко превысить этот лимит и значительно замедлить скорость загрузки страниц.
  • Post Meta (мета-поля) или Custom Fields (произвольные поля) – мета-поля по своей сути предназначены для хранения информации о конкретном посте. Например, если у нас есть тип записи “Продукт”, то информация о серийном номере отлично подходит на то, чтобы записать ее в мета-поле. По этой причине обычно не имеет смысла делать выборки постов на основе метаполей. Это всегда будет медленнее, чем другие способы, потому что значения ключей в таблице post_meta не индексируются и для поиска по ним используется обычный полнотекстовый перебор строк в MySQL.
  • Таксономии и Термы. Таксономии – это средство группировки записей. Если у нас есть несколько записей, которые можно объединить в группу по какому-либо критерию, этот критерий является отличным кандидатом на термин таксономии. К примеру, для типа записей “Машина” можно создать таксономию “Производители”, с термами “Nissan”, “Ford”, “Toyota” и т.д. Термы таксономий также хорошо подходят для поиска и сортировок на их основе, чего не скажешь о мета-полях.
  • Произвольные типы записей (Custom Post Types) – Архитектура WordPress основывается на сущности под названием “типы записей”. “Запись” – это тоже тип записи, и поначалу это может сбивать с толку. Мы можем создавать свои собственные типы записей для хранения разных видов данных. Если нужно хранить произвольное количество объектов, таких как товары или футбольные матчи, произвольные записи будут хорошим вариантом.
  • Объектное кэширование (Object Cache) – см раздел вышеSee the “Caching” section.

И хотя теоретически возможно использовать нативное WordPress Filesystem API для записи/получения данных в файлы, делать это не рекомендуется по причине конфликта такого подхода с большинством современных хостинг-провайдеров.

Запись в базу данных

Запись информации в базу данных является основой любого сайта. Вот несколько рекомендаций по этому поводу:

  • Старайтесь избегать запуска запросов на запись в базу с фронтенда. Это может негативно повлиять на производительность и вызывать условия “гонки” (одновременной отправки большого числа записей в базу, приводящее к потере или искажению данных)
  • Храните информацию в подходящих для этого местах. См. секцию Разумное хранение данных.
  • Опции сайта могут быть отмечены для “автозагрузки”, т.е. загружаться в объектный кэш на каждой страницы. Создавая или изменяя опции, не забывайте об аргументе $autoload, который вы можете передать в функцию add_option(). Если ваша опция не используется часто, не стоит загружать ее на всем сайте с помощью автозагрузки. Начиная с WordPress 4.2, вы можете легко изменять порядок загрузки уже существующих опций с помощью 3 необязательного аргумента $autoload функции update_option(). Это проще и удобнее, чем удалять-добавлять опции лишь для того, чтобы поменять в них значение autoload.

Паттерны проектирования

Если для вас важно развитие и удобство поддержки проекта в долгосрочном периоде – проще всего следовать паттернам (читай – практикам) проектирования PHP приложений. В этом разделе мы разберем стандартные паттерны, которые призваны облегчить ввод новых разработчиков в проект.

Неймспейсы

Мы используем неймспейсы во всем PHP коде, кроме шаблонов темы. Это означает что каждый PHP файл, который не является частью Иерархии Шаблонов WordPress, должен быть часть неймспейса (или псевдо-неймспейса) так, чтобы его содержимое не конфликтовало с другими классами или функциями, имеющими одинаковые названия.

Вкратце, это означает что в начале каждого PHP-файла мы добавляем идентификатор неймспейса, вот так:

Идентификатор неймспейса состоит из неймспейса верхнего уровня (обычно это название компании, “Vendor Name”). Затем обычно идет название проекта или продукта, в примере выше это Buy_N_Large. Дополнительные уровни используются по желанию разработчиков проекта.

Чаще всего, перед запуском команда договаривается между собой о стратегии использования неймспейсов и решает, что будет включаться в идентификаторы. Например, можно использовать название компании заказчика и дополнить его именем отдельного проекта, над которым вы работаете.

Когда команда работает над несколькими проектами для одного заказчика и разрабатывает плагин, который может быть использован между ними, имеет смысл заменить название проекта на Common или Global. Так будет видно отношение конкретного участка кода ко всей кодовой базе.

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

Объявления (declarations) use следует использовать для подключения классов, лежащих вне неймспейса выбранного файла. Лучше единожды указывать полные неймспейсы сторонних классов, чтобы потом обращаться к нему сразу по названию класса. Так значительно повышается читаемость кода и становятся наглядно видны зависимости. Это облегчит жизнь будущим разработчикам, которым придется разбираться в вашем коде.

Все, что объявляется в глобальном неймспейсе, включая сам неймспейс, должно быть уникальным. Неймспейс WordPressify – скорее всего, уникален. Theme – наверняка нет. Для дополнительной уникальности можно добавлять собственные префиксы к неймспейсам.

Проектирование объектов

Если функция не является специфичной для объекта, она должна быть помещена в неймспейс, как показано на примере выше.

Объекты следует делать атомарными, четко определенными и хорошо документированными (с помощью заголовков docblock). Каждый метод и свойство внутри объекта также должны быть документированы и относиться к объекту.

_post = get_post( $post );
	}
}

Видимость

В ООП (объектно-ориентированном программировании) публичные свойства и методы принято делать публичными (ваш Кэп). Все приватные методы следует объявлять protected, а не private. В вашем коде не должно быть никаких private полей или свойств без веской (и хорошо документированной!) причины.

Архитектура и паттерны

  • Не рекомендуется использовать синглтоны. Существует немного причин, оправдывающих их применение, и на практике они создают больше проблем, чем пользы. Особенно при последующей поддержке вашего кода.
  • Зависимости классов следует использовать как можно чаще (по возможности). Таким образом достигается принцип DRY, когда ранее написанные компоненты используются многократно в разных местах вашего приложения
  • Глобальных переменных стоит избегать. Если объекты нужно передавать по всей теме или плагину, объявляйте их как параметры или ссылайтесь на них через фабрику объектов
  • Скрытые зависимости (функции API, супер-глобальные переменные и т.д.) должны также быть задокументированы в заголовке docblock у каждой функции/метода или свойства.
  • Избегайте регистрации хуков в методе __construct. Эта практика жестко связывает кухи и экземпляр класса и является менее гибкой, чем регистрация хука отдельным методом. Также, это значительно затрудняет юнит-тестирование.

Разделяйте плагины и темы с помощью add_theme_support

Плагины должны быть полностью независимы от тем. Деактивация плагина не должна приводить ни к каким ошибкам в коде темы. Аналогично, переключение на другую тему не должно приводить к ошибкам в плагине.

Лучший способ добиться этого – это использовать функции add_theme_support и current_theme_supports.

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

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

Версионирование файлов

Использовать версии для файлов скриптов или стилей – всегда хорошая идея, которая сильно упрощает принудительный сброс кэша пользователей при регулярных обновлениях. К счастью, функции wp_register_script и wp_register_style позволяют нам указывать версии файлов, которые потом прибавляются к именам этих файлов в виде query-строки.

Мы рекомендуем использовать константу для указания версии файлов вашей темы или плагина, а затем обращаться к этой константе везде, где нужно. Например:

Не забывайте увеличивать версию каждый раз, когда меняете файлы. Это можно автоматизировать, например с помощью хука pre_commit.

Безопасность

Безопасность в контексте веб-разработки – очень обширная тема. Этот раздел обращает внимание только на те вещи, которые можно сделать на стороне сервера.

Валидация (validation) и санация (sanitization) вводимых данных

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

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

WordPress имеет несколько встроенных функций для валидации и очистки пользовательского ввода. Иногда бывает непонятно, что лучше использовать в конкретной ситуации. В некоторых случаях и вовсе лучше писать свои собственные методы для этих целей.

Вот пример валидации чисел (id), перед тем, как записать что-либо в мета-поле записи:

$_POST['user_id'] валидируется с помощью using absint(), которая проверяет что число >= 0. Без этого, $_POST['user_id'] может быть использован для внедрения вредоносного кода или данных в базу.

А вот пример санации (очистки) текстового поля перед сохранением его в базу данных:

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

Подготовка и очистка прямых SQL запросов

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

Прямые запросы в базу стоит проверять с особым вниманием. Они должны быть правильно подготовлены и очищены:

get_results( $wpdb->prepare( "SELECT id, name FROM $wpdb->posts WHERE ID='%d'", absint( $post_id ) ) );
?>

$wpdb->prepare() работает как sprintf() и по сути просто выполняет mysqli_real_escape_string() для каждого аргумента.

Функция mysqli_real_escape_string() оборачивает символы типа ' и ", предотвращая таким образом разные типы SQL атак.

Используя % в sprintf(), мы можем быть уверены что переданный аргумент является числом. Здесь вы можете спросить, зачем мы использовали еще и absint(), раз все уже очищено?. Да, но лучше иметь дополнительные слои очистки, чем пропустить что-то лишнее в базу по неосторожности.

А вот еще пример:

insert( $wpdb->posts, array( 'post_content' => wp_kses_post( $post_content ), array( '%s' ) ) );
?>

$wpdb->insert()создает новую строку в базе данных. $post_content передается в колонку post_content. Третий аргумент позволяет нам указывать формат, в стиле sprintf(). Можно принудительно указать, что передаваемое значение является строкой и предотвратить таким образом немало атак, связанных с SQL инъекциями. При этом, все равно стоит использовать wp_kses_post() для проверки $post_content на тот случай, если кто-нибудь решит передать вредоносный JavaScript код.

Экранирование (escape) или валидация (validate) вывода

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

WordPress имеет несколько встроенных в ядро функций, которые можно использовать для экранирования. Хорошей практикой является так называемое “позднее экранирование”. Это означает, что мы экранируем (проверяем на корректность) данные прямо перед самым выводом на экран. Это улучшает читаемость кода и даст вам уверенность в том, что вы точно не пропустили ничего лишнего.

Простой пример позднего экранирования вывода:

esc_html() очищает вывод от любых HTML тегов, таким образом предотвращая JavaScript-инъекции или случайно “поехавшую” верстку.

Или вот еще пример, на этот раз валидации вывода:

Email me

sanitize_email() проверяет, является ли итоговая строка валидным email-адресом. Таким образом мы проводим валидацию. В данном примере можно было бы использовать более общую функцию, типа esc_attr(), но sanitize_email() подходит лучше.

Другой пример:

esc_js() позволяет убедиться, что возвращаемая строка безопасная для вывода внутри скрипта JavaScript. Эта функция изначально предназначалась для использования внутри тегов-аттрибутов, таких как onfocus="...".

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

Например:

wp_json_encode() служит для проверки строк перед выводом в JavaScript коде. Она проверяет, является ли возвращаемая строка безопасной для вставки в ваш скрипт. Функция возвращает строку в формате JSON.

Также,  wp_json_encode() добавляет оборачивающие кавычки к строке.

Иногда вам нужно экранировать данные, которые предполагается использовать как атрибут. Для этого есть специальная функция esc_attr(). Она проверяет, чтобы выводимая строка содержала только допустимые для использования внутри атрибутов символы.


В случаях, когда нужно экранировать вывод таким образом, чтобы разрешить HTML теги, но вырезать потенциально вредный JavaScript, можно использовать функцию wp_kses_*:

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

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

А если вы все-таки используете wp_kses_* на фронтенде, итоговый результат следует кэшировать на максимально возможный срок.

Переведенные строки часто также нуждаются в экранировании вывода. Например так:

Вместо встроенной в PHP функции __(), что-то вроде esc_html__() может быть более применимо к вашей ситуации.  Общие функции_e()также лучше заменять на esc_html_e().

Существует множество ситуаций и примеров экранирования, которые мы не рассмотрели. Всем разработчиком настоятельно рекомендуем ознакомиться со статьей про экранирование и валидацию в Кодексе WordPress.

Нонсы (Nonces)

В программировании есть концепция нонсов. Nonce – a number used only once, в переводе означает число, используемое только раз. Нонсы являются инструментов для борьбы с  CSRF – межсайтосов подделкой запросов.

Задача у нонсов одна и она простая – сделать каждый запрос уникальным так, чтобы он не мог быть повторен извне. Реализация нонсов в WordPress не делает их на самом деле уникальными, хотя они все равно выполняют свою задачу.

Определение нонсов в WordPress звучит так: “Криптографический токен, привязанный к определенному действию, пользователю и временному отрезку”. Таким образом, даже если токены WordPress не является настоящим нонсом, он жестко привязан к действию, пользователю и временному отрезку, для которого был сгенерирован.

Давайте представим, что вы хотите отправить в корзину запись с ID 1. Для этого вам потребуется перейти на страницу, типа https://example.com/wp-admin/post.php?post=1&action=trash

Поскольку вы уже зарегистрированы и авторизованы, злоумышленник может попытаться подменить ваш запрос на: https://example.com/wp-admin/post.php?post=2&action=trash

По этой причине действие удаления записи в WordPress требует наличие валидного нонса (токена).

После посещения https://example.com/wp-admin/post.php?post=1&action=trash&_wpnonce=b192fc4204, этот же нонс не будет работать для https://example.com/wp-admin/post.php?post=2&action=trash&_wpnonce=b192fc4204.

Обновления и удаления записей должны всегда требовать рабочий нонс.

Приведем пример кода для создания нонса:

...

При обработке формы нонс должен быть проверен:

Поддержка переводов

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

WordPress имеет массу встроенного функционала для переводов. Разработчикам стоит уделить внимание таким возможностям, как pluralization и disambiguation, чтобы переводы были гибкими, а переводчики имели доступ ко всей необходимой для переводов информации.

Самуэль Вуд (Отто) собрал воедино все лучшие практики по переводам в WordPress и вам стоит уделить время и ознакомиться с этим гайдом: Internationalization: You’re probably doing it wrong

Здесь важно отметить, что данные, которые передаются в функции перевода, всегда должны быть именно строками. Не переменными или константами, а строками. Также не стоит использовать интерполяцию строк для вставки значений переменных в строки. Большинство инструментов для создания переводов используют библиотеку GNU gettext. При этом PHP код не запускается, а лишь сканируется и проверяется на возможность перевода, точно также как обычный текст. Если API переводов WordPress не могут точно сопоставить строку с шаблонами для переводов, перевести строку не получится. Чтобы избежать этого, используете printf formatting codes внутри строк, предназначенных для перевода, и передавайте переведенную версию строки в sprintf() для вывода значений переменных.

Вот как это работает:

При локализации проектов также важно помнить следующие вещи:

  • Использовать уникальный text domain во всех функциях перевода
  • Переведенные участки обязательно нужно экранировать при выводе

Текстовые домены

Каждый проект должен иметь собственные уникальные текстовые домены для строк. Текстовые домены (text domains) следует писать на латинице, используя буквы, цифры и тире для разделения нескольких слов. Например: tenup-project-name.

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

Если ваш код предназначен для релиза в составе плагина или темы в репозиторий WordPress.org, текстовый домен должен совпадать с именем папки проекта. Это нужно для обеспечения совместимости с системой доставки языковых пакетов WordPress.

Текстовый домен также нужно указывать в заголовке “Text Domain” главного файла плагина или файла стилей темы, чтобы обширное сообщество WordPress могло начать добавлять собственные версии переводов с помощью GlotPress.

Экранирование строк

Большинство встроенных в WordPress функций перевода по умолчанию не экранируют вывод строк. Вот почему важно экранировать переведенные строки также, как и любые другие данные.

Для облегчения этой задачи, WordPress API имеет функции, способные одновременно переводить и экранировать строки. Мы рекомендуем разработчикам использовать именно эти функции:

Для переводов в HTML

  1. esc_html__: возвращает переведенную и экранированную строку
  2. esc_html_e: выводит переведенную и экранированную строку
  3. esc_html_x: возвращает переведенную и экранированную строку, передает контекст в функцию переводов gettext

Для переводов атрибутов

  1. esc_attr__: возвращает переведенную и экранированную строку
  2. esc_attr_e: выводит переведенную и экранированную строку
  3. esc_attr_x: возвращает переведенную и экранированную строку, передает контекст в функцию переводов gettext

Оформление кода и документация

Мы следуем официальным стандартам оформления кода и документации, принятым в мире WordPress. Расширение WordPress Coding Standards for PHP_CodeSniffer позволяет находить большинство распространенных отклонений от стандарта и помечать некорректный код для ручной оценки.

Также, мы крайне рекомендуем подробно комментировать и документировать весь код, с акцентом на использование длинных описаний в docblock секциях. Эти описания должны отвечать на 2 главных вопроса: “Почему этот код здесь?” и “Что именно делает этот код”, причем делать это понятным обычному человеку языком. Хорошим считается такое описание, которое может понять ваш менеджер (не программист), просто прочитав docblock и сопутствующие инлайновые комментарии.

Например, такое:

Юнит-тестирование и интеграционное тестирование

Юнит-тестирование заключается в автоматическом тестировании юнитов (элементов) вашего исходного кода на основании заранее написанных сценариев. Цель юнит-тестирования состоит в создании таких сценариев, которые смогут ответить на вопрос: “действительно ли тестируемый участок кода работает так, как задумывалось?”. Если тест не пройден, обнаруживается потенциальная проблема и код отправляется на доработку.

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

В целом, хорошей практикой будет внедрение юнит- и интеграционных тестов для приложений, предназначенных для публичного релиза. Разработка тестов для клиентских тем на WordPress обычно не дает большого прироста качества конечного результата (здесь, конечно, бывают исключения). При написании тестов рекомендуем использовать PHPUnit, который является стандартной библиотекой в WordPress.

Подробнее про тестирование можно прочитать на странице PHPUnit и в разделе автоматизированное тестирование в WordPress.

Библиотеки и фреймворки

Как правило, для разработки под WordPress лучше не использовать PHP фреймворки или библиотеки, которые не включены в ядро. API WordPress предоставляют 99% всех функций, необходимых в ежедневной работе: от работы с базой данных до отправки емейлов. Также в него входят другие открытые библиотеки и фреймворки (например, PHPUnit), которые можно использовать при создании тем и плагинов.

Избегайте Heredoc и Nowdoc

Встроенный в PHP синтаксис дает возможность оставлять большие куски HTML внутри кода и не волноваться о том, как соединить вместе несколько независимых строк. Такой код проще читать и воспринимать, особенно для начинающих разработчиков.

$y = then stop moving it like that!"
JOKE;

Однако, синтаксис heredoc/nowdoc делает невозможным применение практики позднего экранирования (late escaping):

// Раннее экранирование
$a = esc_attr( $my_class_name );

// Что-то некрасивое может произойти здесь, уже после экранирования
$a .= 'something naughty';

// Поэтому хорошо бы попробовать экранировать сразу в месте вывода, вот здесь
echo test
HTML;

Какими бы удобными они вам не казались, следует избегать использования синтаксисов heredoc/nowdoc в реальных проектах, заменяя их стандартными методами конкатенации (объединения) и вывода строк. Читать HTML в таком случае несколько сложнее. Но зато мы можем быть уверенными в том, что экранирование сработает как надо в месте вывода, независимо от состояния переменных до этого.

// Здесь могли испортить строку...
$my_class_name .= 'something naughty';

// Но это неважно, потому что мы практикуем позднее экранирование
echo '
test
';

А еще лучше будет использовать встроенную в WordPress функцию get_template_part() в качестве базового шаблонизатора. Создавайте шаблоны как можно более чистыми. Пусть в них был только HTML код и немного  вставок там, где вам нужно выводить и экранировать данные. Итоговый файл будет иметь такую же читаемость, как блоки heredoc/nowdoc, но вы сможете практиковать позднее экранирование в самом шаблоне.

Типы хостингов и их различия

Чтобы понять, какой хостинг подойдёт для вашего проекта, нужно знать их типы и различия между ними. Если вы далеко не новичок в этом, то смело пропускайте эту главу и читайте дальше.

Хостинг — дом для сайта, в котором должно быть всё необходимое. Можно арендовать комнату в общежитии — виртуальный или shared-хостинг, однокомнатную квартиру — VPS/VDS или большой загородный дом — выделенный сервер.

Виртуальный хостинг

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

Shared-хостинг подойдёт для информационных сайтов, визиток, интернет-магазинов с небольшим количеством товаров. С хорошей оптимизацией средний тариф легко потянет 2-5 тысяч посетителей в сутки.

VPS или VDS

Виртуальный сервер, который работает на базе физического. Из плюсов: выделенный IP, независимость от «соседей», защита от сетевых атак.

VPS подойдёт для средних проектов на 7-10 тысяч уников. Он пользуется спросом у вебмастеров, которые владеют несколькими десятками или сотнями проектов, так как количество сайтов/баз данных/пользователей FTP ограничивается только ресурсами сервера.

Выделенный или dedicated-сервер

Представляет собой физический компьютер, который размещён в дата-центре. Клиент арендует его мощность и может удалённо использовать ресурсы системы. Полный контроль, сравнимый с правами суперадминистратора на Android-смартфоне.

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

Требования к хостингу для сайта на WordPress

Требования WordPress к хостингу минимальные:

  • PHP 7.3+.
  • MySQL 5.6+.
  • Сервер на Nginx или Apache с модулем для формирования постоянных ссылок mod_rewrite.
  • HTTPS.

Любой вменяемый хостинг обладает всеми вышеперечисленными характеристиками и даёт возможность установить CMS «из коробки» через специальный модуль.

Лучшие хостинги для сайта на WordPress

Список пользовательских требований к хостинг-провайдеру более длинный:

  • Удобная и функциональная панель: cPanel, ISPmanager или самописная.
  • Гибкие и недорогие тарифы с возможностью добавлять/удалять услуги.
  • Отзывчивая техподдержка.
  • Хороший uptime — время работы сервера. В идеале, показатель должен быть равен 100%.
  • Высокое быстродействие — время обработки запросов.
  • Неограниченный трафик — количество посещений сайта.
  • Постоянное резервное копирование — каждый день или раз в 2-3 дня. Как альтернатива — выгрузка в Dropbox или Google Drive.

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

Мы отобрали 10 достойных внимания провайдеров и сравнили их между собой по критериям из списка. За победу в цифрах по каждому пункту хостинг получает 1 звезду.

Хостинг Быстродействие
(кол-во запросов в секунду)
Uptime Поддержка
(скорость ответа)
Стоимость в месяц
(при оплате за год)
Трафик Рейтинг
Timeweb 168 100% 16 минут 119 рублей ☆☆
Beget 140 100% 4 минуты 140 рублей ☆☆☆
Mchost 437 100% 9 минут 114 рублей ☆☆
IHC 3278 100% 3 минуты 109 рублей ☆☆☆☆
Fozzy 99.97% 22 минуты 133 рубля
Fornex 227 99.95% 7 минут 74 рубля
Webhost1 98 99.98% 6 минут 102 рубля
Eurobyte 529 100% 9 минут 159 рублей ☆☆
Majordomo 438 100% 8 минут 99 рублей ☆☆☆
Sprinthost 118 99.99% 7 минут 118 рублей

3 лучших платных хостинга для начинающих

Из всех перечисленных хостеров мы выделили три оптимальных варианта по соотношению цена-качество. Небольшой тревел блог вполне комфортно разместится на минимальном тарифном плане любого хостинга из тройки призёров.

IHC

Провайдер работает на рынке с 2009 года, 25 тысяч клиентов. Новых пользователей может смутить главная страница официального сайта, которая несколько перегружена информацией.

Хостинг IHC

Возможности

Можно оплатить услугу виртуального хостинга, арендовать VPS или выделенный сервер. Перед пополнением баланса пользователь может настроить тариф: выбрать панель управления, настроить конфигурацию оборудования, установить SSL сертификат Let’s Encrypt, установить CMS. В качестве бонуса, хостер выдает промокод на пополнение баланса в Google Adwords.

Тарифы

Тарифная сетка IHC делится на 4 обычных варианта и 1 премиум. В течение 7 дней можно тестировать качество услуг.

Критерий One Basic Optimum Maximum Premium
Стоимость
(в месяц при оплате за год)
83 рубля 133 рубля 191 рубль 450 рублей 1125 рублей
Пространство 1 ГБ 5 ГБ 10 ГБ 20 ГБ 200 ГБ
Кол-во сайтов 1 4 10 40
Кол-во баз данных
Защита от DDoS + + + + +
Выделенные IP адреса
(помесячная оплата)
100 рублей/шт. 100 рублей/шт. 100 рублей/шт. 100 рублей/шт. 100 рублей/шт.

Поддержка

Получить обратную связь от технических специалистов можно в онлайн-чате, тикетах, по электронной почте, в группе «ВКонтакте» и по телефону. Пользователи в отзывах часто говорят о некачественном уровне обслуживания техподдержки — проблемы не решаются в полном объёме.

Плюсы и минусы

Преимущества Недостатки
Наличие тестового периода Неудобная панель управления IHC
Низкая стоимость услуг Посредственная техподдержка
Защита от cетевых атак Низкие лимиты нагрузки
Частое падение серверов

Majordomo

На рынке с 2000 года, 45 тысяч пользователей. Дизайн сайта, как и у IHC — посредственный, стоит поработать над юзабилити и фирменным стилем. Однако среди клиентов — Acer и Lenovo.

Хостинг Majordomo

Возможности

Majordomo даёт возможность регистрировать домены, арендовать виртуальный хостинг, VPS/Dedicated. Доступные панели управления: самописная, cPanel, ISPmanager. Есть защита от DDoS атак, за дополнительную плату (1-2$ в месяц) включается антивирус.

Тарифы

Тарифные планы делятся на базовые (3) и корпоративные (2). Корпоративная подписка даёт приоритетную поддержку, юридическую консультацию и размещение на отдельных серверах. Двухнедельный тестовый период.

Критерий Старт Безлимитный Безлимитный+ Бизнес Бизнес +
Стоимость
(в месяц при оплате за год)
99 рублей 199 рублей 299 рублей 599 рублей 749 рублей
Пространство 5 ГБ 10 ГБ 15 ГБ 10 ГБ 15 ГБ
Кол-во сайтов 10 1 сайт 3 сайта
Кол-во баз данных
Защита от DDoS есть есть есть есть есть
Выделенные IP адреса
(помесячная оплата)

Поддержка

Специалисты технической поддержки отвечают в тикетах и онлайн-чате. Менеджеры иногда отзываются быстро — в течение 10 минут, но иногда ответ приходится ждать 1-2 часа. Отзывы клиентов о работе саппорта в целом положительные, но есть и негативные комментарии.

Плюсы и минусы

Преимущества Недостатки
Отзывчивая техподдержка Скорость загрузки оставляет желать лучшего
Удобная самописная панель Сайты периодически недоступны
Доступные цены

Beget

Один из самых популярных хостинг-провайдеров в Рунете. Компания работает с 2007 года, 152 тысячи клиентов. Аккредитованный регистратор доменных имён. Официальный сайт оформлен хорошо, удобство на максималках, собственное приложение под Android/iOS.

Хостинг Beget

Возможности

Beget даёт в аренду shared-хостинг, VPS и выделенные сервера. Удобная панель управления с понятной структурой. Гибкая настройка PHP, изоляция заражённого сайта от других ресурсов на аккаунте, быстрое создание и восстановление резервных копий.

Тарифы

Тарифы на виртуальный хостинг более дорогие, чем у конкурентов. 30-дневный бесплатный период и возможность вернуть средства, если не устроит качество услуг. Подписки делятся на две категории: базовые и VIP.

Критерий Blog Start Noble Great Town City Mega
Стоимость
(в месяц при оплате за год)
115 рублей 150 рублей 245 рублей 390 рублей 820 рублей 1200 рублей 2250 рублей
Пространство 3 ГБ 10 ГБ 20 ГБ 25 ГБ 30 ГБ 40 ГБ 50 ГБ
Кол-во сайтов 2 5 10 25 50 75
Кол-во баз данных
Защита от DDoS
Выделенные IP адреса
(оплата за год)
660 рублей/шт. 660 рублей/шт. 660 рублей/шт. 660 рублей/шт. 660 рублей/шт. 660 рублей/шт. 660 рублей/шт.

Поддержка

Консультируют в мессенджерах: Telegram, Skype, по телефону (Украина и Россия) и в тикетах. Ещё есть группа «Вконтакте», там отвечают чуть дольше. Отзывы клиентов о техподдержке положительные, отзывчивость на уровне.

Плюсы и минусы

Преимущества Недостатки
Быстрая панель управления Поддомены считаются как сайты
Конструктор тарифного плана Периодические падения
Приложение для смартфона Система лимитов
Встроенный антивирус
Закрывающие документы для юрлиц

3 лучших бесплатных хостинга для начинающих

Бесплатный хостинг — скорее зло, чем добро. Обычно за бесплатностью скрывается множество ограничений. Тем не менее, для небольшого или нового блога вполне логично выбрать бесплатный хостинг, а когда посещаемость вырастет подобрать что-то платное.

WordPress.com

Бесплатный WordPress хостинг от разработчика CMS. Подойдет для небольших блогов и маленьких сайтов-визиток.

Хостинг WordPress

Возможности

В бесплатный тариф включено доменное имя в зоне travel.blog или wordpress.com. Другие домены в международных зонах доступны только в платных подписках.

Функционал ограниченный:

  • Статистика посещаемости и подписчиков.
  • Лог последних 20 событий.
  • Добавление страниц, медиафайлов.
  • Управление комментариями.
  • Импорт контента с Wix, Blogger и т.д.
  • Настройка дизайна AMP страниц для Google.
  • 284 темы, разделённые по категориям.

Поддержка в чате и по email предоставляется только на платных тарифах. В остальных случаях придется обращаться в сообщество Вордпресс.

Плюсы и минусы

Преимущества Недостатки
Высокая скорость загрузки сайта Нельзя установить плагины
Конструктор дизайна Нет поддержки
Поддержка AMP Встроенная реклама
Три сотни шаблонов Нельзя использовать собственный домен
Исходный код заблокирован

Hostiman

Для регистрации бесплатного тарифа нужно сделать селфи с паспортом на фоне сайта или зарегистрировать .ru домен, вступить в группу «Вконтакте» и создать тикет в панели клиента.

Хостинг Hostiman

Возможности

Параметров free-сервера вполне хватит для обучения:

  • 2 сайта, домена и базы данных;
  • 1 ГБ для файлов.
  • Новые версии PHP 7.x.
  • Поддержка Cron.
  • 2 домена третьего уровня.
  • phpMyAdmin для удобного управления базами данных.
  • Панель ISPmanager, которой нет даже в некоторых платных хостингах.

Панель управления услугами Hostiman удобная, но не вызывает восхищения как, например, у Beget.

Поддержка

Поддержка предоставляется в полном объеме. Задать вопрос можно в тикетах и группе «Вконтакте», онлайн-чата нет. Клиенты отмечают, что технические специалисты оперативно решают проблемы.

Плюсы и минусы

Преимущества Недостатки
Нет рекламы Ежемесячное посещение личного кабинета для активации услуги
Техподдержка Предоставление документов
Резервные копии
Управление версией PHP
Бесконечный трафик
Конструктор сайтов
Установка CMS в 1 клик

000webhost

Аффилирован с известным free-хостингом Hostinger, подходит для начинающих вебмастеров.

Хостинг 000webhost

Возможности

В бесплатный тариф входит: 1 ГБ места на диске, 10 ГБ трафика, 2 базы данных, 2 сайта, парковка доменных имён. Доступен конструктор, импорт из Wix.

Из фишек также стоит выделить:

  • Управление версией PHP.
  • Доступ через FTP клиент.
  • 50 писем в день через Sendmail.
  • Восстановление, сброс и удаление сайта.
  • Статистика нагрузки на сервер.
  • Защита каталогов паролем.
  • Редиректы, логи.

Поддержка не предоставляется.

Плюсы и минусы

Преимущества Недостатки
Созданный сайт быстро загружается Встроенная реклама
Привязка доменов Нет поддержки
FTP и PhpMyAdmin Лимит по трафику
Удаление неактивных сайтов
Странный перевод панели

Какой хостинг выбрать?

Достойных хостеров много. Перед тем как сделать окончательный выбор убедитесь, что:

  1. Компания известна в сети и начала работать не вчера.
  2. Клиенты отзываются положительно и рекомендуют хостинг.
  3. Выбранный тариф подходит для вашего проекта.

Лучше запастись аккаунтами на нескольких хостингах, чтобы при возникновении трудностей быстро поменять «дом» и минимизировать потери трафика. Главные критерии: аптайм, быстродействие, гибкость.

Лучше выбрать платный или бесплатный хостинг?

Новичкам, скорее всего, подойдут фри-хостинги. Обратите внимание на Hostiman — среди конкурентов в нише он даёт максимум преимуществ. В остальных случаях лучше потратить 2-3 тысячи рублей в год на минимальный тариф платного хостинга.

Если вы хотите замахнуться на проект вроде «Туристера», то лучше арендовать выделенный сервер и найти компетентного администратора.

Бесплатный хостинг — как демо видеоигры, даёт минимум контроля. С платным вы почувствуйте комфорт и полную свободу.

WordPress

WordPress — бесплатная и наиболее распространенная система управления контентом. На этом движке работают более 35% веб-сайтов во всем мире и почти 45% в Рунете.

Для каких сайтов подходит?

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

Системные требования

Основные технические характеристики WordPress:

  • язык программирования – PHP (версия 7.4 и выше);
  • базы данных – MySQL (версия 5.6 и выше), MariaDB (версия 10.1 и выше);
  • операционные системы – Windows, UNIX;
  • веб-сервер – Apache, Nginx.

Стоит учитывать, что сайт на WordPress не будет работать на uCoz и прочих хостингах, которые не поддерживают PHP, что несколько уменьшает возможности применения движка.

Безопасность и производительность

На WordPress есть несколько важных функций с точки зрения безопасности и производительности:

  • модерация публикуемых материалов;
  • разграничение доступа;
  • кэширование страниц;
  • поддержка SSL.

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

Возможности самостоятельного конфигурирования

Сайты на WordPress легко масштабировать, добавляя дополнительные плагины. Из небольшого корпоративного сайта на ВордПресс можно сделать полноценный портал, добавив онлайн-магазин, форум и прочие страницы.

Удобство использования

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

Встроенные модули

На ВордПресс доступны базовые встроенные модули: поддержка RSS, настройка форм обратной связи, фотогалерея, поиск по сайту и прочие. Есть возможность устанавливать дополнительные плагины, чтобы улучшить функционал. Большая часть из них находится в свободном доступе. Также есть платные модули, а некоторые бесплатные плагины имеют расширенную pro-версию с дополнительным набором функций.

WordPress — одна из наиболее «дружелюбных» платформ для SEO-оптимизации. На движке в базовой версии есть немного встроенных функций. Однако пользователи имеют возможность установить темы, которые помогут вывести сайт на первые строчки в поисковых системах.

1С-Битрикс


1C-Битрикс – коммерческая система управления контентом. Среди платных CMS в русскоязычной онлайн-среде продукт занимает лидирующую позицию. В общем рейтинге система удерживает второе место после ВордПресс – его используют более 13% сайтов.

Для каких сайтов подходит?

CMS 1C-Битрикс – решение преимущественно для крупных сайтов. Движок используют для площадок, где требуется широкий набор функций: интернет-магазинов, корпоративных порталов. Для небольших сайтов, например, лендингов или визиток 1С-Битрикс использовать невыгодно из-за высокой стоимости продукта.

Но это не значит, что движок подходит только для больших площадок. Продукт представлен в нескольких редакциях, которые продают по отдельным лицензиям. Например, тариф «Старт» позволяет создать небольшой корпоративный сайт. Редакция для бизнеса подходит для интернет-магазинов. Цена лицензии станет непосильно высокой для начинающих компаний, поэтому на первых этапах развития стоит отдавать предпочтение бесплатным CMS. Пользоваться 1С-Битрикс в подобных случаях целесообразно, когда планируется расширение проекта.
Кстати, наш хостинг прекрасно справится с размещением любого проекта на 1С-Битрикс!

Системные требования

Среди минимальных требований для системы управления контентом:

  • языки программирования – PHP (версия 7.1 и выше);
  • базы данных – MySQL (версия 5.6 и выше);
  • операционные системы – Windows, UNIX;
  • веб-серверы – Apache.

Даже минимальные рекомендованные технические характеристики дают широкие возможности для использования движка на разных хостингах.

Безопасность и производительность

1C-Битрикс – продукт с высокой степенью защиты. Безопасность обеспечивают встроенные инструменты, также можно купить дополнительные расширения. Система предназначена, в первую очередь, для крупных проектов, поэтому отличается высокой производительностью.

Возможности самостоятельного конфигурирования

1С-Битрикс – это система управления контентом с большими возможностями масштабирования. Чтобы расширить проект, достаточно приобрести редакцию с более широким функционалом. Разработчик может устанавливать не только готовые решения, но и собственноручно созданные модули и шаблоны. Это открывает широкие возможности для создания индивидуальных крупных проектов.

Удобство использования

CMS недостаточно удобна для начинающих разработчиков и пользователей. В бесплатном доступе нет полноценных руководств – обучающая информация в полном объеме представлена в платных курсах.

Встроенные модули

Платформа поддерживает другие решения компании 1С и сторонние продукты. Количество встроенных плагинов и возможности их установки зависят от редакции системы. Младшие версии CMS по функциональности сопоставимы с бесплатными системами. Чтобы получить более широкие возможности, нужно заплатить за расширенную редакцию.

Joomla!

Бесплатный движок Joomla! используют порядка 11% сайтов в Рунете. Система популярна не только в странах СНГ, но и во всем мире и входит в ТОП-5 лидирующих CMS.

Для каких сайтов подходит?

Как и WordPress, Joomla! подходит для всех типов сайтов. При этом не имеет значение масштаб: система одинаково оптимальна для небольших страниц и крупных площадок.

Системные требования

Минимальные технические параметры для Joomla! 3.x:

  • языки программирования – PHP (версия 5.3.10 и выше);
  • базы данных – MySQL (версия 5.5.3 и выше), MS SQL (версия 10.50.1600.1 и выше), Postgres SQL (версия 9.1 и выше);
  • операционные системы – Windows, UNIX
  • веб-серверы – Apache, IIS, nginx.

На большинстве хостингов сайты на Joomla! разворачиваются в один клик.

Безопасность и производительность

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

Возможности самостоятельного конфигурирования

Движок предоставляет возможность создавать неограниченное количество страниц, что удобно для масштабирования проекта. Также можно устанавливать самостоятельно разработанные плагины и создавать индивидуальные макеты.

Удобство использования

Чтобы разобраться, как работает CMS, не нужно долгое время прокачивать скиллы и получать специальные навыки. Установка и настройка системы не вызывают проблем даже у новичков, поэтому движок считается достойной альтернативой ВордПресс.

Встроенные модули

Базовый функционал Joomla! довольно широкий. На движке есть встроенные модули для форумов, RSS, FAQ, интернет-магазина. Расширить возможности помогают разнообразные плагины. Устанавливать их можно из официальных или посторонних источников.
Также необходимо учитывать, что при апдейте Joomla! расширения в старых версиях будут работать некорректно. Это распространенная проблема, которая главным образом касается бесплатных плагинов, — разработчики не всегда вовремя выпускают обновления.

OpenCart

OpenCart — бесплатная CMS, предназначенная для онлайн-магазинов. В русскоязычном интернет-пространстве систему используют около 3% площадок.

Для каких сайтов подходит?

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

Системные требования

Технические требования системы:

  • языки программирования – PHP (версия 5.4 и выше);
  • базы данных – MySQLi;
  • операционные системы – Windows, UNIX;
  • веб-серверы – Apache (рекомендовано), IIS, nginx.

OpenCart подходит для большинства платных хостингов — бесплатные чаще всего не соответствуют системным требованиям CMS.

Безопасность и производительность

Достоинство CMS — хорошая базовая защищенность, которая включает:

  • фиксацию действий пользователей;
  • защиту от автоматического заполнения капчи;
  • модерацию публикаций;
  • распределение прав доступа;
  • поддержку безопасного SSL-протокола.

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

Возможности самостоятельного конфигурирования

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

Система открывает большие возможности для онлайн-продаж на территории СНГ. CMS интегрирована со многими сервисами доставки и оплаты товаров, в том числе и продуктами Яндекса. Если бизнес выходит на международный уровень, сайт легко сделать мультиязычным. Также есть возможность подключить европейские и американские сервисы для доставки и оплаты.

Удобство использования

OpenCart подходит для новичков в разработке. Для управления предусмотрена удобная панель администратора. Интерфейс удобный и полностью русифицированный.

Встроенные модули

Функций OpenCart даже в базовом исполнении достаточно для развития интернет-магазина. Если функционала мало, доступно множество расширений, разработанных для сферы электронной коммерции.

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

Drupal

Drupal — бесплатная система управления контентом с открытым исходным кодом. В рейтинге популярности в Рунете движок занимает пятое место. Его используют для более чем 3% сайтов.

Для каких сайтов подходит?

Drupal можно использовать для сайтов любого направления. Преимущественно движок применяют для крупных проектов, которые требуют высокой производительности. Для небольших блогов оптимальнее будут альтернативные бесплатные системы.

Системные требования

Основные требования Drupal:

  • языки программирования – PHP (версия 7.2 или выше);
  • базы данных – MySQL (версия 5.5.3 и выше), Postgres SQL (9.1.2 или выше), SQLite (версия 3.4.2 или выше);
  • операционные системы – Windows, UNIX;
  • веб-серверы – Apache, nginx, IIS.

Стоит упомянуть, что CMS корректно работает только на высокопроизводительных хостингах. При недостаточной мощности контент будет прогружаться медленно, несмотря на отличные базовые функции.

Безопасность и производительность

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

Возможности самостоятельного конфигурирования

Drupal можно адаптировать и кастомизировать для простых сайтов или сложных веб-приложений. Система гибкая за счет открытого исходного кода и возможности внедрить собственные настройки.

Удобство использования

Drupal имеет не очень «дружелюбный» интерфейс. Мастеру, который еще не работал с этой CMS, он покажется сложным за счет большого количества настроек. Drupal – система для более опытных разработчиков. Упростить задачи по обучению помогут руководства от сообщества пользователей. Установить же систему можно из личного кабинета на хостинге в считанные минуты.

Встроенные модули

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