{ "info": { "author": "Tristen Horton", "author_email": "tristen@tristenhorton.com", "bugtrack_url": null, "classifiers": [ "License :: OSI Approved :: Apache Software License", "Operating System :: OS Independent", "Programming Language :: Python :: 3.6" ], "description": "# pakk\n\nEncrypt and pack several files or folders into a single invokable file.\n\nThis package comes equipped with a CLI tool and a simple library for working with pakk files. See the sections below regarding each.\n\n## Getting Started\n\nPakk is built to work on Python 3.6 and above.\n\nInstall:\n```sh\n$ python3 -m pip install pakk\n```\n\nUsing the CLI:\n```sh\n# pakk 'somefile.txt' and all the files in './somefolder' into 'files.pakk'\n# encrypting with the password 'kitty'\n$ pakk pakk -o files.pakk -p kitty somefile.txt ./somefolder\n\n# unpakk 'files.pakk' into all the original files\n$ pakk unpakk -o . -p kitty files.pakk\n```\n\nUsing the library:\n```py\nimport hashlib\nimport pakk\n\n# encrypt with the password 'kitty'\npassword = \"kitty\"\nkey = hashlib.sha256(password.encode(\"utf-8\")).digest()\n\n# pakk 'somefile.txt' and all the files in './somefolder' into 'files.pakk'\nwith open(\"./files.pakk\", \"wb\") as out_file:\n pakk_files(key, [\"files.pakk\", \"./somefolder\"], out_file)\n\n# unpakk `files.pakk` into all the original files\nunpakk_files(key, \"./files.pakk\")\n```\n\n## CLI\n\nThe pakk CLI tool has two subcommands: `pakk` and `unpakk`. Here are their help outputs:\n\n```\n$ pakk pakk --help\nusage: pakk pakk [-h] [-o OUTPUT] [-p PASSWORD] [-c CHUNKSIZE] input\n\nEncrypts the contents of a specified folder and packs the encrypted content\ninto a single pakk.\n\npositional arguments:\n input input folder to encrypt and pakk.\n\noptional arguments:\n -h, --help show this help message and exit\n -o OUTPUT, --output OUTPUT\n output path of the pakk file.\n -p PASSWORD, --password PASSWORD\n password used to encrypt the contents of the pakk.\n Defaults to 'IsPakked'. It is HIGHLY recommended that\n you supply your own secure password with high entropy\n for each pakk.\n -c CHUNKSIZE, --chunksize CHUNKSIZE\n maximum amount of bytes to encrypt at once when\n pakking files in the folder. Must be an integer\n multiple of 1024. Defaults to 64*1024\n```\n\n```\n$ pakk unpakk --help\nusage: pakk unpakk [-h] [-o OUTPUT] [-p PASSWORD] [-c CHUNKSIZE] input\n\nDecrypts the contents of a specified pakk and unpacks it into an identical\nfolder structure as was originally packed.\n\npositional arguments:\n input input pakk file to decrypt and unpakk.\n\noptional arguments:\n -h, --help show this help message and exit\n -o OUTPUT, --output OUTPUT\n path of the folder to output the pakk contents to.\n -p PASSWORD, --password PASSWORD\n password used to decrypt the contents of the pakk.\n Must be the same password used when the pakk was\n created, otherwise decryption will fail. Defaults to\n 'IsPakked'. It is HIGHLY recommended that you supply\n your own secure password with high entropy for each\n pakk.\n -c CHUNKSIZE, --chunksize CHUNKSIZE\n maximum amount of bytes to decrypt at once when\n unpakking files in the folder. Must be an integer\n multiple of 1024. Defaults to 24*1024\n```\n\n## Library\n\npakk provides a [few functions and types](#API) for working with pakk buffers and files. In most use cases, `pakk_files` and `unpakk` are used to create pakk files and access data from pakk files.\n\n### Example\n\nKeys should be AES-compatible and are typically bytes-like objects:\n```py\nimport hashlib\n\npassword = \"kitty\"\nkey = hashlib.sha256(password.encode(\"utf-8\")).digest()\n```\n\nYou can pakk a single file using `pakk_files`:\n```py\nwith open(\"./outputfile.pakk\", \"wb\") as out_file:\n pakk_files(key, [\"./some/file\"], out_file)\n```\n\nAnd to unpakk back into files, use `unpakk_files`:\n```py\nunpakk_files(key, \"./outputfile.pakk\")\n```\n\nIf you want to invoke a pakks file without unpakking it into the original file structure, use `unpakk`:\n```py\nwith open(\"./outputfile.pakk\", \"rb\") as in_file:\n pakk = unpakk(key, in_file)\n\nfor key, blob in pakk.blobs.items():\n print(f\"{key}: {blob.name}\")\n```\n\n### API\n\n```py\nclass PakkBlob:\n \"\"\"A named stream of blob data, typically represents a single pakk file.\n\n Attributes:\n name (str): The preferrably unique but pronouncable name of the blob.\n size (int): The size of the blob in bytes.\n stream (:obj:`io.BufferedIOBase`): A buffered stream to the blob of data.\n \"\"\"\n\nclass Pakk:\n \"\"\"A collection of blobs. Typically correlates to a pakk file.\n\n Attributes:\n blobs (:obj:`dict` of :obj:`str` to :obj:`PakkBlob`): a dictionary of blobs in this pakk where the key is each blob's name.\n \"\"\"\n\ndef pakk(key: bytes, data: List[PakkBlob], output: io.BufferedIOBase, chunksize=64*1024):\n \"\"\"Encrypt and pakk an input :class:`list` of :class:`PakkBlob` into a single buffered output.\n\n .. note::\n\n Appends to the current position in the output stream.\n\n Args:\n key (bytes): the key to encrypt the incoming blobs with, using SHA256\n data (list of :class:`PakkBlob`): the blobs to encrypt and pakk into the output buffer\n output (:class:`io.BufferedIOBase`): the buffer to write the pakk file data to\n\n Kwargs:\n chunksize (int): the max size, in bytes, of the chunks to write to the output buffer\n \"\"\"\n\ndef unpakk(key: bytes, data: io.BufferedIOBase, chunksize=24*1024) -> Pakk:\n \"\"\"Unpakk and decrypt a buffered stream of pakk file data.\n\n .. note::\n\n Reads from the current position in the stream.\n\n Args:\n key (bytes): the key to decrypt the pakk blobs with, using SHA256\n data (:class:`io.BufferedIOBase`): the buffer to read pakk file data from\n\n Kwargs:\n chunksize (int): the max size, in bytes, of the chunks to read from the data buffer\n\n Returns:\n :class:`Pakk`. The pakks blob info and decrypted blob data.\n \"\"\"\n\ndef pakk_bytes(key, data: List[bytes], output: io.BufferedIOBase):\n \"\"\"Encrypt and pakk an input :class:`list` of :class:`bytes` into a single buffered output.\n\n .. note::\n\n Appends to the current position in the output stream.\n\n Args:\n key (bytes): the key to encrypt the incoming blobs with, using SHA256\n data (list of :class:`bytes`): the bytes objects to encrypt and pakk into the output buffer\n output (:class:`io.BufferedIOBase`): the buffer to write the pakk file data to\n\n Kwargs:\n chunksize (int): the max size, in bytes, of the chunks to write to the output buffer\n \"\"\"\n\ndef unpakk_bytes(key, data: io.BufferedIOBase) -> List[bytes]:\n \"\"\"Unpakk and decrypt a buffered stream of pakk file data into a list of bytes objects.\n\n .. note::\n\n Reads from the current position in the stream.\n\n Args:\n key (bytes): the key to decrypt the pakk blobs with, using SHA256\n data (:class:`io.BufferedIOBase`): the buffer to read pakk file data from\n\n Kwargs:\n chunksize (int): the max size, in bytes, of the chunks to read from the data buffer\n\n Returns:\n list of bytes-objects. The decrypted blob data from the pakk file stream.\n \"\"\"\n\ndef pakk_files(key, files: List[str], destination: Union[io.BufferedIOBase, str], chunksize=64*1024):\n \"\"\"Encrypt and pakk specified files and folders into a single buffered output.\n\n .. note::\n\n Appends to the current position in the output stream.\n\n Args:\n key (bytes): the key to encrypt the incoming blobs with, using SHA256\n files (list of strings): the list of file and folders to encrypt and pakk\n destination (:class:`io.BufferedIOBase` or str): the buffer or file path to write the pakk file data to\n\n Kwargs:\n chunksize (int): the max size, in bytes, of the chunks to write to the output buffer\n \"\"\"\n\ndef unpakk_files(key, file: str, destination=os.curdir, chunksize=24*1024):\n \"\"\"Unpakk and decrypt a pakk file at a specified path, writing the data into the original file structure at a specified root path.\n\n Args:\n key (bytes): the key to decrypt the pakk blobs with, using SHA256\n file (str): the path of the pakk file to unpakk and decrypt\n destination (str): the folder to output the unpakked files to\n\n Kwargs:\n chunksize (int): the max size, in bytes, of the chunks to read from the data buffer\n \"\"\"\n```\n\n\n", "description_content_type": "text/markdown", "docs_url": null, "download_url": "", "downloads": { "last_day": -1, "last_month": -1, "last_week": -1 }, "home_page": "https://github.com/pakk/pakk", "keywords": "", "license": "", "maintainer": "", "maintainer_email": "", "name": "pakk", "package_url": "https://pypi.org/project/pakk/", "platform": "", "project_url": "https://pypi.org/project/pakk/", "project_urls": { "Homepage": "https://github.com/pakk/pakk" }, "release_url": "https://pypi.org/project/pakk/2.1.0/", "requires_dist": null, "requires_python": "", "summary": "A package for encrypting and packing files into a single uncompressed file.", "version": "2.1.0" }, "last_serial": 4360906, "releases": { "0.1.0": [ { "comment_text": "", "digests": { "md5": "454e33a585d6d230df06086560bdfbd0", "sha256": "bae90d330714159858d230619d5f3193f51f7dfcfea008898977350dbe3b339f" }, "downloads": -1, "filename": "pakk-0.1.0-py3-none-any.whl", "has_sig": false, "md5_digest": "454e33a585d6d230df06086560bdfbd0", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 6512, "upload_time": "2018-09-06T23:46:11", "url": "https://files.pythonhosted.org/packages/f4/df/13611d6bc77166214fcef819f7507ea0d9cd16473e1c58af42622cbd69c1/pakk-0.1.0-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "cc04e60d51bce87f69e04b6e1987796c", "sha256": "42a953be99983d9c3b0c6bd5dc40ad6c72295edd726e01fa6fe093900812a860" }, "downloads": -1, "filename": "pakk-0.1.0.tar.gz", "has_sig": false, "md5_digest": "cc04e60d51bce87f69e04b6e1987796c", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 5860, "upload_time": "2018-09-06T23:46:12", "url": "https://files.pythonhosted.org/packages/c3/c7/9b04c9db761a8a45d5426a924e7376e13a33bc483d60400de4204a23bb50/pakk-0.1.0.tar.gz" } ], "0.1.1": [ { "comment_text": "", "digests": { "md5": "e7e9bba9945de96c2f9be9f1c6f076e7", "sha256": "e50ddcaf7f2a28cc06a4284c544ea7e72772e9cd04fbab133613fdf3217ec2e0" }, "downloads": -1, "filename": "pakk-0.1.1-py3-none-any.whl", "has_sig": false, "md5_digest": "e7e9bba9945de96c2f9be9f1c6f076e7", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8607, "upload_time": "2018-09-07T17:38:42", "url": "https://files.pythonhosted.org/packages/cd/35/f1fbb2b5baf04480fe5fd3d81d609c6acc1b0caa8f8d9648e07542cc906e/pakk-0.1.1-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "65fca5863ecdfa56dc2aca2d17585c2d", "sha256": "944d68a79c3cb5590d3aa4dd080b087308ee307aa7e46c1390807ee72a05e656" }, "downloads": -1, "filename": "pakk-0.1.1.tar.gz", "has_sig": false, "md5_digest": "65fca5863ecdfa56dc2aca2d17585c2d", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 8263, "upload_time": "2018-09-07T17:38:45", "url": "https://files.pythonhosted.org/packages/60/49/c3093815a83784f90b162894410af97431ec8162f2a614e3e62949bd35f9/pakk-0.1.1.tar.gz" } ], "1.0.0": [ { "comment_text": "", "digests": { "md5": "7e1ae9552a98d37d002e10ee8a546a9a", "sha256": "e6d93bffc3cfaa9eba7efae6e7d6db42f64b0a8eeda1bb7f9d193a3971020b8c" }, "downloads": -1, "filename": "pakk-1.0.0-py3-none-any.whl", "has_sig": false, "md5_digest": "7e1ae9552a98d37d002e10ee8a546a9a", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8607, "upload_time": "2018-09-07T17:38:44", "url": "https://files.pythonhosted.org/packages/15/cd/23be153bc1ab374fee8306f9a3ac23ecaaf86799ad74f2fac668a8be050e/pakk-1.0.0-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "005ad393da3988981ab94030349cb2b9", "sha256": "8656b9d1ba23299ea754412ff3c4784c177c3b40f8dcca0e8ff2a8b956203fa0" }, "downloads": -1, "filename": "pakk-1.0.0.tar.gz", "has_sig": false, "md5_digest": "005ad393da3988981ab94030349cb2b9", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 8214, "upload_time": "2018-09-07T17:38:46", "url": "https://files.pythonhosted.org/packages/98/81/23eef6b494df0f81077ffac7dd503909e79c17ef5b5702a6be16fdcae62a/pakk-1.0.0.tar.gz" } ], "1.0.1": [ { "comment_text": "", "digests": { "md5": "ab88d25f17dd03458f38796305241c04", "sha256": "d355469c7dcf5b15d9bfbc3817488cf1e2bba3224e0ed752bd09cb810188035e" }, "downloads": -1, "filename": "pakk-1.0.1-py3-none-any.whl", "has_sig": false, "md5_digest": "ab88d25f17dd03458f38796305241c04", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8605, "upload_time": "2018-09-24T17:19:02", "url": "https://files.pythonhosted.org/packages/22/74/6d002bbe6163f612fcb0366df57f5aaaf29bb96662a3ae3685a8e1bb33f0/pakk-1.0.1-py3-none-any.whl" } ], "1.0.2": [ { "comment_text": "", "digests": { "md5": "20cda8913562f5a3d92f0a1d984fee3c", "sha256": "10075df7167eb3069e2839f62467f3d7ff18ceb22772bd240e9d713177714a2f" }, "downloads": -1, "filename": "pakk-1.0.2-py3-none-any.whl", "has_sig": false, "md5_digest": "20cda8913562f5a3d92f0a1d984fee3c", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8605, "upload_time": "2018-09-24T17:23:11", "url": "https://files.pythonhosted.org/packages/cc/42/467c206eb5375ed8b1b1b31fb0a765cc920dbffe0011d8fa25fbffb5ff59/pakk-1.0.2-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "5e75e6099c6d76307e14bf761849d4ee", "sha256": "26853ca77dd58ee5ea2bb2d28cb1ea0fe617d61c54937803b95dfca3109717e1" }, "downloads": -1, "filename": "pakk-1.0.2.tar.gz", "has_sig": false, "md5_digest": "5e75e6099c6d76307e14bf761849d4ee", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 8228, "upload_time": "2018-09-24T17:23:13", "url": "https://files.pythonhosted.org/packages/95/43/544b753d09dd0885a7df848b30c879734c8ade0de0e63e35813420ccb70a/pakk-1.0.2.tar.gz" } ], "2.0.0": [ { "comment_text": "", "digests": { "md5": "426c1637035d4615750014bb69ef2003", "sha256": "de79461cbbb00f7b91cbf082eef606a1181d688d33cf7e405b9ca80a70dba91c" }, "downloads": -1, "filename": "pakk-2.0.0-py3-none-any.whl", "has_sig": false, "md5_digest": "426c1637035d4615750014bb69ef2003", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8630, "upload_time": "2018-09-26T18:28:44", "url": "https://files.pythonhosted.org/packages/1f/9c/df260aac3eacbf533ab4ae4ae387810084ef2a44a0c463f45a55af022193/pakk-2.0.0-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "1e5746175a875fe256798fdc385c7c28", "sha256": "b34053ed775444b73b5bcda6b76d5f46af3a3b6561eb6986de09f9d201300f73" }, "downloads": -1, "filename": "pakk-2.0.0.tar.gz", "has_sig": false, "md5_digest": "1e5746175a875fe256798fdc385c7c28", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 8267, "upload_time": "2018-09-26T18:28:45", "url": "https://files.pythonhosted.org/packages/24/b9/c5d426e08657b05df178fb712dd9e0418a8950948a1e251bf5f7a883b00c/pakk-2.0.0.tar.gz" } ], "2.0.1": [ { "comment_text": "", "digests": { "md5": "c53cf250a1a8840ecc9cbc9391d35290", "sha256": "327260cceb7c8e9e908d77a79d6cf2d1ce7ad8d1f2ae993f5846291de5729754" }, "downloads": -1, "filename": "pakk-2.0.1-py3-none-any.whl", "has_sig": false, "md5_digest": "c53cf250a1a8840ecc9cbc9391d35290", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8637, "upload_time": "2018-09-26T18:45:41", "url": "https://files.pythonhosted.org/packages/c0/29/e116ed76b9c95156b34e311bacc23072673ca80d3fe2575e8fa63560bf6d/pakk-2.0.1-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "93315119cb23b395d0e69d4c512dc20f", "sha256": "59d9bfb27114d0889338b038caf1c8b4d144c967a315ebc0d800d8242fb1bf04" }, "downloads": -1, "filename": "pakk-2.0.1.tar.gz", "has_sig": false, "md5_digest": "93315119cb23b395d0e69d4c512dc20f", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 8271, "upload_time": "2018-09-26T18:45:47", "url": "https://files.pythonhosted.org/packages/bf/13/9c3d38648d1a18be105f0de660fb540adbe8410ce7e4bc48be642f5e8395/pakk-2.0.1.tar.gz" } ], "2.1.0": [ { "comment_text": "", "digests": { "md5": "39c612c7ec527d3fe916ebecbd7567d9", "sha256": "4996b29492745c38656800df7482bb1ed2c8e6ad9f56f203543ddbf494a9dfa2" }, "downloads": -1, "filename": "pakk-2.1.0-py3-none-any.whl", "has_sig": false, "md5_digest": "39c612c7ec527d3fe916ebecbd7567d9", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8685, "upload_time": "2018-10-10T17:17:50", "url": "https://files.pythonhosted.org/packages/13/25/466c79a27a13f7c2595d2dc42f9ca1a2f402006fef825d984df968e1da46/pakk-2.1.0-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "fbef2f44fca015a3c9eda0919817cf4a", "sha256": "d92404582dddd3e083bde964d33bd9519e8fc515a79901499bd67b7f69296429" }, "downloads": -1, "filename": "pakk-2.1.0.tar.gz", "has_sig": false, "md5_digest": "fbef2f44fca015a3c9eda0919817cf4a", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 8324, "upload_time": "2018-10-10T17:17:52", "url": "https://files.pythonhosted.org/packages/fc/d1/7fde64ab1a5093738afc6a71b1f9e875c13a92f5fa2f9a8a75cf7f52319b/pakk-2.1.0.tar.gz" } ] }, "urls": [ { "comment_text": "", "digests": { "md5": "39c612c7ec527d3fe916ebecbd7567d9", "sha256": "4996b29492745c38656800df7482bb1ed2c8e6ad9f56f203543ddbf494a9dfa2" }, "downloads": -1, "filename": "pakk-2.1.0-py3-none-any.whl", "has_sig": false, "md5_digest": "39c612c7ec527d3fe916ebecbd7567d9", "packagetype": "bdist_wheel", "python_version": "py3", "requires_python": null, "size": 8685, "upload_time": "2018-10-10T17:17:50", "url": "https://files.pythonhosted.org/packages/13/25/466c79a27a13f7c2595d2dc42f9ca1a2f402006fef825d984df968e1da46/pakk-2.1.0-py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "fbef2f44fca015a3c9eda0919817cf4a", "sha256": "d92404582dddd3e083bde964d33bd9519e8fc515a79901499bd67b7f69296429" }, "downloads": -1, "filename": "pakk-2.1.0.tar.gz", "has_sig": false, "md5_digest": "fbef2f44fca015a3c9eda0919817cf4a", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 8324, "upload_time": "2018-10-10T17:17:52", "url": "https://files.pythonhosted.org/packages/fc/d1/7fde64ab1a5093738afc6a71b1f9e875c13a92f5fa2f9a8a75cf7f52319b/pakk-2.1.0.tar.gz" } ] }