Glosario

Por qué el 429 Retry-After falta en la mayoría de las APIs de redes sociales

Taras Shynkarenko
Taras Shynkarenko
•Actualizado: •10 min de lectura
Una respuesta HTTP 429 con cabecera Retry-After junto a las señales de límite de tasa de cinco plataformas socialesUna respuesta HTTP 429 con cabecera Retry-After junto a las señales de límite de tasa de cinco plataformas sociales

TL;DR, Respuesta Rápida

10 min de lectura

El RFC 6585 define 429 Too Many Requests y dice que la respuesta puede (MAY) incluir una cabecera Retry-After, que el RFC 9110 define como un número de segundos o una fecha HTTP. Ninguna de las cinco grandes APIs sociales documenta que la envíe. X te remite a x-rate-limit-reset, una marca de tiempo Unix. Meta señala los límites con los códigos de error 4, 17, 32, 613 y 80001 y nunca indica el estado HTTP. LinkedIn devuelve 429 sin cabeceras documentadas y se reinicia a medianoche UTC. TikTok devuelve 429 con rate_limit_exceeded. YouTube informa de una cuota agotada como un 403, no como un 429.

¿Qué significa 429 Retry-After?

Una respuesta 429 Retry-After es un servidor que le dice a un cliente que ha enviado demasiadas peticiones y, de forma opcional, cuánto esperar antes de la siguiente. Las dos mitades vienen de dos especificaciones distintas.

El RFC 6585 define el código de estado: "The 429 status code indicates that the user has sent too many requests in a given amount of time ("rate limiting")." Después hace opcional la cabecera: "The response representations SHOULD include details explaining the condition, and MAY include a Retry-After header indicating how long to wait before making a new request."

El RFC 9110 define la cabecera en sí, en la sección 10.2.3: "Servers send the "Retry-After" header field to indicate how long the user agent ought to wait before making a follow-up request." La sección pasa a describir qué significa la cabecera en un 503 y en una redirección 3xx. Nunca menciona el 429. El vínculo entre el código de estado y la cabecera vive por completo en el RFC 6585, y allí es un MAY.

El RFC 6585 también deja el recuento en manos del servidor: "Note that this specification does not define how the origin server identifies the user, nor how it counts requests." Esa sola frase explica por qué cada plataforma de las de abajo se comporta de forma distinta. El estándar les da un código de estado y una cabecera opcional, y nada más.

Si hay una caché delante de tu cliente de API, el RFC 6585 tiene una regla más para ella: "Responses with the 429 status code MUST NOT be stored by a cache."

¿Cómo se interpreta un valor de Retry-After?

El RFC 9110 permite dos formas: "The Retry-After field value can be either an HTTP-date or a number of seconds to delay after receiving the response."

Retry-After: Fri, 31 Dec 1999 23:59:59 GMT
Retry-After: 120

La forma en segundos es "a non-negative decimal integer, representing time in seconds", y el RFC precisa que el segundo ejemplo significa un retraso de 2 minutos. Un parser tiene que manejar las dos. Prueba primero el entero y, si no encaja, recurre a una fecha:

from email.utils import parsedate_to_datetime
from datetime import datetime, timezone
 
def retry_after_seconds(value):
    if value.strip().isdigit():
        return int(value)
    when = parsedate_to_datetime(value)
    return max(0, (when - datetime.now(timezone.utc)).total_seconds())

Filas de coches atascados en una autopista, una imagen de un servidor que rechaza peticiones cuando llegan demasiadas a la vez.

¿Qué APIs de redes sociales envían una cabecera Retry-After?

Ninguna de las cinco, según su propia documentación. Cada una señala un límite de tasa a su manera, y dos de ellas no siempre usan 429.

PlataformaEstado ante un límite de tasaSeñal en el cuerpoSeñal de tiempo en la documentaciónRetry-After documentado
X429code: 88, "Rate limit exceeded"x-rate-limit-reset, una marca de tiempo UnixNo
Meta Graph APINo indicadoerror.code de 4, 17, 32, 613 o 80001estimated_time_to_regain_access en minutos, solo business use caseNo
LinkedIn429"Resource level throttle limit for calls to this resource is reached."Ninguna, los límites diarios se reinician a medianoche UTCNo
TikTok429rate_limit_exceededNinguna, ventana deslizante de un minutoNo
YouTube403 para la cuota, 429 solo para miniaturasquotaExceeded, uploadRateLimitExceededNingunaNo

Bluesky y Pinterest tienen sus propios esquemas de cabeceras, cubiertos en el desglose del límite de tasa de la API de Bluesky y en la referencia del límite de tasa de la API de Pinterest.

¿Cómo señala la API de X un límite de tasa?

Con un 429 y tres cabeceras en cada respuesta. La página de límites de tasa de X: "Exceeding limits results in a 429 error until the window resets." Documenta x-rate-limit-limit como "Maximum requests allowed", x-rate-limit-remaining como "Requests remaining in window" y x-rate-limit-reset como "Unix timestamp when window resets."

x-rate-limit-reset es el campo que hay que usar, y es una hora absoluta, no un retraso. El valor de ejemplo de X es 1705420800. Pásalo como segundos a una llamada de espera y el worker duerme unos 54 años, así que resta antes la hora Unix actual. La estrategia de recuperación de X tiene tres pasos: "Check x-rate-limit-reset for when the window resets", "Wait until that time before retrying", "Use exponential backoff if needed." Su código de ejemplo espera max(reset_time - time.time(), 60), así que nunca menos de un minuto.

X documenta dos cuerpos distintos para la misma situación. La página de límites de tasa muestra un 429 que devuelve {"errors": [{"code": 88, "message": "Rate limit exceeded"}]}. La página de códigos de respuesta describe los errores como objetos con type, title y detail, y lista un tipo .../rate-limit-exceeded. Comprueba el estado HTTP y trata cualquiera de las dos formas de cuerpo como un límite de tasa.

La misma página añade una trampa. X define el 429 como "Rate limit or usage cap exceeded", y lista un tipo de error aparte, .../usage-capped. Un 429 causado por un tope de uso no se despeja cuando pasa x-rate-limit-reset. Comprueba el tipo de error antes de programar un reintento a la hora del reinicio.

¿Cómo señala Meta un límite de tasa?

Con códigos de error en el cuerpo JSON. La referencia de limitación de tasa y la guía de gestión de errores de Meta los listan, y ninguna de las dos páginas indica qué estado HTTP los acompaña.

AdaptlyPost
AdaptlyPost

Empieza tu prueba gratis de 7 días

Analíticas multiplataforma

Bandeja Social

Asistente con IA

CódigoLo que dice Meta
4"Indicates that the app whose token is being used in the request has reached its rate limit."
17"Indicates that the User whose token is being used in the request has reached their rate limit."
32"Indicates that the User or app whose token is being used in the Pages API request has reached its rate limit."
613"Indicates that a custom rate limit has been reached."
80001"There have been too many calls to this Page account. Wait a bit and try again."

Meta se contradice sobre qué hacer después. La guía de gestión de errores dice, tanto para 4 como para 17: "Temporary issue due to throttling. Wait and retry the operation, or examine your API request volume." La referencia de limitación de tasa dice: "When the limit has been reached, stop making API calls. Continuing to make calls will continue to increase your call count, which will increase the time before calls will be successful again." Quédate con la más estricta, porque reintentar bajo las reglas de Meta alarga el bloqueo.

La señal de tiempo de Meta depende de cuál de sus dos sistemas de límite de tasa te haya atrapado. La cabecera business use case lleva estimated_time_to_regain_access, definido como "Time, in minutes, until calls will not longer be throttled." Fíjate en la unidad: Retry-After cuenta en segundos y este campo cuenta en minutos. La cabecera a nivel de aplicación no tiene ningún campo de tiempo, algo que el desglose de la cabecera x-app-usage cubre en detalle.

Primer plano de un reloj de pared analógico, que representa los límites que se reinician a una hora fija del día, como la medianoche UTC.

¿Cómo señalan LinkedIn y TikTok un límite de tasa?

Las dos devuelven un 429 sin más y no documentan cabeceras de tiempo.

La página de limitación de tasa de LinkedIn: "Rate limited requests will receive a 429 response." Su página de gestión de errores da el mensaje: "Resource level throttle limit for calls to this resource is reached." LinkedIn tampoco publica los límites en sí: "Standard rate limits are not published in documentation." Los encuentras en la pestaña Analytics del Developer Portal, y solo para los endpoints que hayas llamado al menos una vez ese día UTC.

El tiempo sale del calendario en lugar de una cabecera. LinkedIn indica que los límites cubren "a 24 hour period" y que "reset at midnight UTC every day." Tras un 429 de LinkedIn causado por tu propio volumen, el primer reintento útil es a las 00:00 UTC siguientes. LinkedIn también envía 429 por un motivo que no depende de ti: "In rare cases, LinkedIn may also return a 429 response as part of infrastructure protection. API service will return to normal automatically." Nada en la respuesta distingue los dos casos.

La página de límites de tasa de TikTok: "Request rate calculation is based on a one minute sliding window. If the number of requests exceeds the threshold, new requests will be throttled and a response will be returned with HTTP status 429 and error code rate_limit_exceeded." La página lista 600 peticiones para cada uno de /v2/user/info/, /v2/video/query/ y /v2/video/list/. El endpoint de publicación es mucho más estricto. La referencia de la Content Posting API dice de /v2/post/publish/video/init/: "Each user access_token is limited to 6 requests per minute."

El tope diario de publicaciones de TikTok no es un 429. Es un 403 con spam_risk_too_many_posts, descrito como "The daily post cap from the API is reached for the current user." Un bucle de reintentos basado en el 429 nunca lo verá, y un bucle que reintenta cualquier 4xx lo martilleará para nada.

¿Cómo señala YouTube un error de cuota?

Casi siempre con un 403. La referencia de errores de YouTube lista quotaExceeded (403): "The request cannot be completed because you have exceeded your quota." Ese es el error que produce una cuota diaria agotada, y no es un 429.

La visión general de YouTube indica el presupuesto por defecto: "Projects that enable the YouTube Data API have a default quota allocation of 100 search.list calls, 100 videos.insert calls, and 10,000 units per day combined for all other endpoints." También señala que "All API requests, including invalid requests, incur at least a one-point quota cost", así que los reintentos fallidos también gastan cuota.

El único 429 de la referencia de errores de YouTube es el de las miniaturas: tooManyRequests (429) uploadRateLimitExceeded, "The channel has uploaded too many thumbnails recently. Please try the request again later." El tope diario de subidas usa otro estado más, badRequest (400) uploadLimitExceeded, con una descripción muy directa: "This is a YouTube platform restriction and is entirely separate from your Google Cloud project's API quota." Un quotaExceeded no se puede reintentar el mismo día. Subir el techo es un trámite de papeleo, que se cubre en qué implica una ampliación de cuota de la API de YouTube.

¿Qué debe hacer una política de reintentos cuando falta Retry-After?

Leer la señal propia de la plataforma y separar los topes de los límites de tasa antes de reintentar nada.

Si una respuesta sí lleva Retry-After, respétala. Si no, toma la espera de la plataforma: x-rate-limit-reset menos la hora actual para X, estimated_time_to_regain_access en minutos para los límites business use case de Meta, la siguiente medianoche UTC para LinkedIn y al menos un minuto para la ventana deslizante de TikTok. Para los errores a nivel de aplicación de Meta, detén la cola y comprueba X-App-Usage antes de reanudar.

Después, desvía los errores que parecen límites de tasa pero no lo son: spam_risk_too_many_posts de TikTok, quotaExceeded y uploadLimitExceeded de YouTube, y el tope de uso de X. Son techos diarios, y un backoff medido en segundos no despejará ninguno.

Orden de decisión para reintentar
1
Clasifica el error. Los topes diarios, como spam_risk_too_many_posts de TikTok, quotaExceeded y uploadLimitExceeded de YouTube y el tope de uso de X, no se resuelven con backoff. No los reintentes.
2
Busca Retry-After. Si la respuesta lo incluye, respétalo.
3
Lee la señal de la plataforma. x-rate-limit-reset menos la hora actual en X, estimated_time_to_regain_access en minutos en Meta, la próxima medianoche UTC en LinkedIn y al menos un minuto en TikTok.
4
Revisa los errores de Meta a nivel de app. Detén la cola y revisa X-App-Usage antes de reanudar.
Separar los topes de los límites de tasa va primero, porque un backoff de segundos solo resuelve los límites de tasa.

Preguntas frecuentes

¿Es obligatoria la cabecera Retry-After en una respuesta 429?

No. El RFC 6585 dice que una respuesta 429 "MAY include a Retry-After header indicating how long to wait before making a new request." Solo la explicación de la situación es un SHOULD.

AdaptlyPost
AdaptlyPost

Empieza tu prueba gratis de 7 días

Analíticas multiplataforma

Bandeja Social

Asistente con IA

¿Qué formatos puede usar una cabecera Retry-After?

El RFC 9110 permite una fecha HTTP, como Fri, 31 Dec 1999 23:59:59 GMT, o un número entero no negativo de segundos, como 120. Los parsers deben manejar ambos.

¿La API de X envía Retry-After en un 429?

Las páginas de límites de tasa y de errores de X no lo documentan. Te remiten a x-rate-limit-reset, una marca de tiempo Unix que indica cuándo se reinicia la ventana, y el código de ejemplo de X espera al menos 60 segundos.

¿Qué estado HTTP devuelve la Facebook Graph API ante un límite de tasa?

Meta no lo indica ni en la referencia de limitación de tasa ni en la guía de gestión de errores. Las dos identifican los límites de tasa por el campo code del cuerpo de error JSON: 4, 17, 32, 613, o 80001 para los límites business use case de Páginas.

¿La YouTube Data API devuelve 429 cuando se agota la cuota?

No. Una cuota agotada devuelve 403 con el motivo quotaExceeded. El único 429 de la referencia de errores de YouTube es uploadRateLimitExceeded en las subidas de miniaturas.

¿Cuándo se reinicia un límite de tasa de la API de LinkedIn?

A medianoche UTC. La página de limitación de tasa de LinkedIn dice que los límites cubren un periodo de 24 horas y que "reset at midnight UTC every day." LinkedIn no documenta ninguna cabecera de reinicio, así que calcula la espera a partir del reloj.

¿Cómo convierto x-rate-limit-reset en un tiempo de espera?

Resta la hora Unix actual, porque es una marca de tiempo absoluta y no un retraso. El valor de ejemplo de X es 1705420800, y pasado como segundos a una función sleep, el worker duerme unos 54 años. El código de ejemplo de X espera max(reset_time - time.time(), 60), es decir, nunca menos de un minuto.

¿Debo reintentar un error quotaExceeded de YouTube?

Ese mismo día, no. Un quotaExceeded (403) significa que la cuota diaria se agotó, y toda solicitud, incluso las no válidas, cuesta al menos un punto, así que los reintentos solo gastan más cuota. Subir el techo es un trámite de solicitud.

¿Qué devuelve TikTok cuando se alcanza el tope diario de publicaciones?

Un 403 con el código de error spam_risk_too_many_posts, descrito como "El tope diario de publicaciones de la API se alcanzó para el usuario actual." No es un 429, así que un bucle de reintentos basado en 429 nunca lo ve. Reintentar todos los 4xx solo machaca el endpoint sin ganar nada.

¿Debo seguir reintentando cuando Meta devuelve el código de error 4 o 17?

Detén las llamadas. La referencia de rate limiting de Meta advierte de que seguir llamando aumenta el contador de llamadas, lo que alarga el tiempo hasta que las llamadas vuelvan a funcionar. La guía de gestión de errores dice que hay que esperar y reintentar, así que las dos páginas se contradicen y la regla más estricta es la más segura.

¿Te resultó útil este artículo?

¡Cuéntanos qué te parece!

Vernos más en Google

Un clic marca AdaptlyPost como fuente preferida y nuestros artículos aparecen más arriba en tus Noticias destacadas, el modo IA y los resúmenes con IA.

Antes de irte...

AdaptlyPost

AdaptlyPost

Programa tu contenido en todas las plataformas

Gestiona todas tus cuentas de redes sociales en un solo lugar con AdaptlyPost.

Analíticas multiplataforma

Bandeja Social

Asistente con IA

Términos relacionados del glosario

Artículos Relacionados