feat(shorebird_code_push_protocol): patch install/download metric envelope (#3824)
This commit is contained in:
@@ -31,6 +31,7 @@ export 'package:shorebird_code_push_protocol/src/messages/get_organization_apps/
|
||||
export 'package:shorebird_code_push_protocol/src/messages/get_organization_users/get_organization_users_response.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/messages/get_organizations_response.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/messages/get_patch_adoption/get_patch_adoption_response.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/messages/get_patch_metric_response.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/messages/get_release/get_release_response.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/messages/get_release_artifacts/get_release_artifacts_response.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/messages/get_release_patches/get_release_patches_response.dart';
|
||||
@@ -48,7 +49,15 @@ export 'package:shorebird_code_push_protocol/src/models/app.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/app_collaborator_role.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/app_metadata.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/channel.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_app_patch_downloads_parameter2.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_app_patch_downloads_parameter3.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_app_patch_installs_parameter2.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_app_patch_installs_parameter3.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_patch_adoption_parameter3.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_release_patch_downloads_parameter2.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_release_patch_downloads_parameter3.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_release_patch_installs_parameter2.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_release_patch_installs_parameter3.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_unique_users_parameter2.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/get_unique_users_parameter3.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/latest_release.dart';
|
||||
@@ -62,6 +71,10 @@ export 'package:shorebird_code_push_protocol/src/models/patch_adoption_entry.dar
|
||||
export 'package:shorebird_code_push_protocol/src/models/patch_adoption_point.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/patch_artifact.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/patch_check_metadata.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/patch_metric_breakdown_entry.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/patch_metric_current_window.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/patch_metric_time_series_entry.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/patch_metric_window.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/pending_release.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/private_user.dart';
|
||||
export 'package:shorebird_code_push_protocol/src/models/public_user.dart';
|
||||
|
||||
+104
@@ -0,0 +1,104 @@
|
||||
import 'package:meta/meta.dart';
|
||||
import 'package:shorebird_code_push_protocol/model_helpers.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/patch_metric_current_window.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/patch_metric_window.dart';
|
||||
|
||||
/// {@template get_patch_metric_response}
|
||||
/// The response body for the patch-installs and patch-downloads metric
|
||||
/// endpoints (app- and release-scoped): a current/previous envelope.
|
||||
/// `previous` covers the equal-length window immediately preceding
|
||||
/// `current`; period-over-period deltas are client display logic over the
|
||||
/// two totals. `previous` is omitted only when the prior window predates
|
||||
/// the data floor (no comparison data exists). When it reaches past the
|
||||
/// plan's metrics-history horizon, `previous` is still present with its
|
||||
/// total — the delta renders — but without a `time_series` (no
|
||||
/// prior-window overlay): granular history is the resolution the horizon
|
||||
/// gates, the scalar comparison is not.
|
||||
/// {@endtemplate}
|
||||
@immutable
|
||||
class GetPatchMetricResponse {
|
||||
/// {@macro get_patch_metric_response}
|
||||
const GetPatchMetricResponse({
|
||||
required this.asOf,
|
||||
required this.granularity,
|
||||
required this.current,
|
||||
this.previous,
|
||||
});
|
||||
|
||||
/// Converts a `Map<String, dynamic>` to a [GetPatchMetricResponse].
|
||||
factory GetPatchMetricResponse.fromJson(Map<String, dynamic> json) {
|
||||
return parseFromJson(
|
||||
'GetPatchMetricResponse',
|
||||
json,
|
||||
() => GetPatchMetricResponse(
|
||||
asOf: DateTime.parse(json['as_of'] as String),
|
||||
granularity: checkedKey(json, 'granularity') as String?,
|
||||
current: PatchMetricCurrentWindow.fromJson(
|
||||
json['current'] as Map<String, dynamic>,
|
||||
),
|
||||
previous: PatchMetricWindow.maybeFromJson(
|
||||
json['previous'] as Map<String, dynamic>?,
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json object.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetPatchMetricResponse? maybeFromJson(Map<String, dynamic>? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetPatchMetricResponse.fromJson(json);
|
||||
}
|
||||
|
||||
/// Server's UTC timestamp at the moment the response was constructed.
|
||||
/// Not a freshness indicator for the underlying data, which is
|
||||
/// refreshed by an hourly scheduled job and may lag by up to ~1 hour.
|
||||
final DateTime asOf;
|
||||
|
||||
/// The time-series bucket resolution (`hour`, `day`, or `week`), or
|
||||
/// null when no time series was requested. Applies to both windows.
|
||||
final String? granularity;
|
||||
|
||||
/// The `current` window of the patch-metric envelope: the base window atom
|
||||
/// plus the optional `breakdown`. Only `current` carries a breakdown — no
|
||||
/// chart renders a previous-window breakdown, so the asymmetry is declared
|
||||
/// in the contract rather than left as an optional-but-never-populated
|
||||
/// field.
|
||||
final PatchMetricCurrentWindow current;
|
||||
|
||||
/// One window of the patch-metric envelope: the summed count over the
|
||||
/// window's effective range, with a per-bucket series when a `granularity`
|
||||
/// was requested. This base atom is the full shape of `previous`;
|
||||
/// `current` extends it (see PatchMetricCurrentWindow).
|
||||
final PatchMetricWindow? previous;
|
||||
|
||||
/// Converts a [GetPatchMetricResponse] to a `Map<String, dynamic>`.
|
||||
Map<String, dynamic> toJson() {
|
||||
return {
|
||||
'as_of': asOf.toIso8601String(),
|
||||
'granularity': granularity,
|
||||
'current': current.toJson(),
|
||||
'previous': previous?.toJson(),
|
||||
};
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hashAll([
|
||||
asOf,
|
||||
granularity,
|
||||
current,
|
||||
previous,
|
||||
]);
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
return other is GetPatchMetricResponse &&
|
||||
asOf == other.asOf &&
|
||||
granularity == other.granularity &&
|
||||
current == other.current &&
|
||||
previous == other.previous;
|
||||
}
|
||||
}
|
||||
+37
@@ -0,0 +1,37 @@
|
||||
enum GetAppPatchDownloadsParameter2 {
|
||||
hour._('hour'),
|
||||
day._('day'),
|
||||
week._('week');
|
||||
|
||||
const GetAppPatchDownloadsParameter2._(this.value);
|
||||
|
||||
/// Creates a GetAppPatchDownloadsParameter2 from a json value.
|
||||
factory GetAppPatchDownloadsParameter2.fromJson(String json) {
|
||||
return GetAppPatchDownloadsParameter2.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetAppPatchDownloadsParameter2 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetAppPatchDownloadsParameter2? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetAppPatchDownloadsParameter2.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+35
@@ -0,0 +1,35 @@
|
||||
enum GetAppPatchDownloadsParameter3 {
|
||||
release._('release');
|
||||
|
||||
const GetAppPatchDownloadsParameter3._(this.value);
|
||||
|
||||
/// Creates a GetAppPatchDownloadsParameter3 from a json value.
|
||||
factory GetAppPatchDownloadsParameter3.fromJson(String json) {
|
||||
return GetAppPatchDownloadsParameter3.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetAppPatchDownloadsParameter3 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetAppPatchDownloadsParameter3? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetAppPatchDownloadsParameter3.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+37
@@ -0,0 +1,37 @@
|
||||
enum GetAppPatchInstallsParameter2 {
|
||||
hour._('hour'),
|
||||
day._('day'),
|
||||
week._('week');
|
||||
|
||||
const GetAppPatchInstallsParameter2._(this.value);
|
||||
|
||||
/// Creates a GetAppPatchInstallsParameter2 from a json value.
|
||||
factory GetAppPatchInstallsParameter2.fromJson(String json) {
|
||||
return GetAppPatchInstallsParameter2.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetAppPatchInstallsParameter2 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetAppPatchInstallsParameter2? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetAppPatchInstallsParameter2.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+35
@@ -0,0 +1,35 @@
|
||||
enum GetAppPatchInstallsParameter3 {
|
||||
release._('release');
|
||||
|
||||
const GetAppPatchInstallsParameter3._(this.value);
|
||||
|
||||
/// Creates a GetAppPatchInstallsParameter3 from a json value.
|
||||
factory GetAppPatchInstallsParameter3.fromJson(String json) {
|
||||
return GetAppPatchInstallsParameter3.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetAppPatchInstallsParameter3 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetAppPatchInstallsParameter3? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetAppPatchInstallsParameter3.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+37
@@ -0,0 +1,37 @@
|
||||
enum GetReleasePatchDownloadsParameter2 {
|
||||
hour._('hour'),
|
||||
day._('day'),
|
||||
week._('week');
|
||||
|
||||
const GetReleasePatchDownloadsParameter2._(this.value);
|
||||
|
||||
/// Creates a GetReleasePatchDownloadsParameter2 from a json value.
|
||||
factory GetReleasePatchDownloadsParameter2.fromJson(String json) {
|
||||
return GetReleasePatchDownloadsParameter2.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetReleasePatchDownloadsParameter2 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetReleasePatchDownloadsParameter2? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetReleasePatchDownloadsParameter2.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+35
@@ -0,0 +1,35 @@
|
||||
enum GetReleasePatchDownloadsParameter3 {
|
||||
patch._('patch');
|
||||
|
||||
const GetReleasePatchDownloadsParameter3._(this.value);
|
||||
|
||||
/// Creates a GetReleasePatchDownloadsParameter3 from a json value.
|
||||
factory GetReleasePatchDownloadsParameter3.fromJson(String json) {
|
||||
return GetReleasePatchDownloadsParameter3.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetReleasePatchDownloadsParameter3 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetReleasePatchDownloadsParameter3? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetReleasePatchDownloadsParameter3.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+37
@@ -0,0 +1,37 @@
|
||||
enum GetReleasePatchInstallsParameter2 {
|
||||
hour._('hour'),
|
||||
day._('day'),
|
||||
week._('week');
|
||||
|
||||
const GetReleasePatchInstallsParameter2._(this.value);
|
||||
|
||||
/// Creates a GetReleasePatchInstallsParameter2 from a json value.
|
||||
factory GetReleasePatchInstallsParameter2.fromJson(String json) {
|
||||
return GetReleasePatchInstallsParameter2.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetReleasePatchInstallsParameter2 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetReleasePatchInstallsParameter2? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetReleasePatchInstallsParameter2.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+35
@@ -0,0 +1,35 @@
|
||||
enum GetReleasePatchInstallsParameter3 {
|
||||
patch._('patch');
|
||||
|
||||
const GetReleasePatchInstallsParameter3._(this.value);
|
||||
|
||||
/// Creates a GetReleasePatchInstallsParameter3 from a json value.
|
||||
factory GetReleasePatchInstallsParameter3.fromJson(String json) {
|
||||
return GetReleasePatchInstallsParameter3.values.firstWhere(
|
||||
(value) => value.value == json,
|
||||
orElse: () => throw FormatException(
|
||||
'Unknown GetReleasePatchInstallsParameter3 value: $json',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json value.
|
||||
/// Useful when parsing optional fields.
|
||||
static GetReleasePatchInstallsParameter3? maybeFromJson(String? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return GetReleasePatchInstallsParameter3.fromJson(json);
|
||||
}
|
||||
|
||||
/// The value of the enum. This is the exact value
|
||||
/// from the OpenAPI spec and will be used for network transport.
|
||||
final String value;
|
||||
|
||||
/// Converts the enum to its json value.
|
||||
String toJson() => value;
|
||||
|
||||
/// Returns the string form of the enum.
|
||||
@override
|
||||
String toString() => value;
|
||||
}
|
||||
+90
@@ -0,0 +1,90 @@
|
||||
import 'package:meta/meta.dart';
|
||||
import 'package:shorebird_code_push_protocol/model_helpers.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/patch_metric_time_series_entry.dart';
|
||||
|
||||
/// {@template patch_metric_breakdown_entry}
|
||||
/// A patch metric for one value of the `group_by` dimension (one release
|
||||
/// at app scope, or one patch at release scope), optionally with its own
|
||||
/// time series.
|
||||
/// {@endtemplate}
|
||||
@immutable
|
||||
class PatchMetricBreakdownEntry {
|
||||
/// {@macro patch_metric_breakdown_entry}
|
||||
const PatchMetricBreakdownEntry({
|
||||
required this.groupBy,
|
||||
required this.groupValue,
|
||||
required this.count,
|
||||
this.timeSeries,
|
||||
});
|
||||
|
||||
/// Converts a `Map<String, dynamic>` to a [PatchMetricBreakdownEntry].
|
||||
factory PatchMetricBreakdownEntry.fromJson(Map<String, dynamic> json) {
|
||||
return parseFromJson(
|
||||
'PatchMetricBreakdownEntry',
|
||||
json,
|
||||
() => PatchMetricBreakdownEntry(
|
||||
groupBy: json['group_by'] as String,
|
||||
groupValue: json['group_value'] as String,
|
||||
count: json['count'] as int,
|
||||
timeSeries: (json['time_series'] as List?)
|
||||
?.map<PatchMetricTimeSeriesEntry>(
|
||||
(e) => PatchMetricTimeSeriesEntry.fromJson(
|
||||
e as Map<String, dynamic>,
|
||||
),
|
||||
)
|
||||
.toList(),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json object.
|
||||
/// Useful when parsing optional fields.
|
||||
static PatchMetricBreakdownEntry? maybeFromJson(Map<String, dynamic>? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return PatchMetricBreakdownEntry.fromJson(json);
|
||||
}
|
||||
|
||||
/// The dimension this entry breaks down by ("release" or "patch").
|
||||
final String groupBy;
|
||||
|
||||
/// The value within `group_by`: the release version, or the patch
|
||||
/// number as a string.
|
||||
final String groupValue;
|
||||
|
||||
/// The summed count for this group over the window.
|
||||
final int count;
|
||||
|
||||
/// Per-bucket series for this group, present only when a `granularity`
|
||||
/// was requested; otherwise null.
|
||||
final List<PatchMetricTimeSeriesEntry>? timeSeries;
|
||||
|
||||
/// Converts a [PatchMetricBreakdownEntry] to a `Map<String, dynamic>`.
|
||||
Map<String, dynamic> toJson() {
|
||||
return {
|
||||
'group_by': groupBy,
|
||||
'group_value': groupValue,
|
||||
'count': count,
|
||||
'time_series': timeSeries?.map((e) => e.toJson()).toList(),
|
||||
};
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hashAll([
|
||||
groupBy,
|
||||
groupValue,
|
||||
count,
|
||||
listHash(timeSeries),
|
||||
]);
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
return other is PatchMetricBreakdownEntry &&
|
||||
groupBy == other.groupBy &&
|
||||
groupValue == other.groupValue &&
|
||||
count == other.count &&
|
||||
listsEqual(timeSeries, other.timeSeries);
|
||||
}
|
||||
}
|
||||
+108
@@ -0,0 +1,108 @@
|
||||
import 'package:meta/meta.dart';
|
||||
import 'package:shorebird_code_push_protocol/model_helpers.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/metrics_range.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/patch_metric_breakdown_entry.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/patch_metric_time_series_entry.dart';
|
||||
|
||||
/// {@template patch_metric_current_window}
|
||||
/// The `current` window of the patch-metric envelope: the base window atom
|
||||
/// plus the optional `breakdown`. Only `current` carries a breakdown — no
|
||||
/// chart renders a previous-window breakdown, so the asymmetry is declared
|
||||
/// in the contract rather than left as an optional-but-never-populated
|
||||
/// field.
|
||||
/// {@endtemplate}
|
||||
@immutable
|
||||
class PatchMetricCurrentWindow {
|
||||
/// {@macro patch_metric_current_window}
|
||||
const PatchMetricCurrentWindow({
|
||||
required this.count,
|
||||
required this.range,
|
||||
this.timeSeries,
|
||||
this.breakdown,
|
||||
});
|
||||
|
||||
/// Converts a `Map<String, dynamic>` to a [PatchMetricCurrentWindow].
|
||||
factory PatchMetricCurrentWindow.fromJson(Map<String, dynamic> json) {
|
||||
return parseFromJson(
|
||||
'PatchMetricCurrentWindow',
|
||||
json,
|
||||
() => PatchMetricCurrentWindow(
|
||||
count: json['count'] as int,
|
||||
range: MetricsRange.fromJson(json['range'] as Map<String, dynamic>),
|
||||
timeSeries: (json['time_series'] as List?)
|
||||
?.map<PatchMetricTimeSeriesEntry>(
|
||||
(e) => PatchMetricTimeSeriesEntry.fromJson(
|
||||
e as Map<String, dynamic>,
|
||||
),
|
||||
)
|
||||
.toList(),
|
||||
breakdown: (json['breakdown'] as List?)
|
||||
?.map<PatchMetricBreakdownEntry>(
|
||||
(e) =>
|
||||
PatchMetricBreakdownEntry.fromJson(e as Map<String, dynamic>),
|
||||
)
|
||||
.toList(),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json object.
|
||||
/// Useful when parsing optional fields.
|
||||
static PatchMetricCurrentWindow? maybeFromJson(Map<String, dynamic>? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return PatchMetricCurrentWindow.fromJson(json);
|
||||
}
|
||||
|
||||
/// The summed count (installs or downloads) over this window. Unlike
|
||||
/// the HLL-based metrics, per-bucket `time_series` values sum to this
|
||||
/// total.
|
||||
final int count;
|
||||
|
||||
/// The effective (post-default, post-clamp) window a metrics response —
|
||||
/// or one window of a metrics envelope — covers. Always echoed by the
|
||||
/// server; clients must treat it as authoritative rather than reusing
|
||||
/// the requested range.
|
||||
final MetricsRange range;
|
||||
|
||||
/// Per-bucket series for this window, present only when a
|
||||
/// `granularity` was requested; otherwise null. On `previous`, also
|
||||
/// null when the prior window reaches past the plan's metrics-history
|
||||
/// horizon (the total is still present — only the granular overlay is
|
||||
/// withheld). Empty buckets are omitted — gap-fill against this
|
||||
/// window's `range`.
|
||||
final List<PatchMetricTimeSeriesEntry>? timeSeries;
|
||||
|
||||
/// Per-group counts for this window, present only when a
|
||||
/// `group_by` was requested; otherwise null.
|
||||
final List<PatchMetricBreakdownEntry>? breakdown;
|
||||
|
||||
/// Converts a [PatchMetricCurrentWindow] to a `Map<String, dynamic>`.
|
||||
Map<String, dynamic> toJson() {
|
||||
return {
|
||||
'count': count,
|
||||
'range': range.toJson(),
|
||||
'time_series': timeSeries?.map((e) => e.toJson()).toList(),
|
||||
'breakdown': breakdown?.map((e) => e.toJson()).toList(),
|
||||
};
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hashAll([
|
||||
count,
|
||||
range,
|
||||
listHash(timeSeries),
|
||||
listHash(breakdown),
|
||||
]);
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
return other is PatchMetricCurrentWindow &&
|
||||
count == other.count &&
|
||||
range == other.range &&
|
||||
listsEqual(timeSeries, other.timeSeries) &&
|
||||
listsEqual(breakdown, other.breakdown);
|
||||
}
|
||||
}
|
||||
+64
@@ -0,0 +1,64 @@
|
||||
import 'package:meta/meta.dart';
|
||||
import 'package:shorebird_code_push_protocol/model_helpers.dart';
|
||||
|
||||
/// {@template patch_metric_time_series_entry}
|
||||
/// One bucket of a patch-metric time series: the summed count (installs or
|
||||
/// downloads, per the endpoint) in the bucket starting at `period`.
|
||||
/// {@endtemplate}
|
||||
@immutable
|
||||
class PatchMetricTimeSeriesEntry {
|
||||
/// {@macro patch_metric_time_series_entry}
|
||||
const PatchMetricTimeSeriesEntry({
|
||||
required this.period,
|
||||
required this.count,
|
||||
});
|
||||
|
||||
/// Converts a `Map<String, dynamic>` to a [PatchMetricTimeSeriesEntry].
|
||||
factory PatchMetricTimeSeriesEntry.fromJson(Map<String, dynamic> json) {
|
||||
return parseFromJson(
|
||||
'PatchMetricTimeSeriesEntry',
|
||||
json,
|
||||
() => PatchMetricTimeSeriesEntry(
|
||||
period: DateTime.parse(json['period'] as String),
|
||||
count: json['count'] as int,
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json object.
|
||||
/// Useful when parsing optional fields.
|
||||
static PatchMetricTimeSeriesEntry? maybeFromJson(Map<String, dynamic>? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return PatchMetricTimeSeriesEntry.fromJson(json);
|
||||
}
|
||||
|
||||
/// The bucket start (UTC).
|
||||
final DateTime period;
|
||||
|
||||
/// The summed count in this bucket.
|
||||
final int count;
|
||||
|
||||
/// Converts a [PatchMetricTimeSeriesEntry] to a `Map<String, dynamic>`.
|
||||
Map<String, dynamic> toJson() {
|
||||
return {
|
||||
'period': period.toIso8601String(),
|
||||
'count': count,
|
||||
};
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hashAll([
|
||||
period,
|
||||
count,
|
||||
]);
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
return other is PatchMetricTimeSeriesEntry &&
|
||||
period == other.period &&
|
||||
count == other.count;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,92 @@
|
||||
import 'package:meta/meta.dart';
|
||||
import 'package:shorebird_code_push_protocol/model_helpers.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/metrics_range.dart';
|
||||
import 'package:shorebird_code_push_protocol/src/models/patch_metric_time_series_entry.dart';
|
||||
|
||||
/// {@template patch_metric_window}
|
||||
/// One window of the patch-metric envelope: the summed count over the
|
||||
/// window's effective range, with a per-bucket series when a `granularity`
|
||||
/// was requested. This base atom is the full shape of `previous`;
|
||||
/// `current` extends it (see PatchMetricCurrentWindow).
|
||||
/// {@endtemplate}
|
||||
@immutable
|
||||
class PatchMetricWindow {
|
||||
/// {@macro patch_metric_window}
|
||||
const PatchMetricWindow({
|
||||
required this.count,
|
||||
required this.range,
|
||||
this.timeSeries,
|
||||
});
|
||||
|
||||
/// Converts a `Map<String, dynamic>` to a [PatchMetricWindow].
|
||||
factory PatchMetricWindow.fromJson(Map<String, dynamic> json) {
|
||||
return parseFromJson(
|
||||
'PatchMetricWindow',
|
||||
json,
|
||||
() => PatchMetricWindow(
|
||||
count: json['count'] as int,
|
||||
range: MetricsRange.fromJson(json['range'] as Map<String, dynamic>),
|
||||
timeSeries: (json['time_series'] as List?)
|
||||
?.map<PatchMetricTimeSeriesEntry>(
|
||||
(e) => PatchMetricTimeSeriesEntry.fromJson(
|
||||
e as Map<String, dynamic>,
|
||||
),
|
||||
)
|
||||
.toList(),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
/// Convenience to create a nullable type from a nullable json object.
|
||||
/// Useful when parsing optional fields.
|
||||
static PatchMetricWindow? maybeFromJson(Map<String, dynamic>? json) {
|
||||
if (json == null) {
|
||||
return null;
|
||||
}
|
||||
return PatchMetricWindow.fromJson(json);
|
||||
}
|
||||
|
||||
/// The summed count (installs or downloads) over this window. Unlike
|
||||
/// the HLL-based metrics, per-bucket `time_series` values sum to this
|
||||
/// total.
|
||||
final int count;
|
||||
|
||||
/// The effective (post-default, post-clamp) window a metrics response —
|
||||
/// or one window of a metrics envelope — covers. Always echoed by the
|
||||
/// server; clients must treat it as authoritative rather than reusing
|
||||
/// the requested range.
|
||||
final MetricsRange range;
|
||||
|
||||
/// Per-bucket series for this window, present only when a
|
||||
/// `granularity` was requested; otherwise null. On `previous`, also
|
||||
/// null when the prior window reaches past the plan's metrics-history
|
||||
/// horizon (the total is still present — only the granular overlay is
|
||||
/// withheld). Empty buckets are omitted — gap-fill against this
|
||||
/// window's `range`.
|
||||
final List<PatchMetricTimeSeriesEntry>? timeSeries;
|
||||
|
||||
/// Converts a [PatchMetricWindow] to a `Map<String, dynamic>`.
|
||||
Map<String, dynamic> toJson() {
|
||||
return {
|
||||
'count': count,
|
||||
'range': range.toJson(),
|
||||
'time_series': timeSeries?.map((e) => e.toJson()).toList(),
|
||||
};
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => Object.hashAll([
|
||||
count,
|
||||
range,
|
||||
listHash(timeSeries),
|
||||
]);
|
||||
|
||||
@override
|
||||
bool operator ==(Object other) {
|
||||
if (identical(this, other)) return true;
|
||||
return other is PatchMetricWindow &&
|
||||
count == other.count &&
|
||||
range == other.range &&
|
||||
listsEqual(timeSeries, other.timeSeries);
|
||||
}
|
||||
}
|
||||
+35
@@ -0,0 +1,35 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetPatchMetricResponse', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetPatchMetricResponse(
|
||||
asOf: DateTime.utc(2024),
|
||||
granularity: 'example',
|
||||
current: PatchMetricCurrentWindow(
|
||||
count: 0,
|
||||
range: MetricsRange(
|
||||
start: DateTime.utc(2024),
|
||||
end: DateTime.utc(2024),
|
||||
),
|
||||
),
|
||||
);
|
||||
final parsed = GetPatchMetricResponse.maybeFromJson(instance.toJson());
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetPatchMetricResponse.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetPatchMetricResponse.maybeFromJson(<String, dynamic>{}),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetAppPatchDownloadsParameter2', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetAppPatchDownloadsParameter2.values.first;
|
||||
final parsed = GetAppPatchDownloadsParameter2.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetAppPatchDownloadsParameter2.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetAppPatchDownloadsParameter2.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetAppPatchDownloadsParameter2.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetAppPatchDownloadsParameter2.values) {
|
||||
expect(
|
||||
GetAppPatchDownloadsParameter2.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetAppPatchDownloadsParameter3', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetAppPatchDownloadsParameter3.values.first;
|
||||
final parsed = GetAppPatchDownloadsParameter3.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetAppPatchDownloadsParameter3.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetAppPatchDownloadsParameter3.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetAppPatchDownloadsParameter3.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetAppPatchDownloadsParameter3.values) {
|
||||
expect(
|
||||
GetAppPatchDownloadsParameter3.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetAppPatchInstallsParameter2', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetAppPatchInstallsParameter2.values.first;
|
||||
final parsed = GetAppPatchInstallsParameter2.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetAppPatchInstallsParameter2.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetAppPatchInstallsParameter2.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetAppPatchInstallsParameter2.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetAppPatchInstallsParameter2.values) {
|
||||
expect(
|
||||
GetAppPatchInstallsParameter2.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetAppPatchInstallsParameter3', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetAppPatchInstallsParameter3.values.first;
|
||||
final parsed = GetAppPatchInstallsParameter3.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetAppPatchInstallsParameter3.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetAppPatchInstallsParameter3.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetAppPatchInstallsParameter3.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetAppPatchInstallsParameter3.values) {
|
||||
expect(
|
||||
GetAppPatchInstallsParameter3.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetReleasePatchDownloadsParameter2', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetReleasePatchDownloadsParameter2.values.first;
|
||||
final parsed = GetReleasePatchDownloadsParameter2.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetReleasePatchDownloadsParameter2.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetReleasePatchDownloadsParameter2.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetReleasePatchDownloadsParameter2.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetReleasePatchDownloadsParameter2.values) {
|
||||
expect(
|
||||
GetReleasePatchDownloadsParameter2.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetReleasePatchDownloadsParameter3', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetReleasePatchDownloadsParameter3.values.first;
|
||||
final parsed = GetReleasePatchDownloadsParameter3.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetReleasePatchDownloadsParameter3.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetReleasePatchDownloadsParameter3.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetReleasePatchDownloadsParameter3.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetReleasePatchDownloadsParameter3.values) {
|
||||
expect(
|
||||
GetReleasePatchDownloadsParameter3.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetReleasePatchInstallsParameter2', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetReleasePatchInstallsParameter2.values.first;
|
||||
final parsed = GetReleasePatchInstallsParameter2.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetReleasePatchInstallsParameter2.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetReleasePatchInstallsParameter2.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetReleasePatchInstallsParameter2.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetReleasePatchInstallsParameter2.values) {
|
||||
expect(
|
||||
GetReleasePatchInstallsParameter2.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('GetReleasePatchInstallsParameter3', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = GetReleasePatchInstallsParameter3.values.first;
|
||||
final parsed = GetReleasePatchInstallsParameter3.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(GetReleasePatchInstallsParameter3.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => GetReleasePatchInstallsParameter3.maybeFromJson(
|
||||
'__invalid_enum_value__',
|
||||
),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
|
||||
test('toString matches toJson for every value', () {
|
||||
for (final value in GetReleasePatchInstallsParameter3.values) {
|
||||
expect(value.toString(), equals(value.toJson()));
|
||||
}
|
||||
});
|
||||
|
||||
test('fromJson round-trips every value', () {
|
||||
for (final value in GetReleasePatchInstallsParameter3.values) {
|
||||
expect(
|
||||
GetReleasePatchInstallsParameter3.fromJson(value.toJson()),
|
||||
equals(value),
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('PatchMetricBreakdownEntry', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = PatchMetricBreakdownEntry(
|
||||
groupBy: 'example',
|
||||
groupValue: 'example',
|
||||
count: 0,
|
||||
);
|
||||
final parsed = PatchMetricBreakdownEntry.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(PatchMetricBreakdownEntry.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => PatchMetricBreakdownEntry.maybeFromJson(<String, dynamic>{}),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
});
|
||||
}
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('PatchMetricCurrentWindow', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = PatchMetricCurrentWindow(
|
||||
count: 0,
|
||||
range: MetricsRange(
|
||||
start: DateTime.utc(2024),
|
||||
end: DateTime.utc(2024),
|
||||
),
|
||||
);
|
||||
final parsed = PatchMetricCurrentWindow.maybeFromJson(instance.toJson());
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(PatchMetricCurrentWindow.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => PatchMetricCurrentWindow.maybeFromJson(<String, dynamic>{}),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
});
|
||||
}
|
||||
+30
@@ -0,0 +1,30 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('PatchMetricTimeSeriesEntry', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = PatchMetricTimeSeriesEntry(
|
||||
period: DateTime.utc(2024),
|
||||
count: 0,
|
||||
);
|
||||
final parsed = PatchMetricTimeSeriesEntry.maybeFromJson(
|
||||
instance.toJson(),
|
||||
);
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(PatchMetricTimeSeriesEntry.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => PatchMetricTimeSeriesEntry.maybeFromJson(<String, dynamic>{}),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
});
|
||||
}
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
// GENERATED — do not hand-edit.
|
||||
import 'package:shorebird_code_push_protocol/shorebird_code_push_protocol.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('PatchMetricWindow', () {
|
||||
test('round-trips via maybeFromJson/toJson', () {
|
||||
final instance = PatchMetricWindow(
|
||||
count: 0,
|
||||
range: MetricsRange(
|
||||
start: DateTime.utc(2024),
|
||||
end: DateTime.utc(2024),
|
||||
),
|
||||
);
|
||||
final parsed = PatchMetricWindow.maybeFromJson(instance.toJson());
|
||||
expect(parsed, equals(instance));
|
||||
expect(parsed.hashCode, equals(instance.hashCode));
|
||||
});
|
||||
|
||||
test('maybeFromJson returns null on null input', () {
|
||||
expect(PatchMetricWindow.maybeFromJson(null), isNull);
|
||||
});
|
||||
|
||||
test('maybeFromJson throws FormatException on invalid input', () {
|
||||
expect(
|
||||
() => PatchMetricWindow.maybeFromJson(<String, dynamic>{}),
|
||||
throwsFormatException,
|
||||
);
|
||||
});
|
||||
});
|
||||
}
|
||||
Reference in New Issue
Block a user