Statistics
| Branch: | Tag: | Revision:

root / snf-cyclades-app / synnefo / management / common.py @ 0252fb8b

History | View | Annotate | Download (7.9 kB)

1 11300d7b Giorgos Verigakis
# Copyright 2012 GRNET S.A. All rights reserved.
2 11300d7b Giorgos Verigakis
#
3 11300d7b Giorgos Verigakis
# Redistribution and use in source and binary forms, with or
4 11300d7b Giorgos Verigakis
# without modification, are permitted provided that the following
5 11300d7b Giorgos Verigakis
# conditions are met:
6 11300d7b Giorgos Verigakis
#
7 11300d7b Giorgos Verigakis
#   1. Redistributions of source code must retain the above
8 11300d7b Giorgos Verigakis
#      copyright notice, this list of conditions and the following
9 11300d7b Giorgos Verigakis
#      disclaimer.
10 11300d7b Giorgos Verigakis
#
11 11300d7b Giorgos Verigakis
#   2. Redistributions in binary form must reproduce the above
12 11300d7b Giorgos Verigakis
#      copyright notice, this list of conditions and the following
13 11300d7b Giorgos Verigakis
#      disclaimer in the documentation and/or other materials
14 11300d7b Giorgos Verigakis
#      provided with the distribution.
15 11300d7b Giorgos Verigakis
#
16 11300d7b Giorgos Verigakis
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17 11300d7b Giorgos Verigakis
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 11300d7b Giorgos Verigakis
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19 11300d7b Giorgos Verigakis
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20 11300d7b Giorgos Verigakis
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 11300d7b Giorgos Verigakis
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 11300d7b Giorgos Verigakis
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23 11300d7b Giorgos Verigakis
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24 11300d7b Giorgos Verigakis
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25 11300d7b Giorgos Verigakis
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26 11300d7b Giorgos Verigakis
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27 11300d7b Giorgos Verigakis
# POSSIBILITY OF SUCH DAMAGE.
28 11300d7b Giorgos Verigakis
#
29 11300d7b Giorgos Verigakis
# The views and conclusions contained in the software and
30 11300d7b Giorgos Verigakis
# documentation are those of the authors and should not be
31 11300d7b Giorgos Verigakis
# interpreted as representing official policies, either expressed
32 11300d7b Giorgos Verigakis
# or implied, of GRNET S.A.
33 11300d7b Giorgos Verigakis
34 53b9ba10 Christos Stavrakakis
from django.core.management import CommandError
35 b84ed662 Christos Stavrakakis
from synnefo.db.models import Backend, VirtualMachine, Network, Flavor
36 b84ed662 Christos Stavrakakis
from synnefo.api.util import get_image as backend_get_image
37 9ae613af Christos Stavrakakis
from synnefo.api.faults import ItemNotFound, BadRequest, OverLimit
38 bad9404c Christos Stavrakakis
39 9ae613af Christos Stavrakakis
from synnefo.api.util import validate_network_params
40 9ae613af Christos Stavrakakis
from synnefo.settings import (CYCLADES_ASTAKOS_SERVICE_TOKEN as ASTAKOS_TOKEN,
41 f1ffc695 Stratos Psomadakis
                              ASTAKOS_URL)
42 2333a2c4 Christos Stavrakakis
from synnefo.logic.rapi import GanetiApiError, GanetiRapiClient
43 0252fb8b Christos Stavrakakis
from synnefo.logic.utils import (id_from_instance_name,
44 0252fb8b Christos Stavrakakis
                                 id_from_network_name)
45 3170076a Stratos Psomadakis
from synnefo.lib import astakos
46 11300d7b Giorgos Verigakis
47 8814e07c Christos Stavrakakis
import logging
48 8814e07c Christos Stavrakakis
log = logging.getLogger(__name__)
49 8814e07c Christos Stavrakakis
50 11300d7b Giorgos Verigakis
51 f66d8b04 Christos Stavrakakis
def format_vm_state(vm):
52 f66d8b04 Christos Stavrakakis
    if vm.operstate == "BUILD":
53 f66d8b04 Christos Stavrakakis
        return "BUILD(" + str(vm.buildpercentage) + "%)"
54 f66d8b04 Christos Stavrakakis
    else:
55 f66d8b04 Christos Stavrakakis
        return vm.operstate
56 53b9ba10 Christos Stavrakakis
57 53b9ba10 Christos Stavrakakis
58 53b9ba10 Christos Stavrakakis
def validate_network_info(options):
59 53b9ba10 Christos Stavrakakis
    subnet = options['subnet']
60 53b9ba10 Christos Stavrakakis
    gateway = options['gateway']
61 53b9ba10 Christos Stavrakakis
    subnet6 = options['subnet6']
62 53b9ba10 Christos Stavrakakis
    gateway6 = options['gateway6']
63 53b9ba10 Christos Stavrakakis
64 53b9ba10 Christos Stavrakakis
    try:
65 9ae613af Christos Stavrakakis
        validate_network_params(subnet, gateway)
66 9ae613af Christos Stavrakakis
    except (BadRequest, OverLimit) as e:
67 9ae613af Christos Stavrakakis
        raise CommandError(e)
68 53b9ba10 Christos Stavrakakis
69 53b9ba10 Christos Stavrakakis
    return subnet, gateway, subnet6, gateway6
70 b84ed662 Christos Stavrakakis
71 b84ed662 Christos Stavrakakis
72 b84ed662 Christos Stavrakakis
def get_backend(backend_id):
73 b84ed662 Christos Stavrakakis
    try:
74 b84ed662 Christos Stavrakakis
        backend_id = int(backend_id)
75 b84ed662 Christos Stavrakakis
        return Backend.objects.get(id=backend_id)
76 b84ed662 Christos Stavrakakis
    except ValueError:
77 b84ed662 Christos Stavrakakis
        raise CommandError("Invalid Backend ID: %s" % backend_id)
78 b84ed662 Christos Stavrakakis
    except Backend.DoesNotExist:
79 b84ed662 Christos Stavrakakis
        raise CommandError("Backend with ID %s not found in DB. "
80 b84ed662 Christos Stavrakakis
                           " Use snf-manage backend-list to find"
81 b84ed662 Christos Stavrakakis
                           " out available backend IDs." % backend_id)
82 b84ed662 Christos Stavrakakis
83 b84ed662 Christos Stavrakakis
84 b84ed662 Christos Stavrakakis
def get_image(image_id, user_id):
85 b84ed662 Christos Stavrakakis
    if image_id:
86 b84ed662 Christos Stavrakakis
        try:
87 b84ed662 Christos Stavrakakis
            return backend_get_image(image_id, user_id)
88 b84ed662 Christos Stavrakakis
        except ItemNotFound:
89 b84ed662 Christos Stavrakakis
            raise CommandError("Image with ID %s not found."
90 b84ed662 Christos Stavrakakis
                               " Use snf-manage image-list to find"
91 b84ed662 Christos Stavrakakis
                               " out available image IDs." % image_id)
92 b84ed662 Christos Stavrakakis
    else:
93 b84ed662 Christos Stavrakakis
        raise CommandError("image-id is mandatory")
94 b84ed662 Christos Stavrakakis
95 b84ed662 Christos Stavrakakis
96 b84ed662 Christos Stavrakakis
def get_vm(server_id):
97 0252fb8b Christos Stavrakakis
    """Get a VirtualMachine object by its ID.
98 0252fb8b Christos Stavrakakis

99 0252fb8b Christos Stavrakakis
    @type server_id: int or string
100 0252fb8b Christos Stavrakakis
    @param server_id: The server's DB id or the Ganeti name
101 0252fb8b Christos Stavrakakis

102 0252fb8b Christos Stavrakakis
    """
103 b84ed662 Christos Stavrakakis
    try:
104 b84ed662 Christos Stavrakakis
        server_id = int(server_id)
105 0252fb8b Christos Stavrakakis
    except (ValueError, TypeError):
106 0252fb8b Christos Stavrakakis
        try:
107 0252fb8b Christos Stavrakakis
            server_id = id_from_instance_name(server_id)
108 0252fb8b Christos Stavrakakis
        except VirtualMachine.InvalidBackendIdError:
109 0252fb8b Christos Stavrakakis
            raise CommandError("Invalid server ID: %s" % server_id)
110 0252fb8b Christos Stavrakakis
111 0252fb8b Christos Stavrakakis
    try:
112 b84ed662 Christos Stavrakakis
        return VirtualMachine.objects.get(id=server_id)
113 b84ed662 Christos Stavrakakis
    except VirtualMachine.DoesNotExist:
114 b84ed662 Christos Stavrakakis
        raise CommandError("Server with ID %s not found in DB."
115 b84ed662 Christos Stavrakakis
                           " Use snf-manage server-list to find out"
116 b84ed662 Christos Stavrakakis
                           " available server IDs." % server_id)
117 b84ed662 Christos Stavrakakis
118 b84ed662 Christos Stavrakakis
119 b84ed662 Christos Stavrakakis
def get_network(network_id):
120 0252fb8b Christos Stavrakakis
    """Get a Network object by its ID.
121 0252fb8b Christos Stavrakakis

122 0252fb8b Christos Stavrakakis
    @type network_id: int or string
123 0252fb8b Christos Stavrakakis
    @param network_id: The networks DB id or the Ganeti name
124 0252fb8b Christos Stavrakakis

125 0252fb8b Christos Stavrakakis
    """
126 0252fb8b Christos Stavrakakis
127 b84ed662 Christos Stavrakakis
    try:
128 b84ed662 Christos Stavrakakis
        network_id = int(network_id)
129 0252fb8b Christos Stavrakakis
    except (ValueError, TypeError):
130 0252fb8b Christos Stavrakakis
        try:
131 0252fb8b Christos Stavrakakis
            network_id = id_from_network_name(network_id)
132 0252fb8b Christos Stavrakakis
        except Network.InvalidBackendIdError:
133 0252fb8b Christos Stavrakakis
            raise CommandError("Invalid network ID: %s" % network_id)
134 0252fb8b Christos Stavrakakis
135 0252fb8b Christos Stavrakakis
    try:
136 b84ed662 Christos Stavrakakis
        return Network.objects.get(id=network_id)
137 b84ed662 Christos Stavrakakis
    except Network.DoesNotExist:
138 b84ed662 Christos Stavrakakis
        raise CommandError("Network with ID %s not found in DB."
139 b84ed662 Christos Stavrakakis
                           " Use snf-manage network-list to find out"
140 b84ed662 Christos Stavrakakis
                           " available network IDs." % network_id)
141 b84ed662 Christos Stavrakakis
142 b84ed662 Christos Stavrakakis
143 b84ed662 Christos Stavrakakis
def get_flavor(flavor_id):
144 b84ed662 Christos Stavrakakis
    try:
145 b84ed662 Christos Stavrakakis
        flavor_id = int(flavor_id)
146 b84ed662 Christos Stavrakakis
        return Flavor.objects.get(id=flavor_id)
147 b84ed662 Christos Stavrakakis
    except ValueError:
148 b84ed662 Christos Stavrakakis
        raise CommandError("Invalid flavor ID: %s", flavor_id)
149 b84ed662 Christos Stavrakakis
    except Flavor.DoesNotExist:
150 b84ed662 Christos Stavrakakis
        raise CommandError("Flavor with ID %s not found in DB."
151 b84ed662 Christos Stavrakakis
                           " Use snf-manage flavor-list to find out"
152 b84ed662 Christos Stavrakakis
                           " available flavor IDs." % flavor_id)
153 bad9404c Christos Stavrakakis
154 bad9404c Christos Stavrakakis
155 2333a2c4 Christos Stavrakakis
def check_backend_credentials(clustername, port, username, password):
156 2333a2c4 Christos Stavrakakis
    try:
157 2333a2c4 Christos Stavrakakis
        client = GanetiRapiClient(clustername, port, username, password)
158 2333a2c4 Christos Stavrakakis
        # This command will raise an exception if there is no
159 2333a2c4 Christos Stavrakakis
        # write-access
160 2333a2c4 Christos Stavrakakis
        client.ModifyCluster()
161 2333a2c4 Christos Stavrakakis
    except GanetiApiError as e:
162 2333a2c4 Christos Stavrakakis
        raise CommandError(e)
163 2333a2c4 Christos Stavrakakis
164 2333a2c4 Christos Stavrakakis
    info = client.GetInfo()
165 2333a2c4 Christos Stavrakakis
    info_name = info['name']
166 2333a2c4 Christos Stavrakakis
    if info_name != clustername:
167 2333a2c4 Christos Stavrakakis
        raise CommandError("Invalid clustername value. Please use the"
168 2333a2c4 Christos Stavrakakis
                           " Ganeti Cluster name: %s" % info_name)
169 7a0aa449 Christos Stavrakakis
170 7a0aa449 Christos Stavrakakis
171 8283d6c1 Stratos Psomadakis
class UserCache(object):
172 8283d6c1 Stratos Psomadakis
    """uuid<->displayname user 'cache'"""
173 3fa01ebd Stratos Psomadakis
174 f1ffc695 Stratos Psomadakis
    user_catalogs_url = ASTAKOS_URL.replace("im/authenticate",
175 f1ffc695 Stratos Psomadakis
                                            "service/api/user_catalogs")
176 f1ffc695 Stratos Psomadakis
177 8283d6c1 Stratos Psomadakis
    def __init__(self, split=100):
178 3170076a Stratos Psomadakis
        self.users = {}
179 3170076a Stratos Psomadakis
180 8283d6c1 Stratos Psomadakis
        self.split = split
181 8283d6c1 Stratos Psomadakis
        assert(self.split > 0), "split must be positive"
182 8283d6c1 Stratos Psomadakis
183 8283d6c1 Stratos Psomadakis
    def fetch_names(self, uuid_list):
184 d443e1dd Stratos Psomadakis
        total = len(uuid_list)
185 d443e1dd Stratos Psomadakis
        split = self.split
186 8283d6c1 Stratos Psomadakis
187 d443e1dd Stratos Psomadakis
        for start in range(0, total, split):
188 d443e1dd Stratos Psomadakis
            end = start + split
189 8283d6c1 Stratos Psomadakis
            try:
190 8283d6c1 Stratos Psomadakis
                names = \
191 8283d6c1 Stratos Psomadakis
                    astakos.get_displaynames(token=ASTAKOS_TOKEN,
192 8283d6c1 Stratos Psomadakis
                                             url=UserCache.user_catalogs_url,
193 8283d6c1 Stratos Psomadakis
                                             uuids=uuid_list[start:end])
194 8283d6c1 Stratos Psomadakis
                self.users.update(names)
195 8283d6c1 Stratos Psomadakis
            except Exception as e:
196 8283d6c1 Stratos Psomadakis
                log.error("Failed to fetch names: %s",  e)
197 8283d6c1 Stratos Psomadakis
198 8283d6c1 Stratos Psomadakis
    def get_uuid(self, name):
199 8283d6c1 Stratos Psomadakis
        if not name in self.users:
200 8283d6c1 Stratos Psomadakis
            try:
201 8283d6c1 Stratos Psomadakis
                self.users[name] = \
202 8283d6c1 Stratos Psomadakis
                    astakos.get_user_uuid(token=ASTAKOS_TOKEN,
203 8283d6c1 Stratos Psomadakis
                                          url=UserCache.user_catalogs_url,
204 8283d6c1 Stratos Psomadakis
                                          displayname=name)
205 8283d6c1 Stratos Psomadakis
            except Exception as e:
206 8283d6c1 Stratos Psomadakis
                log.error("Can not get uuid for name %s: %s", name, e)
207 8283d6c1 Stratos Psomadakis
                self.users[name] = name
208 8283d6c1 Stratos Psomadakis
209 8283d6c1 Stratos Psomadakis
        return self.users[name]
210 8283d6c1 Stratos Psomadakis
211 8283d6c1 Stratos Psomadakis
    def get_name(self, uuid):
212 8814e07c Christos Stavrakakis
        """Do the uuid-to-email resolving"""
213 3fa01ebd Stratos Psomadakis
214 3170076a Stratos Psomadakis
        if not uuid in self.users:
215 3fa01ebd Stratos Psomadakis
            try:
216 f1ffc695 Stratos Psomadakis
                self.users[uuid] = \
217 8814e07c Christos Stavrakakis
                    astakos.get_displayname(token=ASTAKOS_TOKEN,
218 8283d6c1 Stratos Psomadakis
                                            url=UserCache.user_catalogs_url,
219 8814e07c Christos Stavrakakis
                                            uuid=uuid)
220 8814e07c Christos Stavrakakis
            except Exception as e:
221 8814e07c Christos Stavrakakis
                log.error("Can not get display name for uuid %s: %s", uuid, e)
222 4500650c Stratos Psomadakis
                self.users[uuid] = "-"
223 3170076a Stratos Psomadakis
224 3170076a Stratos Psomadakis
        return self.users[uuid]
225 4500650c Stratos Psomadakis
226 4500650c Stratos Psomadakis
227 4500650c Stratos Psomadakis
class Omit(object):
228 4500650c Stratos Psomadakis
    pass