Skip to content

feat(you): the You tab is your own profile #682

feat(you): the You tab is your own profile

feat(you): the You tab is your own profile #682

Workflow file for this run

name: Cross-platform vector gate
# Asserts this repo reproduces the canonical fixtures in the orchestrator's
# `code/test-vectors/` — the same fixtures code-android-app asserts against. The
# two apps compute keys, signatures, and on-chain amounts in parallel Swift and
# Kotlin implementations; these vectors are what keeps the answers identical.
#
# Two packages because they cannot share a deployment target: FlipcashCore's
# transitive deps (BigDecimal, grpc/nio) pull a macOS floor that CrossPlatformVectors
# does not want. Both run on a simulator — the ed25519 under test moved from a
# host-buildable C package to the shared Kotlin XCFramework, which ships iOS only.
on:
pull_request:
branches: [main]
push:
branches: [main]
concurrency:
group: vectors-${{ github.head_ref || github.ref }}
cancel-in-progress: true
jobs:
vectors:
name: Vectors
runs-on: macos-15
# The app build and its 1664 tests took 22 of the previous 30 on a quiet
# run, which leaves nothing for a slow runner.
timeout-minutes: 45
steps:
- uses: actions/checkout@v4
# FlipcashCore is swift-tools 6.1, which the image's default Xcode may
# predate. Take the newest installed rather than pinning a version that
# can drop out of the runner image.
- name: Select the newest installed Xcode
run: |
set -euo pipefail
XCODE=$(ls -d /Applications/Xcode_*.app 2>/dev/null | sort -V | tail -1 || true)
if [ -n "$XCODE" ]; then
sudo xcode-select -s "$XCODE"
fi
xcodebuild -version
# Simulator model names turn over with each runner image, so pick whatever
# iPhone is installed rather than naming one.
- name: Pick a simulator
id: sim
run: |
set -euo pipefail
UDID=$(xcrun simctl list devices available -j | python3 -c "import json,sys; d=json.load(sys.stdin)['devices']; print(next(x['udid'] for r in sorted(d, reverse=True) for x in d[r] if x['name'].startswith('iPhone')))")
echo "udid=$UDID" >> "$GITHUB_OUTPUT"
- name: Ed25519 vectors
working-directory: CrossPlatformVectors
run: |
xcodebuild test -scheme CrossPlatformVectors-Package \
-destination "platform=iOS Simulator,id=${{ steps.sim.outputs.udid }}" \
-quiet
- name: FlipcashCore vectors
working-directory: FlipcashCoreVectors
run: |
xcodebuild test -scheme FlipcashCoreVectors-Package \
-destination "platform=iOS Simulator,id=${{ steps.sim.outputs.udid }}" \
-quiet
# The app target's own vector suites -- chat drafts, link detection, and chat media -- assert against types
# only the app has, so they cannot move into either package above. Heavier than the two
# package schemes because it builds the app.
# Split so the two failure classes are separable and each stays legible:
# the build runs -quiet (unquieted it prints every compile command, which
# on its own pushed this job past its timeout), while the test runs do
# not, because -quiet there reduces a failure to "Test case ... failed"
# with no assertion text to act on.
- name: App vectors (build)
run: |
xcodebuild build-for-testing -scheme Flipcash \
-destination "platform=iOS Simulator,id=${{ steps.sim.outputs.udid }}" \
-only-testing:FlipcashTests \
-quiet
# Two runs of the one built target, because they answer different questions.
#
# This is the gate: the suites that read the synced copies of `chat_draft.json`,
# `link_detection.json`, and `chat_media.json`. Those fixtures are canonical and
# code-android-app asserts against the same ones, so a failure here is contract
# drift between the platforms -- exactly what this job exists to stop.
- name: App vectors
run: |
xcodebuild test-without-building -scheme Flipcash \
-destination "platform=iOS Simulator,id=${{ steps.sim.outputs.udid }}" \
-only-testing:FlipcashTests/ChatDraftVectorTests \
-only-testing:FlipcashTests/LinkCardClassifierTests \
-only-testing:FlipcashTests/ChatMediaFanOutVectorTests \
-only-testing:FlipcashTests/ChatMediaBubbleVectorTests \
-only-testing:FlipcashTests/ChatMediaStringVectorTests \
-resultBundlePath "${{ runner.temp }}/AppVectors.xcresult"
# The rest of the target reports but does not gate. It holds timing-sensitive
# suites -- typing coalescence, the stress suites, the debounce tests -- that are
# marginal on a shared runner: of eight runs before this split, five failed on one
# of them and it was a different one almost every time. None of them can show
# cross-platform drift, so blocking on them stopped merges without protecting the
# contract. Read the result bundle when this step is red; it is real signal, just
# not a reason to hold a PR.
- name: App suite (advisory)
id: app_suite
continue-on-error: true
run: |
xcodebuild test-without-building -scheme Flipcash \
-destination "platform=iOS Simulator,id=${{ steps.sim.outputs.udid }}" \
-only-testing:FlipcashTests \
-resultBundlePath "${{ runner.temp }}/AppSuite.xcresult"
# Swift Testing's Issue.record messages reach the result bundle and nowhere else, so a
# failure otherwise has to be reconstructed from "Test case ... failed" lines. Four
# GalleryScannerTests failures were triaged that way and one stayed unexplained.
# Uploaded for the advisory step too, which by design leaves the job green.
- name: App result bundles
if: failure() || steps.app_suite.outcome == 'failure'
uses: actions/upload-artifact@v4
with:
name: app-vectors-xcresult
path: |
${{ runner.temp }}/AppVectors.xcresult
${{ runner.temp }}/AppSuite.xcresult
if-no-files-found: ignore
retention-days: 7