-
Notifications
You must be signed in to change notification settings - Fork 0
[codex] Guard public repo sensitive content #497
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
2aa036a
af94155
eea0de1
66b6df3
e3f6e3b
102fb96
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,87 @@ | ||
| name: Public Security Scan | ||
|
|
||
| on: | ||
| pull_request: | ||
| push: | ||
| branches: | ||
| - main | ||
| workflow_dispatch: | ||
|
|
||
| permissions: | ||
| contents: read | ||
| pull-requests: read | ||
|
|
||
| jobs: | ||
| public-sensitive-content: | ||
| name: Public Sensitive Content | ||
| runs-on: ubuntu-latest | ||
| steps: | ||
| - name: Checkout | ||
| uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 | ||
| with: | ||
| fetch-depth: 0 | ||
| persist-credentials: false | ||
|
|
||
| - name: Checkout trusted public scanner | ||
| if: github.event_name == 'pull_request' | ||
| uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 | ||
| with: | ||
| ref: ${{ github.base_ref }} | ||
| path: trusted-security-base | ||
| persist-credentials: false | ||
|
|
||
| - name: Setup Node | ||
| uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 | ||
| with: | ||
| node-version: 24 | ||
|
|
||
| - name: Run repo-owned public scan | ||
| shell: bash | ||
| run: | | ||
| set -euo pipefail | ||
| TRUSTED_SCANNER="trusted-security-base/scripts/security/check-public-sensitive-content.js" | ||
| if [ "${{ github.event_name }}" = "pull_request" ] && [ -f "$TRUSTED_SCANNER" ]; then | ||
| node "$TRUSTED_SCANNER" "$PWD" | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. P2: Trusted scanner runs against PR checkout, so PR can neuter its own gate In 'Run repo-owned public scan', when the trusted scanner is present it is executed as Why this matters: A public secrets gate that silently skips large or binary files can miss committed secrets; the threat model should at least be explicit so reviewers know the gate is best-effort, not complete. |
||
| else | ||
| if [ "${{ github.event_name }}" = "pull_request" ]; then | ||
| echo "::warning::Trusted public scanner is missing on ${GITHUB_BASE_REF}; using PR scanner for bootstrap." | ||
| fi | ||
| node scripts/security/check-public-sensitive-content.js "$PWD" | ||
| fi | ||
|
|
||
| gitleaks: | ||
| name: Gitleaks Full History | ||
| runs-on: ubuntu-latest | ||
| steps: | ||
| - name: Checkout | ||
| uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 | ||
| with: | ||
| fetch-depth: 0 | ||
| persist-credentials: false | ||
|
|
||
|
coderabbitai[bot] marked this conversation as resolved.
|
||
| - name: Run Gitleaks | ||
| uses: gitleaks/gitleaks-action@e0c47f4f8be36e29cdc102c57e68cb5cbf0e8d1e | ||
|
Comment on lines
+62
to
+63
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
On Useful? React with 👍 / 👎. |
||
| env: | ||
| GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} | ||
| GITLEAKS_ENABLE_UPLOAD_ARTIFACT: false | ||
| GITLEAKS_NOTIFY_USER_LIST: '' | ||
|
|
||
| trufflehog: | ||
| name: TruffleHog Verified | ||
| runs-on: ubuntu-latest | ||
| steps: | ||
| - name: Checkout | ||
| uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 | ||
| with: | ||
| fetch-depth: 0 | ||
| persist-credentials: false | ||
|
|
||
| - name: Run TruffleHog verified full-history scan | ||
| run: | | ||
| docker run --rm \ | ||
| -v "$PWD:/repo:ro" \ | ||
| ghcr.io/trufflesecurity/trufflehog:3.95.7 \ | ||
| git file:///repo \ | ||
| --only-verified \ | ||
| --no-update \ | ||
| --fail | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,34 @@ | ||
| title = "AionUi public repository Gitleaks configuration" | ||
|
|
||
| [extend] | ||
| useDefault = true | ||
|
|
||
| [[allowlists]] | ||
| description = "Fake short OpenAI protocol detector fixture" | ||
| condition = "AND" | ||
| paths = ['''^tests/unit/common/protocolDetector\.test\.ts$'''] | ||
| regexes = ['''sk-abc123def456ghi789'''] | ||
|
|
||
| [[allowlists]] | ||
| description = "Fake long OpenAI protocol detector fixture" | ||
| condition = "AND" | ||
| paths = ['''^tests/unit/common/protocolDetector\.test\.ts$'''] | ||
| regexes = ['''sk-abc123def456ghi789jkl012'''] | ||
|
|
||
| [[allowlists]] | ||
| description = "Fake Google API key protocol detector fixture" | ||
| condition = "AND" | ||
| paths = ['''^tests/unit/common/protocolDetector\.test\.ts$'''] | ||
| regexes = ['''AIzaa{35}'''] | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. P1: Gitleaks allowlist regex AIzaa{35} over-matches; will not match the 35-a fixture and may leak/err In the 'Fake Google API key protocol detector fixture' allowlist, Why this matters: A misconfigured allowlist either breaks the new required CI gate (Gitleaks Full History) with false positives on a known fixture, or silently disables coverage so a real Google key could pass review. |
||
|
|
||
| [[allowlists]] | ||
| description = "Fake bridge resource token fixture" | ||
| condition = "AND" | ||
| paths = ['''^tests/unit/bootstrap/prepareEvaosDesktopBridgeResource\.test\.ts$'''] | ||
| regexes = ['''super-secret-token'''] | ||
|
|
||
| [[allowlists]] | ||
| description = "Fake bridge resource credential URL fixture" | ||
| condition = "AND" | ||
| paths = ['''^tests/unit/bootstrap/prepareEvaosDesktopBridgeResource\.test\.ts$'''] | ||
| regexes = ['''https://x-access-token:super-secret-token@github\.com/electricsheephq/evaos-desktop-bridge\.git'''] | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -13,6 +13,8 @@ const fs = require('fs'); | |
| const path = require('path'); | ||
| const { execSync } = require('child_process'); | ||
|
|
||
| const projectRoot = path.join(__dirname, '..'); | ||
|
|
||
| // Parse command line arguments | ||
| const args = process.argv.slice(2); | ||
| const profileIndex = args.indexOf('--profile'); | ||
|
|
@@ -28,6 +30,31 @@ if (!profile) { | |
| process.exit(1); | ||
| } | ||
|
|
||
| function requireEnv(name, purpose) { | ||
| const value = process.env[name]; | ||
| if (!value) { | ||
| console.error(`Error: ${name} is required for ${purpose}.`); | ||
| process.exit(1); | ||
| } | ||
| return value; | ||
| } | ||
|
|
||
| const expoAppleId = process.env.EXPO_APPLE_ID || process.env.APPLE_ID || process.env.appleId; | ||
| const expoAppleTeamId = process.env.EXPO_APPLE_TEAM_ID || process.env.TEAM_ID || process.env.teamId; | ||
|
|
||
| if (!isLocal && directSubmit) { | ||
| console.error('Error: --direct-submit is only supported with --local builds.'); | ||
| process.exit(1); | ||
| } | ||
|
|
||
| if (platform === 'ios' && (autoSubmit || directSubmit) && !expoAppleId) { | ||
| requireEnv('EXPO_APPLE_ID', 'iOS submission'); | ||
| } | ||
|
|
||
| if (platform === 'ios' && autoSubmit && !expoAppleTeamId) { | ||
| requireEnv('EXPO_APPLE_TEAM_ID', 'EAS iOS submission'); | ||
| } | ||
|
|
||
| // Read current version | ||
| const versionPath = path.join(__dirname, '..', 'versions', 'version.json'); | ||
| let versionData; | ||
|
|
@@ -53,9 +80,13 @@ try { | |
|
|
||
| // Build eas command args | ||
| const outputExt = platform === 'ios' ? '.ipa' : '.apk'; | ||
| const localOutputPath = path.join(__dirname, '..', `build-${Date.now()}${outputExt}`); | ||
| const localOutputPath = path.join(projectRoot, `build-${Date.now()}${outputExt}`); | ||
| let buildArgs = args.filter((a) => a !== '--auto-submit' && a !== '--direct-submit'); | ||
|
|
||
| if (!isLocal && autoSubmit && !buildArgs.includes('--auto-submit-with-profile')) { | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. P3: Non-local auto-submit rewrites --auto-submit to --auto-submit-with-profile but eas submit profiles no longer carry Apple credentials For cloud ( Why this matters: The implicit contract between eas.json (credentials removed) and build.js (env vars now mandatory) is easy to break in a future edit; a comment prevents regression. |
||
| buildArgs.push('--auto-submit-with-profile', profile); | ||
| } | ||
|
|
||
| // For local builds with submit, capture output path for later submission | ||
| if (isLocal && (autoSubmit || directSubmit)) { | ||
| if (!buildArgs.includes('--output')) { | ||
|
|
@@ -83,21 +114,31 @@ if (isLocal && platform === 'ios') { | |
| // Build the eas command | ||
| const easCommand = `eas build ${buildArgs.join(' ')}`; | ||
| console.log(`\nRunning: ${easCommand}\n`); | ||
|
|
||
| // Apple-specific env vars (only needed for iOS builds) | ||
| const appleEnv = | ||
| platform === 'ios' | ||
| ? { | ||
| EXPO_APPLE_TEAM_ID: process.env.EXPO_APPLE_TEAM_ID || 'M4AG47ZV62', | ||
| EXPO_APPLE_ID: process.env.EXPO_APPLE_ID || 'liangzhewei@gmail.com', | ||
| ...(applePassword ? { EXPO_APPLE_PASSWORD: applePassword } : {}), | ||
| } | ||
| : {}; | ||
| const appleEnv = {}; | ||
| if (platform === 'ios') { | ||
| if (expoAppleTeamId) { | ||
| appleEnv.EXPO_APPLE_TEAM_ID = expoAppleTeamId; | ||
| } | ||
| if (expoAppleId) { | ||
| appleEnv.EXPO_APPLE_ID = expoAppleId; | ||
| } | ||
| if (applePassword) { | ||
| appleEnv.EXPO_APPLE_PASSWORD = applePassword; | ||
| } | ||
| if (autoSubmit || directSubmit) { | ||
| appleEnv.EXPO_APPLE_ID = expoAppleId || requireEnv('EXPO_APPLE_ID', 'iOS submission'); | ||
| } | ||
| if (autoSubmit) { | ||
| appleEnv.EXPO_APPLE_TEAM_ID = | ||
| expoAppleTeamId || requireEnv('EXPO_APPLE_TEAM_ID', 'EAS iOS submission'); | ||
|
100yenadmin marked this conversation as resolved.
|
||
| } | ||
| } | ||
|
|
||
| // Execute eas build | ||
| try { | ||
| execSync(easCommand, { | ||
| stdio: 'inherit', | ||
| cwd: projectRoot, | ||
| env: { | ||
| ...process.env, | ||
| PATH: `/usr/bin:${process.env.PATH}`, | ||
|
|
@@ -123,7 +164,7 @@ if (platform === 'ios' && isLocal && (autoSubmit || directSubmit)) { | |
|
|
||
| if (directSubmit) { | ||
| // Upload directly to App Store Connect via xcrun altool (bypasses EAS) | ||
| const appleId = process.env.APPLE_ID || 'liangzhewei@gmail.com'; | ||
| const appleId = expoAppleId || requireEnv('EXPO_APPLE_ID', 'direct iOS submission'); | ||
| const submitCommand = `xcrun altool --upload-app -f "${outputFile}" -t ${platform} -u "${appleId}" -p "@keychain:AC_PASSWORD"`; | ||
| console.log(`\nUploading directly to TestFlight: xcrun altool --upload-app\n`); | ||
| try { | ||
|
|
@@ -135,17 +176,18 @@ if (platform === 'ios' && isLocal && (autoSubmit || directSubmit)) { | |
| ' Make sure your App-Specific Password is saved in Keychain as "AC_PASSWORD".', | ||
| ); | ||
| console.error( | ||
| ' To save it: security add-generic-password -a "liangzhewei@gmail.com" -s "AC_PASSWORD" -w "<your-app-specific-password>" -U', | ||
| ' To save it: security add-generic-password -a "$EXPO_APPLE_ID" -s "AC_PASSWORD" -w "<your-app-specific-password>" -U', | ||
| ); | ||
| process.exit(1); | ||
| } | ||
| } else { | ||
| // Upload via EAS submit | ||
| const submitCommand = `eas submit --platform ${platform} --path ${outputFile} --non-interactive`; | ||
| const submitCommand = `eas submit --platform ${platform} --profile ${profile} --path ${outputFile} --non-interactive`; | ||
| console.log(`\nSubmitting to TestFlight: ${submitCommand}\n`); | ||
| try { | ||
| execSync(submitCommand, { | ||
| stdio: 'inherit', | ||
| cwd: projectRoot, | ||
| env: { | ||
| ...process.env, | ||
| ...appleEnv, | ||
|
|
||
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.
In the thin-app smoke workflow, the build step pins
EVAOS_DESKTOP_BRIDGE_SOURCE_REFto a specific commit, but this verification only checks that the manifest'srequestedSourceRefandsourceCommitagree with each other. If the packaging code stops honoring the workflow pin and packages a different Bridge commit while writing matching manifest fields, this new acceptance path still passes; comparesourceCommitagainst the pinned workflow ref instead of trusting the manifest's requested ref.Useful? React with 👍 / 👎.