9
9

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

BEAR.SundayでDoctrine2のORMを使ってみた

Last updated at Posted at 2014-07-10

リソース志向フレームワークBEAR.SundayでDoctrine\ORMを使ってみた。
DB接続設定がべた書きでテスト時にどうやって切り替えたらいいのかまだわからない上に、(主にBEARの)使い方として間違ってないのか?と微妙に不安ながら、一応動いたところまでメモ。
※思考過程ダダ漏れの、ただのメモです。

参考にしたのはこちら
https://github.com/BEARSunday/bearsunday.github.io/wiki/workshop#di%E3%81%A7%E3%83%AD%E3%82%B0%E3%82%92%E6%8F%90%E4%BE%9B
http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/tutorials/getting-started.html

アプリケーションの想定

シンプルなメモAPI。
認証等はひとまず考えない。
apiにget/post/update/deleteのリクエストを投げるとDBのデータをいい感じに取得・作成・更新・削除できればいいな。

BEAR.Sundayインストール

https://github.com/BEARSunday/bearsunday.github.io/wiki/workshop#%E3%82%A2%E3%83%97%E3%83%AA%E3%82%B1%E3%83%BC%E3%82%B7%E3%83%A7%E3%83%B3%E3%81%AE%E3%82%A4%E3%83%B3%E3%82%B9%E3%83%88%E3%83%BC%E3%83%AB
の通り。プロジェクト名は仮でMy.NoteAppとする。

composer create-project bear/skeleton My.NoteApp
cd My.NoteApp
composer install

AppResourceでの利用イメージを考える

Doctrine\ORMのEntityManagerを、BEARのAppResourceでこんな感じで利用できたらいいなーという目標を立てた。

// src/Resource/App/Note.php

namespace My\NoteApp\Resource\App;

use BEAR\Resource\ResourceObject;

class Note extends ResourceObject
{
    public function onGet($id)
    {
        $note = $this->entityManager->find('...', $id);
        $this['note'] = ['body' => $note->getBody()];

        return $this;
    }
}

Providerを書く

ワークショップのMonologProviderと同じように、Doctrine\ORM\EntityManagerを作ってくれるProviderを作ることにした。
mysql環境を作るのが面倒なので仮でsqliteで。
DBファイルの配置先はBEAR.Packageのvar以下を眺めて、仮でvar/dbに置くことに決めた。
Doctrine\ORM\EntityManagerの作り方は下記を参考に適当に コピペ 書いた。
http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/tutorials/getting-started.html#obtaining-the-entitymanager

// src/Module/Provider/DoctrineORMProvider

namespace My\NoteApp\Module\Provider;

use Doctrine\ORM\Tools\Setup;
use Doctrine\ORM\EntityManager;
use Ray\Di\ProviderInterface;
use BEAR\Sunday\Inject\AppDirInject;

class DoctrineORMProvider implements ProviderInterface
{
    use AppDirInject;

    public function get()
    {
        $config = Setup::createAnnotationMetadataConfiguration(array(__DIR__."/../Entity"), false);
        $conn = array(
          'driver' => 'pdo_sqlite',
          'path' => $this->appDir . '/var/db/db.sqlite',
        );
        $entityManager = EntityManager::create($conn, $config);

        return $entityManager;
    }
} 

追記:
@kenji_sさんがBEAR式の設定を注入する方法をブログに書いてくださっています。
BEAR.SundayでDoctrine2のORMを使ってみた(改)
http://blog.a-way-out.net/blog/2014/07/11/bear-sunday-doctrine/

ProviderをDIに登録

src/Module/AppModule.php(最初から存在している)に自作のDoctrineORMProviderを登録。

// src/Module/AppModule.php
    protected function configure()
    {
        $this->install(...); // 最初から書いてある部分

        $this->bind('Doctrine\ORM\EntityManager')->toProvider('My\NoteApp\Module\Provider\DoctrineORMProvider'); // bind,toProviderともに最初のバックスラッシュは要らなかった
    }

entityを書く

entityの置き場所は他に適切なところが思いつかなかったのでsrc配下にEntityディレクトリを作ってそこに置くことにする。(実はProviderを書いた時点で決めてあって、設定にそれ書いてた)
下記を参考にidとbodyだけのNoteエンティティを書く。
http://docs.doctrine-project.org/projects/doctrine-orm/en/latest/tutorials/getting-started.html#starting-with-the-product
普段Symfony2でDoctrine2のentity書くときとは少しアノテーションの書き方が違うので要注意。

// src/Entity/Note.php

namespace My\NoteApp\Entity;

/**
 * @Entity
 * @Table(name="note")
 */
class Note
{
    /**
     * @var int
     * @Id
     * @Column(type="integer")
     * @GeneratedValue
     */
    private $id;

    /**
     * @var string
     * @Column(type="text")
     */
    private $body;

    // getter,setterは省略
}

本当はここでDBにテーブル作成するんだけど、BEAR.Sundayでのコマンドの書き方がわからなかった(汗)のと、Doctrine\ORMのスクリプト書くのも面倒だったので、コマンドでサクッと済ませた。
ついでにテストデータも登録。

sqlite3 var/db/db.sqlite
> create table note(id INTEGER PRIMARY AUTOINCREMENT NOT NULL, body TEXT NULL);
> insert into note(body) values('test body1');
> insert into note(body) values('test body2');
> .exit

実際のAppResourceを書く

ここまでで、最初に想定した利用法でDoctrine\ORM\EntityManagerが使えるようになったはず!
早速NoteリソースにEntityManagerをセットして使ってみよう。
私が作るNoteというAppResourceは、どのメソッドでもEntityManagerを使う想定(本来の使い方とは違うかもしれない?)なので、コンストラクタインジェクションでいいだろう。

// src/Resource/App/Note.php

namespace My\NoteApp\Resource\App;

use BEAR\Resource\ResourceObject;
use Doctrine\ORM\EntityManager;
use Ray\Di\Di\Inject;

class Note extends ResourceObject
{
    /**
     * @var EntityManager
     */
    private $entityManager;

    /**
     * @param EntityManager $entityManager
     * @Inject
     */
    public function __construct(EntityManager $entityManager)
    {
        $this->entityManager = $entityManager;
    }

    public function onGet($id)
    {
        $note = $this->entityManager->find('\My\NoteApp\Entity\Note', $id);
        $this['note'] = ['body' => $note->getBody()];

        return $this;
    }
}

実際にNoteをgetしてみる。

php bootstrap/contexts/api.php get 'app://self/note?id=1'
[BODY]
note => array(
    body test body1
),

[VIEW]
{
    "note": {
        "body": "test body1"
    },
    "_links": {
        "self": {
            "href": "http://localhost/app/note/?id=1"
        }
    }
}

やったー!無事に動きました:)
(次回に続く http://qiita.com/77web@github/items/aa4d4e4faca38300eaec

9
9
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
9
9

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?