SkolemIriConverter isn't reset between requests in worker mode (missing kernel.reset tag)
Los mantenedores suelen responder en 1 día
Nadie ha tomado este issue todavía.
Evaluación
- Dificultad
- 1/5
- Tiempo estimado
- Menos de una hora
- Aptitud para principiantes
- 85/100
Línea de trabajo
Empieza con la definición del servicio api_platform.symfony.iri_converter.skolem en la configuración del bundle de Symfony, y con SkolemIriConverter, que implementa ResetInterface y contiene la propiedad objectHashMap. Comprueba si al servicio le falta la etiqueta kernel.reset y luego confirma que la llamada de reinicio está conectada a través de services_resetter. Está terminado cuando el mapa skolem de la reproducción queda vacío después de cada reinicio.
Escrito por el modelo de indexación a partir del texto del issue.
Descripción
API Platform version(s) affected: 5.0.2 (also 4.4 and main)
Description
I've been upgrading one of our projects to API Platform 5 (Symfony 8.1, FrankenPHP in worker mode). One endpoint returns embedded objects that aren't resources themselves, so they get /.well-known/genid/... IRIs. With that endpoint, a single worker's memory kept growing until it hit our 128M memory_limit. It only took about five requests.
it seems the skolem IRI converter keeps an object → IRI map, and it is never cleared between requests.
I think the cause is that SkolemIriConverter already implements ResetInterface, but its service (api_platform.symfony.iri_converter.skolem) isn't tagged kernel.reset, so services_resetter never calls it. As far as I can see, it's the same in 4.4, 5.0 and main.
How to reproduce
- Create a resource that returns an embedded object which isn't itself a resource, so it gets a genid IRI. For example:
#[ApiResource(operations: [new Get(provider: [self::class, 'provide'])])]
final class Report
{
public string $id = '1';
/** @var Line[] */
public array $lines = [];
public static function provide(): self
{
$r = new self();
foreach (range(1, 500) as $i) {
$r->lines[] = new Line(str_repeat('x', 1000));
}
return $r;
}
}
final class Line
{
public function __construct(public string $text) {}
}
- Boot the kernel once and send several requests through it. Run the services resetter between them, as a FrankenPHP worker would:
$kernel = new Kernel('prod', false);
$kernel->boot();
$skolem = $kernel->getContainer()->get('api_platform.symfony.iri_converter.skolem');
$map = (new \ReflectionProperty($skolem, 'objectHashMap'));
for ($i = 1; $i <= 5; $i++) {
$response = $kernel->handle(Request::create('/reports/1', 'GET', server: ['HTTP_ACCEPT' => 'application/ld+json']));
$kernel->terminate($request ?? Request::create('/'), $response);
$kernel->getContainer()->get('services_resetter')->reset();
printf("request %d: %d skolem entries, %.1f MB\n", $i, count($map->getValue($skolem)), memory_get_usage() / 1048576);
}
- Expected: the skolem map is empty, or at least stays flat, after each reset. What happens: it grows by the number of embedded objects on every request (500, 1000, 1500, …), and memory grows with it. In our app it reached the 128M limit within about five requests.
- Add the kernel.reset tag (see the workaround below) and run it again. The map is cleared after each request, and memory stays flat.
Possible Solution
Add the tag where the service is registered:
->tag('kernel.reset', ['method' => 'reset'])
Additional Context
Workaround for now
override the service definition ourselves for api_platform.symfony.iri_converter.skolem to add the tag
With that in place, memory stays flat across requests.
I'll raise a short PR
- Lenguaje dominante
- PHP
- Estrellas
- 2.6k
- Forks
- 989
- Merge medio
- 2 d 2 h
- PR fusionados (30 d)
- 101
Preparar el entorno
- Sin Dockerfile ni archivo de Docker Compose
- Tiene una plantilla de pull request
- Leer la guía de contribución
Primeros pasos
- Lee el issue completo y luego la guía de contribución del proyecto.
- Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
- Haz un fork del repositorio y trabaja en una rama.
- Abre un pull request que haga referencia al número del issue.
Más de api-platform/core
-
Dificultad 2/5 Menos de una hora Aptitud para principiantes 80/100
api-platform/core#8701 ·
Los mantenedores suelen responder en 1 día
-
JSON:API: `JsonApiCollectionBaseSchemaNoPagination` declares `data` as `type: array` without `items`Abierto
Dificultad 2/5 1-3 horas Aptitud para principiantes 82/100
api-platform/core#8699 ·
Los mantenedores suelen responder en 1 día
-
api:openapi:export --spec-version=3.0.0 outputs `webhooks`, which is invalid in OpenAPI 3.0Posiblemente ocupada Un pull request vinculado a esta issue está abierto o ya se fusionó. Abierto
Dificultad 2/5 1-3 horas Aptitud para principiantes 72/100
api-platform/core#8690 ·
Los mantenedores suelen responder en 1 día
-
Dificultad 3/5 1-2 días Aptitud para principiantes 50/100
api-platform/core#8704 ·
Los mantenedores suelen responder en 1 día
-
JSON:API: request documents with no `data`, no `type` or a wrong `type` are accepted with 201Abierto
Dificultad 3/5 1-2 días Aptitud para principiantes 62/100
api-platform/core#8703 ·
Los mantenedores suelen responder en 1 día
Todos los issues de api-platform/core
Issues similares
-
Dificultad 2/5 1-3 horas Aptitud para principiantes 78/100
-
Featured image not passed to checks in the Tasks column or publish blocksPosiblemente ocupada @roborourke la tomó hoy. Abierto
Dificultad 2/5 1-3 horas Aptitud para principiantes 78/100
humanmade/publication-checklist#100 ·
Los mantenedores suelen responder en 1 día
-
bug customer-reported
Dificultad 2/5 1-3 horas Aptitud para principiantes 62/100
MagnaCapax/PMSS#1072 ·
Los mantenedores suelen responder en 5 días
-
Dificultad 2/5 1-3 horas Aptitud para principiantes 82/100
verbb/formie#3013 · 1 comentario ·
Los mantenedores suelen responder en 1 día
-
bug
Dificultad 2/5 1-3 horas Aptitud para principiantes 62/100
hestiacp/hestiacp#5800 · 1 comentario ·
Los mantenedores suelen responder en 1 día