Writing APIs with Lumen A Hands-on Guide to Writing API Services With PHP Paul Redmond © 2015 - 2016 Paul Redmond Tweet This Book! PleasehelpPaulRedmondbyspreadingthewordaboutthisbookonTwitter! Thesuggestedhashtagforthisbookis#lumenapibook. Findoutwhatotherpeoplearesayingaboutthebookbyclickingonthislinktosearchforthis hashtagonTwitter: https://twitter.com/search?q=#lumenapibook ToBernadette. IwouldberemissifIdidn’tthankTaylorOtwellforcreatingLumenandLaravel,andthe communitycontributionsthatmaketheLaravelecosystemamazing. Contents Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1 TheSameToolstoWriteAPIsandWebApplications . . . . . . . . . . . . . . . . . . . . 1 WhoThisBookisFor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1 ConventionsUsedinThisBook . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2 ToolsYouWillNeed . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4 AboutMe . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5 Chapter1:InstallingLumen . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1 Homestead . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1 MacOSX . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3 Linux . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4 Windows . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8 Chapter2:HelloLumen . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 2.1:SettingUpaNewProject . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 2.2:Routes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12 2.3:MiddlewareandResponses . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14 2.4:Views . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18 Onward . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20 Chapter3:CreatingtheBookApplication . . . . . . . . . . . . . . . . . . . . . . . . . . . 21 BuildSomethingAmazing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21 EnvironmentSetup . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 24 CheckingUnitTests . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 28 SetupComplete . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 29 Chapter4:StartingtheBooksAPI . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30 CreatingtheFirstEndpoint . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30 SettingupModelsandSeedData . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34 EloquentBooks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 40 Success . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 42 Chapter5:Creating,Reading,Updating,andDeletingBooks . . . . . . . . . . . . . . . . 43 5.1:RequestinganIndividualBook . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43 CONTENTS 5.2:CreatingaNewBook . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 53 5.3:UpdatinganExistingBook . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 62 5.4:Deletingbooks . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 69 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81 Chapter6:RespondingtoErrors . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 83 6.1:TestDatabase . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 83 6.2:BetterErrorResponses . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 89 6.3:TestingtheExceptionHandler . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 94 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 111 Chapter7:LevelingUpResponses . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 113 7.1:IntroducingFractal . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 113 7.2:FirstVersionofAPIResponseFormatting . . . . . . . . . . . . . . . . . . . . . . . . 115 7.2:TheFractalResponseClass . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 123 7.3:FractalResponseService . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 141 7.4:IntegratingtheFractalResponseService . . . . . . . . . . . . . . . . . . . . . . . . . 145 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 158 Chapter8:Validation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 159 8.1:FirstAttemptatValidation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 159 8.2:MoreValidationConstraints . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 165 8.3:CustomValidationMessages . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 168 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 170 Chapter9:Authors . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 171 9.1:TheAuthorsdatabaseschema . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 171 9.2:FixingBrokenTests . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 181 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 204 Chapter10:The/authorsAPIResource . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 205 10.1:TheGET/authorsEndpoint . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 206 10.2:TheGET/authors/{id}Endpoint . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 211 10.3:ThePOST/authorsEndpoint . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 224 10.4:ThePUT/authors/{id}Endpoint . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 234 10.5:TheDELETE/authors/{id}Endpoint . . . . . . . . . . . . . . . . . . . . . . . . . . 246 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 247 Chapter11:BookBundles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 248 11.1:DefiningtheRelationshipBetweenBooksandBundles . . . . . . . . . . . . . . . . 248 11.2:TheGET/bundles/{id}Endpoint . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 255 11.3:AddingaBooktoaBundle . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 264 11.4:RemoveaBookfromaBundle . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 266 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 268 CONTENTS Chapter12:Ratings . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 269 12.1:DatabaseDesign . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 269 12.2:RatinganAuthor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 274 12.3:RatingsintheAuthorAPI . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 291 12.4:EagerLoadingRatings . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 297 Conclusion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 298 WhereToGoFromHere . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 299 Laravel . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 299 Laracasts . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 300 Mockery . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 300 Guzzle . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 300 Introduction Lumen is a framework that is designed to write APIs. With the rising popularity ofmicroservices¹, existingpatternslikeSOA²(ServiceOrientedArchitecture),andincreaseddemandforpublicAPIs, Lumenisaperfectfitforwritingtheservicelayerinthesamelanguageasthewebapplicationsyou write. In my experience, it’s not uncommon for PHP shops to write web applications with PHP and API serviceswithsomethinglikeNode.js³.Iamnotsuggestingthatthisisabad idea,butIseeLumenas a chance to improve development workflows for PHP developers and for companies to standarize aroundapowerfulsetofcomplimentaryframeworks:LaravelandLumen. You can write APIs quickly with Lumen using the built-in packages provided, but Lumen can also getoutofyourwayandbeasminimalistasyouwantittobe.Setasideframeworkbenchmarksand open your mind to increased developer productivity. Lumen is fast but more importantly, it helps mebemoreproductive. The Same Tools to Write APIs and Web Applications LumenisaminimalframeworkthatusesasubsetofthesamecomponentsfromLaravel⁴.Together Laravel and Lumen give developers a powerful combination of tools: a lightweight framework for writing APIs and a full-fledged web framework for web applications. Lumen also has a subset of consoletoolsavailablefromLaravel.OtherpowerfulfeaturesfromLaravelareincludedlikedatabase migrations, Eloquent Models (ORM Package), job queues, scheduled jobs, and a test suite focused ontestingAPIs. The development experience between Lumen and Laravel is relatively the same, which means developers will see a productivity boost by adopting both frameworks. Together they provide a consistent workflow and can simplify the software stack for developers, release engineers and operationsteams. Who This Book is For This book is for programmers that want to write APIs in PHP. Familiarity with the HTTP spec, Composer,PHPUnit,andthecommandlinewillhelp,butthisbookwalksyouthrougheachstepof buildinganAPI.Youdon’tneedtobeanexpertonthesesubjects,andmoreexperienceddevelopers canskipthingstheyunderstandtofocusonthespecificcodeneededtowriteAPIsinLumen. ¹http://microservices.io/patterns/microservices.html ²https://en.wikipedia.org/wiki/Service-oriented_architecture ³https://nodejs.org/en/ ⁴https://laravel.com/ 1 Introduction 2 Conventions Used in This Book The book is a hands-on guide to building a working API and so you will see tons of code samples throughoutthebook.Iwillpointoutafewconventionsusedsothatyoucanunderstandtheconsole commandsandcode.ThecodeismeanttoprovideafullyworkingAPIandsoyoucanfollowalong orcopyandpastecodesamples. Code Examples AtypicalPHPcodesnippetlookslikethis: ExamplePHPCodeSnippet /** * A Hello World Example */ $app->get('/', function () { return 'Hello World'; }); Toguidereaders,approximatelinenumbersareusedwhenyouwillbeaddingablockofcodetoan existingclassortestfile: ExamplePHPCodeSnippet 10 /** 11 * A Foobar Example 12 */ 13 $app->get('/foo', function () { 14 return 'bar'; 15 }); Longerlinesendinabackslash(\)andcontinuetothenextline: ExampleofLongLineinPHP $thisIsALongLine = 'Lorem ipsum dolor sit amet, consectetur adipisicing elit. Qu\ os unde deserunt eos?' Whenyouneedtorunconsolecommandstoexecutethetestsuiteorcreatefiles,thesnippetappears asplaintextwithoutlinenumbers.Linesstartwith$whichrepresentstheterminalprompt. Introduction 3 ExampleConsoleCommand $ touch the/file.php Console commands that should be executed in the recommendedHomestead⁵ environment will be indicated like the following example. The book removes extra output from PHPUnit tests to make exampleslessverbose. ConsoleCommandintheHomesteadVirtualMachine # vagrant@homestead:~/Code/bookr$ $ phpunit OK (1 test, 4 assertions) Tips, Notes and Warnings Your Aside title Thisisanaside Hey, Listen! Tipsgiveyoupointersrelatedtoconceptsinthebook. Danger! Warningspointoutpotentialissuesandsecurityconcerns. Need the Info Providesadditionalinforelatedtocodeandconcepts. Git Commit: Amazing Refactor! rm3dwe2f This is an example of a code commit if you are following along and using git to commit yourwork. ⁵https://laravel.com/docs/homestead
Description: