get('twig'); } /** * @return Propel */ public function getPropel() { return $this->get('propel'); } /** * @param Propel $propel */ public function setPropel($propel) { $this->set('propel', $propel); } public function boot($baseDir) { $this->startTimer(["boot", "load"]); $this->setBaseDir($baseDir); $this->loadConfig(); $this->bootContainer(); $this->bootLogger(); $this->bootPropel(); $this->loadRoutes(); $this->loadContainer(); $this->loadServices(); $this->endTimer(["load"]); $this->startTimer(["process"]); $this->processRoutes(); $this->endTimer(["boot", "process"]); } public function startTimer($timers) { $time = microtime(true); foreach ($timers as $timer) { $this->timers[$timer] = [$time, false]; } } public function loadConfig() { $basePath = '?' . $this->getBaseDir() . '/config/app.'; $configs = ['yml', 'json', 'xml', 'ini']; $configPaths = array_map(function ($ext) use ($basePath) { return $basePath . $ext; }, $configs); $this->setConfig(new Config($configPaths)); } /** * @return string */ public function getBaseDir() { return $this->baseDir; } /** * @param string $baseDir */ public function setBaseDir($baseDir) { $this->baseDir = $baseDir; } public function bootContainer() { $this->setContainer(new Container()); $this->set('core', $this); } public function bootLogger() { $config = $this->getConfig(); $logger = new Logger('default'); $logger->pushHandler( new StreamHandler( $config->get('core.log.path', $this->getBaseDir() . '/logs/core.log'), $config->get('core.log.level', Logger::INFO) ) ); $this->setLogger($logger); } /** * @return mixed */ public function getConfig() { return $this->config; } /** * @param mixed $config */ public function setConfig($config) { $this->config = $config; } /** * @param Logger $logger */ public function setLogger($logger) { $this->set('logger', $logger); } public function bootPropel() { include $this->getBaseDir() . '/config/propel/config.php'; Propel::getServiceContainer()->setLogger('defaultLogger', $this->getLogger()); } public function loadRoutes() { $this->startTimer(["load/routes"]); $path = $this->getBaseDir() . '/config/routes.yml'; $routesFile = file_get_contents($path); $routes = Yaml::parse($routesFile); $this->setRoutes($routes); $this->endTimer(["load/routes"]); } public function endTimer($timers) { $logger = $this->getLogger(); $time = microtime(true); foreach ($timers as $timer) { $this->timers[$timer][1] = $time; $elapsed = round(($this->timers[$timer][1] - $this->timers[$timer][0]) * 1000); $logger->addDebug("[CORE] {$timer} took {$elapsed}ms"); } } /** * @return Logger */ public function getLogger() { return $this->get('logger'); } public function loadContainer() { $this->startTimer(["load/container"]); $container = $this->getContainer(); $containerSettings = $this->getConfig()->get('core.container', []); $container->offsetSet("baseDir", $this->getBaseDir()); foreach ($containerSettings as $name => $value) { $container->offsetSet($name, $value); } $this->endTimer(["load/container"]); } public function loadServices() { $this->startTimer(['load/services']); $services = $this->getConfig()->get('core.services', []); $container = $this->getContainer(); foreach ($services as $name => $class) { $container->offsetSet($name, function ($container) use ($class, $name) { /** @var Core $core */ $core = $container->get('core'); $core->startTimer(['load/service/' . $name]); $item = $class::init($container, $name); $core->endTimer(['load/service/' . $name]); return $item; }); } $this->endTimer(['load/services']); } public function processRoutes() { $this->startTimer(["process/routes"]); $routesConfig = $this->getRoutes(); $prefix = $routesConfig["prefix"]; $routes = $routesConfig["routes"]; $this->processRoute("", $routes, $prefix); $this->endTimer(["process/routes"]); } /** * @return array */ public function getRoutes() { return $this->routes; } /** * @param array $routes */ public function setRoutes($routes) { $this->routes = $routes; } /** * @param string $path * @param array $routes * @param string $prefix */ public function processRoute($path, $routes, $prefix) { $slim = $this->getSlim(); $core = $this; $handler = function ($fullRoute) use ($core) { return function (Request $request, Response $response) use ($fullRoute, $core) { return $core->handle($fullRoute, $request, $response, $this); }; }; foreach ($routes as $child => $route) { if ($child[0] !== '/') { $slim->map([strtoupper($child)], $path, $handler($prefix . $route)); continue; } $fullPath = $path . $child; if (is_string($route)) { $slim->get($fullPath, $handler($prefix . $route)); continue; } else { $this->processRoute($fullPath, $route, $prefix); } } } /** * @return App */ public function getSlim() { return $this->get('slim'); } /** * @param string $class * @param Request $request * @param Response $response * @param ContainerInterface $containerInterface * @return Response */ public function handle($class, Request $request, Response $response, ContainerInterface $containerInterface) { $this->startTimer(['response']); /** @var Handler\Main $handler */ $handler = new $class($this, $request, $response, $containerInterface); $this->startTimer(['response/before-handle']); $result = $handler->beforeHandle(); if ($result instanceof Response) { $this->endTimer(['response']); return $result; } $this->startTimer(['response/handle']); $response = $handler->handle(); $this->endTimer(['response/handle']); $this->endTimer(['response']); return $response; } /** * @param App $slim */ public function setSlim($slim) { $this->set('slim', $slim); } /** * @param \Twig_Environment $twig */ public function setTwig($twig) { $this->set('twig', $twig); } public function run() { $this->getSlim()->run(); } }