File size: 9,508 Bytes
fb867c3
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
#!/usr/bin/env python3
"""
Deployment validation script for Felix Framework.
Validates that all deployment components are properly configured.
"""

import os
import sys
import importlib
import json
from pathlib import Path


def validate_file_structure():
    """Validate that all required deployment files exist."""
    required_files = [
        'Dockerfile',
        'docker-compose.yml',
        'requirements-deployment.txt',
        '.env.example',
        'app_fastapi.py',
        'config/settings.py',
        'deployment/web_service.py',
        'deployment/health_checks.py',
        'deployment/logging_config.py',
        'deployment/security.py',
        '.github/workflows/ci-cd.yml',
        '.github/workflows/security-audit.yml',
        'config/nginx/nginx.conf',
        'config/prometheus.yml',
        'config/redis.conf',
        'DEPLOYMENT_GUIDE.md',
        'DEPLOYMENT_SUMMARY.md'
    ]

    missing_files = []
    for file_path in required_files:
        if not Path(file_path).exists():
            missing_files.append(file_path)

    return {
        'valid': len(missing_files) == 0,
        'missing_files': missing_files,
        'total_files': len(required_files),
        'found_files': len(required_files) - len(missing_files)
    }


def validate_imports():
    """Validate that deployment modules can be imported."""
    test_imports = [
        'config.settings',
        'deployment.health_checks',
        'deployment.logging_config',
        'deployment.security'
    ]

    import_results = {}

    for module_name in test_imports:
        try:
            importlib.import_module(module_name)
            import_results[module_name] = {'status': 'success', 'error': None}
        except Exception as e:
            import_results[module_name] = {'status': 'failed', 'error': str(e)}

    successful_imports = sum(1 for result in import_results.values() if result['status'] == 'success')

    return {
        'valid': successful_imports == len(test_imports),
        'results': import_results,
        'successful': successful_imports,
        'total': len(test_imports)
    }


def validate_docker_files():
    """Validate Docker configuration files."""
    docker_files = ['Dockerfile', 'docker-compose.yml']
    results = {}

    for file_path in docker_files:
        if Path(file_path).exists():
            try:
                with open(file_path, 'r') as f:
                    content = f.read()

                # Basic validation
                if file_path == 'Dockerfile':
                    required_keywords = ['FROM', 'COPY', 'RUN', 'EXPOSE', 'CMD']
                elif file_path == 'docker-compose.yml':
                    required_keywords = ['version:', 'services:', 'felix-app:', 'ports:']

                missing_keywords = [kw for kw in required_keywords if kw not in content]

                results[file_path] = {
                    'exists': True,
                    'valid': len(missing_keywords) == 0,
                    'missing_keywords': missing_keywords,
                    'size_bytes': len(content)
                }
            except Exception as e:
                results[file_path] = {
                    'exists': True,
                    'valid': False,
                    'error': str(e)
                }
        else:
            results[file_path] = {
                'exists': False,
                'valid': False,
                'error': 'File not found'
            }

    return results


def validate_configuration():
    """Validate configuration files."""
    config_files = {
        '.env.example': ['ENVIRONMENT=', 'SECRET_KEY=', 'LLM_ENDPOINT='],
        'config/prometheus.yml': ['global:', 'scrape_configs:', 'felix-framework'],
        'config/nginx/nginx.conf': ['server {', 'proxy_pass', 'felix_app'],
        'config/redis.conf': ['bind', 'port', 'maxmemory']
    }

    results = {}

    for file_path, required_content in config_files.items():
        if Path(file_path).exists():
            try:
                with open(file_path, 'r') as f:
                    content = f.read()

                missing_content = [item for item in required_content if item not in content]

                results[file_path] = {
                    'exists': True,
                    'valid': len(missing_content) == 0,
                    'missing_content': missing_content,
                    'size_bytes': len(content)
                }
            except Exception as e:
                results[file_path] = {
                    'exists': True,
                    'valid': False,
                    'error': str(e)
                }
        else:
            results[file_path] = {
                'exists': False,
                'valid': False,
                'error': 'File not found'
            }

    return results


def validate_github_actions():
    """Validate GitHub Actions workflows."""
    workflow_files = ['.github/workflows/ci-cd.yml', '.github/workflows/security-audit.yml']
    results = {}

    for file_path in workflow_files:
        if Path(file_path).exists():
            try:
                with open(file_path, 'r') as f:
                    content = f.read()

                # Check for required GitHub Actions keywords
                required_keywords = ['name:', 'on:', 'jobs:', 'runs-on:', 'steps:']
                missing_keywords = [kw for kw in required_keywords if kw not in content]

                results[file_path] = {
                    'exists': True,
                    'valid': len(missing_keywords) == 0,
                    'missing_keywords': missing_keywords,
                    'size_bytes': len(content)
                }
            except Exception as e:
                results[file_path] = {
                    'exists': True,
                    'valid': False,
                    'error': str(e)
                }
        else:
            results[file_path] = {
                'exists': False,
                'valid': False,
                'error': 'File not found'
            }

    return results


def main():
    """Run all validation checks."""
    print("πŸ” Validating Felix Framework Deployment Configuration")
    print("=" * 60)

    # Run all validations
    file_structure = validate_file_structure()
    print(f"\nπŸ“ File Structure: {'βœ… PASS' if file_structure['valid'] else '❌ FAIL'}")
    print(f"   Found {file_structure['found_files']}/{file_structure['total_files']} required files")

    if file_structure['missing_files']:
        print("   Missing files:")
        for file in file_structure['missing_files']:
            print(f"     - {file}")

    # Skip import validation if running in minimal environment
    try:
        import_validation = validate_imports()
        print(f"\n🐍 Python Imports: {'βœ… PASS' if import_validation['valid'] else '❌ FAIL'}")
        print(f"   {import_validation['successful']}/{import_validation['total']} modules imported successfully")

        for module, result in import_validation['results'].items():
            status = "βœ…" if result['status'] == 'success' else "❌"
            print(f"     {status} {module}")
            if result['error']:
                print(f"       Error: {result['error']}")
    except Exception as e:
        print(f"\n🐍 Python Imports: ⚠️  SKIPPED (missing dependencies)")

    docker_validation = validate_docker_files()
    print(f"\n🐳 Docker Files:")
    for file, result in docker_validation.items():
        status = "βœ… PASS" if result['valid'] else "❌ FAIL"
        print(f"   {status} {file}")
        if not result['valid'] and 'missing_keywords' in result:
            for keyword in result['missing_keywords']:
                print(f"     Missing: {keyword}")

    config_validation = validate_configuration()
    print(f"\nβš™οΈ  Configuration Files:")
    for file, result in config_validation.items():
        status = "βœ… PASS" if result['valid'] else "❌ FAIL"
        print(f"   {status} {file}")
        if not result['valid'] and 'missing_content' in result:
            for content in result['missing_content']:
                print(f"     Missing: {content}")

    github_validation = validate_github_actions()
    print(f"\nπŸš€ GitHub Actions:")
    for file, result in github_validation.items():
        status = "βœ… PASS" if result['valid'] else "❌ FAIL"
        print(f"   {status} {file}")

    # Overall status
    all_validations = [
        file_structure['valid'],
        all(result['valid'] for result in docker_validation.values()),
        all(result['valid'] for result in config_validation.values()),
        all(result['valid'] for result in github_validation.values())
    ]

    overall_status = all(all_validations)

    print(f"\n🎯 Overall Status: {'βœ… DEPLOYMENT READY' if overall_status else '❌ NEEDS ATTENTION'}")

    if overall_status:
        print("\nπŸš€ Felix Framework deployment configuration is complete and ready!")
        print("   Next steps:")
        print("   1. Copy .env.example to .env and configure your environment")
        print("   2. Set up GitHub secrets for HF Spaces deployment")
        print("   3. Push to main branch to trigger automated deployment")
        print("   4. Or run locally with: docker-compose up -d")
    else:
        print("\n⚠️  Some validation checks failed. Please review the issues above.")

    return 0 if overall_status else 1


if __name__ == "__main__":
    exit(main())