~lutostag/ubuntu/trusty/maas/1.5.2+packagefix

« back to all changes in this revision

Viewing changes to src/provisioningserver/config.py

  • Committer: Package Import Robot
  • Author(s): Andres Rodriguez
  • Date: 2014-03-28 10:43:53 UTC
  • mto: This revision was merged to the branch mainline in revision 57.
  • Revision ID: package-import@ubuntu.com-20140328104353-ekpolg0pm5xnvq2s
Tags: upstream-1.5+bzr2204
ImportĀ upstreamĀ versionĀ 1.5+bzr2204

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
# Copyright 2012, 2013 Canonical Ltd.  This software is licensed under the
 
1
# Copyright 2012-2014 Canonical Ltd.  This software is licensed under the
2
2
# GNU Affero General Public License version 3 (see the file LICENSE).
3
3
 
4
4
"""MAAS Provisioning Configuration.
5
5
 
6
 
Configuration for most elements of a Cluster Controller can and be obtained by
7
 
using this module's `Config` class. At the time of writing the exceptions are
8
 
the Celery worker's configuration, the `CLUSTER_UUID` and `MAAS_URL`
9
 
environment variables (see `provisioningserver.cluster_config`), and the
10
 
configuration for ``maas-import-pxe-files`` (soon to be deprecated) and
11
 
``maas-import-ephemerals`` (deprecated).
 
6
Configuration for most elements of a Cluster Controller can be obtained
 
7
through this module's `Config` and `BootConfig` classes.  At the time of
 
8
writing the exceptions are the Celery worker's configuration, as well as the
 
9
`CLUSTER_UUID` and `MAAS_URL` environment variables
 
10
(see `provisioningserver.cluster_config`).
12
11
 
13
12
It's pretty simple. Typical usage is::
14
13
 
54
53
 
55
54
__metaclass__ = type
56
55
__all__ = [
 
56
    "BootConfig",
57
57
    "Config",
58
58
    ]
59
59
 
64
64
from shutil import copyfile
65
65
from threading import RLock
66
66
 
67
 
from formencode import Schema
 
67
from formencode import (
 
68
    ForEach,
 
69
    Schema,
 
70
    )
68
71
from formencode.declarative import DeclarativeMeta
69
72
from formencode.validators import (
 
73
    Bool,
70
74
    Int,
71
75
    RequireIfPresent,
72
76
    Set,
106
110
 
107
111
    if_key_missing = None
108
112
 
 
113
    # Obsolete: old TFTP root directory.  This is retained for the purpose of
 
114
    # deriving new, Simplestreams-based import configuration from previously
 
115
    # imported boot images.
 
116
    # The last time this is needed is for upgrading an older cluster
 
117
    # controller to the Ubuntu 14.04 version of MAAS.  After installation of
 
118
    # the 14.04 version, this setting is never used.
109
119
    root = String(if_missing="/var/lib/maas/tftp")
 
120
 
 
121
    # TFTP root directory, managed by the Simplestreams-based import script.
 
122
    # Equates to $storage/current.  The import script maintains "current" as a
 
123
    # symlink pointing to the most recent images.
 
124
    resource_root = String(
 
125
        if_missing="/var/lib/maas/boot-resources/current/")
 
126
 
110
127
    port = Int(min=1, max=65535, if_missing=69)
111
128
    generator = String(if_missing=b"http://localhost/MAAS/api/1.0/pxeconfig/")
112
129
 
117
134
    if_key_missing = None
118
135
 
119
136
 
120
 
class ConfigBootEphemeral(Schema):
121
 
    """Configuration validator for ephemeral boot configuration."""
122
 
 
123
 
    if_key_missing = None
124
 
 
125
 
    images_directory = String(if_missing="/var/lib/maas/ephemeral")
126
 
    releases = Set(if_missing=None)
 
137
class ConfigBootSourceSelection(Schema):
 
138
    """Configuration validator for boot source election onfiguration."""
 
139
 
 
140
    if_key_missing = None
 
141
 
 
142
    release = String(if_missing="*")
 
143
    arches = Set(if_missing=["*"])
 
144
    subarches = Set(if_missing=['*'])
 
145
    labels = Set(if_missing=['*'])
 
146
 
 
147
 
 
148
class ConfigBootSource(Schema):
 
149
    """Configuration validator for boot source configuration."""
 
150
 
 
151
    if_key_missing = None
 
152
 
 
153
    path = String(
 
154
        if_missing="http://maas.ubuntu.com/images/ephemeral/releases/")
 
155
    keyring = String(
 
156
        if_missing="/usr/share/keyrings/ubuntu-cloudimage-keyring.gpg")
 
157
    selections = ForEach(
 
158
        ConfigBootSourceSelection,
 
159
        if_missing=[ConfigBootSourceSelection.to_python({})])
127
160
 
128
161
 
129
162
class ConfigBoot(Schema):
131
164
 
132
165
    if_key_missing = None
133
166
 
134
 
    ephemeral = ConfigBootEphemeral
135
 
    architectures = Set(if_missing=None)
136
 
 
137
 
 
138
 
class ConfigMeta(DeclarativeMeta):
139
 
    """Metaclass for the root configuration schema."""
140
 
 
141
 
    def _get_default_filename(cls):
142
 
        # Avoid circular imports.
143
 
        from provisioningserver.utils import locate_config
144
 
 
145
 
        # Get the configuration filename from the environment. Failing that,
146
 
        # look for the configuration in its default locations.
147
 
        return environ.get(
148
 
            "MAAS_PROVISIONING_SETTINGS",
149
 
            locate_config('pserv.yaml'))
150
 
 
151
 
    def _set_default_filename(cls, filename):
152
 
        # Set the configuration filename in the environment.
153
 
        environ["MAAS_PROVISIONING_SETTINGS"] = filename
154
 
 
155
 
    def _delete_default_filename(cls):
156
 
        # Remove any setting of the configuration filename from the
157
 
        # environment.
158
 
        environ.pop("MAAS_PROVISIONING_SETTINGS", None)
159
 
 
160
 
    DEFAULT_FILENAME = property(
161
 
        _get_default_filename, _set_default_filename,
162
 
        _delete_default_filename, doc=(
163
 
            "The default config file to load. Refers to "
164
 
            "MAAS_PROVISIONING_SETTINGS in the environment."))
165
 
 
166
 
 
167
 
class Config(Schema):
168
 
    """Configuration validator."""
169
 
 
170
 
    __metaclass__ = ConfigMeta
171
 
 
172
 
    if_key_missing = None
173
 
 
174
 
    logfile = String(if_empty=b"pserv.log", if_missing=b"pserv.log")
175
 
    oops = ConfigOops
176
 
    broker = ConfigBroker
177
 
    tftp = ConfigTFTP
178
 
    rpc = ConfigRPC
179
 
    boot = ConfigBoot
 
167
    storage = String(if_missing="/var/lib/maas/boot-resources/")
 
168
    sources = ForEach(
 
169
        ConfigBootSource, if_missing=[ConfigBootSource.to_python({})])
 
170
 
 
171
    # Marker in the bootresources.yaml file: if True, the file has not been
 
172
    # edited yet and needs to be either configured with initial choices, or
 
173
    # rewritten based on previously downloaded boot images.
 
174
    configure_me = Bool(if_missing=False)
 
175
 
 
176
 
 
177
class ConfigBase(Schema):
 
178
    """Base configuration validator."""
180
179
 
181
180
    @classmethod
182
181
    def parse(cls, stream):
242
241
            return deepcopy(cls._cache[filename])
243
242
 
244
243
    @classmethod
 
244
    def flush_cache(cls, filename=None):
 
245
        """Evict a config file, or any cached config files, from cache."""
 
246
        with cls._cache_lock:
 
247
            if filename is None:
 
248
                cls._cache.clear()
 
249
            else:
 
250
                if filename in cls._cache:
 
251
                    del cls._cache[filename]
 
252
 
 
253
    @classmethod
245
254
    def field(target, *steps):
246
255
        """Obtain a field by following `steps`."""
247
256
        for step in steps:
252
261
    def get_defaults(cls):
253
262
        """Return the default configuration."""
254
263
        return cls.to_python({})
 
264
 
 
265
 
 
266
class ConfigMeta(DeclarativeMeta):
 
267
    """Metaclass for the root configuration schema."""
 
268
 
 
269
    envvar = None  # Set this in subtypes.
 
270
    default = None  # Set this in subtypes.
 
271
 
 
272
    def _get_default_filename(cls):
 
273
        # Avoid circular imports.
 
274
        from provisioningserver.utils import locate_config
 
275
 
 
276
        # Get the configuration filename from the environment. Failing that,
 
277
        # look for the configuration in its default locations.
 
278
        return environ.get(cls.envvar, locate_config(cls.default))
 
279
 
 
280
    def _set_default_filename(cls, filename):
 
281
        # Set the configuration filename in the environment.
 
282
        environ[cls.envvar] = filename
 
283
 
 
284
    def _delete_default_filename(cls):
 
285
        # Remove any setting of the configuration filename from the
 
286
        # environment.
 
287
        environ.pop(cls.envvar, None)
 
288
 
 
289
    DEFAULT_FILENAME = property(
 
290
        _get_default_filename, _set_default_filename,
 
291
        _delete_default_filename, doc=(
 
292
            "The default config file to load. Refers to "
 
293
            "`cls.envvar` in the environment."))
 
294
 
 
295
 
 
296
class Config(ConfigBase):
 
297
    """Configuration for the provisioning server."""
 
298
 
 
299
    class __metaclass__(ConfigMeta):
 
300
        envvar = "MAAS_PROVISIONING_SETTINGS"
 
301
        default = "pserv.yaml"
 
302
 
 
303
    if_key_missing = None
 
304
 
 
305
    logfile = String(if_empty=b"pserv.log", if_missing=b"pserv.log")
 
306
    oops = ConfigOops
 
307
    broker = ConfigBroker
 
308
    tftp = ConfigTFTP
 
309
    rpc = ConfigRPC
 
310
 
 
311
 
 
312
class BootConfig(ConfigBase):
 
313
    """Configuration for boot resources."""
 
314
 
 
315
    class __metaclass__(ConfigMeta):
 
316
        envvar = "MAAS_BOOT_RESOURCES_SETTINGS"
 
317
        default = "bootresources.yaml"
 
318
 
 
319
    if_key_missing = None
 
320
 
 
321
    boot = ConfigBoot