瀏覽代碼

Enhance parse_ignition file content decoding

Review of MCD/ignition code reveals that data is encoded
in file contents following RFC 2397.

This commit vendors in code from upstream python to support
more robust parsing of this scheme.
Michael Gugino 6 年之前
父節點
當前提交
c5287ced5d
共有 1 個文件被更改,包括 21 次插入5 次删除
  1. 21 5
      roles/lib_utils/action_plugins/parse_ignition.py

+ 21 - 5
roles/lib_utils/action_plugins/parse_ignition.py

@@ -8,17 +8,33 @@ from ansible import errors
 from six.moves import urllib
 
 
+# pylint: disable=too-many-function-args
+def get_file_data(encoded_contents):
+    """Decode data URLs as specified in RFC 2397"""
+    # The following source is adapted from Python3 source
+    # License: https://github.com/python/cpython/blob/3.7/LICENSE
+    # retrieved from: https://github.com/python/cpython/blob/3.7/Lib/urllib/request.py
+    _, data = encoded_contents.split(":", 1)
+    mediatype, data = data.split(",", 1)
+
+    # even base64 encoded data URLs might be quoted so unquote in any case:
+    data = urllib.parse.unquote(data)
+    if mediatype.endswith(";base64"):
+        data = base64.b64decode(data).decode('utf-8')
+        mediatype = mediatype[:-7]
+    # End PSF software
+    return data
+
+
+# pylint: disable=too-many-function-args
 def get_files(files_dict, systemd_dict, dir_list, data):
     """parse data to populate file_dict"""
     for item in data['storage']['files']:
         path = item["path"]
         dir_list.add(os.path.dirname(path))
         # remove prefix "data:,"
-        encoding, contents = item['contents']['source'].split(',', 1)
-        if 'base64' in encoding:
-            contents = base64.b64decode(contents).decode('utf-8')
-        else:
-            contents = urllib.parse.unquote(contents)
+        encoded_contents = item['contents']['source']
+        contents = get_file_data(encoded_contents)
         # convert from int to octal, padding at least to 4 places.
         # eg, 420 becomes '0644'
         mode = str(format(int(item["mode"]), '04o'))