Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve doc #335

Merged
merged 2 commits into from
Oct 2, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
65 changes: 35 additions & 30 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,43 +17,48 @@ Try it online at <https://demo.api-platform.com>.

$ git clone https://github.com/api-platform/demo.git
$ cd demo
$ docker compose up -d
$ docker compose up --wait

You can now go to https://localhost

## What Can I Find In This Demo?

This demo application contains several things you may be interested.

### API Testing

All entities used in this project are thoroughly tested. Each test class extends
the `ApiTestCase`, which contains specific API assertions. It will make your tests
much more straightforward than using the standard `WebTestCase` provided by Symfony.

* [Documentation](https://api-platform.com/docs/core/testing/)
* [Code in api/tests/](api/tests)

### Extensions

The `Download` collection is restricted to the current user, except for admin users. The Doctrine Query is overridden
using a Doctrine Extension.

* [Documentation](https://api-platform.com/docs/core/extensions/)
* [Code in api/src/Doctrine/Orm/Extension](api/src/Doctrine/Orm/Extension)

### State Processors

The `Download` and `Review` entities require dynamic properties set before save: a date of creation, and a link to the
current user. This is done using State Processors.

* [Documentation](https://api-platform.com/docs/core/state-processors/)
* [Code in api/src/State/Processor](api/src/State/Processor)
## What Can I Find In This Demo?

This demo application contains several things you may be interested:

| Feature | Usage |
|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| [Bringing your Own Model](https://api-platform.com/docs/distribution/#bringing-your-own-model) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22%23%5BApiResource%22&type=code) |
| [Model Scaffolding](https://api-platform.com/docs/schema-generator/getting-started/#model-scaffolding) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22%23%5BApiProperty%28types%3A%22&type=code) |
| [Plugging the Persistence System](https://api-platform.com/docs/distribution/#plugging-the-persistence-system) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22%23%5BORM%22&type=code) |
| [Exposing Enums with API Platform](https://les-tilleuls.coop/blog/exposez-vos-enums-avec-api-platform) | [Search usage](api/src/Enum) |
| [Validating Data](https://api-platform.com/docs/distribution/#validating-data) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22%23%5BAssert%22&type=code) |
| [Configuring Operations](https://api-platform.com/docs/core/operations/) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22operations%3A%22&type=code) |
| [Defining Which Operation to Use to Generate the IRI](https://api-platform.com/docs/core/operations/#defining-which-operation-to-use-to-generate-the-iri) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22itemUriTemplate%3A%22&type=code) |
| [Subresources](https://api-platform.com/docs/core/subresources/) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc%2FEntity+%22uriTemplate%3A+%27%2Fbooks%2F%7BbookId%7D%2Freviews%7B._format%7D%27%22&type=code) |
| [Doctrine ORM Filters](https://api-platform.com/docs/core/filters/) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22%23%5BApiFilter%22&type=code) |
| [Creating Custom Doctrine ORM Filters](https://api-platform.com/docs/core/filters/#creating-custom-doctrine-orm-filters) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi+%22NameFilter%22+OR+%22app.filter.user.admin.name%22&type=code) |
| [Overriding Default Order](https://api-platform.com/docs/core/default-order/) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22order%3A%22&type=code) |
| [Changing the Number of Items per Page Client-side For a Specific Resource](https://api-platform.com/docs/core/pagination/#changing-the-number-of-items-per-page-client-side-for-a-specific-resource) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22paginationClientItemsPerPage%22&type=code) |
| [Advanced serialization](https://api-platform.com/docs/core/serialization/) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc+%22%23%5BGroups%22&type=code) |
| [User Support](https://api-platform.com/docs/core/user/) | [Search usage](api/src/Entity/User.php) |
| [Custom Doctrine ORM Extension](https://api-platform.com/docs/core/extensions/) | [Search usage](api/src/Doctrine/Orm/Extension) |
| [Custom State Processor](https://api-platform.com/docs/core/state-processors/) | [Search usage](api/src/State/Processor) |
| [Creating Async APIs using the Mercure Protocol](https://api-platform.com/docs/core/mercure/) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc%2FEntity+%22mercure%3A%22&type=code) |
| [Advanced Authentication and Authorization Rules](https://api-platform.com/docs/core/security/) | [Search usage](https://github.com/search?q=repo%3Aapi-platform%2Fdemo+path%3Aapi%2Fsrc%2FEntity+%22security%3A%22+OR+%22securityPostDenormalize%3A%22&type=code) |
| [API Testing](https://api-platform.com/docs/core/testing/) | [Search usage](api/tests) |
| [The Admin](https://api-platform.com/docs/distribution/#the-admin) | [Search usage](pwa/pages/admin) |
| [A Next.js Web App](https://api-platform.com/docs/distribution/#a-nextjs-web-app) | [Search usage](pwa) |
| [Deploying to a Kubernetes Cluster](https://api-platform.com/docs/deployment/kubernetes) | [Search usage](helm/api-platform) |

> Note: this demo application implements [OpenID Connect Specification Support](https://openid.net/developers/specs/)
> (using [Keycloak](https://www.keycloak.org/)). See [usage in API](api/config/packages/security.yaml) and
> [usage in PWA](pwa/pages/api/auth/%5B...nextauth%5D.tsx).

## Contributing

[Read the contributing guide](.github/CONTRIBUTING.md)

## Credits

Created by [Kévin Dunglas](https://dunglas.fr/). Commercial support available at [Les-Tilleuls.coop](https://les-tilleuls.coop/).
Created by [Kévin Dunglas](https://dunglas.fr/). Commercial support available
at [Les-Tilleuls.coop](https://les-tilleuls.coop/).
12 changes: 7 additions & 5 deletions api/src/Entity/Book.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@
use Symfony\Bridge\Doctrine\Types\UuidType;
use Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntity;
use Symfony\Component\Serializer\Annotation\Groups;
use Symfony\Component\Serializer\Normalizer\AbstractNormalizer;
use Symfony\Component\Serializer\Normalizer\AbstractObjectNormalizer;
use Symfony\Component\Uid\Uuid;
use Symfony\Component\Validator\Constraints as Assert;

Expand Down Expand Up @@ -61,11 +63,11 @@
),
],
normalizationContext: [
'groups' => ['Book:read:admin', 'Enum:read'],
'skip_null_values' => true,
AbstractNormalizer::GROUPS => ['Book:read:admin', 'Enum:read'],
AbstractObjectNormalizer::SKIP_NULL_VALUES => true,
],
denormalizationContext: [
'groups' => ['Book:write'],
AbstractNormalizer::GROUPS => ['Book:write'],
],
// todo waiting for https://github.com/api-platform/core/pull/5844
// collectDenormalizationErrors: true,
Expand All @@ -80,8 +82,8 @@
new Get(),
],
normalizationContext: [
'groups' => ['Book:read', 'Enum:read'],
'skip_null_values' => true,
AbstractNormalizer::GROUPS => ['Book:read', 'Enum:read'],
AbstractObjectNormalizer::SKIP_NULL_VALUES => true,
]
)]
#[ORM\Entity(repositoryClass: BookRepository::class)]
Expand Down
8 changes: 5 additions & 3 deletions api/src/Entity/Bookmark.php
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@
use Doctrine\ORM\Mapping as ORM;
use Symfony\Bridge\Doctrine\Types\UuidType;
use Symfony\Component\Serializer\Annotation\Groups;
use Symfony\Component\Serializer\Normalizer\AbstractNormalizer;
use Symfony\Component\Serializer\Normalizer\AbstractObjectNormalizer;
use Symfony\Component\Uid\Uuid;
use Symfony\Component\Validator\Constraints as Assert;

Expand All @@ -40,14 +42,14 @@
),
],
normalizationContext: [
'groups' => ['Bookmark:read'],
'skip_null_values' => true,
AbstractNormalizer::GROUPS => ['Bookmark:read'],
AbstractObjectNormalizer::SKIP_NULL_VALUES => true,
IriTransformerNormalizer::CONTEXT_KEY => [
'book' => '/books/{id}{._format}',
],
],
denormalizationContext: [
'groups' => ['Bookmark:write'],
AbstractNormalizer::GROUPS => ['Bookmark:write'],
],
// todo waiting for https://github.com/api-platform/core/pull/5844
// collectDenormalizationErrors: true,
Expand Down
16 changes: 9 additions & 7 deletions api/src/Entity/Review.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@
use Doctrine\ORM\Mapping as ORM;
use Symfony\Bridge\Doctrine\Types\UuidType;
use Symfony\Component\Serializer\Annotation\Groups;
use Symfony\Component\Serializer\Normalizer\AbstractNormalizer;
use Symfony\Component\Serializer\Normalizer\AbstractObjectNormalizer;
use Symfony\Component\Uid\Uuid;
use Symfony\Component\Validator\Constraints as Assert;

Expand Down Expand Up @@ -66,11 +68,11 @@
'book' => '/admin/books/{id}{._format}',
'user' => '/admin/users/{id}{._format}',
],
'skip_null_values' => true,
'groups' => ['Review:read', 'Review:read:admin'],
AbstractObjectNormalizer::SKIP_NULL_VALUES => true,
AbstractNormalizer::GROUPS => ['Review:read', 'Review:read:admin'],
],
denormalizationContext: [
'groups' => ['Review:write', 'Review:write:admin'],
AbstractNormalizer::GROUPS => ['Review:write', 'Review:write:admin'],
],
// todo waiting for https://github.com/api-platform/core/pull/5844
// collectDenormalizationErrors: true,
Expand Down Expand Up @@ -101,7 +103,7 @@
processor: ReviewPersistProcessor::class,
provider: CreateProvider::class,
itemUriTemplate: '/books/{bookId}/reviews/{id}{._format}',
validationContext: ['groups' => ['Default', 'Review:create']]
validationContext: [AbstractNormalizer::GROUPS => ['Default', 'Review:create']]
),
new Patch(
uriTemplate: '/books/{bookId}/reviews/{id}{._format}',
Expand Down Expand Up @@ -129,11 +131,11 @@
'book' => '/books/{id}{._format}',
'user' => '/users/{id}{._format}',
],
'skip_null_values' => true,
'groups' => ['Review:read'],
AbstractObjectNormalizer::SKIP_NULL_VALUES => true,
AbstractNormalizer::GROUPS => ['Review:read'],
],
denormalizationContext: [
'groups' => ['Review:write'],
AbstractNormalizer::GROUPS => ['Review:write'],
],
// todo waiting for https://github.com/api-platform/core/pull/5844
// collectDenormalizationErrors: true
Expand Down
6 changes: 4 additions & 2 deletions api/src/Entity/User.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
use Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntity;
use Symfony\Component\Security\Core\User\UserInterface;
use Symfony\Component\Serializer\Annotation\Groups;
use Symfony\Component\Serializer\Normalizer\AbstractNormalizer;
use Symfony\Component\Serializer\Normalizer\AbstractObjectNormalizer;
use Symfony\Component\Uid\Uuid;

/**
Expand Down Expand Up @@ -41,8 +43,8 @@
),
],
normalizationContext: [
'groups' => ['User:read'],
'skip_null_values' => true,
AbstractNormalizer::GROUPS => ['User:read'],
AbstractObjectNormalizer::SKIP_NULL_VALUES => true,
]
)]
#[ORM\Entity(repositoryClass: UserRepository::class)]
Expand Down
Loading