restartApp method
Hands the staged update to the native installer or restart helper.
Implementation
Future<void> restartApp() async {
final stagingPath = _stagingPath;
final stageResult = _activeStageResult;
final provenance = _stageProvenance;
final provenanceSha256 = _stageProvenanceSha256;
final client = _client;
if (stagingPath == null ||
stagingPath.isEmpty ||
stageResult == null ||
provenance == null ||
provenanceSha256 == null ||
client == null) {
throw StateError("No downloaded update is ready to install.");
}
_state = const UpdateInstalling();
_diagnosticsRecorder.record(
stage: UpdateDiagnosticStage.install,
level: UpdateDiagnosticLevel.info,
message: "Install handoff started for $stagingPath",
);
_diagnosticsRecorder.record(
stage: UpdateDiagnosticStage.install,
level: UpdateDiagnosticLevel.info,
message: "Relaunch attempt scheduled.",
);
emitUpdateTelemetry(
telemetry,
UpdateTelemetryEvent.installScheduled(
stagingPath: stagingPath,
version: _activeDescriptor?.version,
channel: _activeDescriptor?.channel,
platform: _activeDescriptor?.platform,
artifactKind: _activeDescriptor?.artifact.kind,
installStrategy: _activeDescriptor?.install.strategy,
),
);
notifyListeners();
var dispatchAttempted = false;
try {
_validateNativeInstallTrust();
final candidateTransactionId = _createInstallTransactionId();
final receipt = await _writePendingRecoveryMarker(
stagingPath,
candidateTransactionId,
);
// Once the durable receipt exists, every failure from the dispatch
// boundary is ambiguous to the app. Keep the marker until authenticated
// recovery proves absence or terminal completion.
dispatchAttempted = true;
await dispatchVerifiedInstall(
session: client,
stageResult: stageResult,
persistedTransaction: receipt,
);
final cleanupReport = _buildCleanupReport(
stagingPath: stagingPath,
cleanupAttempted: false,
);
_recordCleanupReport(cleanupReport);
_state = UpdateInstalling(cleanupReport: cleanupReport);
notifyListeners();
} on Object catch (error) {
if (!dispatchAttempted) {
await _clearPendingRecoveryMarker();
}
_recordCleanupReport(
_buildCleanupReport(
stagingPath: stagingPath,
cleanupAttempted: false,
cleanupSucceeded: false,
errorText: error.toString(),
),
);
_diagnosticsRecorder.record(
stage: UpdateDiagnosticStage.install,
level: UpdateDiagnosticLevel.error,
message: "Install failed.",
error: error,
);
_state = UpdateFailed(
error,
report: _buildProblemReport(
error,
updateVersion: _activeDescriptor?.version,
stagingPath: stagingPath,
),
);
emitUpdateTelemetry(
telemetry,
UpdateTelemetryEvent.installFailed(
stagingPath: stagingPath,
version: _activeDescriptor?.version,
channel: _activeDescriptor?.channel,
platform: _activeDescriptor?.platform,
artifactKind: _activeDescriptor?.artifact.kind,
installStrategy: _activeDescriptor?.install.strategy,
error: error,
),
);
notifyListeners();
rethrow;
}
}