Si usas cuentas de servicio en las instancias para ejecutar tareas automatizadas y, además, interactuar con otras API de Google Cloud Platform, esa cuenta de servicio también puede requerir acceso SSH a otras instancias de Compute Engine. En este instructivo, se muestra cómo configurar apps para acceder a tus instancias a través de conexiones SSH. La app de muestra de este instructivo usa una cuenta de servicio y acceso a SO para la administración de Llaves SSH.
Para omitir el ejercicio y ver la muestra de código completo, visita la página de GitHub GoogleCloudPlatform/python-docs-samples.
Objetivos
En este instructivo, aprenderás a lograr los siguientes objetivos:
- Crear una cuenta de servicio y configurarla con el objetivo de proporcionar acceso SSH administrado con acceso a SO para las aplicaciones que se conectan a tus instancias
- Crear una instancia asociada con tu cuenta de servicio
- Configurar la app de muestra en tu instancia para que use la cuenta de servicio a fin de administrar sus propias Llaves SSH y establecer conexiones SSH.
- Ejecutar la app en una instancia en la que esté asociada la cuenta de servicio
- Ejecutar la app fuera de Compute Engine, donde debe proporcionar la clave de la cuenta de servicio de forma manual y especificar parámetros SSH adicionales.
Costos
En este instructivo, se usan componentes facturables de GCP, incluido Compute Engine.
Los usuarios nuevos de GCP podrían cumplir con los requisitos para obtener una prueba gratuita.Antes de comenzar
-
Accede a tu Cuenta de Google.
Si todavía no tienes una cuenta, regístrate para obtener una nueva.
-
Selecciona o crea un proyecto de GCP.
-
Asegúrate de tener habilitada la facturación para tu proyecto.
-
Tu cuenta de usuario debe tener permiso para crear, borrar y modificar varios recursos de Compute Engine. En este instructivo, se supone que tienes las siguientes funciones de IAM para tu proyecto:
compute.instanceAdmin.v1
compute.networkAdmin
compute.osAdminLogin
iam.serviceAccountAdmin
iam.serviceAccountKeyAdmin
iam.serviceAccountUser
- En este instructivo, se supone que usas Cloud Shell para ejecutar los comandos de la herramienta de línea de comandos de
gcloud
.
Crea y configura la cuenta de servicio y las instancias de ejemplo
En este instructivo, se usa una cuenta de servicio y dos instancias para mostrar cómo tus apps pueden ejecutar comandos SSH en instancias remotas.
Usa los siguientes comandos para configurar el entorno de prueba:
Abre Cloud Shell en la consola:
Exporta una variable de entorno a fin de establecer el ID del proyecto para futuros comandos:
export PROJECT_ID='[PROJECT_ID]'
Crea una cuenta de servicio nueva en el proyecto. Para este ejemplo, crea una cuenta de servicio llamada
ssh-account
:gcloud iam service-accounts create ssh-account --project $PROJECT_ID \ --display-name "ssh-account"
Crea una red temporal llamada
ssh-example
para usarla solo en este ejemplo:gcloud compute networks create ssh-example --project $PROJECT_ID
Crea una regla de firewall que habilite todas las conexiones SSH a las instancias de la red
ssh-example
:gcloud compute firewall-rules create ssh-all --project $PROJECT_ID \ --network ssh-example --allow tcp:22
Crea una instancia en
us-central1-f
llamadatarget
. Esta instancia sirve como la instancia remota a la que se conectará tu cuenta de servicio a través de SSH. La instancia debe tener habilitado el acceso a SO a nivel del proyecto o de la instancia. En este ejemplo, se muestra cómo usar la marca--metadata
para habilitar el acceso a SO en esta instancia específica. Incluye las marcas--no-service-account
y--no-scopes
, ya que esta instancia no necesita ejecutar ninguna solicitud a la API para este ejemplo específico:gcloud compute instances create target --project $PROJECT_ID \ --zone us-central1-f --network ssh-example \ --no-service-account --no-scopes \ --machine-type f1-micro --metadata=enable-oslogin=TRUE
Otorga la función de IAM
compute.osAdminLogin
a la cuenta de servicio para que pueda establecer conexiones SSH específicamente con la instancia llamadatarget
. La funcióncompute.osAdminLogin
también otorga a la cuenta de servicio privilegios de superusuario en la instancia. Aunque podrías otorgar esta función a nivel del proyecto para que se aplique a todas las instancias del proyecto, otorga la función específicamente a nivel de la instancia a fin de mantener los permisos limitados en este ejemplo:gcloud compute instances add-iam-policy-binding target \ --project $PROJECT_ID --zone us-central1-f \ --member serviceAccount:ssh-account@$PROJECT_ID.iam.gserviceaccount.com \ --role roles/compute.osAdminLogin
Crea una instancia en
us-central1-f
llamadasource
. Asocia la instancia con la cuenta de serviciossh-account
. Además, especifica el alcancecloud-platform
, que se requiere para que la cuenta de servicio ejecute solicitudes a la API en esta instancia:gcloud compute instances create source \ --project $PROJECT_ID --zone us-central1-f \ --service-account ssh-account@$PROJECT_ID.iam.gserviceaccount.com \ --scopes https://www.googleapis.com/auth/cloud-platform \ --network ssh-example --machine-type f1-micro
Ahora, la cuenta de servicio puede administrar sus propios pares de Llaves SSH y puede usar SSH para conectarse específicamente a la instancia target
. Debido a que la instancia source
está asociada con la cuenta de servicio ssh-account
que creaste, las bibliotecas cliente de Cloud para Python pueden usar credenciales predeterminadas de la aplicación a fin de autenticarse como la cuenta de servicio y usar las funciones que otorgaste a esa cuenta de servicio con anterioridad.
A continuación, configura y ejecuta una app que pueda establecer una conexión SSH de una instancia a otra.
Ejecuta una app SSH en una instancia
Cuando las apps que se ejecutan en tus instancias requieren acceso SSH a otras instancias, puedes administrar los pares de Llaves SSH para la cuenta de servicio y ejecutar comandos SSH de manera programática. Para este ejemplo, ejecuta una app de muestra con el siguiente proceso:
Conéctate a la instancia
source
con la herramienta de línea de comandos degcloud
:gcloud compute ssh source --project $PROJECT_ID --zone us-central1-f
En la instancia
source
, instalapip
y la biblioteca cliente de Python:my-username@source:~$ sudo apt update && sudo apt install python-pip -y && pip install --upgrade google-api-python-client
Descarga la aplicación de muestra
service_account_ssh.py
de GoogleCloudPlatform/python-docs-samples:my-username@source:~$ curl -O https://raw.githubusercontent.com/GoogleCloudPlatform/python-docs-samples/master/compute/oslogin/service_account_ssh.py
Ejecuta la app de muestra, que usa
argparse
para aceptar variables desde la línea de comandos. En este ejemplo, indica a la app que instale y ejecutecowsay
en la instanciatarget
. Para este comando, agrega el ID del proyecto de forma manual:my-username@source:~$ python service_account_ssh.py \ --cmd 'sudo apt install cowsay -y && cowsay "It works!"' \ --project [PROJECT_ID] --zone us-central1-f --instance target ⋮ ___________ It works! ----------- \ ^__^ \ (oo)\_______ (__)\ )\/\ ||----w | || ||
Si la aplicación se ejecuta de forma correcta, recibirás el resultado de la app cowsay
. Puedes modificar la marca --cmd
para incluir cualquier comando que desees. De manera alternativa, puedes escribir tu propia app que importe service_account_ssh.py
y la llame de forma directa.
Ejecuta exit
para desconectarte de la instancia source
y volver a Cloud Shell.
Ejecuta una app SSH fuera de Compute Engine
En el ejemplo anterior, ejecutaste la app en una instancia de Compute Engine en la que las bibliotecas cliente de Cloud para Python podían usar credenciales predeterminadas de la aplicación a fin de usar la cuenta de servicio asociada con la instancia source
. Si ejecutas esta app fuera de una instancia de Compute Engine, la biblioteca cliente no puede acceder a la cuenta de servicio ni a sus permisos, a menos que proporciones la clave de la cuenta de servicio de forma manual.
Obtén la dirección IP externa de la instancia
target
que creaste con anterioridad en este instructivo. Puedes encontrar esta dirección en la consola en la página Instancias o ejecuta el siguiente comando desde la herramienta de línea de comandos degcloud
:gcloud compute instances describe target \ --project $PROJECT_ID --zone us-central1-f
Crea una clave de cuenta de servicio para la cuenta de servicio
ssh-account
que usaste en el ejemplo anterior y descarga el archivo de claves en tu estación de trabajo local.Copia la clave de la cuenta de servicio en el sistema en el que deseas ejecutar la muestra.
Abre una terminal en el sistema en el que deseas ejecutar esta muestra.
Configura la variable de entorno
GOOGLE_APPLICATION_CREDENTIALS
para que apunte a la ruta en la que se encuentra el archivo de claves.json
de tu cuenta de servicio. Si su clave está en la carpetaDownloads
, puedes establecer una variable de entorno como se muestra en el siguiente ejemplo:$ export GOOGLE_APPLICATION_CREDENTIALS="/home/user/Downloads/key.json"
Instala los requisitos previos en este sistema:
Descarga la app de muestra:
$ curl -O https://raw.githubusercontent.com/GoogleCloudPlatform/python-docs-samples/master/compute/oslogin/service_account_ssh.py
Ejecuta la app de muestra. Cuando ejecutas la app fuera de Compute Engine, el servidor de metadatos no está disponible, por lo que debes especificar el correo electrónico de la cuenta de servicio de forma manual. También debes especificar la dirección IP externa para la instancia
target
que obtuviste con anterioridad.$ python service_account_ssh.py \ --cmd 'sudo apt install cowsay -y && cowsay "It works!"' \ --account ssh-account@[PROJECT_ID].iam.gserviceaccount.com \ --project [PROJECT_ID] --hostname [TARGET_EXTERNAL_IP] ⋮ ___________ It works! ----------- \ ^__^ \ (oo)\_______ (__)\ )\/\ ||----w | || ||
Si la aplicación se ejecuta de manera correcta, recibirás el resultado de la app cowsay
.
Cómo funciona la app de muestra
La app de muestra service_account_ssh.py
funciona mediante el siguiente proceso:
- Inicializa el objeto de la API de acceso a SO.
- Si no proporcionas la dirección de correo electrónico de la cuenta de servicio de forma manual, la app lee los metadatos de la instancia para identificar la cuenta de servicio asociada con la instancia. Si ejecutas esta app fuera de Compute Engine, debes proporcionar la dirección de la cuenta de servicio de forma manual.
- Llama al método
create_ssh_key()
a fin de generar una Llave SSH temporal para la cuenta de servicio en la instancia en la que se ejecuta este ejemplo y agrega la clave pública a la cuenta de servicio con un temporizador de vencimiento que puedes especificar. - Llama al método
getLoginProfile()
desde la API de acceso a SO para obtener el nombre de usuario POSIX que usa la cuenta de servicio. - Llama al método
run_ssh()
para ejecutar un comando SSH remoto como la cuenta de servicio. - Imprime la respuesta desde el comando SSH remoto.
- Quita los archivos de Llave SSH temporales.
- El Acceso a SO quita los archivos de claves públicos de manera automática cuando pasa la fecha de vencimiento.
El método create_ssh_key()
genera un nuevo par de Llaves SSH. Luego, el método llama a users().importSshPublicKey()
desde la API de acceso a SO para asociar la clave pública con la cuenta de servicio. El método users().importSshPublicKey()
también acepta un valor de vencimiento, que indica durante cuánto tiempo permanece válida la clave pública.
Como práctica recomendada, configura tus cuentas de servicio a fin de generar nuevos pares de claves para ellas con regularidad. En este ejemplo, la cuenta de servicio crea un par de claves nuevo para cada conexión SSH que establece, pero puedes modificar esto a fin de que se ejecute en un horario que se adapte mejor las necesidades de tu app.
El cuerpo de la solicitud para users().importSshPublicKey()
incluye el valor expirationTimeUsec
, que le indica al acceso a SO cuándo debe caducar la clave.
Cada cuenta puede tener solo hasta 32 KB de datos de Llave SSH, por lo que es mejor configurar tus Llaves SSH públicas para que caduquen poco después de que tu cuenta de servicio haya completado sus operaciones.
Después de que tu cuenta de servicio configure las Llaves SSH, podrá ejecutar comandos remotos. En este ejemplo, la app usa el método run_ssh()
para ejecutar un comando en una instancia remota y mostrar el resultado del comando.
Realiza una limpieza
Sigue estos pasos para evitar que se apliquen cargos a tu cuenta de Google Cloud Platform por los recursos que usaste en este instructivo:
Usa los siguientes comandos para limpiar los recursos en tu entorno de prueba:
Abre Cloud Shell en la consola:
Borra la instancia llamada
source
:gcloud compute instances delete source \ --project $PROJECT_ID --zone us-central1-f
Borra la instancia llamada
target
:gcloud compute instances delete target \ --project $PROJECT_ID --zone us-central1-f
Borra la cuenta de servicio
ssh-account
:gcloud iam service-accounts delete ssh-account --project $PROJECT_ID
Borra la red llamada
ssh-example
:gcloud compute networks delete ssh-example --project $PROJECT_ID
Pasos siguientes
- Descarga y observa la muestra de código completa. La muestra completa incluye una pequeña muestra del uso de todos estos métodos juntos. No dudes en descargarla, modificarla y ejecutarla para adaptarla a tus necesidades.
- Revisa la referencia de la API de Compute Engine y la referencia de la API de acceso a SO para aprender a realizar otras tareas con estas API.
- Comienza a crear tus propias apps.