mystic_CBK commited on
Commit
f71b308
·
1 Parent(s): a76f477

Fix ECG-FM deployment: Update Dockerfile, server.py, requirements.txt with fairseq-signals integration

Browse files
FAIRSEQ_SIGNALS_DEPLOYMENT.md CHANGED
@@ -239,3 +239,4 @@ RUN pip install --no-cache-dir torch==1.13.1+cpu torchvision==0.14.1+cpu torchau
239
  ✅ **Complete model architecture** with interpretation heads
240
 
241
  **This is a game-changer** - from 25% to 80%+ clinical accuracy!
 
 
239
  ✅ **Complete model architecture** with interpretation heads
240
 
241
  **This is a game-changer** - from 25% to 80%+ clinical accuracy!
242
+
app.py CHANGED
@@ -4,12 +4,12 @@ Hugging Face Spaces Entry Point for ECG-FM API
4
  This file serves as the main entry point for HF Spaces deployment
5
  """
6
 
7
- # HF Spaces Entry Point
8
- # This file is specifically for Hugging Face Spaces deployment
9
-
10
- import uvicorn
11
  from server import app
12
 
 
 
13
  if __name__ == "__main__":
 
14
  uvicorn.run(app, host="0.0.0.0", port=7860)
15
 
 
4
  This file serves as the main entry point for HF Spaces deployment
5
  """
6
 
7
+ # Import our main server application
 
 
 
8
  from server import app
9
 
10
+ # HF Spaces will automatically detect this as a FastAPI app
11
+ # and serve it on the configured port
12
  if __name__ == "__main__":
13
+ import uvicorn
14
  uvicorn.run(app, host="0.0.0.0", port=7860)
15
 
create_compatible_env.py DELETED
@@ -1,230 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Create Compatible Environment Script
4
- ===================================
5
-
6
- Creates a compatible Python environment for ECG-FM testing.
7
- This addresses the version incompatibilities found in the lightweight test.
8
- """
9
-
10
- import subprocess
11
- import sys
12
- import os
13
-
14
- def check_python_version():
15
- """Check current Python version"""
16
- version = sys.version_info
17
- print(f"🐍 Current Python: {version.major}.{version.minor}.{version.micro}")
18
-
19
- if version.major == 3 and 8 <= version.minor <= 11:
20
- print("✅ Python version is compatible with HF Spaces")
21
- return True
22
- else:
23
- print("❌ Python version NOT compatible with HF Spaces")
24
- print(" Need Python 3.8-3.11, have 3.13.3")
25
- return False
26
-
27
- def create_virtual_env():
28
- """Create a virtual environment with compatible Python"""
29
- print("\n🔧 Creating Virtual Environment")
30
- print("=" * 40)
31
-
32
- # Check if virtualenv is available
33
- try:
34
- result = subprocess.run([sys.executable, '-m', 'pip', 'install', 'virtualenv'],
35
- capture_output=True, text=True)
36
- if result.returncode == 0:
37
- print("✅ virtualenv installed")
38
- else:
39
- print("❌ Failed to install virtualenv")
40
- return False
41
- except Exception as e:
42
- print(f"❌ Error installing virtualenv: {e}")
43
- return False
44
-
45
- # Create virtual environment
46
- env_name = "ecg_fm_env"
47
- try:
48
- cmd = [sys.executable, '-m', 'virtualenv', env_name]
49
- print(f"Creating environment: {env_name}")
50
- result = subprocess.run(cmd, capture_output=True, text=True)
51
-
52
- if result.returncode == 0:
53
- print(f"✅ Virtual environment created: {env_name}")
54
- return True
55
- else:
56
- print("❌ Failed to create virtual environment")
57
- print(result.stderr)
58
- return False
59
- except Exception as e:
60
- print(f"❌ Error creating environment: {e}")
61
- return False
62
-
63
- def install_compatible_packages():
64
- """Install compatible package versions"""
65
- print("\n📦 Installing Compatible Packages")
66
- print("=" * 40)
67
-
68
- # These versions are compatible with each other
69
- packages = [
70
- "numpy==1.24.3",
71
- "torch==1.13.1",
72
- "torchvision==0.14.1",
73
- "torchaudio==0.13.1",
74
- "omegaconf==2.3.0",
75
- "fastapi==0.104.1",
76
- "uvicorn[standard]==0.24.0",
77
- "huggingface-hub==0.19.4",
78
- "transformers==4.21.0",
79
- "einops==0.7.0",
80
- "pyyaml==6.0.1"
81
- ]
82
-
83
- # Get the virtual environment Python
84
- if os.name == 'nt': # Windows
85
- python_path = os.path.join("ecg_fm_env", "Scripts", "python.exe")
86
- else: # Unix/Linux
87
- python_path = os.path.join("ecg_fm_env", "bin", "python")
88
-
89
- if not os.path.exists(python_path):
90
- print("❌ Virtual environment Python not found")
91
- return False
92
-
93
- print(f"Using Python: {python_path}")
94
-
95
- all_good = True
96
-
97
- for package in packages:
98
- print(f"Installing {package}...")
99
- try:
100
- cmd = [python_path, '-m', 'pip', 'install', package]
101
- result = subprocess.run(cmd, capture_output=True, text=True, timeout=120)
102
-
103
- if result.returncode == 0:
104
- print(f" ✅ {package} installed")
105
- else:
106
- print(f" ❌ {package} failed")
107
- print(f" Error: {result.stderr}")
108
- all_good = False
109
-
110
- except subprocess.TimeoutExpired:
111
- print(f" ⚠️ {package} timed out")
112
- all_good = False
113
- except Exception as e:
114
- print(f" ❌ {package} error: {e}")
115
- all_good = False
116
-
117
- return all_good
118
-
119
- def test_compatible_environment():
120
- """Test the compatible environment"""
121
- print("\n🧪 Testing Compatible Environment")
122
- print("=" * 40)
123
-
124
- if os.name == 'nt': # Windows
125
- python_path = os.path.join("ecg_fm_env", "Scripts", "python.exe")
126
- else: # Unix/Linux
127
- python_path = os.path.join("ecg_fm_env", "bin", "python")
128
-
129
- if not os.path.exists(python_path):
130
- print("❌ Virtual environment not found")
131
- return False
132
-
133
- # Test imports
134
- test_script = f"""
135
- import sys
136
- print(f"Python: {{sys.version}}")
137
-
138
- try:
139
- import numpy
140
- print(f"NumPy: {{numpy.__version__}}")
141
- except ImportError as e:
142
- print(f"NumPy: ❌ {{e}}")
143
-
144
- try:
145
- import torch
146
- print(f"PyTorch: {{torch.__version__}}")
147
- except ImportError as e:
148
- print(f"PyTorch: ❌ {{e}}")
149
-
150
- try:
151
- import omegaconf
152
- print(f"OmegaConf: {{omegaconf.__version__}}")
153
- except ImportError as e:
154
- print(f"OmegaConf: ❌ {{e}}")
155
-
156
- try:
157
- import fastapi
158
- print(f"FastAPI: {{fastapi.__version__}}")
159
- except ImportError as e:
160
- print(f"FastAPI: ❌ {{e}}")
161
-
162
- try:
163
- import transformers
164
- print(f"Transformers: {{transformers.__version__}}")
165
- except ImportError as e:
166
- print(f"Transformers: ❌ {{e}}")
167
- """
168
-
169
- try:
170
- result = subprocess.run([python_path, '-c', test_script],
171
- capture_output=True, text=True)
172
-
173
- if result.returncode == 0:
174
- print("✅ Environment test successful!")
175
- print("\n📋 Package Versions:")
176
- print(result.stdout)
177
- return True
178
- else:
179
- print("❌ Environment test failed!")
180
- print(result.stderr)
181
- return False
182
-
183
- except Exception as e:
184
- print(f"❌ Test error: {e}")
185
- return False
186
-
187
- def main():
188
- """Main function"""
189
- print("🚀 Creating Compatible Environment for ECG-FM")
190
- print("=" * 60)
191
- print("This will create a virtual environment with compatible versions")
192
- print()
193
-
194
- # Step 1: Check Python version
195
- if not check_python_version():
196
- print("\n⚠️ Warning: Python 3.13.3 may cause issues")
197
- print(" Virtual environment will help isolate dependencies")
198
-
199
- # Step 2: Create virtual environment
200
- if not create_virtual_env():
201
- print("\n❌ Failed to create virtual environment")
202
- return 1
203
-
204
- # Step 3: Install compatible packages
205
- if not install_compatible_packages():
206
- print("\n❌ Failed to install compatible packages")
207
- return 1
208
-
209
- # Step 4: Test environment
210
- if not test_compatible_environment():
211
- print("\n❌ Environment test failed")
212
- return 1
213
-
214
- print("\n🎉 COMPATIBLE ENVIRONMENT CREATED!")
215
- print("✅ All packages installed with compatible versions")
216
- print("🚀 Ready for local testing before HF upload")
217
-
218
- # Instructions
219
- print("\n📋 How to use:")
220
- if os.name == 'nt': # Windows
221
- print(" Activate: ecg_fm_env\\Scripts\\activate")
222
- print(" Python: ecg_fm_env\\Scripts\\python.exe")
223
- else: # Unix/Linux
224
- print(" Activate: source ecg_fm_env/bin/activate")
225
- print(" Python: ecg_fm_env/bin/python")
226
-
227
- return 0
228
-
229
- if __name__ == "__main__":
230
- sys.exit(main())
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
create_compatible_env_py313.py DELETED
@@ -1,296 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Create Compatible Environment for Python 3.13
4
- ============================================
5
-
6
- Creates a compatible Python environment for ECG-FM testing on Python 3.13.
7
- Uses newer package versions that are compatible with Python 3.13.
8
- """
9
-
10
- import subprocess
11
- import sys
12
- import os
13
-
14
- def check_python_version():
15
- """Check current Python version"""
16
- version = sys.version_info
17
- print(f"🐍 Current Python: {version.major}.{version.minor}.{version.micro}")
18
-
19
- if version.major == 3 and version.minor >= 13:
20
- print("⚠️ Python 3.13+ detected - Using newer package versions")
21
- print(" Note: HF Spaces supports Python 3.8-3.11")
22
- return "py313"
23
- elif version.major == 3 and 8 <= version.minor <= 11:
24
- print("✅ Python version is compatible with HF Spaces")
25
- return "py311"
26
- else:
27
- print("❌ Python version not supported")
28
- return None
29
-
30
- def create_virtual_env():
31
- """Create a virtual environment"""
32
- print("\n🔧 Creating Virtual Environment")
33
- print("=" * 40)
34
-
35
- # Check if virtualenv is available
36
- try:
37
- result = subprocess.run([sys.executable, '-m', 'pip', 'install', 'virtualenv'],
38
- capture_output=True, text=True)
39
- if result.returncode == 0:
40
- print("✅ virtualenv installed")
41
- else:
42
- print("❌ Failed to install virtualenv")
43
- return False
44
- except Exception as e:
45
- print(f"❌ Error installing virtualenv: {e}")
46
- return False
47
-
48
- # Create virtual environment
49
- env_name = "ecg_fm_env_py313"
50
- try:
51
- cmd = [sys.executable, '-m', 'virtualenv', env_name]
52
- print(f"Creating environment: {env_name}")
53
- result = subprocess.run(cmd, capture_output=True, text=True)
54
-
55
- if result.returncode == 0:
56
- print(f"✅ Virtual environment created: {env_name}")
57
- return True
58
- else:
59
- print("❌ Failed to create virtual environment")
60
- print(result.stderr)
61
- return False
62
- except Exception as e:
63
- print(f"❌ Error creating environment: {e}")
64
- return False
65
-
66
- def install_compatible_packages_py313():
67
- """Install Python 3.13 compatible package versions"""
68
- print("\n📦 Installing Python 3.13 Compatible Packages")
69
- print("=" * 50)
70
-
71
- # Python 3.13 compatible versions
72
- packages = [
73
- "numpy>=2.0.0", # Python 3.13 compatible
74
- "torch>=2.6.0", # Latest PyTorch for Python 3.13
75
- "torchvision>=0.21.0",
76
- "torchaudio>=2.6.0",
77
- "omegaconf>=2.3.0", # Has is_primitive_type
78
- "fastapi>=0.104.1",
79
- "uvicorn[standard]>=0.24.0",
80
- "huggingface-hub>=0.19.4",
81
- "transformers>=4.21.0",
82
- "einops>=0.7.0",
83
- "pyyaml>=6.0.1"
84
- ]
85
-
86
- # Get the virtual environment Python
87
- if os.name == 'nt': # Windows
88
- python_path = os.path.join("ecg_fm_env_py313", "Scripts", "python.exe")
89
- else: # Unix/Linux
90
- python_path = os.path.join("ecg_fm_env_py313", "bin", "python")
91
-
92
- if not os.path.exists(python_path):
93
- print("❌ Virtual environment Python not found")
94
- return False
95
-
96
- print(f"Using Python: {python_path}")
97
-
98
- all_good = True
99
-
100
- for package in packages:
101
- print(f"Installing {package}...")
102
- try:
103
- cmd = [python_path, '-m', 'pip', 'install', package]
104
- result = subprocess.run(cmd, capture_output=True, text=True, timeout=180)
105
-
106
- if result.returncode == 0:
107
- print(f" ✅ {package} installed")
108
- else:
109
- print(f" ❌ {package} failed")
110
- print(f" Error: {result.stderr}")
111
- all_good = False
112
-
113
- except subprocess.TimeoutExpired:
114
- print(f" ⚠️ {package} timed out")
115
- all_good = False
116
- except Exception as e:
117
- print(f" ❌ {package} error: {e}")
118
- all_good = False
119
-
120
- return all_good
121
-
122
- def test_compatible_environment():
123
- """Test the compatible environment"""
124
- print("\n🧪 Testing Compatible Environment")
125
- print("=" * 40)
126
-
127
- if os.name == 'nt': # Windows
128
- python_path = os.path.join("ecg_fm_env_py313", "Scripts", "python.exe")
129
- else: # Unix/Linux
130
- python_path = os.path.join("ecg_fm_env_py313", "bin", "python")
131
-
132
- if not os.path.exists(python_path):
133
- print("❌ Virtual environment not found")
134
- return False
135
-
136
- # Test imports
137
- test_script = """
138
- import sys
139
- print(f"Python: {sys.version}")
140
-
141
- try:
142
- import numpy
143
- print(f"NumPy: {numpy.__version__}")
144
- except ImportError as e:
145
- print(f"NumPy: ❌ {e}")
146
-
147
- try:
148
- import torch
149
- print(f"PyTorch: {torch.__version__}")
150
- except ImportError as e:
151
- print(f"PyTorch: ❌ {e}")
152
-
153
- try:
154
- import omegaconf
155
- print(f"OmegaConf: {omegaconf.__version__}")
156
- # Test if is_primitive_type exists
157
- if hasattr(omegaconf._utils, 'is_primitive_type'):
158
- print("✅ omegaconf._utils.is_primitive_type available")
159
- else:
160
- print("❌ omegaconf._utils.is_primitive_type NOT available")
161
- except ImportError as e:
162
- print(f"OmegaConf: ❌ {e}")
163
-
164
- try:
165
- import fastapi
166
- print(f"FastAPI: {fastapi.__version__}")
167
- except ImportError as e:
168
- print(f"FastAPI: ❌ {e}")
169
-
170
- try:
171
- import transformers
172
- print(f"Transformers: {transformers.__version__}")
173
- except ImportError as e:
174
- print(f"Transformers: ❌ {e}")
175
-
176
- try:
177
- import huggingface_hub
178
- print(f"HuggingFace Hub: {huggingface_hub.__version__}")
179
- except ImportError as e:
180
- print(f"HuggingFace Hub: ❌ {e}")
181
- """
182
-
183
- try:
184
- result = subprocess.run([python_path, '-c', test_script],
185
- capture_output=True, text=True)
186
-
187
- if result.returncode == 0:
188
- print("✅ Environment test successful!")
189
- print("\n📋 Package Versions:")
190
- print(result.stdout)
191
- return True
192
- else:
193
- print("❌ Environment test failed!")
194
- print(result.stderr)
195
- return False
196
-
197
- except Exception as e:
198
- print(f"❌ Test error: {e}")
199
- return False
200
-
201
- def create_hf_compatible_requirements():
202
- """Create HF Spaces compatible requirements file"""
203
- print("\n📝 Creating HF Spaces Compatible Requirements")
204
- print("=" * 50)
205
-
206
- # Create requirements file for HF Spaces (Python 3.9)
207
- hf_requirements = """# HF Spaces Requirements - Python 3.9 Compatible
208
- # These versions work on HF Spaces with Python 3.9
209
-
210
- # Core dependencies
211
- fastapi==0.104.1
212
- uvicorn[standard]==0.24.0
213
- huggingface-hub==0.19.4
214
- pyyaml==6.0.1
215
- einops==0.7.0
216
-
217
- # PyTorch 1.13.x - Compatible with Python 3.9 and NumPy 1.24
218
- torch==1.13.1
219
- torchvision==0.14.1
220
- torchaudio==0.13.1
221
-
222
- # NumPy 1.24.x - Compatible with PyTorch 1.13.x
223
- numpy==1.24.3
224
-
225
- # OmegaConf - Version that has is_primitive_type
226
- omegaconf==2.3.0
227
-
228
- # Transformers - Compatible version
229
- transformers==4.21.0
230
-
231
- # fairseq-signals will be installed from source in Dockerfile
232
- """
233
-
234
- try:
235
- with open("requirements_hf_spaces_py39.txt", "w") as f:
236
- f.write(hf_requirements)
237
- print("✅ Created requirements_hf_spaces_py39.txt")
238
- print(" This file is compatible with HF Spaces Python 3.9")
239
- return True
240
- except Exception as e:
241
- print(f"❌ Failed to create requirements file: {e}")
242
- return False
243
-
244
- def main():
245
- """Main function"""
246
- print("🚀 Creating Python 3.13 Compatible Environment for ECG-FM")
247
- print("=" * 70)
248
- print("This will create a virtual environment with Python 3.13 compatible versions")
249
- print()
250
-
251
- # Step 1: Check Python version
252
- py_version = check_python_version()
253
- if not py_version:
254
- return 1
255
-
256
- # Step 2: Create virtual environment
257
- if not create_virtual_env():
258
- print("\n❌ Failed to create virtual environment")
259
- return 1
260
-
261
- # Step 3: Install compatible packages
262
- if py_version == "py313":
263
- if not install_compatible_packages_py313():
264
- print("\n❌ Failed to install compatible packages")
265
- return 1
266
-
267
- # Step 4: Test environment
268
- if not test_compatible_environment():
269
- print("\n❌ Environment test failed")
270
- return 1
271
-
272
- # Step 5: Create HF compatible requirements
273
- create_hf_compatible_requirements()
274
-
275
- print("\n🎉 COMPATIBLE ENVIRONMENT CREATED!")
276
- print("✅ All packages installed with compatible versions")
277
- print("🚀 Ready for local testing before HF upload")
278
-
279
- # Instructions
280
- print("\n📋 How to use:")
281
- if os.name == 'nt': # Windows
282
- print(" Activate: ecg_fm_env_py313\\Scripts\\activate")
283
- print(" Python: ecg_fm_env_py313\\Scripts\\python.exe")
284
- else: # Unix/Linux
285
- print(" Activate: source ecg_fm_env_py313/bin/activate")
286
- print(" Python: ecg_fm_env_py313/bin/python")
287
-
288
- print("\n⚠️ IMPORTANT NOTES:")
289
- print(" - Local environment uses Python 3.13 compatible versions")
290
- print(" - HF Spaces will use Python 3.9 with requirements_hf_spaces_py39.txt")
291
- print(" - Test locally first, then upload to HF Spaces")
292
-
293
- return 0
294
-
295
- if __name__ == "__main__":
296
- sys.exit(main())
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
deploy_hf_spaces_final.ps1 DELETED
@@ -1,185 +0,0 @@
1
- # 🚀 HF Spaces Deployment Script for ECG-FM with fairseq-signals
2
- # PowerShell version for Windows
3
-
4
- param(
5
- [string]$HFUsername = "your_username"
6
- )
7
-
8
- Write-Host "🚀 ECG-FM HF Spaces Deployment with fairseq-signals" -ForegroundColor Green
9
- Write-Host "==================================================" -ForegroundColor Green
10
-
11
- # Configuration
12
- $SpaceName = "ecg-fm-fairseq-signals"
13
- $RepoUrl = "https://huggingface.co/spaces/$HFUsername/$SpaceName"
14
-
15
- Write-Host "📋 Configuration:" -ForegroundColor Blue
16
- Write-Host " Space Name: $SpaceName" -ForegroundColor White
17
- Write-Host " HF Username: $HFUsername" -ForegroundColor White
18
- Write-Host " Repository: $RepoUrl" -ForegroundColor White
19
- Write-Host ""
20
-
21
- # Check if HF CLI is installed
22
- try {
23
- $null = Get-Command huggingface-cli -ErrorAction Stop
24
- Write-Host "✅ HF CLI check passed" -ForegroundColor Green
25
- } catch {
26
- Write-Host "❌ Hugging Face CLI not found" -ForegroundColor Red
27
- Write-Host "Please install it with: pip install huggingface_hub" -ForegroundColor Yellow
28
- exit 1
29
- }
30
-
31
- # Check if logged in to HF
32
- try {
33
- $whoami = huggingface-cli whoami 2>$null
34
- if ($LASTEXITCODE -eq 0) {
35
- Write-Host "✅ Logged in to HF as: $whoami" -ForegroundColor Green
36
- } else {
37
- throw "Not logged in"
38
- }
39
- } catch {
40
- Write-Host "❌ Not logged in to Hugging Face" -ForegroundColor Red
41
- Write-Host "Please login with: huggingface-cli login" -ForegroundColor Yellow
42
- exit 1
43
- }
44
-
45
- # Create or clone the space
46
- if (Test-Path $SpaceName) {
47
- Write-Host "📁 Space directory exists, updating..." -ForegroundColor Yellow
48
- Set-Location $SpaceName
49
- git pull origin main
50
- } else {
51
- Write-Host "📁 Creating new HF Space..." -ForegroundColor Blue
52
- huggingface-cli repo create $SpaceName --type space --space-sdk docker
53
- git clone "$RepoUrl.git" $SpaceName
54
- Set-Location $SpaceName
55
- }
56
-
57
- Write-Host "✅ HF Space ready" -ForegroundColor Green
58
-
59
- # Copy deployment files
60
- Write-Host "📁 Copying deployment files..." -ForegroundColor Blue
61
-
62
- # Copy core files
63
- Copy-Item ..\server.py .
64
- Copy-Item ..\requirements_hf_spaces.txt .
65
- Copy-Item ..\Dockerfile .
66
- Copy-Item ..\app.py .
67
-
68
- # Copy additional files
69
- Copy-Item ..\test_fairseq_signals.py .
70
- Copy-Item ..\FAIRSEQ_SIGNALS_DEPLOYMENT.md .
71
-
72
- # Create .gitattributes for HF Spaces
73
- @"
74
- *.md filter=lfs diff=lfs merge=lfs -text
75
- *.png filter=lfs diff=lfs merge=lfs -text
76
- *.jpg filter=lfs diff=lfs merge=lfs -text
77
- *.jpeg filter=lfs diff=lfs merge=lfs -text
78
- *.gif filter=lfs diff=lfs merge=lfs -text
79
- *.pdf filter=lfs diff=lfs merge=lfs -text
80
- *.zip filter=lfs diff=lfs merge=lfs -text
81
- *.tar.gz filter=lfs diff=lfs merge=lfs -text
82
- *.pt filter=lfs diff=lfs merge=lfs -text
83
- *.pth filter=lfs diff=lfs merge=lfs -text
84
- *.bin filter=lfs diff=lfs merge=lfs -text
85
- *.safetensors filter=lfs diff=lfs merge=lfs -text
86
- "@ | Out-File -FilePath .gitattributes -Encoding UTF8
87
-
88
- # Create README for the space
89
- @"
90
- # ECG-FM API with fairseq-signals
91
-
92
- ## 🎯 Overview
93
- This is the official ECG-FM implementation using fairseq-signals for full clinical interpretation capabilities.
94
-
95
- ## 🚀 Features
96
- - **Full ECG-FM functionality** (not just features)
97
- - **Clinical interpretation** and abnormality detection
98
- - **Confidence scoring** for clinical decisions
99
- - **Research-proven accuracy** (80-95%)
100
-
101
- ## 🔧 Technical Details
102
- - **Model**: wanglab/ecg-fm
103
- - **Implementation**: fairseq-signals (official)
104
- - **Framework**: FastAPI + PyTorch
105
- - **Deployment**: Docker on HF Spaces
106
-
107
- ## 📊 API Endpoints
108
- - `GET /` - API information
109
- - `GET /healthz` - Health check
110
- - `POST /predict` - ECG analysis
111
-
112
- ## 🎉 Expected Results
113
- - **Before**: 25% accuracy (features only)
114
- - **After**: 80%+ accuracy (full clinical interpretation)
115
- - **Improvement**: 3x better clinical value
116
-
117
- ## 🚨 Important Notes
118
- - This is for research/development purposes
119
- - Clinical validation required for medical use
120
- - Always consult healthcare professionals
121
- "@ | Out-File -FilePath README.md -Encoding UTF8
122
-
123
- Write-Host "✅ Deployment files copied" -ForegroundColor Green
124
-
125
- # Verify critical files
126
- Write-Host "🔍 Verifying critical files..." -ForegroundColor Blue
127
- if (-not (Test-Path "server.py")) {
128
- Write-Host "❌ server.py not found" -ForegroundColor Red
129
- exit 1
130
- }
131
-
132
- if (-not (Test-Path "requirements_hf_spaces.txt")) {
133
- Write-Host "❌ requirements_hf_spaces.txt not found" -ForegroundColor Red
134
- exit 1
135
- }
136
-
137
- if (-not (Test-Path "Dockerfile")) {
138
- Write-Host "❌ Dockerfile not found" -ForegroundColor Red
139
- exit 1
140
- }
141
-
142
- Write-Host "✅ All critical files verified" -ForegroundColor Green
143
-
144
- # Check git status
145
- Write-Host "📊 Git status:" -ForegroundColor Blue
146
- git status
147
-
148
- # Add all files
149
- Write-Host "📝 Adding files to git..." -ForegroundColor Blue
150
- git add .
151
-
152
- # Commit changes
153
- Write-Host "💾 Committing changes..." -ForegroundColor Blue
154
- git commit -m "🚀 Deploy ECG-FM with fairseq-signals - Full clinical interpretation
155
-
156
- - Updated server.py to use fairseq_signals.models
157
- - Fixed version compatibility (PyTorch 1.13.1, omegaconf 1.4.1)
158
- - Enhanced Dockerfile with proper fairseq-signals installation
159
- - Added comprehensive error handling and monitoring
160
- - Expected: 3x accuracy improvement (25% to 80%+)"
161
-
162
- # Push to trigger build
163
- Write-Host "🚀 Pushing to HF Spaces..." -ForegroundColor Blue
164
- git push origin main
165
-
166
- Write-Host ""
167
- Write-Host "🎉 Deployment completed successfully!" -ForegroundColor Green
168
- Write-Host ""
169
- Write-Host "📋 Next steps:" -ForegroundColor Blue
170
- Write-Host "1. Monitor build at: https://huggingface.co/spaces/$HFUsername/$SpaceName" -ForegroundColor White
171
- Write-Host "2. Wait for build completion (10-15 minutes)" -ForegroundColor White
172
- Write-Host "3. Test API endpoints" -ForegroundColor White
173
- Write-Host "4. Verify fairseq_signals implementation" -ForegroundColor White
174
- Write-Host ""
175
- Write-Host "⚠️ Important:" -ForegroundColor Yellow
176
- Write-Host "- Build may take 10-15 minutes for first deployment" -ForegroundColor White
177
- Write-Host "- Monitor build logs for any issues" -ForegroundColor White
178
- Write-Host "- Verify fairseq_signals installation in build logs" -ForegroundColor White
179
- Write-Host ""
180
- Write-Host "🎯 Expected Results:" -ForegroundColor Green
181
- Write-Host "- fairseq_signals import successful" -ForegroundColor White
182
- Write-Host "- Full ECG-FM clinical interpretation" -ForegroundColor White
183
- Write-Host "- 3x accuracy improvement" -ForegroundColor White
184
- Write-Host ""
185
- Write-Host "🔗 Space URL: https://huggingface.co/spaces/$HFUsername/$SpaceName" -ForegroundColor Blue
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
deploy_hf_spaces_final.sh CHANGED
@@ -183,3 +183,4 @@ echo "- Full ECG-FM clinical interpretation"
183
  echo "- 3x accuracy improvement"
184
  echo ""
185
  echo -e "${BLUE}🔗 Space URL:${NC} https://huggingface.co/spaces/${HF_USERNAME}/${SPACE_NAME}"
 
 
183
  echo "- 3x accuracy improvement"
184
  echo ""
185
  echo -e "${BLUE}🔗 Space URL:${NC} https://huggingface.co/spaces/${HF_USERNAME}/${SPACE_NAME}"
186
+
deploy_simple.ps1 DELETED
@@ -1,73 +0,0 @@
1
- # Simple HF Spaces Deployment Script
2
- param([string]$HFUsername = "mystic-cbk")
3
-
4
- Write-Host "🚀 Starting HF Spaces Deployment..." -ForegroundColor Green
5
-
6
- $SpaceName = "ecg-fm-fairseq-signals"
7
- $RepoUrl = "https://huggingface.co/spaces/$HFUsername/$SpaceName"
8
-
9
- Write-Host "Space: $SpaceName" -ForegroundColor Blue
10
- Write-Host "Username: $HFUsername" -ForegroundColor Blue
11
-
12
- # Create or clone the space
13
- if (Test-Path $SpaceName) {
14
- Write-Host "Updating existing space..." -ForegroundColor Yellow
15
- Set-Location $SpaceName
16
- git pull origin main
17
- } else {
18
- Write-Host "Creating new HF Space..." -ForegroundColor Blue
19
-
20
- # Use Python API to create space
21
- python -c "
22
- from huggingface_hub import HfApi
23
- api = HfApi()
24
- try:
25
- api.create_repo(repo_id='$HFUsername/$SpaceName', repo_type='space', space_sdk='docker')
26
- print('Space created successfully!')
27
- except Exception as e:
28
- print(f'Error creating space: {e}')
29
- "
30
-
31
- git clone "$RepoUrl.git" $SpaceName
32
- Set-Location $SpaceName
33
- }
34
-
35
- Write-Host "Space ready!" -ForegroundColor Green
36
-
37
- # Copy files
38
- Write-Host "Copying deployment files..." -ForegroundColor Blue
39
- Copy-Item ..\server.py .
40
- Copy-Item ..\requirements_hf_spaces.txt .
41
- Copy-Item ..\Dockerfile .
42
- Copy-Item ..\app.py .
43
-
44
- # Create README
45
- @"
46
- # ECG-FM API with fairseq-signals
47
-
48
- Full clinical interpretation capabilities using official fairseq-signals implementation.
49
-
50
- ## Features
51
- - Full ECG-FM functionality (not just features)
52
- - Clinical interpretation and abnormality detection
53
- - Confidence scoring for clinical decisions
54
- - Research-proven accuracy (80-95%)
55
-
56
- ## Expected Results
57
- - Before: 25% accuracy (features only)
58
- - After: 80%+ accuracy (full clinical interpretation)
59
- - Improvement: 3x better clinical value
60
- "@ | Out-File -FilePath README.md -Encoding UTF8
61
-
62
- Write-Host "Files copied!" -ForegroundColor Green
63
-
64
- # Git operations
65
- Write-Host "Git operations..." -ForegroundColor Blue
66
- git add .
67
- git commit -m "Deploy ECG-FM with fairseq-signals - Full clinical interpretation"
68
- git push origin main
69
-
70
- Write-Host ""
71
- Write-Host "🎉 Deployment completed!" -ForegroundColor Green
72
- Write-Host "Monitor build at: https://huggingface.co/spaces/$HFUsername/$SpaceName" -ForegroundColor Blue
73
- Write-Host "Expected: 3x accuracy improvement (25% to 80%+)" -ForegroundColor Yellow
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
requirements.txt CHANGED
@@ -1,5 +1,3 @@
1
- # ECG-FM API Requirements - Aligned with Dockerfile
2
- # Core dependencies
3
  fastapi
4
  uvicorn[standard]
5
  numpy<2.0
@@ -7,12 +5,8 @@ huggingface-hub
7
  pyyaml
8
  einops
9
  transformers==4.21.0
10
-
11
- # PyTorch - Aligned with Dockerfile (torch==1.13.1)
12
- # Note: Dockerfile installs specific PyTorch versions
13
- # These are fallback requirements for local development
14
- torch>=1.13.0,<2.0.0
15
- torchaudio>=0.13.0,<0.15.0
16
-
17
- # fairseq-signals will be installed in Docker with specific version constraints
18
- # This ensures we get the official ECG-FM implementation
 
 
 
1
  fastapi
2
  uvicorn[standard]
3
  numpy<2.0
 
5
  pyyaml
6
  einops
7
  transformers==4.21.0
8
+ # fairseq will be installed in Docker with specific version constraints
9
+ # Alternative: torch and torchaudio for model loading fallback
10
+ torch>=2.0.0
11
+ torchaudio>=2.0.0
12
+ # PyTorch will be installed separately in Dockerfile for Python 3.9 compatibility
 
 
 
 
requirements_hf_spaces.txt DELETED
@@ -1,23 +0,0 @@
1
- # HF Spaces Requirements - SYSTEMATIC FIX
2
- # Based on official PyTorch compatibility matrix
3
-
4
- # Core dependencies - Exact versions
5
- fastapi==0.104.1
6
- uvicorn[standard]==0.24.0
7
- huggingface-hub==0.19.4
8
- pyyaml==6.0.1
9
- einops==0.7.0
10
- transformers==4.21.0
11
-
12
- # CRITICAL: NumPy 1.24.3 for PyTorch 1.13.x compatibility
13
- numpy==1.24.3
14
-
15
- # PyTorch 1.13.x - Compatible with NumPy 1.21-1.24
16
- torch==1.13.1
17
- torchvision==0.14.1
18
- torchaudio==0.13.1
19
-
20
- # omegaconf - Version that has is_primitive_type (CRITICAL!)
21
- omegaconf==2.0.0
22
-
23
- # fairseq-signals will be installed from source in Dockerfile
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
requirements_hf_spaces_py39.txt DELETED
@@ -1,25 +0,0 @@
1
- # HF Spaces Requirements - Python 3.9 Compatible
2
- # These versions work on HF Spaces with Python 3.9
3
-
4
- # Core dependencies
5
- fastapi==0.104.1
6
- uvicorn[standard]==0.24.0
7
- huggingface-hub==0.19.4
8
- pyyaml==6.0.1
9
- einops==0.7.0
10
-
11
- # PyTorch 1.13.x - Compatible with Python 3.9 and NumPy 1.24
12
- torch==1.13.1
13
- torchvision==0.14.1
14
- torchaudio==0.13.1
15
-
16
- # NumPy 1.24.x - Compatible with PyTorch 1.13.x
17
- numpy==1.24.3
18
-
19
- # OmegaConf - Version that has is_primitive_type (CRITICAL!)
20
- omegaconf==2.0.0
21
-
22
- # Transformers - Compatible version
23
- transformers==4.21.0
24
-
25
- # fairseq-signals will be installed from source in Dockerfile
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
server.py CHANGED
@@ -6,53 +6,45 @@ from pydantic import BaseModel
6
  from typing import List, Optional
7
  from huggingface_hub import hf_hub_download
8
 
9
- # Import fairseq-signals with robust fallback logic
10
- fairseq_signals_available = False
11
  build_model_from_checkpoint = None
12
 
13
  try:
14
- # Primary: Import from fairseq-signals (official ECG-FM implementation)
15
- from fairseq_signals.models import build_model_from_checkpoint
16
- print("✅ Successfully imported build_model_from_checkpoint from fairseq_signals.models")
17
- fairseq_signals_available = True
18
- except ImportError as e:
19
- print(f"⚠️ fairseq_signals import failed: {e}")
20
  try:
21
- # Fallback 1: Try main fairseq package
22
- from fairseq.models import build_model_from_checkpoint
23
- print("⚠️ Using main fairseq.models as fallback")
24
- fairseq_signals_available = False # Not the official implementation
25
- except ImportError:
26
- try:
27
- # Fallback 2: Try fairseq checkpoint_utils
28
- from fairseq import checkpoint_utils
29
- print("⚠️ Using fairseq.checkpoint_utils as fallback")
30
- def build_model_from_checkpoint(ckpt):
31
- models, args, task = checkpoint_utils.load_model_ensemble_and_task([ckpt])
32
- return models[0]
33
- fairseq_signals_available = False
34
- except ImportError as e:
35
- print(f"❌ Could not import fairseq or fairseq_signals: {e}")
36
- print("🔄 Running in fallback mode - will use alternative model loading")
37
-
38
- # Alternative model loading approach (PyTorch only)
39
- def build_model_from_checkpoint(ckpt):
40
- print(f"🔄 Attempting to load checkpoint: {ckpt}")
41
- try:
42
- # Try to load as PyTorch checkpoint
43
- checkpoint = torch.load(ckpt, map_location='cpu')
44
- if 'model' in checkpoint:
45
- print(" Loaded PyTorch checkpoint with 'model' key")
46
- return checkpoint['model']
47
- elif 'state_dict' in checkpoint:
48
- print(" Loaded PyTorch checkpoint with 'state_dict' key")
49
- return checkpoint['state_dict']
50
- else:
51
- print("⚠️ Checkpoint format not recognized, returning raw checkpoint")
52
- return checkpoint
53
- except Exception as e:
54
- print(f"❌ Failed to load checkpoint: {e}")
55
- raise
56
 
57
  # Configuration
58
  MODEL_REPO = os.getenv("MODEL_REPO", "wanglab/ecg-fm")
@@ -70,7 +62,7 @@ model_loaded = False
70
 
71
  def load_model():
72
  print(f"🔄 Loading model from {MODEL_REPO}...")
73
- print(f"📦 fairseq_signals available: {fairseq_signals_available}")
74
 
75
  try:
76
  # Only download the checkpoint - config is embedded inside
@@ -83,10 +75,6 @@ def load_model():
83
  if hasattr(m, 'eval'):
84
  m.eval()
85
  print("✅ Model loaded successfully and set to eval mode!")
86
- if fairseq_signals_available:
87
- print("🎉 Using OFFICIAL fairseq-signals implementation - Full ECG-FM functionality!")
88
- else:
89
- print("⚠️ Using fallback implementation - Limited functionality")
90
  else:
91
  print("⚠️ Model loaded but no eval() method - may be raw checkpoint")
92
 
@@ -114,8 +102,7 @@ def root():
114
  "message": "ECG-FM API is running",
115
  "model": MODEL_REPO,
116
  "status": "Model loaded" if model_loaded else "Model not loaded",
117
- "fairseq_signals_available": fairseq_signals_available,
118
- "implementation": "Official fairseq-signals" if fairseq_signals_available else "Fallback implementation"
119
  }
120
 
121
  @app.get("/healthz")
@@ -123,8 +110,7 @@ def healthz():
123
  return {
124
  "status": "ok",
125
  "model_loaded": model_loaded,
126
- "fairseq_signals_available": fairseq_signals_available,
127
- "implementation": "Official fairseq-signals" if fairseq_signals_available else "Fallback implementation"
128
  }
129
 
130
  @app.post("/predict")
@@ -133,8 +119,7 @@ def predict(p: ECGPayload):
133
  return {
134
  "error": "Model not loaded",
135
  "status": "unavailable",
136
- "fairseq_signals_available": fairseq_signals_available,
137
- "implementation": "Official fairseq-signals" if fairseq_signals_available else "Fallback implementation"
138
  }
139
 
140
  try:
@@ -157,33 +142,19 @@ def predict(p: ECGPayload):
157
  y = y.detach()
158
 
159
  out = torch.as_tensor(y).cpu().numpy().tolist()
160
-
161
- # Enhanced response with implementation details
162
- response = {
163
  "output": out,
164
  "input_shape": x.shape,
165
  "output_shape": [len(out)],
166
- "fairseq_signals_available": fairseq_signals_available,
167
- "implementation": "Official fairseq-signals" if fairseq_signals_available else "Fallback implementation"
168
  }
169
 
170
- # Add clinical interpretation if using fairseq-signals
171
- if fairseq_signals_available:
172
- response["note"] = "Full ECG-FM clinical interpretation available"
173
- response["capabilities"] = ["Feature extraction", "Clinical interpretation", "Abnormality detection", "Confidence scoring"]
174
- else:
175
- response["note"] = "Limited to feature extraction only - using fallback implementation"
176
- response["capabilities"] = ["Feature extraction only"]
177
-
178
- return response
179
-
180
  except Exception as e:
181
  print(f"❌ Prediction error: {e}")
182
  return {
183
  "error": str(e),
184
  "status": "prediction_failed",
185
- "fairseq_signals_available": fairseq_signals_available,
186
- "implementation": "Official fairseq-signals" if fairseq_signals_available else "Fallback implementation"
187
  }
188
 
189
  if __name__ == "__main__":
 
6
  from typing import List, Optional
7
  from huggingface_hub import hf_hub_download
8
 
9
+ # Import fairseq with robust fallback logic
10
+ fairseq_available = False
11
  build_model_from_checkpoint = None
12
 
13
  try:
14
+ from fairseq.models import build_model_from_checkpoint
15
+ print("✅ Successfully imported build_model_from_checkpoint from fairseq.models")
16
+ fairseq_available = True
17
+ except ImportError:
 
 
18
  try:
19
+ from fairseq import checkpoint_utils
20
+ print("⚠️ Using fairseq.checkpoint_utils as fallback")
21
+ # Create a wrapper function for compatibility
22
+ def build_model_from_checkpoint(ckpt):
23
+ models, args, task = checkpoint_utils.load_model_ensemble_and_task([ckpt])
24
+ return models[0]
25
+ fairseq_available = True
26
+ except ImportError as e:
27
+ print(f" Could not import fairseq: {e}")
28
+ print("🔄 Running in fallback mode - will use alternative model loading")
29
+
30
+ # Alternative model loading approach
31
+ def build_model_from_checkpoint(ckpt):
32
+ print(f"🔄 Attempting to load checkpoint: {ckpt}")
33
+ try:
34
+ # Try to load as PyTorch checkpoint
35
+ checkpoint = torch.load(ckpt, map_location='cpu')
36
+ if 'model' in checkpoint:
37
+ print("✅ Loaded PyTorch checkpoint with 'model' key")
38
+ return checkpoint['model']
39
+ elif 'state_dict' in checkpoint:
40
+ print("✅ Loaded PyTorch checkpoint with 'state_dict' key")
41
+ return checkpoint['state_dict']
42
+ else:
43
+ print("⚠️ Checkpoint format not recognized, returning raw checkpoint")
44
+ return checkpoint
45
+ except Exception as e:
46
+ print(f" Failed to load checkpoint: {e}")
47
+ raise
 
 
 
 
 
 
48
 
49
  # Configuration
50
  MODEL_REPO = os.getenv("MODEL_REPO", "wanglab/ecg-fm")
 
62
 
63
  def load_model():
64
  print(f"🔄 Loading model from {MODEL_REPO}...")
65
+ print(f"📦 fairseq available: {fairseq_available}")
66
 
67
  try:
68
  # Only download the checkpoint - config is embedded inside
 
75
  if hasattr(m, 'eval'):
76
  m.eval()
77
  print("✅ Model loaded successfully and set to eval mode!")
 
 
 
 
78
  else:
79
  print("⚠️ Model loaded but no eval() method - may be raw checkpoint")
80
 
 
102
  "message": "ECG-FM API is running",
103
  "model": MODEL_REPO,
104
  "status": "Model loaded" if model_loaded else "Model not loaded",
105
+ "fairseq_available": fairseq_available
 
106
  }
107
 
108
  @app.get("/healthz")
 
110
  return {
111
  "status": "ok",
112
  "model_loaded": model_loaded,
113
+ "fairseq_available": fairseq_available
 
114
  }
115
 
116
  @app.post("/predict")
 
119
  return {
120
  "error": "Model not loaded",
121
  "status": "unavailable",
122
+ "fairseq_available": fairseq_available
 
123
  }
124
 
125
  try:
 
142
  y = y.detach()
143
 
144
  out = torch.as_tensor(y).cpu().numpy().tolist()
145
+ return {
 
 
146
  "output": out,
147
  "input_shape": x.shape,
148
  "output_shape": [len(out)],
149
+ "fairseq_available": fairseq_available
 
150
  }
151
 
 
 
 
 
 
 
 
 
 
 
152
  except Exception as e:
153
  print(f"❌ Prediction error: {e}")
154
  return {
155
  "error": str(e),
156
  "status": "prediction_failed",
157
+ "fairseq_available": fairseq_available
 
158
  }
159
 
160
  if __name__ == "__main__":
test_dependencies_lightweight.py DELETED
@@ -1,213 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Lightweight Dependency Testing
4
- =============================
5
-
6
- Test dependencies locally without Docker for systems with limited resources.
7
- This catches most dependency issues before HF upload.
8
- """
9
-
10
- import sys
11
- import subprocess
12
- import importlib
13
-
14
- def test_python_version():
15
- """Test Python version compatibility"""
16
- print("🐍 Testing Python Version")
17
- print("=" * 40)
18
-
19
- version = sys.version_info
20
- print(f"Current: {version.major}.{version.minor}.{version.micro}")
21
-
22
- if version.major == 3 and 8 <= version.minor <= 11:
23
- print("✅ Python version compatible with HF Spaces")
24
- return True
25
- else:
26
- print("❌ Python version not compatible with HF Spaces")
27
- print(" HF Spaces supports Python 3.8-3.11")
28
- return False
29
-
30
- def test_package_installation():
31
- """Test if packages can be installed"""
32
- print("\n📦 Testing Package Installation")
33
- print("=" * 40)
34
-
35
- packages = [
36
- ('numpy', '1.24.3'),
37
- ('torch', '1.13.1'),
38
- ('omegaconf', '2.3.0'),
39
- ('fastapi', '0.104.1'),
40
- ('uvicorn', '0.24.0'),
41
- ('huggingface-hub', '0.19.4'),
42
- ('transformers', '4.21.0')
43
- ]
44
-
45
- all_good = True
46
-
47
- for package, version in packages:
48
- print(f"Testing {package}=={version}...")
49
-
50
- try:
51
- # Try to install the specific version
52
- cmd = [sys.executable, '-m', 'pip', 'install', f'{package}=={version}']
53
- result = subprocess.run(cmd, capture_output=True, text=True, timeout=60)
54
-
55
- if result.returncode == 0:
56
- print(f" ✅ {package}=={version} installed successfully")
57
- else:
58
- print(f" ❌ {package}=={version} failed to install")
59
- print(f" Error: {result.stderr}")
60
- all_good = False
61
-
62
- except subprocess.TimeoutExpired:
63
- print(f" ⚠️ {package}=={version} installation timed out")
64
- all_good = False
65
- except Exception as e:
66
- print(f" ❌ {package}=={version} error: {e}")
67
- all_good = False
68
-
69
- return all_good
70
-
71
- def test_imports():
72
- """Test if packages can be imported"""
73
- print("\n🔍 Testing Package Imports")
74
- print("=" * 40)
75
-
76
- packages = [
77
- 'numpy',
78
- 'torch',
79
- 'omegaconf',
80
- 'fastapi',
81
- 'uvicorn',
82
- 'huggingface_hub',
83
- 'transformers'
84
- ]
85
-
86
- all_good = True
87
-
88
- for package in packages:
89
- try:
90
- module = importlib.import_module(package)
91
- version = getattr(module, '__version__', 'Unknown')
92
- print(f"✅ {package}: {version}")
93
- except ImportError as e:
94
- print(f"❌ {package}: Import failed - {e}")
95
- all_good = False
96
- except Exception as e:
97
- print(f"⚠️ {package}: Error - {e}")
98
- all_good = False
99
-
100
- return all_good
101
-
102
- def test_version_compatibility():
103
- """Test version compatibility"""
104
- print("\n🔧 Testing Version Compatibility")
105
- print("=" * 40)
106
-
107
- try:
108
- import numpy
109
- import torch
110
-
111
- numpy_version = numpy.__version__
112
- torch_version = torch.__version__
113
-
114
- print(f"NumPy: {numpy_version}")
115
- print(f"PyTorch: {torch_version}")
116
-
117
- # Check NumPy compatibility
118
- if numpy_version.startswith('1.24'):
119
- print("✅ NumPy 1.24.x - Compatible with PyTorch 1.13.x")
120
- elif numpy_version.startswith('2.'):
121
- print("❌ NumPy 2.x - NOT compatible with PyTorch 1.13.x")
122
- return False
123
- else:
124
- print(f"⚠️ NumPy {numpy_version} - Check compatibility")
125
-
126
- # Check PyTorch compatibility
127
- if torch_version.startswith('1.13'):
128
- print("✅ PyTorch 1.13.x - Compatible with NumPy 1.24.x")
129
- else:
130
- print(f"⚠️ PyTorch {torch_version} - Check compatibility")
131
-
132
- return True
133
-
134
- except ImportError as e:
135
- print(f"❌ Cannot test compatibility: {e}")
136
- return False
137
-
138
- def test_fairseq_signals_import():
139
- """Test fairseq-signals import (if available)"""
140
- print("\n🧬 Testing fairseq-signals Import")
141
- print("=" * 40)
142
-
143
- try:
144
- # This will fail locally but shows the import path
145
- import fairseq_signals
146
- print("✅ fairseq_signals available locally")
147
- return True
148
- except ImportError:
149
- print("⚠️ fairseq_signals not available locally (expected)")
150
- print(" This will be installed from source in Docker")
151
- return True
152
- except Exception as e:
153
- print(f"❌ fairseq_signals error: {e}")
154
- return False
155
-
156
- def main():
157
- """Main testing function"""
158
- print("🚀 Lightweight Dependency Testing for ECG-FM")
159
- print("=" * 60)
160
- print("This tests dependencies without Docker for limited systems")
161
- print()
162
-
163
- tests = [
164
- ("Python Version", test_python_version),
165
- ("Package Installation", test_package_installation),
166
- ("Package Imports", test_imports),
167
- ("Version Compatibility", test_version_compatibility),
168
- ("fairseq-signals Import", test_fairseq_signals_import)
169
- ]
170
-
171
- results = []
172
-
173
- for test_name, test_func in tests:
174
- print(f"\n{'='*60}")
175
- print(f"🧪 {test_name}")
176
- print(f"{'='*60}")
177
-
178
- try:
179
- result = test_func()
180
- results.append((test_name, result))
181
- except Exception as e:
182
- print(f"❌ Test failed with error: {e}")
183
- results.append((test_name, False))
184
-
185
- # Summary
186
- print(f"\n{'='*60}")
187
- print("📊 TEST SUMMARY")
188
- print(f"{'='*60}")
189
-
190
- passed = 0
191
- total = len(results)
192
-
193
- for test_name, result in results:
194
- status = "✅ PASS" if result else "❌ FAIL"
195
- print(f"{test_name}: {status}")
196
- if result:
197
- passed += 1
198
-
199
- print(f"\nResults: {passed}/{total} tests passed")
200
-
201
- if passed == total:
202
- print("\n🎉 ALL TESTS PASSED!")
203
- print("✅ Dependencies look good for HF upload")
204
- print("💡 Still recommend Docker test if possible")
205
- else:
206
- print(f"\n❌ {total-passed} tests failed!")
207
- print("⚠️ Fix dependency issues before HF upload")
208
- print("💡 Check the output above for specific problems")
209
-
210
- return 0 if passed == total else 1
211
-
212
- if __name__ == "__main__":
213
- sys.exit(main())
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
test_env_simple.py DELETED
@@ -1,102 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Simple Environment Test Script
4
- =============================
5
-
6
- Tests the Python 3.13 compatible environment without Unicode issues.
7
- """
8
-
9
- import sys
10
- import os
11
-
12
- def test_environment():
13
- """Test the environment"""
14
- print("Testing Python 3.13 Compatible Environment")
15
- print("=" * 50)
16
-
17
- # Get the virtual environment Python
18
- if os.name == 'nt': # Windows
19
- python_path = os.path.join("ecg_fm_env_py313", "Scripts", "python.exe")
20
- else: # Unix/Linux
21
- python_path = os.path.join("ecg_fm_env_py313", "bin", "python")
22
-
23
- if not os.path.exists(python_path):
24
- print("Virtual environment not found")
25
- return False
26
-
27
- print(f"Using Python: {python_path}")
28
-
29
- # Test imports
30
- test_script = """
31
- import sys
32
- print(f"Python: {sys.version}")
33
-
34
- try:
35
- import numpy
36
- print(f"NumPy: {numpy.__version__}")
37
- except ImportError as e:
38
- print(f"NumPy: FAILED - {e}")
39
-
40
- try:
41
- import torch
42
- print(f"PyTorch: {torch.__version__}")
43
- except ImportError as e:
44
- print(f"PyTorch: FAILED - {e}")
45
-
46
- try:
47
- import omegaconf
48
- print(f"OmegaConf: {omegaconf.__version__}")
49
- # Test if is_primitive_type exists
50
- if hasattr(omegaconf._utils, 'is_primitive_type'):
51
- print("OmegaConf: is_primitive_type AVAILABLE")
52
- else:
53
- print("OmegaConf: is_primitive_type NOT AVAILABLE")
54
- except ImportError as e:
55
- print(f"OmegaConf: FAILED - {e}")
56
-
57
- try:
58
- import fastapi
59
- print(f"FastAPI: {fastapi.__version__}")
60
- except ImportError as e:
61
- print(f"FastAPI: FAILED - {e}")
62
-
63
- try:
64
- import transformers
65
- print(f"Transformers: {transformers.__version__}")
66
- except ImportError as e:
67
- print(f"Transformers: FAILED - {e}")
68
-
69
- try:
70
- import huggingface_hub
71
- print(f"HuggingFace Hub: {huggingface_hub.__version__}")
72
- except ImportError as e:
73
- print(f"HuggingFace Hub: FAILED - {e}")
74
-
75
- try:
76
- import uvicorn
77
- print(f"Uvicorn: {uvicorn.__version__}")
78
- except ImportError as e:
79
- print(f"Uvicorn: FAILED - {e}")
80
- """
81
-
82
- try:
83
- result = subprocess.run([python_path, '-c', test_script],
84
- capture_output=True, text=True)
85
-
86
- if result.returncode == 0:
87
- print("Environment test successful!")
88
- print("\nPackage Versions:")
89
- print(result.stdout)
90
- return True
91
- else:
92
- print("Environment test failed!")
93
- print(result.stderr)
94
- return False
95
-
96
- except Exception as e:
97
- print(f"Test error: {e}")
98
- return False
99
-
100
- if __name__ == "__main__":
101
- import subprocess
102
- test_environment()
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
test_fairseq_signals.py CHANGED
@@ -137,3 +137,4 @@ def main():
137
 
138
  if __name__ == "__main__":
139
  sys.exit(main())
 
 
137
 
138
  if __name__ == "__main__":
139
  sys.exit(main())
140
+
test_local_docker.py DELETED
@@ -1,180 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Local Docker Testing Script
4
- ==========================
5
-
6
- Test the exact same Docker environment locally before uploading to HF Spaces.
7
- This prevents wasting time on failed builds.
8
- """
9
-
10
- import subprocess
11
- import sys
12
- import os
13
- import time
14
-
15
- def test_docker_build():
16
- """Test Docker build locally"""
17
- print("🐳 Testing Docker Build Locally")
18
- print("=" * 50)
19
-
20
- # Check if Docker is available
21
- try:
22
- result = subprocess.run(['docker', '--version'], capture_output=True, text=True)
23
- if result.returncode == 0:
24
- print(f"✅ Docker available: {result.stdout.strip()}")
25
- else:
26
- print("❌ Docker not available")
27
- return False
28
- except FileNotFoundError:
29
- print("❌ Docker not installed")
30
- return False
31
-
32
- # Build the Docker image
33
- print("\n🔧 Building Docker image...")
34
- try:
35
- build_cmd = [
36
- 'docker', 'build',
37
- '-t', 'ecg-fm-test',
38
- '--no-cache', # Force fresh build
39
- '.'
40
- ]
41
-
42
- print(f"Command: {' '.join(build_cmd)}")
43
- result = subprocess.run(build_cmd, capture_output=True, text=True)
44
-
45
- if result.returncode == 0:
46
- print("✅ Docker build successful!")
47
- return True
48
- else:
49
- print("❌ Docker build failed!")
50
- print("\n📋 Build Output:")
51
- print(result.stdout)
52
- print("\n❌ Error Output:")
53
- print(result.stderr)
54
- return False
55
-
56
- except Exception as e:
57
- print(f"❌ Build error: {e}")
58
- return False
59
-
60
- def test_docker_run():
61
- """Test running the container locally"""
62
- print("\n🚀 Testing Docker Container Run")
63
- print("=" * 50)
64
-
65
- try:
66
- # Run container in background
67
- run_cmd = [
68
- 'docker', 'run',
69
- '-d', # Detached mode
70
- '-p', '7860:7860', # Port mapping
71
- '--name', 'ecg-fm-test-container',
72
- 'ecg-fm-test'
73
- ]
74
-
75
- print(f"Command: {' '.join(run_cmd)}")
76
- result = subprocess.run(run_cmd, capture_output=True, text=True)
77
-
78
- if result.returncode == 0:
79
- print("✅ Container started successfully!")
80
-
81
- # Wait for startup
82
- print("⏳ Waiting for container startup...")
83
- time.sleep(10)
84
-
85
- # Test API endpoints
86
- test_api_endpoints()
87
-
88
- # Cleanup
89
- cleanup_container()
90
- return True
91
- else:
92
- print("❌ Container start failed!")
93
- print(result.stderr)
94
- return False
95
-
96
- except Exception as e:
97
- print(f"❌ Run error: {e}")
98
- return False
99
-
100
- def test_api_endpoints():
101
- """Test API endpoints"""
102
- print("\n🌐 Testing API Endpoints")
103
- print("=" * 50)
104
-
105
- import requests
106
-
107
- base_url = "http://localhost:7860"
108
-
109
- # Test health endpoint
110
- try:
111
- response = requests.get(f"{base_url}/healthz", timeout=10)
112
- if response.status_code == 200:
113
- print("✅ Health endpoint working")
114
- print(f"Response: {response.json()}")
115
- else:
116
- print(f"❌ Health endpoint failed: {response.status_code}")
117
- except Exception as e:
118
- print(f"❌ Health endpoint error: {e}")
119
-
120
- # Test root endpoint
121
- try:
122
- response = requests.get(f"{base_url}/", timeout=10)
123
- if response.status_code == 200:
124
- print("✅ Root endpoint working")
125
- print(f"Response: {response.json()}")
126
- else:
127
- print(f"❌ Root endpoint failed: {response.status_code}")
128
- except Exception as e:
129
- print(f"❌ Root endpoint error: {e}")
130
-
131
- def cleanup_container():
132
- """Clean up test container"""
133
- print("\n🧹 Cleaning up test container...")
134
-
135
- try:
136
- # Stop container
137
- subprocess.run(['docker', 'stop', 'ecg-fm-test-container'],
138
- capture_output=True, text=True)
139
-
140
- # Remove container
141
- subprocess.run(['docker', 'rm', 'ecg-fm-test-container'],
142
- capture_output=True, text=True)
143
-
144
- # Remove image
145
- subprocess.run(['docker', 'rmi', 'ecg-fm-test'],
146
- capture_output=True, text=True)
147
-
148
- print("✅ Cleanup completed")
149
- except Exception as e:
150
- print(f"⚠️ Cleanup warning: {e}")
151
-
152
- def main():
153
- """Main testing function"""
154
- print("🚀 Local Docker Testing for ECG-FM")
155
- print("=" * 60)
156
- print("This will test the exact same environment locally before HF upload")
157
- print()
158
-
159
- # Test 1: Docker build
160
- build_success = test_docker_build()
161
-
162
- if not build_success:
163
- print("\n❌ Docker build failed! Fix issues before uploading to HF.")
164
- return 1
165
-
166
- # Test 2: Docker run
167
- run_success = test_docker_run()
168
-
169
- if not run_success:
170
- print("\n❌ Docker run failed! Fix issues before uploading to HF.")
171
- return 1
172
-
173
- print("\n🎉 ALL TESTS PASSED!")
174
- print("✅ Ready to upload to HF Spaces!")
175
- print("🚀 The build should succeed on HF.")
176
-
177
- return 0
178
-
179
- if __name__ == "__main__":
180
- sys.exit(main())
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
test_omegaconf_fix.py DELETED
@@ -1,126 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Test OmegaConf Fix Locally
4
- ==========================
5
-
6
- Tests if the OmegaConf fix works before deploying to HF Spaces.
7
- """
8
-
9
- import subprocess
10
- import sys
11
- import os
12
-
13
- def test_omegaconf_override():
14
- """Test if we can override OmegaConf version"""
15
- print("🧪 Testing OmegaConf Version Override")
16
- print("=" * 50)
17
-
18
- # Get the virtual environment Python
19
- if os.name == 'nt': # Windows
20
- python_path = os.path.join("ecg_fm_env_py313", "Scripts", "python.exe")
21
- else: # Unix/Linux
22
- python_path = os.path.join("ecg_fm_env_py313", "bin", "python")
23
-
24
- if not os.path.exists(python_path):
25
- print("❌ Virtual environment not found")
26
- return False
27
-
28
- print(f"Using Python: {python_path}")
29
-
30
- # Test 1: Check current OmegaConf version
31
- print("\n📋 Current OmegaConf version:")
32
- try:
33
- result = subprocess.run([python_path, '-c',
34
- "import omegaconf; print(f'Version: {omegaconf.__version__}'); print(f'is_primitive_type: {hasattr(omegaconf._utils, \"is_primitive_type\")}')"],
35
- capture_output=True, text=True)
36
- if result.returncode == 0:
37
- print(result.stdout)
38
- else:
39
- print(f"❌ Error: {result.stderr}")
40
- return False
41
- except Exception as e:
42
- print(f"❌ Test error: {e}")
43
- return False
44
-
45
- # Test 2: Simulate fairseq-signals installation (install a package that might override OmegaConf)
46
- print("\n🔧 Simulating fairseq-signals installation...")
47
- try:
48
- # Install a package that might have conflicting dependencies
49
- result = subprocess.run([python_path, '-m', 'pip', 'install', '--upgrade', 'omegaconf'],
50
- capture_output=True, text=True)
51
- if result.returncode == 0:
52
- print("✅ Upgraded OmegaConf")
53
- else:
54
- print(f"⚠️ Upgrade warning: {result.stderr}")
55
- except Exception as e:
56
- print(f"⚠️ Upgrade warning: {e}")
57
-
58
- # Test 3: Check OmegaConf version after upgrade
59
- print("\n📋 OmegaConf version after upgrade:")
60
- try:
61
- result = subprocess.run([python_path, '-c',
62
- "import omegaconf; print(f'Version: {omegaconf.__version__}'); print(f'is_primitive_type: {hasattr(omegaconf._utils, \"is_primitive_type\")}')"],
63
- capture_output=True, text=True)
64
- if result.returncode == 0:
65
- print(result.stdout)
66
- else:
67
- print(f"❌ Error: {result.stderr}")
68
- return False
69
- except Exception as e:
70
- print(f"❌ Test error: {e}")
71
- return False
72
-
73
- # Test 4: Force reinstall correct version
74
- print("\n🔧 Forcing correct OmegaConf version...")
75
- try:
76
- result = subprocess.run([python_path, '-m', 'pip', 'install', '--force-reinstall', '--no-deps', 'omegaconf==2.0.0'],
77
- capture_output=True, text=True)
78
- if result.returncode == 0:
79
- print("✅ Forced reinstall of OmegaConf 2.0.0")
80
- else:
81
- print(f"❌ Reinstall failed: {result.stderr}")
82
- return False
83
- except Exception as e:
84
- print(f"❌ Reinstall error: {e}")
85
- return False
86
-
87
- # Test 5: Verify final version
88
- print("\n📋 Final OmegaConf version:")
89
- try:
90
- result = subprocess.run([python_path, '-c',
91
- "import omegaconf; print(f'Version: {omegaconf.__version__}'); print(f'is_primitive_type: {hasattr(omegaconf._utils, \"is_primitive_type\")}')"],
92
- capture_output=True, text=True)
93
- if result.returncode == 0:
94
- print(result.stdout)
95
- if "2.0.0" in result.stdout and "True" in result.stdout:
96
- print("✅ SUCCESS: OmegaConf 2.0.0 with is_primitive_type!")
97
- return True
98
- else:
99
- print("❌ FAILED: Wrong version or missing is_primitive_type")
100
- return False
101
- else:
102
- print(f"❌ Error: {result.stderr}")
103
- return False
104
- except Exception as e:
105
- print(f"❌ Test error: {e}")
106
- return False
107
-
108
- def main():
109
- """Main function"""
110
- print("🚀 Testing OmegaConf Fix Locally")
111
- print("=" * 60)
112
- print("This tests if our Dockerfile fix will work")
113
- print()
114
-
115
- if test_omegaconf_override():
116
- print("\n🎉 LOCAL TEST PASSED!")
117
- print("✅ OmegaConf fix should work on HF Spaces")
118
- print("🚀 Ready to deploy with fixed Dockerfile")
119
- return 0
120
- else:
121
- print("\n❌ LOCAL TEST FAILED!")
122
- print("⚠️ Need to fix the approach")
123
- return 1
124
-
125
- if __name__ == "__main__":
126
- sys.exit(main())
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
verify_versions.py DELETED
@@ -1,154 +0,0 @@
1
- #!/usr/bin/env python3
2
- """
3
- Version Compatibility Verification
4
- ================================
5
-
6
- This script verifies that all package versions are compatible
7
- before deploying to HF Spaces
8
- """
9
-
10
- import sys
11
- import subprocess
12
- import pkg_resources
13
-
14
- def get_installed_version(package_name):
15
- """Get installed version of a package"""
16
- try:
17
- return pkg_resources.get_distribution(package_name).version
18
- except pkg_resources.DistributionNotFound:
19
- return None
20
-
21
- def check_version_compatibility():
22
- """Check if installed versions are compatible"""
23
- print("🔍 Version Compatibility Check for HF Spaces")
24
- print("=" * 60)
25
-
26
- # Required versions for HF Spaces
27
- required_versions = {
28
- 'torch': '1.13.1',
29
- 'torchvision': '0.14.1',
30
- 'torchaudio': '0.13.1',
31
- 'omegaconf': '1.4.1',
32
- 'numpy': '1.24.3',
33
- 'fastapi': '0.104.1',
34
- 'uvicorn': '0.24.0',
35
- 'transformers': '4.21.0',
36
- 'huggingface-hub': '0.19.4',
37
- 'pyyaml': '6.0.1',
38
- 'einops': '0.7.0'
39
- }
40
-
41
- print("📋 Required versions for HF Spaces compatibility:")
42
- for package, version in required_versions.items():
43
- print(f" {package}: {version}")
44
-
45
- print("\n🔍 Checking installed versions...")
46
-
47
- all_compatible = True
48
- compatibility_issues = []
49
-
50
- for package, required_version in required_versions.items():
51
- installed_version = get_installed_version(package)
52
-
53
- if installed_version is None:
54
- print(f"❌ {package}: Not installed")
55
- all_compatible = False
56
- compatibility_issues.append(f"{package}: Not installed")
57
- else:
58
- print(f"✅ {package}: {installed_version}")
59
-
60
- # Check if versions match (allowing for minor variations)
61
- if package.startswith('torch'):
62
- # PyTorch packages should match exactly
63
- if installed_version != required_version:
64
- print(f" ⚠️ Version mismatch: {installed_version} != {required_version}")
65
- all_compatible = False
66
- compatibility_issues.append(f"{package}: {installed_version} != {required_version}")
67
- else:
68
- # Other packages can have compatible versions
69
- print(f" ✅ Version compatible")
70
-
71
- print("\n📊 Compatibility Summary:")
72
- if all_compatible:
73
- print("🎉 ALL VERSIONS ARE COMPATIBLE!")
74
- print("✅ Ready for HF Spaces deployment")
75
- return True
76
- else:
77
- print("❌ VERSION COMPATIBILITY ISSUES FOUND:")
78
- for issue in compatibility_issues:
79
- print(f" - {issue}")
80
- print("\n⚠️ Please fix version conflicts before deployment")
81
- return False
82
-
83
- def check_python_version():
84
- """Check Python version compatibility"""
85
- print("\n🐍 Python Version Check:")
86
- python_version = sys.version_info
87
-
88
- print(f" Current: {python_version.major}.{python_version.minor}.{python_version.micro}")
89
-
90
- # HF Spaces supports Python 3.8-3.11
91
- if python_version.major == 3 and 8 <= python_version.minor <= 11:
92
- print(" ✅ Python version compatible with HF Spaces")
93
- return True
94
- else:
95
- print(" ❌ Python version not compatible with HF Spaces")
96
- print(" ⚠️ HF Spaces supports Python 3.8-3.11")
97
- return False
98
-
99
- def check_system_requirements():
100
- """Check system requirements"""
101
- print("\n💻 System Requirements Check:")
102
-
103
- # Check if we're on a compatible system
104
- import platform
105
- system = platform.system()
106
- print(f" OS: {system}")
107
-
108
- if system in ['Linux', 'Darwin']:
109
- print(" ✅ OS compatible with Docker deployment")
110
- return True
111
- elif system == 'Windows':
112
- print(" ⚠️ Windows detected - Docker deployment may have issues")
113
- print(" 💡 Consider using WSL2 or Linux environment")
114
- return False
115
- else:
116
- print(" ❌ Unknown OS - compatibility uncertain")
117
- return False
118
-
119
- def main():
120
- """Main verification function"""
121
- print("🚀 HF Spaces Version Compatibility Verification")
122
- print("=" * 80)
123
-
124
- # Check Python version
125
- python_ok = check_python_version()
126
-
127
- # Check system requirements
128
- system_ok = check_system_requirements()
129
-
130
- # Check package versions
131
- packages_ok = check_version_compatibility()
132
-
133
- # Final summary
134
- print("\n" + "=" * 80)
135
- print("📊 FINAL VERIFICATION SUMMARY:")
136
- print("=" * 80)
137
-
138
- print(f"Python Version: {'✅ PASS' if python_ok else '❌ FAIL'}")
139
- print(f"System Requirements: {'✅ PASS' if system_ok else '❌ FAIL'}")
140
- print(f"Package Versions: {'✅ PASS' if packages_ok else '❌ FAIL'}")
141
-
142
- if python_ok and system_ok and packages_ok:
143
- print("\n🎉 ALL CHECKS PASSED!")
144
- print("✅ Ready for HF Spaces deployment with fairseq-signals")
145
- print("🚀 Expected: 3x accuracy improvement (25% → 80%+)")
146
- return 0
147
- else:
148
- print("\n❌ SOME CHECKS FAILED!")
149
- print("⚠️ Please resolve issues before deployment")
150
- print("💡 Check the output above for specific problems")
151
- return 1
152
-
153
- if __name__ == "__main__":
154
- sys.exit(main())