GasFree4you
Ingeniería·8 min de lectura

Error OUT OF ENERGY en TRON: postmortem de nuestro incidente

Un incidente de 31 horas afectó a menos del 5% de los clientes. Explicamos el fallo al transferir en TRON, la fórmula de Energy y la solución aplicada.

de clientes afectados
<5%
duración del incidente
31 horas
blockchain
TRON

Qué ocurrió

Delegábamos suficiente Energy para una transferencia, pero algunos clientes recibían FAILED — OUT OF ENERGY. El incidente duró 31 horas y afectó a menos del 5% de los clientes. En este postmortem de GasFree4you explicamos el cambio en el alquiler, la investigación y el regreso a la retirada automática tras las transferencias.

La gestión del ciclo de delegación es responsabilidad nuestra. Permitir que el cliente finalizara el alquiler no debía dejar su siguiente pedido sin recursos suficientes.

Cómo funcionaba el alquiler de Energy

Delegamos Energy durante una hora. Antes, el servicio la retiraba inmediatamente después de la transferencia; si no se utilizaba, la retiraba al cabo de una hora.

Después dejamos que el cliente solicitara la retirada anticipada cuando terminara la transferencia o ya no necesitara el recurso. Mantuvimos la retirada automática a la hora. El cliente solicita la retirada al servicio: la operación en la cadena la ejecuta el propietario del stake delegado.

Todo parecía funcionar. Sin embargo, un cliente podía mantener abierto el alquiler anterior y pedir uno nuevo para la misma dirección. La superposición de ambos ciclos resultó decisiva.

Había energía. ¿Adónde fue?

Las primeras quejas parecían contradictorias: la delegación era suficiente y el contrato de transferencia seguía consumiendo lo mismo. Creamos un analizador para reconstruir la Energy disponible en cada dirección a lo largo del tiempo.

La escasez era real. La nueva delegación aportaba recursos suficientes, pero después vencía el plazo de una hora del pedido anterior y se ejecutaba su retirada. La Energy disponible caía antes de la siguiente transferencia. Haber entregado suficientes recursos no describía el estado de la dirección en el momento de ejecución.

La secuencia que provocó el error

Lo decisivo era el orden de las operaciones en una misma dirección. El temporizador correspondía al alquiler antiguo, pero afectaba a los recursos compartidos que necesitaba la transferencia nueva.

  1. 01 · Se delega el pedido antiguo A
  2. 02 · Se completa la transferencia; el cliente no solicita retirar A
  3. 03 · Se delega el nuevo pedido B a la misma dirección
  4. 04 · A cumple una hora y se retira automáticamente
  5. 05 · La Energy disponible cae antes de la siguiente transferencia

Qué hace la retirada en java-tron

Sospechamos un error del blockchain y revisamos el código Java de TRON. En UnDelegateResourceActuator.java encontramos el cálculo proporcional de transferUsage. Explicaba un mecanismo que nuestra lógica de pedidos no había contemplado.

La retirada elimina stake que respalda Energy. El límite disminuye en la capacidad correspondiente, mientras que el consumo acumulado solo disminuye en una proporción calculada, limitada por la capacidad del stake retirado. Son magnitudes distintas.

El denominador getAllFrozenBalanceForEnergy() incluye todo el stake que respalda Energy en la dirección: el propio y las delegaciones recibidas, también de otros propietarios. La fórmula no asigna el consumo al pedido antiguo ni reserva recursos intactos para el nuevo.

Java · UnDelegateResourceActuator

transferUsage = (long) (receiverCapsule.getEnergyUsage()
    * ((double) (unDelegateBalance) / receiverCapsule.getAllFrozenBalanceForEnergy()));
transferUsage = min(unDelegateMaxUsage, transferUsage);

Código fuente de TRON: java-tron · UnDelegateResourceActuator.java (ENERGY), java-tron · AccountCapsule.getAllFrozenBalanceForEnergy().

Ejemplo: un pedido nuevo, menos Energy disponible

Tomemos dos delegaciones iguales de 100 unidades ilustrativas de Energy. El pedido antiguo consumió 100 y el nuevo añade otras 100. Antes de retirar, el límite es 200, el consumo registrado es 100 y quedan 100 disponibles.

Retirar la mitad del stake reduce el límite en 100, pero el consumo solo en 50: 100 × 1/2. El límite queda en 100, el consumo en 50 y la disponibilidad en 50. Una llamada posterior que necesite 80 ya no dispone de suficientes recursos delegados.

Energy disponible antes y después de la retirada
Antes de retirar A
100
Después de retirar A
50

La siguiente llamada necesita 80 unidades ilustrativas

Cómo resolvimos el incidente

Volvimos a retirar la energía desde el servicio inmediatamente después de la transferencia. Ya no esperamos a que el cliente lo solicite ni a que venza la hora de alquiler. Para la energía no utilizada se mantiene el plazo de una hora.

Así eliminamos la dependencia de la acción del cliente para cerrar un alquiler utilizado. La integración debe considerar el estado de la dirección y el orden de las operaciones en la cadena.

Qué revisar ante FAILED — OUT OF ENERGY

Si una transferencia USDT TRC-20 u otra llamada a un contrato falla con OUT OF ENERGY, haber comprado energía no basta para explicar el resultado. Importan los recursos disponibles durante la ejecución.

  1. Busca el TxID y el resultado de ejecución en TRONSCAN. Anota la dirección emisora y el orden de los bloques.
  2. Compara delegaciones y retiradas, especialmente alquileres anteriores que vencen antes de la transferencia. Los recursos actuales no sustituyen el historial.
  3. Revisa la Energy disponible, la estimación de la llamada, fee_limit y si hay TRX para cubrir recursos insuficientes. El mismo mensaje de error no demuestra la misma causa.
  4. Envía al soporte el TxID, la dirección y la hora del pedido. No se necesita la clave privada ni la frase semilla.

Código fuente de TRON: TRON · FeeLimit and Energy cost, TRON · Transaction receipt.

La lección para las integraciones con TRON

El incidente puso a prueba nuestro modelo de recursos de TRON. Un pedido independiente en la base de datos del servicio no crea una reserva aislada de Energy en el blockchain.

Nuestra experiencia en pagos y transferencias se construye con investigaciones así: desde el aviso del cliente y la reconstrucción de eventos hasta la lectura del código fuente y el cambio de comportamiento del servicio. Seguiremos compartiendo casos técnicos de TRON en el blog.

Preguntas sobre OUT OF ENERGY

¿Por qué faltaba Energy después de un nuevo alquiler?

En nuestro caso, la delegación antigua se retiraba después de recibir la nueva. Esto reducía los recursos compartidos de la dirección antes de la siguiente transferencia.

¿Se cayó toda la red TRON?

No. Fue un incidente de nuestro servicio que afectó a menos del 5% de los clientes. El código explicó el comportamiento del protocolo; no demuestra un error del blockchain ni una caída de la red.

¿Qué cambió tras la investigación?

El servicio vuelve a retirar Energy después de la transferencia, sin esperar la solicitud del cliente ni el fin de la hora de alquiler.

← Todos los artículos