diff --git a/.docheader b/.docheader
index a4eca36626724ba1e3c0698afdf12f9be441598b..78662df8235bf22a96eaa7952ca37511aaafbbfa 100644
--- a/.docheader
+++ b/.docheader
@@ -1,6 +1,5 @@
 This file is part of "%package%".
 
-"%package%" generates Typescript interfaces for Angular using api-platform metadata.
 Copyright (C) %yearRange% IRSTEA
 
 This program is free software: you can redistribute it and/or modify it under
diff --git a/composer.json b/composer.json
index d3a69bcfc2a1cb3b5af576c2960580fd12a33cda..d927851f66b199b928dbae8b84c58089fba07645 100644
--- a/composer.json
+++ b/composer.json
@@ -30,6 +30,7 @@
   },
   "require": {
     "php": "^7.1",
+    "api-platform/core": "^2.4",
     "beberlei/assert": "^3.2"
   },
   "require-dev": {
@@ -42,7 +43,8 @@
     "phpunit/phpunit": "^7.5",
     "roave/security-advisories": "dev-master",
     "sebastian/phpcpd": "^4.1",
-    "sensiolabs/security-checker": "^5.0"
+    "sensiolabs/security-checker": "^5.0",
+    "symfony/http-kernel": "^4.2"
   },
   "autoload": {
     "psr-4": {
diff --git a/composer.lock b/composer.lock
index bfe38931e1db3935640f05197a2383419fa25b18..acb299e554c13e16ea69d43c29170a4c104ec442 100644
--- a/composer.lock
+++ b/composer.lock
@@ -4,62 +4,1368 @@
         "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
         "This file is @generated automatically"
     ],
-    "content-hash": "4dccfc56090d6b5c36e98bca7ebc6ded",
+    "content-hash": "92a3acd6847db14636677bd4f443c0aa",
     "packages": [
+        {
+            "name": "api-platform/core",
+            "version": "v2.4.2",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/api-platform/core.git",
+                "reference": "76a47b73bdeca31bec647bb2f4e018f3dc29a3d7"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/api-platform/core/zipball/76a47b73bdeca31bec647bb2f4e018f3dc29a3d7",
+                "reference": "76a47b73bdeca31bec647bb2f4e018f3dc29a3d7",
+                "shasum": ""
+            },
+            "require": {
+                "doctrine/inflector": "^1.0",
+                "php": ">=7.1",
+                "psr/cache": "^1.0",
+                "psr/container": "^1.0",
+                "symfony/http-foundation": "^3.4 || ^4.0",
+                "symfony/http-kernel": "^3.4 || ^4.0",
+                "symfony/property-access": "^3.4 || ^4.0",
+                "symfony/property-info": "^3.4 || ^4.0",
+                "symfony/serializer": "^4.1",
+                "symfony/web-link": "^4.1",
+                "willdurand/negotiation": "^2.0.3"
+            },
+            "conflict": {
+                "doctrine/common": "<2.7",
+                "doctrine/mongodb-odm": "<2.0"
+            },
+            "require-dev": {
+                "behat/behat": "^3.1",
+                "behat/mink": "^1.7",
+                "behat/mink-browserkit-driver": "^1.3.1",
+                "behat/mink-extension": "^2.2",
+                "behat/symfony2-extension": "^2.1.1",
+                "behatch/contexts": "3.1.0",
+                "doctrine/annotations": "^1.2",
+                "doctrine/doctrine-bundle": "^1.8",
+                "doctrine/doctrine-cache-bundle": "^1.3.5",
+                "doctrine/mongodb-odm": "^2.0.0@beta",
+                "doctrine/mongodb-odm-bundle": "^4.0.0@beta",
+                "doctrine/orm": "^2.6.3",
+                "elasticsearch/elasticsearch": "^6.0",
+                "friendsofsymfony/user-bundle": "^2.2@dev",
+                "guzzlehttp/guzzle": "^6.0",
+                "jangregor/phpstan-prophecy": "^0.3",
+                "justinrainbow/json-schema": "^5.0",
+                "nelmio/api-doc-bundle": "^2.13.3",
+                "php-mock/php-mock-phpunit": "^2.0",
+                "phpdocumentor/reflection-docblock": "^3.0 || ^4.0",
+                "phpdocumentor/type-resolver": "^0.3 || ^0.4",
+                "phpspec/prophecy": "^1.8",
+                "phpstan/phpstan": "^0.11.3",
+                "phpstan/phpstan-doctrine": "^0.11.2",
+                "phpstan/phpstan-phpunit": "^0.11",
+                "phpstan/phpstan-symfony": "^0.11.2",
+                "phpunit/phpunit": "^7.5.2",
+                "psr/log": "^1.0",
+                "ramsey/uuid": "^3.7",
+                "ramsey/uuid-doctrine": "^1.4",
+                "sebastian/object-enumerator": "^3.0.3",
+                "symfony/asset": "^3.4 || ^4.0",
+                "symfony/cache": "^3.4 || ^4.0",
+                "symfony/config": "^3.4 || ^4.0",
+                "symfony/console": "^3.4 || ^4.0",
+                "symfony/css-selector": "^3.4 || ^4.0",
+                "symfony/debug": "^3.4 || ^4.0",
+                "symfony/dependency-injection": "^3.4 || ^4.0",
+                "symfony/doctrine-bridge": "^3.4 || ^4.0",
+                "symfony/dom-crawler": "^3.4 || ^4.0",
+                "symfony/event-dispatcher": "^3.4 || ^4.0",
+                "symfony/expression-language": "^3.4 || ^4.0",
+                "symfony/finder": "^3.4 || ^4.0",
+                "symfony/form": "^3.4 || ^4.0",
+                "symfony/framework-bundle": "^4.2",
+                "symfony/mercure-bundle": "*",
+                "symfony/messenger": "^4.2",
+                "symfony/phpunit-bridge": "^3.4.5 || ^4.0.5",
+                "symfony/routing": "^3.4 || ^4.0",
+                "symfony/security": "^3.4 || ^4.0",
+                "symfony/security-bundle": "^3.4 || ^4.0",
+                "symfony/twig-bundle": "^3.4 || ^4.0",
+                "symfony/validator": "^3.4 || ^4.0",
+                "symfony/web-profiler-bundle": "^4.2",
+                "symfony/yaml": "^3.4 || ^4.0",
+                "webonyx/graphql-php": ">=0.13 <1.0"
+            },
+            "suggest": {
+                "doctrine/mongodb-odm-bundle": "To support MongoDB. Only versions 4.0 and later are supported.",
+                "elasticsearch/elasticsearch": "To support Elasticsearch.",
+                "friendsofsymfony/user-bundle": "To use the FOSUserBundle bridge.",
+                "guzzlehttp/guzzle": "To use the HTTP cache invalidation system.",
+                "phpdocumentor/reflection-docblock": "To support extracting metadata from PHPDoc.",
+                "psr/cache-implementation": "To use metadata caching.",
+                "ramsey/uuid": "To support Ramsey's UUID identifiers.",
+                "symfony/cache": "To have metadata caching when using Symfony integration.",
+                "symfony/config": "To load XML configuration files.",
+                "symfony/expression-language": "To use authorization features.",
+                "symfony/security": "To use authorization features.",
+                "symfony/twig-bundle": "To use the Swagger UI integration.",
+                "symfony/web-profiler-bundle": "To use the data collector.",
+                "webonyx/graphql-php": "To support GraphQL."
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "2.5.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "ApiPlatform\\Core\\": "src/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Kévin Dunglas",
+                    "email": "dunglas@gmail.com",
+                    "homepage": "https://dunglas.fr"
+                }
+            ],
+            "description": "Build a fully-featured hypermedia or GraphQL API in minutes",
+            "homepage": "https://api-platform.com",
+            "keywords": [
+                "Hydra",
+                "JSON-LD",
+                "api",
+                "graphql",
+                "hal",
+                "jsonapi",
+                "openapi",
+                "rest",
+                "swagger"
+            ],
+            "time": "2019-03-28T20:16:27+00:00"
+        },
         {
             "name": "beberlei/assert",
             "version": "v3.2.0",
             "source": {
                 "type": "git",
-                "url": "https://github.com/beberlei/assert.git",
-                "reference": "fd82f4c8592c8128dd74481034c31da71ebafc56"
+                "url": "https://github.com/beberlei/assert.git",
+                "reference": "fd82f4c8592c8128dd74481034c31da71ebafc56"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/beberlei/assert/zipball/fd82f4c8592c8128dd74481034c31da71ebafc56",
+                "reference": "fd82f4c8592c8128dd74481034c31da71ebafc56",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7"
+            },
+            "require-dev": {
+                "friendsofphp/php-cs-fixer": "*",
+                "phpstan/phpstan-shim": "*",
+                "phpunit/phpunit": "*"
+            },
+            "type": "library",
+            "autoload": {
+                "psr-4": {
+                    "Assert\\": "lib/Assert"
+                },
+                "files": [
+                    "lib/Assert/functions.php"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "BSD-2-Clause"
+            ],
+            "authors": [
+                {
+                    "name": "Benjamin Eberlei",
+                    "email": "kontakt@beberlei.de",
+                    "role": "Lead Developer"
+                },
+                {
+                    "name": "Richard Quadling",
+                    "email": "rquadling@gmail.com",
+                    "role": "Collaborator"
+                }
+            ],
+            "description": "Thin assertion library for input validation in business models.",
+            "keywords": [
+                "assert",
+                "assertion",
+                "validation"
+            ],
+            "time": "2018-12-24T15:25:25+00:00"
+        },
+        {
+            "name": "doctrine/inflector",
+            "version": "v1.3.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/doctrine/inflector.git",
+                "reference": "5527a48b7313d15261292c149e55e26eae771b0a"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/doctrine/inflector/zipball/5527a48b7313d15261292c149e55e26eae771b0a",
+                "reference": "5527a48b7313d15261292c149e55e26eae771b0a",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1"
+            },
+            "require-dev": {
+                "phpunit/phpunit": "^6.2"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.3.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Doctrine\\Common\\Inflector\\": "lib/Doctrine/Common/Inflector"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Roman Borschel",
+                    "email": "roman@code-factory.org"
+                },
+                {
+                    "name": "Benjamin Eberlei",
+                    "email": "kontakt@beberlei.de"
+                },
+                {
+                    "name": "Guilherme Blanco",
+                    "email": "guilhermeblanco@gmail.com"
+                },
+                {
+                    "name": "Jonathan Wage",
+                    "email": "jonwage@gmail.com"
+                },
+                {
+                    "name": "Johannes Schmitt",
+                    "email": "schmittjoh@gmail.com"
+                }
+            ],
+            "description": "Common String Manipulations with regard to casing and singular/plural rules.",
+            "homepage": "http://www.doctrine-project.org",
+            "keywords": [
+                "inflection",
+                "pluralize",
+                "singularize",
+                "string"
+            ],
+            "time": "2018-01-09T20:05:19+00:00"
+        },
+        {
+            "name": "fig/link-util",
+            "version": "1.0.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/php-fig/link-util.git",
+                "reference": "1a07821801a148be4add11ab0603e4af55a72fac"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/php-fig/link-util/zipball/1a07821801a148be4add11ab0603e4af55a72fac",
+                "reference": "1a07821801a148be4add11ab0603e4af55a72fac",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.5.0",
+                "psr/link": "~1.0@dev"
+            },
+            "require-dev": {
+                "phpunit/phpunit": "^5.1",
+                "squizlabs/php_codesniffer": "^2.3.1"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Fig\\Link\\": "src/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "PHP-FIG",
+                    "homepage": "http://www.php-fig.org/"
+                }
+            ],
+            "description": "Common utility implementations for HTTP links",
+            "keywords": [
+                "http",
+                "http-link",
+                "link",
+                "psr",
+                "psr-13",
+                "rest"
+            ],
+            "time": "2016-10-17T18:31:11+00:00"
+        },
+        {
+            "name": "psr/cache",
+            "version": "1.0.1",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/php-fig/cache.git",
+                "reference": "d11b50ad223250cf17b86e38383413f5a6764bf8"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/php-fig/cache/zipball/d11b50ad223250cf17b86e38383413f5a6764bf8",
+                "reference": "d11b50ad223250cf17b86e38383413f5a6764bf8",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.3.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Psr\\Cache\\": "src/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "PHP-FIG",
+                    "homepage": "http://www.php-fig.org/"
+                }
+            ],
+            "description": "Common interface for caching libraries",
+            "keywords": [
+                "cache",
+                "psr",
+                "psr-6"
+            ],
+            "time": "2016-08-06T20:24:11+00:00"
+        },
+        {
+            "name": "psr/container",
+            "version": "1.0.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/php-fig/container.git",
+                "reference": "b7ce3b176482dbbc1245ebf52b181af44c2cf55f"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/php-fig/container/zipball/b7ce3b176482dbbc1245ebf52b181af44c2cf55f",
+                "reference": "b7ce3b176482dbbc1245ebf52b181af44c2cf55f",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.3.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Psr\\Container\\": "src/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "PHP-FIG",
+                    "homepage": "http://www.php-fig.org/"
+                }
+            ],
+            "description": "Common Container Interface (PHP FIG PSR-11)",
+            "homepage": "https://github.com/php-fig/container",
+            "keywords": [
+                "PSR-11",
+                "container",
+                "container-interface",
+                "container-interop",
+                "psr"
+            ],
+            "time": "2017-02-14T16:28:37+00:00"
+        },
+        {
+            "name": "psr/link",
+            "version": "1.0.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/php-fig/link.git",
+                "reference": "eea8e8662d5cd3ae4517c9b864493f59fca95562"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/php-fig/link/zipball/eea8e8662d5cd3ae4517c9b864493f59fca95562",
+                "reference": "eea8e8662d5cd3ae4517c9b864493f59fca95562",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.3.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Psr\\Link\\": "src/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "PHP-FIG",
+                    "homepage": "http://www.php-fig.org/"
+                }
+            ],
+            "description": "Common interfaces for HTTP links",
+            "keywords": [
+                "http",
+                "http-link",
+                "link",
+                "psr",
+                "psr-13",
+                "rest"
+            ],
+            "time": "2016-10-28T16:06:13+00:00"
+        },
+        {
+            "name": "psr/log",
+            "version": "1.1.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/php-fig/log.git",
+                "reference": "6c001f1daafa3a3ac1d8ff69ee4db8e799a654dd"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/php-fig/log/zipball/6c001f1daafa3a3ac1d8ff69ee4db8e799a654dd",
+                "reference": "6c001f1daafa3a3ac1d8ff69ee4db8e799a654dd",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.3.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Psr\\Log\\": "Psr/Log/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "PHP-FIG",
+                    "homepage": "http://www.php-fig.org/"
+                }
+            ],
+            "description": "Common interface for logging libraries",
+            "homepage": "https://github.com/php-fig/log",
+            "keywords": [
+                "log",
+                "psr",
+                "psr-3"
+            ],
+            "time": "2018-11-20T15:27:04+00:00"
+        },
+        {
+            "name": "symfony/contracts",
+            "version": "v1.0.2",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/contracts.git",
+                "reference": "1aa7ab2429c3d594dd70689604b5cf7421254cdf"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/contracts/zipball/1aa7ab2429c3d594dd70689604b5cf7421254cdf",
+                "reference": "1aa7ab2429c3d594dd70689604b5cf7421254cdf",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3"
+            },
+            "require-dev": {
+                "psr/cache": "^1.0",
+                "psr/container": "^1.0"
+            },
+            "suggest": {
+                "psr/cache": "When using the Cache contracts",
+                "psr/container": "When using the Service contracts",
+                "symfony/cache-contracts-implementation": "",
+                "symfony/service-contracts-implementation": "",
+                "symfony/translation-contracts-implementation": ""
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Contracts\\": ""
+                },
+                "exclude-from-classmap": [
+                    "**/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Nicolas Grekas",
+                    "email": "p@tchwork.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "A set of abstractions extracted out of the Symfony components",
+            "homepage": "https://symfony.com",
+            "keywords": [
+                "abstractions",
+                "contracts",
+                "decoupling",
+                "interfaces",
+                "interoperability",
+                "standards"
+            ],
+            "time": "2018-12-05T08:06:11+00:00"
+        },
+        {
+            "name": "symfony/debug",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/debug.git",
+                "reference": "2d279b6bb1d582dd5740d4d3251ae8c18812ed37"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/debug/zipball/2d279b6bb1d582dd5740d4d3251ae8c18812ed37",
+                "reference": "2d279b6bb1d582dd5740d4d3251ae8c18812ed37",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3",
+                "psr/log": "~1.0"
+            },
+            "conflict": {
+                "symfony/http-kernel": "<3.4"
+            },
+            "require-dev": {
+                "symfony/http-kernel": "~3.4|~4.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\Debug\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Fabien Potencier",
+                    "email": "fabien@symfony.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony Debug Component",
+            "homepage": "https://symfony.com",
+            "time": "2019-04-11T11:27:41+00:00"
+        },
+        {
+            "name": "symfony/event-dispatcher",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/event-dispatcher.git",
+                "reference": "fbce53cd74ac509cbe74b6f227622650ab759b02"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/fbce53cd74ac509cbe74b6f227622650ab759b02",
+                "reference": "fbce53cd74ac509cbe74b6f227622650ab759b02",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3",
+                "symfony/contracts": "^1.0"
+            },
+            "conflict": {
+                "symfony/dependency-injection": "<3.4"
+            },
+            "require-dev": {
+                "psr/log": "~1.0",
+                "symfony/config": "~3.4|~4.0",
+                "symfony/dependency-injection": "~3.4|~4.0",
+                "symfony/expression-language": "~3.4|~4.0",
+                "symfony/stopwatch": "~3.4|~4.0"
+            },
+            "suggest": {
+                "symfony/dependency-injection": "",
+                "symfony/http-kernel": ""
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\EventDispatcher\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Fabien Potencier",
+                    "email": "fabien@symfony.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony EventDispatcher Component",
+            "homepage": "https://symfony.com",
+            "time": "2019-04-06T13:51:08+00:00"
+        },
+        {
+            "name": "symfony/http-foundation",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/http-foundation.git",
+                "reference": "6ebbe61f48069033225c9d3fa7eb5ed116d766d6"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/http-foundation/zipball/6ebbe61f48069033225c9d3fa7eb5ed116d766d6",
+                "reference": "6ebbe61f48069033225c9d3fa7eb5ed116d766d6",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3",
+                "symfony/polyfill-mbstring": "~1.1"
+            },
+            "require-dev": {
+                "predis/predis": "~1.0",
+                "symfony/expression-language": "~3.4|~4.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\HttpFoundation\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Fabien Potencier",
+                    "email": "fabien@symfony.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony HttpFoundation Component",
+            "homepage": "https://symfony.com",
+            "time": "2019-04-17T14:56:00+00:00"
+        },
+        {
+            "name": "symfony/http-kernel",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/http-kernel.git",
+                "reference": "3db83303dbc1da9777e5ff63423b8b7fde423a1b"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/http-kernel/zipball/3db83303dbc1da9777e5ff63423b8b7fde423a1b",
+                "reference": "3db83303dbc1da9777e5ff63423b8b7fde423a1b",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3",
+                "psr/log": "~1.0",
+                "symfony/contracts": "^1.0.2",
+                "symfony/debug": "~3.4|~4.0",
+                "symfony/event-dispatcher": "~4.1",
+                "symfony/http-foundation": "^4.1.1",
+                "symfony/polyfill-ctype": "~1.8"
+            },
+            "conflict": {
+                "symfony/config": "<3.4",
+                "symfony/dependency-injection": "<4.2",
+                "symfony/translation": "<4.2",
+                "symfony/var-dumper": "<4.1.1",
+                "twig/twig": "<1.34|<2.4,>=2"
+            },
+            "provide": {
+                "psr/log-implementation": "1.0"
+            },
+            "require-dev": {
+                "psr/cache": "~1.0",
+                "symfony/browser-kit": "~3.4|~4.0",
+                "symfony/config": "~3.4|~4.0",
+                "symfony/console": "~3.4|~4.0",
+                "symfony/css-selector": "~3.4|~4.0",
+                "symfony/dependency-injection": "^4.2",
+                "symfony/dom-crawler": "~3.4|~4.0",
+                "symfony/expression-language": "~3.4|~4.0",
+                "symfony/finder": "~3.4|~4.0",
+                "symfony/process": "~3.4|~4.0",
+                "symfony/routing": "~3.4|~4.0",
+                "symfony/stopwatch": "~3.4|~4.0",
+                "symfony/templating": "~3.4|~4.0",
+                "symfony/translation": "~4.2",
+                "symfony/var-dumper": "^4.1.1"
+            },
+            "suggest": {
+                "symfony/browser-kit": "",
+                "symfony/config": "",
+                "symfony/console": "",
+                "symfony/dependency-injection": "",
+                "symfony/var-dumper": ""
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\HttpKernel\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Fabien Potencier",
+                    "email": "fabien@symfony.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony HttpKernel Component",
+            "homepage": "https://symfony.com",
+            "time": "2019-04-17T16:17:13+00:00"
+        },
+        {
+            "name": "symfony/inflector",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/inflector.git",
+                "reference": "275e54941a4f17a471c68d2a00e2513fc1fd4a78"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/inflector/zipball/275e54941a4f17a471c68d2a00e2513fc1fd4a78",
+                "reference": "275e54941a4f17a471c68d2a00e2513fc1fd4a78",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3",
+                "symfony/polyfill-ctype": "~1.8"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\Inflector\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Bernhard Schussek",
+                    "email": "bschussek@gmail.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony Inflector Component",
+            "homepage": "https://symfony.com",
+            "keywords": [
+                "inflection",
+                "pluralize",
+                "singularize",
+                "string",
+                "symfony",
+                "words"
+            ],
+            "time": "2019-01-16T20:31:39+00:00"
+        },
+        {
+            "name": "symfony/polyfill-ctype",
+            "version": "v1.11.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/polyfill-ctype.git",
+                "reference": "82ebae02209c21113908c229e9883c419720738a"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/82ebae02209c21113908c229e9883c419720738a",
+                "reference": "82ebae02209c21113908c229e9883c419720738a",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.3.3"
+            },
+            "suggest": {
+                "ext-ctype": "For best performance"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.11-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Polyfill\\Ctype\\": ""
+                },
+                "files": [
+                    "bootstrap.php"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                },
+                {
+                    "name": "Gert de Pagter",
+                    "email": "backendtea@gmail.com"
+                }
+            ],
+            "description": "Symfony polyfill for ctype functions",
+            "homepage": "https://symfony.com",
+            "keywords": [
+                "compatibility",
+                "ctype",
+                "polyfill",
+                "portable"
+            ],
+            "time": "2019-02-06T07:57:58+00:00"
+        },
+        {
+            "name": "symfony/polyfill-mbstring",
+            "version": "v1.11.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/polyfill-mbstring.git",
+                "reference": "fe5e94c604826c35a32fa832f35bd036b6799609"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/fe5e94c604826c35a32fa832f35bd036b6799609",
+                "reference": "fe5e94c604826c35a32fa832f35bd036b6799609",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.3.3"
+            },
+            "suggest": {
+                "ext-mbstring": "For best performance"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.11-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Polyfill\\Mbstring\\": ""
+                },
+                "files": [
+                    "bootstrap.php"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Nicolas Grekas",
+                    "email": "p@tchwork.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony polyfill for the Mbstring extension",
+            "homepage": "https://symfony.com",
+            "keywords": [
+                "compatibility",
+                "mbstring",
+                "polyfill",
+                "portable",
+                "shim"
+            ],
+            "time": "2019-02-06T07:57:58+00:00"
+        },
+        {
+            "name": "symfony/property-access",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/property-access.git",
+                "reference": "5440dd2b5373073beee051bd978b58a0f543b192"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/property-access/zipball/5440dd2b5373073beee051bd978b58a0f543b192",
+                "reference": "5440dd2b5373073beee051bd978b58a0f543b192",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3",
+                "symfony/inflector": "~3.4|~4.0"
+            },
+            "require-dev": {
+                "symfony/cache": "~3.4|~4.0"
+            },
+            "suggest": {
+                "psr/cache-implementation": "To cache access methods."
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\PropertyAccess\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Fabien Potencier",
+                    "email": "fabien@symfony.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony PropertyAccess Component",
+            "homepage": "https://symfony.com",
+            "keywords": [
+                "access",
+                "array",
+                "extraction",
+                "index",
+                "injection",
+                "object",
+                "property",
+                "property path",
+                "reflection"
+            ],
+            "time": "2019-03-04T09:16:25+00:00"
+        },
+        {
+            "name": "symfony/property-info",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/property-info.git",
+                "reference": "22d5dffd43454b5c8b5c1432b6ffef53e9f058e5"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/property-info/zipball/22d5dffd43454b5c8b5c1432b6ffef53e9f058e5",
+                "reference": "22d5dffd43454b5c8b5c1432b6ffef53e9f058e5",
+                "shasum": ""
+            },
+            "require": {
+                "php": "^7.1.3",
+                "symfony/inflector": "~3.4|~4.0"
+            },
+            "conflict": {
+                "phpdocumentor/reflection-docblock": "<3.0||>=3.2.0,<3.2.2",
+                "phpdocumentor/type-resolver": "<0.3.0",
+                "symfony/dependency-injection": "<3.4"
+            },
+            "require-dev": {
+                "doctrine/annotations": "~1.0",
+                "phpdocumentor/reflection-docblock": "^3.0|^4.0",
+                "symfony/cache": "~3.4|~4.0",
+                "symfony/dependency-injection": "~3.4|~4.0",
+                "symfony/serializer": "~3.4|~4.0"
+            },
+            "suggest": {
+                "phpdocumentor/reflection-docblock": "To use the PHPDoc",
+                "psr/cache-implementation": "To cache results",
+                "symfony/doctrine-bridge": "To use Doctrine metadata",
+                "symfony/serializer": "To use Serializer metadata"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\PropertyInfo\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Kévin Dunglas",
+                    "email": "dunglas@gmail.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony Property Info Component",
+            "homepage": "https://symfony.com",
+            "keywords": [
+                "doctrine",
+                "phpdoc",
+                "property",
+                "symfony",
+                "type",
+                "validator"
+            ],
+            "time": "2019-03-05T10:20:58+00:00"
+        },
+        {
+            "name": "symfony/serializer",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/serializer.git",
+                "reference": "602bded27aee8c2b0844f6b772947d44f61747a0"
             },
             "dist": {
                 "type": "zip",
-                "url": "https://api.github.com/repos/beberlei/assert/zipball/fd82f4c8592c8128dd74481034c31da71ebafc56",
-                "reference": "fd82f4c8592c8128dd74481034c31da71ebafc56",
+                "url": "https://api.github.com/repos/symfony/serializer/zipball/602bded27aee8c2b0844f6b772947d44f61747a0",
+                "reference": "602bded27aee8c2b0844f6b772947d44f61747a0",
                 "shasum": ""
             },
             "require": {
-                "php": "^7"
+                "php": "^7.1.3",
+                "symfony/polyfill-ctype": "~1.8"
+            },
+            "conflict": {
+                "phpdocumentor/type-resolver": "<0.2.1",
+                "symfony/dependency-injection": "<3.4",
+                "symfony/property-access": "<3.4",
+                "symfony/property-info": "<3.4",
+                "symfony/yaml": "<3.4"
             },
             "require-dev": {
-                "friendsofphp/php-cs-fixer": "*",
-                "phpstan/phpstan-shim": "*",
-                "phpunit/phpunit": "*"
+                "doctrine/annotations": "~1.0",
+                "doctrine/cache": "~1.0",
+                "phpdocumentor/reflection-docblock": "^3.0|^4.0",
+                "symfony/cache": "~3.4|~4.0",
+                "symfony/config": "~3.4|~4.0",
+                "symfony/dependency-injection": "~3.4|~4.0",
+                "symfony/http-foundation": "~3.4|~4.0",
+                "symfony/property-access": "~3.4|~4.0",
+                "symfony/property-info": "~3.4|~4.0",
+                "symfony/validator": "~3.4|~4.0",
+                "symfony/yaml": "~3.4|~4.0"
+            },
+            "suggest": {
+                "doctrine/annotations": "For using the annotation mapping. You will also need doctrine/cache.",
+                "doctrine/cache": "For using the default cached annotation reader and metadata cache.",
+                "psr/cache-implementation": "For using the metadata cache.",
+                "symfony/config": "For using the XML mapping loader.",
+                "symfony/http-foundation": "To use the DataUriNormalizer.",
+                "symfony/property-access": "For using the ObjectNormalizer.",
+                "symfony/property-info": "To deserialize relations.",
+                "symfony/yaml": "For using the default YAML mapping loader."
             },
             "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
             "autoload": {
                 "psr-4": {
-                    "Assert\\": "lib/Assert"
+                    "Symfony\\Component\\Serializer\\": ""
                 },
-                "files": [
-                    "lib/Assert/functions.php"
+                "exclude-from-classmap": [
+                    "/Tests/"
                 ]
             },
             "notification-url": "https://packagist.org/downloads/",
             "license": [
-                "BSD-2-Clause"
+                "MIT"
             ],
             "authors": [
                 {
-                    "name": "Benjamin Eberlei",
-                    "email": "kontakt@beberlei.de",
-                    "role": "Lead Developer"
+                    "name": "Fabien Potencier",
+                    "email": "fabien@symfony.com"
                 },
                 {
-                    "name": "Richard Quadling",
-                    "email": "rquadling@gmail.com",
-                    "role": "Collaborator"
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
                 }
             ],
-            "description": "Thin assertion library for input validation in business models.",
+            "description": "Symfony Serializer Component",
+            "homepage": "https://symfony.com",
+            "time": "2019-04-11T11:27:41+00:00"
+        },
+        {
+            "name": "symfony/web-link",
+            "version": "v4.2.7",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/symfony/web-link.git",
+                "reference": "47b8188b4bb8d24eef0bb287b0737d5b84a6cab8"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/symfony/web-link/zipball/47b8188b4bb8d24eef0bb287b0737d5b84a6cab8",
+                "reference": "47b8188b4bb8d24eef0bb287b0737d5b84a6cab8",
+                "shasum": ""
+            },
+            "require": {
+                "fig/link-util": "^1.0",
+                "php": "^7.1.3",
+                "psr/link": "^1.0"
+            },
+            "require-dev": {
+                "symfony/event-dispatcher": "~3.4|~4.0",
+                "symfony/http-foundation": "~3.4|~4.0",
+                "symfony/http-kernel": "~3.4|~4.0"
+            },
+            "suggest": {
+                "symfony/http-kernel": ""
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "4.2-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Symfony\\Component\\WebLink\\": ""
+                },
+                "exclude-from-classmap": [
+                    "/Tests/"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Kévin Dunglas",
+                    "email": "dunglas@gmail.com"
+                },
+                {
+                    "name": "Symfony Community",
+                    "homepage": "https://symfony.com/contributors"
+                }
+            ],
+            "description": "Symfony WebLink Component",
+            "homepage": "https://symfony.com",
             "keywords": [
-                "assert",
-                "assertion",
-                "validation"
+                "dns-prefetch",
+                "http",
+                "http2",
+                "link",
+                "performance",
+                "prefetch",
+                "preload",
+                "prerender",
+                "psr13",
+                "push"
             ],
-            "time": "2018-12-24T15:25:25+00:00"
+            "time": "2019-01-16T20:31:39+00:00"
+        },
+        {
+            "name": "willdurand/negotiation",
+            "version": "v2.3.1",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/willdurand/Negotiation.git",
+                "reference": "03436ededa67c6e83b9b12defac15384cb399dc9"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/willdurand/Negotiation/zipball/03436ededa67c6e83b9b12defac15384cb399dc9",
+                "reference": "03436ededa67c6e83b9b12defac15384cb399dc9",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.4.0"
+            },
+            "require-dev": {
+                "phpunit/phpunit": "~4.5"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "2.3-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Negotiation\\": "src/Negotiation"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "William Durand",
+                    "email": "will+git@drnd.me"
+                }
+            ],
+            "description": "Content Negotiation tools for PHP provided as a standalone library.",
+            "homepage": "http://williamdurand.fr/Negotiation/",
+            "keywords": [
+                "accept",
+                "content",
+                "format",
+                "header",
+                "negotiation"
+            ],
+            "time": "2017-05-14T17:21:12+00:00"
         }
     ],
     "packages-dev": [
@@ -2712,109 +4018,13 @@
                 }
             ],
             "description": "The PHP Unit Testing framework.",
-            "homepage": "https://phpunit.de/",
-            "keywords": [
-                "phpunit",
-                "testing",
-                "xunit"
-            ],
-            "time": "2019-03-26T13:23:54+00:00"
-        },
-        {
-            "name": "psr/container",
-            "version": "1.0.0",
-            "source": {
-                "type": "git",
-                "url": "https://github.com/php-fig/container.git",
-                "reference": "b7ce3b176482dbbc1245ebf52b181af44c2cf55f"
-            },
-            "dist": {
-                "type": "zip",
-                "url": "https://api.github.com/repos/php-fig/container/zipball/b7ce3b176482dbbc1245ebf52b181af44c2cf55f",
-                "reference": "b7ce3b176482dbbc1245ebf52b181af44c2cf55f",
-                "shasum": ""
-            },
-            "require": {
-                "php": ">=5.3.0"
-            },
-            "type": "library",
-            "extra": {
-                "branch-alias": {
-                    "dev-master": "1.0.x-dev"
-                }
-            },
-            "autoload": {
-                "psr-4": {
-                    "Psr\\Container\\": "src/"
-                }
-            },
-            "notification-url": "https://packagist.org/downloads/",
-            "license": [
-                "MIT"
-            ],
-            "authors": [
-                {
-                    "name": "PHP-FIG",
-                    "homepage": "http://www.php-fig.org/"
-                }
-            ],
-            "description": "Common Container Interface (PHP FIG PSR-11)",
-            "homepage": "https://github.com/php-fig/container",
-            "keywords": [
-                "PSR-11",
-                "container",
-                "container-interface",
-                "container-interop",
-                "psr"
-            ],
-            "time": "2017-02-14T16:28:37+00:00"
-        },
-        {
-            "name": "psr/log",
-            "version": "1.1.0",
-            "source": {
-                "type": "git",
-                "url": "https://github.com/php-fig/log.git",
-                "reference": "6c001f1daafa3a3ac1d8ff69ee4db8e799a654dd"
-            },
-            "dist": {
-                "type": "zip",
-                "url": "https://api.github.com/repos/php-fig/log/zipball/6c001f1daafa3a3ac1d8ff69ee4db8e799a654dd",
-                "reference": "6c001f1daafa3a3ac1d8ff69ee4db8e799a654dd",
-                "shasum": ""
-            },
-            "require": {
-                "php": ">=5.3.0"
-            },
-            "type": "library",
-            "extra": {
-                "branch-alias": {
-                    "dev-master": "1.0.x-dev"
-                }
-            },
-            "autoload": {
-                "psr-4": {
-                    "Psr\\Log\\": "Psr/Log/"
-                }
-            },
-            "notification-url": "https://packagist.org/downloads/",
-            "license": [
-                "MIT"
-            ],
-            "authors": [
-                {
-                    "name": "PHP-FIG",
-                    "homepage": "http://www.php-fig.org/"
-                }
-            ],
-            "description": "Common interface for logging libraries",
-            "homepage": "https://github.com/php-fig/log",
-            "keywords": [
-                "log",
-                "psr",
-                "psr-3"
+            "homepage": "https://phpunit.de/",
+            "keywords": [
+                "phpunit",
+                "testing",
+                "xunit"
             ],
-            "time": "2018-11-20T15:27:04+00:00"
+            "time": "2019-03-26T13:23:54+00:00"
         },
         {
             "name": "roave/security-advisories",
@@ -3858,74 +5068,6 @@
             "homepage": "https://symfony.com",
             "time": "2019-04-08T14:23:48+00:00"
         },
-        {
-            "name": "symfony/contracts",
-            "version": "v1.0.2",
-            "source": {
-                "type": "git",
-                "url": "https://github.com/symfony/contracts.git",
-                "reference": "1aa7ab2429c3d594dd70689604b5cf7421254cdf"
-            },
-            "dist": {
-                "type": "zip",
-                "url": "https://api.github.com/repos/symfony/contracts/zipball/1aa7ab2429c3d594dd70689604b5cf7421254cdf",
-                "reference": "1aa7ab2429c3d594dd70689604b5cf7421254cdf",
-                "shasum": ""
-            },
-            "require": {
-                "php": "^7.1.3"
-            },
-            "require-dev": {
-                "psr/cache": "^1.0",
-                "psr/container": "^1.0"
-            },
-            "suggest": {
-                "psr/cache": "When using the Cache contracts",
-                "psr/container": "When using the Service contracts",
-                "symfony/cache-contracts-implementation": "",
-                "symfony/service-contracts-implementation": "",
-                "symfony/translation-contracts-implementation": ""
-            },
-            "type": "library",
-            "extra": {
-                "branch-alias": {
-                    "dev-master": "1.0-dev"
-                }
-            },
-            "autoload": {
-                "psr-4": {
-                    "Symfony\\Contracts\\": ""
-                },
-                "exclude-from-classmap": [
-                    "**/Tests/"
-                ]
-            },
-            "notification-url": "https://packagist.org/downloads/",
-            "license": [
-                "MIT"
-            ],
-            "authors": [
-                {
-                    "name": "Nicolas Grekas",
-                    "email": "p@tchwork.com"
-                },
-                {
-                    "name": "Symfony Community",
-                    "homepage": "https://symfony.com/contributors"
-                }
-            ],
-            "description": "A set of abstractions extracted out of the Symfony components",
-            "homepage": "https://symfony.com",
-            "keywords": [
-                "abstractions",
-                "contracts",
-                "decoupling",
-                "interfaces",
-                "interoperability",
-                "standards"
-            ],
-            "time": "2018-12-05T08:06:11+00:00"
-        },
         {
             "name": "symfony/dependency-injection",
             "version": "v4.2.7",
@@ -3999,70 +5141,6 @@
             "homepage": "https://symfony.com",
             "time": "2019-04-16T11:19:53+00:00"
         },
-        {
-            "name": "symfony/event-dispatcher",
-            "version": "v4.2.7",
-            "source": {
-                "type": "git",
-                "url": "https://github.com/symfony/event-dispatcher.git",
-                "reference": "fbce53cd74ac509cbe74b6f227622650ab759b02"
-            },
-            "dist": {
-                "type": "zip",
-                "url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/fbce53cd74ac509cbe74b6f227622650ab759b02",
-                "reference": "fbce53cd74ac509cbe74b6f227622650ab759b02",
-                "shasum": ""
-            },
-            "require": {
-                "php": "^7.1.3",
-                "symfony/contracts": "^1.0"
-            },
-            "conflict": {
-                "symfony/dependency-injection": "<3.4"
-            },
-            "require-dev": {
-                "psr/log": "~1.0",
-                "symfony/config": "~3.4|~4.0",
-                "symfony/dependency-injection": "~3.4|~4.0",
-                "symfony/expression-language": "~3.4|~4.0",
-                "symfony/stopwatch": "~3.4|~4.0"
-            },
-            "suggest": {
-                "symfony/dependency-injection": "",
-                "symfony/http-kernel": ""
-            },
-            "type": "library",
-            "extra": {
-                "branch-alias": {
-                    "dev-master": "4.2-dev"
-                }
-            },
-            "autoload": {
-                "psr-4": {
-                    "Symfony\\Component\\EventDispatcher\\": ""
-                },
-                "exclude-from-classmap": [
-                    "/Tests/"
-                ]
-            },
-            "notification-url": "https://packagist.org/downloads/",
-            "license": [
-                "MIT"
-            ],
-            "authors": [
-                {
-                    "name": "Fabien Potencier",
-                    "email": "fabien@symfony.com"
-                },
-                {
-                    "name": "Symfony Community",
-                    "homepage": "https://symfony.com/contributors"
-                }
-            ],
-            "description": "Symfony EventDispatcher Component",
-            "homepage": "https://symfony.com",
-            "time": "2019-04-06T13:51:08+00:00"
-        },
         {
             "name": "symfony/filesystem",
             "version": "v4.2.7",
@@ -4216,123 +5294,6 @@
             ],
             "time": "2019-04-10T16:20:36+00:00"
         },
-        {
-            "name": "symfony/polyfill-ctype",
-            "version": "v1.11.0",
-            "source": {
-                "type": "git",
-                "url": "https://github.com/symfony/polyfill-ctype.git",
-                "reference": "82ebae02209c21113908c229e9883c419720738a"
-            },
-            "dist": {
-                "type": "zip",
-                "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/82ebae02209c21113908c229e9883c419720738a",
-                "reference": "82ebae02209c21113908c229e9883c419720738a",
-                "shasum": ""
-            },
-            "require": {
-                "php": ">=5.3.3"
-            },
-            "suggest": {
-                "ext-ctype": "For best performance"
-            },
-            "type": "library",
-            "extra": {
-                "branch-alias": {
-                    "dev-master": "1.11-dev"
-                }
-            },
-            "autoload": {
-                "psr-4": {
-                    "Symfony\\Polyfill\\Ctype\\": ""
-                },
-                "files": [
-                    "bootstrap.php"
-                ]
-            },
-            "notification-url": "https://packagist.org/downloads/",
-            "license": [
-                "MIT"
-            ],
-            "authors": [
-                {
-                    "name": "Symfony Community",
-                    "homepage": "https://symfony.com/contributors"
-                },
-                {
-                    "name": "Gert de Pagter",
-                    "email": "backendtea@gmail.com"
-                }
-            ],
-            "description": "Symfony polyfill for ctype functions",
-            "homepage": "https://symfony.com",
-            "keywords": [
-                "compatibility",
-                "ctype",
-                "polyfill",
-                "portable"
-            ],
-            "time": "2019-02-06T07:57:58+00:00"
-        },
-        {
-            "name": "symfony/polyfill-mbstring",
-            "version": "v1.11.0",
-            "source": {
-                "type": "git",
-                "url": "https://github.com/symfony/polyfill-mbstring.git",
-                "reference": "fe5e94c604826c35a32fa832f35bd036b6799609"
-            },
-            "dist": {
-                "type": "zip",
-                "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/fe5e94c604826c35a32fa832f35bd036b6799609",
-                "reference": "fe5e94c604826c35a32fa832f35bd036b6799609",
-                "shasum": ""
-            },
-            "require": {
-                "php": ">=5.3.3"
-            },
-            "suggest": {
-                "ext-mbstring": "For best performance"
-            },
-            "type": "library",
-            "extra": {
-                "branch-alias": {
-                    "dev-master": "1.11-dev"
-                }
-            },
-            "autoload": {
-                "psr-4": {
-                    "Symfony\\Polyfill\\Mbstring\\": ""
-                },
-                "files": [
-                    "bootstrap.php"
-                ]
-            },
-            "notification-url": "https://packagist.org/downloads/",
-            "license": [
-                "MIT"
-            ],
-            "authors": [
-                {
-                    "name": "Nicolas Grekas",
-                    "email": "p@tchwork.com"
-                },
-                {
-                    "name": "Symfony Community",
-                    "homepage": "https://symfony.com/contributors"
-                }
-            ],
-            "description": "Symfony polyfill for the Mbstring extension",
-            "homepage": "https://symfony.com",
-            "keywords": [
-                "compatibility",
-                "mbstring",
-                "polyfill",
-                "portable",
-                "shim"
-            ],
-            "time": "2019-02-06T07:57:58+00:00"
-        },
         {
             "name": "symfony/polyfill-php70",
             "version": "v1.11.0",
diff --git a/src/Bridge/Bundle/IrsteaApiMetadataBundle.php b/src/Bridge/Bundle/IrsteaApiMetadataBundle.php
new file mode 100644
index 0000000000000000000000000000000000000000..a1d25a1a49bbfe021869f27d11443b37b39e007e
--- /dev/null
+++ b/src/Bridge/Bundle/IrsteaApiMetadataBundle.php
@@ -0,0 +1,28 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Bridge\Bundle;
+
+/**
+ * Class IrsteaApiMetadataBundle.
+ */
+final class IrsteaApiMetadataBundle
+{
+}
diff --git a/src/DataProvider/ResourceMetadataProvider.php b/src/DataProvider/ResourceMetadataProvider.php
new file mode 100644
index 0000000000000000000000000000000000000000..29cd8fcb39a79388e4f62c52603cd0710c0b6617
--- /dev/null
+++ b/src/DataProvider/ResourceMetadataProvider.php
@@ -0,0 +1,258 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\DataProvider;
+
+use ApiPlatform\Core\Api\OperationMethodResolverInterface;
+use ApiPlatform\Core\Api\OperationType;
+use ApiPlatform\Core\DataProvider\CollectionDataProviderInterface;
+use ApiPlatform\Core\DataProvider\ItemDataProviderInterface;
+use ApiPlatform\Core\DataProvider\RestrictedDataProviderInterface;
+use ApiPlatform\Core\Exception\PropertyNotFoundException;
+use ApiPlatform\Core\Exception\ResourceClassNotFoundException;
+use ApiPlatform\Core\Metadata\Property\Factory\PropertyMetadataFactoryInterface;
+use ApiPlatform\Core\Metadata\Property\Factory\PropertyNameCollectionFactoryInterface;
+use ApiPlatform\Core\Metadata\Resource\Factory\ResourceMetadataFactoryInterface;
+use ApiPlatform\Core\Metadata\Resource\Factory\ResourceNameCollectionFactoryInterface;
+use ApiPlatform\Core\Metadata\Resource\ResourceMetadata as APIResourceMetadata;
+use ApiPlatform\Core\PathResolver\OperationPathResolverInterface;
+use Irstea\ApiMetadata\Model\EmbeddedMetadata;
+use Irstea\ApiMetadata\Model\LinkMetadata;
+use Irstea\ApiMetadata\Model\OperationMetadata;
+use Irstea\ApiMetadata\Model\PropertyMetadata;
+use Irstea\ApiMetadata\Model\ResourceMetadata;
+use Irstea\ApiMetadata\Model\ScalarMetadata;
+use Irstea\ApiMetadata\Model\TypeMetadata;
+use Symfony\Component\PropertyInfo\Type;
+
+/**
+ * Class ResourceMetadataProvider.
+ */
+class ResourceMetadataProvider implements CollectionDataProviderInterface, ItemDataProviderInterface, RestrictedDataProviderInterface
+{
+    /**
+     * @var ResourceNameCollectionFactoryInterface
+     */
+    private $resourceNameCollectionFactory;
+
+    /**
+     * @var ResourceMetadataFactoryInterface
+     */
+    private $resourceMetadataFactory;
+
+    /**
+     * @var PropertyMetadataFactoryInterface
+     */
+    private $propertyMetadataFactory;
+
+    /**
+     * @var PropertyNameCollectionFactoryInterface
+     */
+    private $propertyNameCollectionFactory;
+
+    /**
+     * @var OperationMethodResolverInterface
+     */
+    private $operationMethodResolver;
+
+    /**
+     * @var OperationPathResolverInterface
+     */
+    private $operationPathResolver;
+
+    /**
+     * ResourceMetadataProvider constructor.
+     *
+     * @param ResourceNameCollectionFactoryInterface $resourceNameCollectionFactory
+     * @param ResourceMetadataFactoryInterface       $resourceMetadataFactory
+     * @param PropertyNameCollectionFactoryInterface $propertyNameCollectionFactory
+     * @param PropertyMetadataFactoryInterface       $propertyMetadataFactory
+     * @param OperationMethodResolverInterface       $operationMethodResolver
+     * @param OperationPathResolverInterface         $operationPathResolver
+     */
+    public function __construct(
+        ResourceNameCollectionFactoryInterface $resourceNameCollectionFactory,
+        ResourceMetadataFactoryInterface $resourceMetadataFactory,
+        PropertyNameCollectionFactoryInterface $propertyNameCollectionFactory,
+        PropertyMetadataFactoryInterface $propertyMetadataFactory,
+        OperationMethodResolverInterface $operationMethodResolver,
+        OperationPathResolverInterface $operationPathResolver
+    ) {
+        $this->resourceNameCollectionFactory = $resourceNameCollectionFactory;
+        $this->resourceMetadataFactory = $resourceMetadataFactory;
+        $this->propertyMetadataFactory = $propertyMetadataFactory;
+        $this->propertyNameCollectionFactory = $propertyNameCollectionFactory;
+        $this->operationMethodResolver = $operationMethodResolver;
+        $this->operationPathResolver = $operationPathResolver;
+    }
+
+    /**
+     * @param string      $resourceClass
+     * @param string|null $operationName
+     * @param array       $context
+     *
+     * @return bool
+     */
+    public function supports(string $resourceClass, string $operationName = null, array $context = []): bool
+    {
+        return $resourceClass === ResourceMetadata::class && $operationName === 'get';
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getCollection(string $resourceClass, string $operationName = null): \Generator
+    {
+        foreach ($this->resourceNameCollectionFactory->create() as $className) {
+            $metadata = $this->getResourceMetadata($className);
+            yield $metadata->shortName => $metadata;
+        }
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getItem(string $resourceClass, $id, string $operationName = null, array $context = [])
+    {
+        foreach ($this->resourceNameCollectionFactory->create() as $className) {
+            $resource = $this->resourceMetadataFactory->create($className);
+            if ($resource->getShortName() === $id) {
+                return $this->getResourceMetadata($className);
+            }
+        }
+
+        return null;
+    }
+
+    /**
+     * @param string $resourceClass
+     *
+     * @throws PropertyNotFoundException
+     * @throws ResourceClassNotFoundException
+     *
+     * @return ResourceMetadata
+     */
+    private function getResourceMetadata(string $resourceClass): ResourceMetadata
+    {
+        $resource = $this->resourceMetadataFactory->create($resourceClass);
+
+        $properties = [];
+
+        foreach ($this->propertyNameCollectionFactory->create($resourceClass) as $name) {
+            $prop = $this->getPropertyMetadata($resourceClass, $name);
+            $properties[$prop->name] = $prop;
+        }
+
+        $operations = [];
+
+        foreach ($resource->getItemOperations() as $name => $attributes) {
+            $operations[] = $this->getOperationMetadata($resource, $resourceClass, OperationType::ITEM, $name, $attributes);
+        }
+
+        foreach ($resource->getCollectionOperations() as $name => $attributes) {
+            $operations[] = $this->getOperationMetadata($resource, $resourceClass, OperationType::COLLECTION, $name, $attributes);
+        }
+
+        return new ResourceMetadata(
+            $resource->getShortName(),
+            $properties,
+            $operations
+        );
+    }
+
+    /**
+     * @param string $resourceClass
+     * @param string $name
+     *
+     * @throws PropertyNotFoundException
+     *
+     * @return PropertyMetadata
+     */
+    private function getPropertyMetadata(string $resourceClass, string $name): PropertyMetadata
+    {
+        $property = $this->propertyMetadataFactory->create($resourceClass, $name);
+        $type = $property->getType();
+
+        return new PropertyMetadata(
+            $name,
+            $this->getTypeMetadata($type),
+            $type && !$type->isNullable(),
+            !$property->isWritable() ?: false,
+            $property->isIdentifier() ?: false
+        );
+    }
+
+    /**
+     * @param Type|null $type
+     *
+     * @return TypeMetadata
+     */
+    private function getTypeMetadata(?Type $type): TypeMetadata
+    {
+        if (!$type) {
+            return ScalarMetadata::create('any');
+        }
+
+        if ($type->isCollection()) {
+            return $this->getCollectionMetadata($type->getCollectionKeyType(), $type->getCollectionValueType());
+        }
+
+        if (!$type->getClassName()) {
+            return ScalarMetadata::create($type->getBuiltinType());
+        }
+
+        $className = $type->getClassName();
+        try {
+            $this->resourceMetadataFactory->create($className);
+
+            return LinkMetadata::create($className);
+        } catch (ResourceClassNotFoundException $ex) {
+            // Pass
+        }
+
+        return EmbeddedMetadata::create($className);
+    }
+
+    /**
+     * @param APIResourceMetadata $resource
+     * @param string              $resourceClass
+     * @param string              $type
+     * @param string              $name
+     * @param array               $attributes
+     *
+     * @return OperationMetadata
+     */
+    private function getOperationMetadata(APIResourceMetadata $resource, string $resourceClass, string $type, string $name, array $attributes): OperationMetadata
+    {
+        $path = $this->operationPathResolver->resolveOperationPath($resource->getShortName(), $attributes, $type, $name);
+
+        $getter = $type === 'collection' ? 'getCollectionOperationMethod' : 'getItemOperationMethod';
+        $method = $this->operationMethodResolver->$getter($resourceClass, $name);
+
+        return new OperationMetadata(
+            $type,
+            $name,
+            $path,
+            $method,
+            null,
+            null
+        );
+    }
+}
diff --git a/src/Factory/OperationFactory.php b/src/Factory/OperationFactory.php
new file mode 100644
index 0000000000000000000000000000000000000000..63f94f7d1080678888ab30182cd85217c7761445
--- /dev/null
+++ b/src/Factory/OperationFactory.php
@@ -0,0 +1,45 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+use Irstea\ApiMetadata\Model\OperationMetadata;
+
+/**
+ * Class OperationFactory.
+ */
+final class OperationFactory implements OperationFactoryInterface
+{
+    /**
+     * {@inheritdoc}
+     */
+    public function create(string $class, string $type, string $name): OperationMetadata
+    {
+        throw new \RuntimeException('Not yet implemented');
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function enumerate(string $class): array
+    {
+        throw new \RuntimeException('Not yet implemented');
+    }
+}
diff --git a/src/Factory/OperationFactoryInterface.php b/src/Factory/OperationFactoryInterface.php
new file mode 100644
index 0000000000000000000000000000000000000000..affc0971df7f956d6f20f804eeb37f229c5d46fe
--- /dev/null
+++ b/src/Factory/OperationFactoryInterface.php
@@ -0,0 +1,45 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+use Irstea\ApiMetadata\Model\OperationMetadata;
+
+/**
+ * Class OperationFactoryInterface.
+ */
+interface OperationFactoryInterface
+{
+    /**
+     * @param string $class
+     * @param string $type
+     * @param string $name
+     *
+     * @return OperationMetadata
+     */
+    public function create(string $class, string $type, string $name): OperationMetadata;
+
+    /**
+     * @param string $class
+     *
+     * @return OperationMetadata[]
+     */
+    public function enumerate(string $class): array;
+}
diff --git a/src/Factory/PropertyFactory.php b/src/Factory/PropertyFactory.php
new file mode 100644
index 0000000000000000000000000000000000000000..cba213ef672cb080fb89107f66678f08a4cdd5f9
--- /dev/null
+++ b/src/Factory/PropertyFactory.php
@@ -0,0 +1,45 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+use Irstea\ApiMetadata\Model\PropertyMetadata;
+
+/**
+ * Class PropertyFactory.
+ */
+final class PropertyFactory implements PropertyFactoryInterface
+{
+    /**
+     * {@inheritdoc}
+     */
+    public function create(string $class, string $name): PropertyMetadata
+    {
+        throw new \RuntimeException('Not yet implemented');
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function enumerate(string $class): array
+    {
+        throw new \RuntimeException('Not yet implemented');
+    }
+}
diff --git a/src/Factory/PropertyFactoryInterface.php b/src/Factory/PropertyFactoryInterface.php
new file mode 100644
index 0000000000000000000000000000000000000000..e61a570704321abca85505875f12adc8d0948147
--- /dev/null
+++ b/src/Factory/PropertyFactoryInterface.php
@@ -0,0 +1,44 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+use Irstea\ApiMetadata\Model\PropertyMetadata;
+
+/**
+ * Class PropertyFactoryInterface.
+ */
+interface PropertyFactoryInterface
+{
+    /**
+     * @param string $class
+     * @param string $name
+     *
+     * @return PropertyMetadata
+     */
+    public function create(string $class, string $name): PropertyMetadata;
+
+    /**
+     * @param string $class
+     *
+     * @return PropertyMetadata[]
+     */
+    public function enumerate(string $class): array;
+}
diff --git a/src/Factory/ResourcePropertyFactory.php b/src/Factory/ResourcePropertyFactory.php
new file mode 100644
index 0000000000000000000000000000000000000000..5121ce08a3df46a54fd3f53e149d628de0a3e64c
--- /dev/null
+++ b/src/Factory/ResourcePropertyFactory.php
@@ -0,0 +1,28 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+/**
+ * Class ResourcePropertyFactory.
+ */
+final class ResourcePropertyFactory
+{
+}
diff --git a/src/Factory/ResourceTypeFactory.php b/src/Factory/ResourceTypeFactory.php
new file mode 100644
index 0000000000000000000000000000000000000000..e2724c2edf327e72dc4d5475af1168d36970278c
--- /dev/null
+++ b/src/Factory/ResourceTypeFactory.php
@@ -0,0 +1,110 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+use ApiPlatform\Core\Exception\ResourceClassNotFoundException;
+use ApiPlatform\Core\Metadata\Resource\Factory\ResourceMetadataFactoryInterface;
+use Irstea\ApiMetadata\Model\ResourceMetadata;
+use Irstea\ApiMetadata\Model\TypeMetadata;
+use Symfony\Component\PropertyInfo\Type;
+
+/**
+ * Class ResourceTypeFactory.
+ */
+final class ResourceTypeFactory implements TypeFactoryInterface
+{
+    /** @var OperationFactoryInterface */
+    private $operationFactory;
+
+    /** @var PropertyFactoryInterface */
+    private $propertyFactory;
+
+    /** @var ResourceMetadataFactoryInterface */
+    private $resourceMetadataFactory;
+    /**
+     * @var TypeFactoryInterface
+     */
+    private $decorated;
+
+    /**
+     * ResourceTypeFactory constructor.
+     *
+     * @param PropertyFactoryInterface         $propertyFactory
+     * @param OperationFactoryInterface        $operationFactory
+     * @param ResourceMetadataFactoryInterface $resourceMetadataFactory
+     * @param TypeFactoryInterface|null        $decorated
+     */
+    public function __construct(
+        PropertyFactoryInterface $propertyFactory,
+        OperationFactoryInterface $operationFactory,
+        ResourceMetadataFactoryInterface $resourceMetadataFactory,
+        TypeFactoryInterface $decorated = null
+    ) {
+        $this->operationFactory = $operationFactory;
+        $this->propertyFactory = $propertyFactory;
+
+        $this->resourceMetadataFactory = $resourceMetadataFactory;
+        $this->decorated = $decorated;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function create(?Type $type): TypeMetadata
+    {
+        $resourceClass = $type ? $type->getClassName() : null;
+        if (!$resourceClass) {
+            return  $this->decorated->create($type);
+        }
+
+        try {
+            $resource = $this->resourceMetadataFactory->create($resourceClass);
+        } catch (ResourceClassNotFoundException $ex) {
+            if ($this->decorated) {
+                return $this->decorated->create($type);
+            }
+            throw $ex;
+        }
+
+        /*        $properties = [];
+
+                foreach ($this->propertyNameCollectionFactory->create($resourceClass) as $name) {
+                    $prop = $this->getPropertyMetadata($resourceClass, $name);
+                    $properties[$prop->name] = $prop;
+                }
+
+                $operations = [];
+
+                foreach ($resource->getItemOperations() as $name => $attributes) {
+                    $operations[] = $this->getOperationMetadata($resource, $resourceClass, OperationType::ITEM, $name, $attributes);
+                }
+
+                foreach ($resource->getCollectionOperations() as $name => $attributes) {
+                    $operations[] = $this->getOperationMetadata($resource, $resourceClass, OperationType::COLLECTION, $name, $attributes);
+                }*/
+
+        return new ResourceMetadata(
+            $resource->getShortName(),
+            $this->propertyFactory->enumerate($resourceClass),
+            $this->operationFactory->enumerate($resourceClass)
+        );
+    }
+}
diff --git a/src/Factory/TypeFactory.php b/src/Factory/TypeFactory.php
new file mode 100644
index 0000000000000000000000000000000000000000..a9ddd887dd7a430c1147795be9cc1b6eeb83a15c
--- /dev/null
+++ b/src/Factory/TypeFactory.php
@@ -0,0 +1,103 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+use Irstea\ApiMetadata\Model\ArrayMetadata;
+use Irstea\ApiMetadata\Model\EmbeddedMetadata;
+use Irstea\ApiMetadata\Model\MapMetadata;
+use Irstea\ApiMetadata\Model\ScalarMetadata;
+use Irstea\ApiMetadata\Model\TypeMetadata;
+use Symfony\Component\PropertyInfo\Type;
+
+/**
+ * Class TypeFactory.
+ */
+final class TypeFactory implements TypeFactoryInterface
+{
+    /**
+     * @var TypeFactoryInterface
+     */
+    private $typeFactory;
+
+    /**
+     * TypeFactory constructor.
+     *
+     * @param TypeFactoryInterface|null $typeFactory
+     */
+    public function __construct(TypeFactoryInterface $typeFactory = null)
+    {
+        $this->typeFactory = $typeFactory ?: $this;
+    }
+
+    /**
+     * Set typeFactory.
+     *
+     * @param TypeFactoryInterface $typeFactory
+     */
+    public function setTypeFactory(TypeFactoryInterface $typeFactory): void
+    {
+        $this->typeFactory = $typeFactory;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function create(?Type $type): TypeMetadata
+    {
+        if (!$type) {
+            return ScalarMetadata::create('any');
+        }
+
+        if ($type->isCollection()) {
+            return $this->getCollectionMetadata($type->getCollectionKeyType(), $type->getCollectionValueType());
+        }
+
+        if (!$type->getClassName()) {
+            return ScalarMetadata::create($type->getBuiltinType());
+        }
+
+        $className = $type->getClassName();
+
+        return EmbeddedMetadata::create($className);
+    }
+
+    /**
+     * @param Type|null $keyType
+     * @param Type|null $valueType
+     *
+     * @return TypeMetadata
+     */
+    private function getCollectionMetadata(?Type $keyType, ?Type $valueType): TypeMetadata
+    {
+        if (!$keyType) {
+            return ScalarMetadata::create('any');
+        }
+
+        if ($keyType->getBuiltinType() === 'int') {
+            return new ArrayMetadata($this->typeFactory->create($valueType));
+        }
+
+        return new MapMetadata(
+            $this->typeFactory->create($keyType),
+            $this->typeFactory->create($valueType)
+        );
+    }
+}
diff --git a/src/Factory/TypeFactoryInterface.php b/src/Factory/TypeFactoryInterface.php
new file mode 100644
index 0000000000000000000000000000000000000000..f4e48a410e5436cce60e5c2106e4be0ff9b46b2e
--- /dev/null
+++ b/src/Factory/TypeFactoryInterface.php
@@ -0,0 +1,37 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Factory;
+
+use Irstea\ApiMetadata\Model\TypeMetadata;
+use Symfony\Component\PropertyInfo\Type;
+
+/**
+ * Class TypeFactoryInterface.
+ */
+interface TypeFactoryInterface
+{
+    /**
+     * @param Type|null $type
+     *
+     * @return TypeMetadata
+     */
+    public function create(?Type $type): TypeMetadata;
+}
diff --git a/src/Model/ArrayMetadata.php b/src/Model/ArrayMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..2e79395f50a8f6cd9fabdcbd4e8e71f266585c6e
--- /dev/null
+++ b/src/Model/ArrayMetadata.php
@@ -0,0 +1,40 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class ArrayMetadata.
+ */
+final class ArrayMetadata extends TypeMetadata
+{
+    /** @var TypeMetadata */
+    public $valueType;
+
+    /**
+     * ArrayMetadata constructor.
+     *
+     * @param TypeMetadata $valueType
+     */
+    public function __construct(TypeMetadata $valueType)
+    {
+        $this->valueType = $valueType;
+    }
+}
diff --git a/src/Model/EmbeddedMetadata.php b/src/Model/EmbeddedMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..824fa57a7b13eebf9aaa72ec73fd608a5798df7b
--- /dev/null
+++ b/src/Model/EmbeddedMetadata.php
@@ -0,0 +1,29 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class EmbeddedMetadata.
+ */
+final class EmbeddedMetadata extends TypeMetadata
+{
+    use MultitonTrait;
+}
diff --git a/src/Model/LinkMetadata.php b/src/Model/LinkMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..fb64d3c9df6c8abc3bd086ee9aa931bb67a6bdc3
--- /dev/null
+++ b/src/Model/LinkMetadata.php
@@ -0,0 +1,29 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class LinkMetadata.
+ */
+final class LinkMetadata extends TypeMetadata
+{
+    use MultitonTrait;
+}
diff --git a/src/Model/MapMetadata.php b/src/Model/MapMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..07aa876abd2b2005b0a3cf794f41112f3bac0395
--- /dev/null
+++ b/src/Model/MapMetadata.php
@@ -0,0 +1,45 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class MapMetadata.
+ */
+final class MapMetadata extends TypeMetadata
+{
+    /** @var TypeMetadata */
+    public $keyType;
+
+    /** @var TypeMetadata */
+    public $valueType;
+
+    /**
+     * MapMetadata constructor.
+     *
+     * @param TypeMetadata $keyType
+     * @param TypeMetadata $valueType
+     */
+    public function __construct(TypeMetadata $keyType, TypeMetadata $valueType)
+    {
+        $this->keyType = $keyType;
+        $this->valueType = $valueType;
+    }
+}
diff --git a/src/Model/MultitonTrait.php b/src/Model/MultitonTrait.php
new file mode 100644
index 0000000000000000000000000000000000000000..a833c730629f5b09c54055bd3c3a7a75e938b1d9
--- /dev/null
+++ b/src/Model/MultitonTrait.php
@@ -0,0 +1,56 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class MultitonTrait.
+ */
+trait MultitonTrait
+{
+    /** @var string */
+    public $name;
+
+    /**
+     * ScalarMetadata constructor.
+     *
+     * @param string $name
+     */
+    protected function __construct(string $name)
+    {
+        $this->name = $name;
+    }
+
+    /**
+     * @param string $name
+     *
+     * @return ScalarMetadata
+     */
+    public static function create(string $name): self
+    {
+        static $instance = [];
+
+        if (!isset($instance[$name])) {
+            $instance[$name] = new self($name);
+        }
+
+        return $instance[$name];
+    }
+}
diff --git a/src/Model/ObjectMetadata.php b/src/Model/ObjectMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..cb149d7bf03c84c72c9d0806fb152a0389359299
--- /dev/null
+++ b/src/Model/ObjectMetadata.php
@@ -0,0 +1,46 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+use Assert\Assertion;
+
+/**
+ * Class ObjectMetadata.
+ */
+class ObjectMetadata extends TypeMetadata
+{
+    /**
+     * @var array<string, PropertyMetadata>
+     */
+    public $properties;
+
+    /**
+     * ObjectMetadata constructor.
+     *
+     * @param PropertyMetadata[] $properties
+     */
+    public function __construct(array $properties)
+    {
+        Assertion::allIsInstanceOf($properties, PropertyMetadata::class);
+
+        $this->properties = $properties;
+    }
+}
diff --git a/src/Model/OperationMetadata.php b/src/Model/OperationMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..367d16b184f43981e583e519694920830a30dfdb
--- /dev/null
+++ b/src/Model/OperationMetadata.php
@@ -0,0 +1,65 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class OperationMetadata.
+ */
+final class OperationMetadata
+{
+    /** @var string */
+    public $type;
+
+    /** @var string */
+    public $name;
+
+    /** @var string */
+    public $path;
+
+    /** @var string */
+    public $method;
+
+    /** @var TypeMetadata|null */
+    public $input;
+
+    /** @var TypeMetadata|null */
+    public $output;
+
+    /**
+     * OperationMetadata constructor.
+     *
+     * @param string            $type
+     * @param string            $name
+     * @param string            $path
+     * @param string            $method
+     * @param TypeMetadata|null $input
+     * @param TypeMetadata|null $output
+     */
+    public function __construct(string $type, string $name, string $path, string $method, ?TypeMetadata $input, ?TypeMetadata $output)
+    {
+        $this->type = $type;
+        $this->name = $name;
+        $this->path = $path;
+        $this->method = $method;
+        $this->input = $input;
+        $this->output = $output;
+    }
+}
diff --git a/src/Model/PropertyMetadata.php b/src/Model/PropertyMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..6003f8bc99be216b92c6bd769705db81b0c75444
--- /dev/null
+++ b/src/Model/PropertyMetadata.php
@@ -0,0 +1,59 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class PropertyMetadata.
+ */
+final class PropertyMetadata
+{
+    /** @var string */
+    public $name;
+
+    /** @var TypeMetadata */
+    public $type;
+
+    /** @var bool */
+    public $required;
+
+    /** @var bool */
+    public $readonly;
+
+    /** @var bool */
+    public $identifier;
+
+    /**
+     * PropertyMetadata constructor.
+     *
+     * @param string       $name
+     * @param TypeMetadata $type
+     * @param bool         $required
+     * @param bool         $readonly
+     */
+    public function __construct(string $name, TypeMetadata $type, bool $required, bool $readonly, bool $identifier)
+    {
+        $this->name = $name;
+        $this->type = $type;
+        $this->required = $required;
+        $this->readonly = $readonly;
+        $this->identifier = $identifier;
+    }
+}
diff --git a/src/Model/ResourceMetadata.php b/src/Model/ResourceMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..87209b00b78b8fcb5e3ca3dc5fba81da6634e818
--- /dev/null
+++ b/src/Model/ResourceMetadata.php
@@ -0,0 +1,57 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+use ApiPlatform\Core\Annotation as API;
+use Assert\Assertion;
+
+/**
+ * Class ResourceMetadata.
+ *
+ * @API\ApiResource
+ */
+final class ResourceMetadata extends ObjectMetadata
+{
+    /**
+     * @API\ApiProperty(identifier=true)
+     *
+     * @var string
+     */
+    public $shortName;
+
+    /** @var array<OperationMetadata> */
+    public $operations = [];
+
+    /**
+     * ResourceMetadata constructor.
+     *
+     * @param string              $shortName
+     * @param OperationMetadata[] $operations
+     */
+    public function __construct(string $shortName, array $properties, array $operations)
+    {
+        Assertion::allIsInstanceOf($operations, OperationMetadata::class);
+
+        parent::__construct($properties);
+        $this->shortName = $shortName;
+        $this->operations = $operations;
+    }
+}
diff --git a/src/Model/ScalarMetadata.php b/src/Model/ScalarMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..fc03439a7a0c3c2da11db843a68a498f52e02dd3
--- /dev/null
+++ b/src/Model/ScalarMetadata.php
@@ -0,0 +1,29 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+/**
+ * Class ScalarMetadata.
+ */
+final class ScalarMetadata extends TypeMetadata
+{
+    use MultitonTrait;
+}
diff --git a/src/Model/TypeMetadata.php b/src/Model/TypeMetadata.php
new file mode 100644
index 0000000000000000000000000000000000000000..977757e114a30ae25263630730a04ea522492e9f
--- /dev/null
+++ b/src/Model/TypeMetadata.php
@@ -0,0 +1,42 @@
+<?php declare(strict_types=1);
+/*
+ * This file is part of "irstea/api-metadata".
+ *
+ * Copyright (C) 2019 IRSTEA
+ *
+ * This program is free software: you can redistribute it and/or modify it under
+ * the terms of the GNU Lesser General Public License as published by the Free
+ * Software Foundation, either version 3 of the License, or (at your option) any
+ * later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE. See the GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License and the GNU
+ * Lesser General Public License along with this program. If not, see
+ * <https://www.gnu.org/licenses/>.
+ */
+
+namespace Irstea\ApiMetadata\Model;
+
+use Doctrine\Common\Inflector\Inflector;
+
+/**
+ * Class TypeMetadata.
+ */
+abstract class TypeMetadata implements \JsonSerializable
+{
+    /**
+     * @return array|mixed
+     */
+    public function jsonSerialize()
+    {
+        $fqcn = get_class($this);
+        $pos = strrpos($fqcn, '\\');
+
+        return [
+                '$type' => Inflector::tableize(substr($fqcn, $pos + 1, strlen($fqcn) - $pos - 9)),
+        ] + \get_object_vars($this);
+    }
+}