

# Uso del formato JSON en AWS Glue
<a name="aws-glue-programming-etl-format-json-home"></a>

AWS Glue recupera datos de fuentes y escribe datos en destinos almacenados y transportados en varios formatos de datos. Si los datos se almacenan o se transportan en formato de datos JSON, este documento presenta las características disponibles para utilizar los datos en AWS Glue.

AWS Glue admite el uso del formato JSON. Este formato representa estructuras de datos con forma consistente, pero con contenido flexible, que no están basadas en filas o columnas. JSON está definido por estándares paralelos emitidos por varias autoridades, una de las cuales es ECMA-404. Para obtener una introducción al formato por parte de un origen al que normalmente se hace referencia, consulte [Introducción a JSON](https://www.json.org/).

Puede utilizar AWS Glue para leer archivos JSON de Amazon S3, así como archivos JSON comprimidos con `bzip` y `gzip`. Debe configurar el comportamiento de compresión en el [Parámetros de conexión S3](aws-glue-programming-etl-connect-s3-home.md#aws-glue-programming-etl-connect-s3) en lugar de en la configuración que se describe en esta página. 


| Lectura | Escritura | Lectura de streaming | Grupo de archivos pequeños | Marcadores de trabajo | 
| --- | --- | --- | --- | --- | 
| Compatible | Soportado | Soportado | Soportado | Compatible | 

## Ejemplo: leer archivos o carpetas JSON de S3
<a name="aws-glue-programming-etl-format-json-read"></a>

**Requisitos previos:** necesitará las rutas de S3 (`s3path`) de las carpetas o los archivos JSON que desee leer. 

**Configuración:** en las opciones de la función, especifique `format="json"`. En sus `connection_options`, utilice la clave `paths` para especificar su `s3path`. Puede modificar aún más la manera en que la operación de lectura atravesará S3 en las opciones de conexión; consulte [Referencia de opción de conexión de Amazon S3](aws-glue-programming-etl-connect-s3-home.md#aws-glue-programming-etl-connect-s3) para obtener más detalles. Puede configurar la manera en que el lector interpreta los archivos JSON en sus `format_options`. Para obtener más información, consulte [Referencia de configuración de JSON](#aws-glue-programming-etl-format-json-reference). 

 El siguiente script de ETL de AWS Glue muestra el proceso de lectura de archivos o carpetas JSON de S3: 

------
#### [ Python ]

Para este ejemplo, use el método [create\$1dynamic\$1frame.from\$1options](aws-glue-api-crawler-pyspark-extensions-glue-context.md#aws-glue-api-crawler-pyspark-extensions-glue-context-create_dynamic_frame_from_options).

```
# Example: Read JSON from S3
# For show, we handle a nested JSON file that we can limit with the JsonPath parameter
# For show, we also handle a JSON where a single entry spans multiple lines
# Consider whether optimizePerformance is right for your workflow.

from pyspark.context import SparkContext
from awsglue.context import GlueContext

sc = SparkContext.getOrCreate()
glueContext = GlueContext(sc)
spark = glueContext.spark_session

dynamicFrame = glueContext.create_dynamic_frame.from_options(
    connection_type="s3",
    connection_options={"paths": ["s3://s3path"]},
    format="json",
    format_options={
        "jsonPath": "$.id",
        "multiline": True,
        # "optimizePerformance": True, -> not compatible with jsonPath, multiline
    }
)
```

También puede usar DataFrames en un script (`pyspark.sql.DataFrame`).

```
dataFrame = spark.read\
    .option("multiline", "true")\
    .json("s3://s3path")
```

------
#### [ Scala ]

Para este ejemplo, use la operación [getSourceWithFormat](glue-etl-scala-apis-glue-gluecontext.md#glue-etl-scala-apis-glue-gluecontext-defs-getSourceWithFormat).

```
// Example: Read JSON from S3
// For show, we handle a nested JSON file that we can limit with the JsonPath parameter
// For show, we also handle a JSON where a single entry spans multiple lines
// Consider whether optimizePerformance is right for your workflow.

import com.amazonaws.services.glue.util.JsonOptions
import com.amazonaws.services.glue.{DynamicFrame, GlueContext}
import org.apache.spark.SparkContext

object GlueApp {
  def main(sysArgs: Array[String]): Unit = {
    val spark: SparkContext = new SparkContext()
    val glueContext: GlueContext = new GlueContext(spark)

    val dynamicFrame = glueContext.getSourceWithFormat(
      formatOptions=JsonOptions("""{"jsonPath": "$.id", "multiline": true, "optimizePerformance":false}"""),
      connectionType="s3",
      format="json",
      options=JsonOptions("""{"paths": ["s3://s3path"], "recurse": true}""")
    ).getDynamicFrame()
  }
}
```

También puede usar DataFrames en un script (`pyspark.sql.DataFrame`).

```
val dataFrame = spark.read
    .option("multiline", "true")
    .json("s3://s3path")
```

------

## Ejemplo: escribir archivos y carpetas JSON en S3
<a name="aws-glue-programming-etl-format-json-write"></a>

**Requisitos previos:** necesitará un DataFrame inicializado (`dataFrame`) o un DynamicFrame (`dynamicFrame`). También necesitará la ruta de salida S3 prevista, `s3path`. 

**Configuración:** en las opciones de la función, especifique `format="json"`. En sus `connection_options`, utilice la clave `paths` para especificar `s3path`. Puede modificar aún más la forma en que el escritor interactúa con S3 en las `connection_options`. Para obtener más información, consulte Opciones de formato de datos para entradas y salidas de ETL en AWS Glue: [Referencia de opción de conexión de Amazon S3](aws-glue-programming-etl-connect-s3-home.md#aws-glue-programming-etl-connect-s3). Puede configurar la forma en que el escritor interpreta los archivos JSON en sus `format_options`. Para obtener más información, consulte [Referencia de configuración de JSON](#aws-glue-programming-etl-format-json-reference). 

El siguiente script de ETL de AWS Glue muestra el proceso de escritura de archivos o carpetas JSON de S3:

------
#### [ Python ]

Para este ejemplo, use el método [write\$1dynamic\$1frame.from\$1options](aws-glue-api-crawler-pyspark-extensions-glue-context.md#aws-glue-api-crawler-pyspark-extensions-glue-context-write_dynamic_frame_from_options).

```
# Example: Write JSON to S3

from pyspark.context import SparkContext
from awsglue.context import GlueContext

sc = SparkContext.getOrCreate()
glueContext = GlueContext(sc)

glueContext.write_dynamic_frame.from_options(
    frame=dynamicFrame,
    connection_type="s3",
    connection_options={"path": "s3://s3path"},
    format="json"
)
```

También puede usar DataFrames en un script (`pyspark.sql.DataFrame`).

```
df.write.json("s3://s3path/")
```

------
#### [ Scala ]

Para este ejemplo, use el método [getSinkWithFormat](glue-etl-scala-apis-glue-gluecontext.md#glue-etl-scala-apis-glue-gluecontext-defs-getSinkWithFormat).

```
// Example: Write JSON to S3

import com.amazonaws.services.glue.util.JsonOptions
import com.amazonaws.services.glue.{DynamicFrame, GlueContext}
import org.apache.spark.SparkContext

object GlueApp {
  def main(sysArgs: Array[String]): Unit = {
    val spark: SparkContext = new SparkContext()
    val glueContext: GlueContext = new GlueContext(spark)

    glueContext.getSinkWithFormat(
        connectionType="s3",
        options=JsonOptions("""{"path": "s3://s3path"}"""),
        format="json"
    ).writeDynamicFrame(dynamicFrame)
  }
}
```

También puede usar DataFrames en un script (`pyspark.sql.DataFrame`).

```
df.write.json("s3://s3path")
```

------

## Referencia de configuración de JSON
<a name="aws-glue-programming-etl-format-json-reference"></a>

Puede utilizar los siguientes valores `format_options` con `format="json"`:
+ `jsonPath`: una expresión [JsonPath](https://github.com/json-path/JsonPath) que identifica un objeto que se leerá en los registros. Esto resulta particularmente útil cuando un archivo contiene registros anidados en una matriz exterior. Por ejemplo, la siguiente expresión JsonPath se dirige al campo `id` de un objeto JSON.

  ```
  format="json", format_options={"jsonPath": "$.id"}
  ```
+ `multiline`: un valor booleano que especifica si un solo registro puede abarcar varias líneas. Esto puede suceder cuando un campo contiene un carácter de nueva línea entre comillas. Debe configurar esta opción en `"true"` si un registro abarca varias líneas. El valor predeterminado es `"false"`, que permite una división de archivo más dinámica durante el análisis.
+ `optimizePerformance`: un valor booleano que especifica si se debe utilizar el lector SIMD JSON avanzado junto con los formatos de memoria en columnas basados en Apache Arrow. Solo se encuentra disponible en AWS Glue 3.0. No compatible con `multiline` ni `jsonPath`. Proporcionar cualquiera de esas opciones indicará a AWS Glue que regrese al lector estándar.
+ `withSchema`— Un valor de cadena que especifica un esquema de tabla en el formato descrito en [Especifique manualmente el esquema XML](aws-glue-programming-etl-format-xml-home.md#aws-glue-programming-etl-format-xml-withschema). Solo se usa con `optimizePerformance` al leer desde conexiones que no son de catálogo.

## Uso del lector SIMD JSON vectorizado con formato en columnas de Apache Arrow
<a name="aws-glue-programming-etl-format-simd-json-reader"></a>

AWS Glue versión 3.0 agrega un lector vectorizado para datos JSON. Funciona dos veces más rápido en ciertas condiciones, en comparación con el lector estándar. Este lector viene con ciertas limitaciones documentadas en esta sección que los usuarios deben tener en cuenta antes de usarlo.

Para usar el lector optimizado, configure `"optimizePerformance"` como True en `format_options` o propiedad de tabla. También deberá proporcionar `withSchema` a menos que esté leyendo del catálogo. `withSchema` espera una entrada como se describe en [Especifique manualmente el esquema XML](aws-glue-programming-etl-format-xml-home.md#aws-glue-programming-etl-format-xml-withschema)

```
// Read from S3 data source        
glueContext.create_dynamic_frame.from_options(
    connection_type = "s3", 
    connection_options = {"paths": ["s3://s3path"]}, 
    format = "json", 
    format_options={
        "optimizePerformance": True,
        "withSchema": SchemaString
        })    
 
// Read from catalog table
glueContext.create_dynamic_frame.from_catalog(
    database = database, 
    table_name = table, 
    additional_options = {
    // The vectorized reader for JSON can read your schema from a catalog table property.
        "optimizePerformance": True,
        })
```

Para obtener más información sobre la creación de un *SchemaString* en la biblioteca de AWS Glue, consulte [Tipos de extensión PySpark](aws-glue-api-crawler-pyspark-extensions-types.md).

**Limitaciones para el lector CSV vectorizado**  
Presenta las siguientes limitaciones:
+ No se admiten elementos JSON con objetos anidados o valores de matriz. Si se proporciona, AWS Glue volverá al lector estándar.
+ Se debe proporcionar un esquema, ya sea del Catálogo o con `withSchema`.
+ No compatible con `multiline` ni `jsonPath`. Proporcionar cualquiera de esas opciones indicará a AWS Glue que regrese al lector estándar.
+ Proporcionar registros de entrada que no coincidan con el esquema de entrada provocará un error en el lector.
+ No se crearán [registros de errores](https://docs.aws.amazon.com/glue/latest/dg/glue-etl-scala-apis-glue-dynamicframe-class.html#glue-etl-scala-apis-glue-dynamicframe-class-defs-errorsAsDynamicFrame).
+ No se admiten archivos JSON con caracteres multibytes (como caracteres japoneses o chinos).