Funciones definidas por el usuario de Amazon Aurora PostgreSQL para Amazon Location Service - Amazon Location Service

Las traducciones son generadas a través de traducción automática. En caso de conflicto entre la traducción y la version original de inglés, prevalecerá la version en inglés.

Funciones definidas por el usuario de Amazon Aurora PostgreSQL para Amazon Location Service

Puede utilizar Amazon Location Service para trabajar con las coordenadas y direcciones almacenadas en tablas de bases de datos para limpiar y enriquecer sus datos geoespaciales.

Por ejemplo:

  • Puede utilizar la geocodificación para convertir las direcciones en coordenadas a fin de normalizar y rellenar los huecos en los datos de las direcciones almacenadas en una tabla de base de datos.

  • Puede geocodificar las direcciones para obtener sus posiciones y utilizar las coordenadas con funciones espaciales de la base de datos, como una función que muestre las filas de un área específica.

  • Puede utilizar datos enriquecidos para generar informes automatizados, como generar un informe automatizado que ilustre todos los dispositivos de un área determinada, o un informe automatizado para machine learning que ilustre las áreas con tasas de error más altas al enviar actualizaciones de ubicación.

En este tutorial se muestra cómo formatear y enriquecer las direcciones almacenadas en una tabla de base de datos de Amazon Aurora PostgreSQL mediante Amazon Location Service.

  • Amazon Aurora PostgreSQL: un motor de base de datos relacional completamente administrado, compatible con MySQL y PostgreSQL, que genera hasta cinco veces el rendimiento de MySQL y hasta tres veces el rendimiento de PostgreSQL sin cambiar la mayoría de sus aplicaciones existentes. Para obtener más información, consulte la sección ¿Qué es Amazon Aurora? en la Guía del usuario de Amazon Aurora.

importante

La aplicación resultante de este tutorial utiliza un índice de ubicación que almacena resultados de geocodificación. Para obtener información sobre los cargos aplicables por almacenar resultados de geocodificación, consulte los precios de Amazon Location Service.

El código de muestra está disponible en el repositorio de muestras de Amazon Location Service GitHub, que incluye una AWS CloudFormation plantilla.

Información general

La arquitectura incluye las siguientes integraciones:

  • Esta solución utiliza un recurso de índice de ubicación de Amazon Location para admitir las consultas de geocodificación que utilizan la operación SearchPlaceIndexForText.

  • AWS Lambda utiliza un Lambda de Python que geocodifica las direcciones cuando una política de IAM da permiso para permitir que AWS Lambda llame a la operación de geocodificación de Amazon Location, SearchPlaceIndexForText.

  • Conceda permiso a Amazon Aurora PostgreSQL para invocar la función de Lambda de geocodificación mediante una función SQL definida por el usuario.

Requisitos previos

Antes de empezar, necesita los siguientes requisitos previos:

  • Un clúster de Amazon Aurora PostgreSQL. Para obtener más información sobre Crear un clúster de base de datos de Amazon Aurora en la Guía del usuario de Amazon Aurora.

    nota

    Si su clúster de Amazon Aurora no está disponible de forma pública, también debe configurar Amazon Aurora para conectarse a AWS Lambda en una nube privada virtual (VPC) de su cuenta de AWS. Para obtener más información, consulte Conceder a Amazon Aurora PostgreSQL acceso a AWS Lambda.

  • Una herramienta de desarrollo de SQL para conectarse al clúster de Amazon Aurora PostgreSQL.

Inicio rápido

Como alternativa a seguir los pasos de este tutorial, puede lanzar una pila rápida para implementar una función de AWS Lambda que admita la operación SearchPlaceIndexForText de Amazon Location. Esto configura automáticamente su cuenta de AWS para permitir que Amazon Aurora llame a AWS Lambda.

Una vez que haya configurado su cuenta de AWS, tendrá que:

Crear un recurso de índice de ubicación

Comience creando un recurso de índice de ubicación para admitir las consultas de geocodificación.

  1. Abra la consola de Amazon Location Service en https://console.aws.amazon.com/location/.

  2. En el panel de navegación izquierdo, elija Índices de lugares.

  3. Complete las casillas siguientes:

    • Nombre: introduzca un nombre para el recurso de índice de ubicación. Por ejemplo, AuroraPlaceIndex. 100 caracteres como máximo. Entre las entradas válidas se incluyen caracteres alfanuméricos, guiones, puntos y guiones bajos.

    • Descripción: escriba una descripción opcional. Por ejemplo, Índice de lugares para Amazon Aurora.

  4. En Proveedores de datos, elija un proveedor de datos disponible para usarlo con su recurso de índice de ubicación. Si no tiene ninguna preferencia, le recomendamos que comience con Esri.

  5. En Opciones de almacenamiento de datos, especifique Sí, se almacenarán los resultados. Esto indica que tiene intención de guardar los resultados de geocodificación en una base de datos.

  6. (Opcional) En Etiquetas, escriba una Clave y un Valor de etiqueta. Esto añade una etiqueta a su nuevo recurso de índice de ubicación. Para obtener más información, consulte Etiquetado de los recursos.

  7. Elija Crear índice de ubicación.

Crear una función de AWS Lambda para geocodificación

Para crear una conexión entre Amazon Aurora PostgreSQL y Amazon Location Service, necesita una función de AWS Lambda que gestione las solicitudes del motor de base de datos. Esta función traduce el evento de la función definida por el usuario de Lambda y llama a la operación SearchPlaceIndexForText de Amazon Location.

Puede crear la función mediante la consola de AWS Lambda, AWS Command Line Interface o las API de AWS Lambda.

Para crear una función definida por el usuario de Lambda con la consola

  1. Abra la consola de AWS Lambda en https://console.aws.amazon.com/lambda/.

  2. En el panel de navegación izquierdo, elija Funciones.

  3. Elija Crear función y asegúrese de que esté seleccionada la opción Autor desde cero.

  4. Complete las casillas siguientes:

    • Nombre de función: introduzca un nombre único para su función. Las entradas válidas incluyen caracteres alfanuméricos, guiones y guiones bajos sin espacios. Por ejemplo, AuroraGeocoder.

    • Tiempo de ejecución: elija Python 3.8.

  5. Elija Crear función.

  6. Elija la pestaña Código para abrir el editor.

  7. Sobrescriba el código del marcador de posición en lambda_function.py con lo siguiente:

    from os import environ import boto3 from botocore.config import Config # load the place index name from the environment, falling back to a default PLACE_INDEX_NAME = environ.get("PLACE_INDEX_NAME", "AuroraPlaceIndex") location = boto3.client("location", config=Config(user_agent="Amazon Aurora PostgreSQL")) """ This Lambda function receives a payload from Amazon Aurora and translates it to an Amazon Location `SearchPlaceIndex` call and returns the results as-is, to be post-processed by a PL/pgSQL function. """ def lambda_handler(event, context): kwargs = {} if event.get("biasPosition") is not None: kwargs["BiasPosition"] = event["biasPosition"] if event.get("filterBBox") is not None: kwargs["FilterBBox"] = event["filterBBox"] if event.get("filterCountries") is not None: kwargs["FilterCountries"] = event["filterCountries"] if event.get("maxResults") is not None: kwargs["MaxResults"] = event["maxResults"] return location.search_place_index_for_text( IndexName=PLACE_INDEX_NAME, Text=event["text"], **kwargs)["Results"]
  8. Si has asignado a tu índice de sitios un nombre diferente al de AuroraPlaceIndex, crea una variable de entorno con un nombre PLACE_INDEX_NAME para asignar el nombre del recurso a:

    • En la pestaña Configuración, elija Variables de entorno.

    • Seleccione Editar y, a continuación, seleccione agregar variable de entorno.

    • Para Clave: escriba PLACE_INDEX_NAME.

    • Para Valor: escriba el nombre de su recurso de índice de ubicación.

  9. Seleccione Implementar para almacenar la función actualizada.

  10. En el menú desplegable Prueba, elija Configurar evento de prueba.

  11. Elija Crear nuevo evento de prueba.

  12. Introduzca el siguiente evento de prueba:

    { "text": "Baker Beach", "biasPosition": [-122.483, 37.790], "filterCountries": ["USA"] }
  13. Elija Prueba para probar la función de Lambda.

  14. Elija la pestaña Configuración.

  15. En Configuración general: seleccione Permisos.

  16. En Rol de ejecución: elija el Nombre del rol con el hipervínculo para conceder permisos de Amazon Location Service a su función de Lambda.

  17. En la pestaña Permisos: seleccione el menú desplegable Agregar permisos y, a continuación, Crear política insertada.

  18. Seleccione la pestaña JSON.

  19. Agregue la política de IAM siguiente:

    • La siguiente política otorga permiso para enviar SearchPlaceIndexForText al recurso del índice de sitios AuroraPlaceIndex.

      { "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": "geo:SearchPlaceIndexForText", "Resource": "arn:aws:geo:<Region>:<AccountId>:place-index/AuroraPlaceIndex" } ] }
  20. Elija Revisar política.

  21. Escriba un nombre para la política. Por ejemplo, AuroraPlaceIndexReadOnly.

  22. Elija Crear política.

Conceder a Amazon Aurora PostgreSQL acceso a AWS Lambda

Antes de que Amazon Aurora PostgreSQL pueda invocar una función de AWS Lambda, debe conceder permiso de acceso.

Si su clúster de Amazon Aurora PostgreSQL no es de acceso público, primero tendrá que crear un punto de conexión de VPC para AWS Lambda a fin de que Amazon Aurora pueda llamar a su función de Lambda.

Crear un punto de conexión de VPC para AWS Lambda

nota

Este paso solo es obligatorio si no se puede acceder a su clúster de Amazon Aurora PostgreSQL de forma pública.

  1. Abra la Amazon Virtual Private Cloud Console.

  2. En el panel de navegación izquierdo, elija Puntos de conexión.

  3. Seleccione Crear punto de conexión.

  4. En el filtro Nombre de servicio, introduzca «lambda» y, a continuación, seleccione com.amazonaws.<region>.lambda.

  5. Elija la VPC que contiene el clúster de Aurora.

  6. Seleccione una subred para cada zona de disponibilidad.

  7. En el filtro Grupo de seguridad, introduzca «predeterminado» o el nombre del grupo de seguridad al que pertenece su clúster de Aurora y, a continuación, elija el grupo de seguridad.

  8. Seleccione Crear punto de conexión.

Crear una política de IAM para permitir que se invoque su función de AWS Lambda

  1. Abra la consola de IAM.

  2. En el panel de navegación izquierdo, amplíe Administración de acceso para elegir Políticas.

  3. Elija Crear política.

  4. En la pestaña JSON, introduzca la política siguiente:

    • Se muestra un ejemplo de una política de IAM que concede a Amazon Aurora PostgreSQL permiso para invocar la función AuroraGeocoder de AWS Lambda.

    { "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": "lambda:InvokeFunction", "Resource": [ "arn:aws:lambda:<Region>:<AccountId>:function:AuroraGeocoder" ] } ] }
  5. Elija Siguiente: Etiquetas para agregar etiquetas opcionales.

  6. Elija Siguiente: Revisar.

  7. Revise su política e introduzca los siguientes detalles para la política:

    • Nombre: utilice caracteres alfanuméricos y ‘+=,.@-_’. 128 caracteres como máximo. Por ejemplo, AuroraGeocoderInvoke.

    • Descripción: escriba una descripción opcional. Utilice caracteres alfanuméricos y '+=, .@-_'. 1000 caracteres como máximo.

  8. Elija Crear política. Anote el ARN de esta política, que utiliza para asociar la política a un rol de IAM.

Crear un rol de IAM para conceder permiso a Amazon Relational Database Service (Amazon RDS)

Al crear un rol de IAM, Amazon Aurora PostgreSQL puede asumir el rol en su nombre para acceder a su función de Lambda. Para obtener más información, vea Crear un rol para delegar permisos a un usuario de IAM en Guía del usuario de IAM.

El siguiente ejemplo es un AWS CLI comando que crea un rol llamado AuroraGeocoderInvokeRole:

aws iam create-role --role-name rds-lambda-role --assume-role-policy-document '{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "Service": "rds.amazonaws.com" }, "Action": "sts:AssumeRole" } ] }'

Adjuntar su política de IAM al rol de IAM

Cuando tenga un rol de IAM, asocie la política de IAM que creó.

El siguiente ejemplo es un AWS CLI comando que asocia la política AuroraGeocoderInvokeal rol AuroraGeocoderInvokeRole.

aws iam attach-role-policy --policy-arn AuroraGeocoderInvoke --role-name AuroraGeocoderInvokeRole

Agregar el rol de IAM a un clúster de base de datos de Amazon Aurora

El siguiente ejemplo es un AWS CLI comando para añadir una función de IAM a un Amazon Aurora PostgreSQL clúster de base de datos denominado. MyAuroraCluster

aws rds add-role-to-db-cluster \ --db-cluster-identifier MyAuroraCluster \ --feature-name Lambda \ --role-arn AuroraGeocoderInvokeRole \ --region your-region

Invocar la función de AWS Lambda

Tras conceder permiso a Amazon Aurora PostgreSQL para invocar la función de Lambda de geocodificación, puede crear una función de Amazon Aurora PostgreSQL definida por el usuario para invocar la función de AWS Lambda de geocodificación. Para obtener más información, consulte Invocación de una función de AWS Lambda desde un clúster de bases de datos de Amazon Aurora PostgreSQL en la Guía del usuario de Amazon Aurora.

Instalar las extensiones necesarias de PostgreSQL

Para instalar las extensiones aws_lambda y aws _commons de PostgreSQL necesarias, consulte Información general sobre el uso de una función de Lambda en la Guía del usuario de Amazon Aurora.

CREATE EXTENSION IF NOT EXISTS aws_lambda CASCADE;

Instalar las extensiones necesarias de PostGIS

PostGIS es una extensión de PostgreSQL para almacenar y administrar información espacial. Para obtener más información, consulte Trabajo con la extensión de PostGIS en la Guía del usuario de Amazon Relational Database Service.

CREATE EXTENSION IF NOT EXISTS postgis;

Crear una función de SQL definida por el usuario que invoque la función de Lambda

En un editor de SQL, cree una nueva función definida por el usuario f_SearchPlaceIndexForText para invocarla: AuroraGeocoder

CREATE OR REPLACE FUNCTION f_SearchPlaceIndexForText( text text, bias_position geometry(Point, 4326) DEFAULT NULL, filter_bbox box2d DEFAULT NULL, filter_countries text[] DEFAULT NULL, max_results int DEFAULT 1 ) RETURNS TABLE ( label text, address_number text, street text, municipality text, postal_code text, sub_region text, region text, country text, geom geometry(Point, 4326) ) LANGUAGE plpgsql IMMUTABLE AS $function$ begin RETURN QUERY WITH results AS ( SELECT json_array_elements(payload) rsp FROM aws_lambda.invoke( aws_commons.create_lambda_function_arn('AuroraGeocoder'), json_build_object( 'text', text, 'biasPosition', CASE WHEN bias_position IS NOT NULL THEN array_to_json(ARRAY[ST_X(bias_position), ST_Y(bias_position)]) END, 'filterBBox', CASE WHEN filter_bbox IS NOT NULL THEN array_to_json(ARRAY[ST_XMin(filter_bbox), ST_YMin(filter_bbox), ST_XMax(filter_bbox), ST_YMax(filter_bbox)]) END, 'filterCountries', filter_countries, 'maxResults', max_results ) ) ) SELECT rsp->'Place'->>'Label' AS label, rsp->'Place'->>'AddressNumber' AS address_number, rsp->'Place'->>'Street' AS street, rsp->'Place'->>'Municipality' AS municipality, rsp->'Place'->>'PostalCode' AS postal_code, rsp->'Place'->>'SubRegion' AS sub_region, rsp->'Place'->>'Region' AS region, rsp->'Place'->>'Country' AS country, ST_GeomFromGeoJSON( json_build_object( 'type', 'Point', 'coordinates', rsp->'Place'->'Geometry'->'Point' ) ) geom FROM results; end; $function$;

Llamar a la función de SQL para geocodificar desde Aurora

Al ejecutar la instrucción SQL, se invoca la AuroraGeocoderfunción Lambda, que toma los registros de direcciones de la tabla de la base de datos de la base de datos y Amazon Aurora PostgreSQL los geocodifica mediante un recurso de índice de lugares.

nota

Amazon Aurora PostgreSQL invoca la función de Lambda para cada llamada a la función de SQL definida por el usuario.

Si está geocodificando 50 filas, Amazon Aurora PostgreSQL invoca la función de Lambda 50 veces. Una invocación para cada fila.

La siguiente función f_SearchPlaceIndexForText SQL realiza solicitudes a la SearchPlaceIndexForText API de Amazon Location a través de la función AuroraGeocoderLambda. La función devuelve una columna de geom que es una geometría de PostGIS, que ST_AsText(geom) convierte en texto.

SELECT *, ST_AsText(geom) FROM f_SearchPlaceIndexForText('Vancouver, BC');

De forma predeterminada, el retorno contendrá una fila. Para solicitar filas adicionales, hasta el límite de MaxResults, ejecute la siguiente instrucción de SQL proporcionando un BiasPosition y limitándolo a los resultados en Canadá.

SELECT * FROM f_SearchPlaceIndexForText('Mount Pleasant', ST_MakePoint(-123.113, 49.260), null, '{"CAN"}', 5);

Para filtrar los resultados mediante un cuadro delimitador, pase un Box2D como filter_bbox:

  • FilterBBox: filtra los resultados devolviendo los lugares dentro de un cuadro delimitador. Se trata de un parámetro opcional.

SELECT * FROM f_SearchPlaceIndexForText('Mount Pleasant', null, 'BOX(-139.06 48.30, -114.03 60.00)'::box2d, '{"CAN"}', 5);

Para obtener más información sobre los tipos y funciones de PostGIS, consulte la Referencia de PostGIS.

Enriquecer una base de datos que contiene datos de direcciones

Puede crear una dirección formateada y, al mismo tiempo, normalizarla y geocodificarla mediante la operación SearchPlaceIndexForTextde Amazon Location dada una tabla de base de datos con los siguientes datos divididos en las siguientes columnas:

  • id

  • address

  • city

  • state

  • zip

WITH source_data AS ( SELECT id, address || ', ' || city || ', ' || state || ', ' || zip AS formatted_address FROM addresses ), geocoded_data AS ( SELECT *, (f_SearchPlaceIndexForText(formatted_address)).* FROM source_data ) SELECT id, formatted_address, label normalized_address, ST_Y(geom) latitude, ST_X(geom) longitude FROM geocoded_data -- limit the number of rows that will be geocoded; remove this to geocode the entire table LIMIT 1;

En el siguiente ejemplo, se ilustra una fila de tabla de datos resultante:

id | formatted_address | normalized_address | latitude | longitude ----+--------------------------------+--------------------------------------------+------------------+------------------- 42 | 123 Anytown Ave N, Seattle, WA | 123 Anytown Ave N, Seattle, WA, 12345, USA | 47.6223000127926 | -122.336745971039 (1 row)

Actualizar la tabla de la base de datos y rellenar las columnas

En el siguiente ejemplo, se actualiza la tabla y se rellenan las columnas con los resultados de las consultas de SearchPlaceIndexForText:

WITH source_data AS ( -- select rows that have not been geocoded and created a formatted address for each SELECT id, address || ', ' || city || ', ' || state || ', ' || zip AS formatted_address FROM addresses WHERE label IS NULL -- limit the number of rows that will be geocoded; remove this to geocode the entire table LIMIT 1 ), geocoded_data AS ( -- geocode each row and keep it linked to the source's ID SELECT id, (f_SearchPlaceIndexForText(formatted_address)).* FROM source_data ) UPDATE addresses -- populate columns SET normalized_address = geocoded_data.label, latitude = ST_Y(geocoded_data.geom), longitude = ST_X(geocoded_data.geom) FROM geocoded_data -- ensure that rows match WHERE addresses.id = geocoded_data.id;

Siguientes pasos

El código de muestra está disponible en el repositorio de muestras de Amazon Location Service GitHub, que incluye una AWS CloudFormation plantilla.