示例#1
0
 public function testIfWillProperlyCacheNamespacesForDifferentMetaContainers()
 {
     $path = (new ConfigDetector())->getRuntimePath();
     if (!is_dir($path)) {
         mkdir($path);
     }
     // Simulate different meta container classes by creating different paths
     $path1 = sprintf('%s/path1', $path);
     $path2 = sprintf('%s/path2', $path);
     $path3 = sprintf('%s/path3', $path);
     if (!is_dir($path1)) {
         mkdir($path1);
     }
     if (!is_dir($path2)) {
         mkdir($path2);
     }
     if (!is_dir($path3)) {
         mkdir($path3);
     }
     $ns1 = new NsCache($path1, Addendum::fly(), new CacheOptionsOne());
     $ns1->set();
     codecept_debug($ns1->get());
     $this->assertTrue($ns1->valid());
     $ns2 = new NsCache($path2, Addendum::fly(), new CacheOptionsTwo());
     $ns2->set();
     codecept_debug($ns2->get());
     $this->assertTrue($ns1->valid());
     $this->assertTrue($ns2->valid());
     $ns3 = new NsCache($path3, Addendum::fly(), new CacheOptionsOne());
     $ns3->set();
     codecept_debug($ns3->get());
     $this->assertTrue($ns1->valid());
     $this->assertTrue($ns2->valid());
     $this->assertTrue($ns3->valid());
 }
 public function testIfWillRecognizeAnnotationAfterDynamicallyAddingNamespace()
 {
     $model = new ModelWithTwoNsAnnotations();
     $options = new MetaOptions();
     $options->namespaces[] = NamespacedAnnotation::Ns;
     $meta = Meta::create($model, $options)->title;
     $this->assertTrue($meta->namespaced);
     // Not added second namespace
     $this->assertNull($meta->second);
     $this->assertNull($meta->third);
     // Second ns
     $options->namespaces[] = SecondNsAnnotation::Ns;
     $metaContainer2 = Meta::create($model, $options);
     $this->assertNotNull($metaContainer2);
     $meta2 = $metaContainer2->title;
     $this->assertTrue($meta2->namespaced);
     // Added second namespace
     $this->assertTrue($meta2->second, 'That namespace added via options id detected');
     // Third ns
     Addendum::fly()->addNamespace(ThirdNsAnnotation::Ns);
     $meta3 = Meta::create($model, $options)->title;
     $this->assertTrue($meta3->namespaced);
     $this->assertTrue($meta3->second);
     // Added second namespace
     $this->assertTrue($meta3->third, 'That namespace added via Addendum::addNamespace is detected');
 }
示例#3
0
 /**
  * @param string|object|AnnotatedInterface $model
  * @param MetaOptions $options
  * @throws Exception
  */
 protected function __construct($model = null, MetaOptions $options = null)
 {
     // For internal use
     if (null === $model) {
         return;
     }
     if (null === $options) {
         $options = new MetaOptions();
     }
     // TODO Use adapter here
     // ?TODO Abstract from component meta, so other kinds of meta extractors could be used
     // For example, for development annotation based extractor could be used, which could compile
     // Metadata to arrays, and for production environment, compiled arrays could be used
     $annotations = [];
     $mes = [];
     // Get reflection data
     $ad = Addendum::fly($options->instanceId);
     $ad->addNamespaces($options->namespaces);
     $info = $ad->annotate($model);
     // Class name of working component
     $className = is_object($model) ? get_class($model) : $model;
     if (!$info instanceof ReflectionAnnotatedClass) {
         throw new Exception(sprintf('Could not annotate `%s`', $className));
     }
     $properties = $info->getProperties(ReflectionProperty::IS_PUBLIC);
     $defaults = $info->getDefaultProperties();
     $methods = $info->getMethods(ReflectionMethod::IS_PUBLIC);
     // Setup type
     /**
      * @todo Fix it: $this->_meta->{$this->name}->...
      * ^-- _meta __get and __set is only for fields AND use _fields field,
      * for class OR methods it should use different fields
      * for class should be _main
      * for methods should be _methods
      * __get and __set should distinguish it somehow... - maybe by field type EComponentMetaProperty for fieltds etc.
      * Currently disabled
      * OR add function to Annotation to setEntity, which should point to _field, _main or _method?
      */
     // Setup class annotations
     $this->_type = new $options->typeClass($info);
     foreach ($info->getAllAnnotations() as $annotation) {
         if (!$annotation instanceof MetaAnnotationInterface) {
             continue;
         }
         $annotation->setName($info->name);
         $annotation->setEntity($this->_type);
         $annotation->setMeta($this);
         $annotation->init();
         $annotations[] = $annotation;
     }
     // Setup methods
     foreach ($methods as $method) {
         if (!$method instanceof ReflectionAnnotatedMethod) {
             throw new Exception(sprintf('Could not annotate `%s::%s()`', $className, $method->name));
         }
         // Ignore magic methods
         if (preg_match('~^__~', $method->name)) {
             continue;
         }
         // Ignore @Ignored marked methods
         if (IgnoredChecker::check($method)) {
             continue;
         }
         // Create method holder class based on options
         $methodMeta = new $options->methodClass($method);
         foreach ($method->getAllAnnotations() as $annotation) {
             if (!$annotation instanceof MetaAnnotationInterface) {
                 continue;
             }
             $annotation->setName($method->name);
             $annotation->setEntity($methodMeta);
             $annotation->setMeta($this);
             $annotation->init();
             $annotations[] = $annotation;
         }
         // Put it to metadata object
         $this->_methods[$method->name] = $methodMeta;
         // Get getters and setters for properties setup
         if (preg_match('~^[gs]et~', $method->name) && !$method->isStatic()) {
             $mes[$method->name] = true;
         }
     }
     // Setup properties
     foreach ($properties as $property) {
         if (!$property instanceof ReflectionAnnotatedProperty) {
             throw new Exception(sprintf('Could not annotate `%s::%s`', $className, $property->name));
         }
         if (IgnoredChecker::check($property)) {
             continue;
         }
         $name = $property->name;
         /* @var $property ReflectionAnnotatedProperty */
         $field = new $options->propertyClass($property);
         // Access options
         $field->callGet = isset($mes[$field->methodGet]) && $mes[$field->methodGet];
         $field->callSet = isset($mes[$field->methodSet]) && $mes[$field->methodSet];
         $field->direct = !($field->callGet || $field->callSet);
         $field->isStatic = $property->isStatic();
         // Other
         if (array_key_exists($name, $defaults)) {
             $field->default = $defaults[$name];
         }
         // Put it to metadata object
         $this->_fields[$field->name] = $field;
         foreach ($property->getAllAnnotations() as $annotation) {
             if (!$annotation instanceof MetaAnnotationInterface) {
                 continue;
             }
             $annotation->setName($field->name);
             $annotation->setEntity($field);
             $annotation->setMeta($this);
             $annotation->init();
             $annotations[] = $annotation;
         }
     }
     foreach ($annotations as $annotation) {
         $annotation->afterInit();
     }
 }
示例#4
0
 /**
  *
  * @param string $metaClass
  * @param AnnotatedInterface|object|string $component
  * @param MetaOptions|Addendum $options
  */
 public function __construct($metaClass = null, $component = null, $options = null)
 {
     if (null === self::$runtimePath) {
         self::$runtimePath = (new ConfigDetector())->getRuntimePath();
     }
     $this->path = self::$runtimePath . '/addendum';
     $this->metaClass = $metaClass;
     $this->component = $component;
     if (empty($options)) {
         $this->instanceId = Addendum::DefaultInstanceId;
     } elseif ($options instanceof Addendum) {
         $this->instanceId = $options->getInstanceId();
     } elseif ($options instanceof MetaOptions) {
         $this->instanceId = $options->instanceId;
     } else {
         throw new UnexpectedValueException('Unknown options');
     }
     $this->prepare();
     $this->addendum = Addendum::fly($this->instanceId);
     $this->nsCache = new NsCache(dirname($this->getFilename()), $this->addendum);
 }