1
1
#!/usr/bin/env python
2
2
import os
3
- import sys
4
- import hashlib
5
- import requests
6
- import zipfile
7
- import tarfile
8
- import shutil
9
3
import subprocess
10
-
4
+ import sys
11
5
from pathlib import Path
12
- from tqdm import tqdm
13
- from wheel .wheelfile import WheelFile
14
- from tempfile import TemporaryDirectory
15
6
16
7
# Define the base information for the download
17
8
gptscript_info = {
@@ -36,7 +27,7 @@ suffixes = {
36
27
37
28
38
29
def wheel_platform_tag (platform , arch ):
39
- py_arch = {
30
+ py_arch = {
40
31
"universal" : "universal2" ,
41
32
"arm64" : "aarch64" ,
42
33
"amd64" : "x86_64" ,
@@ -47,68 +38,13 @@ def wheel_platform_tag(platform, arch):
47
38
48
39
py_platform = {
49
40
"linux" : "manylinux2014" ,
50
- "macOS" :"macosx_10_9" ,
51
- "windows" :"win" ,
41
+ "macOS" : "macosx_10_9" ,
42
+ "windows" : "win" ,
52
43
}[platform ]
53
44
54
45
return f"{ py_platform } _{ py_arch } "
55
46
56
47
57
- def download_file (url , save_path ):
58
- response = requests .get (url , stream = True )
59
- total_size = int (response .headers .get ("content-length" , 0 ))
60
- block_size = 1024
61
- progress_bar = tqdm (
62
- total = total_size ,
63
- unit = "B" ,
64
- unit_scale = True ,
65
- desc = f"Downloading { url .split ('/' )[- 1 ]} " ,
66
- )
67
-
68
- with open (save_path , "wb" ) as f :
69
- for data in response .iter_content (block_size ):
70
- progress_bar .update (len (data ))
71
- f .write (data )
72
-
73
- progress_bar .close ()
74
-
75
-
76
- def extract_archive (archive_path , extract_dir ):
77
- if archive_path .suffix == ".zip" :
78
- with zipfile .ZipFile (archive_path , "r" ) as zip_ref :
79
- zip_ref .extractall (extract_dir )
80
- elif archive_path .suffixes [- 2 :] == [".tar" , ".gz" ]:
81
- with tarfile .open (archive_path , "r:gz" ) as tar_ref :
82
- tar_ref .extractall (extract_dir )
83
-
84
-
85
- def setup_directories (base_dir ):
86
- for platform_name in platform_names .values ():
87
- for arch in platform_name ["archs" ]:
88
- os .makedirs (base_dir / platform_name ["name" ] / arch , exist_ok = True )
89
-
90
-
91
- def stage_gptscript_binaries (base_dir ):
92
- setup_directories (base_dir )
93
-
94
- for platform_name in platform_names .values ():
95
- for arch in platform_name ["archs" ]:
96
- pltfm_dir = platform_name ["name" ]
97
- file_suffix = suffixes [pltfm_dir ]
98
-
99
- artifact_name = f"{ gptscript_info ['name' ]} -{ gptscript_info ['version' ]} -{ pltfm_dir } -{ arch } .{ file_suffix } "
100
- url = f"{ gptscript_info ['url' ]} { gptscript_info ['version' ]} /{ artifact_name } "
101
-
102
- download_path = base_dir / pltfm_dir / arch / artifact_name
103
- download_file (url , download_path )
104
-
105
- # Extract the downloaded archive
106
- extract_archive (download_path , base_dir / pltfm_dir / arch )
107
-
108
- # Remove the archive file after extraction
109
- download_path .unlink ()
110
-
111
-
112
48
def build_wheel_for_platform (output_dir ):
113
49
"""
114
50
Build a wheel for each platform specified in platform_names.
@@ -128,75 +64,12 @@ def build_wheel_for_platform(output_dir):
128
64
del os .environ ["PLAT" ]
129
65
130
66
131
- def file_hash_and_size (file_path ):
132
- """Compute the SHA256 hash and size of a file."""
133
- sha256 = hashlib .sha256 ()
134
- size = 0
135
- with open (file_path , 'rb' ) as f :
136
- while True :
137
- data = f .read (8192 )
138
- if not data :
139
- break
140
- sha256 .update (data )
141
- size += len (data )
142
- return sha256 .hexdigest (), f"{ size } "
143
-
144
-
145
- def modify_and_repackage_wheel (wheel_path , binary_dir , platform , arch ):
146
- with TemporaryDirectory () as temp_dir :
147
- temp_dir_path = Path (temp_dir )
148
- with WheelFile (wheel_path , "r" ) as original_wheel :
149
- original_wheel .extractall (temp_dir_path )
150
-
151
- # Identify the .dist-info directory
152
- dist_info_dirs = list (temp_dir_path .glob ('*.dist-info' ))
153
- if len (dist_info_dirs ) != 1 :
154
- raise RuntimeError ("Expected exactly one .dist-info directory" )
155
- dist_info_dir = dist_info_dirs [0 ]
156
-
157
- # Perform necessary modifications here
158
- # Example: Adding a binary file to the .data directory
159
- binary_name = "gptscript" + (".exe" if platform == "windows" else "" )
160
- binary_src = binary_dir / platform / arch / binary_name
161
- data_dir = temp_dir_path / dist_info_dir .name .replace ('.dist-info' , '.data' ) / 'scripts'
162
- data_dir .mkdir (parents = True , exist_ok = True )
163
- shutil .copy (binary_src , data_dir / binary_name )
164
-
165
- # Update the RECORD file with new files
166
- record_path = dist_info_dir / "RECORD"
167
- with open (record_path , "a" ) as record_file :
168
- binary_rel_path = data_dir .relative_to (temp_dir_path ) / binary_name
169
- hash_digest , size = file_hash_and_size (data_dir / binary_name )
170
- record_file .write (f"{ binary_rel_path } ,{ hash_digest } ,{ size } \n " )
171
-
172
- platform_tag = "none-" + wheel_platform_tag (platform , arch )
173
- new_wheel_filename = wheel_path .name .replace ("none-any" , platform_tag )
174
- new_wheel_path = wheel_path .parent / new_wheel_filename
175
-
176
- # Repackage the wheel, overwriting the original
177
- #new_wheel_path = wheel_path # Overwrite the original wheel or specify a new path
178
- with WheelFile (new_wheel_path , "w" ) as new_wheel :
179
- new_wheel .write_files (temp_dir_path )
180
-
181
- print (f"Wheel modified and saved to: { new_wheel_path } " )
182
-
183
-
184
67
def main ():
185
68
base_dir = Path (__file__ ).resolve ().parent
186
- bin_dir = base_dir .parent / "bin"
187
69
dist_dir = base_dir .parent / "dist"
188
70
189
- stage_gptscript_binaries (bin_dir )
190
71
build_wheel_for_platform (dist_dir )
191
72
192
- # Modify and repackage wheels
193
- wheel_files = list (dist_dir .glob ("*.whl" ))
194
- for _ , data in platform_names .items ():
195
- for arch in data ["archs" ]:
196
- # Find the wheel file (assuming there's only one for simplicity)
197
- if wheel_files :
198
- modify_and_repackage_wheel (wheel_files [0 ], bin_dir , data ["name" ], arch )
199
-
200
73
201
74
if __name__ == "__main__" :
202
75
main ()
0 commit comments