Author: Bernhard Wick (bw@appserver.io)
Author: Hans Höchtl (hhoechtl@1drop.de)
 /**
  * Provisions all web applications.
  *
  * @param \AppserverIo\Psr\Application\ApplicationInterface $application The application instance
  *
  * @return void
  */
 public function provision(ApplicationInterface $application)
 {
     // check if the webapps directory exists
     if (is_dir($webappPath = $application->getWebappPath())) {
         // prepare the glob expression with the application's directories to parse
         $applicationDirectories = AppEnvironmentHelper::getEnvironmentAwareGlobPattern($webappPath, '{WEB-INF,META-INF}/provision', GLOB_BRACE);
         // load the service instance
         /** @var \AppserverIo\Appserver\Core\Api\ProvisioningService $service */
         $service = $this->getService();
         // load the configuration service instance
         /** @var \AppserverIo\Appserver\Core\Api\ConfigurationService $configurationService */
         $configurationService = $this->getInitialContext()->newService('AppserverIo\\Appserver\\Core\\Api\\ConfigurationService');
         // load the container node to initialize the system properties
         /** @var \AppserverIo\Appserver\Core\Api\Node\ContainerNodeInterface $containerNode */
         $containerNode = $application->getContainer()->getContainerNode();
         // iterate through all provisioning files (provision.xml), validate them and attach them to the configuration
         foreach ($service->globDir($applicationDirectories, GLOB_BRACE) as $provisionFile) {
             try {
                 // validate the file, but skip it if the validation fails
                 $configurationService->validateFile($provisionFile, null);
                 // load the system properties
                 $properties = $service->getSystemProperties($containerNode);
                 // append the application specific properties
                 $properties->add(SystemPropertyKeys::WEBAPP, $webappPath);
                 $properties->add(SystemPropertyKeys::WEBAPP_NAME, basename($webappPath));
                 $properties->add(SystemPropertyKeys::WEBAPP_CACHE, $application->getCacheDir());
                 $properties->add(SystemPropertyKeys::WEBAPP_SESSION, $application->getSessionDir());
                 // create a new provision node instance and replace the properties
                 $provisionNode = new ProvisionNode();
                 $provisionNode->initFromFile($provisionFile);
                 $provisionNode->replaceProperties($properties);
                 // query whether we've a datasource configured or not
                 if ($datasource = $provisionNode->getDatasource()) {
                     // try to load the datasource from the system configuration
                     $datasourceNode = $service->findByName($datasource->getName());
                     // try to inject the datasource node if available
                     if ($datasourceNode != null) {
                         $provisionNode->injectDatasource($datasourceNode);
                     }
                 }
                 /* Re-provision the provision.xml (reinitialize).
                  *
                  * ATTENTION: The re-provisioning is extremely important, because
                  * this allows dynamic replacement of placeholders by using the
                  * XML file as a template that will reinterpreted with the PHP
                  * interpreter!
                  */
                 $provisionNode->reprovision($provisionFile);
                 // execute the provisioning workflow
                 $this->executeProvision($application, $provisionNode, new \SplFileInfo($webappPath));
             } catch (ConfigurationException $ce) {
                 // load the logger and log the XML validation errors
                 $systemLogger = $this->getInitialContext()->getSystemLogger();
                 $systemLogger->error($ce->__toString());
                 // additionally log a message that DS will be missing
                 $systemLogger->critical(sprintf('Will skip reading provisioning steps in %s, provisioning might not have been done.', $provisionFile));
             }
         }
     }
 }
 /**
  * Parses the bean context's deployment descriptor file for beans
  * that has to be registered in the object manager.
  *
  * @return void
  */
 public function parse()
 {
     // load the web application base directory
     $webappPath = $this->getBeanContext()->getWebappPath();
     // prepare the deployment descriptor
     $deploymentDescriptor = AppEnvironmentHelper::getEnvironmentAwareGlobPattern($webappPath, 'META-INF' . DIRECTORY_SEPARATOR . 'epb');
     // query whether we found epb.xml deployment descriptor file
     if (file_exists($deploymentDescriptor) === false) {
         return;
     }
     // validate the passed configuration file
     /** @var \AppserverIo\Appserver\Core\Api\ConfigurationService $configurationService */
     $configurationService = $this->getApplication()->newService('AppserverIo\\Appserver\\Core\\Api\\ConfigurationService');
     $configurationService->validateFile($deploymentDescriptor, null, true);
     // prepare and initialize the configuration node
     $epbNode = new EpbNode();
     $epbNode->initFromFile($deploymentDescriptor);
     // query whether or not the deployment descriptor contains any beans
     /** @var \AppserverIo\Appserver\Core\Api\Node\EnterpriseBeansNode $enterpriseBeans */
     if ($enterpriseBeans = $epbNode->getEnterpriseBeans()) {
         // parse the session beans of the deployment descriptor
         /** @var \AppserverIo\Appserver\Core\Api\Node\SessionNode $sessionNode */
         foreach ($enterpriseBeans->getSessions() as $sessionNode) {
             $this->processConfigurationNode($sessionNode);
         }
         // parse the message driven beans from the deployment descriptor
         /** @var \AppserverIo\Appserver\Core\Api\Node\MessageDrivenNode $messageDrivenNode */
         foreach ($enterpriseBeans->getMessageDrivens() as $messageDrivenNode) {
             $this->processConfigurationNode($messageDrivenNode);
         }
     }
 }
 /**
  * Returns all datasource files we potentially use
  *
  * @return array
  */
 protected function getDatasourceFiles()
 {
     // if we have a valid app base we will collect all datasources
     $datasourceFiles = array();
     if (is_dir($appBase = $this->getAppBase())) {
         // get all the global datasource files first
         $datasourceFiles = array_merge($datasourceFiles, $this->prepareDatasourceFiles($this->getDeploymentService()->globDir($appBase . DIRECTORY_SEPARATOR . '*-ds.xml', 0, false)));
         // iterate over all applications and collect the environment specific datasources
         foreach (glob($appBase . '/*', GLOB_ONLYDIR) as $webappPath) {
             // append the datasource files of the webapp
             $datasourceFiles = array_merge($datasourceFiles, $this->prepareDatasourceFiles($this->getDeploymentService()->globDir(AppEnvironmentHelper::getEnvironmentAwareGlobPattern($webappPath, '*-ds'))));
         }
     }
     // return the found datasource files
     return $datasourceFiles;
 }
 /**
  * Loads the container instances from the META-INF/containers.xml configuration file of the
  * passed web application path and add/merge them to/with the system configuration.
  *
  * @param \AppserverIo\Appserver\Core\Api\Node\ContainerNodeInterface         $containerNode       The container node used for property replacement
  * @param \AppserverIo\Appserver\Core\Interfaces\SystemConfigurationInterface $systemConfiguration The system configuration to add/merge the found containers to/with
  * @param string                                                              $webappPath          The path to the web application to search for a META-INF/containers.xml file
  *
  * @return void
  */
 public function loadContainerInstance(ContainerNodeInterface $containerNode, SystemConfigurationInterface $systemConfiguration, $webappPath)
 {
     // load the service to validate the files
     /** @var \AppserverIo\Appserver\Core\Api\ConfigurationService $configurationService */
     $configurationService = $this->newService('AppserverIo\\Appserver\\Core\\Api\\ConfigurationService');
     // iterate through all server configurations (servers.xml), validate and merge them
     foreach ($this->globDir(AppEnvironmentHelper::getEnvironmentAwareGlobPattern($webappPath, 'META-INF/containers')) as $containersConfigurationFile) {
         try {
             // validate the application specific container configurations
             $configurationService->validateFile($containersConfigurationFile, null);
             // create a new containers node instance
             $containersNodeInstance = new ContainersNode();
             $containersNodeInstance->initFromFile($containersConfigurationFile);
             // load the system properties
             $properties = $this->getSystemProperties($containerNode);
             // prepare the sytsem properties
             $this->prepareSystemProperties($properties, $webappPath);
             /** @var \AppserverIo\Appserver\Core\Api\Node\ContainerNodeInterface $containerNodeInstance */
             foreach ($containersNodeInstance->getContainers() as $containerNodeInstance) {
                 // replace the properties for the found container node instance
                 $containerNodeInstance->replaceProperties($properties);
                 // query whether we've to merge or append the server node instance
                 if ($container = $systemConfiguration->getContainer($containerNodeInstance->getName())) {
                     $container->merge($containerNodeInstance);
                 } else {
                     $systemConfiguration->attachContainer($containerNodeInstance);
                 }
             }
         } catch (ConfigurationException $ce) {
             // load the logger and log the XML validation errors
             $systemLogger = $this->getInitialContext()->getSystemLogger();
             $systemLogger->error($ce->__toString());
             // additionally log a message that server configuration will be missing
             $systemLogger->critical(sprintf('Will skip app specific server configuration because of invalid file %s', $containersConfigurationFile));
         }
     }
 }
 /**
  * Registers the entity managers at startup.
  *
  * @param \AppserverIo\Psr\Application\ApplicationInterface $application The application instance
  *
  * @return void
  */
 public function registerEntityManagers(ApplicationInterface $application)
 {
     // build up META-INF directory var
     $metaInfDir = $this->getWebappPath() . DIRECTORY_SEPARATOR . 'META-INF';
     // check if we've found a valid directory
     if (is_dir($metaInfDir) === false) {
         return;
     }
     // check META-INF + subdirectories for XML files with MQ definitions
     /** @var \AppserverIo\Appserver\Core\Api\DeploymentService $service */
     $service = $application->newService('AppserverIo\\Appserver\\Core\\Api\\DeploymentService');
     $xmlFiles = $service->globDir(AppEnvironmentHelper::getEnvironmentAwareGlobPattern($this->getWebappPath(), 'META-INF' . DIRECTORY_SEPARATOR . 'persistence'));
     // load the configuration service instance
     /** @var \AppserverIo\Appserver\Core\Api\ConfigurationService $configurationService */
     $configurationService = $application->newService('AppserverIo\\Appserver\\Core\\Api\\ConfigurationService');
     // load the container node to initialize the system properties
     /** @var \AppserverIo\Appserver\Core\Api\Node\ContainerNodeInterface $containerNode */
     $containerNode = $application->getContainer()->getContainerNode();
     // gather all the deployed web applications
     foreach ($xmlFiles as $file) {
         try {
             // validate the file here, but skip if the validation fails
             $configurationService->validateFile($file, null, true);
             // load the system properties
             $properties = $service->getSystemProperties($containerNode);
             // append the application specific properties
             $properties->add(SystemPropertyKeys::WEBAPP, $webappPath = $application->getWebappPath());
             $properties->add(SystemPropertyKeys::WEBAPP_NAME, basename($webappPath));
             $properties->add(SystemPropertyKeys::WEBAPP_CACHE, $application->getCacheDir());
             $properties->add(SystemPropertyKeys::WEBAPP_SESSION, $application->getSessionDir());
             // create a new persistence manager node instance and replace the properties
             $persistenceNode = new PersistenceNode();
             $persistenceNode->initFromFile($file);
             $persistenceNode->replaceProperties($properties);
             // register the entity managers found in the configuration
             foreach ($persistenceNode->getPersistenceUnits() as $persistenceUnitNode) {
                 $this->registerEntityManager($application, $persistenceUnitNode);
             }
         } catch (InvalidConfigurationException $e) {
             // try to load the system logger instance
             /** @var \Psr\Log\LoggerInterface $systemLogger */
             if ($systemLogger = $this->getApplication()->getInitialContext()->getSystemLogger()) {
                 $systemLogger->error($e->getMessage());
                 $systemLogger->critical(sprintf('Persistence configuration file %s is invalid, needed entity managers might be missing.', $file));
             }
         } catch (\Exception $e) {
             // try to load the system logger instance
             /** @var \Psr\Log\LoggerInterface $systemLogger */
             if ($systemLogger = $this->getApplication()->getInitialContext()->getSystemLogger()) {
                 $systemLogger->error($e->__toString());
             }
         }
     }
 }
 /**
  * Initializes the available CRON configurations and returns them.
  *
  * @return array The array with the available CRON configurations
  */
 public function findAll()
 {
     try {
         // initialize the array with the CRON instances
         $cronInstances = array();
         // load the service necessary to validate CRON configuration files
         /** @var \AppserverIo\Appserver\Core\Api\ConfigurationService $configurationService */
         $configurationService = $this->newService('AppserverIo\\Appserver\\Core\\Api\\ConfigurationService');
         // load the base CRON configuration file
         $baseCronPath = $this->getConfdDir('cron.xml');
         // we will need to test our CRON configuration files
         $configurationService->validateFile($baseCronPath, null);
         // validate the base CRON file and load it as default if validation succeeds
         $cronInstance = new CronNode();
         $cronInstance->initFromFile($baseCronPath);
         // iterate over all jobs to configure the directory where they has to be executed
         /** @var \AppserverIo\Appserver\Core\Api\Node\JobNodeInterface $jobNode */
         foreach ($cronInstance->getJobs() as $job) {
             // load the execution information
             $execute = $job->getExecute();
             // query whether or not a base directory has been specified
             if ($execute && $execute->getDirectory() == null) {
                 // set the directory where the cron.xml file located as base directory, if not
                 $execute->setDirectory(dirname($baseCronPath));
             }
         }
         // add the default CRON configuration
         $cronInstances[] = $cronInstance;
         // iterate over the configured containers
         /** @var \AppserverIo\Appserver\Core\Api\Node\ContainerNodeInterface $containerNode */
         foreach ($this->getSystemConfiguration()->getContainers() as $containerNode) {
             // iterate over all applications and create the CRON configuration
             foreach (glob($this->getWebappsDir($containerNode) . '/*', GLOB_ONLYDIR) as $webappPath) {
                 // iterate through all CRON configurations (cron.xml), validate and merge them
                 foreach ($this->globDir(AppEnvironmentHelper::getEnvironmentAwareGlobPattern($webappPath, 'META-INF/cron')) as $cronFile) {
                     try {
                         // validate the file, but skip it if validation fails
                         $configurationService->validateFile($cronFile, null);
                         // load the system properties
                         $properties = $this->getSystemProperties($containerNode);
                         // append the application specific properties
                         $properties->add(SystemPropertyKeys::WEBAPP, $webappPath);
                         $properties->add(SystemPropertyKeys::WEBAPP_NAME, basename($webappPath));
                         // create a new CRON node instance and replace the properties
                         $cronInstance = new CronNode();
                         $cronInstance->initFromFile($cronFile);
                         $cronInstance->replaceProperties($properties);
                         // append it to the other CRON configurations
                         $cronInstances[] = $cronInstance;
                     } catch (ConfigurationException $ce) {
                         // load the logger and log the XML validation errors
                         $systemLogger = $this->getInitialContext()->getSystemLogger();
                         $systemLogger->error($ce->__toString());
                         // additionally log a message that CRON configuration will be missing
                         $systemLogger->critical(sprintf('Will skip app specific CRON configuration %s, configuration might be faulty.', $cronFile));
                     }
                 }
             }
         }
     } catch (ConfigurationException $ce) {
         // load the logger and log the XML validation errors
         $systemLogger = $this->getInitialContext()->getSystemLogger();
         $systemLogger->error($ce->__toString());
         // additionally log a message that DS will be missing
         $systemLogger->critical(sprintf('Problems validating base CRON file %s, this might affect app configurations badly.', $baseCronPath));
     }
     // return the array with the CRON instances
     return $cronInstances;
 }
Example #7
0
 /**
  * Registers aspects written within source files which we might encounter
  *
  * @param \AppserverIo\Psr\Application\ApplicationInterface $application The application instance
  *
  * @return void
  */
 public function registerAspectXml(ApplicationInterface $application)
 {
     /** @var \AppserverIo\Appserver\Core\Api\ConfigurationService $configurationService */
     $configurationService = $application->newService('AppserverIo\\Appserver\\Core\\Api\\ConfigurationService');
     // check if we even have a XMl file to read from
     $xmlPaths = $configurationService->globDir(AppEnvironmentHelper::getEnvironmentAwareGlobPattern($this->getWebappPath(), '{WEB-INF,META-INF,common}' . DIRECTORY_SEPARATOR . self::CONFIG_FILE_GLOB, GLOB_BRACE), GLOB_BRACE);
     foreach ($xmlPaths as $xmlPath) {
         // iterate all XML configuration files we found
         if (is_readable($xmlPath)) {
             // validate the file here, if it is not valid we can skip further steps
             try {
                 $configurationService->validateFile($xmlPath, null, true);
             } catch (InvalidConfigurationException $e) {
                 /** @var \Psr\Log\LoggerInterface $systemLogger */
                 $systemLogger = $this->getApplication()->getInitialContext()->getSystemLogger();
                 $systemLogger->error($e->getMessage());
                 $systemLogger->critical(sprintf('Pointcuts configuration file %s is invalid, AOP functionality might not work as expected.', $xmlPath));
                 continue;
             }
             // load the aop config
             $config = new \SimpleXMLElement(file_get_contents($xmlPath));
             $config->registerXPathNamespace('a', 'http://www.appserver.io/appserver');
             // create us an aspect
             // name of the aspect will be the application name
             $aspect = new Aspect();
             $aspect->setName($xmlPath);
             // check if we got some pointcuts
             foreach ($config->xpath('/a:pointcuts/a:pointcut') as $pointcutConfiguration) {
                 // build up the pointcut and add it to the collection
                 $pointcut = new Pointcut();
                 $pointcut->setAspectName($aspect->getName());
                 $pointcut->setName((string) $pointcutConfiguration->{'pointcut-name'});
                 $pointcut->setPointcutExpression(new PointcutExpression((string) $pointcutConfiguration->{'pointcut-pattern'}));
                 $aspect->getPointcuts()->add($pointcut);
             }
             // check if we got some advices
             foreach ($config->xpath('/a:pointcuts/a:advice') as $adviceConfiguration) {
                 // build up the advice and add it to the aspect
                 $advice = new Advice();
                 $advice->setAspectName((string) $adviceConfiguration->{'advice-aspect'});
                 $advice->setName($advice->getAspectName() . '->' . (string) $adviceConfiguration->{'advice-name'});
                 $advice->setCodeHook((string) $adviceConfiguration->{'advice-type'});
                 $pointcutPointcut = $this->generatePointcutPointcut((array) $adviceConfiguration->{'advice-pointcuts'}->{'pointcut-name'}, $aspect);
                 $advice->getPointcuts()->add($pointcutPointcut);
                 // finally add the advice to our aspect (we will also add it without pointcuts of its own)
                 $aspect->getAdvices()->add($advice);
             }
             // if the aspect contains pointcuts or advices it can be used
             if ($aspect->getPointcuts()->count() > 0 || $aspect->getAdvices()->count() > 0) {
                 $this->getAspectRegister()->set($aspect->getName(), $aspect);
             }
         }
     }
 }