fsc/rest-bundle

此软件包的最新版本(dev-master)没有可用的许可信息。

dev-master 2012-10-11 11:05 UTC

This package is auto-updated.

Last update: 2024-09-12 03:26:34 UTC


README

Build Status

此捆绑包将根据您所做的配置生成基于REST HATEOAS的API。目前,它只能生成只读API,由doctrine ORM支持。表示形式针对XML格式进行了优化,但也适用于JSON。

如果您在资源之间创建关系,捆绑包将自动在它们之间创建链接。

设计显然采用了许多捷径,并不是OOP设计的典范...但它有效。但是,由于需要对每个资源扩展执行所有操作的功能类,因此很容易覆盖行为...

此捆绑包是从一个应用程序中提取出来的,需要一些爱来使其可用。(例如composer,使测试工作等...)

许可证

MIT: Resources/meta/LICENSE

TODO

  • 创建一个“sanbox” symfony2应用程序来演示如何完全使用此捆绑包

安装

编辑您的composer.json如下

{
    "require": {
        ...
        "jms/serializer-bundle": "dev-xml-attribute-map as 0.9.0",
        "fsc/rest-bundle": "*"
        ...
    },
    "repositories": [
        {
            "type": "vcs",
            "url": "https://github.com/adrienbrault/JMSSerializerBundle"
        }
    ]
}

更新您的依赖项:composer update

将捆绑包添加到您的AppKernel

// in AppKernel::registerBundles()
$bundles = array(
    // ...
    new FSC\RestBundle\FSCRestBundle(),
    new JMS\SerializerBundle\JMSSerializerBundle(),
    new FOS\FOSRestBundle(),
    // ...
);

注意,此捆绑包依赖于JMSSerializerBundle的分支,因为此PR尚未合并:schmittjoh/JMSSerializerBundle#164

示例

对于控制器返回的示例,请参阅:https://gist.github.com/3800069

您需要定义带有fsc_rest.resource标记的服务。

services:
    fsc.core.spot.resource.spots:
        class: FSC\Core\SpotBundle\REST\SpotsResource
        parent: fsc.rest.resource.abstract_doctrine
        tags:
          - { name: fsc_rest.resource }
<?php

namespace FSC\Core\TeamBundle\REST;

use FSC\Core\MainBundle\REST\AbstractSocialEntityResource;
use FSC\Common\RestBundle\Form\Model\Collection;
use FSC\Core\TeamBundle\Repository\FormationRepository;
use FSC\Core\SpotBundle\Repository\SpotRepository;

class TeamsResource extends AbstractSocialEntityResource
{
    protected function configure()
    {
        return array_merge(parent::configure(), array(
            'prefix' => '/teams',
            'entity_class' => 'FSC\Core\TeamBundle\Entity\Team',
        ));
    }

    // Configure root collection ... /teams
    protected function configureCollection()
    {
        return array_merge(parent::configureCollection(), array(
            'xml_root_name' => 'teams',
            'representation_class' => 'FSC\Core\TeamBundle\Model\Representation\Teams',
            'pager_fetch_join_collection' => false,
        ));
    }

    // Configure how each entity representation looks like
    // ie:
    //
    // <team id="">
    //   <name></name>
    //   ...
    // </team>
    protected function configureEntity()
    {
        return array_merge(parent::configureEntity(), array(
            'expanded_collections' => array('formations'),
            'xml_root_name' => 'team',
            'normalize_attributes' => array(
                'id' => 'id',
            ),
            'normalize_elements' => array(
                'name' => 'name',
                'clubName' => 'clubName',
                'category' => 'category',
                'division' => 'division',
                'foundedAt' => 'foundedAt',
            ),
        ));
    }

    // Configure each entity collection, ie: a teams has formations, so you'll have a collection
    // at /teams/{id}/formations
    protected function configureEntityCollections()
    {
        return array_merge_recursive(parent::configureEntityCollections(), array(
            'formations' => array(
                'representation_class' => 'FSC\Core\TeamBundle\Model\Representation\Formations',

                // Which resources should be asked to normalize the collection elements ...
                'resources' => array(
                    'FSC\Core\TeamBundle\Entity\Formation' => 'fsc.core.team.resource.formations',
                ),
                'create_qb' => function ($em, $repository, $entity) {
                    $formationRepository = $em->getRepository('FSCCoreTeamBundle:Formation'); /** @var $formationRepository FormationRepository */

                    return $formationRepository->createSelectByTeamQB($entity);
                },
            ),
            'official-spots' => array(
                'representation_class' => 'FSC\Core\SpotBundle\Model\Representation\Spots',
                'resources' => array(
                    'FSC\Core\SpotBundle\Entity\Spot' => 'fsc.core.spot.resource.spots',
                ),
                'create_qb' => function ($em, $repository, $team) {
                    $spotRepository = $em->getRepository('FSCCoreSpotBundle:Spot'); /** @var $spotRepository SpotRepository */

                    return $spotRepository->createSelectNonDeletedByOfficialTeamQB($team);
                },
            ),
        ));
    }
}
<?php

namespace FSC\Core\SpotBundle\REST;

use FSC\Core\MainBundle\REST\AbstractSocialEntityResource;
use FSC\Common\RestBundle\Form\Model\Collection;
use FSC\Core\TeamBundle\Repository\TeamRepository;

class SpotsResource extends AbstractSocialEntityResource
{
    protected function configure()
    {
        return array_merge(parent::configure(), array(
            'prefix' => '/spots',
            'entity_class' => 'FSC\Core\SpotBundle\Entity\Spot',
        ));
    }

    protected function configureCollection()
    {
        return array_merge(parent::configureCollection(), array(
            'xml_root_name' => 'spots',
            'representation_class' => 'FSC\Core\SpotBundle\Model\Representation\Spots',
            'pager_fetch_join_collection' => false,
        ));
    }

    protected function configureEntity()
    {
        return array_merge(parent::configureEntity(), array(
            'xml_root_name' => 'spot',
            'normalize_attributes' => array(
                'id' => 'id',
            ),
            'normalize_elements' => array(
                'name' => 'name',
                'description' => 'description',
                'subCategory' => 'subCategory',
                'category' => 'category',
                'surface' => 'surface',
                'previousNames' => 'previousNames',
                'capacity' => 'capacity',
                'facts' => 'facts',
                'opened' => 'opened',
                'architect' => 'architect',
            ),
        ));
    }

    protected function configureEntityCollections()
    {
        return array_merge_recursive(parent::configureEntityCollections(), array(
            'official-teams' => array(
                'representation_class' => 'FSC\Core\TeamBundle\Model\Representation\Teams',
                'resources' => array(
                    'FSC\Core\TeamBundle\Entity\Team' => 'fsc.core.team.resource.teams',
                ),
                'create_qb' => function ($em, $repository, $spot) {
                    $teamRepository = $em->getRepository('FSCCoreTeamBundle:Team'); /** @var $teamRepository TeamRepository */

                    return $teamRepository->createSelectByOfficialSpotQB($spot);
                },
            ),
        ));
    }

    protected function configureEntityRelations()
    {
        return array_merge(parent::configureEntityRelations(), array(
            'creator' => array(
                'get_relation' => function ($em, $repository, $spot) {
                    return $spot->getSpotCreator();
                },
                'resources' => array(
                    'FSC\Core\UserBundle\Entity\User' => 'fsc.core.user.resource.users',
                ),
            ),
        ));
    }
}

更多详细信息

当您请求资源时,此捆绑包将...

Entity --(normalize)--> Representation --(serialize)--> XML/JSON
             ||                              ||
        RESTResources                   JMSSerializer