oficina / memoria Public

Verify native note forms and record release review

Co-Authored-By: Codex <codex~paul@keymail.dev>
codex agent, operated by paul@keymail.dev 439e5c70d55abd1554262de214f2294a6c25d8d0 parent d72e5bd
5 files changed, +66 −0
  • internal/memoria/native_test.go +10 −0
  • native/README.md +8 −0
  • native/REVIEW.md +11 −0
  • native/ios/UITests/NativeUITests.swift +19 −0
  • native/ios/project.yml +18 −0
diff --git a/internal/memoria/native_test.go b/internal/memoria/native_test.go
index 66f64bb..2a0a628 100644
--- a/internal/memoria/native_test.go
+++ b/internal/memoria/native_test.go
@@ -87,6 +87,16 @@ func TestNativeSearchUsesCurrentPermission(t *testing.T) {
t.Fatal(err)
}
defer os.Remove(path)
+
+ if os.Getenv("NATIVE_REVIEW_UI_TESTS") != "" {
+ command := exec.CommandContext(t.Context(), "xcodebuild", "-project", "native/ios/MemoriaPhone.xcodeproj", "-scheme", "MemoriaReviewPhone", "-destination", "platform=iOS Simulator,id="+simulator, "-parallel-testing-enabled", "NO", "-derivedDataPath", "native/build/ios", "CODE_SIGNING_ALLOWED=NO", "test")
+ command.Dir = "../.."
+ output, err := command.CombinedOutput()
+ _ = os.WriteFile(filepath.Join(os.TempDir(), "memoria-native-ui-tests.log"), output, 0600)
+ if err != nil {
+ t.Fatal("Native UI tests failed; see temporary xcodebuild log", err)
+ }
+ }
run("launch", simulator, bundle)
time.Sleep(3 * time.Second)
run("io", simulator, "screenshot", os.Getenv("NATIVE_REVIEW_OUTPUT"))
diff --git a/native/README.md b/native/README.md
index 5046d4b..5a02551 100644
--- a/native/README.md
+++ b/native/README.md
@@ -25,3 +25,11 @@ credential over stdin, renders the real workspace and captures its window.
Set NATIVE_REVIEW_BINARY and NATIVE_REVIEW_OUTPUT when running `go test
./internal/memoria -run TestNative` to exercise it against the app's real test
server. It is never included in the Mac or iOS app bundle.
+
+For XCTest interaction checks against the isolated authenticated fixture, set
+`NATIVE_REVIEW_SIMULATOR=<UDID> NATIVE_REVIEW_UI_TESTS=1` with a writable
+`NATIVE_REVIEW_OUTPUT` PNG path when running the native Go fixture test. First
+build/install the separate ReviewPhone target. The UI tests create and inspect
+fixture notes and never connect to a real account. Xcode result bundles
+are under `native/build/ios/Logs/Test`. Review credentials enter only the isolated
+review app's Documents directory and are removed when the fixture exits.
diff --git a/native/REVIEW.md b/native/REVIEW.md
index d2408c1..4b1b64c 100644
--- a/native/REVIEW.md
+++ b/native/REVIEW.md
@@ -17,3 +17,14 @@ Mac and iPhone/iPad screens were rendered from the actual Swift clients against
an authenticated Go fixture. Native approval/exchange creates the fixture client
credential. Memoria's available Apple Foundation Model generated a response on
this Mac. Calendar's three Swift civil-date tests and both Go CI suites pass.
+
+Final merge `d72e5bd` reviewed against both parents (5899232 and aab25c0) by
+`/root/canary_release_review`, dispatched as `gpt-6-astra` with high reasoning.
+Runtime model identity was not independently verified. Code and deployed canary
+review approved, with no remaining findings. Direct `/api/version` and the router
+reported the exact reviewed version. Native pending exchanges returned 202 without
+credentials; incorrect proofs returned 404, cross-origin requests 403, anonymous
+approval was refused, and failed approval left the request pending. No email or
+user-data mutation was performed. Existing credits access and branding remained
+intact. The final Go CI passed, and XCTest exercised native form and navigation
+against an isolated authenticated fixture.
diff --git a/native/ios/UITests/NativeUITests.swift b/native/ios/UITests/NativeUITests.swift
new file mode 100644
index 0000000..5dafcf1
--- /dev/null
+++ b/native/ios/UITests/NativeUITests.swift
@@ -0,0 +1,19 @@
+import XCTest
+@MainActor final class NativeUITests: XCTestCase {
+ func testNativeFormAndNavigation() {
+ let app=XCUIApplication();app.launch()
+ XCTAssertTrue(app.buttons["Add note"].waitForExistence(timeout: 10))
+
+ app.buttons["Add note"].tap()
+ let title=app.textFields["Title"]
+ XCTAssertTrue(title.waitForExistence(timeout: 5)); title.tap(); title.typeText("Native UI note")
+ let body=app.textViews.firstMatch;body.tap();body.typeText("A new note created through the native iPhone form.")
+ app.buttons["Save"].tap()
+ XCTAssertTrue(app.staticTexts["Native UI note"].firstMatch.waitForExistence(timeout: 10))
+ app.staticTexts["Native UI note"].firstMatch.tap()
+ XCTAssertTrue(app.navigationBars["Source"].waitForExistence(timeout: 5))
+ XCTAssertTrue(app.staticTexts["A new note created through the native iPhone form."].firstMatch.waitForExistence(timeout: 5))
+
+ let capture=XCTAttachment(screenshot: app.screenshot());capture.lifetime = .keepAlways;add(capture)
+ }
+}
diff --git a/native/ios/project.yml b/native/ios/project.yml
index 99f2c87..8f1b26b 100644
--- a/native/ios/project.yml
+++ b/native/ios/project.yml
@@ -54,3 +54,21 @@ targets:
TARGETED_DEVICE_FAMILY: '1,2'
GENERATE_INFOPLIST_FILE: YES
INFOPLIST_KEY_UILaunchScreen_Generation: YES
+
+ MemoriaPhoneUITests:
+ type: bundle.ui-testing
+ platform: iOS
+ sources: [UITests]
+ dependencies:
+ - target: MemoriaReviewPhone
+ settings:
+ base:
+ GENERATE_INFOPLIST_FILE: YES
+ TEST_TARGET_NAME: MemoriaReviewPhone
+schemes:
+ MemoriaReviewPhone:
+ build:
+ targets:
+ MemoriaReviewPhone: all
+ test:
+ targets: [MemoriaPhoneUITests]