Principiante7 min de lectura

DynamoDB JSON y clasificación

La primera vez que lees datos sin procesar del DynamoDB API, no se parece al JSON. usted ingresa. Un objeto simple como {"status": "open", "priority": 3} regresa como {"status": {"S": "open"}, "priority": {"N": "3"}}. Cada valor está envuelto en un objeto de una clave que nombra su tipo. Ese envoltorio es DynamoDB JSON, y la conversión a y de ahí se llama marshalling.

Esa envoltura es la forma en que DynamoDB mantiene los tipos sin ambigüedades en el cable. pero se tropieza cualquiera que espere JSON, y escribirlo a mano es propenso a errores.

¿Qué es DynamoDB JSON?

DynamoDB JSON es el formato de cable con etiqueta tipográfica que utiliza DynamoDB, donde cada valor está envuelto en un objeto de una clave que nombra su tipo: {"S": "open"} para una cadena, {"N": "3"} para un número. Convertir JSON a él (y viceversa) se llama marshalling. Mantiene los tipos sin ambigüedades, ya que JSON no puede expresar conjuntos o binarios, y debido a que DynamoDB los números viajan por el cable como cadenas, un 3 sin etiquetar sería ambiguo.

  • DynamoDB JSON etiqueta cada valor con su tipo{"S": "..."} para una cadena, {"N": "..."} para un número, y así sucesivamente.
  • Marshalling = simple JSON → DynamoDB JSON. Desclasificación = al revés.
  • Los números son hilos en el cable{"N": "3"}, no {"N": 3} — para preservar Precisión.
  • Las etiquetas de tipo son el sistema de tipo de datos con el que ya modelas: S, N, B, BOOL, NULO, L, M, SS, NS, BS.
  • No lo escribas a mano. El documento del SDK client (o un convertidor) reúne usted; hágalo manualmente solo al depurar o crear expresiones.

El problema: simple JSON no es suficiente

JSON tiene exactamente tres tipos escalares (cadena, número, booleano) más nulo, matrices y objetos. DynamoDB tiene más: binario y tres tipos de conjuntos (conjunto de cadenas, conjunto de números, conjunto binario) que JSON no puede expresar en absoluto. Y porque DynamoDB números viajan por el cable como cadenas, un 3 sin etiquetar sería ambiguo; además, JSON no puede distinguir una lista de una conjunto.

Por lo tanto, DynamoDB no puede simplemente almacenar su JSON tal como está: necesita indicar el tipo exacto de cada valor. explícitamente. El tipo descriptor es cómo lo hace, sin pérdidas, en cada solicitud y respuesta.

Cómo funciona la codificación

Cada valor de atributo se convierte en un objeto de una sola clave cuya clave es un tipo descriptor:

DescriptorTipoEjemplo
SCadena{"S": "open"}
NNúmero (como una cadena){"N": "3"}
BBinario{"B": "dGV4dA=="}
BOOLBooleano{"BOOL": true}
NULLNulo{"NULL": true}
LLista{"L": [{"S": "a"}, {"N": "1"}]}
MMapa{"M": {"k": {"S": "v"}}}
SS / NS / BSCadena/Número/Conjunto binario{"SS": ["a", "b"]}

Las listas y los mapas anidan los mismos descriptores hasta el final, por lo que un elemento profundamente estructurado queda profundamente envuelto. Los números viajan en el cable como cuerdas a propósito: permite DynamoDB conserva sus 38 dígitos completos de precisión numérica que un número JSON (un IEEE-754 doble, ~15–17 dígitos significativos) se redondearía silenciosamente. Estos son los mismos tipos de datos con los que modelas; DynamoDB JSON es solo su explícito formulario en el cable, definido en el AWS nivel bajo API referencia.

Ejemplo resuelto: una entrada del registro de auditoría

Simple JSON escribirías en tu aplicación:

{
  "actor": "u-204",
  "action": "ticket.close",
  "ticketId": 8842,
  "tags": ["billing", "urgent"],
  "redacted": false
}

Marshalled a DynamoDB JSON para el API:

{
  "actor": {"S": "u-204"},
  "action": {"S": "ticket.close"},
  "ticketId": {"N": "8842"},
  "tags": {"SS": ["billing", "urgent"]},
  "redacted": {"BOOL": false}
}

Tenga en cuenta las opciones detrás de este elemento: ticketId se convirtió en N con un valor de cadena; tags como conjunto de cadenas (SS), no una lista, es una elección de modelado hecha a mano: una El convertidor genérico alimentado con JSON emite L, porque se solicita una matriz JSON y puede repita, mientras SS deduplica y está desordenado. Si tags debe ser SS o L es un llamada de modelado que el convertidor no puede hacer por usted, que es exactamente la razón por la cual comprender el la codificación importa.

Convirtiendo en DynoTable

Rara vez será necesario leer o escribir esto a mano. Pegue JSON en el DynamoDB JSON convertidor para ordenarlo (y viceversa), y Cuando estás armando una solicitud, el DynamoDB generador de expresiones emite la expresión correcta marshalled mapa atributo-valor sologside la expresión. En la propia aplicación, DynoTable muestra los elementos como valores sencillos y legibles y los organiza al escribirlos.

DynoTable muestra un elemento como valores simples, con el DynamoDB JSON disponible.
DynoTable muestra un elemento como valores simples, con el DynamoDB JSON disponible.

Escollos + próximos pasos

  • Los números son cadenas en DynamoDB JSON{"N": "3"}. Citar importa; no lo hagas emitir un número desnudo.
  • Conjuntos versus listas es una decisión de modelado la codificación hace visible - elegir deliberadamente (ver tipos de datos).
  • Prefiera el documento SDK client a la clasificación manual en el código de la aplicación; manual de reserva DynamoDB JSON para depuración y expresiones.
  • Se permiten cadenas vacías para atributos que no son clave (desde 2020), pero aún se rechazan para claves de tabla e índice, y históricamente han disparado herramientas: valide casos extremos.

¿Quiere buscar elementos como valores simples en lugar de decodificar etiquetas de tipo a simple vista? Descarga DynoTable y trabaja con tus datos directamente.

Nivel bajo client vs documento client

El AWS SDK ofrece dos capas:

CapaForma de entrada¿Quién dirige?
@aws-sdk/client-dynamodb (nivel bajo)DynamoDB JSON AttributeValue mapasTu código o ayudante
@aws-sdk/lib-dynamodb (documento)Objetos JS simplesSDK en enviar/recibir

El código de aplicación debe ser el documento predeterminado client para PutItem/GetItem. Busque mapas de bajo nivel cuando cree a mano actualizar expresiones o cuando una biblioteca espera valores de atributos escritos.

Los valores de los atributos de expresión también son marshalled

ConditionExpression, UpdateExpression y FilterExpression marcadores de posición (:val, :inc) se asigna a marshalled valores en ExpressionAttributeValues:

":status": {"S": "open"}
":count": {"N": "1"}

Una falta de coincidencia: enviar "open" sin el contenedor S en el nivel client de bajo nivel. devuelve ValidationException. el generador de expresiones emite el mapa sologside la cadena de expresión para que los marcadores de posición y los tipos permanezcan alineados.

Atributo nombres que chocan con reservado words uso ExpressionAttributeNames (#st) en su lugar; la herramienta de verificación genera el alias mapa listo para pegar.

Sorpresas sin precedentes en las pruebas.

Fallos comunes en las pruebas de marshalling:

  • Conjuntos vacíos — DynamoDB rechaza SS/NS/BS; omitir el atributo en cambio.
  • Flota en N: envía "3.14" como una cadena, no como un número JSON en el cable.
  • Binario en NodeUint8Array en el documento client; base64 en bruto JSON.
  • Atributos no definidos — documento clitiras de datos undefined; client de bajo nivel puede enviar payloads no válidos.

Cuando un Lambda registra API respuestas sin procesar, pegue un elemento en el DynamoDB JSON convertidor a formato simple legible JSON antes de diferenciarse de los partidos.

Tamaño del impacto del etiquetado

Cada contenedor de tipo agrega bytes. Un objeto plano JSON marshalled campo a campo crece aproximadamente entre un 30% y un 40% en el cable, dependiendo de los nombres de los atributos, que la inflación alimenta tamaño del elemento y RCU/WCU redondeo. Mapas grandes con nombres de atributos cortos se amortizan los gastos generales; pequeñas banderas booleanas todavía pagan por sus nombres clave más {"BOOL":true}.

Antes de cargar de forma masiva marshalled elementos, verifique el total de bytes en el calculadora de tamaño de artículo para escribir por lotes no cruza inesperadamente el límite de solicitud de 16 MB.

Las dos vistas de DynoTable

El editor de elementos sigue ordenando cosas invisibles día a día: usted edita valores simples, y compromete al mariscal al enviarlo. Al depurar un elemento de producción copiado de Registros de CloudWatch, cambie a DynamoDB JSON para ver las etiquetas exactas y, luego, regrese a Normal JSON para realizar ediciones. Las acciones de exportación copian cualquiera de las representaciones de los tickets y casos de prueba.

Actualizado