fix new namespace

This commit is contained in:
root
2023-06-11 23:33:13 +00:00
parent 063a0fdec6
commit f0ee8e3776
19 changed files with 4 additions and 4 deletions

View File

@@ -0,0 +1,2 @@
storage/*
!storage

View File

@@ -0,0 +1,105 @@
<?php
// Фреймворк ArangoDB
use mirzaev\arangodb\connection,
mirzaev\arangodb\collection,
mirzaev\arangodb\document;
// Библиотека для ArangoDB
use ArangoDBClient\Document as _document;
// Фреймворк для Google Sheets
use Flow\ETL\Adapter\GoogleSheet\GoogleSheetRange,
Flow\ETL\Adapter\GoogleSheet\GoogleSheetExtractor,
Flow\ETL\Adapter\GoogleSheet\Columns,
Flow\ETL\Flow,
Flow\ETL\Config,
Flow\ETL\FlowContext,
Flow\ETL\Row\Entry,
Flow\ETL\Row,
Flow\ETL\DSL\To,
Flow\ETL\DSL\From;
// Фреймворк для Google API
use Google\Client,
Google\Service\Sheets,
Google\Service\Sheets\ValueRange;
require __DIR__ . '/../../../../../../vendor/autoload.php';
$arangodb = new connection(require '../settings/arangodb.php');
function generateLabel(string $name): string
{
return match ($name) {
'id', 'ID', 'ТТ' => 'id',
'type', 'ТИП', 'Тип', 'тип' => 'type',
'director', 'ДИРЕКТОР', 'Директор', 'директор' => 'director',
'address', 'АДРЕС', 'Адрес', 'адрес' => 'address',
default => throw new exception("Неизвестный столбец: $name")
};
}
function degenerateLabel(string $name): string
{
return match ($name) {
'ID', 'id' => 'ID',
'ТИП', 'type' => 'ТИП',
'ДИРЕКТОР', 'director' => 'ДИРЕКТОР',
'АДРЕС', 'address' => 'АДРЕС',
default => throw new exception("Неизвестный столбец: $name")
};
}
function init(array $row, bool $reverse = false): array
{
$buffer = [];
foreach ($row as $key => $value) $buffer[(($reverse ? 'de' : null) . 'generateLabel')($key)] = $value ?? '';
return $buffer;
}
function sync(Row &$row, string $city = 'Красноярск'): void
{
global $arangodb;
$_row = init($row->entries()->toArray()['row']);
if ($_row['id'] !== null)
if (collection::init($arangodb->session, 'markets'))
if ($market = collection::search($arangodb->session, sprintf("FOR d IN markets FILTER d.id == '%s' RETURN d", $_row['id'])))
if ($_row === $new = array_diff_key($market->getAll(), ['_key' => true, 'created' => true, 'city' => true]));
else $row = $row->set((new Flow())->read(From::array([init($new, true)]))->fetch(1)[0]->get('row'));
else if (collection::search($arangodb->session, sprintf("FOR d IN markets FILTER d._id == '%s' RETURN d", document::write($arangodb->session, 'markets', $_row + ['city' => $city]))));
else throw new exception('Не удалось создать или найти созданного магазина');
else throw new exception('Не удалось инициализировать коллекцию');
}
$settings = json_decode(require('../settings/markets/google.php'), true);
$document = require('../settings/markets/document.php');
$sheets = require('../settings/markets/sheets.php');
$client = new Client();
$client->setScopes(Sheets::SPREADSHEETS);
$client->setAuthConfig($settings);
$api = new Sheets($client);
foreach ($sheets as $sheet) {
$rows = (new Flow())->read(new GoogleSheetExtractor($api, $document, new Columns($sheet, 'A', 'D'), true, 1000, 'row'));
$i = 1;
foreach ($rows->fetch(100) as $row) {
++$i;
$buffer = $row;
sync($row, $sheet);
if ($buffer !== $row)
$api->spreadsheets_values->update(
$document,
"$sheet!A$i:D$i",
new ValueRange(['values' => [array_values($row->entries()->toArray()['row'])]]),
['valueInputOption' => 'USER_ENTERED']
);
}
}

View File

@@ -0,0 +1,188 @@
<?php
// Фреймворк ArangoDB
use mirzaev\arangodb\connection,
mirzaev\arangodb\collection,
mirzaev\arangodb\document;
// Библиотека для ArangoDB
use ArangoDBClient\Document as _document;
// Фреймворк для Google Sheets
use Flow\ETL\Adapter\GoogleSheet\GoogleSheetRange,
Flow\ETL\Adapter\GoogleSheet\GoogleSheetExtractor,
Flow\ETL\Adapter\GoogleSheet\Columns,
Flow\ETL\Flow,
Flow\ETL\Config,
Flow\ETL\FlowContext,
Flow\ETL\Row\Entry,
Flow\ETL\Row,
Flow\ETL\DSL\To,
Flow\ETL\DSL\From;
// Фреймворк для Google API
use Google\Client,
Google\Service\Sheets,
Google\Service\Sheets\ValueRange;
require __DIR__ . '/../../../../../../vendor/autoload.php';
$arangodb = new connection(require '../settings/arangodb.php');
function generateLabel(string $name): string
{
return match ($name) {
'id', 'ID', '1', '11', '111', '1111', '11111', 'index', 'Index', 'код', 'Код', 'ключ', 'Ключ', 'айди', 'Айди', 'идентификатор', 'Идентификатор' => 'id',
'name', 'ФИО', 'фио', 'ф.и.о.', 'ф. и. о.', 'Ф.И.О.', 'Ф. И. О.' => 'name',
'phone', 'Номер', 'номер', 'телефон', 'Телефон' => 'phone',
'birth', 'Дата рождения', 'дата рождения', 'Год рождения', 'год рождения', 'Год', 'год', 'День рождения', 'день рождения' => 'birth',
'address', 'Адрес регистрации', 'адрес регистрации', 'Адрес', 'адрес', 'Регистрация', 'регистрация' => 'address',
'commentary', 'Комментарий', 'ПРИМЕЧАНИЕ', 'Примечание', 'примечание' => 'commentary',
'activity', 'Работа', 'работа', 'Вид Работы', 'Вид работы', 'вид работы' => 'activity',
'passport', 'Паспорт', 'паспорт', 'серия и номер паспорта', 'Серия и номер паспорта' => 'passport',
'issued', 'Выдан', 'выдан' => 'issued',
'department', 'Код подразделения', 'код подразделения', 'Подразделение', 'подразделение' => 'department',
'hiring', 'Дата присоединения', 'Когда устроили', 'когда устроили' => 'hiring',
'district', 'Район', 'район' => 'district',
'requisites', 'Реквизиты', 'реквизиты' => 'requisites',
'fired', 'Дата увольнения', 'дата увольнения', 'Уволен', 'уволен', 'Увольнение', 'увольнение' => 'fired',
'payment', 'Оплата', 'оплата' => 'payment',
'tax', 'ИНН', 'инн' => 'tax',
default => throw new exception("Неизвестный столбец: $name")
};
}
function degenerateLabel(string $name): string
{
return match ($name) {
'ID', 'id' => 'ID',
'ФИО', 'name' => 'ФИО',
'Номер', 'phone' => 'Номер',
'Дата рождения', 'birth' => 'Дата рождения',
'Адрес регистрации', 'address' => 'Адрес регистрации',
'Комментарий', 'commentary' => 'Комментарий',
'Работа', 'activity' => 'Работа',
'Паспорт', 'passport' => 'Паспорт',
'Выдан', 'issued' => 'Выдан',
'Код подразделения', 'department' => 'Код подразделения',
'Дата присоединения', 'hiring' => 'Дата присоединения',
'Район', 'district' => 'Район',
'Реквизиты', 'requisites' => 'Реквизиты',
'Дата увольнения', 'fired' => 'Дата увольнения',
'Оплата', 'payment' => 'Оплата',
'ИНН', 'tax' => 'ИНН',
default => throw new exception("Неизвестный столбец: $name")
};
}
function init(array $row, bool $reverse = false): array
{
$buffer = [];
foreach ($row as $key => $value) $buffer[(($reverse ? 'de' : null) . 'generateLabel')($key)] = $value ?? '';
return $buffer;
}
function connect(_document $worker, _document $robot): void
{
global $arangodb;
if (
collection::init($arangodb->session, 'connections', true)
&& (collection::search(
$arangodb->session,
sprintf(
"FOR d IN connections FILTER d._from == '%s' && d._to == '%s' RETURN d",
$worker->getId(),
$robot->getId()
)
)
?? collection::search(
$arangodb->session,
sprintf(
"FOR d IN connections FILTER d._id == '%s' RETURN d",
document::write(
$arangodb->session,
'connections',
['_from' => $worker->getId(), '_to' => $robot->getId()]
)
)
))
) {
// Инициализировано ребро: workers -> robot (любой)
// Активация
$robot->status = 'active';
document::update($arangodb->session, $robot);
}
}
function connectAll(_document $worker): void
{
global $arangodb;
// Инициализация ребра: workers -> viber
if (
collection::init($arangodb->session, 'viber')
&& $viber = collection::search(
$arangodb->session,
sprintf(
"FOR d IN viber FILTER d.number == '%d' RETURN d",
$worker->phone
)
)
) connect($worker, $viber);
}
function sync(Row &$row, string $city = 'Красноярск'): void
{
global $arangodb;
$_row = init($row->entries()->toArray()['row']);
if ($_row['id'] !== null)
if (collection::init($arangodb->session, 'workers'))
if ($worker = collection::search($arangodb->session, sprintf("FOR d IN workers FILTER d.id == '%s' RETURN d", $_row['id']))
?? collection::search($arangodb->session, sprintf("FOR d IN workers FILTER d._id == '%s' RETURN d", document::write($arangodb->session, 'workers', $_row + ['city' => $city])))
) {
// Инициализирован работник
// Реинициализация строки с актуальными записями (приоритет у базы данных)
if ($_row !== $new = array_diff_key($worker->getAll(), ['_key' => true, 'created' => true, 'city' => true]))
$row = $row->set((new Flow())->read(From::array([init($new, true)]))->fetch(1)[0]->get('row'));
// Подключение к чат-роботам
connectAll($worker);
} else throw new exception('Не удалось создать или найти созданного работника');
else throw new exception('Не удалось инициализировать коллекцию');
}
$settings = json_decode(require('../settings/workers/google.php'), true);
$document = require('../settings/workers/document.php');
$sheets = require('../settings/workers/sheets.php');
$client = new Client();
$client->setScopes(Sheets::SPREADSHEETS);
$client->setAuthConfig($settings);
$api = new Sheets($client);
foreach ($sheets as $sheet) {
$rows = (new Flow())->read(new GoogleSheetExtractor($api, $document, new Columns($sheet, 'A', 'P'), true, 1000, 'row'));
$i = 1;
foreach ($rows->fetch(5000) as $row) {
++$i;
$buffer = $row;
sync($row, $sheet);
if ($buffer !== $row) {
$api->spreadsheets_values->update(
$document,
"$sheet!A$i:P$i",
new ValueRange(['values' => [array_values($row->entries()->toArray()['row'])]]),
['valueInputOption' => 'USER_ENTERED']
);
}
}
}

View File

@@ -0,0 +1,190 @@
<?php
// Фреймворк ArangoDB
use mirzaev\arangodb\connection,
mirzaev\arangodb\collection,
mirzaev\arangodb\document;
// Библиотека для ArangoDB
use ArangoDBClient\Document as _document;
// Фреймворк для Google Sheets
use Flow\ETL\Adapter\GoogleSheet\GoogleSheetRange,
Flow\ETL\Adapter\GoogleSheet\GoogleSheetExtractor,
Flow\ETL\Adapter\GoogleSheet\Columns,
Flow\ETL\Flow,
Flow\ETL\Config,
Flow\ETL\FlowContext,
Flow\ETL\Row\Entry,
Flow\ETL\Row,
Flow\ETL\DSL\To,
Flow\ETL\DSL\From;
// Фреймворк для Google API
use Google\Client,
Google\Service\Sheets,
Google\Service\Sheets\ValueRange;
require __DIR__ . '/../../../../../../vendor/autoload.php';
$arangodb = new connection(require '../settings/arangodb.php');
function generateLabel(string $name): string
{
return match ($name) {
'_id', 'ID' => '_id',
'market', 'Магазин' => 'market',
'worker', 'Сотрудник' => 'worker',
'work', 'Работа' => 'work',
'date', 'Дата' => 'date',
'start', 'Начало' => 'start',
'end', 'Конец' => 'end',
'confirmed', 'Подтверждено' => 'confirmed',
'commentary', 'Комментарий' => 'commentary',
'response', 'Ответ' => 'response',
default => throw new exception("Неизвестный столбец: $name")
};
}
function degenerateLabel(string $name): string
{
return match ($name) {
'ID', '_id' => 'ID',
'Магазин', 'market' => 'Магазин',
'Сотрудник', 'worker' => 'Сотрудник',
'Работа', 'work' => 'Работа',
'Дата', 'date' => 'Дата',
'Начало', 'start' => 'Начало',
'Конец', 'end' => 'Конец',
'Подтверждено', 'confirmed' => 'Подтверждено',
'Комментарий', 'commentary' => 'Комментарий',
'Ответ', 'response' => 'Ответ',
default => throw new exception("Неизвестный столбец: $name")
};
}
function init(array $row, bool $reverse = false): array
{
$buffer = [];
foreach ($row as $key => $value) $buffer[(($reverse ? 'de' : null) . 'generateLabel')($key)] = $value;
return $buffer;
}
function sync(Row &$row): void
{
global $arangodb;
$_row = init($row->entries()->toArray()['row']);
if (collection::init($arangodb->session, 'works'))
if (!empty($_row['_id']) && $work = collection::search($arangodb->session, sprintf("FOR d IN works FILTER d._id == '%s' RETURN d", $_row['_id']))) {
// Найдена запись работы (строки) в базе данных
// Очистка перед записью в таблицу
$new = array_diff_key($work->getAll(), ['_key' => true, 'created' => true]);
// Инициализация выбранного сотрудника
if (collection::init($arangodb->session, 'readinesses', true) && collection::init($arangodb->session, 'workers'))
$new = ['worker' => collection::search(
$arangodb->session,
sprintf(
"FOR d IN workers LET e = (FOR e IN readinesses FILTER e._to == '%s' RETURN e._from)[0] FILTER d._id == e RETURN d",
$_row['_id']
)
)->id ?? ''] + $new;
else throw new exception('Не удалось инициализировать коллекции');
// Инициализация магазина
if (collection::init($arangodb->session, 'requests', true) && collection::init($arangodb->session, 'markets'))
if ($market = collection::search(
$arangodb->session,
sprintf(
"FOR d IN markets LET e = (FOR e IN requests FILTER e._to == '%s' RETURN e._from)[0] FILTER d._id == e RETURN d",
$_row['_id']
)
)) $new = ['market' => $market->id] + $new;
else throw new exception('Не удалось найти магазин');
else throw new exception('Не удалось инициализировать коллекции');
// Запись идентификатора только что созданной записи в базе данных для записи в таблицу
$new = ['_id' => $work->getId()] + $new;
// Реинициализация строки с новыми данными по ссылке (приоритет из базы данных)
if ($_row !== $new) $row = $row->set((new Flow())->read(From::array([init($new, true)]))->fetch(1)[0]->get('row'));
} else if (
!empty($_row['market'])
&& collection::init($arangodb->session, 'requests', true) && collection::init($arangodb->session, 'markets')
&& ($market = collection::search($arangodb->session, sprintf("FOR d IN markets FILTER d.id == '%s' RETURN d", $_row['market'])))
&& $work = collection::search(
$arangodb->session,
sprintf(
"FOR d IN works FILTER d._id == '%s' RETURN d",
document::write($arangodb->session, 'works', array_diff_key($_row, ['_id' => true, 'market' => true, 'worker' => true]))
)
)
) {
// Не найдена запись работы (строки) в базе данных и была создана
// Инициализация ребра: market -> work (запрос магазина о работе)
if (collection::search(
$arangodb->session,
sprintf(
"FOR d IN requests FILTER d._id == '%s' RETURN d",
document::write($arangodb->session, 'requests', ['_from' => $market->getId(), '_to' => $work->getId()])
)
));
else throw new exception('Не удалось создать заявку магазина');
if (
!empty($_row['worker'])
&& collection::init($arangodb->session, 'readinesses', true) && collection::init($arangodb->session, 'workers')
&& ($worker = collection::search($arangodb->session, sprintf("FOR d IN workers FILTER d.id == '%s' RETURN d", $_row['worker'])))
) {
// Инициализация ребра: workers -> work (готовность работника приступать к заявке)
if (collection::search(
$arangodb->session,
sprintf(
"FOR d IN readinesses FILTER d._id == '%s' RETURN d",
document::write($arangodb->session, 'readinesses', ['_from' => $worker->getId(), '_to' => $work->getId()])
)
));
else throw new exception('Не удалось создать готовность сотрудника');
}
// Реинициализация строки с новыми данными по ссылке (приоритет из базы данных)
$row = $row->set((new Flow())->read(From::array([init(['_id' => $work->getId()] + $_row, true)]))->fetch(1)[0]->get('row'));
} else return;
else throw new exception('Не удалось инициализировать коллекцию');
}
$settings = json_decode(require('../settings/works/google.php'), true);
$document = require('../settings/works/document.php');
$sheets = require('../settings/works/sheets.php');
$client = new Client();
$client->setScopes(Sheets::SPREADSHEETS);
$client->setAuthConfig($settings);
foreach ($sheets as $sheet) {
$sheets = new Sheets($client);
$rows = (new Flow())->read(new GoogleSheetExtractor($sheets, $document, new Columns($sheet, 'A', 'J'), true, 1000, 'row'));
$i = 1;
foreach ($rows->fetch(10000) as $row) {
++$i;
$buffer = $row;
sync($row);
if ($buffer !== $row)
$sheets->spreadsheets_values->update(
$document,
"$sheet!A$i:J$i",
new ValueRange(['values' => [array_values($row->entries()->toArray()['row'])]]),
['valueInputOption' => 'USER_ENTERED']
);
}
}

View File

@@ -0,0 +1,4 @@
*
!*/
!.gitignore
!*.sample

View File

@@ -0,0 +1,8 @@
<?php
return [
'endpoint' => 'unix:///var/run/arangodb3/arango.sock',
'database' => '',
'name' => '',
'password' => ''
];

View File

@@ -0,0 +1,3 @@
*
!.gitignore
!*.sample

View File

@@ -0,0 +1,3 @@
<?php
return '';

View File

@@ -0,0 +1,17 @@
<?php
return <<<'JSON'
{
"type": "",
"project_id": "",
"private_key_id": "",
"private_key": "",
"client_email": "",
"client_id": "",
"auth_uri": "",
"token_uri": "",
"auth_provider_x509_cert_url": "",
"client_x509_cert_url": "",
"universe_domain": ""
}
JSON;

View File

@@ -0,0 +1,28 @@
<?php
return [
'Ангарск',
'Байкальск',
'Бирюсинск',
'Братск',
'Вихоревка',
'Зима',
'Иркутск',
'Нижнеудинск',
'Юрты',
'Чунский',
'Саянск',
'Тулун',
'Черемхово',
'Абакан',
'Зыково',
'Берёзовка',
'Емельяново',
'Дивногорск',
'Железногорск',
'Канск',
'Усолье-Сибирское',
'Тайшет',
'Красноярск',
'Лесосибирск'
];

View File

@@ -0,0 +1,3 @@
*
!.gitignore
!*.sample

View File

@@ -0,0 +1,3 @@
<?php
return '';

View File

@@ -0,0 +1,17 @@
<?php
return <<<'JSON'
{
"type": "",
"project_id": "",
"private_key_id": "",
"private_key": "",
"client_email": "",
"client_id": "",
"auth_uri": "",
"token_uri": "",
"auth_provider_x509_cert_url": "",
"client_x509_cert_url": "",
"universe_domain": ""
}
JSON;

View File

@@ -0,0 +1,5 @@
<?php
return [
'Красноярск'
];

View File

@@ -0,0 +1,3 @@
*
!.gitignore
!*.sample

View File

@@ -0,0 +1,3 @@
<?php
return '';

View File

@@ -0,0 +1,17 @@
<?php
return <<<'JSON'
{
"type": "",
"project_id": "",
"private_key_id": "",
"private_key": "",
"client_email": "",
"client_id": "",
"auth_uri": "",
"token_uri": "",
"auth_provider_x509_cert_url": "",
"client_x509_cert_url": "",
"universe_domain": ""
}
JSON;

View File

@@ -0,0 +1,5 @@
<?php
return [
'Красноярск'
];