API Platform Installation!

Video not working?

It looks like your browser may not support the H264 codec. If you're using Linux, try a different browser or try installing the gstreamer0.10-ffmpeg gstreamer0.10-plugins-good packages.

Thanks! This saves us from needing to use Flash or encode videos in multiple formats. And that let's us get back to making more videos :). But as always, please feel free to message us.

Yo friends! It's time to talk about... drum roll... how to bake a delicious cake that looks like an Oreo. Wait... ah! Wrong tutorial. It's time to talk about API Platform... so fun, it's almost as delicious as a cake shaped like an Oreo.

API Platform is crushing it these days. I feel like everywhere I turn, someone is raving about it! Its lead developer - Kévin Dunglas - is a core contributor of Symfony, super nice guy and is absolutely pushing the boundaries of what API's can do. We're going to see that first-hand. He was also nice enough to guide us on this tutorial!

Modern APIs are Hard. API Platform is not

If you only need to build a few API endpoints just to support some JavaScript, you might be thinking:

What's the big deal? Returning some JSON here and there is already pretty easy!

I've had this same opinion for awhile. But little-by-little, I think this is becoming less and less true. Just like how frameworks were born when web apps became more and more complex, tools like API Platform have been created because the same things is currently happening with APIs.

These days, API's are more than just returning JSON: it's about being able to serialize and deserialize your models consistently, maybe into multiple formats, like JSON or XML, but also JSON-LD or HAL JSON. Then there's hypermedia, linked data, status codes, error formats, documentation - including API spec documentation that can power Swagger. Then there's security, CORS, access control and other important features like pagination, filtering, validation, content-type negotiation, GraphQL... and... honestly, I could keep going.

This is why API Platform exists: to allow us to build killer APIs and love the process! Oh, and that big list of stuff I just mentioned that an API needs? API Platform comes with all of it. And it's not just for building a huge API. It really is the perfect tool, even if you only need a few endpoints to power your own JavaScript.

API Platform Distribution

So let's do this! API Platform is an independent PHP library that's built on top of the Symfony components. You don't need to use it from inside a Symfony app, but, as you can see here, that's how they recommend using it, which is great for us.

If you follow their docs, they have their own API Platform distribution: a custom directory structure with a bunch of stuff: one directory for your Symfony-powered API, another for your JavaScript frontend, another for an admin frontend all wired together with Docker! Woh! It can feel a bit "big" to start with, but you get all of the features out-of-the-box... even more than I just described. If that sounds awesome, you can totally use that.

But we're going to do something different: we're going to install API Platform as a bundle into a normal, traditional Symfony app. It makes learning API Platform a bit easier. Once you're confident, for your project, you can do it this same way or jump in and use the official distribution. Like I said, it's super powerful.

Project Setup

Anyways, to become the API hero that we all need, you should totally code along with me by downloading the course code from this page. After you unzip it, you'll find a start/ directory inside with the same code that you see here... which is actually just a new Symfony 4.2 skeleton project: there is nothing special installed or configured yet. Follow the README.md file for the setup instructions.

The last step will be to open a terminal, move into the project and start the Symfony server with:

symfony serve -d

This uses the symfony executable - an awesome little dev tool that you can get at https://symfony.com/download. This starts a web server on port 8000 that runs in the background. Which means that we can find our browser, head to localhost:8000 and see... well, basically nothing! Just the nice welcome page you see in an empty Symfony app.

Installing API Platform

Now that we have our empty Symfony app, how can we install API Platform? Oh, it's so awesome. Find your terminal and run:

composer require api

That's it. You'll notice that this is installing something called api-platform/api-pack. If you remember from our Symfony series, a "pack" is sort of a "fake" library that helps install several thing at once.

Heck, you can see this at https://github.com/api-platform/api-pack: it's a single composer.json file that requires several libraries, like Doctrine, a CORS bundle that we'll talk about later, annotations, API Platform itself and a few parts of Symfony, like the validation system, security component and even twig, which is used to generate some really cool documentation that we'll see in a minute.

But, there's nothing that interesting yet: just API Platform and some standard Symfony packages.

Back in the terminal, it's done! And has some details on how to get started. A few recipes also ran that gave us some config files. Before we do anything else, go back to the browser and head to https://localhost:8000/api to see... woh! We have API documentation! Well, we don't even have any API yet... so there's nothing here. But this is going to be a huge, free feature you get with API Platform: as we build our API, this page will automatically update.

Let's see that next by creating and exposing our first API Resource.

Leave a comment!

  • 2020-06-29 Diego Aguiar

    Hey Sachin G Kulkarni

    In this course we don't teach how to work with GraphQL but you can read everything you need here https://api-platform.com/do...

    Cheers!

  • 2020-06-28 Sachin G Kulkarni

    Hey please let me know how to use GraphQL with API Platform. I am struggling to use it and end up getting few errors...

  • 2020-05-18 Vladimir Sadicov

    Perfect! no problem It's great that you solved it!!!

    Cheers and have a nice day!

  • 2020-05-18 Vladimir Sadicov

    I guess you have wrong symfony cli installed. Did you installed it from here? https://symfony.com/download Probably you got a very outdated tool installed somehow, install one from link I gave, and try again

    Cheers!

  • 2020-05-18 mike last

    Hi Vladamir, I managed to fix my issue - something going wrong with docker somewhere - thanks for taking the time to help

  • 2020-05-18 mike last

    server command is not defined, im on latest macOS and cli version is 1.5.11

  • 2020-05-18 Vladimir Sadicov

    that sounds weird, ok what about symfony server:start? And several other questions, what OS do you use? What version of symfony cli tool? check it with symfony version command

  • 2020-05-18 mike last

    serve command is not defined

  • 2020-05-18 Vladimir Sadicov

    Hey mike last

    Have you tried symfony serve without -d flag?

    Cheers!

  • 2020-05-18 mike last

    I cannot get symfony serve -d to start, there is no output, is there some way to get output, or fix a timeout issue

  • 2020-02-11 MrWeksalwm

    Sorry for the late reply. Yes, that fixed it, grazie mille!

  • 2020-01-21 Diego Aguiar

    Hey José Neto

    The bin/console is a php file, so it's likely that your Windows installation is not executing such file with PHP. Try running it like this: php bin/console and let me know if it worked

    Cheers!

  • 2020-01-21 José Neto

    How do I install it on Windows? After the require, the bin/console is not a win executable.

  • 2020-01-08 weaverryan

    Hey @MrWeksalwm!

    Hmm. Try running:

    composer require symfony/apache-pack

    That's a fake package that will add a public/.htaccess file that's needed by Apache. I bet that's what you're missing - as Apache's rewrite rules won't work without it.

    Let me know if that helps!

    Cheers!

  • 2020-01-08 MrWeksalwm

    I have a problem, due to doing things slightly differently than recommended in the tutorial (mea culpa). Instead of using "symfony serve", I am using Docker for my local environment. A portion of my "docker-compose.yml" looks like this:

    services:
    cheese_main:
    container_name: cheese_main
    image: webdevops/php-apache-dev:7.3
    links:
    - cheese_mysql
    depends_on:
    - cheese_mysql
    ports:
    - 8470:443
    volumes:
    - .:/app
    environment:
    docker: 'true'
    WEB_DOCUMENT_ROOT: '/app/public'
    WEB_NO_CACHE_PATTERN: '\.(.*)$$'
    working_dir: '/app'

    When I visit "https://localhost:8470", I get the Symfony home screen, all good. But when I visit "https://localhost:8470/api", I get a 4040 not found error. Any ideas where I'm going wrong? Thanks!

  • 2019-12-16 Victor Bocharsky

    Hey Arindam,

    Did you try to install bundle's assets? Try to execute:
    $ bin/console assets:install

    Does it help?

    Cheers!

  • 2019-12-14 Arindam SARKAR

    Here is the log that I found:

    NotFoundHttpException: "No route found for "GET /bundles/apiplatform/swagger-ui/swagger-ui.css"
    NotFoundHttpException: "No route found for "GET /bundles/apiplatform/init-swagger-ui.js" (from "https://localhost:8001/api")"
    NotFoundHttpException: "No route found for "GET /bundles/apiplatform/webby.png" (from "https://localhost:8001/api")"

  • 2019-12-14 Arindam SARKAR

    Hello,
    I've installed the API Platform with the following command "composer require api".
    It has been intalled and I have acces to "/api" but I don't see any CSS as saw in the video tutorial.

    Can someone let me know how to use the default CSS like him? Or do I need to configure it?
    Thank in advance!

  • 2019-12-10 Diego Aguiar

    Hey Annemieke Buijs

    Welcome to Symfony and ApiPlatform :)
    What you are experiencing is normal. The default "homepage" only works on the dev environment. You just need to create your own routes and it should work fine

    Cheers!

  • 2019-12-07 Annemieke Buijs

    I really really like symfony and api platform. But i have a weird challenge.
    (i've never installed anything on a linux machine before, so bear with me please AND i am a newbie to symfony 4).

    We have a new Azure server. CentOs is the operating system on which the symfony applications are going to run.
    I've installed the latest php, symfony, apache, composer etc.
    I have created a Virtual host ,



    ServerName www.example.com
    ServerAlias example.com *.example.com
    DocumentRoot /var/www/html/example.com
    DirectoryIndex public/index.php

    Also tried this:

    ServerName www.example.com
    ServerAlias example.com *.example.com
    DocumentRoot /var/www/html/example.com/public
    DirectoryIndex index.php

    I've tested this virtual host with an index.php in the public folder. This index.php has some links to html files in different folders.
    This works just fine, no problem.

    Then i took the zipfile from this course and put the start project of this zipfile on the server. Just for testing purposes. See if i can get it to work.
    The welcome page works fine but the url /api gives a "is not found".
    As soon as i change APP_ENV to prod (cache:clear) the welcome page does not show up anymore, I get a 404.

    This is result of bin/console about:
    -------------------- ---------------------------------
    Symfony
    -------------------- ---------------------------------
    Version 4.4.1
    Long-Term Support Yes
    End of maintenance 11/2022
    End of life 11/2023
    -------------------- ---------------------------------
    Kernel
    -------------------- ---------------------------------
    Type App\Kernel
    Environment prod
    Debug false
    Charset UTF-8
    Cache directory ./var/cache/prod (2.5 MiB)
    Log directory ./var/log (39 KiB)
    -------------------- ---------------------------------
    PHP
    -------------------- ---------------------------------
    Version 7.3.12
    Architecture 64 bits
    Intl locale n/a
    Timezone UTC (2019-12-07T14:58:02+00:00)
    OPcache false
    APCu false
    Xdebug false
    -------------------- ---------------------------------

    Do i have to change the rights or owner of folders maybe?

    Can anyone help me?

    I have fixed it. Thank you.

  • 2019-10-07 weaverryan

    Hey zpine!

    > Yes, I tried the DTO approach by following the official documentation examples and it solved the problem

    💯nice work!

    > But as I mentioned before it's not easy as following your screencasts

    That's always our goal - thanks :)

    > Can't blame anyone since it's open source project and it's our responsibility to contribute

    Yep... this is a real challenge for open source. We try to give back (in this case to API Platform) by consulting with them (for $) on the tutorial and other ways. Hopefully everyone wins, with great screencasts and a bit more support back to the project itself.

    Cheers!

  • 2019-10-04 zpine

    Hello Ryan,

    Sorry for the delayed reply, Thank you very much for your quick response and detailed explanation! Very impressive!

    1. Yes, I tried the DTO approach by following the official documentation examples and it solved the problem. But as I mentioned before it's not easy as following your screencasts. There are so many pieces missing and official document requires lots of improvements (Can't blame anyone since it's open source project and it's our responsibility to contribute). Unfortunately I cannot contribute to documentations because of my limited English.

    I am more than satisfied with your answers!

    Cheers!

  • 2019-09-26 weaverryan

    Hey zpine!

    1. Hmm, yea, I understand much better now - thanks for the clear code and database structure :). Because you're writing to fields from multiple entities, the "cleanest" situation here is probably a DTO (https://api-platform.com/do... ... or maybe an API resource that is not an entity (those are subtly different things). If you used a DTO, it would just give you a bit of a "cleaner" way to have the extra fields and then create the underlying entities that you need. Basically, you wouldn't need to create those extra fields in the User entity because they would be on your "input" DTO. But, I may be missing a detail - because I'm not sure what you other things you're processing in the doctrine event listener.

    Btw, adding an extra "setBusinessName()" method to your User entity so that you have a businessName field is not a bad solution. And you could either use a custom data persister to use that value to create the Account object. That's the classic trade-off between a DTO and adding custom fields via customer getters/setters: adding a custom getter/setter is a bit dirty, but super easy, and a nice solution if you only need to add limited fields. But if you need several more fields, a DTO becomes more attractive and keeps things cleaner.

    I don't know if I fully answered your question, so let me now :).

    Cheers!

  • 2019-09-25 zpine

    Hi Ryan,

    Thank you very much for the quick response.

    1. I think my English terms are confusing..... It's difficult for me to explain without an example (English is not my native), so I have created a gist with minimal version of app entities

    https://gist.github.com/zsp...

    Think of a SignUp scenario with following form:

    - Email
    - Password
    - Business Name (Account -> Name)

    This form collects data of 2 different entities in a single request and after a successful signup a new User and a Account object will be created along with membership role 'ROLE_OWNER'. So to be frank with you I really don't know the proper steps to handle this but as a work around I created some extra fields on User entity and created a doctrine event listener to do the rest of the things based on logged in user. I am pretty sure there maybe a better way to handle this. (DTO or Some other technique)

    2. Exciting news :) and waiting....

    Thank you!

    P.S. Sorry I think I am asking too many questions....

  • 2019-09-25 weaverryan

    Hey zpine!

    Awesome! Super happy to hear that! :D

    > 1. Many to Many with extra fields (by only exposing one resource to the API)

    Can you tell me more about this? I understand the Many to Many with extra fields part, but I'm not sure what you mean by only exposing one resource to the API part.

    > 2. Working with DTOs

    Yep, definitely - next course will cover this - one of my favorite "missing" features for the tutorial :).

    Cheers!

  • 2019-09-24 zpine

    Hi Ryan,

    I have followed your "API Platform Part 2" course series and now I realize that most of the challenges I had already covered in that course. So now I agree that API Platform can be used for any type of API implementations :), thanks again for your efforts to make this course simple to understand. It would be great if you can add some more sections which covers the following:

    1. Many to Many with extra fields (by only exposing one resource to the API)
    2. Working with DTOs

    Apart from that a separate course for VueJs with Symfony would be great!

    Thank you! Cheers!

  • 2019-09-23 weaverryan

    Hey zpine!

    Thanks for the kind words! It especially means a lot to me because you've already worked on API Platform before :).

    > 1. Is it a good idea to use API Platform for building public 3rd party interacting APIs? (e.g: Similar to SendGrid API)

    I would say... yes! If you ask the API Platform team, that would of *course* say yes... and I think I agree with them. But, I'm interested about what challenges you see with using it for a public API? The fact that it exposes the JSON-LD & OpenAPI stuff makes it especially a good fit for a public API. And, from an authentication standpoint, it's really "agnostic" to how you authenticate. What I mean is, you can setup whatever authentication mechanism you want.

    So, what challenges are you thinking about? I would really like to hear your thoughts :).

    Cheers!

  • 2019-09-20 zpine

    Hi! Thank you for this excellent course. I have worked with API Platform on several projects by referring the official documentation but it's not easy as following this course. I really love the way you explain things in plain simple English.

    I have a general question: (I am sorry if it's not related to course content)

    1. Is it a good idea to use API Platform for building public 3rd party interacting APIs? (e.g: Similar to SendGrid API)
    Personally I believe it's well suited for CRUD operations (js based front-end clients and mobile apps). When it comes to 3rd party APIs there are several challenges and I feel like using API Platform would complicate things.

  • 2019-07-30 Virginie Burlot

    Hi, and thank you for your courses, I just updated my subscription back to start learning again.

    But, I'm a bit frustrated by this new Symfony CLI. I can't make it work on my work computer.

    I've followed all the instuction to install it, and I can't create new SF4 projects, it tells me to use composer for SF4 projects, that the Symfony CLI only works for SF2 and 3 projects..

    I've followed all the steps in your README for this course, and I still can't use the Symfony CLI, when I try the "symfony serve" command, I have an InvalidArgumentException : Command "serve" is not defined.

    I'm on Windows 7 here at work, and maybe the Symfony CLI don't work on this OS and won't as it's kinda old.
    I really don't know how to solve this, I see everywhere now, in every documentation, to use the Symfony CLI, and I'm completely stuck.

    I can still use composer, as I did when I started my precedent project, but I would like so much to follow the hype train.

    Edit : I just added the webserver-bundle to continue this course, it's so frustating !

    Edit 2 : So, basically, I feel stupid. I had installed the old symfony.phar (dating back to SF3) in one of my PHP folder. This folder itself was in my PATH. So, the "symfony" command wasn't calling the new Symfony CLI, but the symfony.phar. Thanks to W7 horrible PATH management, I did not see it coming.

    I deleted the old .phar, and everything went as expected. Gosh, I feel stupid.

  • 2019-07-02 weaverryan

    Hey Azeem Michael!

    There will be - but not in this part 1. We've still got a lot to do with events, data persisters, custom endpoints, etc, which will likely be covered in part 3 (after part 2, security). We're going to work to minimize the delay between the parts.

    Cheers!

  • 2019-06-24 Azeem Michael

    is there going to be a session on event listeners? I don't see it in the chapters. Would be helpful if people want to to some pre/post events. E.g., make a stripe api call or send email on order creation.

  • 2019-06-18 Steven

    Hey Vladimir,
    thanks for the news! Works like a charm!

  • 2019-06-14 Vladimir Sadicov

    Hey Steven

    I have a good news. Setting environment variable NODE_TLS_REJECT_UNAUTHORIZED to 0 should fix this issue.
    You can set it with
    export NODE_TLS_REJECT_UNAUTHORIZED=0
    before running your command.

    Hope it will help!

    Cheers!

  • 2019-06-11 Victor Bocharsky

    Hey Vinz,

    Ah, nice! Good luck with the migration! I hope it won't be too complex. Every new version of Symfony has a lot of improvements, this will be a big step forward ;)

    Cheers!

  • 2019-06-11 Vinz Stoned Orgies

    Thanks Victor Bocharsky, I'm in the process of migrating to SF4.3 so it should be OK. And I always prefer to work on my own projects :)

  • 2019-06-11 Victor Bocharsky

    Hey Vinz,

    We always suggest our users to download the course code and code along with us from start/ directory. But of course it's not a requirement, you can follow the tutorial making changes in your own project. Well, to improve DX it would be good if your Symfony 3.4 project uses Symfony Flex, otherwise you would need to create configs and register bundles yourself. I see API platform should work on Symfony 3.4, though probably not the latest version, so if you want to go this way - I think you can try.

    Cheers!

  • 2019-06-10 Steven

    Hey Victor,
    removing and installing the ca again did the trick. I actually did the $ symfony server:ca:install several weeks ago, that must have been the problem.
    Seems I was a bit hasty there: the problem persists. I'm running this on debian 9.9 with symfony cli v4.5.5. I'll just use http in the meantime and wait for a fix.

    If your're interested, here's the full error when running npx @api-platform/client-generator https://localhost:8000/api src --resource person

    { api:
    Api { entrypoint: 'https://localhost:8000/api', resources: [] },
    error:
    { FetchError: request to https://localhost:8000/api failed, reason: self signed certificate in certificate chain
    at ClientRequest.<anonymous> (/home/steven/.npm/_npx/7260/lib/node_modules/@api-platform/client-generator/node_modules/node-fetch/index.js:133:11)
    at ClientRequest.emit (events.js:193:13)
    at TLSSocket.socketErrorListener (_http_client.js:397:9)
    at TLSSocket.emit (events.js:193:13)
    at emitErrorNT (internal/streams/destroy.js:91:8)
    at emitErrorAndCloseNT (internal/streams/destroy.js:59:3)
    at processTicksAndRejections (internal/process/task_queues.js:81:17)
    name: 'FetchError',
    message:
    'request to https://localhost:8000/api failed, reason: self signed certificate in certificate chain',
    type: 'system',
    errno: 'SELF_SIGNED_CERT_IN_CHAIN',
    code: 'SELF_SIGNED_CERT_IN_CHAIN' },
    response: undefined,
    status: undefined }

    Thanks again!

  • 2019-06-10 Vinz Stoned Orgies

    Hi, is it possible to user API Platform on an existing SF3.4 project ? Or is it better do to it on SF4 ?

  • 2019-06-10 Victor Bocharsky

    Hey Steven,

    Hm, are you on Windows? Try to remove certs with another command:

    $ symfony server:ca:uninstall

    Then try upgrade your Symfony client to the latest version with:

    $ symfony self:update

    And reinstall the certs again:

    $ symfony server:ca:install

    Does it help? Did you see any errors in the output?

    You can search for a similar on the Symfony Client repository: https://github.com/symfony/cli - I see there's a few opened issues about similar problem.

    If the problem persist, as a workaround you can try to use HTTP instead of HTTPS in the URL.

    Cheers!

  • 2019-06-09 Steven

    Hey, thanks for these awesome tutorials.
    I have some slight problems using the new symfony executable: after setting up https by doing symfony server:ca:install i can't use the api-platform client-generator in my local environment due to the self-signed certificate:

    FetchError: request to https://localhost:8000/api failed, reason: self signed certificate in certificate chain


    Are there any resources on how to fix this, or do I need to deploy the api first, before developing the client?
    Thank you!

  • 2019-06-03 Diego Aguiar

    Hey Jérôme 

    Can you show me the full message? Also, what Symfony CLI version do you have?

    Cheers!

  • 2019-06-03 Jérôme 

    I have a question for you... Maybe it's a silly question, but I'd really like to know. I've been seeing everywhere people using the Symfony CLI to make projects, but I still use composer to do it. For example, in this tutorial, you've used "symfony serve -d"... But when I tried to use the SF CLI, a message tells me to use composer, so I'm a little bit confused. Am I doing something wrong, or did I miss something? I'm curious... Thank you!

  • 2019-05-16 Diego Aguiar

    Thanks Jérôme  :)

  • 2019-05-16 Jérôme 

    Hey, thank you for this course. I think API Platform is great! I've been learning it for days now and I can't wait to see what you're going to teach us here. Keep up the good work, that's fantastic!