-
Notifications
You must be signed in to change notification settings - Fork 0
feat: Add core CI/CD infrastructure workflows #234
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,178 @@ | ||
| name: PR Validation | ||
|
|
||
| on: | ||
| pull_request: | ||
| branches: [ main, develop ] | ||
| types: [ opened, synchronize, reopened, ready_for_review ] | ||
|
|
||
| permissions: | ||
| contents: read | ||
| pull-requests: write | ||
| issues: write | ||
|
|
||
| env: | ||
| XCODE_VERSION: '15.0' | ||
| SWIFT_VERSION: '5.9' | ||
|
|
||
| jobs: | ||
| validate: | ||
| name: Validate Pull Request | ||
| runs-on: macos-14 | ||
| if: github.event.pull_request.draft == false | ||
|
|
||
| steps: | ||
| - name: Checkout code | ||
| uses: actions/checkout@v4 | ||
| with: | ||
| fetch-depth: 0 | ||
|
|
||
| - name: Setup Xcode | ||
| uses: maxim-lobanov/setup-xcode@v1 | ||
| with: | ||
| xcode-version: ${{ env.XCODE_VERSION }} | ||
|
|
||
| - name: Cache Swift Package Manager | ||
| uses: actions/cache@v4 | ||
| with: | ||
| path: | | ||
| ~/Library/Developer/Xcode/DerivedData/**/SourcePackages | ||
| ~/Library/Caches/org.swift.swiftpm | ||
| .build | ||
| key: ${{ runner.os }}-spm-${{ hashFiles('**/Package.resolved', 'project.yml') }} | ||
| restore-keys: | | ||
| ${{ runner.os }}-spm- | ||
|
|
||
| - name: Install SwiftLint | ||
| run: | | ||
| if ! command -v swiftlint &> /dev/null; then | ||
| brew install swiftlint | ||
| fi | ||
|
|
||
| - name: Run SwiftLint | ||
| run: | | ||
| if [ -f .swiftlint.yml ]; then | ||
| swiftlint lint --reporter github-actions-logging --config .swiftlint.yml | ||
| else | ||
| echo "No .swiftlint.yml found, running with default configuration" | ||
| swiftlint lint --reporter github-actions-logging || true | ||
| fi | ||
|
|
||
| - name: Validate project structure | ||
| run: | | ||
| # Check if project.yml exists (XcodeGen project) | ||
| if [ ! -f "project.yml" ]; then | ||
| echo "::error::project.yml not found - this project uses XcodeGen" | ||
| exit 1 | ||
| fi | ||
|
|
||
| # Verify all module directories exist | ||
| echo "Checking module structure..." | ||
| modules=("Foundation-Core" "Foundation-Models" "Foundation-Resources" "Infrastructure-Network" "Infrastructure-Storage" "Infrastructure-Security" "Infrastructure-Monitoring" "Services-Authentication" "Services-Business" "Services-External" "Services-Search" "Services-Sync" "UI-Core" "UI-Components" "UI-Styles" "Features-Inventory" "Features-Scanner" "Features-Settings" "Features-Analytics" "Features-Locations" "App-Main") | ||
|
|
||
| for module in "${modules[@]}"; do | ||
| if [ ! -d "$module" ]; then | ||
| echo "::warning::Module directory $module not found" | ||
| else | ||
| echo "✓ $module exists" | ||
| fi | ||
| done | ||
|
|
||
| - name: Generate Xcode project | ||
| run: | | ||
| if ! command -v xcodegen &> /dev/null; then | ||
| echo "Installing XcodeGen..." | ||
| brew install xcodegen | ||
| fi | ||
| xcodegen generate | ||
|
|
||
| - name: Resolve Swift Package Dependencies | ||
| run: | | ||
| xcodebuild -resolvePackageDependencies \ | ||
| -project HomeInventoryModular.xcodeproj \ | ||
| -scheme HomeInventoryApp | ||
|
|
||
| - name: Build for iOS Simulator | ||
| run: | | ||
| set -o pipefail | ||
| xcodebuild build \ | ||
| -project HomeInventoryModular.xcodeproj \ | ||
| -scheme HomeInventoryApp \ | ||
| -destination 'platform=iOS Simulator,name=iPhone 15 Pro,OS=17.0' \ | ||
| -configuration Debug \ | ||
| CODE_SIGNING_ALLOWED=NO | ||
|
|
||
| - name: Check for compilation warnings | ||
| run: | | ||
| set -o pipefail | ||
| warnings=$(xcodebuild clean build \ | ||
| -project HomeInventoryModular.xcodeproj \ | ||
| -scheme HomeInventoryApp \ | ||
| -destination 'platform=iOS Simulator,name=iPhone 15 Pro,OS=17.0' \ | ||
| -configuration Debug \ | ||
| 2>&1 | grep -i warning | wc -l) | ||
|
|
||
| echo "Total warnings: $warnings" | ||
| if [ "$warnings" -gt 50 ]; then | ||
| echo "::warning::High number of compilation warnings ($warnings). Consider addressing them." | ||
| fi | ||
|
|
||
| - name: Validate module boundaries | ||
| run: | | ||
| if [ -f "scripts/validate-module-dependencies.sh" ]; then | ||
| chmod +x scripts/validate-module-dependencies.sh | ||
| ./scripts/validate-module-dependencies.sh || echo "::warning::Module dependency validation failed" | ||
| else | ||
| echo "Module dependency validation script not found" | ||
| fi | ||
|
|
||
| - name: Check for TODO and FIXME comments | ||
| run: | | ||
| todos=$(find . -name "*.swift" -not -path "./.*" -exec grep -n "TODO\|FIXME" {} + | wc -l) | ||
| echo "Found $todos TODO/FIXME comments" | ||
| if [ "$todos" -gt 100 ]; then | ||
| echo "::warning::High number of TODO/FIXME comments ($todos). Consider addressing some before merging." | ||
| fi | ||
|
|
||
| - name: Security checks | ||
| run: | | ||
| # Check for potential security issues | ||
| echo "Running basic security checks..." | ||
|
|
||
| # Check for hardcoded secrets (basic patterns) | ||
| if grep -r -i "password\s*=\s*\"" --include="*.swift" . | grep -v "placeholder\|example\|test"; then | ||
| echo "::warning::Potential hardcoded passwords found" | ||
| fi | ||
|
|
||
| if grep -r -i "api[_-]?key\s*=\s*\"" --include="*.swift" . | grep -v "placeholder\|example\|test"; then | ||
| echo "::warning::Potential hardcoded API keys found" | ||
| fi | ||
|
|
||
| # Check for SQL injection vulnerabilities | ||
| if grep -r "\".*SELECT.*\\\(.*\\\).*\"" --include="*.swift" .; then | ||
| echo "::warning::Potential SQL injection vulnerability found" | ||
| fi | ||
|
|
||
| - name: Report PR Status | ||
| if: always() | ||
| uses: actions/github-script@v7 | ||
| with: | ||
| script: | | ||
| const { owner, repo } = context.repo; | ||
| const { number } = context.issue; | ||
|
|
||
| await github.rest.issues.createComment({ | ||
| owner, | ||
| repo, | ||
| issue_number: number, | ||
| body: `## 🔍 PR Validation Results | ||
|
|
||
| **Build Status:** ${{ job.status == 'success' && '✅ Passed' || '❌ Failed' }} | ||
| **SwiftLint:** ${{ steps.swiftlint.outcome == 'success' && '✅ Passed' || '⚠️ Issues found' }} | ||
| **Project Structure:** ${{ steps.validate.outcome == 'success' && '✅ Valid' || '❌ Issues found' }} | ||
|
||
| **Compilation:** ${{ steps.build.outcome == 'success' && '✅ Success' || '❌ Failed' }} | ||
|
||
|
|
||
| ${context.payload.pull_request.mergeable === false ? '⚠️ **Merge conflicts detected** - Please resolve before merging' : ''} | ||
|
|
||
| --- | ||
| *This comment was automatically generated by the PR validation workflow.*` | ||
| }); | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The step ID 'swiftlint' doesn't match any step ID in the workflow. The SwiftLint step doesn't have an ID defined, so this reference will always be empty. Add id: swiftlint to the SwiftLint step.