SCBL007
Descripción general
En este lab, escribirás aplicaciones que utilizan bases de datos de Spanner y las implementarás en Cloud Run Functions y Cloud Run. También instalarás, configurarás y habilitarás el emulador de Spanner para usarlo en entornos de desarrollo.
Objetivos
En este lab, aprenderás a realizar las siguientes tareas:
- Implementar Cloud Run Functions que lean y escriban en bases de datos de Spanner
- Configurar y usar el emulador de Spanner para el desarrollo
- Compilar una API de REST que te permita leer y escribir datos de Spanner
- Implementar una API de REST en Google Cloud Run
Configuración y requisitos
Antes de hacer clic en el botón Comenzar lab
Lee estas instrucciones. Los labs son cronometrados y no se pueden pausar. El cronómetro, que comienza a funcionar cuando haces clic en Comenzar lab, indica por cuánto tiempo tendrás a tu disposición los recursos de Google Cloud.
En este lab práctico, se te proporcionarán credenciales temporales nuevas para acceder a Google Cloud y realizar las actividades en un entorno de nube real, no en uno de simulación o demostración.
Para completar este lab, necesitarás lo siguiente:
- Acceso a un navegador de Internet estándar (se recomienda el navegador Chrome)
Nota: Usa una ventana de navegador privada o de incógnito para ejecutar el lab. Así evitarás cualquier conflicto entre tu cuenta personal y la cuenta de estudiante, lo que podría generar cargos adicionales en tu cuenta personal.
- Tiempo para completar el lab (recuerda que, una vez que comienzas un lab, no puedes pausarlo)
Nota: Si ya tienes un proyecto o una cuenta personal de Google Cloud, no los uses en este lab para evitar cargos adicionales en tu cuenta.
Active Google Cloud Shell
Google Cloud Shell es una máquina virtual que cuenta con herramientas de desarrollo. Ofrece un directorio principal persistente de 5 GB y se ejecuta en Google Cloud.
Google Cloud Shell proporciona acceso de línea de comandos a sus recursos de GCP.
-
En GCP Console, en la barra de herramientas superior derecha, haga clic en el botón Abrir Cloud Shell.

-
Haga clic en Continue (Continuar):

Toma unos minutos aprovisionar y conectarse con el entorno. Cuando está conectado, ya está autenticado y el proyecto está configurado en su PROJECT_ID . Por ejemplo:

gcloud es la herramienta de línea de comandos para Google Cloud Platform. Viene preinstalada en Cloud Shell y es compatible con la función “tab-completion”.
Puede mostrar el nombre de la cuenta activa con este comando:
gcloud auth list
Resultado:
ACTIVE: *
ACCOUNT: student-01-xxxxxxxxxxxx@qwiklabs.net
To set the active account, run:
$ gcloud config set account `ACCOUNT`
Puede mostrar el ID del proyecto con este comando:
gcloud config list project
Resultado:
[core]
project = <project_ID>
Resultado de ejemplo:
[core]
project = qwiklabs-gcp-44776a13dea667a6
Tarea 1. Crea una base de datos con datos de prueba
-
En la barra de título de la consola de Google Cloud, haz clic en Activar Cloud Shell (
). Si se te solicita, haz clic en Continuar. De manera opcional, puedes hacer lo mismo seleccionando la ventana de la consola de Cloud y, luego, presionando la tecla G y, luego, la tecla S.
-
Ejecuta el siguiente comando para habilitar las APIs de Cloud Build, Cloud Run y Event Arc. Si se te solicita autorizar el comando, hazlo.
gcloud services enable cloudbuild.googleapis.com
gcloud services enable run.googleapis.com
gcloud services enable eventarc.googleapis.com
- Ejecuta el siguiente comando Bash con el objetivo de crear un archivo de esquema para la base de datos de mascotas.
mkdir ~/lab-files
cd ~/lab-files
cat > ./pets-db-schema.sql << ENDOFFILE
CREATE TABLE Owners (
OwnerID STRING(36) NOT NULL,
OwnerName STRING(MAX) NOT NULL
) PRIMARY KEY (OwnerID);
CREATE TABLE Pets (
OwnerID STRING(36) NOT NULL,
PetID STRING(MAX) NOT NULL,
PetType STRING(MAX) NOT NULL,
PetName STRING(MAX) NOT NULL,
Breed STRING(MAX) NOT NULL,
) PRIMARY KEY (OwnerID,PetID),
INTERLEAVE IN PARENT Owners ON DELETE CASCADE
ENDOFFILE
- Ejecuta los siguientes comandos para crear una instancia y una base de datos de Spanner.
gcloud spanner instances create test-spanner-instance --config=regional-{{{project_0.default_region|place_holder_text}}} --description="test-spanner-instance" --processing-units=100
gcloud spanner databases create pets-db --instance=test-spanner-instance --database-dialect=GOOGLE_STANDARD_SQL --ddl-file=./pets-db-schema.sql
- Agrega algunos registros de prueba a la base de datos con los siguientes comandos.
owner_uuid=$(cat /proc/sys/kernel/random/uuid)
gcloud spanner rows insert --table=Owners --database=pets-db --instance=test-spanner-instance --data=OwnerID=$owner_uuid,OwnerName=Doug
gcloud spanner rows insert --table=Pets --database=pets-db --instance=test-spanner-instance --data=PetID=$(cat /proc/sys/kernel/random/uuid),OwnerID=$owner_uuid,PetName='Noir',PetType='Dog',Breed='Schnoodle'
gcloud spanner rows insert --table=Pets --database=pets-db --instance=test-spanner-instance --data=PetID=$(cat /proc/sys/kernel/random/uuid),OwnerID=$owner_uuid,PetName='Bree',PetType='Dog',Breed='Mutt'
gcloud spanner rows insert --table=Pets --database=pets-db --instance=test-spanner-instance --data=PetID=$(cat /proc/sys/kernel/random/uuid),OwnerID=$owner_uuid,PetName='Gigi',PetType='Dog',Breed='Retriever'
Tarea 2. Crea una Cloud Run Function para leer desde Spanner
- Crea una carpeta para tu primera Cloud Run Function con el siguiente comando.
mkdir ~/lab-files/spanner_get_pets
cd ~/lab-files/spanner_get_pets
- Crea 2 archivos para tu aplicación:
main.py
y requirements.txt
.
touch main.py requirements.txt
- Haz clic en el botón Abrir editor. En el archivo
lab-files/spanner_get_pets/requirements.txt
que acabas de crear, agrega el siguiente código.
google-cloud-spanner==3.27.0
- En el archivo
lab-files/spanner_get_pets/main.py
, agrega el siguiente código que lee de la base de datos y devuelve las mascotas.
from google.cloud import spanner
instance_id = 'test-spanner-instance'
database_id = 'pets-db'
client = spanner.Client()
instance = client.instance(instance_id)
database = instance.database(database_id)
def spanner_get_pets(request):
query = """SELECT OwnerName, PetName, PetType, Breed
FROM Owners
JOIN Pets ON Owners.OwnerID = Pets.OwnerID;"""
outputs = []
with database.snapshot() as snapshot:
results = snapshot.execute_sql(query)
output = '<div>OwnerName,PetName,PetType,Breed</div>'
outputs.append(output)
for row in results:
output = '<div>{},{},{},{}</div>'.format(*row)
outputs.append(output)
return '\n'.join(outputs)
- Haz clic en el botón Abrir terminal. Luego, implementa la Cloud Run Function con el siguiente comando. Ten en cuenta que el activador será un activador HTTP, lo que significa que se generará una URL para invocar la función. (El comando tardará unos minutos en completarse).
gcloud functions deploy spanner_get_pets --runtime python310 --trigger-http --region={{{project_0.default_region|place_holder_text}}} --quiet
- Cuando el comando se complete para implementar la Cloud Run Function, pruébala con el siguiente comando. Se deberían devolver los datos de prueba.
curl -m 70 -X GET https://{{{project_0.default_region|place_holder_text}}}-${GOOGLE_CLOUD_PROJECT}.cloudfunctions.net/spanner_get_pets -H "Authorization: bearer $(gcloud auth print-identity-token)" -H "Content-Type: application/json"
Tarea 3. Crea una Cloud Run Function para escribir en Spanner
- Crea una carpeta para tu segunda Cloud Run Function con el siguiente comando.
mkdir ~/lab-files/spanner_save_pets
cd ~/lab-files/spanner_save_pets
- Crea dos archivos para tu aplicación:
main.py
y requirements.txt
.
touch main.py requirements.txt
- Haz clic en el botón Abrir editor. En el archivo
lab-files/spanner_save_pets/requirements.txt
que acabas de crear, agrega el siguiente código.
google-cloud-spanner==3.27.0
- En el archivo
lab-files/spanner_save_pets/main.py
, agrega el siguiente código que lee de la base de datos y devuelve las mascotas.
from google.cloud import spanner
import base64
import uuid
import json
instance_id = 'test-spanner-instance'
database_id = 'pets-db'
client = spanner.Client()
instance = client.instance(instance_id)
database = instance.database(database_id)
def spanner_save_pets(event, context):
pubsub_message = base64.b64decode(event['data']).decode('utf-8')
data = json.loads(pubsub_message)
# Revisa si el propietario ya existe
con database.snapshot() como instantánea:
results = snapshot.execute_sql("""
SELECT OwnerID FROM OWNERS
WHERE OwnerName = @owner_name""",
params={"owner_name": data["OwnerName"]},
param_types={"owner_name": spanner.param_types.STRING})
row = results.one_or_none()
if row != None:
owner_exists = True
owner_id = row[0]
else:
owner_exists = False
owner_id = str(uuid.uuid4())
# Se necesita un UUID para la nueva mascota
pet_id = str(uuid.uuid4())
def insert_owner_pet(transaction, data, owner_exists):
try:
row_ct = 0
params = { "owner_id": owner_id,
"owner_name": data["OwnerName"],
"pet_id": pet_id,
"pet_name": data["PetName"],
"pet_type": data["PetType"],
"breed": data["Breed"],
}
param_types = { "owner_id": spanner.param_types.STRING,
"owner_name": spanner.param_types.STRING,
"pet_id": spanner.param_types.STRING,
"pet_name": spanner.param_types.STRING,
"pet_type": spanner.param_types.STRING,
"breed": spanner.param_types.STRING,
}
# Solo agrega el propietario si todavía no existe
if not owner_exists:
row_ct = transaction.execute_update(
"""INSERT Owners (OwnerID, OwnerName) VALUES (@owner_id, @owner_name)""",
params=params,
param_types=param_types,)
# Agrega la mascota
row_ct += transaction.execute_update(
"""INSERT Pets (PetID, OwnerID, PetName, PetType, Breed) VALUES (@pet_id, @owner_id, @pet_name, @pet_type, @breed)
""",
params=params,
param_types=param_types,)
except:
row_ct = 0
return row_ct
row_ct = database.run_in_transaction(insert_owner_pet, data, owner_exists)
print("{} record(s) inserted.".format(row_ct))
- Haz clic en el botón Abrir terminal. Esta Cloud Run Function se activa con un mensaje de Pub/Sub. Para que funcione, primero debes crear el tema de Pub/Sub con el siguiente comando.
gcloud pubsub topics create new-pet-topic
- Implementa la Cloud Run Function con el siguiente comando. (El comando tardará unos minutos en completarse).
gcloud functions deploy spanner_save_pets --runtime python310 --trigger-topic=new-pet-topic --region={{{project_0.default_region|place_holder_text}}} --quiet
- Cuando se complete el comando, navega al servicio Pub/Sub en la consola. Haz clic en el tema new-pet-topic para ver sus detalles.
En la página de detalles, haz clic en la pestaña Mensajes y, luego, en el botón Publicar mensaje.
Ingresa el mensaje que se muestra a continuación y, luego, haz clic en el botón Publicar. Nota: El mensaje está en formato JSON y debe usar el esquema correcto como se muestra para que la función se ejecute.
{"OwnerName": "Jean", "PetName": "Sally", "PetType": "Frog", "Breed": "Green"}
- Activa la Cloud Run Function
spanner_gets_pets
con el comando curl
que ejecutaste antes. Verifica si se agregaron el nuevo propietario, Jean, y su rana, Sally.
curl -m 70 -X GET https://{{{project_0.default_region|place_holder_text}}}-${GOOGLE_CLOUD_PROJECT}.cloudfunctions.net/spanner_get_pets -H "Authorization: bearer $(gcloud auth print-identity-token)" -H "Content-Type: application/json"
Tarea 4. Inicia el emulador de Spanner
- En la terminal de Cloud Shell, ejecuta el siguiente comando para instalar y, luego, iniciar el emulador de Spanner.
sudo apt-get install google-cloud-sdk-spanner-emulator
gcloud emulators spanner start
- El emulador toma el control de la terminal, así que, en la barra de herramientas de Cloud Shell, haz clic en el ícono + para abrir una nueva pestaña de la terminal. Ejecuta los siguientes comandos para configurar el SDK de Cloud y, así, usar el emulador.
gcloud config configurations create emulator
gcloud config set auth/disable_credentials true
gcloud config set project $GOOGLE_CLOUD_PROJECT
gcloud config set api_endpoint_overrides/spanner http://localhost:9020/
- Crea la instancia y la base de datos con gcloud, pero ten en cuenta que estos comandos usan el emulador ahora, no Spanner en la nube. Ejecuta cada una por separado, no como un todo.
cd ~/lab-files
gcloud spanner instances create emulator-instance --config=emulator-config --description="EmulatorInstance" --nodes=1
gcloud spanner databases create pets-db --instance=emulator-instance --database-dialect=GOOGLE_STANDARD_SQL --ddl-file=./pets-db-schema.sql
- Para que el código de la biblioteca cliente de Python use el emulador, se debe configurar la variable de entorno
SPANNER_EMULATOR_HOST
. Ejecuta el siguiente código ahora para hacerlo.
export SPANNER_EMULATOR_HOST=localhost:9010
Tarea 5. Escribe una API de REST para la base de datos de mascotas de Spanner
- Crea una carpeta para los archivos de programa de Cloud Run y agrega los archivos necesarios.
mkdir ~/lab-files/cloud-run
cd ~/lab-files/cloud-run
touch Dockerfile main.py requirements.txt
- Haz clic en el botón Abrir editor. En el archivo
lab-files/cloud-run/requirements.txt
que acabas de crear, agrega el siguiente código.
Flask==3.0.3
Flask-RESTful==0.3.10
google-cloud-spanner==3.27.0
gunicorn==22.0.0
- En
main.py
, agrega lo siguiente. Este código usa Python Flask y la biblioteca Flask-RESTful con el objetivo de compilar una API de REST para la base de datos de mascotas.
Nota: Presta atención al uso de las variables de entorno cerca de la parte superior del archivo (líneas de 11 a 20). Cuando implementas en Cloud Run, configuras estas variables para que apunten a la base de datos real de Spanner. Si no se configuran las variables, el emulador se establecerá de forma predeterminada.
import os
import uuid
from flask import Flask, jsonify, request
from flask_restful import Api, Resource
from google.api_core import exceptions
from google.cloud import spanner
from werkzeug.exceptions import BadRequest, NotFound
# --- Configuration ---
# Use emulator settings by default, but override with environment variables if they exist.
INSTANCE_ID = os.environ.get("INSTANCE_ID", "emulator-instance")
DATABASE_ID = os.environ.get("DATABASE_ID", "pets-db")
# --- Database Repository ---
class SpannerRepository:
"""
A repository class to handle all database interactions with Google Cloud Spanner.
This separates database logic from the API/view layer.
"""
def __init__(self, instance_id, database_id):
spanner_client = spanner.Client()
self.instance = spanner_client.instance(instance_id)
self.database = self.instance.database(database_id)
def list_all_pets(self):
"""Retrieves all pets with their owner information."""
query = """
SELECT o.OwnerID, o.OwnerName, p.PetID, p.PetName, p.PetType, p.Breed
FROM Owners o JOIN Pets p ON o.OwnerID = p.OwnerID
"""
with self.database.snapshot() as snapshot:
results = snapshot.execute_sql(query)
# 1. Materialize the iterator into a list of rows.
# Each 'row' in this list is a regular Python list of values.
rows = list(results)
# 2. If there are no rows, the metadata might be incomplete.
# This check prevents the original 'NoneType' error.
if not rows:
return []
# 3. If we have rows, the metadata is guaranteed to be available.
# Get the column names from the result set's metadata.
# Note: results.metadata is the correct attribute.
keys = [field.name for field in results.metadata.row_type.fields]
# 4. Zip the keys with each row's list of values to create dicts.
return [dict(zip(keys, row)) for row in rows]
def get_pet_by_id(self, pet_id):
"""Retrieves a single pet by its ID."""
query = """
SELECT o.OwnerID, o.OwnerName, p.PetID, p.PetName, p.PetType, p.Breed
FROM Owners o JOIN Pets p ON o.OwnerID = p.OwnerID
WHERE p.PetID = @pet_id
"""
params = {"pet_id": pet_id}
param_types = {"pet_id": spanner.param_types.STRING}
with self.database.snapshot() as snapshot:
results = snapshot.execute_sql(
query, params=params, param_types=param_types
)
# results.one_or_none() returns a special Row object (not a list)
# that has a .keys() method, so this is correct and simpler.
row = results.one_or_none()
if not row:
return None
return dict(zip(row.keys(), row))
def create_pet_and_owner(self, data):
"""
Creates a new pet. If the owner doesn't exist, creates the owner as well.
This entire operation is performed in a single transaction.
"""
def _tx_create_pet(transaction):
pet_id = str(uuid.uuid4())
owner_name = data["OwnerName"]
owner_result = transaction.execute_sql(
"SELECT OwnerID FROM Owners WHERE OwnerName = @name",
params={"name": owner_name},
param_types={"name": spanner.param_types.STRING},
).one_or_none()
if owner_result:
owner_id = owner_result[0]
else:
owner_id = str(uuid.uuid4())
transaction.insert(
"Owners",
columns=("OwnerID", "OwnerName"),
values=[(owner_id, owner_name)],
)
pet_columns = ["PetID", "OwnerID", "PetName", "PetType", "Breed"]
pet_values = [
pet_id,
owner_id,
data["PetName"],
data["PetType"],
data["Breed"],
]
transaction.insert("Pets", columns=pet_columns, values=[pet_values])
new_pet_data = {
"PetID": pet_id,
"OwnerID": owner_id,
"OwnerName": owner_name,
"PetName": data["PetName"],
"PetType": data["PetType"],
"Breed": data["Breed"],
}
return new_pet_data
return self.database.run_in_transaction(_tx_create_pet)
def delete_pet_by_id(self, pet_id):
"""Deletes a single pet by its ID in a transaction."""
def _tx_delete_pet(transaction):
return transaction.execute_update(
"DELETE FROM Pets WHERE PetID = @pet_id",
params={"pet_id": pet_id},
param_types={"pet_id": spanner.param_types.STRING},
)
return self.database.run_in_transaction(_tx_delete_pet)
def delete_all_pets_and_owners(self):
"""Deletes all owners, which cascades to delete all pets."""
def _tx_delete_all(transaction):
return transaction.execute_update("DELETE FROM Owners WHERE true")
return self.database.run_in_transaction(_tx_delete_all)
# --- API Resources ---
db_repo = SpannerRepository(INSTANCE_ID, DATABASE_ID)
class PetsList(Resource):
def get(self):
"""Returns a list of all pets."""
pets = db_repo.list_all_pets()
return jsonify(pets)
def post(self):
"""Creates a new pet and possibly a new owner."""
try:
data = request.get_json(force=True)
required_fields = ["OwnerName", "PetName", "PetType", "Breed"]
if not all(field in data for field in required_fields):
raise BadRequest("Missing required fields in JSON payload.")
except BadRequest as e:
return {"message": str(e)}, 400
try:
new_pet = db_repo.create_pet_and_owner(data)
return new_pet, 201
except exceptions.GoogleAPICallError as e:
return {"message": "Database transaction failed", "error": str(e)}, 500
def delete(self):
"""Deletes all owners and pets."""
deleted_count = db_repo.delete_all_pets_and_owners()
return {"message": f"{deleted_count} owner record(s) deleted (pets cascaded)."}, 200
class Pet(Resource):
def get(self, pet_id):
"""Returns a single pet by ID."""
pet = db_repo.get_pet_by_id(pet_id)
if pet:
return jsonify(pet)
raise NotFound("Pet with the specified ID was not found.")
def delete(self, pet_id):
"""Deletes a single pet by ID."""
try:
deleted_count = db_repo.delete_pet_by_id(pet_id)
if deleted_count > 0:
return {"message": f"Pet with ID {pet_id} was deleted."}, 200
raise NotFound("Pet with the specified ID was not found.")
except exceptions.NotFound:
raise NotFound("Pet with the specified ID was not found.")
def patch(self, pet_id):
"""This endpoint is not implemented."""
return {"message": "Update operation is not implemented."}, 501
# --- Flask App Initialization ---
def create_app():
"""Application factory to create and configure the Flask app."""
app = Flask(__name__)
api = Api(app)
# API Resource routing
api.add_resource(PetsList, "/pets")
api.add_resource(Pet, "/pets/<string:pet_id>")
# Centralized error handling
@app.errorhandler(NotFound)
def handle_not_found(e):
return jsonify({"message": str(e)}), 404
@app.errorhandler(BadRequest)
def handle_bad_request(e):
return jsonify({"message": str(e)}), 400
@app.errorhandler(Exception)
def handle_generic_error(e):
app.logger.error(f"An unhandled exception occurred: {e}", exc_info=True)
return jsonify({"message": "An internal server error occurred."}), 500
return app
app = create_app()
if __name__ == "__main__":
# Use debug=False in a production environment
app.run(host="0.0.0.0", port=8080, debug=True)
- Haz clic en el botón Abrir terminal y, luego, ejecuta el siguiente código para instalar los paquetes necesarios.
pip install -r requirements.txt
- Ahora, ejecuta el siguiente código en la terminal para iniciar el programa.
python main.py
-
En la barra de herramientas de Cloud Shell, haz clic nuevamente en el ícono + para abrir una tercera pestaña de la terminal.
-
Puedes usar curl
para probar la API. Primero, agrega algunos registros con los comandos HTTP POST.
curl -X POST --data '{"OwnerName": "Sue", "PetName": "Sparky", "PetType": "Cat", "Breed": "Alley"}' http://localhost:8080/pets
curl -X POST --data '{"OwnerName": "Sue", "PetName": "Pickles", "PetType": "Dog", "Breed": "Shepherd"}' http://localhost:8080/pets
curl -X POST --data '{"OwnerName": "Doug", "PetName": "Noir", "PetType": "Dog", "Breed": "Schnoodle"}' http://localhost:8080/pets
curl -X POST --data '{"OwnerName": "Doug", "PetName": "Bree", "PetType": "Dog", "Breed": "Mutt"}' http://localhost:8080/pets
curl -X POST --data '{"OwnerName": "Joey", "PetName": "Felix", "PetType": "Cat", "Breed": "Tabby"}' http://localhost:8080/pets
- Comprueba si se agregaron los registros con un comando HTTP GET. Los registros se deben devolver en formato JSON.
curl http://localhost:8080/pets
Nota: En caso de que hayas omitido algún paso o no obtengas el resultado deseado, intenta seguir los pasos de la tarea 4 nuevamente con Cloud Shell.
- Escribe
exit
para cerrar la tercera pestaña de la terminal y, luego, presiona Ctrl + C
para detener el programa de Python en la segunda pestaña de la terminal. Escribe exit
para cerrar la segunda pestaña. Regresa a la primera pestaña de la terminal y presiona Ctrl + C
para detener el emulador.
Nota: Estos registros se agregaron al emulador. A continuación, implementarás en Cloud Run y usarás la instancia real de Spanner.
Tarea 6: Implementa una app en Cloud Run
- Para implementar en Cloud Run, necesitas una imagen de Docker. Primero, cambia de directorio a la carpeta cloud-run.
cd ~/lab-files/cloud-run
- Para crear la imagen de Docker, debes agregar instrucciones al archivo Dockerfile. Haz clic en el botón Abrir editor y abre el archivo Dockerfile. Pega el siguiente código en él.
FROM python:3.9
WORKDIR /app
COPY . .
RUN pip install gunicorn
RUN pip install -r requirements.txt
ENV PORT=8080
CMD exec gunicorn --bind :$PORT --workers 1 --threads 8 main:app
- Vuelve a la terminal y ejecuta el siguiente código para crear la imagen de Docker. (Asegúrate de estar en la carpeta ~/lab-files/cloud-run).
gcloud builds submit --tag=gcr.io/$GOOGLE_CLOUD_PROJECT/spanner-pets-api:v1.0 .
-
Asegúrate de que Cloud Run esté habilitado para tu proyecto a través de Explorar y habilitar APIs.
-
Ahora, implementa la aplicación de Cloud Run con el siguiente comando. Ten en cuenta cómo se establecen las variables de entorno en el comando, de modo que el código use la instancia de Cloud Spanner, no el emulador
. El comando tardará unos minutos en completarse.
gcloud run deploy spanner-pets-api --image gcr.io/$GOOGLE_CLOUD_PROJECT/spanner-pets-api:v1.0 --update-env-vars INSTANCE_ID=test-spanner-instance,DATABASE_ID=pets-db --region={{{project_0.default_region|place_holder_text}}}
- Cuando se complete el comando, anota la URL del servicio y cópiala en el portapapeles. Como hiciste con el emulador, puedes usar comandos curl para probar la API. Primero, crea una variable para almacenar la URL, como se muestra a continuación. Asegúrate de pegar la URL completa, incluida la parte
https://…
, en lugar del marcador de posición completo: <YOUR_SERVICE_URL_HERE>.
pets_url=<YOUR_SERVICE_URL_HERE>
- Agrega algunos registros con curl.
curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" -X POST --data '{"OwnerName": "Sue", "PetName": "Sparky", "PetType": "Cat", "Breed": "Alley"}' $pets_url/pets
curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" -X POST --data '{"OwnerName": "Sue", "PetName": "Pickles", "PetType": "Dog", "Breed": "Shepherd"}' $pets_url/pets
curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" -X POST --data '{"OwnerName": "Doug", "PetName": "Noir", "PetType": "Dog", "Breed": "Schnoodle"}' $pets_url/pets
curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" -X POST --data '{"OwnerName": "Doug", "PetName": "Bree", "PetType": "Dog", "Breed": "Mutt"}' $pets_url/pets
curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" -X POST --data '{"OwnerName": "Joey", "PetName": "Felix", "PetType": "Cat", "Breed": "Tabby"}' $pets_url/pets
-
Los registros se agregaron correctamente. En la consola, navega al servicio Cloud Run y haz clic en tu servicio para ver sus detalles y consultar los registros. Verás cada solicitud que hayas realizado registrada allí.
-
Verifica si se agregaron los registros.
curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" $pets_url/pets
-
Navega a Spanner y explora la instancia y la base de datos.
-
La API también implementa DELETE. Regresa a la terminal y, luego, ingresa el siguiente comando para borrar todos los datos.
curl -H "Authorization: Bearer $(gcloud auth print-identity-token)" -X DELETE $pets_url/pets
- En la consola, borra la instancia de Spanner para que ya no se te cobre por ella.
¡Felicitaciones! Escribiste aplicaciones que usan bases de datos de Spanner y las implementaste en Cloud Run Functions y Cloud Run. También instalaste, configuraste y habilitaste el emulador de Spanner para usarlo en entornos de desarrollo.
Finalice su lab
Cuando haya completado su lab, haga clic en End Lab. Qwiklabs quitará los recursos que usó y limpiará la cuenta por usted.
Tendrá la oportunidad de calificar su experiencia en el lab. Seleccione la cantidad de estrellas que corresponda, ingrese un comentario y haga clic en Submit.
La cantidad de estrellas indica lo siguiente:
- 1 estrella = Muy insatisfecho
- 2 estrellas = Insatisfecho
- 3 estrellas = Neutral
- 4 estrellas = Satisfecho
- 5 estrellas = Muy satisfecho
Puede cerrar el cuadro de diálogo si no desea proporcionar comentarios.
Para enviar comentarios, sugerencias o correcciones, use la pestaña Support.
Copyright 2024 Google LLC. Todos los derechos reservados. Google y el logotipo de Google son marcas de Google LLC. El resto de los nombres de productos y empresas pueden ser marcas de las respectivas empresas a las que están asociados.