Fujitsu K5 Infrastructure as Code (Cookie Cutter)

2017-03-10

Fujitsu K5 Infrastructure as Code (Cookie Cutter)

Machine-translated — the English original is authoritative.

Mon dernier défi consistait à développer un processus pour déployer un modèle d’infrastructure prédéfini, un réseau simple avec 3 nœuds, de manière cohérente et reproductible. Cependant, ce modèle devait être déployé dans chaque type de saveur (flavor) avec des configurations de disque différentes.

En substance, un client souhaitait un mécanisme reproductible pour tester les performances des différentes saveurs de nœuds à grande échelle.

Nous aurions pu simplement nous appuyer sur les exemples HEAT précédents et rédiger un modèle YAML massif contenant l’infrastructure requise. Cependant, cette approche est sujette aux erreurs, difficile à déboguer et peu efficace ou flexible.

Ce dont nous avons besoin, c’est de séparer les composants statiques et dynamiques de l’infrastructure – définir un modèle qui correspond aux composants statiques et permet de transmettre les composants dynamiques en tant que paramètres. Tout développeur sera familier avec le principe DRY (Don’t Repeat Yourself – Ne vous répétez pas), ce qui s’applique ici également.

Étant donné que nous déployions dans un projet disposant déjà d’une infrastructure, j’ai également transmis certains de ces détails au tas Heat en tant que paramètres d’entrée – par exemple, routerId, kpName.

Le modèle d’infrastructure de base ressemblait à ceci :

Ce fichier contient des caractères Unicode cachés ou bidirectionnels qui peuvent être interprétés ou compilés différemment de ce qui apparaît ci-dessous. Pour les examiner, ouvrez le fichier dans un éditeur qui révèle les caractères Unicode cachés.
En savoir plus sur les caractères Unicode bidirectionnels

Afficher les caractères cachés

heat_template_version: 2013-05-23
# Auteur : Graham Land
# Date : 08/03/2017
# Objectif : Modèle Heat IaaS OpenStack Fujitsu K5 qui déploie 3 serveurs sur un nouveau réseau et attache le réseau à un routeur donné.
# Paramètres d’entrée –
# routerId – identifiant unique du routeur auquel le réseau doit être attaché
# imageName – l’image OS qui sera déployée
# flavorName – la taille des vCPU et de la RAM des serveurs
# dataVolume – la taille du volume de données à attacher aux serveurs
# cidr – détails de l’adresse IP du réseau privé
# azName – la zone de disponibilité dans laquelle déployer les serveurs – évidemment, cela doit correspondre à l’emplacement du routeur
# kpName – le nom d’une paire de clés SSH existante à utiliser dans la zone de disponibilité
#
#
# Paramètres de sortie – les adresses IP des 3 serveurs
#
# Twitter : @allthingsclowd
# Blog : https://allthingscloud.eu
#
description : Modèle Heat IaaS OpenStack Fujitsu K5 qui déploie 3 serveurs sur un nouveau réseau et attache le réseau à un routeur donné.
# Paramètres d’entrée
parameters:
imageName:
type: string
label: Nom de l’image
description: Image à utiliser pour l’instance de calcul
default: "Ubuntu Server 14.04 LTS (English) 02"
flavorName:
type: string
label: Saveur (Flavor)
description: X vCPU et XXXXMB RAM
default: "T-1"
kpName:
type: string
label: Nom de la clé
description: Nom de la paire de clés à utiliser pour l’instance de calcul
default: "k5-loadtest-az1"
cidr:
type: string
label: Détails de l’adresse IP
description: Plage d’adresses réseau
default: "10.99.99.0/24"
dataVolume:
type: string
label: Taille du volume
description: Taille en Go du volume de données à attacher au serveur
default: "3"
osVolume:
type: string
label: Taille du volume
description: Taille en Go du volume OS à attacher au serveur
default: "20"
azName:
type: string
label: Zone de disponibilité
description: Région AZ à utiliser
default: "uk-1a"
securityGroup:
type: string
label: Nom du groupe de sécurité K5 existant
description: Groupe de sécurité du projet
default: "demosecuritygroup"
routerId:
type: string
label: Routeur externe
description: Routeur avec accès externe pour l’allocation d’IP globale
default: "fcb1dddc-e0c8-4dd5-8a3f-4eee3b042912"
# Ressources d’infrastructure K5 à créer
resources:
############################ Ressources Réseau ####################
# Créer un réseau privé dans la zone de disponibilité
demostack_private_net :
type: OS::Neutron::Net
properties:
name: "private"
availability_zone: { get_param: azName}
# Créer un nouveau sous-réseau sur le réseau privé
demostack_private_subnet :
type: OS::Neutron::Subnet
depends_on: demostack_private_net
properties:
availability_zone: { get_param: azName}
network_id: { get_resource: demostack_private_net }
cidr: { get_param: cidr}
dns_nameservers: ["62.60.39.9", "62.60.39.10"]
# Connecter une interface sur le sous-réseau du réseau demostacks au routeur
router_interface:
type: OS::Neutron::RouterInterface
depends_on: [demostack_private_subnet ]
properties:
router_id: { get_param: routerId }
subnet_id: { get_resource: demostack_private_subnet }
################## Ressources Serveurs ###########################
################################ créer le serveur demo-mgmt1-server ##############################
# Créer un volume de données à utiliser avec le serveur
demo-mgmt1-server-data-vol:
type: OS::Cinder::Volume
properties:
availability_zone: { get_param: azName}
description: Stockage de données
size: { get_param: dataVolume}
volume_type: "M1"
# Créer un volume système à utiliser avec le serveur
demo-mgmt1-server-sys-vol:
type: OS::Cinder::Volume
properties:
availability_zone: { get_param: azName}
size: { get_param: osVolume}
volume_type: "M1"
image : { get_param: imageName }
# Construire un serveur en utilisant le volume système défini ci-dessus
demo-mgmt1-server:
type: OS::Nova::Server
depends_on: [ demostack_private_subnet ]
properties:
key_name: { get_param: kpName }
image: { get_param: imageName }
flavor: { get_param: flavorName }
security_groups: [{get_param: securityGroup}]
block_device_mapping: [{"volume_size": { get_param: osVolume}, "volume_id": {get_resource: demo-mgmt1-server-sys-vol}, "delete_on_termination": True, "device_name": "/dev/vda"}]
admin_user: "ubuntu"
metadata: { "fcx.autofailover": True, "Example Custom Tag": "Multiple Server Build" }
user_data:
str_replace:
template:
#cloud-config
write_files:
– content:
#!/bin/bash
voldata_id=%voldata_id%
voldata_dev="/dev/disk/by-id/virtio-$(echo ${voldata_id}
mkfs.ext4 ${voldata_dev}
mkdir -pv /mnt/appdata
echo "${voldata_dev} /mnt/appdata ext4 defaults 1 2" >> /etc/fstab
mount /mnt/appdata
chmod 0777 /mnt/appdata
path: /tmp/format-disks
permissions: '0700'
runcmd:
– /tmp/format-disks
params:
"%voldata_id%": { get_resource: demo-mgmt1-server-data-vol }
user_data_format: RAW
networks: ["uuid": {get_resource: demostack_private_net} ]
# Attacher le volume de données précédemment défini au serveur
attach-demo-mgmt1-server-data-vol:
type: OS::Cinder::VolumeAttachment
depends_on: [ demo-mgmt1-server-data-vol, demo-mgmt1-server ]
properties:
instance_uuid: {get_resource: demo-mgmt1-server}
mountpoint: "/dev/vdb"
volume_id: {get_resource: demo-mgmt1-server-data-vol}
################################ créer le serveur demo-mgmt2-server ##############################
# Créer un volume de données à utiliser avec le serveur
demo-mgmt2-server-data-vol:
type: OS::Cinder::Volume
properties:
availability_zone: { get_param: azName}
description: Stockage de données
size: { get_param: dataVolume}
volume_type: "M1"
# Créer un volume système à utiliser avec le serveur
demo-mgmt2-server-sys-vol:
type: OS::Cinder::Volume
properties:
availability_zone: { get_param: azName}
size: { get_param: osVolume}
volume_type: "M1"
image : { get_param: imageName }
# Construire un serveur en utilisant le volume système défini ci-dessus
demo-mgmt2-server:
type: OS::Nova::Server
depends_on: [ demostack_private_subnet ]
properties:
key_name: { get_param: kpName }
image: { get_param: imageName }
flavor: { get_param: flavorName }
block_device_mapping: [{"volume_size": { get_param: osVolume}, "volume_id": {get_resource: demo-mgmt2-server-sys-vol}, "delete_on_termination": True, "device_name": "/dev/vda"}]
admin_user: "ubuntu"
security_groups: [{get_param: securityGroup}]
metadata: { "fcx.autofailover": True, "Example Custom Tag": "Multiple Server Build" }
user_data:
str_replace:
template:
#cloud-config
write_files:
– content:
#!/bin/bash
voldata_id=%voldata_id%
voldata_dev="/dev/disk/by-id/virtio-$(echo ${voldata_id}
mkfs.ext4 ${voldata_dev}
mkdir -pv /mnt/appdata
echo "${voldata_dev} /mnt/appdata ext4 defaults 1 2" >> /etc/fstab
mount /mnt/appdata
chmod 0777 /mnt/appdata
path: /tmp/format-disks
permissions: '0700'
runcmd:
– /tmp/format-disks
params:
"%voldata_id%": { get_resource: demo-mgmt2-server-data-vol }
user_data_format: RAW
networks: ["uuid": {get_resource: demostack_private_net} ]
# Attacher le volume de données précédemment défini au serveur
attach-demo-mgmt2-server-data-vol:
type: OS::Cinder::VolumeAttachment
depends_on: [ demo-mgmt2-server-data-vol, demo-mgmt2-server ]
properties:
instance_uuid: {get_resource: demo-mgmt2-server}
mountpoint: "/dev/vdb"
volume_id: {get_resource: demo-mgmt2-server-data-vol}
################################ créer le serveur demo-mgmt3-server ##############################
# Créer un volume de données à utiliser avec le serveur
demo-mgmt3-server-data-vol:
type: OS::Cinder::Volume
properties:
availability_zone: { get_param: azName}
description: Stockage de données
size: { get_param: dataVolume}
volume_type: "M1"
# Créer un volume système à utiliser avec le serveur
demo-mgmt3-server-sys-vol:
type: OS::Cinder::Volume
properties:
availability_zone: { get_param: azName}
size: { get_param: osVolume}
volume_type: "M1"
image : { get_param: imageName }
# Construire un serveur en utilisant le volume système défini ci-dessus
demo-mgmt3-server:
type: OS::Nova::Server
depends_on: [ demostack_private_subnet ]
properties:
key_name: { get_param: kpName }
image: { get_param: imageName }
flavor: { get_param: flavorName }
block_device_mapping: [{"volume_size": { get_param: osVolume}, "volume_id": {get_resource: demo-mgmt3-server-sys-vol}, "delete_on_termination": True, "device_name": "/dev/vda"}]
admin_user: "ubuntu"
security_groups: [{get_param: securityGroup}]
metadata: { "fcx.autofailover": True, "Example Custom Tag": "Multiple Server Build" }
user_data:
str_replace:
template:
#cloud-config
write_files:
– content:
#!/bin/bash
voldata_id=%voldata_id%
voldata_dev="/dev/disk/by-id/virtio-$(echo ${voldata_id}
mkfs.ext4 ${voldata_dev}
mkdir -pv /mnt/appdata
echo "${voldata_dev} /mnt/appdata ext4 defaults 1 2" >> /etc/fstab
mount /mnt/appdata
chmod 0777 /mnt/appdata
path: /tmp/format-disks
permissions: '0700'
runcmd:
– /tmp/format-disks
params:
"%voldata_id%": { get_resource: demo-mgmt3-server-data-vol }
user_data_format: RAW
networks: ["uuid": {get_resource: demostack_private_net} ]
# Attacher le volume de données précédemment défini au serveur
attach-demo-mgmt3-server-data-vol:
type: OS::Cinder::VolumeAttachment
depends_on: [ demo-mgmt3-server-data-vol, demo-mgmt3-server ]
properties:
instance_uuid: {get_resource: demo-mgmt3-server}
mountpoint: "/dev/vdb"
volume_id: {get_resource: demo-mgmt3-server-data-vol}
outputs:
server1_ip:
description: IP fixe attribuée au serveur 1
value: { get_attr: [demo-mgmt1-server, networks, "private", 0]}
server2_ip:
description: IP fixe attribuée au serveur 2
value: { get_attr: [demo-mgmt2-server, networks, "private", 0]}
server3_ip:
description: IP fixe attribuée au serveur 3
value: { get_attr: [demo-mgmt3-server, networks, "private", 0]}

voir le code brut
simple_3_node_template.yml
hébergé avec ❤ par GitHub

Maintenant que nous disposons de notre Infrastructure as Code, comment la déployons-nous à grande échelle tout en modifiant les paramètres d’entrée ? Eh bien, c’est ici que l’« API Economy » entre en jeu. Fujitsu K5 est basé sur OpenStack, qui est une plateforme axée sur les API – en termes simples, plutôt que marketing, cela signifie essentiellement que la plateforme peut être pilotée à 100 % via des interactions API uniquement… toujours confus ? Je peux utiliser plus de code !

Je peux envoyer le modèle Heat ci-dessus ainsi que les différents ensembles de paramètres au moteur d’orchestration de K5 à l’aide d’un script Python qui enverra les données au point de terminaison d’orchestration.

Ce fichier contient des caractères Unicode cachés ou bidirectionnels qui peuvent être interprétés ou compilés différemment de ce qui apparaît ci-dessous. Pour les examiner, ouvrez le fichier dans un éditeur qui révèle les caractères Unicode cachés.
En savoir plus sur les caractères Unicode bidirectionnels

Afficher les caractères cachés

def deploy_heat_stack(k5token, stack_name, stack_to_deploy, stack_parameters):
"""Résumé : Appel API HEAT K5 pour envoyer un tas Heat, enveloppé dans une chaîne, à un projet K5
Retourne :
TYPE : Objet JSON contenant le nouvel ID de Tas ou les codes d’erreur
"""
orchestrationURL = unicode(get_endpoint(k5token, "orchestration")) + unicode("/stacks")
print orchestrationURL
token = k5token.headers['X-Subject-Token']
try:
response = requests.post(orchestrationURL,
headers={
'X-Auth-Token': token, 'Content-Type': 'application/json', 'Accept': 'application/json'},
json={
"files": {},
"disable_rollback": True,
"parameters": stack_parameters,
"stack_name": stack_name,
"template": stack_to_deploy,
"timeout_mins": 60
})
return response
except:
return ("\nErreur inattendue :", sys.exc_info())

voir le code brut
Deploy_Heat_Stack.py
hébergé avec ❤ par GitHub

L’avantage ici est que l’ensemble du processus est désormais défini dans le code – et cela peut facilement être contrôlé par un système de gestion de versions, ce qui aide à garantir des déploiements cohérents.

La version complète de cette solution peut être récupérée ici : https://github.com/allthingsclowd/Fujitsu_OpenStack_K5_Heat_Cookie_Cutter

openstack heat cookie cutterv2

K5_Stack_Deployer – Modèle OpenStack

Auteur : Graham Land

Date : 08/03/17

Twitter : @allthingsclowd

Github : https://github.com/allthingscloud

Blog : https://allthingscloud.eu

deploy_stacks.py

Ce script démontre comment déployer un modèle OpenStack HEAT
plusieurs fois avec des paramètres différents à chaque fois

k5regionapiv1.py

Ce fichier est importé par deploy_stacks.py et contient des wrappers de fonctions API K5/OpenStack

simple_3_node_stack.py

Ce fichier contient simplement le tas HEAT YAML enveloppé sous forme de chaîne pour une utilisation dans Python

simple_3_node_stack.yml

Est le modèle HEAT natif déployé (non utilisé, sauf si vous souhaitez jouer avec séparément)

k5contractsettingsV12.py

Vous DEVEZ configurer ce fichier pour qu’il corresponde à votre environnement avant de déployer.
Il contient une section environnementale et une section application.
La section environnementale est l’endroit où vous entrez vos détails K5, tandis que la section application est où les « lots » de paramètres à alimenter dans le modèle Heat sont configurés.
Chaque lot contient une liste de paramètres d’entrée du modèle Heat – chaque liste de paramètres représente un tas Heat déployé.

Lien vers Github
https://github.com/allthingsclowd/Fujitsu_OpenStack_K5_Heat_Cookie_Cutter

voir le code brut
K5_Cookie_Cutter.md
hébergé avec ❤ par GitHub

Bon déploiement de tas !

withk5youcan

Originally published on allthingscloud.eu (2017-03-10).

← All posts