Upgrade to Pro — share decks privately, control downloads, hide ads and more …

クリーンアーキテクチャの考え方にもとづく Laravel との付き合い方 #phpcondo

Shohei Okada
September 20, 2019

クリーンアーキテクチャの考え方にもとづく Laravel との付き合い方 #phpcondo

最近、設計に対する関心高まりを感じています。
その一方で「名前は聞いたことあるけど、敷居が高そう......」「本は読んだけど実際に実装するイメージがつかない......」と感じている方もいらっしゃるのではないでしょうか?
本セッションでは設計に関するテーマとして「クリーンアーキテクチャ」を扱い、セッション前半ではクリーンアーキテクチャのコアとなる考え方を説明します。
後半では「フレームワーク非依存」を謳うクリーンアーキテクチャの考え方を、Laravelのプロジェクトに適用する方法を提案します。
※本セッションは、PHPカンファレンス福岡2019でお話した「Laravelでやってみるクリーンアーキテクチャ」(https://www.slideshare.net/ShoheiOkada/laravel-phpconfuk-152500600)を再編した内容になります

2019/09/21 開催の PHP カンファレンス北海道2019 (https://phpcon.hokkaido.jp/) の発表資料です。

Shohei Okada

September 20, 2019
Tweet

More Decks by Shohei Okada

Other Decks in Programming

Transcript

  1. ΫϦʔϯΞʔΩςΫνϟͷ
    ߟ͑ํʹ΋ͱͮ͘
    Laravel ͱͷ෇͖߹͍͔ͨ
    PHP Conference Hokkaido 2019
    @okashoi WILLGATE, Inc.

    View Slide

  2. ͸͡Ίʹ
    • εϥΠυ͸ެ։ࡁΈͰ͢
    • ࣸਅ౳΋׻ܴͰ͢ 🙆
    • ײ૝ɾϑΟʔυόοΫ౳͓଴͍ͪͯ͠·͢ʂ
    • ϋογϡλά #phpcondo
    2

    View Slide

  3. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    3

    View Slide

  4. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    4

    View Slide

  5. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    5

    View Slide

  6. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    6

    View Slide

  7. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    7

    View Slide

  8. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    8

    View Slide

  9. ͜ͷτʔΫͷΊ͟͢ͱ͜Ζ🏁
    ҎԼͷ͜ͱΛ஌ͬͯ΋Β͏
    • ΫϦʔϯΞʔΩςΫνϟͷίΞͱͳΔߟ͑ํ
    • Laravel ͱͷڞଘͤ͞ํ
    ͦͯ͠ɺগ͠Ͱ΋ࠓޙͷ։ൃʹ׆͔ͯ͠΋Β͏
    9

    View Slide

  10. ͜ͷτʔΫͰ࿩͞ͳ͍͜ͱ🙅
    • ʰΫϦʔϯΞʔΩςΫνϟʱʹग़ͯ͘Δ֓೦
    ͷৄࡉͳղઆ
    • Laravel ͷػೳͷղઆ
    • ۩ମతͳ࣮૷Ϩϕϧͷ͓࿩
    10

    View Slide

  11. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    11

    View Slide

  12. ݪయʢ2012೥ʣ
    ”The Clean Architecture - The Clean Code Blog”,
    https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html
    12

    View Slide

  13. ॻ੶
    13
    2017 ೥ॳ൛ൃߦ 2018 ೥ॳ൛ൃߦ

    View Slide

  14. ΫϦʔϯΞʔΩςΫνϟͷਤ
    ग़యɿ”The Clean Architecture - The Clean Code Blog”,
    https://blog.cleancoder.com/uncle-bob/2012/08/13/the-clean-architecture.html
    14

    View Slide

  15. ΫϦʔϯΞʔΩςΫνϟͷਤ
    • ΫϦʔϯΞʔΩςΫνϟʹ͍ͭͯௐ΂Δͱ

    ·ͣ໨ʹ͢Δਤ
    • ຊτʔΫͰ͸֤૚ͷৄࡉͳղઆ͸͠ͳ͍
    • ͜ͷਤʹ஧࣮ʹ࣮૷͑͢͞Ε͹Α͍ɺͱ͍͏
    Θ͚Ͱ͸ͳ͍
    15

    View Slide

  16. ԿΛ໨తͱ͍ͯ͠Δ͔ʁ
    • ಠཱ։ൃՄೳ
    • ಠཱσϓϩΠՄೳʢ˞ʣ
    • ςετՄೳ
    ※ PHP ։ൃʹ͓͍ͯ͸Πϝʔδ͠ʹ͍͔͘΋
    16

    View Slide

  17. “ιϑτ΢ΣΞΞʔΩςΫνϟͷ໨త͸ɺ

    ٻΊΒΕΔγεςϜΛߏஙɾอक͢ΔͨΊʹ
    ඞཁͳਓࡐΛ࠷খݶʹ཈͑Δ͜ͱͰ͋Δɻ”
    17

    View Slide

  18. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    18

    View Slide

  19. ίΞͱͳΔߟ͑ํ
    ʮॏཁͳ΋ͷʯΛʮࠣࡉͳ΋ͷʯʹґଘͤ͞ͳ͍
    19

    View Slide

  20. ॏཁͳ΋ͷʁ
    20
    σʔλϕʔε
    ϑϨʔϜϫʔΫ
    ςετ
    6* 8FC
    03.

    View Slide

  21. ॏཁͳ΋ͷʁ
    21
    σʔλϕʔε
    ϑϨʔϜϫʔΫ
    ςετ
    6* 8FC
    03.
    🙅
    ⾠͋͘·ͰΫϦʔϯΞʔΩςΫνϟͷจ຺ͷ࿩

    View Slide

  22. ॏཁͳ΋ͷʁ
    ॏཁͳ΋ͷ͸ʮϏδωεϧʔϧʯ
    22

    View Slide

  23. ΫϦʔϯΞʔΩςΫνϟͷਤ
    23

    View Slide

  24. ॏཁͳ΋ͷʁ
    ॏཁͳ΋ͷ͸ʮϏδωεϧʔϧʯ
    • ΤϯςΟςΟʢEnterprise Business Rulesʣ
    • ࠷ॏཁϏδωεϧʔϧ
    • ΞϓϦέʔγϣϯ͕ଘࡏ͠ͳͯ͘΋ݱ࣮ੈքʹଘࡏ͢Δ
    • ϢʔεέʔεʢApplication Business Rulesʣ
    • ΞϓϦέʔγϣϯݻ༗ͷϏδωεϧʔϧ
    24

    View Slide

  25. ࢀߟɿ
    https://little-hands.hatenablog.com/entry/2019/07/26/
    domain-knowledge 25

    View Slide

  26. ίΞͱͳΔߟ͑ํ
    ʮॏཁͳ΋ͷʯΛʮࠣࡉͳ΋ͷʯʹґଘͤ͞ͳ͍
    26

    View Slide

  27. ίΞͱͳΔߟ͑ํ
    ʮॏཁͳ΋ͷʯΛʮࠣࡉͳ΋ͷʯʹґଘͤ͞ͳ͍
    27
    ɹɹ ↑
    Ͳ͏΍ͬͯʁ

    View Slide

  28. ґଘؔ܎ٯస
    28

    View Slide

  29. యܕతͳґଘؔ܎ͷίʔυ
    package foo;
    import bar;
    class Foo {
    bar.Bar x;
    function doFoo() {
    x.process();
    }
    }
    29
    package bar;
    class Bar {
    function process() {
    // do something...
    }
    }

    View Slide

  30. యܕతͳґଘؔ܎ͷίʔυ
    package foo;
    import bar;
    class Foo {
    bar.Bar x;
    function doFoo() {
    x.process();
    }
    }
    30
    package bar;
    class Bar {
    function process() {
    // do something...
    }
    }
    foo ͔Β bar ͷॲཧΛݺͼग़͢ = ॲཧͷํ޲ foo → bar

    View Slide

  31. యܕతͳґଘؔ܎ͷίʔυ
    package foo;
    import bar;
    class Foo {
    bar.Bar x;
    function doFoo() {
    x.process();
    }
    }
    31
    package bar;
    class Bar {
    function process() {
    // do something...
    }
    }
    foo ͕ bar ͷ͜ͱΛ஌͍ͬͯΔ = ґଘͷํ޲ foo → bar

    View Slide

  32. యܕతͳґଘؔ܎ͷίʔυ
    package foo;
    import bar;
    class Foo {
    bar.Bar x;
    function doFoo() {
    x.process();
    }
    }
    32
    package bar;
    class Bar {
    function process() {
    // do something...
    }
    }
    ॲཧͷํ޲ foo → bar
    ґଘͷํ޲ foo → bar

    View Slide

  33. ґଘؔ܎ٯసͨ͠ίʔυ
    package foo;
    class Foo {
    Buz x;
    function doFoo() {
    x.process();
    }
    }
    interface Buz {
    function process();
    }
    33
    package bar;
    import foo;
    class Bar implements foo.Buz {
    function process() {
    // do something...
    }
    }

    View Slide

  34. ґଘؔ܎ٯసͨ͠ίʔυ
    package foo;
    class Foo {
    Buz x;
    function doFoo() {
    x.process();
    }
    }
    interface Buz {
    function process();
    }
    34
    package bar;
    import foo;
    class Bar implements foo.Buz {
    function process() {
    // do something...
    }
    }

    View Slide

  35. ґଘؔ܎ٯసͨ͠ίʔυ
    package foo;
    class Foo {
    Buz x;
    function doFoo() {
    x.process();
    }
    }
    interface Buz {
    function process();
    }
    35
    package bar;
    import foo;
    class Bar implements foo.Buz {
    function process() {
    // do something...
    }
    }
    foo ͔Β bar ͷॲཧΛݺͼग़͢ = ॲཧͷํ޲ foo → bar

    View Slide

  36. ґଘؔ܎ٯసͨ͠ίʔυ
    package foo;
    class Foo {
    Buz x;
    function doFoo() {
    x.process();
    }
    }
    interface Buz {
    function process();
    }
    36
    package bar;
    import foo;
    class Bar implements foo.Buz {
    function process() {
    // do something...
    }
    }
    bar ͕ foo ͷ͜ͱΛ஌͍ͬͯΔ = ґଘͷํ޲ foo ← bar

    View Slide

  37. ґଘؔ܎ٯసͨ͠ίʔυ
    package foo;
    class Foo {
    Buz x;
    function doFoo() {
    x.process();
    }
    }
    interface Buz {
    function process();
    }
    37
    package bar;
    import foo;
    class Bar implements foo.Buz {
    function process() {
    // do something...
    }
    }
    ॲཧͷํ޲ foo → bar
    ґଘͷํ޲ foo ← bar

    View Slide

  38. = ґଘͷํ޲͸ࣗ༝ʹܾΊΒΕΔ
    ʢॲཧͷํ޲ʹӨڹ͠ͳ͍ʣ
    38

    View Slide

  39. “ιϑτ΢ΣΞΞʔΩςΫτ͸ɺ

    γεςϜʹ͋Δ͢΂ͯͷιʔείʔυͷ

    ґଘؔ܎ͷํ޲Λઈରతʹ੍ޚͰ͖Δ”
    39

    View Slide

  40. Կ͕خ͍͠ͷ͔ʁ
    • Ұൠ࿦ͱͯ͠ɺԿ͔Λมߋͨ͠ͱ͖

    ͦΕʹґଘ͍ͯ͠Δ΋ͷશͯʹӨڹ͕ٴͿ
    ➡ มߋ͕ى͜Γʹ͍͘΋ͷʹґଘ͢ΔΑ͏ʹ

    ઃܭ͢Δ͜ͱͰӨڹΛখ͘͞ཹΊΒΕΔ
    40

    View Slide

  41. ίΞͱͳΔߟ͑ํ
    ʮॏཁͳ΋ͷʯΛʮࠣࡉͳ΋ͷʯʹґଘͤ͞ͳ͍
    41
    σʔλϕʔεɾ
    UIɾϑϨʔϜϫʔΫͳͲ
    ༰қʹมߋͰ͖Δ
    Ϗδωεϧʔϧ
    มߋ͕ى͜Γʹ͍͘

    View Slide

  42. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    42

    View Slide

  43. Laravel Λ࢖͏ಈػ
    • DIʢґଘੑͷ஫ೖʣͷͨΊͷڧྗͳ͘͠Έ
    • ศརͳίϯϙʔωϯτ܊ʢEloquent ͳͲʣ
    43

    View Slide

  44. Laravel ͱͷ෇͖߹͍͔ͨ
    • খ͍͞ύοέʔδ୯Ґʹ෼ׂͯ͠։ൃ

    Service Provider ͰͦΕΒΛ౷߹͢Δ
    • Laravel ͷػೳΛ࢖͏৔߹͸

    ϏδωεϧʔϧΑΓ΋֎ଆͷ૚Ͱ࢖͏
    44

    View Slide

  45. Laravel ͱͷ෇͖߹͍͔ͨ
    • খ͍͞ύοέʔδ୯Ґʹ෼ׂͯ͠։ൃ

    Service Provider ͰͦΕΒΛ౷߹͢Δ
    • Laravel ͷػೳΛ࢖͏৔߹͸

    ϏδωεϧʔϧΑΓ΋֎ଆͷ૚Ͱ࢖͏
    45

    View Slide

  46. ࢀߟεϥΠυ@Laravel JP Conference 2019
    https://speakerdeck.com/mikakane/laravel-package-
    development 46

    View Slide

  47. σΟϨΫτϦߏ੒
    47
    packages ҎԼʹ

    ύοέʔδΛ࡞ͬͯΏ͘

    View Slide

  48. Service Provider
    • ΠϯλʔϑΣʔεͱ࣮૷ͷΫϥεΛ݁ͼ͚ͭΔ
    • Πϝʔδɿن֨ʹଇͬͯ࡞ΒΕͨ෦඼Λ૊Έཱͯͯ

    Ұͭͷ੡඼Λ࡞Δ
    • ن֨ = ΠϯλʔϑΣʔε
    • ੡඼ = ΞϓϦέʔγϣϯ
    48

    View Slide

  49. Service Provider
    ΠϯλʔϑΣʔεͱ۩৅ΫϥεΛ݁ͼ͚ͭΔ
    49
    class AppServiceProvider extends ServiceProvider
    {
    /**
    * Register any application services.
    *
    * @return void
    */
    public function register()
    {
    $this->app->bind(IdProvider::class, AutoIncrementTaskIdProvider::class);
    $this->app->bind(TaskRepositoryInterface::class, TaskRepository::class);
    }

    View Slide

  50. Service Container
    ΠϯλʔϑΣʔεͰܕએݴΛ͢Δ͕

    ࣮ࡍʹ͸۩৅ΫϥεͷΠϯελϯε͕౉͞ΕΔ
    50
    /**
    * Interactor constructor.
    * @param IdProvider $idProvider
    * @param TaskRepository $taskRepository
    * @param NormalOutputBoundary $normalOutputBoundary
    */
    public function __construct(IdProvider $idProvider, TaskRepository $taskRepository, …
    {
    $this->idProvider = $idProvider;
    $this->taskRepository = $taskRepository;
    $this->normalOutputBoundary = $normalOutputBoundary;
    }

    View Slide

  51. Laravel ͱͷ෇͖߹͍͔ͨ
    • খ͍͞ύοέʔδ୯Ґʹ෼ׂͯ͠։ൃ

    Service Provider ͰͦΕΒΛ౷߹͢Δ
    • Laravel ͷػೳΛ࢖͏৔߹͸

    ϏδωεϧʔϧΑΓ΋֎ଆͷ૚Ͱ࢖͏
    51

    View Slide

  52. Clean Architecture ΋͏ͻͱͭͷਤ
    ग़యɿʰClean Architecture ୡਓʹֶͿιϑτ΢ΣΞͷߏ଄ͱઃܭʱ
    ʢKindle ൛ɺ ҐஔNo. 3228/6016ʣ 52

    View Slide

  53. ΤϯςΟςΟ
    53

    View Slide

  54. ΤϯςΟςΟ
    54

    View Slide

  55. ࠷ॳʹΤϯςΟςΟΛநग़
    • ΞϓϦέʔγϣϯʹґΒͳ͍ϧʔϧΛݟग़͢
    • ػೳҰཡͰ͸ͳ͍
    ʮλεΫΛ࡞੒Ͱ͖ΔʯʮλεΫ໊ΛมߋͰ͖Δʯ
    ʮλεΫ͸ඞͣλεΫIDͱλεΫ໊Λ࣋ͭʯ

    ɹʮணख೔ʹաڈͷ೔෇ΛೳಈతʹઃఆͰ͖ͳ͍ʯ
    55

    View Slide

  56. ΤϯςΟςΟͷ࣮૷
    • நग़ͨ͠ϏδωεϧʔϧΛ࣮૷Ͱදݱ͢Δ
    • ϑϨʔϜϫʔΫ΍σʔλϕʔε౳ʹґଘͤ͞ͳ͍
    • POPOʢPlain Old PHP ObjectʣͰॻ͘
    ➡ ґଘ͢Δ΋ͷ͕ແ͍ͷͰಠཱͯ͠։ൃՄೳ
    56

    View Slide

  57. ϑϨʔϜϫʔΫʹґଘͤ͞ͳ͍
    PHP ૊ΈࠐΈͷΫϥεఔ౓ʹͱͲΊΔ
    57
    namespace MyApp\Entities\Task;
    use DatetimeImmutable;
    /**
    * Class Inbox
    * @package MyApp\Entities\Task
    */
    final class Inbox extends Task
    {
    /**
    * @var EstimatedTime|null
    */
    private $estimatedTime;

    View Slide

  58. Ϣʔεέʔε
    58

    View Slide

  59. Ϣʔεέʔε
    59

    View Slide

  60. Ϣʔεέʔεͷ࣮૷
    • ΞϓϦέʔγϣϯݻ༗ͷϏδωεϧʔϧ
    • ΞϓϦέʔγϣϯͷʮػೳʯͱ΋

    ݴ͍͔͑ΒΕΔ
    • ೖग़ྗͷσʔλ͸ഔମ΍σʔλϕʔεʹ

    ґଘ͠ͳ͍ܗʹ͢Δ
    60

    View Slide

  61. σʔλϕʔε౳ʹґଘͤ͞ͳ͍
    ग़ྗ΍σʔλૢ࡞ͷΠϯλʔϑΣʔεΛఆٛ
    61
    namespace MyApp\Components\CreateInbox\UseCase;
    use MyApp\Entities\Task\{Task, Id};
    /**
    * Interface TaskRepository
    * @package MyApp\Components\CreateInbox\UseCase
    */
    interface TaskRepository
    {
    /**
    * 与えられたタスクを永続化する
    *
    * @param Task $task
    */
    public function save(Task $task): void;

    View Slide

  62. σʔλϕʔε
    62

    View Slide

  63. WebʗUI
    63

    View Slide

  64. σʔλϕʔεʗWebʗUI
    ಉ৺ԁͷ֎ଆ
    64

    View Slide

  65. σʔλϕʔεʗWebʗUI
    • ϢʔεέʔεͰఆٛͨ͠ΠϯλʔϑΣʔεΛ࣮૷
    • ͜ͷ͋ͨΓ͸ϑϨʔϜϫʔΫʹґଘͤͯ͞΋🙆
    • Eloquent ౳Λ࢖͏ͳΒ͜͜Ͱ࢖͏
    65

    View Slide

  66. namespace MyApp\Components\CreateInbox\DataAccess\Database\Repositories;
    // 略
    /**
    * Class TaskRepository
    * @package MyApp\Components\CreateInbox\DataAccess\Database\Repositories
    */
    class TaskRepository implements TaskRepositoryInterface
    {
    /**
    * 与えられたタスクを永続化する
    *
    * @param Task $task
    */
    public function save(Task $task): void
    {
    $taskRecord = Eloquents\Task::create([
    'name' => $task->name()->value(),
    'note' => $task->note()->value(),
    ]);
    ΠϯλʔϑΣʔεͷ࣮૷
    ϢʔεέʔεͰఆٛͨ͠ΠϯλʔϑΣʔεΛ࣮૷
    66

    View Slide

  67. namespace MyApp\Components\CreateInbox\DataAccess\Database\Repositories;
    // 略
    /**
    * Class TaskRepository
    * @package MyApp\Components\CreateInbox\DataAccess\Database\Repositories
    */
    class TaskRepository implements TaskRepositoryInterface
    {
    /**
    * 与えられたタスクを永続化する
    *
    * @param Task $task
    */
    public function save(Task $task): void
    {
    $taskRecord = Eloquents\Task::create([
    'name' => $task->name()->value(),
    'note' => $task->note()->value(),
    ]);
    ΠϯλʔϑΣʔεͷ࣮૷
    Eloquent ౳͸͜͜Ͱ࢖ͬͯྑ͍
    67

    View Slide

  68. “ϑϨʔϜϫʔΫΛ࢖͏͜ͱ͸໰୊ͳ͍ɻ

    ͨͩ͠ɺ݁߹͠ͳ͍͜ͱ͕େ੾ͩɻ

    ϑϨʔϜϫʔΫͱ͸Ұఆͷڑ཭Λอͭ͜ͱɻ

    ϑϨʔϜϫʔΫ͸ɺΞʔΩςΫνϟͷ

    ԁͷ֎ଆʹ͋Δ΋ͷͱͯ͠ѻ͓͏ɻ”
    68

    View Slide

  69. ࢀߟɿαϯϓϧίʔυ
    https://github.com/okashoi/laravel-clean-
    architecture
    • ͋͘·ͰʮҰྫʯͰ͋Δ͜ͱʹཹҙ
    • ͜ͷܗ͕ઈରతͳ౴͑Ͱ͸ͳ͍
    • ࠓޙɺεϥΠυͷ಺༰ͱมΘΔՄೳੑ΋͋Δ
    69

    View Slide

  70. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • Laravel ͱͷ෇͖߹͍͔ͨʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    70

    View Slide

  71. ίΞͱͳΔߟ͑ํ
    ʮॏཁͳ΋ͷʯΛʮࠣࡉͳ΋ͷʯʹґଘͤ͞ͳ͍
    71
    σʔλϕʔεɾ
    UIɾϑϨʔϜϫʔΫͳͲ
    ༰қʹมߋͰ͖Δ
    Ϗδωεϧʔϧ
    มߋ͕ى͜Γʹ͍͘

    View Slide

  72. ґଘؔ܎ٯసͨ͠ίʔυ
    package foo;
    class Foo {
    Buz x;
    function doFoo() {
    x.process();
    }
    }
    interface Buz {
    function process();
    }
    72
    package bar;
    import foo;
    class Bar implements foo.Buz {
    function process() {
    // do something...
    }
    }

    View Slide

  73. Laravel ͱͷ෇͖߹͍͔ͨ
    • খ͍͞ύοέʔδ୯Ґʹ෼ׂͯ͠։ൃ

    Service Provider ͰͦΕΒΛ౷߹͢Δ
    • Laravel ͷػೳΛ࢖͏৔߹͸

    ϏδωεϧʔϧΑΓ΋֎ଆͷ૚Ͱ࢖͏
    73

    View Slide

  74. ໨࣍
    • ͜ͷτʔΫͷΊ͟͢ͱ͜Ζʢ2 ෼ʣ
    • ΫϦʔϯΞʔΩςΫνϟͷ֓ཁʢ3 ෼ʣ
    • ίΞͱͳΔߟ͑ํʢ5 ෼ʣ
    • ۩ମతͳίʔυྫʢ10 ෼ʣ
    • ·ͱΊʢ3 ෼ʣ
    • ࣗݾ঺հʢ2 ෼ʣ
    74

    View Slide

  75. ࣗݾ঺հ
    Ԭా ਖ਼ฏ / ͓͔͠ΐ͍
    @okashoi
    @okashoi
    ΞʔΩςΫτ ݉ ٕज़޿ใ
    75

    View Slide

  76. ࣗݾ঺հ
    ίϛϡχςΟ׆ಈ
    • Hacker’s GATE ӡӦ
    76

    View Slide

  77. ࣗݾ঺հ
    ίϛϡχςΟ׆ಈ
    • एख΋ͷͮ͘Γूஂ Oysters ϝϯόʔ
    77

    View Slide

  78. ࣗݾ঺հ
    ίϛϡχςΟ׆ಈ
    • Laravel JP Conference 2020 ίΞελοϑ
    78
    https://conference2020.laravel.jp/

    View Slide

  79. ࣗݾ঺հ
    Ԭా ਖ਼ฏ / ͓͔͠ΐ͍
    @okashoi
    @okashoi
    ΞʔΩςΫτ ݉ ٕज़޿ใ
    79
    ࠙਌ձ౳Ͱ͓࿩͠·͠ΐ͏😄

    View Slide