Класс Application¶
Cущность Tygh\Application
появилась с версии 4.3.2.
Объект класса Application
создаётся при инициализации ядра в файле init.php, после чего он доступен отовсюду:
// получение объекта Application
Tygh::$app
На текущий момент единственное его предназначение - IoC контейнер, хранящий объекты и фабричные анонимные функции для создания объектов.
IoC контейнер¶
Ранее хранением объектов занимался класс Registry, который помимо этого занимается хранением кэша и других runtime-данных:
// было
$smarty = Registry::get('view');
// стало
$smarty = Tygh::$app['view'];
Основное отличие контейнера, который предоставляет Application
, от Registry
— возможность “ленивого” объявления объектов, которые должны храниться в нём. Объекты, хранящиеся в контейнере называются сервисами — обычно это компоненты большей системы, имеющие свою узкую зону ответственности, например: менеджер отправки писем, соединение с базой данных.
// регистрируем объект в контейнере при помощи анонимной фабричной функции
Tygh::$app['foo'] = function($app) {
return new Tygh\Foo();
};
Tygh::$app['bar'] = function($app) {
return new Tygh\Bar($app['foo']);
};
// на текущий момент ни одного объекта ещё создано не было, они будут созданы по первому требованию
// Application вернёт результат выполнения анонимной функции-фабрики, которую мы зарегистрировали ранее,
// причём в конструктор класса Tygh\Bar будет передан результат выполнения другой функции-фабрики.
$bar_instance = Tygh::$app['bar'];
// строка выше эквивалентна этому коду:
// $foo_instance = new Tygh\Foo();
// $bar_instance = new Tygh\Bar($foo_instance);
// если мы захотим получить сервис из контейнера снова, то будет возвращён тот же самый объект (новый создан не будет)
var_dump($bar_instance === Tygh::$app['bar']); // true
// если же нам НУЖНО, чтобы при каждом обращении к сервису в контейнер возвращался НОВЫЙ объект,
// то при регистрации сервиса необходимо обернуть анонимную функцию-фабрику таким образом:
Tygh::$app['cool_service'] = Tygh::$app->factory(function($app) {
return new Tygh\CoolService();
});
// это всё разные объекты
$a = Tygh::$app['cool_service'];
$b = Tygh::$app['cool_service'];
$c = Tygh::$app['cool_service'];
// кроме вышеупомянутых способов, можно просто положить конкретный объект в контейнер,
// это то поведение, которое предоставлял Registry
Tygh::$app['my_object'] = new Tygh\MyClass();
Подробную документацию по использованию контейнера можно найти на странице http://pimple.sensiolabs.org/.
Для обеспечения обратной совместимости Registry
перенаправляет вызовы к сервисам api
, crypt
, view
, ajax
и class_loader
в контейнер.
Что дальше?¶
В будущем Application возьмёт на себя обязанности по исполнению функций-инициализаторов (fn_init()
) и по обработке текущего запроса (fn_dispatch()
).