@@ -20,20 +20,23 @@ class BinaryManager:
20
20
def __init__ (self , version : Optional [str ] = None ):
21
21
if version is None :
22
22
version = __version__
23
- self .version = version
24
-
25
- def sqlite_download_url (self ) -> str :
26
- """
27
- Constructs a download URL for the `usearch_sqlite` binary based on the operating system, architecture, and version.
28
-
29
- Args:
30
- version (str): The version of the binary to download.
23
+ self .version = version or __version__
24
+ self .download_dir = self .determine_download_dir ()
25
+
26
+ @staticmethod
27
+ def determine_download_dir ():
28
+ # Check if running within a virtual environment
29
+ virtual_env = os .getenv ("VIRTUAL_ENV" )
30
+ if virtual_env :
31
+ # Use a subdirectory within the virtual environment for binaries
32
+ return os .path .join (virtual_env , "bin" , "usearch_binaries" )
33
+ else :
34
+ # Fallback to a directory in the user's home folder
35
+ home_dir = os .path .expanduser ("~" )
36
+ return os .path .join (home_dir , ".usearch" , "binaries" )
31
37
32
- Returns:
33
- A string representing the download URL.
34
- """
38
+ def sqlite_file_name (self ) -> str :
35
39
version = self .version
36
- base_url = "https://github.com/unum-cloud/usearch/releases/download"
37
40
os_map = {"Linux" : "linux" , "Windows" : "windows" , "Darwin" : "macos" }
38
41
arch_map = {
39
42
"x86_64" : "amd64" if platform .system () != "Darwin" else "x86_64" ,
@@ -47,6 +50,12 @@ def sqlite_download_url(self) -> str:
47
50
arch_part = arch_map .get (arch , "" )
48
51
extension = {"Linux" : "so" , "Windows" : "dll" , "Darwin" : "dylib" }.get (platform .system (), "" )
49
52
filename = f"usearch_sqlite_{ os_part } _{ arch_part } _{ version } .{ extension } "
53
+ return filename
54
+
55
+ def sqlite_download_url (self ) -> str :
56
+ version = self .version
57
+ filename = self .sqlite_file_name ()
58
+ base_url = "https://github.com/unum-cloud/usearch/releases/download"
50
59
url = f"{ base_url } /v{ version } /{ filename } "
51
60
return url
52
61
@@ -66,7 +75,6 @@ def download_binary(self, url: str, dest_folder: str) -> str:
66
75
urllib .request .urlretrieve (url , dest_path )
67
76
return dest_path
68
77
69
- @property
70
78
def sqlite_found_or_downloaded (self ) -> Optional [str ]:
71
79
"""
72
80
Attempts to locate the pre-installed `usearch_sqlite` binary.
@@ -89,20 +97,16 @@ def sqlite_found_or_downloaded(self) -> Optional[str]:
89
97
return os .path .join (root , file ).removesuffix (file_extension )
90
98
91
99
# Check a temporary directory (assuming the binary might be downloaded from a GitHub release)
92
- temp_dir = tempfile .gettempdir ()
93
- for root , _ , files in os .walk (temp_dir ):
94
- for file in files :
95
- if file .endswith (file_extension ) and "usearch_sqlite" in file :
96
- return os .path .join (root , file ).removesuffix (file_extension )
100
+ local_path = os .path .join (self .download_dir , self .sqlite_file_name ())
101
+ if os .path .exists (local_path ):
102
+ return local_path .removesuffix (file_extension )
97
103
98
104
# If not found locally, warn the user and download from GitHub
99
- temp_dir = tempfile .gettempdir ()
100
105
warnings .warn ("Will download `usearch_sqlite` binary from GitHub." , UserWarning )
101
-
102
- # If the download fails due to HTTPError (e.g., 404 Not Found), like a missing lib version
103
106
try :
104
- binary_path = self .download_binary (self .sqlite_download_url (), temp_dir )
107
+ binary_path = self .download_binary (self .sqlite_download_url (), self . download_dir )
105
108
except HTTPError as e :
109
+ # If the download fails due to HTTPError (e.g., 404 Not Found), like a missing lib version
106
110
if e .code == 404 :
107
111
warnings .warn (f"Download failed: { e .url } could not be found." , UserWarning )
108
112
else :
@@ -117,6 +121,9 @@ def sqlite_found_or_downloaded(self) -> Optional[str]:
117
121
return None
118
122
119
123
120
- # Use the function to set the `sqlite` computed property
121
- binary_manager = BinaryManager ()
122
- sqlite = binary_manager .sqlite_found_or_downloaded
124
+ def sqlite_path (version : str = None ) -> str :
125
+ manager = BinaryManager (version = version )
126
+ result = manager .sqlite_found_or_downloaded ()
127
+ if result is None :
128
+ raise FileNotFoundError ("Failed to find or download `usearch_sqlite` binary." )
129
+ return result
0 commit comments