{
  "endpoint": "https://loader.artpipe.epicgames.com",
  "hash": "540d0101df2b662d002355204651f2cd",
  "url": "https://unpipe-loader-bucket.s3.amazonaws.com/unpipe_loader.zip?AWSAccessKeyId=ASIATA4GVB54AHPPYHXC&Signature=k9WvT67BXmyDcP0h04%2BqemXtkWo%3D&x-amz-security-token=IQoJb3JpZ2luX2VjEE4aCXVzLWVhc3QtMSJHMEUCIBQ3I6qkzLBTureuQgreuyd42p8yrUt9kRZ72URE1xXyAiEA2hnV3CY%2FtPlNUkIz41G17Y2NE6Kx5YqE8JZjOaHiaMgq4AMIFxABGgwyMDgwNTE0NDE1MjgiDNw0o8v39Ey8mIIAsiq9A8mI%2FwPrPksFTP2VotBHWwlY1rGF1QDr%2B4aPZcE1Q8sKzIru1%2B4Sw6xdA%2BOKFE684hOtUUpJB2aRmG4MEQOrtqB6b5svhuVehOzWNFPJDTTt%2B7%2BrkoRIbJqn8rnOlihpkb7nBfEtpIhkYUlwgLpNgVGsHImi%2BEzc%2BvRfG8aXrYRY7a42pccWNiS30ct7Dbu52oz6WTsi3cVfbTHZQIGv5alcvEJz%2FADLkzGRnVFAxMGK7RsAApTyWXxTMvBnuf2oqTunWshGpiDBCpdRkAsi%2FIPOgbWbU9%2BsUsBZyCaAhwKdbfO8NovmsCuCQHKQribqeLsmyXImriJlyNlBVSCqWno2d2ivMhYU%2FV1V3F7dtdbBk0mZUTg5Dqw%2BgPihAZPA8mTb3wco6byd6dLpX8sMyeaQfkwv%2FSApjsl2e0ru5zT%2FKxdWyMG34q6QPCzHsLAfuJzhi12FtQhJS9mOkhB6kD2FcHf%2FywFNhvBtkOt7oFQ%2FYR0%2BM4voiBig8aO7i1tuCEDBsLnfcyipQJ8XYZ1Kk8s7gJBC7mtY8kXsHgzlr52Ld5Rsdfg25UnmKmhMpY5eziV0hUkxo9AlmbpW7TgwoL7o0QY6oQG4v6kg%2FSDqbvJY0k89zmtBiC4hB2Iex5QQKKO7g6en7eYCmhV1bkZo1rrVw7ryVFHnhMSuiqao3RN5I3S3KwYSEd9u8OnW6bDVF3%2FhyoN4u2ErmwJBZwduR%2Bv3k0YFJ4D9P4fMp%2BFAh4Bn47Ko51083HwSDJ7yViWEAVonHo90ChlXCfJV61j%2Byw7nLOjVWj9Mn3AWY9KFByawk1C3FgbaBg%3D%3D&Expires=1782196589",
  "setup": "# Copyright Epic Games, Inc. All Rights Reserved.\nfrom __future__ import annotations\n\n\n__version__ = '1.0.1'\n\nimport io\nimport os\nimport re\nimport sys\nimport json\nimport time\nimport runpy\nimport pathlib\nimport zipfile\nimport tempfile\nfrom urllib.request import urlopen\n\n\n# Provided as exec globals when running this script\nloader_info = globals()['loader_info']\nloader_path = globals().get('cache_path')\ncache_only = globals().get('cache_only', False)\n\nif not loader_path:\n    namespace = re.sub(r\"[/\\\\?%*:|\\\"<>\\x7F\\x00-\\x1F]\", \"-\", loader_info['endpoint'].rpartition('://')[-1])\n    if sys.platform == 'win32':\n        loader_path = pathlib.Path.home() / f'AppData/Roaming/UnPipe/loader/{namespace}'\n    elif sys.platform.startswith('linux'):\n        loader_path = pathlib.Path.home() / f'.local/share/UnPipe/loader/{namespace}'\n    elif sys.platform == 'darwin':\n        loader_path = pathlib.Path.home() / f'Library/Application Support/UnPipe/loader/{namespace}'\n    else:\n        raise OSError(f'Unsupported platform {sys.platform}')\n\n# Create cache parent directory\nloader_path.parent.mkdir(parents=True, exist_ok=True)\ncache_file = loader_path.joinpath('.cached')\ncache_file_temp = loader_path.joinpath('.cached.tmp')\ntry:\n    cache_info = json.loads(cache_file.read_text()) if cache_file.exists() else {}\nexcept json.JSONDecodeError:\n    cache_info = {}\n\n# Only extract if the hashes missmatch\nif cache_info.get('hash') != loader_info['hash']:\n    # Grab the zip\n    with urlopen(loader_info['url']) as response:\n        loader_zipfile = zipfile.ZipFile(io.BytesIO(response.read()))\n\n    # Extract\n    with tempfile.TemporaryDirectory(dir=loader_path.parent) as tempdir:\n        loader_zipfile.extractall(path=tempdir)\n        if loader_path.exists():\n            # Let the tempdir cleanup handle the prior loader\n            os.rename(loader_path, tempdir + '/.cleanup')\n\n        # Write a new .cached file to the extracted copy, before moving it over\n        pathlib.Path(tempdir, 'unpipe_loader', '.cached').write_text(\n            json.dumps(\n                {\n                    'hash': loader_info['hash'],\n                    'loader_url': loader_info['endpoint'],\n                    'path': str(loader_path),\n                    'timestamp': time.time(),\n                },\n                indent=2,\n            )\n        )\n        os.rename(tempdir + '/unpipe_loader', loader_path)\nelse:\n    if cache_info:\n        cache_file_temp.write_text(\n            json.dumps(\n                {\n                    **cache_info,\n                    'timestamp': time.time(),\n                }\n            )\n        )\n        cache_file_temp.replace(cache_file)\n\n# If this isn't in cache-only mode, run the loader entry point\nif not cache_only:\n    runpy.run_path(str(loader_path))\n"
}