Merge "[firstapp] add samples for section1 using python-openstacksdk"

This commit is contained in:
Jenkins 2015-11-11 05:18:01 +00:00 committed by Gerrit Code Review
commit 705447a53e
4 changed files with 351 additions and 38 deletions

View File

@ -0,0 +1,188 @@
# step-1
import base64
from os.path import expanduser
from openstack import connection
from openstack import exceptions
auth_username = 'your_auth_username'
auth_password = 'your_auth_password'
auth_url = 'http://controller:5000/v2.0'
project_name = 'your_project_name_or_id'
region_name = 'your_region_name'
conn = connection.Connection(auth_url=auth_url,
project_name=project_name,
username=auth_username,
password=auth_password,
region=region_name)
# step-2
images = conn.image.images()
for image in images:
print(image)
# step-3
flavors = conn.compute.flavors()
for flavor in flavors:
print(flavor)
# step-4
image_id = 'cb6b7936-d2c5-4901-8678-c88b3a6ed84c'
image = conn.compute.get_image(image_id)
print(image)
# step-5
flavor_id = '2'
flavor = conn.compute.get_flavor(flavor_id)
print(flavor)
# step-6
instance_name = 'testing'
image_args = {
'name': instance_name,
'imageRef': image,
'flavorRef': flavor
}
testing_instance = conn.compute.create_server(**image_args)
print(testing_instance)
# step-7
instances = conn.compute.servers()
for instance in instances:
print(instance)
# step-8
conn.compute.delete_server(testing_instance)
# step-9
print('Checking for existing SSH key pair...')
keypair_name = 'demokey'
keypair_exists = False
for keypair in conn.compute.keypairs():
if keypair.name == keypair_name:
keypair_exists = True
if keypair_exists:
print('Keypair ' + keypair_name + ' already exists. Skipping import.')
else:
print('adding keypair...')
pub_key_file = open(expanduser('~/.ssh/id_rsa.pub')).read()
keypair_args = {
"name": keypair_name,
"public_key": pub_key_file
}
conn.compute.create_keypair(**keypair_args)
for keypair in conn.compute.keypairs():
print(keypair)
# step-10
print('Checking for existing security group...')
security_group_name = 'all-in-one'
security_group_exists = False
for security_group in conn.network.security_groups():
if security_group.name == security_group_name:
all_in_one_security_group = security_group
security_group_exists = True
if security_group_exists:
print('Security Group ' + all_in_one_security_group.name + ' already exists. Skipping creation.')
else:
security_group_args = {
'name' : security_group_name,
'description': 'network access for all-in-one application.'
}
all_in_one_security_group = conn.network.create_security_group(**security_group_args)
security_rule_args = {
'security_group_id': all_in_one_security_group,
'direction': 'ingress',
'protocol': 'tcp',
'port_range_min': '80',
'port_range_max': '80'
}
conn.network.create_security_group_rule(**security_rule_args)
security_rule_args['port_range_min'] = '22'
security_rule_args['port_range_max'] = '22'
conn.network.create_security_group_rule(**security_rule_args)
for security_group in conn.network.security_groups():
print(security_group)
# step-11
userdata = '''#!/usr/bin/env bash
curl -L -s https://git.openstack.org/cgit/openstack/faafo/plain/contrib/install.sh | bash -s -- \
-i faafo -i messaging -r api -r worker -r demo
'''
userdata_b64str = base64.b64encode(userdata)
# step-12
print('Checking for existing instance...')
instance_name = 'all-in-one'
instance_exists = False
for instance in conn.compute.servers():
if instance.name == instance_name:
testing_instance = instance
instance_exists = True
if instance_exists:
print('Instance ' + testing_instance.name + ' already exists. Skipping creation.')
else:
testing_instance_args = {
'name': instance_name,
'imageRef': image,
'flavorRef': flavor,
'key_name': keypair_name,
'user_data': userdata_b64str,
'security_groups': [{'name': all_in_one_security_group.name}]
}
testing_instance = conn.compute.create_server(**testing_instance_args)
conn.compute.wait_for_server(testing_instance)
for instance in conn.compute.servers():
print(instance)
# step-13
print('Checking if Floating IP is already assigned to testing_instance...')
testing_instance_floating_ip = None
for values in testing_instance.addresses.itervalues():
for address in values:
if address['OS-EXT-IPS:type'] == 'floating':
testing_instance_floating_ip = conn.network.find_ip(address['addr'])
unused_floating_ip = None
if not testing_instance_floating_ip:
print('Checking for unused Floating IP...')
for floating_ip in conn.network.ips():
if not floating_ip.fixed_ip_address:
unused_floating_ip = floating_ip
break
if not testing_instance_floating_ip and not unused_floating_ip:
print('No free unused Floating IPs. Allocating new Floating IP...')
public_network_id = conn.network.find_network('public').id
try:
unused_floating_ip = conn.network.create_ip(floating_network_id=public_network_id)
unused_floating_ip = conn.network.get_ip(unused_floating_ip)
print(unused_floating_ip)
except exceptions.HttpException as e:
print(e)
# step-14
if testing_instance_floating_ip:
print('Instance ' + testing_instance.name + ' already has a public ip. Skipping attachment.')
else:
for port in conn.network.ports():
if port.device_id == testing_instance.id:
testing_instance_port = port
testing_instance_floating_ip = unused_floating_ip
conn.network.add_ip_to_port(testing_instance_port, testing_instance_floating_ip)
# step-15
print('The Fractals app will be deployed to http://%s' % testing_instance_floating_ip.floating_ip_address)

View File

@ -123,8 +123,8 @@ To interact with the cloud, you must also have
.. only:: libcloud
`libcloud 0.15.1 or higher installed
<https://libcloud.apache.org/getting-started.html>`_.
`libcloud 0.15.1 or higher installed
<https://libcloud.apache.org/getting-started.html>`_.
.. only:: pkgcloud
@ -135,11 +135,8 @@ To interact with the cloud, you must also have
.. only:: openstacksdk
the OpenStack SDK installed.
.. warning::
This document has not yet been completed for the OpenStack SDK.
a recent version of `openstacksdk <http://python-openstacksdk.readthedocs.org/en/latest/users/index.html>`_
installed.
.. only:: phpopencloud
@ -204,12 +201,12 @@ to run code snippets in your language of choice.
.. only:: openstacksdk
.. code-block:: python
To try it out, add the following code to a Python script (or use an
interactive Python shell) by calling :code:`python -i`.
from openstack import connection
conn = connection.Connection(auth_url="http://controller:5000/v3",
user_name="your_auth_username",
password="your_auth_password", ...)
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-1
:end-before: step-2
.. only:: pkgcloud
@ -273,6 +270,14 @@ to run code snippets in your language of choice.
:start-after: step-1
:end-before: step-2
.. only:: openstacksdk
.. note:: If you receive the exception
:code:`openstack.exceptions.HttpException: HttpException:
401 Client Error: Unauthorized,` while trying to run one
of the following API calls please double-check your
credentials.
Flavors and images
~~~~~~~~~~~~~~~~~~
@ -378,6 +383,19 @@ To list the images that are available in your cloud, run some API calls:
updated_at: '2014-10-15T22:42:52Z'
visibility: public
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-2
:end-before: step-3
You should see output something like this:
.. code-block:: python
openstack.image.v1.image.Image(attrs={u'name': u'ubuntu-14.04', u'container_format': u'bare', u'disk_format': u'qcow2', u'checksum': u'6d8f1c8cf05e1fbdc8b543fda1a9fa7f', u'id': u'cb6b7936-d2c5-4901-8678-c88b3a6ed84c', u'size': 258540032}, loaded=True)
...
You can also get information about available flavors:
@ -480,6 +498,25 @@ You can also get information about available flavors:
swap: ''
vcpus: 1
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-3
:end-before: step-4
You should see output something like this:
.. code-block:: python
openstack.compute.v2.flavor.FlavorDetail(attrs={u'name': u'm1.tiny', u'links': [{u'href': u'http://controller:8774/v2/96ff6aa79e60423d9848b70d5475c415/flavors/1', u'rel': u'self'}, {u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/flavors/1', u'rel': u'bookmark'}], u'ram': 512, u'OS-FLV-DISABLED:disabled': False, u'vcpus': 1, u'swap': u'', u'os-flavor-access:is_public': True, u'rxtx_factor': 1.0, u'OS-FLV-EXT-DATA:ephemeral': 0, u'disk': 1, u'id': u'1'}, loaded=True)
openstack.compute.v2.flavor.FlavorDetail(attrs={u'name': u'm1.small', u'links': [{u'href': u'http://controller:8774/v2/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'self'}, {u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'bookmark'}], u'ram': 2048, u'OS-FLV-DISABLED:disabled': False, u'vcpus': 1, u'swap': u'', u'os-flavor-access:is_public': True, u'rxtx_factor': 1.0, u'OS-FLV-EXT-DATA:ephemeral': 0, u'disk': 20, u'id': u'2'}, loaded=True)
openstack.compute.v2.flavor.FlavorDetail(attrs={u'name': u'm1.medium', u'links': [{u'href': u'http://controller:8774/v2/96ff6aa79e60423d9848b70d5475c415/flavors/3', u'rel': u'self'}, {u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/flavors/3', u'rel': u'bookmark'}], u'ram': 4096, u'OS-FLV-DISABLED:disabled': False, u'vcpus': 2, u'swap': u'', u'os-flavor-access:is_public': True, u'rxtx_factor': 1.0, u'OS-FLV-EXT-DATA:ephemeral': 0, u'disk': 40, u'id': u'3'}, loaded=True)
...
Your images and flavors will be different, of course.
Choose an image and flavor for your instance. You need about 1GB RAM, 1 CPU,
@ -578,8 +615,19 @@ image that you picked in the previous section:
updated_at: '2014-10-27T22:08:55Z'
visibility: public
.. only:: openstacksdk
Next, choose which flavor you want to use:
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-4
:end-before: step-5
You should see output something like this:
.. code-block:: python
openstack.image.v1.image.Image(attrs={u'name': u'ubuntu-14.04', u'container_format': u'bare', u'disk_format': u'qcow2', u'checksum': u'6d8f1c8cf05e1fbdc8b543fda1a9fa7f', u'id': u'cb6b7936-d2c5-4901-8678-c88b3a6ed84c', u'size': 258540032}, loaded=True)
Next, tell the script which flavor you want to use:
.. only:: fog
@ -666,6 +714,18 @@ Next, choose which flavor you want to use:
swap: ''
vcpus: 1
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-5
:end-before: step-6
You should see output something like this:
.. code-block:: python
openstack.compute.v2.flavor.Flavor(attrs={u'name': u'm1.small', u'links': [{u'href': u'http://controller:8774/v2/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'self'}, {u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'bookmark'}], u'ram': 2048, u'OS-FLV-DISABLED:disabled': False, u'vcpus': 1, u'swap': u'', u'os-flavor-access:is_public': True, u'rxtx_factor': 1.0, u'OS-FLV-EXT-DATA:ephemeral': 0, u'disk': 20, 'id': u'2'}, loaded=True)
Now, you're ready to launch the instance.
Launch an instance
@ -705,14 +765,15 @@ Create the instance.
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-6
:end-before: step-7
You should see output something like:
.. code-block:: python
args = {
"name": "testing",
"flavorRef": flavor,
"imageRef": image,
}
instance = conn.compute.create_server(**args)
openstack.compute.v2.server.Server(attrs={'flavorRef': openstack.compute.v2.flavor.Flavor(attrs={u'name': u'm1.small', u'links': [{u'href': u'http://controller:8774/v2/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'self'}, {u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'bookmark'}], u'ram': 2048, u'OS-FLV-DISABLED:disabled': False, u'vcpus': 1, u'swap': u'', u'os-flavor-access:is_public': True, u'rxtx_factor': 1.0, u'OS-FLV-EXT-DATA:ephemeral': 0, u'disk': 20, 'id': u'2'}, loaded=True), 'name': 'testing', 'imageRef': openstack.image.v1.image.Image(attrs={u'name': u'ubuntu14.04', u'container_format': u'bare', u'disk_format': u'qcow2', u'checksum': u'6d8f1c8cf05e1fbdc8b543fda1a9fa7f', u'id': u'cb6b7936-d2c5-4901-8678-c88b3a6ed84c', u'size': 258540032}, loaded=True), 'id': u'a1700b84-dc9a-434e-8f7a-40852e97781c'}, loaded=False)
.. only:: pkgcloud
@ -782,6 +843,12 @@ If you list existing instances:
:end-before: step-8
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-7
:end-before: step-8
The new instance appears.
.. only:: libcloud
@ -794,9 +861,7 @@ The new instance appears.
.. code-block:: python
instances = conn.compute.list_servers()
for instance in instances:
print(instance)
openstack.compute.v2.server.ServerDetail(attrs={u'OS-EXT-STS:task_state': u'scheduling', u'addresses': {}, u'links': [{u'href': u'http://controller:8774/v2/96ff6aa79e60423d9848b70d5475c415/servers/a1700b84-dc9a-434e-8f7a-40852e97781c', u'rel': u'self'}, {u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/servers/a1700b84-dc9a-434e-8f7a-40852e97781c', u'rel': u'bookmark'}], u'image': {u'id': u'cb6b7936-d2c5-4901-8678-c88b3a6ed84c', u'links': [{u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/images/cb6b7936-d2c5-4901-8678-c88b3a6ed84c', u'rel': u'bookmark'}]}, u'OS-EXT-STS:vm_state': u'building', u'OS-SRV-USG:launched_at': None, u'flavor': {u'id': u'2', u'links': [{u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'bookmark'}]}, u'id': u'a1700b84-dc9a-434e-8f7a-40852e97781c', u'user_id': u'59f76712914b44819cf311af43946079', 'imageRef': openstack.compute.v2.image.Image(attrs={u'id': u'cb6b7936-d2c5-4901-8678-c88b3a6ed84c', u'links': [{u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/images/cb6b7936-d2c5-4901-8678-c88b3a6ed84c', u'rel': u'bookmark'}]}, loaded=False), u'OS-DCF:diskConfig': u'MANUAL', u'accessIPv4': u'', u'accessIPv6': u'', u'progress': 0, u'OS-EXT-STS:power_state': 0, u'OS-EXT-AZ:availability_zone': u'nova', u'config_drive': u'', u'status': u'BUILD', u'updated': u'2015-10-12T13:45:37Z', u'hostId': u'', u'OS-SRV-USG:terminated_at': None, u'key_name': None, 'flavorRef': openstack.compute.v2.flavor.Flavor(attrs={u'id': u'2', u'links': [{u'href': u'http://controller:8774/96ff6aa79e60423d9848b70d5475c415/flavors/2', u'rel': u'bookmark'}]}, loaded=False), u'name': u'testing', u'created': u'2015-10-12T13:45:37Z', u'tenant_id': u'96ff6aa79e60423d9848b70d5475c415', u'os-extended-volumes:volumes_attached': [], u'metadata': {}}, loaded=True)
.. only:: pkgcloud
@ -929,6 +994,12 @@ money. Destroy cloud resources to avoid unexpected expenses.
:start-after: step-8
:end-before: step-9
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-8
:end-before: step-9
If you list the instances again, the instance disappears.
Leave your shell open to use it for another instance deployment in this
@ -958,10 +1029,10 @@ instance:
`these instructions <https://help.github.com/articles/generating-ssh- keys/>`_ first.
We'll cover these instructions in depth in :doc:`/introduction`.
.. only:: fog
In the following example, :code:`pub_key_file` should be set to the location
of your public SSH key file.
In the following example, :code:`pub_key_file` should be set to
the location of your public SSH key file.
.. only:: fog
.. literalinclude:: ../samples/fog/getting_started.rb
:language: ruby
@ -971,9 +1042,6 @@ instance:
.. only:: libcloud
In the following example, :code:`pub_key_file` should be set to
the location of your public SSH key file.
.. literalinclude:: ../samples/libcloud/getting_started.py
:start-after: step-9
:end-before: step-10
@ -984,22 +1052,25 @@ instance:
.. only:: pkgcloud
In the following example, :code:`pub_key_file` should be set to
the location of your public SSH key file.
.. literalinclude:: ../samples/pkgcloud/getting_started.js
:start-after: step-9
:end-before: step-10
.. only:: shade
In the following example, :code:`pub_key_file` should be set to
the location of your public SSH key file.
.. literalinclude:: ../samples/shade/getting_started.py
:start-after: step-9
:end-before: step-10
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-9
:end-before: step-10
.. code-block:: python
openstack.compute.v2.keypair.Keypair(attrs={u'public_key': u'ssh-rsa ABAAABAQCyyzkyaPf.....', u'name': u'demokey', u'fingerprint': aa:bb:cc:... '}, loaded=True)
* Network access. By default, OpenStack filters all traffic. You must create
a security group and apply it to your instance. The security group allows HTTP
@ -1030,7 +1101,13 @@ instance:
:start-after: step-10
:end-before: step-11
* User data. During instance creation, you can provide user data to OpenStack to
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-10
:end-before: step-11
* Userdata. During instance creation, you can provide userdata to OpenStack to
configure instances after they boot. The cloud-init service applies the
user data to an instance. You must pre-install the cloud-init service on your
chosen image. We'll go into more detail in :doc:`/introduction`.
@ -1060,6 +1137,14 @@ instance:
:start-after: step-11
:end-before: step-12
.. only:: openstacksdk
.. note:: User data in openstacksdk must be encoded to base64
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-11
:end-before: step-12
Now, you can boot and configure the instance.
Boot and configure an instance
@ -1095,6 +1180,12 @@ request the instance, wait for it to build.
:start-after: step-12
:end-before: step-13
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-12
:end-before: step-13
When the instance boots, the `ex_userdata` variable value instructs the
instance to deploy the Fractals application.
@ -1148,7 +1239,6 @@ address to your instance.
:start-after: step-14
:end-before: step-15
.. only:: pkgcloud
Use :code:`getFloatingIps` to check for unused addresses, selecting the
@ -1177,6 +1267,31 @@ address to your instance.
:start-after: step-13
:end-before: step-14
.. only:: openstacksdk
.. note:: For this example we take Floating IP pool from network
which is called 'public'. This should be your external
network.
List all available Floating IPs for this project and select the first free
one. Allocate new Floating IP if none is available.
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-13
:end-before: step-14
This code returns the floating IP address:
.. code-block:: python
openstack.network.v2.floating_ip.FloatingIP(attrs={u'router_id': None, u'status': u'DOWN', u'tenant_id': u'96ff6aa79e60423d9848b70d5475c415', u'floating_network_id': u'0e43db46-8fd9-4ef1-8826-4cf9e809aede', u'fixed_ip_address': None, u'floating_ip_address': u'203.0.113.101', u'port_id': None, u'id': u'da890b1e-0afa-4724-9af6-0e5ab9cc33dd'}, loaded=True)
You can then attach it to the instance:
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-14
:end-before: step-15
Run the script to start the deployment.
@ -1209,6 +1324,11 @@ by using your preferred browser.
.. literalinclude:: ../samples/shade/getting_started.py
:start-after: step-15
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:start-after: step-15
.. note:: If you do not use floating IPs, substitute another IP address as appropriate
.. figure:: images/screenshot_webinterface.png
@ -1269,3 +1389,8 @@ information, the flavor ID, and image ID.
.. literalinclude:: ../samples/libcloud/getting_started.py
:language: python
.. only:: openstacksdk
.. literalinclude:: ../samples/openstacksdk/getting_started.py
:language: python

View File

@ -9,7 +9,7 @@ for tag in libcloud; do
done
# Draft documents
for tag in dotnet fog pkgcloud shade; do
for tag in dotnet fog openstacksdk pkgcloud shade; do
tools/build-rst.sh firstapp \
--tag ${tag} --target "api-ref/draft/firstapp-${tag}"
done

View File

@ -51,7 +51,7 @@ if [ ${DOCNAME} = "install-guide" ] ; then
TAG="-t obs -t rdo -t ubuntu -t debian"
fi
if [ ${DOCNAME} = "firstapp" ] ; then
TAG="-t libcloud -t dotnet -t fog -t pkgcloud -t shade"
TAG="-t libcloud -t dotnet -t fog -t openstacksdk -t pkgcloud -t shade"
fi
sphinx-build -b gettext $TAG ${DIRECTORY}/source/ \
${DIRECTORY}/source/locale/