понедельник, 14 декабря 2015 г.

zabbix + iostat

Где взять:
Итак, мониторинг состоит из файла конфигурации для агента, двух скриптов для сбора/получения данных и шаблон для веб-интерфейса. Все это доступно в репозитории на Github, поэтому любым доступным способом (git clone, wget, curl, etc...) скачиваем их на машины которые хотим замониторить и переходим к следующему пункту.

Как настроить:
  • iostat.conf — содержимое этого файла следует поместить в файл конфигурации zabbix агента, либо положить в каталог конфигурации который указан в Include опции основной конфигурации агента. Вобщем зависит от политики партии. Я использую второй вариант, для кастомных конфигов у меня отдельная директория.
  • scripts/iostat-collect.sh и scripts/iostat-parse.sh — эта два рабочих скрипта следует скопировать в /usr/libexec/zabbix-extensions/scripts/. Тут также можно использовать удобное вам размещение, однако в таком случае не забудьте поправить пути в параметрах определенных в iostat.conf. Не забудьте проверить что они исполняемы (mode=755).

заливать файлы в бинарном режиме

Как настроить в web интейрфейс:
Теперь остался шаблон iostat-disk-utilization-template.xml. Через веб интерфейс импортируем его в раздел шаблонов и назначем на наш хост. Тут все просто. Теперь остается ждать примерно один час, такое время установлено в LLD правиле (тоже настраивается). Или можно поглядывать в Latest Data наблюдаемого хоста, в раздел Iostat. Как только там появились значения, можно перейти в раздел графиков и понаблюдать за первыми данными.

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

Iotop или jbd2/sda1-8

iotop - консольная программа, написанная на Python и выводящая данные по использованию жесткого диска. Это отличная программа для того, чтобы узнать, какой процесс использует ваш жесткий диск в настоящее время. Эта команда аналогична команде top. Вы можете использовать стрелки перемещения для изменения сортировки процессов.
Как раз программа из серии ответов на вопросы типа:
  • как определить какой процесс обращается к жесткому диску в linux

Установка iotop

В системе DebianUbuntuLinux Mint.
sudo apt-get install iotop В системе Red HatFedora,CentOS yum install iotop

Использование

Если запустить программу iotop с ключом -o, то будут выведены наиболее активные процессы.
Если смотреть на кучу нулей нет нужды, можно вывести только те данные, которые имеют какие-либо значения:
iotop –only
Собираем статистику за определённое время. Например, ставим эту программу минут на 10 и смотрим, что же за эти 10 минут произошло:
iotop -o -a
Этот вариант, например, позволил мне найти решение проблемы, когда запись на флешку идёт очень долго. Основным пожирателем ресурсов оказался jbd2/sda1-8. Для решения этого отдаём команду
mount -o remount,rw,commit=1200 /dev/sdb1

Расшифровка параметров

  • TID - ID процесса, его же можно посмотреть в ps auxf
  • PRIO - приоритет процесса
  • USER - имя пользователя, от которого запущен процесс
  • DISK READ - скорость чтения с диска
  • DISK WRITE - скорость записи на диск
  • SWAPIN - процент в свап
  • IO - процент напрямую
  • COMMAND - команда, которая “безобразничает” и которую так долго искали

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

суббота, 12 декабря 2015 г.

Установка Zabbix



wget http://repo.zabbix.com/zabbix/2.2/ubuntu/pool/main/z/zabbix-release/zabbix-release_2.2-1+trusty_all.deb

sudo dpkg -i zabbix-release_2.2-1+trusty_all.deb
sudo apt-get update && sudo apt-get -y dist-upgrade
sudo apt-get install zabbix-server-mysql zabbix-frontend-php zabbix-agent


запускаем
Start the server :
sudo /etc/init.d/zabbix-server start

Start the agent:
sudo /etc/init.d/zabbix-agent start

проверяем
ps -aux | grep zabbix


Также добавим zabbix server и агент в автозапуск
systemctl enable zabbix-server-pgsql
systemctl enable zabbix-agent

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

Создание, Форматирование, Монтирование разделов на диске для Ubuntu

Будем использовать утилиту fdisk. Посмотреть список дисков подключенных к компьютеру можно командой:
fdisk -l
Вывод примерно следующий:
Диск /dev/sdc: 21.5 ГБ, 21474836480 байт
255 heads, 63 sectors/track, 2610 cylinders
Units = цилиндры of 16065 * 512 = 8225280 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disk identifier: 0x000bedde
Устр-во Загр     Начало       Конец       Блоки   Id  Система
/dev/sdc1   *           1        2497    20051968   83  Linux
/dev/sdc2            2497        2611      916481    5  Расширенный
/dev/sdc5            2497        2611      916480   82  Linux своп / Solaris
Диск /dev/sdd: 2147 МБ, 2147483648 байт
255 heads, 63 sectors/track, 261 cylinders
Units = цилиндры of 16065 * 512 = 8225280 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disk identifier: 0x00000000
На диске /dev/sdd отсутствует верная таблица разделов
Здесь видно что имеем мы 2 диска sdc и sdd. На sdc уже созданы 3 раздела sdc1,sdc2,sdc3.
sdd еще не размечен.
Для создания разделов на sdd, выполним команду
fdisk /dev/sdd
Будет предложено ввести `m` для справки, вводим и смотрим какие есть возможности по работе с диском
Действие команды
a   переключение флага загрузки
b   редактирование метки диска bsd
c   переключение флага dos-совместимости
d   удаление раздела
l   список известных типов файловых систем
m   вывод этого меню
n   добавление нового раздела
o   создание новой пустой таблицы разделов DOS
p   вывод таблицы разделов
q   выход без сохранения изменений
s   создание новой чистой метки диска Sun
t   изменение id системы раздела
u   изменение единиц измерения экрана/содержимого
v   проверка таблицы разделов
w   запись таблицы разделов на диск и выход
x   дополнительная функциональность (только для экспертов)
Нам необходимо ввести `n` то есть добавим новый раздел
Команда (m для справки): n
Действие команды
e   расширенный
p   основной раздел (1-4)
выбираем основной нажав `p`, либо расширенный если вам необходим он.
Номер раздела (1-4):
Ставим номер раздела, без разницы какой, но для порядка я бы посоветовал ставить 1 (если он не занят конечно). Эта цифра означает как будет называться ваш диск sdd1 или sdd2 ну и т.д.
Далее размечаем только что созданный раздел. Если раздел будет на весь диск, то оставляем все по умолчанию, ничего не вводя а просто нажимая Enter, либо вводим то как вам нужно разметить диск
Первый цилиндр (1-261, по умолчанию 1):
Используется значение по умолчанию 1
Last цилиндр, +цилиндры or +size{K,M,G} (1-261, по умолчанию 261):
Используется значение по умолчанию 261
После всех проделанных действий вводим `w` что означает сохранить настройки и выйти.
Команда (m для справки): w
Таблица разделов была изменена!
Вызывается ioctl() для перечитывания таблицы разделов.
Синхронизируются диски.

Ниже приведен способ форматирования диска в среде Ubuntu через командную строку.
Воспользуемся командой mkfs
Формат ее простой mkfs.файловая система устройство
Например нам необходимо отформатировать наш /dev/sdd1 в ext4, для этого выполним следующую команду:
mkfs.ext4 /dev/sdd1
Чтобы посмотреть какие еще можно использовать файловые системы наберите mkfs и два раза нажмите на знак табуляции. Выдаст примерно следующее:
# mkfs  (+2 знака TAB)
mkfs          mkfs.ext2     mkfs.ext4dev  mkfs.vfat
mkfs.bfs      mkfs.ext3     mkfs.minix    mkfs.xfs
mkfs.cramfs   mkfs.ext4     mkfs.msdos
Некоторые файловые системы как например XFS команда mkfs по умолчанию не поддерживает для этого пришлось доставить xfsprogs
apt-get install xfsprogs

Теперь нам необходимо примонтировать наш новый жесткий диск к системе.
Выполним это с помощью команды mount
mount -t ext4 /dev/sdd1 /usr/data
-t ext4 – указываем файловую систему подключаемого диска
/dev/sdd1 – Собственно, сам раздел который мы подключаем
/usr/data – Точка монтирования место куда подключается наш раздел

Кстати размонтировать диск можно командой umount указав диск
umount /dev/sdd1
Чтобы наш диск монтировался в системе автоматически после перезагрузки необходимо прописать его в файле /etc/fstab
Переходим на новую строчку и добавляем строку такого вида:
раздел_винчестера точка_монтирования файловая_система опции_монтирования два_вспомогательных_числа
Например чтобы описать наш раздел /dev/sdd1 с файловой системой XFS добавляем следующую строчку:
/dev/sdd1      /usr/data     xfs    defaults    1 2
где, /dev/sdd1 – наш раздел, диск, устройство называйте его как хотите
/usr/data – точка монтирования, где будут файлы с нашего диска
xfs – файловая система, на примонтированном диске
defaults – все опции по умолчанию. Читайте ниже их описание
1 2 – Вспомогательные числа, также читайте описание ниже
Тут привожу таблицу опций:
 ОпцияОписание
defaultsИспользовать настройки по умолчанию. То есть такие: rw,suid,dev,exec,auto,nouser,async.
rw / roРазрешено чтение и запись / Разрешено только чтение
suid / nosuidРазрешение / Блокировка работы suid, и sgid бит
dev / nodevИнтерпретировать / не интерпретировать блок специальных устройств на файловой системе.
exec / noexecРазрешить выполнять двоичные файлы находящиеся на этом диске / Запретить
auto / noautoУстройство будет устанавливаться автоматически при загрузке / Не будет
nouser / userЗапрещение монтирование от всех кроме root (nouser) / Разрешение монтировать от лица любого пользователя
async / syncЗапись и чтение на диске будут производиться асинхронно / Синхронно
Вспомогательные числа:
1 число
Возможные значения 0 или 1 –  означает, включить/выключить резервное копирование файловой системы при помощи команды dump. Устаревшая опция.
2 число
Возможные значения 0, 1, 2,  – означает порядок, в котором файловая система должна быть проверена при загрузке:
0 – не проверять.
1 – должна проверяться первой и использоваться как корневая.
Для всех остальных систем ставится 2.

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

Как определить тип файловой системы в Linux?

 Использовать команду df -T

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

Ускоряем раздачу статики

Как понять, что хард тормозит?

В Linux проблемы со скоростью дисковой системой напрямую связаны с параметром iowait (процент простоя CPU в ожидании операций ввода/вывода). Для того, чтоб мониторить этот параметр есть несколько комманд: mpstat, iostat, sar. Я обычно запускаю iostat 5 (замеры будут производиться каждые 5 сек.)
Я спокоен за сервер, у которого средний показатель iowait до 0.5%. Скорее всего на Вашем сервере «раздачи» этот параметр будет выше. Есть смысл не откладывать оптимизацию, если iowait > 10% Ваша система тратит очень много времени на перемещение головок по винчестеру вместо чтения информации, это может приводить к «торможению» и других процессов на сервере.

Как быть с большим iowait?

Очевидно, что если уменьшить количество дисковых операций ввода/вывода, винчестеру стант легче и iowait упадет.
Вот несколько рекомендаций:

  • Отключите access_log
  • Отключите обновление даты последнего доступа к файлу и директории, также позвольте системе кешировать операции записи на диск. Для этого монтируем файловую систему со следующими опциями: async,nodiratime,noatime,barrier=0. ('barrier=0' неоправданный риск, если на этом же разделе находится база данных)
  • Можно увеличить таймаут между сбросом «грязных» буферов vm.dirty_writeback_centisecs в /etc/sysctl.conf. У меня установлено vm.dirty_writeback_centisecs = 15000
  • Вы случайно не забыли про директиву expires max?
  • Не лишним будет включить кеширование дескрипторов файлов.
  • Приминение клиентской оптимизации: css-спрайты, все css — в один файл, все js — в один файл

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

вторник, 1 декабря 2015 г.

Установка imagemagick

sudo apt-get install php5-imagick

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

суббота, 14 ноября 2015 г.

Знакомство с Elasticsearch

Знакомство с Elasticsearch

В этом уроке мы познакомим вас с Elasticsearch и рассмотрим как связать данный инструмент с PHP. Elasticsearch - это бесплатный поисковый сервер, работающий на основе Apache Lucene. Главное преимущество данного инструмента в том, что он предоставляет возможность осуществить быстрый и гибкий поиск. Так же нам доступен REST API, который позволяет создавать, удалять, изменять и получать данные.

Установка Elasticsearch

Для установки Elasticsearch нам потребуется Java. По умолчанию в Ubuntu её нет, так что сначала добавляем репозиторий.
1sudo add-apt-repository ppa:webupd8team/java
2sudo apt-get update
Теперь приступаем непосредственно к установке Java.
1sudo apt-get install oracle-java8-installer
Далее скачиваем Elasticsearch, используя wget.
1wget https://download.elasticsearch.org/elasticsearch/elasticsearch/elasticsearch-1.5.2.tar.gz
На данный момент версия 1.5.2 является самой стабильной, поэтому мы будем использовать именно её. Если вам нужна какая-то другая версия, то архив релизов можно найти тут.
Затем распаковываем и запускаем установку.
1mkdir es
2tar -xf elasticsearch-1.5.2.tar.gz -C es
3cd es
4./bin/elasticsearch
Теперь после обращения к адресу http://localhost:9200 в адресной строке браузера, вы должны увидеть следующее:
01{
02  "status" : 200,
03  "name" : "Rumiko Fujikawa",
04  "cluster_name" : "elasticsearch",
05  "version" : {
06    "number" : "1.5.2",
07    "build_hash" : "62ff9868b4c8a0c45860bebb259e21980778ab1c",
08    "build_timestamp" : "2015-04-27T09:21:06Z",
09    "build_snapshot" : false,
10    "lucene_version" : "4.10.4"
11  },
12  "tagline" : "You Know, for Search"
13}

Использование Elasticsearch

Теперь можем начать наше взаимодействие с Elasticsearch. Для начала давайте установим PHP клиент для работы с Elasticsearch.
1composer require elasticsearch/elasticsearch
Затем создаём новый php файл, который будем использовать для примеров.
1<?php
2require 'vendor/autoload.php';
3
4$client = new Elasticsearch\Client();

Индексация документов

Индексация документов осуществляется вызовом метода index, который принимает массив аргументов. В нём должно быть три ключа: body, index и type. В ключе body будет располагаться массив с данными, которые нужно индексировать. В index следует указывать сегмент, где вы собираетесь индексировать данные (что-то типа название базы данных). В type следует указывать категорию документа (что-то типа названия таблицы). Вот пример:
01$params = array();
02$params['body']  = array(
03  'name' => 'Ash Ketchum',
04  'age' => 10,
05  'badges' => 8
06);
07
08$params['index'] = 'pokemon';
09$params['type']  = 'pokemon_trainer';
10
11$result = $client->index($params);
Если вывести $result, то результат будет такой:
1Array
2(
3    [_index] => pokemon
4    [_type] => pokemon_trainer
5    [_id] => AU1Bn51W5l_vSaLQKPOy
6    [_version] => 1
7    [created] => 1
8)
В приведённом примере мы не указали ID документа. В этом случае Elasticsearch автоматически присвоит уникальный ID. Это можно сделать и самим:
01$params = array();
02$params['body']  = array(
03  'name' => 'Brock',
04  'age' => 15,
05  'badges' => 0
06);
07
08$params['index'] = 'pokemon';
09$params['type']  = 'pokemon_trainer';
10$params['id'] = '1A-000';
11
12$result = $client->index($params);
Результат вывода переменной $result:
1Array
2(
3    [_index] => pokemon
4    [_type] => pokemon_trainer
5    [_id] => 1A-001
6    [_version] => 1
7    [created] => 1
8)
Для индексации документов мы можем использовать как простые массивы, так и вложенные:
01$params = array();
02$params['body']  = array(
03  'name' => 'Misty',
04  'age' => 13,
05  'badges' => 0,
06  'pokemon' => array(
07    'psyduck' => array(
08      'type' => 'water',
09      'moves' => array(
10        'Water Gun' => array(
11          'pp' => 25,
12          'power' => 40
13        )
14      )
15    )
16  )
17);
18
19$params['index'] = 'pokemon';
20$params['type']  = 'pokemon_trainer';
21$params['id'] = '1A-002';
22
23$result = $client->index($params);
Вложенность может быть какой угодно глубины (однако увлекаться этим не стоит).

Поиск по документам

Для поиска следует использовать метод get или search: get в случа, если вы знаете ID документа. Так же следует отметить, что данный метод возвращает только один документ. Для поиска набора результатов по различным критериям (по полям) следует использовать метод search().

Get

Давайте начнём с метода get. Точно так же как метод index он принимает массив аргументов. В массиве должны быть ключи index, type и id документа, который вы хотите найти.
1$params = array();
2$params['index'] = 'pokemon';
3$params['type'] = 'pokemon_trainer';
4$params['id'] = '1A-001';
5
6$result = $client->get($params);
Результат поиска:
01Array
02(
03    [_index] => pokemon
04    [_type] => pokemon_trainer
05    [_id] => 1A-001
06    [_version] => 1
07    [found] => 1
08    [_source] => Array
09        (
10            [name] => Brock
11            [age] => 15
12            [badges] => 0
13        )
14
15)

Поиск по определённым полям

В массиве аргументов для метода search следует указать ключи index, type и body. В ключе body указываем критерии запроса. Вот как можно вернуть все документы, где возраст равен 15.
1$params['index'] = 'pokemon';
2$params['type'] = 'pokemon_trainer';
3$params['body']['query']['match']['age'] = 15;
4
5$result = $client->search($params);
Результат:
01Array
02(
03    [took] => 177
04    [timed_out] =>
05    [_shards] => Array
06        (
07            [total] => 5
08            [successful] => 5
09            [failed] => 0
10        )
11
12    [hits] => Array
13        (
14            [total] => 1
15            [max_score] => 1
16            [hits] => Array
17                (
18                    [0] => Array
19                        (
20                            [_index] => pokemon
21                            [_type] => pokemon_trainer
22                            [_id] => 1A-001
23                            [_score] => 1
24                            [_source] => Array
25                                (
26                                    [name] => Brock
27                                    [age] => 15
28                                    [badges] => 0
29                                )
30
31                        )
32
33                )
34
35        )
36
37)
Давайте разберём результат:
  • took – время выполнения запроса.
  • timed_out – возвращает true если время выполнения запроса прошло.
  • _shards – по умолчанию, Elasticsearch размещает данные по 5 шардам (сегментам). Если значение 5 будет в total и successful то каждый шард работает корректно.
  • hits содержит результат поиска.
Метод который мы продемонстрировали, позволяет осуществить поиск по глубине равной единице. Если мы хотим искать глубже, то нам следует воспользоваться bool запросами. Для этого указываем ключ bool в query. Теперь в поиске будут задействованы все поля, разделяя их знаком . .
1$params['index'] = 'pokemon';
2$params['type']  = 'pokemon_trainer';
3$params['body']['query']['bool']['must'][]['match']['pokemon.psyduck.type'] = 'water';
4$result = $client->search($params);

Поиск массивами

Так же мы можем осуществлять запросы, используя массивы, указав ключ bool, а затем must, terms. В качестве значения указываем массив значений, который должен быть задействован в поиске. В данном примере ищем документы, где поле age равняется 10 и 15.
1$params['index'] = 'pokemon';
2$params['type']  = 'pokemon_trainer';
3
4$params['body']['query']['bool']['must']['terms']['age'] = array(10, 15);
В данном способе можно применять только линейные массивы.

Поиск по фильтрам

Теперь давайте посмотрим как можно осуществить поиск с применением фильтров. Для фильтрации нужно указать ключ filtered, а в качестве значения начальное и конечно число диапазона искомых значений. В данном случае мы будем искать по полю age, где значение больше или равно (gte) 11 и меньше или равно (lte) 20.
1$params['index'] = 'pokemon';
2$params['type']  = 'pokemon_trainer';
3$params['body']['query']['filtered']['filter']['range']['age']['gte'] = 11;
4$params['body']['query']['filtered']['filter']['range']['age']['lte'] = 20;
5$result = $client->search($params);

OR и AND

При работе с запросами в реляционных СУБД мы часто используем ключевые слова AND или OR. В Elasticsearch у нас тоже есть такая возможность: для этого просто указываем ключ and. Выберем все документы, где возраст age равен 10 и badge равен 8.
1$params['index'] = 'pokemon';
2$params['type']  = 'pokemon_trainer';
3
4$params['body']['query']['filtered']['filter']['and'][]['term']['age'] = 10;
5$params['body']['query']['filtered']['filter']['and'][]['term']['badges'] = 8;
6
7$result = $client->search($params);
Если нужно осуществить поиск по одному из этих двух значений, то используйте ключ or.
1$params['body']['query']['filtered']['filter']['or'][]['term']['age'] = 10;
2$params['body']['query']['filtered']['filter']['or'][]['term']['badges'] = 8;

Выбор определённого числа результатов

Мы можем ограничить число результатов поиска, используя поле size. Пример:
1$params['body']['query']['filtered']['filter']['and'][]['term']['age'] = 10;
2$params['body']['query']['filtered']['filter']['and'][]['term']['badges'] = 8;
3$params['size'] = 1;
Возвращает только один документ.

Постраничное разделение

В реляционных СУБД есть возможность выбирать данные по различным сегментам, используя ключевые слова LIMIT и OFFSET. В Elasticsearch тоже есть аналоги: ключи size и from. from позволяет нам осуществить выборку с нужного нам “отступа”. Индексация документов начинается с нуля. Вот как мы можем получить вторую страницу результатов:
1$params['index'] = 'pokemon';
2$params['type']  = 'pokemon_trainer';
3
4$params['size'] = 10;
5$params['from'] = 10; // <-- возврат второй страницы

Редактирование документа

Для обновления данных в документе нам необходимо сначала его извлечь. Для этого указываем index, type и id документа в методе get. Текущие данные можно найти в сегменте _source. Для обновления данных, просто обращаемся к полям и задаём новые значения. Для сохранения результатов следует вызвать метод update.
01$params = array();
02$params['index'] = 'pokemon';
03$params['type'] = 'pokemon_trainer';
04$params['id'] = '1A-001';
05$result = $client->get($params);
06
07
08$result['_source']['age'] = 21; //задаём полю новое значение
09
10//добавляем новое поле
11$result['_source']['pokemon'] = array(
12  'Onix' => array(
13    'type' => 'rock',
14    'moves' => array(
15      'Rock Slide' => array(
16        'power' => 100,
17        'pp' => 40
18      ),
19      'Earthquake' => array(
20        'power' => 200,
21        'pp' => 100
22      )
23    )
24  )
25);
26
27$params['body']['doc'] = $result['_source'];
28
29$result = $client->update($params);
Результат:
1Array
2(
3    [_index] => pokemon
4    [_type] => pokemon_trainer
5    [_id] => 1A-001
6    [_version] => 2
7)
Значение поля _version будет увеличиваться каждый раз при вызове метода update (в том случае, если хоть одно поле было изменено).
Вы можете подумать, что Elasticsearch сохраняет предыдущие версии документа, но это не так. Данный счётчик просто показывает количество обновлений документа.

Удаление документа

Для удаление документа достаточно вызвать метод delete. В массиве аргументов следует указать поля index, type и id.
1$params = array();
2$params['index'] = 'pokemon';
3$params['type'] = 'pokemon_trainer';
4$params['id'] = '1A-001';
5
6$result = $client->delete($params);
Результат:
1Array
2(
3    [found] => 1
4    [_index] => pokemon
5    [_type] => pokemon_trainer
6    [_id] => 1A-001
7    [_version] => 7
8)
Заметка: если вытащить документ, используя метод get, а затем его удалить, то может возникнуть ошибка.

Вывод

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

Отблагодарить можно через форму справа "Donate" ... )

To reward you via the form on the right "Donate" ... )

:)

друзья )

Сохраняйте и делитесь желаниями, и не забывайте о важных датах! парсинг центр