View Capture Service
Overview
The ViewCaptureService
is in charge of automatically instrumenting UIViewController
load and render times.
You can customize the service behavior by passing a custom ViewCaptureService
when setting up the Embrace SDK:
let services = CaptureServiceBuilder()
.add(.view(options: ViewCaptureService.Options(instrumentVisibility: true, instrumentFirstRender: true)))
.addDefaults()
.build()
try Embrace
.setup(
options: Embrace.Options(
appId: "APPID",
captureServices: services
//...other options
)
)
.start()
Screen visibility
This feature is enabled by setting instrumentVisibility
to true
in the ViewCaptureService.Options
.
The service will generate spans that start when a UIViewController
appears (viewDidAppear
) and ends when it disappears (viewDidDisappear
).
Time to First Render
This feature is enabled by setting instrumentFirstRender
to true
in the ViewCaptureService.Options
.
The service will generate spans that start when a UIViewController
is loaded (viewDidLoad
) and ends when it becomes visible for the first time (viewDidAppear
).
The service will also generate child spans measuring several steps in the process: viewDidLoad
, viewWillAppear
and viewDidAppear
.
If the UIViewController
disappears before it finishes loading, the spans status will be set to .error
with the .userAbandon
code.
Time to Interactive
This feature is enabled by setting instrumentFirstRender
to true
in the ViewCaptureService.Options
, and making a UIViewController
implement the InteractableViewController
protocol.
The service will generate spans that start when a UIViewController
is loaded (viewDidLoad
) and ends when it is flagged as ready for interaction (setInteractionReady()
).
If you implement this protocol in one of your UIViewControllers
, you need to call setInteractionReady()
when the screen is ready to be interacted by the user.
Example:
class MyViewController: UIViewController, InteractableViewController {
override func viewDidLoad() {
super.viewDidLoad()
// some async operation
MyDataFetcher.fetch { [weak self] data in
self?.loadData(data)
self?.setInteractionReady()
}
}
}
If the UIViewController
disappears before it is flagged as ready for interaction, the spans status will be set to .error
with the .userAbandon
code.
Custom child spans
When the first render instrumentation is enabled, you can also add custom child spans to the ones automatically generated by the service.
You'll need to implement the InstrumentableViewController
protocol and use the buildChildSpan
or recordCompletedChildSpan
methods
Example:
class MyViewController: UIViewController, InstrumentableViewController {
override func viewDidLoad() {
super.viewDidLoad()
let childSpan = buildChildSpan(name: "data-fetch").startSpan()
// some async operation
MyDataFetcher.fetch { [weak self] data in
self?.loadData(data)
childSpan.end()
}
}
}