Slim framework или как мы отказались от CMS

в 8:34, , рубрики: cms, framework, php, slim framework, web-разработка

Эта публикация будет интересна небольшим компаниям по разработкам сайтов с использованием CMS. Небольшая предыстория: мы — это небольшой отдел, который занимается разработкой веб-сайтов. Очень долгое время мы разрабатывали сайты только на системах управления (OpenCart, WordPress, MODX и самописная), которые по своей сути были простые и однотипные, но с лета прошлого года пришёл тренд на разработку сайтов, которые не просто были в интернете лицом компании, но одним из инструментов бизнеса.

Так, например, был заказ для транспортной компании, которая осуществляет рейсовые маршруты и хотела бы, чтобы всё управление (бронирование и оплата билета, в том числе через кассира) происходила через сайт.

Как вы можете догадываться, большой пользы от CMS тут ждать не приходится. Даже наоборот — любой алгоритм, которому она следовала, нам мешал. Через несколько дней на первом же таком сайте были одни костыли и практически вся обработка шла исключительно на javascript, а CMS использовалась как прослойка для записи и выборки из базы данных.

Терпеть такое мы долго не смогли и, посовещавшись, решили, что для таких проектов мы будем использовать mifroframework — и сразу же положили глаз на Slim.

Как гласит официальный сайт:

Slim — это микро фреймворк, который поможет вам быстро писать простые, но мощные веб-приложения.

И это действительно так, вы можете скачать его вручную архивом или воспользоваться Composer. После этого создайте index.php со следующим содержанием:

	//Подключаем фреймворк
	require 'Slim/Slim.php';


	//Регистрируем автозагрузку
	SlimSlim::registerAutoloader();


	$app = new SlimSlim();
	$app->get('/hello/:name', function ($name) {
  		  echo "Привет, $name";
		});
	$app->run();

Это простое приложение которое выводит привет {{username}} при переходе на url.
Но как же мы были разочарованы, что на этом большинство статей в интернете заканчивается и на данном этапе многое остается для нас непонятным.

Сам Slim не задает чёткой системы распределений файлов на диске, поэтому мы не нашли лучшего способа, чем иклюдить каждый роутинг. На следующий день, поняв, что что-то идёт не так, было решено создать отдельную папку и класть туда файлы по группам. В файл index.php добавилось следующее

	foreach (glob('Routes/*.php') as $file)
		include($file);

Со временем каждый такой файл стал слишком большим, но посмотрев официальную документацию, ничего не обнаружили. Решение было найдено на github, где было сказано, что надо делать:

$app->get('post/:type/:id', 'ControllerPost:onePost');

Где ControllerPost — класс, который, как я понимаю, добавлен в соответствии с RSP-0. А onePost — это его метод.
Таким образом наша файловая структура обновилась ещё одной директории Controller, в которую мы записывали действия, которые могли использовать сразу в нескольких вариантах роутинга. Я считаю хорошим примером данный роутинг, который заключён в группу, стиль, который почему-то не описан в той же документации.

$app->group('/', function () use ($app) {
	$app->get('post/:type/:id', 'ControllerPost:onePost')
		->conditions(
			array('type' => '[a-zA-Z]{3,}', 'id' => '[0-9]{1,}')
		)
		->setParams(
			array('app' => $app, 'type' => $type = NULL, 'id' => $id = 0)
		)
		->name('onePost');
});

Где conditions — валидация по регулярному выражению, setParams — передача параметров методу onePost, а name — имя для возможного редиректа на данную страницу (Например $app->redirectTo('onePost');)

Не лишним будет проводить проверку на доступность не в самом контроллере, а на уровне роутига, благодаря «Middleware». Например, для панели администратора сразу же можно поставить на целую группу такую как:

$app->group('/admin', $authenticateForRole($app, 'admin'), function () use ($app) {
...
});

Где вторым аргументом является присвоенная анонимная функция переменной. В моём случае она выглядит таким образом:

	$authenticateForRole = function ($app, $role = 'admin') {
		return function () use ($app, $role) {
			ControllerAutch::chekUserRole($app, $role);
		};
	};

К сожалению, а для некоторых, может, и к счастью, в slim нет встроенной работы с базой данных, но этот вопрос достаточно просто решается, когда мы создаём объект App. Мы можем передавать некоторые аргументы, которые будут им использоваться.

Например:

	$app = new SlimSlim(array(
		'templates.path' => 'Views',
		'debug'          => TRUE,
		'mode'           => 'development',
		'BDbase'         => 'localhost',
		'BDuser'         => 'username',
		'BDpassword'     => 'password',
		'BDname'         => 'basename'
	));

После этого мы сможем спокойно воспользоваться Dependency Injection для работы с базой данных, обращаясь к параметрам, переданным при создании с помощью метода $app-config('Имя');

	$app->database = new mysqli(
		$app->config('BDbase'),
		$app->config('BDuser'),
		$app->config('BDpassword'),
		$app->config('BDname')
	);
	if ($app->database->connect_errno) {
		echo "Не удалось подключиться к MySQL: (" . $app->database->connect_errno . ") " . $app->database->connect_error;
		die();
	}

	$app->database->query("SET NAMES 'utf8'");
	$app->database->query("SET CHARACTER SET 'utf8'");
	$app->database->query("SET SESSION collation_connection = 'utf8_general_ci'");

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

Автор: tatu

Источник

* - обязательные к заполнению поля


https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js