Skip to content

✨ Align Ruby and Swift SDKs#286

Merged
Robdel12 merged 3 commits into
mainfrom
rd/sdk-ruby-swift
May 31, 2026
Merged

✨ Align Ruby and Swift SDKs#286
Robdel12 merged 3 commits into
mainfrom
rd/sdk-ruby-swift

Conversation

@Robdel12
Copy link
Copy Markdown
Contributor

@Robdel12 Robdel12 commented May 31, 2026

Why

This PR aligns the Ruby and Swift SDKs with the contract established by the core, web, Vitest, and Ember slices.

These SDKs are especially important because users do not see the main JavaScript implementation details. They just call Vizzly.screenshot(...), client.screenshot(...), or app.vizzlyScreenshot(...) and expect the same build grouping, metadata, request timeout, comparison, and diff-failure behavior they get elsewhere.

Before this pass, Ruby and Swift were close but not fully aligned. Build IDs and request timeouts could be treated like metadata. failOnDiff was not consistently available. Swift XCTest helpers duplicated metadata construction across overloads. Ruby accepted flexible option shapes, but the behavior was not crisp enough about what was a real SDK option versus user metadata.

The goal is parity without overbuilding: one conceptual contract, expressed idiomatically in Ruby and Swift.

What changed

Ruby SDK

  • Adds fail_on_diff: and honors VIZZLY_FAIL_ON_DIFF plus discovered .vizzly/server.json settings.
  • Honors VIZZLY_ENABLED=false and reports disabled/ready state consistently.
  • Accepts snake_case options and JS-style camelCase aliases where useful: min_cluster_size/minClusterSize, full_page/fullPage, build_id/buildId, and request_timeout/requestTimeout.
  • Sends buildId as a request field, not screenshot metadata.
  • Applies request_timeout to the HTTP read timeout in milliseconds.
  • Treats properties as the user metadata bag.
  • Strips reserved/config options from properties, promotes them to the correct behavior when no top-level value exists, and emits a warning.
  • Raises on both current 200-style and older 422-style TDD diff responses when fail-on-diff is enabled.
  • Exposes both snake_case and camelCase info fields where that helps Ruby users and cross-SDK tooling.

Swift SDK

  • Adds optional failOnDiff override and honors VIZZLY_FAIL_ON_DIFF plus discovered server config.
  • Adds optional fullPage, buildId, and requestTimeout.
  • Converts millisecond request timeout into URLRequest.timeoutInterval.
  • Sends buildId outside properties.
  • Preserves fullPage: false as an intentional value.
  • Includes a stable properties object in payloads.
  • Handles both current and legacy TDD diff response shapes.

Swift XCTest helpers

  • Centralizes XCTest metadata construction in VizzlyXCTestMetadata.
  • Adds app/test/element metadata through one merge path.
  • Includes platform/device/OS/viewport metadata for app screenshots.
  • Includes platform metadata and element type for element screenshots.
  • Keeps user-provided properties as the intentional override layer.
  • Forwards buildId and requestTimeout through helper overloads.

Docs and package surface

  • Ruby README examples now show the screenshot-level options where they are actually accepted.
  • Swift README and integration docs describe the current API signatures and current vizzly run "..." command style.
  • Swift package metadata now covers both the client and XCTest helper tests.

Testing

  • Ruby tests cover disabled state, info shape, env/server-config fail-on-diff, current and legacy diff responses, fractional thresholds, nested viewport metadata, aliases, zero values, build ID routing, timeout conversion, and reserved properties warnings.
  • Swift tests cover info/fail state, payload shape, explicit false full-page behavior, build ID routing, nested viewport metadata, default comparison behavior, and XCTest metadata merging.

The Ruby follow-up for the properties contract was re-run after the stack split. The broader real visual-diff E2E matrix is still intentionally left for a focused follow-up so this already-large SDK slice stays reviewable.

Verification

  • Ruby preservation-branch verification: 20 tests / 55 assertions.
  • Ruby post-split verification after properties warning work: bundle exec rake test in clients/ruby: 21 runs, 64 assertions, 0 failures.
  • Swift preservation-branch verification: swift test --filter VizzlyClientTests: 17 passed.
  • Covered by the full preservation branch verification before the stack was split.
  • Stack cleanup verification: git diff --check and PR file-list checks for ✨ Align core SDK option contracts #283 through 📝 Document aligned SDK workflows #287.

@Robdel12 Robdel12 force-pushed the rd/sdk-vitest-ember branch from 9deaf1d to 7771992 Compare May 31, 2026 17:29
@Robdel12 Robdel12 force-pushed the rd/sdk-ruby-swift branch from 90d00ed to 70832ad Compare May 31, 2026 17:29
@Robdel12 Robdel12 force-pushed the rd/sdk-vitest-ember branch from 7771992 to 47dde46 Compare May 31, 2026 18:25
@Robdel12 Robdel12 force-pushed the rd/sdk-ruby-swift branch from 70832ad to af326b3 Compare May 31, 2026 18:25
@Robdel12 Robdel12 force-pushed the rd/sdk-vitest-ember branch from 47dde46 to 3d543fa Compare May 31, 2026 19:00
@Robdel12 Robdel12 force-pushed the rd/sdk-ruby-swift branch from 1febcd4 to 4f031ba Compare May 31, 2026 19:01
@Robdel12 Robdel12 changed the base branch from rd/sdk-vitest-ember to main May 31, 2026 19:03
@Robdel12 Robdel12 force-pushed the rd/sdk-ruby-swift branch from 4f031ba to 9eb6b78 Compare May 31, 2026 19:55
@vizzly-testing

This comment has been minimized.

@Robdel12 Robdel12 force-pushed the rd/sdk-ruby-swift branch from 9eb6b78 to 0e56874 Compare May 31, 2026 20:37
@vizzly-testing

This comment has been minimized.

@Robdel12 Robdel12 marked this pull request as ready for review May 31, 2026 20:40
Keep the Ruby option-alignment behavior unchanged while satisfying the SDK unit workflow's RuboCop checks across the Ruby matrix.
@vizzly-testing
Copy link
Copy Markdown

Vizzly - Visual Test Results

CLI Reporter - Waiting for build

No builds received yet for this pull request.

CLI TUI - Approved

5 comparisons, no changes detected.

View build


rd/sdk-ruby-swift · c6adb798

@Robdel12 Robdel12 merged commit 68661c7 into main May 31, 2026
33 checks passed
@Robdel12 Robdel12 deleted the rd/sdk-ruby-swift branch May 31, 2026 20:44
Robdel12 added a commit that referenced this pull request May 31, 2026
## Why

This PR is the docs polish slice for the SDK alignment stack. The code
PRs make the option contract real; this one makes sure the public docs
describe the product users actually get.

The docs had fallen behind in a few important ways. They did not clearly
show the current cloud setup flow. JSON output examples were stale.
Browser flag docs did not include Ember. Some command examples still
used older names or older payload shapes. And, most importantly after
the latest cleanup, the screenshot options docs did not clearly separate
user metadata from SDK/config options.

That separation matters. `properties` is the user key/value metadata
bag. Options like `threshold`, `minClusterSize`, `fullPage`, `buildId`,
and `requestTimeout` are behavior/request options and should stay
top-level. If docs blur that line, users copy the wrong shape and the
SDK has to guess what they meant.

## What changed

### README

- Adds split agent-init flags so users can install only the agent skill
or skip it when they only want config.
- Clarifies the cloud path: `vizzly login`, `vizzly project link`, then
`vizzly run "..." --wait`.
- Updates the JS client screenshot example to show structured viewport
metadata, `fullPage`, and `requestTimeout`.
- Clarifies that `properties` is user metadata.
- Clarifies that SDK/config options stay top-level and that
transport/request fields like `requestTimeout` and `buildId` are not
stored as screenshot metadata.
- Expands upload examples with `--threshold`, `--min-cluster-size`,
`--batch-size`, `--upload-timeout`, `--upload-all`, `--parallel-id`, and
`--allow-no-token`.

### JSON output reference

- Reworks command examples to show the standard `{ status, data }`
wrapper.
- Updates `run`, `run --wait`, TDD commands, builds, comparisons,
config, baselines, API, upload, preview, status, init, and project
examples to match current payload shapes.
- Clarifies that field selection applies before the standard output
envelope is wrapped.
- Updates project command docs from stale `project:*` examples to
current `project link` and `projects` flows.
- Adds current preview fields such as new bytes, reused blob count,
dedupe ratio, and base path.

### Browser flags

- Documents that Ember uses the same sandbox and CI-stability subset as
the browser-based SDKs.
- Adds the Ember launcher path to the source list reviewers should check
when browser flags change.
- Clarifies why Ember uses a smaller subset because Testem owns the rest
of the browser lifecycle.

## Testing and confidence

This is docs-only, so the useful verification is consistency against the
code PRs and diff hygiene. The docs now say the same thing the core/Ruby
changes enforce: user metadata belongs in `properties`; options that
change behavior stay top-level.

The remaining testing gap is not in this docs PR but in the broader
product stack: we still want a focused follow-up with real E2E
visual-diff tests that exercise the CLI/API/dashboard path with an
intentionally changed fixture.

## Review guide

1. Start with `README.md` and check the screenshot/options examples
against #283 and #286.
2. Review `docs/json-output.md` against the JSON output work in #283.
3. Check `docs/browser-flags.md` against the Storybook/static-site/Ember
browser launchers from the SDK PRs.

## Verification

- Docs-only slice.
- `git diff --check` passed after stack cleanup.
- Final stacked branch differs from the original preservation branch
only by intentional docs/code split changes and the removed custom
plugin example.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant