nicklasos
11/6/2014 - 11:37 AM

php annotations

php annotations

<?php
/**
 * @Get 12
 * @Annotation var1
 * @Yep true
 * @Yey
 */
function do_one()
{

}


/**
 * Very simple annotation parser
 * <code>
 * /**
 *  * @Get 12
 *  * @Annotation test
 *  * @Yey
 *  *\/
 *  function do_one() {}
 *
 *  var_dump(function_annotation('do_one', ['Get, 'Yey', 'Rar']);
 *
 *  result:
 *   array (size=3)
 *    'Get' => string '12' (length=2)
 *    'Yey' => boolean true
 *    'Rar' => null
 * </code>
 * @param $funcName
 * @param array $annotations
 * @return array
 */
function function_annotations($funcName, array $annotations)
{
    $result = [];
    $reflection = new ReflectionFunction($funcName);
    $docBlock = $reflection->getDocComment();

    foreach ($annotations as $annotation) {
        $re = "/@{$annotation}(.*)/";
        preg_match_all($re, $docBlock, $matches);

        if (isset($matches[0][0])) {
            $result[$annotation] = !empty($matches[1][0]) ? ltrim($matches[1][0]) : true;
        } else {
            $result[$annotation] = null;
        }
    }

    return $result;
}


$an = function_annotations('do_one', ['Get', 'Yey', 'Rar']);
var_dump($an);
<?php
/**
 * Class Person
 * @Table people
 */
class Person
{
    /**
     * @Prop Yep
     */
    public function doSom()
    {

    }
}

/**
 * @Get 12
 * @Annotation var1
 * @Yep true
 * @Yey
 */
function do_one()
{

}


/**
 * Class AnnotationParser
 * Very basic annotation parser
 *
 * <code>
 * /**
 *  * @Get 12
 *  * @Annotation test
 *  * @Yey
 *  *\/
 *  function do_one() {}
 *
 *  var_dump(AnnotationParser::parseFunction('do_one', ['Get, 'Yey', 'Rar']);
 *
 *  result:
 *   array (size=3)
 *    'Get' => string '12' (length=2)
 *    'Yey' => boolean true
 *    'Rar' => null
 * </code>
 */
class AnnotationParser
{
    /**
     * Functions annotations parser
     * <code>
     * AnnotationParser::parseFunction('func_name', ['Foo', 'Bar']
     * </code>
     * @param $funcName
     * @param array $annotations
     * @return array
     */
    public static function parseFunction($funcName, array $annotations)
    {
        return self::parse(
            new ReflectionFunction($funcName),
            $annotations
        );
    }

    /**
     * <code>
     * AnnotationParser::parseClass(SomeClass::class, ['Foo', 'Bar']
     * </code>
     * @param $className
     * @param array $annotations
     * @return mixed
     */
    public static function parseClass($className, array $annotations)
    {
        return self::parse(
            new ReflectionClass($className),
            $annotations
        );
    }

    /**
     * <code>
     * AnnotationParser::parseMethod(SomeClass:class, 'someMethod', ['Test', 'Foo'])
     * </code>
     * @param $className
     * @param $methodName
     * @param array $annotations
     * @return mixed
     */
    public static function parseMethod($className, $methodName, array $annotations)
    {
        return self::parse(
            (new ReflectionClass($className))->getMethod($methodName),
            $annotations
        );
    }

    /**
     * @param ReflectionFunction|ReflectionClass|Reflector $reflector
     * @param array $annotations
     * @return mixed
     */
    private static function parse(Reflector $reflector, array $annotations)
    {
        $docBlock = $reflector->getDocComment();
        $result = [];

        foreach ($annotations as $annotation) {
            $re = "/@{$annotation}(.*)/";
            preg_match_all($re, $docBlock, $matches);

            if (isset($matches[0][0])) {
                $result[$annotation] = !empty($matches[1][0]) ? ltrim($matches[1][0]) : true;
            } else {
                $result[$annotation] = null;
            }
        }

        return $result;
    }
}


var_dump(AnnotationParser::parseFunction('do_one', ['Get', 'Yey', 'Rar']));
var_dump(AnnotationParser::parseClass(Person::class, ['Table']));
var_dump(AnnotationParser::parseMethod(Person::class, 'doSom', ['Prop', 'Rar']));