summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJoshua Harlow <harlowja@yahoo-inc.com>2012-07-11 11:20:24 -0700
committerJoshua Harlow <harlowja@yahoo-inc.com>2012-07-11 11:20:24 -0700
commiteb939e7765f490529aade46e38ee0f85d8a911dd (patch)
treefff7fc071416d2e19c919bbe3136cfa3aff4ba15
parent7b24230437a27779bafa0828e73ab595c5aeb202 (diff)
downloadvyos-cloud-init-eb939e7765f490529aade46e38ee0f85d8a911dd.tar.gz
vyos-cloud-init-eb939e7765f490529aade46e38ee0f85d8a911dd.zip
Adjust the decoding of the files that are given so that a canonicalize
happens first, which will examine the incoming encoding, and decide the neccasary decoding types needed to get the final resultant string and then use these normalized decoding types to actually do the final decode. Also change the name of the config key that is looked up to 'write_files' since 'files' is pretty generic and could have clashes with other modules. Add an example that shows how to use this in the different encoding formats that are supported.
-rw-r--r--cloudinit/config/cc_write_files.py49
-rw-r--r--doc/examples/cloud-config-write-files.txt32
2 files changed, 73 insertions, 8 deletions
diff --git a/cloudinit/config/cc_write_files.py b/cloudinit/config/cc_write_files.py
index 683eac27..9e8f63a5 100644
--- a/cloudinit/config/cc_write_files.py
+++ b/cloudinit/config/cc_write_files.py
@@ -25,10 +25,11 @@ from cloudinit.settings import PER_INSTANCE
frequency = PER_INSTANCE
DEFAULT_PERMS = 0644
+UNKNOWN_ENC = 'text/plain'
def handle(name, cfg, _cloud, log, _args):
- files = cfg.get('files')
+ files = cfg.get('write_files')
if not files:
log.debug(("Skipping module named %s,"
" no/empty 'files' key in configuration"), name)
@@ -36,6 +37,29 @@ def handle(name, cfg, _cloud, log, _args):
write_files(name, files, log)
+def canonicalize_decoding(enc):
+ if not enc:
+ enc = ''
+ enc = enc.lower().strip()
+ # Translate to a mime-type (or set of) that will be understood
+ # when decoding (for now we only support a limited set of known mime-types)
+ # See: http://tiny.cc/m4kahw
+ # See: http://www.iana.org/assignments/media-types/index.html
+ if enc in ['gz', 'gzip']:
+ # Should we assume that this is 'always' base64?
+ # Someone might of got lucky and not had to encode it?
+ return ['application/x-gzip']
+ if enc in ['gz+base64', 'gzip+base64', 'gz+b64', 'gzip+b64']:
+ return ['application/base64', 'application/x-gzip']
+ if enc in ['base64', 'b64']:
+ return ['application/base64']
+ if enc in ['base32', 'b32']:
+ return ['application/base32']
+ if enc in ['base16', 'b16']:
+ return ['application/base16']
+ return [UNKNOWN_ENC]
+
+
def write_files(name, files, log):
if not files:
return
@@ -47,8 +71,8 @@ def write_files(name, files, log):
i + 1, name)
continue
path = os.path.abspath(path)
- contents = decode_string(f_info.get('content', ''),
- f_info.get('compression'))
+ decodings = canonicalize_decoding(f_info.get('encoding'))
+ contents = decode_contents(f_info.get('content', ''), decodings)
(u, g) = util.extract_usergroup(f_info.get('owner'))
perms = safe_int(f_info.get('permissions'), DEFAULT_PERMS)
util.write_file(path, contents, mode=perms)
@@ -62,8 +86,17 @@ def safe_int(text, default):
return default
-def decode_string(contents, content_type):
- if util.is_true(content_type, addons=['gzip', 'gz']):
- contents_dec = base64.b64decode(contents)
- contents = util.decomp_gzip(contents_dec, quiet=False)
- return contents
+def decode_contents(contents, decodings):
+ result = str(contents)
+ for enc in decodings:
+ if enc == 'application/x-gzip':
+ result = util.decomp_gzip(result, quiet=False)
+ elif enc == 'application/base64':
+ result = base64.b64decode(result)
+ elif enc == 'application/base32':
+ result = base64.b32decode(result)
+ elif enc == 'application/base16':
+ result = base64.b16decode(result)
+ elif enc == UNKNOWN_ENC:
+ pass
+ return result
diff --git a/doc/examples/cloud-config-write-files.txt b/doc/examples/cloud-config-write-files.txt
new file mode 100644
index 00000000..fb0c1541
--- /dev/null
+++ b/doc/examples/cloud-config-write-files.txt
@@ -0,0 +1,32 @@
+#cloud-config
+# vim: syntax=yaml
+#
+# This is the configuration syntax that the write_files module
+# will know how to understand, it can be given b64, b32, b16, or
+# gz (or gz+b64) encoded strings which will be decoded accordingly
+# and then written to the path that is provided.
+#
+# Note: Content strings here are truncated for example purposes.
+#
+write_files:
+- content: CiMgVGhpcyBmaWxlIGNvbnRyb2xzIHRoZSBzdGF0ZSBvZiBTRUxpbnV4IG9u.....
+ encoding: b64
+ path: /etc/sysconfig/selinux
+- content: '
+
+ # My new /etc/sysconfig/samba file
+
+ SMBDOPTIONS="-D"
+
+ '
+ path: /etc/sysconfig/samba
+- content: H4sIADXC/U8C/+1Yf2wbVx1/d7YT122TQEMpadS6kgOZqL30J+.....
+ encoding: gz+b64
+ path: /usr/bin/uptime
+- content: BIRSAU3FOR2GS3THOMQGM33SEB2GQZJAINJE6TRAMRQWK3LPNYXAU===
+ encoding: b32
+ path: /etc/sysconfig/crond
+- content: 0A232053657474696E677320666F7220746865204E4653206461656D6F6E2E0A
+ encoding: b16
+ path: /etc/sysconfig/nfs
+