From 86398b35d3c8479d68ef33c036c9db4c6b26cedb Mon Sep 17 00:00:00 2001
From: Thomas Reifenberger <tom-mi@users.noreply.github.com>
Date: Sun, 15 Nov 2015 14:03:42 +0100
Subject: [PATCH] Add functions to load and pack to files

---
 mkp/__init__.py              | 26 ++++++++++++++++++++++----
 test/integration/test_mkp.py | 34 ++++++++++++++++++++++++++++++++++
 2 files changed, 56 insertions(+), 4 deletions(-)

diff --git a/mkp/__init__.py b/mkp/__init__.py
index 9d58c74..e64003c 100644
--- a/mkp/__init__.py
+++ b/mkp/__init__.py
@@ -19,6 +19,11 @@ _DIRECTORIES = [
 _VERSION_PACKAGED = 'python-mkp'
 
 
+def load_file(path):
+    file_io = open(path, 'rb')
+    return Package(file_io)
+
+
 def load_bytes(data):
     bytes_io = io.BytesIO(data)
     return Package(bytes_io)
@@ -49,11 +54,16 @@ def _find_files_in_directory(path):
     return result
 
 
+def pack_to_file(info, path, outfile):
+    with open(outfile, 'wb') as f:
+        f.write(pack_to_bytes(info, path))
+
+
 def pack_to_bytes(info, path):
     _patch_info(info)
     bytes_io = io.BytesIO()
     with tarfile.open(fileobj=bytes_io, mode='w:gz') as archive:
-        info_data = pprint.pformat(info).encode()
+        info_data = encode_info(info)
         tarinfo, fileobj = _create_tarinfo_and_buffer(info_data, 'info')
         archive.addfile(tarinfo, fileobj=fileobj)
 
@@ -89,15 +99,23 @@ def _create_tarinfo_and_buffer(data, filename):
     return tarinfo, bytes_io
 
 
+def encode_info(info):
+    return pprint.pformat(info).encode()
+
+
+def decode_info(info_bytes):
+    return ast.literal_eval(info_bytes.decode())
+
+
 class Package(object):
 
     def __init__(self, fileobj):
         self.archive = tarfile.open(fileobj=fileobj)
-        self._info = self._load_info()
+        self._info = self._get_info()
 
-    def _load_info(self):
+    def _get_info(self):
         info_file = self.archive.extractfile('info')
-        return ast.literal_eval(info_file.read().decode())
+        return decode_info(info_file.read())
 
     @property
     def info(self):
diff --git a/test/integration/test_mkp.py b/test/integration/test_mkp.py
index cf0d5c6..f61af32 100644
--- a/test/integration/test_mkp.py
+++ b/test/integration/test_mkp.py
@@ -17,6 +17,15 @@ def test_load_bytes(original_mkp_file):
     assert package.info['title'] == 'Title of test'
 
 
+def test_load_file(original_mkp_file, tmpdir):
+    tmpdir.join('test.mkp').write_binary(original_mkp_file)
+
+    package = mkp.load_file(str(tmpdir.join('test.mkp')))
+
+    assert type(package) == mkp.Package
+    assert package.info['title'] == 'Title of test'
+
+
 def test_extract_files(original_mkp_file, tmpdir):
     package = mkp.load_bytes(original_mkp_file)
 
@@ -51,6 +60,31 @@ def test_pack_to_bytes(tmpdir):
     assert agent_file.read() == b'hello'
 
 
+def test_pack_to_file(tmpdir):
+    info = {
+        'files': {'agents': ['special/agent_test']},
+        'title': 'Test package',
+    }
+    tmpdir.join('agents', 'special', 'agent_test').write_binary(b'hello', ensure=True)
+
+    outfile = tmpdir.join('test.mkp')
+
+    mkp.pack_to_file(info, str(tmpdir), str(outfile))
+
+    archive = tarfile.open(str(outfile))
+
+    info_file = archive.extractfile('info').read()
+    extracted_info = ast.literal_eval(info_file.decode())
+    assert extracted_info['files'] == info['files']
+    assert extracted_info['title'] == info['title']
+    assert extracted_info['version.packaged'] == 'python-mkp'
+
+    agents_archive_file = archive.extractfile('agents.tar')
+    agents_archive = tarfile.open(fileobj=agents_archive_file, mode='r:')
+    agent_file = agents_archive.extractfile('special/agent_test')
+    assert agent_file.read() == b'hello'
+
+
 def test_find_files_searches_all_directories(tmpdir):
     for directory in DIRECTORIES:
         tmpdir.join(directory, 'test').write_binary(b'Foo', ensure=True)
-- 
GitLab