Documentation Index
Fetch the complete documentation index at: https://docs.go.gbgplc.com/llms.txt
Use this file to discover all available pages before exploring further.
A minimal integration that loads a web-based identity journey inside a native iOS app. This example compiles and runs as a standalone SwiftUI app.
What This Example Demonstrates
- Initializing a
BridgeHost with typed capability slots
- Declaring document capture support via handler assignment
- Displaying a journey using
BridgeWebView
- Observing bridge errors
Complete Source
import GBGBridge
import SwiftUI
// MARK: - App Entry Point
@main
struct HelloJourneyApp: App {
var body: some Scene {
WindowGroup {
JourneyView()
}
}
}
// MARK: - Journey View
struct JourneyView: View {
// 1. Create the bridge host
@StateObject private var host = BridgeHost(hostVersion: "1.0.0")
// 2. Set the journey URL
private let journeyURL = URL(string: "https://journey.example.com")!
var body: some View {
NavigationStack {
VStack(spacing: 0) {
// 3. Embed the bridge-connected WebView
BridgeWebView(url: journeyURL, host: host)
// 4. Show errors if any
if let error = host.lastError {
ErrorBanner(message: error) {
host.clearError()
}
}
}
.navigationTitle("Identity Verification")
.navigationBarTitleDisplayMode(.inline)
.onAppear {
// 5. Declare document capture support by setting a handler
host.documentCapture.handler = { [weak host] request in
guard let host else { return .cancelled(reason: "Host deallocated") }
return await host.documentCapture.awaitCompletion()
}
// 6. Detect and report camera permission state
let camera = CameraDetector.check()
host.documentCapture.permissionState = camera.permissionState
}
}
}
}
// MARK: - Error Banner
struct ErrorBanner: View {
let message: String
let onDismiss: () -> Void
var body: some View {
HStack {
Image(systemName: "exclamationmark.triangle.fill")
.foregroundColor(.white)
Text(message)
.font(.caption)
.foregroundColor(.white)
.lineLimit(2)
Spacer()
Button(action: onDismiss) {
Image(systemName: "xmark.circle.fill")
.foregroundColor(.white.opacity(0.7))
}
}
.padding(.horizontal)
.padding(.vertical, 8)
.background(Color.red)
}
}
How It Works
-
BridgeHost(hostVersion:) creates a host with typed capability slots. No separate configuration dictionary is needed.
-
Setting a handler on
documentCapture declares the capability as supported. The handler uses awaitCompletion() to suspend until the UI layer calls complete().
-
CameraDetector.check() detects camera hardware and permission state. The permissionState is included in capability query responses.
-
BridgeWebView creates a WKWebView, injects the bootstrap script, registers the message handler, attaches the WebView to the host, and loads the journey URL.
-
Error observation —
host.lastError is @Published, so the error banner appears and disappears reactively.
What Happens at Runtime
1. App launches -> JourneyView renders
2. BridgeWebView creates and configures WKWebView
3. Bootstrap script injected (window.GBGBridge namespace created)
4. Journey URL loads, handler set on documentCapture slot
5. Web journey sends: capability.query request
6. Built-in handler responds: { environment: "ios", capabilities: { camera.document: { supported: true, permissionState: "granted" } } }
7. Web journey adapts its flow based on available capabilities and permissions
Required Info.plist Entries
For this minimal example, no special Info.plist entries are needed beyond the defaults. If your journey URL uses HTTP during development, add:
<key>NSAppTransportSecurity</key>
<dict>
<key>NSAllowsLocalNetworking</key>
<true/>
</dict>
Next Steps