mirror of
https://github.com/retailcrm/NelmioApiDocBundle.git
synced 2025-02-08 18:49:26 +03:00
[ApiBundle] Added a controller to get a complete documentation
* Added an Extractor to get the documentation from all annotated controllers * Refactored some parts (command, event listener, ...)
This commit is contained in:
parent
72b8976006
commit
c4c7d14354
@ -9,11 +9,6 @@ use Symfony\Component\Console\Output\OutputInterface;
|
||||
|
||||
class DumpCommand extends ContainerAwareCommand
|
||||
{
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
protected $annotationClass = 'Nelmio\\ApiBundle\\Annotation\\ApiDoc';
|
||||
|
||||
/**
|
||||
* @var array
|
||||
*/
|
||||
@ -43,22 +38,13 @@ class DumpCommand extends ContainerAwareCommand
|
||||
$formatter = $this->getContainer()->get(sprintf('nelmio.api.formatter.%s_formatter', $format));
|
||||
}
|
||||
|
||||
$results = array();
|
||||
foreach ($routeCollection->all() as $route) {
|
||||
preg_match('#(.+)::([\w]+)#', $route->getDefault('_controller'), $matches);
|
||||
$method = new \ReflectionMethod($matches[1], $matches[2]);
|
||||
|
||||
if ($annot = $this->getContainer()->get('annotation_reader')->getMethodAnnotation($method, $this->annotationClass)) {
|
||||
$results[] = $formatter->format($annot, $route);
|
||||
}
|
||||
}
|
||||
$extractedDoc = $this->getContainer()->get('nelmio.api.extractor.api_doc_extractor')->all();
|
||||
$result = $formatter->format($extractedDoc);
|
||||
|
||||
if ('json' === $format) {
|
||||
$output->writeln(json_encode($results));
|
||||
$output->writeln(json_encode($result));
|
||||
} else {
|
||||
foreach ($results as $result) {
|
||||
$output->writeln($result);
|
||||
}
|
||||
$output->writeln($result);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
17
Controller/ApiDocController.php
Normal file
17
Controller/ApiDocController.php
Normal file
@ -0,0 +1,17 @@
|
||||
<?php
|
||||
|
||||
namespace Nelmio\ApiBundle\Controller;
|
||||
|
||||
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
|
||||
use Symfony\Component\HttpFoundation\Response;
|
||||
|
||||
class ApiDocController extends Controller
|
||||
{
|
||||
public function indexAction()
|
||||
{
|
||||
$extractedDoc = $this->get('nelmio.api.extractor.api_doc_extractor')->all();
|
||||
$htmlContent = $this->get('nelmio.api.formatter.html_formatter')->format($extractedDoc);
|
||||
|
||||
return new Response($htmlContent);
|
||||
}
|
||||
}
|
@ -15,6 +15,7 @@ class NelmioApiExtension extends Extension
|
||||
public function load(array $configs, ContainerBuilder $container)
|
||||
{
|
||||
$loader = new XmlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config'));
|
||||
$loader->load('formatters.xml');
|
||||
$loader->load('request_listener.xml');
|
||||
$loader->load('services.xml');
|
||||
}
|
||||
|
@ -2,28 +2,22 @@
|
||||
|
||||
namespace Nelmio\ApiBundle\EventListener;
|
||||
|
||||
use Doctrine\Common\Annotations\Reader;
|
||||
use Nelmio\ApiBundle\Extractor\ApiDocExtractor;
|
||||
use Nelmio\ApiBundle\Formatter\FormatterInterface;
|
||||
use Symfony\Component\HttpFoundation\JsonResponse;
|
||||
use Symfony\Component\HttpFoundation\Response;
|
||||
use Symfony\Component\HttpFoundation\Request;
|
||||
use Symfony\Component\HttpKernel\HttpKernelInterface;
|
||||
use Symfony\Component\HttpKernel\Event\GetResponseEvent;
|
||||
use Symfony\Component\Routing\RouterInterface;
|
||||
|
||||
class RequestListener
|
||||
{
|
||||
protected $annotationClass = 'Nelmio\\ApiBundle\\Annotation\\ApiDoc';
|
||||
|
||||
protected $reader;
|
||||
|
||||
protected $router;
|
||||
protected $extractor;
|
||||
|
||||
protected $formatter;
|
||||
|
||||
public function __construct(Reader $reader, RouterInterface $router, FormatterInterface $formatter)
|
||||
public function __construct(ApiDocExtractor $extractor, FormatterInterface $formatter)
|
||||
{
|
||||
$this->reader = $reader;
|
||||
$this->router = $router;
|
||||
$this->extractor = $extractor;
|
||||
$this->formatter = $formatter;
|
||||
}
|
||||
|
||||
@ -42,16 +36,15 @@ class RequestListener
|
||||
return;
|
||||
}
|
||||
|
||||
preg_match('#(.+)::([\w]+)#', $request->get('_controller'), $matches);
|
||||
$method = new \ReflectionMethod($matches[1], $matches[2]);
|
||||
$route = $request->get('_route');
|
||||
$controller = $request->get('_controller');
|
||||
$route = $request->get('_route');
|
||||
|
||||
if ($annot = $this->reader->getMethodAnnotation($method, $this->annotationClass)) {
|
||||
if ($route = $this->router->getRouteCollection()->get($route)) {
|
||||
$result = $this->formatter->format($annot, $route);
|
||||
if (null !== $array = $this->extractor->get($controller, $route)) {
|
||||
$result = $this->formatter->formatOne($array['annotation'], $array['route']);
|
||||
|
||||
$event->setResponse(new JsonResponse($result));
|
||||
}
|
||||
$event->setResponse(new Response($result, 200, array(
|
||||
'Content-Type' => 'text/html'
|
||||
)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
56
Extractor/ApiDocExtractor.php
Normal file
56
Extractor/ApiDocExtractor.php
Normal file
@ -0,0 +1,56 @@
|
||||
<?php
|
||||
|
||||
namespace Nelmio\ApiBundle\Extractor;
|
||||
|
||||
use Doctrine\Common\Annotations\Reader;
|
||||
use Symfony\Component\Routing\RouterInterface;
|
||||
|
||||
class ApiDocExtractor
|
||||
{
|
||||
const ANNOTATION_CLASS = 'Nelmio\\ApiBundle\\Annotation\\ApiDoc';
|
||||
|
||||
/**
|
||||
* @var
|
||||
*/
|
||||
private $router;
|
||||
|
||||
/**
|
||||
* @var \Doctrine\Common\Annotations\Reader
|
||||
*/
|
||||
private $reader;
|
||||
|
||||
public function __construct(RouterInterface $router, Reader $reader)
|
||||
{
|
||||
$this->router = $router;
|
||||
$this->reader = $reader;
|
||||
}
|
||||
|
||||
public function all()
|
||||
{
|
||||
$array = array();
|
||||
foreach ($this->router->getRouteCollection()->all() as $route) {
|
||||
preg_match('#(.+)::([\w]+)#', $route->getDefault('_controller'), $matches);
|
||||
$method = new \ReflectionMethod($matches[1], $matches[2]);
|
||||
|
||||
if ($annot = $this->reader->getMethodAnnotation($method, self::ANNOTATION_CLASS)) {
|
||||
$array[] = array('annotation' => $annot, 'route' => $route);
|
||||
}
|
||||
}
|
||||
|
||||
return $array;
|
||||
}
|
||||
|
||||
public function get($controller, $route)
|
||||
{
|
||||
preg_match('#(.+)::([\w]+)#', $controller, $matches);
|
||||
$method = new \ReflectionMethod($matches[1], $matches[2]);
|
||||
|
||||
if ($annot = $this->reader->getMethodAnnotation($method, self::ANNOTATION_CLASS)) {
|
||||
if ($route = $this->router->getRouteCollection()->get($route)) {
|
||||
return array('annotation' => $annot, 'route' => $route);
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
@ -41,8 +41,7 @@ class FormTypeParser
|
||||
}
|
||||
}
|
||||
|
||||
$parameters[] = array(
|
||||
'name' => $name,
|
||||
$parameters[$name] = array(
|
||||
'type' => $bestType,
|
||||
'is_required' => $b->getRequired()
|
||||
);
|
||||
|
@ -9,9 +9,8 @@
|
||||
|
||||
<services>
|
||||
<service id="nelmio.api.event_listener.request" class="%nelmio.api.event_listener.request.class%">
|
||||
<argument type="service" id="annotation_reader" />
|
||||
<argument type="service" id="router" />
|
||||
<argument type="service" id="nelmio.api.formatter.simple_formatter" />
|
||||
<argument type="service" id="nelmio.api.extractor.api_doc_extractor" />
|
||||
<argument type="service" id="nelmio.api.formatter.html_formatter" />
|
||||
<tag name="kernel.event_listener" event="kernel.request" method="onKernelRequest" />
|
||||
</service>
|
||||
</services>
|
||||
|
5
Resources/config/routing.yml
Normal file
5
Resources/config/routing.yml
Normal file
@ -0,0 +1,5 @@
|
||||
nelmio_api_api_doc_index:
|
||||
pattern: /api/doc
|
||||
defaults: { _controller: NelmioApiBundle:ApiDoc:index }
|
||||
requirements:
|
||||
_method: GET
|
@ -4,23 +4,14 @@
|
||||
xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd">
|
||||
|
||||
<parameters>
|
||||
<parameter key="nelmio.api.parser.form_type_parser.class">Nelmio\ApiBundle\Parser\FormTypeParser</parameter>
|
||||
<parameter key="nelmio.api.formatter.abstract_formatter.class">Nelmio\ApiBundle\Formatter\AbstractFormatter</parameter>
|
||||
<parameter key="nelmio.api.formatter.markdown_formatter.class">Nelmio\ApiBundle\Formatter\MarkdownFormatter</parameter>
|
||||
<parameter key="nelmio.api.formatter.simple_formatter.class">Nelmio\ApiBundle\Formatter\SimpleFormatter</parameter>
|
||||
<parameter key="nelmio.api.extractor.api_doc_extractor.class">Nelmio\ApiBundle\Extractor\ApiDocExtractor</parameter>
|
||||
</parameters>
|
||||
|
||||
<services>
|
||||
<service id="nelmio.api.parser.form_type_parser" class="%nelmio.api.parser.form_type_parser.class%">
|
||||
<argument type="service" id="form.factory" />
|
||||
<service id="nelmio.api.extractor.api_doc_extractor" class="%nelmio.api.extractor.api_doc_extractor.class%">
|
||||
<argument type="service" id="router" />
|
||||
<argument type="service" id="annotation_reader" />
|
||||
</service>
|
||||
<service id="nelmio.api.formatter.abstract_formatter" class="%nelmio.api.formatter.abstract_formatter.class%">
|
||||
<argument type="service" id="nelmio.api.parser.form_type_parser" />
|
||||
</service>
|
||||
<service id="nelmio.api.formatter.markdown_formatter" class="%nelmio.api.formatter.markdown_formatter.class%"
|
||||
parent="nelmio.api.formatter.abstract_formatter" />
|
||||
<service id="nelmio.api.formatter.simple_formatter" class="%nelmio.api.formatter.simple_formatter.class%"
|
||||
parent="nelmio.api.formatter.abstract_formatter" />
|
||||
</services>
|
||||
|
||||
</container>
|
||||
|
Loading…
x
Reference in New Issue
Block a user