From 86940524b5065e553155b270212eb729b639791d Mon Sep 17 00:00:00 2001 From: Sebastian Roth Date: Wed, 30 Jul 2025 11:13:39 +0100 Subject: [PATCH 1/6] chore: update dependencies to latest versions - Update Pigeon from 22.7.4 to 26.0.0 for enhanced multi-platform support - Update androidx.work from 2.9.0 to 2.10.2 with improved Flow-based observability - Update permission_handler in example app from 11.3.1 to 12.0.1 - Fix Kotlin null safety issues with androidx.work 2.10.2 type system improvements - Regenerate Pigeon files with new version --- CLAUDE.md | 2 +- example/ios/Runner.xcodeproj/project.pbxproj | 2 +- .../xcshareddata/xcschemes/Runner.xcscheme | 2 +- example/pubspec.yaml | 2 +- workmanager/CHANGELOG.md | 7 + workmanager/pubspec.yaml | 2 +- workmanager_android/android/build.gradle | 2 +- .../workmanager/DebugHelper.kt | 4 +- .../workmanager/pigeon/WorkmanagerApi.g.kt | 172 +++- .../ios/Classes/pigeon/WorkmanagerApi.g.swift | 116 ++- .../workmanager/pigeon/WorkmanagerApi.g.kt | 804 ------------------ .../ios/Classes/pigeon/WorkmanagerApi.g.swift | 681 --------------- .../lib/src/pigeon/workmanager_api.g.dart | 175 +++- workmanager_platform_interface/pubspec.yaml | 2 +- 14 files changed, 412 insertions(+), 1561 deletions(-) delete mode 100644 workmanager_platform_interface/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt delete mode 100644 workmanager_platform_interface/ios/Classes/pigeon/WorkmanagerApi.g.swift diff --git a/CLAUDE.md b/CLAUDE.md index 86e3b57f..aa9cd9a6 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -15,7 +15,7 @@ - Use melos to run all tests: `melos run test` - Or run tests in individual packages: - `cd workmanager_android && flutter test` - - `cd workmanager_apple && flutter test` + - `cd workmanager_apple && flutter test`you did just - `cd workmanager && flutter test` - Before running tests in workmanager package, ensure mocks are up-to-date: `melos run generate:dart` diff --git a/example/ios/Runner.xcodeproj/project.pbxproj b/example/ios/Runner.xcodeproj/project.pbxproj index b4c1ea9b..9b957cf2 100644 --- a/example/ios/Runner.xcodeproj/project.pbxproj +++ b/example/ios/Runner.xcodeproj/project.pbxproj @@ -227,7 +227,7 @@ attributes = { BuildIndependentTargetsInParallel = YES; LastSwiftUpdateCheck = 1250; - LastUpgradeCheck = 1640; + LastUpgradeCheck = 1510; ORGANIZATIONNAME = "The Chromium Authors"; TargetAttributes = { 97C146ED1CF9000F007C117D = { diff --git a/example/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme b/example/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme index 345e6f83..58c125ed 100644 --- a/example/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme +++ b/example/ios/Runner.xcodeproj/xcshareddata/xcschemes/Runner.xcscheme @@ -1,6 +1,6 @@ ? = null, + payload: Map? = null, fetchDuration: Long, result: ListenableWorker.Result, ) { @@ -56,7 +56,7 @@ object DebugHelper { ctx: Context, threadIdentifier: Int, dartTask: String, - payload: Map? = null, + payload: Map? = null, callbackHandle: Long, callbackInfo: FlutterCallbackInformation?, dartBundlePath: String?, diff --git a/workmanager_android/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt b/workmanager_android/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt index b529542d..efc3fec6 100644 --- a/workmanager_android/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt +++ b/workmanager_android/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt @@ -1,7 +1,7 @@ // // Copyright 2024 The Flutter Workmanager Authors. All rights reserved. // // Use of this source code is governed by a MIT-style license that can be // // found in the LICENSE file. -// Autogenerated from Pigeon (v22.7.4), do not edit directly. +// Autogenerated from Pigeon (v26.0.0), do not edit directly. // See also: https://pub.dev/packages/pigeon @file:Suppress("UNCHECKED_CAST", "ArrayInDataClass") @@ -16,29 +16,61 @@ import io.flutter.plugin.common.StandardMethodCodec import io.flutter.plugin.common.StandardMessageCodec import java.io.ByteArrayOutputStream import java.nio.ByteBuffer +private object WorkmanagerApiPigeonUtils { -private fun wrapResult(result: Any?): List { - return listOf(result) -} + fun createConnectionError(channelName: String): FlutterError { + return FlutterError("channel-error", "Unable to establish connection on channel: '$channelName'.", "") } -private fun wrapError(exception: Throwable): List { - return if (exception is FlutterError) { - listOf( - exception.code, - exception.message, - exception.details - ) - } else { - listOf( - exception.javaClass.simpleName, - exception.toString(), - "Cause: " + exception.cause + ", Stacktrace: " + Log.getStackTraceString(exception) - ) + fun wrapResult(result: Any?): List { + return listOf(result) } -} -private fun createConnectionError(channelName: String): FlutterError { - return FlutterError("channel-error", "Unable to establish connection on channel: '$channelName'.", "")} + fun wrapError(exception: Throwable): List { + return if (exception is FlutterError) { + listOf( + exception.code, + exception.message, + exception.details + ) + } else { + listOf( + exception.javaClass.simpleName, + exception.toString(), + "Cause: " + exception.cause + ", Stacktrace: " + Log.getStackTraceString(exception) + ) + } + } + fun deepEquals(a: Any?, b: Any?): Boolean { + if (a is ByteArray && b is ByteArray) { + return a.contentEquals(b) + } + if (a is IntArray && b is IntArray) { + return a.contentEquals(b) + } + if (a is LongArray && b is LongArray) { + return a.contentEquals(b) + } + if (a is DoubleArray && b is DoubleArray) { + return a.contentEquals(b) + } + if (a is Array<*> && b is Array<*>) { + return a.size == b.size && + a.indices.all{ deepEquals(a[it], b[it]) } + } + if (a is List<*> && b is List<*>) { + return a.size == b.size && + a.indices.all{ deepEquals(a[it], b[it]) } + } + if (a is Map<*, *> && b is Map<*, *>) { + return a.size == b.size && a.all { + (b as Map).containsKey(it.key) && + deepEquals(it.value, b[it.key]) + } + } + return a == b + } + +} /** * Error class for passing custom error details to Flutter via a thrown PlatformException. @@ -234,6 +266,16 @@ data class Constraints ( requiresStorageNotLow, ) } + override fun equals(other: Any?): Boolean { + if (other !is Constraints) { + return false + } + if (this === other) { + return true + } + return WorkmanagerApiPigeonUtils.deepEquals(toList(), other.toList()) } + + override fun hashCode(): Int = toList().hashCode() } /** Generated class from Pigeon that represents data sent in messages. */ @@ -255,6 +297,16 @@ data class BackoffPolicyConfig ( backoffDelayMillis, ) } + override fun equals(other: Any?): Boolean { + if (other !is BackoffPolicyConfig) { + return false + } + if (this === other) { + return true + } + return WorkmanagerApiPigeonUtils.deepEquals(toList(), other.toList()) } + + override fun hashCode(): Int = toList().hashCode() } /** Generated class from Pigeon that represents data sent in messages. */ @@ -276,6 +328,16 @@ data class InitializeRequest ( isInDebugMode, ) } + override fun equals(other: Any?): Boolean { + if (other !is InitializeRequest) { + return false + } + if (this === other) { + return true + } + return WorkmanagerApiPigeonUtils.deepEquals(toList(), other.toList()) } + + override fun hashCode(): Int = toList().hashCode() } /** Generated class from Pigeon that represents data sent in messages. */ @@ -318,6 +380,16 @@ data class OneOffTaskRequest ( outOfQuotaPolicy, ) } + override fun equals(other: Any?): Boolean { + if (other !is OneOffTaskRequest) { + return false + } + if (this === other) { + return true + } + return WorkmanagerApiPigeonUtils.deepEquals(toList(), other.toList()) } + + override fun hashCode(): Int = toList().hashCode() } /** Generated class from Pigeon that represents data sent in messages. */ @@ -363,6 +435,16 @@ data class PeriodicTaskRequest ( existingWorkPolicy, ) } + override fun equals(other: Any?): Boolean { + if (other !is PeriodicTaskRequest) { + return false + } + if (this === other) { + return true + } + return WorkmanagerApiPigeonUtils.deepEquals(toList(), other.toList()) } + + override fun hashCode(): Int = toList().hashCode() } /** Generated class from Pigeon that represents data sent in messages. */ @@ -396,6 +478,16 @@ data class ProcessingTaskRequest ( requiresCharging, ) } + override fun equals(other: Any?): Boolean { + if (other !is ProcessingTaskRequest) { + return false + } + if (this === other) { + return true + } + return WorkmanagerApiPigeonUtils.deepEquals(toList(), other.toList()) } + + override fun hashCode(): Int = toList().hashCode() } private open class WorkmanagerApiPigeonCodec : StandardMessageCodec() { override fun readValueOfType(type: Byte, buffer: ByteBuffer): Any? { @@ -540,9 +632,9 @@ interface WorkmanagerHostApi { api.initialize(requestArg) { result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { - reply.reply(wrapResult(null)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(null)) } } } @@ -559,9 +651,9 @@ interface WorkmanagerHostApi { api.registerOneOffTask(requestArg) { result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { - reply.reply(wrapResult(null)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(null)) } } } @@ -578,9 +670,9 @@ interface WorkmanagerHostApi { api.registerPeriodicTask(requestArg) { result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { - reply.reply(wrapResult(null)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(null)) } } } @@ -597,9 +689,9 @@ interface WorkmanagerHostApi { api.registerProcessingTask(requestArg) { result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { - reply.reply(wrapResult(null)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(null)) } } } @@ -616,9 +708,9 @@ interface WorkmanagerHostApi { api.cancelByUniqueName(uniqueNameArg) { result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { - reply.reply(wrapResult(null)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(null)) } } } @@ -635,9 +727,9 @@ interface WorkmanagerHostApi { api.cancelByTag(tagArg) { result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { - reply.reply(wrapResult(null)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(null)) } } } @@ -652,9 +744,9 @@ interface WorkmanagerHostApi { api.cancelAll{ result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { - reply.reply(wrapResult(null)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(null)) } } } @@ -671,10 +763,10 @@ interface WorkmanagerHostApi { api.isScheduledByUniqueName(uniqueNameArg) { result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { val data = result.getOrNull() - reply.reply(wrapResult(data)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(data)) } } } @@ -689,10 +781,10 @@ interface WorkmanagerHostApi { api.printScheduledTasks{ result: Result -> val error = result.exceptionOrNull() if (error != null) { - reply.reply(wrapError(error)) + reply.reply(WorkmanagerApiPigeonUtils.wrapError(error)) } else { val data = result.getOrNull() - reply.reply(wrapResult(data)) + reply.reply(WorkmanagerApiPigeonUtils.wrapResult(data)) } } } @@ -724,7 +816,7 @@ class WorkmanagerFlutterApi(private val binaryMessenger: BinaryMessenger, privat callback(Result.success(Unit)) } } else { - callback(Result.failure(createConnectionError(channelName))) + callback(Result.failure(WorkmanagerApiPigeonUtils.createConnectionError(channelName))) } } } @@ -744,7 +836,7 @@ class WorkmanagerFlutterApi(private val binaryMessenger: BinaryMessenger, privat callback(Result.success(output)) } } else { - callback(Result.failure(createConnectionError(channelName))) + callback(Result.failure(WorkmanagerApiPigeonUtils.createConnectionError(channelName))) } } } diff --git a/workmanager_apple/ios/Classes/pigeon/WorkmanagerApi.g.swift b/workmanager_apple/ios/Classes/pigeon/WorkmanagerApi.g.swift index 62737650..f2cf58cf 100644 --- a/workmanager_apple/ios/Classes/pigeon/WorkmanagerApi.g.swift +++ b/workmanager_apple/ios/Classes/pigeon/WorkmanagerApi.g.swift @@ -1,7 +1,7 @@ // // Copyright 2024 The Flutter Workmanager Authors. All rights reserved. // // Use of this source code is governed by a MIT-style license that can be // // found in the LICENSE file. -// Autogenerated from Pigeon (v22.7.4), do not edit directly. +// Autogenerated from Pigeon (v26.0.0), do not edit directly. // See also: https://pub.dev/packages/pigeon import Foundation @@ -18,9 +18,9 @@ import Foundation final class PigeonError: Error { let code: String let message: String? - let details: Any? + let details: Sendable? - init(code: String, message: String?, details: Any?) { + init(code: String, message: String?, details: Sendable?) { self.code = code self.message = message self.details = details @@ -29,7 +29,7 @@ final class PigeonError: Error { var localizedDescription: String { return "PigeonError(code: \(code), message: \(message ?? ""), details: \(details ?? "")" - } + } } private func wrapResult(_ result: Any?) -> [Any?] { @@ -71,6 +71,70 @@ private func nilOrValue(_ value: Any?) -> T? { return value as! T? } +func deepEqualsWorkmanagerApi(_ lhs: Any?, _ rhs: Any?) -> Bool { + let cleanLhs = nilOrValue(lhs) as Any? + let cleanRhs = nilOrValue(rhs) as Any? + switch (cleanLhs, cleanRhs) { + case (nil, nil): + return true + + case (nil, _), (_, nil): + return false + + case is (Void, Void): + return true + + case let (cleanLhsHashable, cleanRhsHashable) as (AnyHashable, AnyHashable): + return cleanLhsHashable == cleanRhsHashable + + case let (cleanLhsArray, cleanRhsArray) as ([Any?], [Any?]): + guard cleanLhsArray.count == cleanRhsArray.count else { return false } + for (index, element) in cleanLhsArray.enumerated() { + if !deepEqualsWorkmanagerApi(element, cleanRhsArray[index]) { + return false + } + } + return true + + case let (cleanLhsDictionary, cleanRhsDictionary) as ([AnyHashable: Any?], [AnyHashable: Any?]): + guard cleanLhsDictionary.count == cleanRhsDictionary.count else { return false } + for (key, cleanLhsValue) in cleanLhsDictionary { + guard cleanRhsDictionary.index(forKey: key) != nil else { return false } + if !deepEqualsWorkmanagerApi(cleanLhsValue, cleanRhsDictionary[key]!) { + return false + } + } + return true + + default: + // Any other type shouldn't be able to be used with pigeon. File an issue if you find this to be untrue. + return false + } +} + +func deepHashWorkmanagerApi(value: Any?, hasher: inout Hasher) { + if let valueList = value as? [AnyHashable] { + for item in valueList { deepHashWorkmanagerApi(value: item, hasher: &hasher) } + return + } + + if let valueDict = value as? [AnyHashable: AnyHashable] { + for key in valueDict.keys { + hasher.combine(key) + deepHashWorkmanagerApi(value: valueDict[key]!, hasher: &hasher) + } + return + } + + if let hashableValue = value as? AnyHashable { + hasher.combine(hashableValue.hashValue) + } + + return hasher.combine(String(describing: value)) +} + + + /// An enumeration of various network types that can be used as Constraints for work. /// /// Fully supported on Android. @@ -168,7 +232,7 @@ enum OutOfQuotaPolicy: Int { } /// Generated class from Pigeon that represents data sent in messages. -struct Constraints { +struct Constraints: Hashable { var networkType: NetworkType? = nil var requiresBatteryNotLow: Bool? = nil var requiresCharging: Bool? = nil @@ -201,10 +265,15 @@ struct Constraints { requiresStorageNotLow, ] } + static func == (lhs: Constraints, rhs: Constraints) -> Bool { + return deepEqualsWorkmanagerApi(lhs.toList(), rhs.toList()) } + func hash(into hasher: inout Hasher) { + deepHashWorkmanagerApi(value: toList(), hasher: &hasher) + } } /// Generated class from Pigeon that represents data sent in messages. -struct BackoffPolicyConfig { +struct BackoffPolicyConfig: Hashable { var backoffPolicy: BackoffPolicy? = nil var backoffDelayMillis: Int64? = nil @@ -225,10 +294,15 @@ struct BackoffPolicyConfig { backoffDelayMillis, ] } + static func == (lhs: BackoffPolicyConfig, rhs: BackoffPolicyConfig) -> Bool { + return deepEqualsWorkmanagerApi(lhs.toList(), rhs.toList()) } + func hash(into hasher: inout Hasher) { + deepHashWorkmanagerApi(value: toList(), hasher: &hasher) + } } /// Generated class from Pigeon that represents data sent in messages. -struct InitializeRequest { +struct InitializeRequest: Hashable { var callbackHandle: Int64 var isInDebugMode: Bool @@ -249,10 +323,15 @@ struct InitializeRequest { isInDebugMode, ] } + static func == (lhs: InitializeRequest, rhs: InitializeRequest) -> Bool { + return deepEqualsWorkmanagerApi(lhs.toList(), rhs.toList()) } + func hash(into hasher: inout Hasher) { + deepHashWorkmanagerApi(value: toList(), hasher: &hasher) + } } /// Generated class from Pigeon that represents data sent in messages. -struct OneOffTaskRequest { +struct OneOffTaskRequest: Hashable { var uniqueName: String var taskName: String var inputData: [String?: Any?]? = nil @@ -301,10 +380,15 @@ struct OneOffTaskRequest { outOfQuotaPolicy, ] } + static func == (lhs: OneOffTaskRequest, rhs: OneOffTaskRequest) -> Bool { + return deepEqualsWorkmanagerApi(lhs.toList(), rhs.toList()) } + func hash(into hasher: inout Hasher) { + deepHashWorkmanagerApi(value: toList(), hasher: &hasher) + } } /// Generated class from Pigeon that represents data sent in messages. -struct PeriodicTaskRequest { +struct PeriodicTaskRequest: Hashable { var uniqueName: String var taskName: String var frequencySeconds: Int64 @@ -357,10 +441,15 @@ struct PeriodicTaskRequest { existingWorkPolicy, ] } + static func == (lhs: PeriodicTaskRequest, rhs: PeriodicTaskRequest) -> Bool { + return deepEqualsWorkmanagerApi(lhs.toList(), rhs.toList()) } + func hash(into hasher: inout Hasher) { + deepHashWorkmanagerApi(value: toList(), hasher: &hasher) + } } /// Generated class from Pigeon that represents data sent in messages. -struct ProcessingTaskRequest { +struct ProcessingTaskRequest: Hashable { var uniqueName: String var taskName: String var inputData: [String?: Any?]? = nil @@ -397,6 +486,11 @@ struct ProcessingTaskRequest { requiresCharging, ] } + static func == (lhs: ProcessingTaskRequest, rhs: ProcessingTaskRequest) -> Bool { + return deepEqualsWorkmanagerApi(lhs.toList(), rhs.toList()) } + func hash(into hasher: inout Hasher) { + deepHashWorkmanagerApi(value: toList(), hasher: &hasher) + } } private class WorkmanagerApiPigeonCodecReader: FlutterStandardReader { @@ -705,7 +799,7 @@ class WorkmanagerFlutterApi: WorkmanagerFlutterApiProtocol { let details: String? = nilOrValue(listResponse[2]) completion(.failure(PigeonError(code: code, message: message, details: details))) } else { - completion(.success(Void())) + completion(.success(())) } } } diff --git a/workmanager_platform_interface/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt b/workmanager_platform_interface/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt deleted file mode 100644 index 438608d3..00000000 --- a/workmanager_platform_interface/android/src/main/kotlin/dev/fluttercommunity/workmanager/pigeon/WorkmanagerApi.g.kt +++ /dev/null @@ -1,804 +0,0 @@ -// // Copyright 2024 The Flutter Workmanager Authors. All rights reserved. -// // Use of this source code is governed by a MIT-style license that can be -// // found in the LICENSE file. -// Autogenerated from Pigeon (v22.7.4), do not edit directly. -// See also: https://pub.dev/packages/pigeon -@file:Suppress("UNCHECKED_CAST", "ArrayInDataClass") - -package dev.fluttercommunity.workmanager.pigeon - -import android.util.Log -import io.flutter.plugin.common.BasicMessageChannel -import io.flutter.plugin.common.BinaryMessenger -import io.flutter.plugin.common.MessageCodec -import io.flutter.plugin.common.StandardMessageCodec -import java.io.ByteArrayOutputStream -import java.nio.ByteBuffer - -private fun wrapResult(result: Any?): List = listOf(result) - -private fun wrapError(exception: Throwable): List = - if (exception is FlutterError) { - listOf( - exception.code, - exception.message, - exception.details, - ) - } else { - listOf( - exception.javaClass.simpleName, - exception.toString(), - "Cause: " + exception.cause + ", Stacktrace: " + Log.getStackTraceString(exception), - ) - } - -private fun createConnectionError(channelName: String): FlutterError = - FlutterError("channel-error", "Unable to establish connection on channel: '$channelName'.", "") - -/** - * Error class for passing custom error details to Flutter via a thrown PlatformException. - * @property code The error code. - * @property message The error message. - * @property details The error details. Must be a datatype supported by the api codec. - */ -class FlutterError( - val code: String, - override val message: String? = null, - val details: Any? = null, -) : Throwable() - -/** - * An enumeration of various network types that can be used as Constraints for work. - * - * Fully supported on Android. - * - * On iOS, this enumeration is used to define whether a piece of work requires - * internet connectivity, by checking for either [NetworkType.connected] or - * [NetworkType.metered]. - */ -enum class NetworkType( - val raw: Int, -) { - /** Any working network connection is required for this work. */ - CONNECTED(0), - - /** A metered network connection is required for this work. */ - METERED(1), - - /** Default value. A network is not required for this work. */ - NOT_REQUIRED(2), - - /** A non-roaming network connection is required for this work. */ - NOT_ROAMING(3), - - /** An unmetered network connection is required for this work. */ - UNMETERED(4), - - /** - * A temporarily unmetered Network. This capability will be set for - * networks that are generally metered, but are currently unmetered. - * - * Android API 30+ - */ - TEMPORARILY_UNMETERED(5), - ; - - companion object { - fun ofRaw(raw: Int): NetworkType? = values().firstOrNull { it.raw == raw } - } -} - -/** - * An enumeration of backoff policies when retrying work. - * These policies are used when you have a return ListenableWorker.Result.retry() from a worker to determine the correct backoff time. - * Backoff policies are set in WorkRequest.Builder.setBackoffCriteria(BackoffPolicy, long, TimeUnit) or one of its variants. - */ -enum class BackoffPolicy( - val raw: Int, -) { - /** Used to indicate that WorkManager should increase the backoff time exponentially */ - EXPONENTIAL(0), - - /** Used to indicate that WorkManager should increase the backoff time linearly */ - LINEAR(1), - ; - - companion object { - fun ofRaw(raw: Int): BackoffPolicy? = values().firstOrNull { it.raw == raw } - } -} - -/** An enumeration of the conflict resolution policies in case of a collision. */ -enum class ExistingWorkPolicy( - val raw: Int, -) { - /** If there is existing pending (uncompleted) work with the same unique name, append the newly-specified work as a child of all the leaves of that work sequence. */ - APPEND(0), - - /** If there is existing pending (uncompleted) work with the same unique name, do nothing. */ - KEEP(1), - - /** If there is existing pending (uncompleted) work with the same unique name, cancel and delete it. */ - REPLACE(2), - - /** - * If there is existing pending (uncompleted) work with the same unique name, it will be updated the new specification. - * Note: This maps to appendOrReplace in the native implementation. - */ - UPDATE(3), - ; - - companion object { - fun ofRaw(raw: Int): ExistingWorkPolicy? = values().firstOrNull { it.raw == raw } - } -} - -/** - * An enumeration of policies that help determine out of quota behavior for expedited jobs. - * - * Only supported on Android. - */ -enum class OutOfQuotaPolicy( - val raw: Int, -) { - /** - * When the app does not have any expedited job quota, the expedited work request will - * fallback to a regular work request. - */ - RUN_AS_NON_EXPEDITED_WORK_REQUEST(0), - - /** - * When the app does not have any expedited job quota, the expedited work request will - * we dropped and no work requests are enqueued. - */ - DROP_WORK_REQUEST(1), - ; - - companion object { - fun ofRaw(raw: Int): OutOfQuotaPolicy? = values().firstOrNull { it.raw == raw } - } -} - -/** Generated class from Pigeon that represents data sent in messages. */ -data class Constraints( - val networkType: NetworkType? = null, - val requiresBatteryNotLow: Boolean? = null, - val requiresCharging: Boolean? = null, - val requiresDeviceIdle: Boolean? = null, - val requiresStorageNotLow: Boolean? = null, -) { - companion object { - fun fromList(pigeonVar_list: List): Constraints { - val networkType = pigeonVar_list[0] as NetworkType? - val requiresBatteryNotLow = pigeonVar_list[1] as Boolean? - val requiresCharging = pigeonVar_list[2] as Boolean? - val requiresDeviceIdle = pigeonVar_list[3] as Boolean? - val requiresStorageNotLow = pigeonVar_list[4] as Boolean? - return Constraints(networkType, requiresBatteryNotLow, requiresCharging, requiresDeviceIdle, requiresStorageNotLow) - } - } - - fun toList(): List = - listOf( - networkType, - requiresBatteryNotLow, - requiresCharging, - requiresDeviceIdle, - requiresStorageNotLow, - ) -} - -/** Generated class from Pigeon that represents data sent in messages. */ -data class BackoffPolicyConfig( - val backoffPolicy: BackoffPolicy? = null, - val backoffDelayMillis: Long? = null, -) { - companion object { - fun fromList(pigeonVar_list: List): BackoffPolicyConfig { - val backoffPolicy = pigeonVar_list[0] as BackoffPolicy? - val backoffDelayMillis = pigeonVar_list[1] as Long? - return BackoffPolicyConfig(backoffPolicy, backoffDelayMillis) - } - } - - fun toList(): List = - listOf( - backoffPolicy, - backoffDelayMillis, - ) -} - -/** Generated class from Pigeon that represents data sent in messages. */ -data class InitializeRequest( - val callbackHandle: Long, - val isInDebugMode: Boolean, -) { - companion object { - fun fromList(pigeonVar_list: List): InitializeRequest { - val callbackHandle = pigeonVar_list[0] as Long - val isInDebugMode = pigeonVar_list[1] as Boolean - return InitializeRequest(callbackHandle, isInDebugMode) - } - } - - fun toList(): List = - listOf( - callbackHandle, - isInDebugMode, - ) -} - -/** Generated class from Pigeon that represents data sent in messages. */ -data class OneOffTaskRequest( - val uniqueName: String, - val taskName: String, - val inputData: Map? = null, - val initialDelaySeconds: Long? = null, - val constraints: Constraints? = null, - val backoffPolicy: BackoffPolicyConfig? = null, - val tag: String? = null, - val existingWorkPolicy: ExistingWorkPolicy? = null, - val outOfQuotaPolicy: OutOfQuotaPolicy? = null, -) { - companion object { - fun fromList(pigeonVar_list: List): OneOffTaskRequest { - val uniqueName = pigeonVar_list[0] as String - val taskName = pigeonVar_list[1] as String - val inputData = pigeonVar_list[2] as Map? - val initialDelaySeconds = pigeonVar_list[3] as Long? - val constraints = pigeonVar_list[4] as Constraints? - val backoffPolicy = pigeonVar_list[5] as BackoffPolicyConfig? - val tag = pigeonVar_list[6] as String? - val existingWorkPolicy = pigeonVar_list[7] as ExistingWorkPolicy? - val outOfQuotaPolicy = pigeonVar_list[8] as OutOfQuotaPolicy? - return OneOffTaskRequest( - uniqueName, - taskName, - inputData, - initialDelaySeconds, - constraints, - backoffPolicy, - tag, - existingWorkPolicy, - outOfQuotaPolicy, - ) - } - } - - fun toList(): List = - listOf( - uniqueName, - taskName, - inputData, - initialDelaySeconds, - constraints, - backoffPolicy, - tag, - existingWorkPolicy, - outOfQuotaPolicy, - ) -} - -/** Generated class from Pigeon that represents data sent in messages. */ -data class PeriodicTaskRequest( - val uniqueName: String, - val taskName: String, - val frequencySeconds: Long, - val flexIntervalSeconds: Long? = null, - val inputData: Map? = null, - val initialDelaySeconds: Long? = null, - val constraints: Constraints? = null, - val backoffPolicy: BackoffPolicyConfig? = null, - val tag: String? = null, - val existingWorkPolicy: ExistingWorkPolicy? = null, -) { - companion object { - fun fromList(pigeonVar_list: List): PeriodicTaskRequest { - val uniqueName = pigeonVar_list[0] as String - val taskName = pigeonVar_list[1] as String - val frequencySeconds = pigeonVar_list[2] as Long - val flexIntervalSeconds = pigeonVar_list[3] as Long? - val inputData = pigeonVar_list[4] as Map? - val initialDelaySeconds = pigeonVar_list[5] as Long? - val constraints = pigeonVar_list[6] as Constraints? - val backoffPolicy = pigeonVar_list[7] as BackoffPolicyConfig? - val tag = pigeonVar_list[8] as String? - val existingWorkPolicy = pigeonVar_list[9] as ExistingWorkPolicy? - return PeriodicTaskRequest( - uniqueName, - taskName, - frequencySeconds, - flexIntervalSeconds, - inputData, - initialDelaySeconds, - constraints, - backoffPolicy, - tag, - existingWorkPolicy, - ) - } - } - - fun toList(): List = - listOf( - uniqueName, - taskName, - frequencySeconds, - flexIntervalSeconds, - inputData, - initialDelaySeconds, - constraints, - backoffPolicy, - tag, - existingWorkPolicy, - ) -} - -/** Generated class from Pigeon that represents data sent in messages. */ -data class ProcessingTaskRequest( - val uniqueName: String, - val taskName: String, - val inputData: Map? = null, - val initialDelaySeconds: Long? = null, - val networkType: NetworkType? = null, - val requiresCharging: Boolean? = null, -) { - companion object { - fun fromList(pigeonVar_list: List): ProcessingTaskRequest { - val uniqueName = pigeonVar_list[0] as String - val taskName = pigeonVar_list[1] as String - val inputData = pigeonVar_list[2] as Map? - val initialDelaySeconds = pigeonVar_list[3] as Long? - val networkType = pigeonVar_list[4] as NetworkType? - val requiresCharging = pigeonVar_list[5] as Boolean? - return ProcessingTaskRequest(uniqueName, taskName, inputData, initialDelaySeconds, networkType, requiresCharging) - } - } - - fun toList(): List = - listOf( - uniqueName, - taskName, - inputData, - initialDelaySeconds, - networkType, - requiresCharging, - ) -} - -private open class WorkmanagerApiPigeonCodec : StandardMessageCodec() { - override fun readValueOfType( - type: Byte, - buffer: ByteBuffer, - ): Any? { - return when (type) { - 129.toByte() -> { - return (readValue(buffer) as Long?)?.let { - NetworkType.ofRaw(it.toInt()) - } - } - 130.toByte() -> { - return (readValue(buffer) as Long?)?.let { - BackoffPolicy.ofRaw(it.toInt()) - } - } - 131.toByte() -> { - return (readValue(buffer) as Long?)?.let { - ExistingWorkPolicy.ofRaw(it.toInt()) - } - } - 132.toByte() -> { - return (readValue(buffer) as Long?)?.let { - OutOfQuotaPolicy.ofRaw(it.toInt()) - } - } - 133.toByte() -> { - return (readValue(buffer) as? List)?.let { - Constraints.fromList(it) - } - } - 134.toByte() -> { - return (readValue(buffer) as? List)?.let { - BackoffPolicyConfig.fromList(it) - } - } - 135.toByte() -> { - return (readValue(buffer) as? List)?.let { - InitializeRequest.fromList(it) - } - } - 136.toByte() -> { - return (readValue(buffer) as? List)?.let { - OneOffTaskRequest.fromList(it) - } - } - 137.toByte() -> { - return (readValue(buffer) as? List)?.let { - PeriodicTaskRequest.fromList(it) - } - } - 138.toByte() -> { - return (readValue(buffer) as? List)?.let { - ProcessingTaskRequest.fromList(it) - } - } - else -> super.readValueOfType(type, buffer) - } - } - - override fun writeValue( - stream: ByteArrayOutputStream, - value: Any?, - ) { - when (value) { - is NetworkType -> { - stream.write(129) - writeValue(stream, value.raw) - } - is BackoffPolicy -> { - stream.write(130) - writeValue(stream, value.raw) - } - is ExistingWorkPolicy -> { - stream.write(131) - writeValue(stream, value.raw) - } - is OutOfQuotaPolicy -> { - stream.write(132) - writeValue(stream, value.raw) - } - is Constraints -> { - stream.write(133) - writeValue(stream, value.toList()) - } - is BackoffPolicyConfig -> { - stream.write(134) - writeValue(stream, value.toList()) - } - is InitializeRequest -> { - stream.write(135) - writeValue(stream, value.toList()) - } - is OneOffTaskRequest -> { - stream.write(136) - writeValue(stream, value.toList()) - } - is PeriodicTaskRequest -> { - stream.write(137) - writeValue(stream, value.toList()) - } - is ProcessingTaskRequest -> { - stream.write(138) - writeValue(stream, value.toList()) - } - else -> super.writeValue(stream, value) - } - } -} - -/** Generated interface from Pigeon that represents a handler of messages from Flutter. */ -interface WorkmanagerHostApi { - fun initialize( - request: InitializeRequest, - callback: (Result) -> Unit, - ) - - fun registerOneOffTask( - request: OneOffTaskRequest, - callback: (Result) -> Unit, - ) - - fun registerPeriodicTask( - request: PeriodicTaskRequest, - callback: (Result) -> Unit, - ) - - fun registerProcessingTask( - request: ProcessingTaskRequest, - callback: (Result) -> Unit, - ) - - fun cancelByUniqueName( - uniqueName: String, - callback: (Result) -> Unit, - ) - - fun cancelByTag( - tag: String, - callback: (Result) -> Unit, - ) - - fun cancelAll(callback: (Result) -> Unit) - - fun isScheduledByUniqueName( - uniqueName: String, - callback: (Result) -> Unit, - ) - - fun printScheduledTasks(callback: (Result) -> Unit) - - companion object { - /** The codec used by WorkmanagerHostApi. */ - val codec: MessageCodec by lazy { - WorkmanagerApiPigeonCodec() - } - - /** Sets up an instance of `WorkmanagerHostApi` to handle messages through the `binaryMessenger`. */ - @JvmOverloads - fun setUp( - binaryMessenger: BinaryMessenger, - api: WorkmanagerHostApi?, - messageChannelSuffix: String = "", - ) { - val separatedMessageChannelSuffix = if (messageChannelSuffix.isNotEmpty()) ".$messageChannelSuffix" else "" - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.initialize$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { message, reply -> - val args = message as List - val requestArg = args[0] as InitializeRequest - api.initialize(requestArg) { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - reply.reply(wrapResult(null)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.registerOneOffTask$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { message, reply -> - val args = message as List - val requestArg = args[0] as OneOffTaskRequest - api.registerOneOffTask(requestArg) { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - reply.reply(wrapResult(null)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.registerPeriodicTask$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { message, reply -> - val args = message as List - val requestArg = args[0] as PeriodicTaskRequest - api.registerPeriodicTask(requestArg) { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - reply.reply(wrapResult(null)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.registerProcessingTask$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { message, reply -> - val args = message as List - val requestArg = args[0] as ProcessingTaskRequest - api.registerProcessingTask(requestArg) { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - reply.reply(wrapResult(null)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.cancelByUniqueName$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { message, reply -> - val args = message as List - val uniqueNameArg = args[0] as String - api.cancelByUniqueName(uniqueNameArg) { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - reply.reply(wrapResult(null)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.cancelByTag$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { message, reply -> - val args = message as List - val tagArg = args[0] as String - api.cancelByTag(tagArg) { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - reply.reply(wrapResult(null)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.cancelAll$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { _, reply -> - api.cancelAll { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - reply.reply(wrapResult(null)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.isScheduledByUniqueName$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { message, reply -> - val args = message as List - val uniqueNameArg = args[0] as String - api.isScheduledByUniqueName(uniqueNameArg) { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - val data = result.getOrNull() - reply.reply(wrapResult(data)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - run { - val channel = - BasicMessageChannel( - binaryMessenger, - "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.printScheduledTasks$separatedMessageChannelSuffix", - codec, - ) - if (api != null) { - channel.setMessageHandler { _, reply -> - api.printScheduledTasks { result: Result -> - val error = result.exceptionOrNull() - if (error != null) { - reply.reply(wrapError(error)) - } else { - val data = result.getOrNull() - reply.reply(wrapResult(data)) - } - } - } - } else { - channel.setMessageHandler(null) - } - } - } - } -} - -/** Generated class from Pigeon that represents Flutter messages that can be called from Kotlin. */ -class WorkmanagerFlutterApi( - private val binaryMessenger: BinaryMessenger, - private val messageChannelSuffix: String = "", -) { - companion object { - /** The codec used by WorkmanagerFlutterApi. */ - val codec: MessageCodec by lazy { - WorkmanagerApiPigeonCodec() - } - } - - fun backgroundChannelInitialized(callback: (Result) -> Unit) { - val separatedMessageChannelSuffix = if (messageChannelSuffix.isNotEmpty()) ".$messageChannelSuffix" else "" - val channelName = "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerFlutterApi.backgroundChannelInitialized$separatedMessageChannelSuffix" - val channel = BasicMessageChannel(binaryMessenger, channelName, codec) - channel.send(null) { - if (it is List<*>) { - if (it.size > 1) { - callback(Result.failure(FlutterError(it[0] as String, it[1] as String, it[2] as String?))) - } else { - callback(Result.success(Unit)) - } - } else { - callback(Result.failure(createConnectionError(channelName))) - } - } - } - - fun executeTask( - taskNameArg: String, - inputDataArg: Map?, - callback: (Result) -> Unit, - ) { - val separatedMessageChannelSuffix = if (messageChannelSuffix.isNotEmpty()) ".$messageChannelSuffix" else "" - val channelName = "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerFlutterApi.executeTask$separatedMessageChannelSuffix" - val channel = BasicMessageChannel(binaryMessenger, channelName, codec) - channel.send(listOf(taskNameArg, inputDataArg)) { - if (it is List<*>) { - if (it.size > 1) { - callback(Result.failure(FlutterError(it[0] as String, it[1] as String, it[2] as String?))) - } else if (it[0] == null) { - callback(Result.failure(FlutterError("null-error", "Flutter api returned null value for non-null return value.", ""))) - } else { - val output = it[0] as Boolean - callback(Result.success(output)) - } - } else { - callback(Result.failure(createConnectionError(channelName))) - } - } - } -} diff --git a/workmanager_platform_interface/ios/Classes/pigeon/WorkmanagerApi.g.swift b/workmanager_platform_interface/ios/Classes/pigeon/WorkmanagerApi.g.swift deleted file mode 100644 index 97a9cd1d..00000000 --- a/workmanager_platform_interface/ios/Classes/pigeon/WorkmanagerApi.g.swift +++ /dev/null @@ -1,681 +0,0 @@ -// // Copyright 2024 The Flutter Workmanager Authors. All rights reserved. -// // Use of this source code is governed by a MIT-style license that can be -// // found in the LICENSE file. -// Autogenerated from Pigeon (v22.7.4), do not edit directly. -// See also: https://pub.dev/packages/pigeon - -import Foundation - -#if os(iOS) - import Flutter -#elseif os(macOS) - import FlutterMacOS -#else - #error("Unsupported platform.") -#endif - -/// Error class for passing custom error details to Dart side. -final class PigeonError: Error { - let code: String - let message: String? - let details: Any? - - init(code: String, message: String?, details: Any?) { - self.code = code - self.message = message - self.details = details - } - - var localizedDescription: String { - return - "PigeonError(code: \(code), message: \(message ?? ""), details: \(details ?? "")" - } -} - -private func wrapResult(_ result: Any?) -> [Any?] { - return [result] -} - -private func wrapError(_ error: Any) -> [Any?] { - if let pigeonError = error as? PigeonError { - return [ - pigeonError.code, - pigeonError.message, - pigeonError.details - ] - } - if let flutterError = error as? FlutterError { - return [ - flutterError.code, - flutterError.message, - flutterError.details - ] - } - return [ - "\(error)", - "\(type(of: error))", - "Stacktrace: \(Thread.callStackSymbols)" - ] -} - -private func createConnectionError(withChannelName channelName: String) -> PigeonError { - return PigeonError(code: "channel-error", message: "Unable to establish connection on channel: '\(channelName)'.", details: "") -} - -private func isNullish(_ value: Any?) -> Bool { - return value is NSNull || value == nil -} - -private func nilOrValue(_ value: Any?) -> T? { - if value is NSNull { return nil } - return value as! T? -} - -/// An enumeration of various network types that can be used as Constraints for work. -/// -/// Fully supported on Android. -/// -/// On iOS, this enumeration is used to define whether a piece of work requires -/// internet connectivity, by checking for either [NetworkType.connected] or -/// [NetworkType.metered]. -enum NetworkType: Int { - /// Any working network connection is required for this work. - case connected = 0 - /// A metered network connection is required for this work. - case metered = 1 - /// Default value. A network is not required for this work. - case notRequired = 2 - /// A non-roaming network connection is required for this work. - case notRoaming = 3 - /// An unmetered network connection is required for this work. - case unmetered = 4 - /// A temporarily unmetered Network. This capability will be set for - /// networks that are generally metered, but are currently unmetered. - /// - /// Android API 30+ - case temporarilyUnmetered = 5 -} - -/// An enumeration of backoff policies when retrying work. -/// These policies are used when you have a return ListenableWorker.Result.retry() from a worker to determine the correct backoff time. -/// Backoff policies are set in WorkRequest.Builder.setBackoffCriteria(BackoffPolicy, long, TimeUnit) or one of its variants. -enum BackoffPolicy: Int { - /// Used to indicate that WorkManager should increase the backoff time exponentially - case exponential = 0 - /// Used to indicate that WorkManager should increase the backoff time linearly - case linear = 1 -} - -/// An enumeration of the conflict resolution policies in case of a collision. -enum ExistingWorkPolicy: Int { - /// If there is existing pending (uncompleted) work with the same unique name, append the newly-specified work as a child of all the leaves of that work sequence. - case append = 0 - /// If there is existing pending (uncompleted) work with the same unique name, do nothing. - case keep = 1 - /// If there is existing pending (uncompleted) work with the same unique name, cancel and delete it. - case replace = 2 - /// If there is existing pending (uncompleted) work with the same unique name, it will be updated the new specification. - /// Note: This maps to appendOrReplace in the native implementation. - case update = 3 -} - -/// An enumeration of policies that help determine out of quota behavior for expedited jobs. -/// -/// Only supported on Android. -enum OutOfQuotaPolicy: Int { - /// When the app does not have any expedited job quota, the expedited work request will - /// fallback to a regular work request. - case runAsNonExpeditedWorkRequest = 0 - /// When the app does not have any expedited job quota, the expedited work request will - /// we dropped and no work requests are enqueued. - case dropWorkRequest = 1 -} - -/// Generated class from Pigeon that represents data sent in messages. -struct Constraints { - var networkType: NetworkType? - var requiresBatteryNotLow: Bool? - var requiresCharging: Bool? - var requiresDeviceIdle: Bool? - var requiresStorageNotLow: Bool? - - // swift-format-ignore: AlwaysUseLowerCamelCase - static func fromList(_ pigeonVar_list: [Any?]) -> Constraints? { - let networkType: NetworkType? = nilOrValue(pigeonVar_list[0]) - let requiresBatteryNotLow: Bool? = nilOrValue(pigeonVar_list[1]) - let requiresCharging: Bool? = nilOrValue(pigeonVar_list[2]) - let requiresDeviceIdle: Bool? = nilOrValue(pigeonVar_list[3]) - let requiresStorageNotLow: Bool? = nilOrValue(pigeonVar_list[4]) - - return Constraints( - networkType: networkType, - requiresBatteryNotLow: requiresBatteryNotLow, - requiresCharging: requiresCharging, - requiresDeviceIdle: requiresDeviceIdle, - requiresStorageNotLow: requiresStorageNotLow - ) - } - func toList() -> [Any?] { - return [ - networkType, - requiresBatteryNotLow, - requiresCharging, - requiresDeviceIdle, - requiresStorageNotLow - ] - } -} - -/// Generated class from Pigeon that represents data sent in messages. -struct BackoffPolicyConfig { - var backoffPolicy: BackoffPolicy? - var backoffDelayMillis: Int64? - - // swift-format-ignore: AlwaysUseLowerCamelCase - static func fromList(_ pigeonVar_list: [Any?]) -> BackoffPolicyConfig? { - let backoffPolicy: BackoffPolicy? = nilOrValue(pigeonVar_list[0]) - let backoffDelayMillis: Int64? = nilOrValue(pigeonVar_list[1]) - - return BackoffPolicyConfig( - backoffPolicy: backoffPolicy, - backoffDelayMillis: backoffDelayMillis - ) - } - func toList() -> [Any?] { - return [ - backoffPolicy, - backoffDelayMillis - ] - } -} - -/// Generated class from Pigeon that represents data sent in messages. -struct InitializeRequest { - var callbackHandle: Int64 - var isInDebugMode: Bool - - // swift-format-ignore: AlwaysUseLowerCamelCase - static func fromList(_ pigeonVar_list: [Any?]) -> InitializeRequest? { - let callbackHandle = pigeonVar_list[0] as! Int64 - let isInDebugMode = pigeonVar_list[1] as! Bool - - return InitializeRequest( - callbackHandle: callbackHandle, - isInDebugMode: isInDebugMode - ) - } - func toList() -> [Any?] { - return [ - callbackHandle, - isInDebugMode - ] - } -} - -/// Generated class from Pigeon that represents data sent in messages. -struct OneOffTaskRequest { - var uniqueName: String - var taskName: String - var inputData: [String?: Any?]? - var initialDelaySeconds: Int64? - var constraints: Constraints? - var backoffPolicy: BackoffPolicyConfig? - var tag: String? - var existingWorkPolicy: ExistingWorkPolicy? - var outOfQuotaPolicy: OutOfQuotaPolicy? - - // swift-format-ignore: AlwaysUseLowerCamelCase - static func fromList(_ pigeonVar_list: [Any?]) -> OneOffTaskRequest? { - let uniqueName = pigeonVar_list[0] as! String - let taskName = pigeonVar_list[1] as! String - let inputData: [String?: Any?]? = nilOrValue(pigeonVar_list[2]) - let initialDelaySeconds: Int64? = nilOrValue(pigeonVar_list[3]) - let constraints: Constraints? = nilOrValue(pigeonVar_list[4]) - let backoffPolicy: BackoffPolicyConfig? = nilOrValue(pigeonVar_list[5]) - let tag: String? = nilOrValue(pigeonVar_list[6]) - let existingWorkPolicy: ExistingWorkPolicy? = nilOrValue(pigeonVar_list[7]) - let outOfQuotaPolicy: OutOfQuotaPolicy? = nilOrValue(pigeonVar_list[8]) - - return OneOffTaskRequest( - uniqueName: uniqueName, - taskName: taskName, - inputData: inputData, - initialDelaySeconds: initialDelaySeconds, - constraints: constraints, - backoffPolicy: backoffPolicy, - tag: tag, - existingWorkPolicy: existingWorkPolicy, - outOfQuotaPolicy: outOfQuotaPolicy - ) - } - func toList() -> [Any?] { - return [ - uniqueName, - taskName, - inputData, - initialDelaySeconds, - constraints, - backoffPolicy, - tag, - existingWorkPolicy, - outOfQuotaPolicy - ] - } -} - -/// Generated class from Pigeon that represents data sent in messages. -struct PeriodicTaskRequest { - var uniqueName: String - var taskName: String - var frequencySeconds: Int64 - var flexIntervalSeconds: Int64? - var inputData: [String?: Any?]? - var initialDelaySeconds: Int64? - var constraints: Constraints? - var backoffPolicy: BackoffPolicyConfig? - var tag: String? - var existingWorkPolicy: ExistingWorkPolicy? - - // swift-format-ignore: AlwaysUseLowerCamelCase - static func fromList(_ pigeonVar_list: [Any?]) -> PeriodicTaskRequest? { - let uniqueName = pigeonVar_list[0] as! String - let taskName = pigeonVar_list[1] as! String - let frequencySeconds = pigeonVar_list[2] as! Int64 - let flexIntervalSeconds: Int64? = nilOrValue(pigeonVar_list[3]) - let inputData: [String?: Any?]? = nilOrValue(pigeonVar_list[4]) - let initialDelaySeconds: Int64? = nilOrValue(pigeonVar_list[5]) - let constraints: Constraints? = nilOrValue(pigeonVar_list[6]) - let backoffPolicy: BackoffPolicyConfig? = nilOrValue(pigeonVar_list[7]) - let tag: String? = nilOrValue(pigeonVar_list[8]) - let existingWorkPolicy: ExistingWorkPolicy? = nilOrValue(pigeonVar_list[9]) - - return PeriodicTaskRequest( - uniqueName: uniqueName, - taskName: taskName, - frequencySeconds: frequencySeconds, - flexIntervalSeconds: flexIntervalSeconds, - inputData: inputData, - initialDelaySeconds: initialDelaySeconds, - constraints: constraints, - backoffPolicy: backoffPolicy, - tag: tag, - existingWorkPolicy: existingWorkPolicy - ) - } - func toList() -> [Any?] { - return [ - uniqueName, - taskName, - frequencySeconds, - flexIntervalSeconds, - inputData, - initialDelaySeconds, - constraints, - backoffPolicy, - tag, - existingWorkPolicy - ] - } -} - -/// Generated class from Pigeon that represents data sent in messages. -struct ProcessingTaskRequest { - var uniqueName: String - var taskName: String - var inputData: [String?: Any?]? - var initialDelaySeconds: Int64? - var networkType: NetworkType? - var requiresCharging: Bool? - - // swift-format-ignore: AlwaysUseLowerCamelCase - static func fromList(_ pigeonVar_list: [Any?]) -> ProcessingTaskRequest? { - let uniqueName = pigeonVar_list[0] as! String - let taskName = pigeonVar_list[1] as! String - let inputData: [String?: Any?]? = nilOrValue(pigeonVar_list[2]) - let initialDelaySeconds: Int64? = nilOrValue(pigeonVar_list[3]) - let networkType: NetworkType? = nilOrValue(pigeonVar_list[4]) - let requiresCharging: Bool? = nilOrValue(pigeonVar_list[5]) - - return ProcessingTaskRequest( - uniqueName: uniqueName, - taskName: taskName, - inputData: inputData, - initialDelaySeconds: initialDelaySeconds, - networkType: networkType, - requiresCharging: requiresCharging - ) - } - func toList() -> [Any?] { - return [ - uniqueName, - taskName, - inputData, - initialDelaySeconds, - networkType, - requiresCharging - ] - } -} - -private class WorkmanagerApiPigeonCodecReader: FlutterStandardReader { - override func readValue(ofType type: UInt8) -> Any? { - switch type { - case 129: - let enumResultAsInt: Int? = nilOrValue(self.readValue() as! Int?) - if let enumResultAsInt = enumResultAsInt { - return NetworkType(rawValue: enumResultAsInt) - } - return nil - case 130: - let enumResultAsInt: Int? = nilOrValue(self.readValue() as! Int?) - if let enumResultAsInt = enumResultAsInt { - return BackoffPolicy(rawValue: enumResultAsInt) - } - return nil - case 131: - let enumResultAsInt: Int? = nilOrValue(self.readValue() as! Int?) - if let enumResultAsInt = enumResultAsInt { - return ExistingWorkPolicy(rawValue: enumResultAsInt) - } - return nil - case 132: - let enumResultAsInt: Int? = nilOrValue(self.readValue() as! Int?) - if let enumResultAsInt = enumResultAsInt { - return OutOfQuotaPolicy(rawValue: enumResultAsInt) - } - return nil - case 133: - return Constraints.fromList(self.readValue() as! [Any?]) - case 134: - return BackoffPolicyConfig.fromList(self.readValue() as! [Any?]) - case 135: - return InitializeRequest.fromList(self.readValue() as! [Any?]) - case 136: - return OneOffTaskRequest.fromList(self.readValue() as! [Any?]) - case 137: - return PeriodicTaskRequest.fromList(self.readValue() as! [Any?]) - case 138: - return ProcessingTaskRequest.fromList(self.readValue() as! [Any?]) - default: - return super.readValue(ofType: type) - } - } -} - -private class WorkmanagerApiPigeonCodecWriter: FlutterStandardWriter { - override func writeValue(_ value: Any) { - if let value = value as? NetworkType { - super.writeByte(129) - super.writeValue(value.rawValue) - } else if let value = value as? BackoffPolicy { - super.writeByte(130) - super.writeValue(value.rawValue) - } else if let value = value as? ExistingWorkPolicy { - super.writeByte(131) - super.writeValue(value.rawValue) - } else if let value = value as? OutOfQuotaPolicy { - super.writeByte(132) - super.writeValue(value.rawValue) - } else if let value = value as? Constraints { - super.writeByte(133) - super.writeValue(value.toList()) - } else if let value = value as? BackoffPolicyConfig { - super.writeByte(134) - super.writeValue(value.toList()) - } else if let value = value as? InitializeRequest { - super.writeByte(135) - super.writeValue(value.toList()) - } else if let value = value as? OneOffTaskRequest { - super.writeByte(136) - super.writeValue(value.toList()) - } else if let value = value as? PeriodicTaskRequest { - super.writeByte(137) - super.writeValue(value.toList()) - } else if let value = value as? ProcessingTaskRequest { - super.writeByte(138) - super.writeValue(value.toList()) - } else { - super.writeValue(value) - } - } -} - -private class WorkmanagerApiPigeonCodecReaderWriter: FlutterStandardReaderWriter { - override func reader(with data: Data) -> FlutterStandardReader { - return WorkmanagerApiPigeonCodecReader(data: data) - } - - override func writer(with data: NSMutableData) -> FlutterStandardWriter { - return WorkmanagerApiPigeonCodecWriter(data: data) - } -} - -class WorkmanagerApiPigeonCodec: FlutterStandardMessageCodec, @unchecked Sendable { - static let shared = WorkmanagerApiPigeonCodec(readerWriter: WorkmanagerApiPigeonCodecReaderWriter()) -} - -/// Generated protocol from Pigeon that represents a handler of messages from Flutter. -protocol WorkmanagerHostApi { - func initialize(request: InitializeRequest, completion: @escaping (Result) -> Void) - func registerOneOffTask(request: OneOffTaskRequest, completion: @escaping (Result) -> Void) - func registerPeriodicTask(request: PeriodicTaskRequest, completion: @escaping (Result) -> Void) - func registerProcessingTask(request: ProcessingTaskRequest, completion: @escaping (Result) -> Void) - func cancelByUniqueName(uniqueName: String, completion: @escaping (Result) -> Void) - func cancelByTag(tag: String, completion: @escaping (Result) -> Void) - func cancelAll(completion: @escaping (Result) -> Void) - func isScheduledByUniqueName(uniqueName: String, completion: @escaping (Result) -> Void) - func printScheduledTasks(completion: @escaping (Result) -> Void) -} - -/// Generated setup class from Pigeon to handle messages through the `binaryMessenger`. -class WorkmanagerHostApiSetup { - static var codec: FlutterStandardMessageCodec { WorkmanagerApiPigeonCodec.shared } - /// Sets up an instance of `WorkmanagerHostApi` to handle messages through the `binaryMessenger`. - static func setUp(binaryMessenger: FlutterBinaryMessenger, api: WorkmanagerHostApi?, messageChannelSuffix: String = "") { - let channelSuffix = messageChannelSuffix.count > 0 ? ".\(messageChannelSuffix)" : "" - let initializeChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.initialize\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - initializeChannel.setMessageHandler { message, reply in - let args = message as! [Any?] - let requestArg = args[0] as! InitializeRequest - api.initialize(request: requestArg) { result in - switch result { - case .success: - reply(wrapResult(nil)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - initializeChannel.setMessageHandler(nil) - } - let registerOneOffTaskChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.registerOneOffTask\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - registerOneOffTaskChannel.setMessageHandler { message, reply in - let args = message as! [Any?] - let requestArg = args[0] as! OneOffTaskRequest - api.registerOneOffTask(request: requestArg) { result in - switch result { - case .success: - reply(wrapResult(nil)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - registerOneOffTaskChannel.setMessageHandler(nil) - } - let registerPeriodicTaskChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.registerPeriodicTask\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - registerPeriodicTaskChannel.setMessageHandler { message, reply in - let args = message as! [Any?] - let requestArg = args[0] as! PeriodicTaskRequest - api.registerPeriodicTask(request: requestArg) { result in - switch result { - case .success: - reply(wrapResult(nil)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - registerPeriodicTaskChannel.setMessageHandler(nil) - } - let registerProcessingTaskChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.registerProcessingTask\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - registerProcessingTaskChannel.setMessageHandler { message, reply in - let args = message as! [Any?] - let requestArg = args[0] as! ProcessingTaskRequest - api.registerProcessingTask(request: requestArg) { result in - switch result { - case .success: - reply(wrapResult(nil)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - registerProcessingTaskChannel.setMessageHandler(nil) - } - let cancelByUniqueNameChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.cancelByUniqueName\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - cancelByUniqueNameChannel.setMessageHandler { message, reply in - let args = message as! [Any?] - let uniqueNameArg = args[0] as! String - api.cancelByUniqueName(uniqueName: uniqueNameArg) { result in - switch result { - case .success: - reply(wrapResult(nil)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - cancelByUniqueNameChannel.setMessageHandler(nil) - } - let cancelByTagChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.cancelByTag\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - cancelByTagChannel.setMessageHandler { message, reply in - let args = message as! [Any?] - let tagArg = args[0] as! String - api.cancelByTag(tag: tagArg) { result in - switch result { - case .success: - reply(wrapResult(nil)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - cancelByTagChannel.setMessageHandler(nil) - } - let cancelAllChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.cancelAll\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - cancelAllChannel.setMessageHandler { _, reply in - api.cancelAll { result in - switch result { - case .success: - reply(wrapResult(nil)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - cancelAllChannel.setMessageHandler(nil) - } - let isScheduledByUniqueNameChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.isScheduledByUniqueName\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - isScheduledByUniqueNameChannel.setMessageHandler { message, reply in - let args = message as! [Any?] - let uniqueNameArg = args[0] as! String - api.isScheduledByUniqueName(uniqueName: uniqueNameArg) { result in - switch result { - case .success(let res): - reply(wrapResult(res)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - isScheduledByUniqueNameChannel.setMessageHandler(nil) - } - let printScheduledTasksChannel = FlutterBasicMessageChannel(name: "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerHostApi.printScheduledTasks\(channelSuffix)", binaryMessenger: binaryMessenger, codec: codec) - if let api = api { - printScheduledTasksChannel.setMessageHandler { _, reply in - api.printScheduledTasks { result in - switch result { - case .success(let res): - reply(wrapResult(res)) - case .failure(let error): - reply(wrapError(error)) - } - } - } - } else { - printScheduledTasksChannel.setMessageHandler(nil) - } - } -} -/// Generated protocol from Pigeon that represents Flutter messages that can be called from Swift. -protocol WorkmanagerFlutterApiProtocol { - func backgroundChannelInitialized(completion: @escaping (Result) -> Void) - func executeTask(taskName taskNameArg: String, inputData inputDataArg: [String?: Any?]?, completion: @escaping (Result) -> Void) -} -class WorkmanagerFlutterApi: WorkmanagerFlutterApiProtocol { - private let binaryMessenger: FlutterBinaryMessenger - private let messageChannelSuffix: String - init(binaryMessenger: FlutterBinaryMessenger, messageChannelSuffix: String = "") { - self.binaryMessenger = binaryMessenger - self.messageChannelSuffix = messageChannelSuffix.count > 0 ? ".\(messageChannelSuffix)" : "" - } - var codec: WorkmanagerApiPigeonCodec { - return WorkmanagerApiPigeonCodec.shared - } - func backgroundChannelInitialized(completion: @escaping (Result) -> Void) { - let channelName: String = "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerFlutterApi.backgroundChannelInitialized\(messageChannelSuffix)" - let channel = FlutterBasicMessageChannel(name: channelName, binaryMessenger: binaryMessenger, codec: codec) - channel.sendMessage(nil) { response in - guard let listResponse = response as? [Any?] else { - completion(.failure(createConnectionError(withChannelName: channelName))) - return - } - if listResponse.count > 1 { - let code: String = listResponse[0] as! String - let message: String? = nilOrValue(listResponse[1]) - let details: String? = nilOrValue(listResponse[2]) - completion(.failure(PigeonError(code: code, message: message, details: details))) - } else { - completion(.success(Void())) - } - } - } - func executeTask(taskName taskNameArg: String, inputData inputDataArg: [String?: Any?]?, completion: @escaping (Result) -> Void) { - let channelName: String = "dev.flutter.pigeon.workmanager_platform_interface.WorkmanagerFlutterApi.executeTask\(messageChannelSuffix)" - let channel = FlutterBasicMessageChannel(name: channelName, binaryMessenger: binaryMessenger, codec: codec) - channel.sendMessage([taskNameArg, inputDataArg] as [Any?]) { response in - guard let listResponse = response as? [Any?] else { - completion(.failure(createConnectionError(withChannelName: channelName))) - return - } - if listResponse.count > 1 { - let code: String = listResponse[0] as! String - let message: String? = nilOrValue(listResponse[1]) - let details: String? = nilOrValue(listResponse[2]) - completion(.failure(PigeonError(code: code, message: message, details: details))) - } else if listResponse[0] == nil { - completion(.failure(PigeonError(code: "null-error", message: "Flutter api returned null value for non-null return value.", details: ""))) - } else { - let result = listResponse[0] as! Bool - completion(.success(result)) - } - } - } -} diff --git a/workmanager_platform_interface/lib/src/pigeon/workmanager_api.g.dart b/workmanager_platform_interface/lib/src/pigeon/workmanager_api.g.dart index 40f63a91..545dc53e 100644 --- a/workmanager_platform_interface/lib/src/pigeon/workmanager_api.g.dart +++ b/workmanager_platform_interface/lib/src/pigeon/workmanager_api.g.dart @@ -1,7 +1,7 @@ // // Copyright 2024 The Flutter Workmanager Authors. All rights reserved. // // Use of this source code is governed by a MIT-style license that can be // // found in the LICENSE file. -// Autogenerated from Pigeon (v22.7.4), do not edit directly. +// Autogenerated from Pigeon (v26.0.0), do not edit directly. // See also: https://pub.dev/packages/pigeon // ignore_for_file: public_member_api_docs, non_constant_identifier_names, avoid_as, unused_import, unnecessary_parenthesis, prefer_null_aware_operators, omit_local_variable_types, unused_shown_name, unnecessary_import, no_leading_underscores_for_local_identifiers @@ -27,6 +27,20 @@ List wrapResponse({Object? result, PlatformException? error, bool empty } return [error.code, error.message, error.details]; } +bool _deepEquals(Object? a, Object? b) { + if (a is List && b is List) { + return a.length == b.length && + a.indexed + .every(((int, dynamic) item) => _deepEquals(item.$2, b[item.$1])); + } + if (a is Map && b is Map) { + return a.length == b.length && a.entries.every((MapEntry entry) => + (b as Map).containsKey(entry.key) && + _deepEquals(entry.value, b[entry.key])); + } + return a == b; +} + /// An enumeration of various network types that can be used as Constraints for work. /// @@ -143,7 +157,7 @@ class Constraints { bool? requiresStorageNotLow; - Object encode() { + List _toList() { return [ networkType, requiresBatteryNotLow, @@ -153,6 +167,9 @@ class Constraints { ]; } + Object encode() { + return _toList(); } + static Constraints decode(Object result) { result as List; return Constraints( @@ -163,6 +180,23 @@ class Constraints { requiresStorageNotLow: result[4] as bool?, ); } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + bool operator ==(Object other) { + if (other is! Constraints || other.runtimeType != runtimeType) { + return false; + } + if (identical(this, other)) { + return true; + } + return _deepEquals(encode(), other.encode()); + } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + int get hashCode => Object.hashAll(_toList()) +; } class BackoffPolicyConfig { @@ -175,13 +209,16 @@ class BackoffPolicyConfig { int? backoffDelayMillis; - Object encode() { + List _toList() { return [ backoffPolicy, backoffDelayMillis, ]; } + Object encode() { + return _toList(); } + static BackoffPolicyConfig decode(Object result) { result as List; return BackoffPolicyConfig( @@ -189,6 +226,23 @@ class BackoffPolicyConfig { backoffDelayMillis: result[1] as int?, ); } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + bool operator ==(Object other) { + if (other is! BackoffPolicyConfig || other.runtimeType != runtimeType) { + return false; + } + if (identical(this, other)) { + return true; + } + return _deepEquals(encode(), other.encode()); + } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + int get hashCode => Object.hashAll(_toList()) +; } class InitializeRequest { @@ -201,13 +255,16 @@ class InitializeRequest { bool isInDebugMode; - Object encode() { + List _toList() { return [ callbackHandle, isInDebugMode, ]; } + Object encode() { + return _toList(); } + static InitializeRequest decode(Object result) { result as List; return InitializeRequest( @@ -215,6 +272,23 @@ class InitializeRequest { isInDebugMode: result[1]! as bool, ); } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + bool operator ==(Object other) { + if (other is! InitializeRequest || other.runtimeType != runtimeType) { + return false; + } + if (identical(this, other)) { + return true; + } + return _deepEquals(encode(), other.encode()); + } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + int get hashCode => Object.hashAll(_toList()) +; } class OneOffTaskRequest { @@ -248,7 +322,7 @@ class OneOffTaskRequest { OutOfQuotaPolicy? outOfQuotaPolicy; - Object encode() { + List _toList() { return [ uniqueName, taskName, @@ -262,6 +336,9 @@ class OneOffTaskRequest { ]; } + Object encode() { + return _toList(); } + static OneOffTaskRequest decode(Object result) { result as List; return OneOffTaskRequest( @@ -276,6 +353,23 @@ class OneOffTaskRequest { outOfQuotaPolicy: result[8] as OutOfQuotaPolicy?, ); } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + bool operator ==(Object other) { + if (other is! OneOffTaskRequest || other.runtimeType != runtimeType) { + return false; + } + if (identical(this, other)) { + return true; + } + return _deepEquals(encode(), other.encode()); + } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + int get hashCode => Object.hashAll(_toList()) +; } class PeriodicTaskRequest { @@ -312,7 +406,7 @@ class PeriodicTaskRequest { ExistingPeriodicWorkPolicy? existingWorkPolicy; - Object encode() { + List _toList() { return [ uniqueName, taskName, @@ -327,6 +421,9 @@ class PeriodicTaskRequest { ]; } + Object encode() { + return _toList(); } + static PeriodicTaskRequest decode(Object result) { result as List; return PeriodicTaskRequest( @@ -342,6 +439,23 @@ class PeriodicTaskRequest { existingWorkPolicy: result[9] as ExistingPeriodicWorkPolicy?, ); } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + bool operator ==(Object other) { + if (other is! PeriodicTaskRequest || other.runtimeType != runtimeType) { + return false; + } + if (identical(this, other)) { + return true; + } + return _deepEquals(encode(), other.encode()); + } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + int get hashCode => Object.hashAll(_toList()) +; } class ProcessingTaskRequest { @@ -366,7 +480,7 @@ class ProcessingTaskRequest { bool? requiresCharging; - Object encode() { + List _toList() { return [ uniqueName, taskName, @@ -377,6 +491,9 @@ class ProcessingTaskRequest { ]; } + Object encode() { + return _toList(); } + static ProcessingTaskRequest decode(Object result) { result as List; return ProcessingTaskRequest( @@ -388,6 +505,23 @@ class ProcessingTaskRequest { requiresCharging: result[5] as bool?, ); } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + bool operator ==(Object other) { + if (other is! ProcessingTaskRequest || other.runtimeType != runtimeType) { + return false; + } + if (identical(this, other)) { + return true; + } + return _deepEquals(encode(), other.encode()); + } + + @override + // ignore: avoid_equals_and_hash_code_on_mutable_classes + int get hashCode => Object.hashAll(_toList()) +; } @@ -492,8 +626,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send([request]); final List? pigeonVar_replyList = - await pigeonVar_channel.send([request]) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -514,8 +649,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send([request]); final List? pigeonVar_replyList = - await pigeonVar_channel.send([request]) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -536,8 +672,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send([request]); final List? pigeonVar_replyList = - await pigeonVar_channel.send([request]) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -558,8 +695,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send([request]); final List? pigeonVar_replyList = - await pigeonVar_channel.send([request]) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -580,8 +718,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send([uniqueName]); final List? pigeonVar_replyList = - await pigeonVar_channel.send([uniqueName]) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -602,8 +741,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send([tag]); final List? pigeonVar_replyList = - await pigeonVar_channel.send([tag]) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -624,8 +764,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send(null); final List? pigeonVar_replyList = - await pigeonVar_channel.send(null) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -646,8 +787,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send([uniqueName]); final List? pigeonVar_replyList = - await pigeonVar_channel.send([uniqueName]) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { @@ -673,8 +815,9 @@ class WorkmanagerHostApi { pigeonChannelCodec, binaryMessenger: pigeonVar_binaryMessenger, ); + final Future pigeonVar_sendFuture = pigeonVar_channel.send(null); final List? pigeonVar_replyList = - await pigeonVar_channel.send(null) as List?; + await pigeonVar_sendFuture as List?; if (pigeonVar_replyList == null) { throw _createConnectionError(pigeonVar_channelName); } else if (pigeonVar_replyList.length > 1) { diff --git a/workmanager_platform_interface/pubspec.yaml b/workmanager_platform_interface/pubspec.yaml index 9fd3b263..24ab3049 100644 --- a/workmanager_platform_interface/pubspec.yaml +++ b/workmanager_platform_interface/pubspec.yaml @@ -18,5 +18,5 @@ dependencies: dev_dependencies: flutter_lints: ^6.0.0 - pigeon: ^22.6.0 + pigeon: ^26.0.0 From e23ac3f9cce32c6ace298af3f5619888493be0b1 Mon Sep 17 00:00:00 2001 From: Sebastian Roth Date: Wed, 30 Jul 2025 11:16:51 +0100 Subject: [PATCH 2/6] fix: typo in CLAUDE.md and correct changelog entries - Fix typo in CLAUDE.md line 18 - Move dependency updates to correct changelog files - Remove incorrect BREAKING label from Pigeon update --- CLAUDE.md | 2 +- workmanager/CHANGELOG.md | 2 +- workmanager_platform_interface/CHANGELOG.md | 5 +++++ 3 files changed, 7 insertions(+), 2 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index aa9cd9a6..fb43274a 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -15,7 +15,7 @@ - Use melos to run all tests: `melos run test` - Or run tests in individual packages: - `cd workmanager_android && flutter test` - - `cd workmanager_apple && flutter test`you did just + - `cd workmanager_apple && flutter test` - `cd workmanager && flutter test` - Before running tests in workmanager package, ensure mocks are up-to-date: `melos run generate:dart` diff --git a/workmanager/CHANGELOG.md b/workmanager/CHANGELOG.md index 5b9a3047..0599d4c6 100644 --- a/workmanager/CHANGELOG.md +++ b/workmanager/CHANGELOG.md @@ -1,7 +1,7 @@ # Future ## Dependencies & Infrastructure Updates -* **BREAKING**: Updated Pigeon from 22.7.4 to 26.0.0 for enhanced multi-platform support +* Updated Pigeon from 22.7.4 to 26.0.0 for enhanced multi-platform support * Updated androidx.work from 2.9.0 to 2.10.2 with improved Flow-based observability and precise periodic scheduling * Updated permission_handler in example app from 11.3.1 to 12.0.1 * Updated dev dependencies for better compatibility diff --git a/workmanager_platform_interface/CHANGELOG.md b/workmanager_platform_interface/CHANGELOG.md index 5a2bb152..3dce3547 100644 --- a/workmanager_platform_interface/CHANGELOG.md +++ b/workmanager_platform_interface/CHANGELOG.md @@ -1,5 +1,10 @@ ## Future +### Dependencies & Infrastructure Updates +* Updated Pigeon from 22.7.4 to 26.0.0 for enhanced multi-platform support +* Regenerated platform interface files with new Pigeon version +* Fixed Kotlin null safety issues compatibility + ### Breaking Changes * **BREAKING**: Separate `ExistingWorkPolicy` and `ExistingPeriodicWorkPolicy` enums for better type safety * Mirrors Android's native WorkManager API design From 56a8023c5f9cfc39322aa70ea25c53f16dddd7ac Mon Sep 17 00:00:00 2001 From: Sebastian Roth Date: Wed, 30 Jul 2025 11:19:27 +0100 Subject: [PATCH 3/6] fix: remove irrelevant Kotlin reference from platform_interface changelog The platform_interface package is pure Dart and doesn't involve Kotlin --- workmanager_platform_interface/CHANGELOG.md | 1 - 1 file changed, 1 deletion(-) diff --git a/workmanager_platform_interface/CHANGELOG.md b/workmanager_platform_interface/CHANGELOG.md index 3dce3547..6d18d9fc 100644 --- a/workmanager_platform_interface/CHANGELOG.md +++ b/workmanager_platform_interface/CHANGELOG.md @@ -3,7 +3,6 @@ ### Dependencies & Infrastructure Updates * Updated Pigeon from 22.7.4 to 26.0.0 for enhanced multi-platform support * Regenerated platform interface files with new Pigeon version -* Fixed Kotlin null safety issues compatibility ### Breaking Changes * **BREAKING**: Separate `ExistingWorkPolicy` and `ExistingPeriodicWorkPolicy` enums for better type safety From fa600c9ceb12aa71bd76ce83e47b644b5b2887d4 Mon Sep 17 00:00:00 2001 From: Sebastian Roth Date: Wed, 30 Jul 2025 11:20:34 +0100 Subject: [PATCH 4/6] docs: update Android and Apple package changelogs - Add dependency updates to workmanager_android changelog (androidx.work 2.10.2, Kotlin fixes) - Add Pigeon file regeneration to workmanager_apple changelog - Ensure all packages with changes have updated changelogs --- workmanager_android/CHANGELOG.md | 5 +++++ workmanager_apple/CHANGELOG.md | 3 +++ 2 files changed, 8 insertions(+) diff --git a/workmanager_android/CHANGELOG.md b/workmanager_android/CHANGELOG.md index 6228321f..cfe32e0b 100644 --- a/workmanager_android/CHANGELOG.md +++ b/workmanager_android/CHANGELOG.md @@ -1,5 +1,10 @@ ## Future +### Dependencies & Infrastructure Updates +* Updated androidx.work from 2.9.0 to 2.10.2 with improved Flow-based observability +* Fixed Kotlin null safety issues with androidx.work 2.10.2 type system improvements +* Regenerated Pigeon files with updated version 26.0.0 + ### Breaking Changes * **BREAKING**: Update `registerPeriodicTask` to use `ExistingPeriodicWorkPolicy` instead of `ExistingWorkPolicy` * This provides better type safety and mirrors Android's native API diff --git a/workmanager_apple/CHANGELOG.md b/workmanager_apple/CHANGELOG.md index 61af2b73..63d34116 100644 --- a/workmanager_apple/CHANGELOG.md +++ b/workmanager_apple/CHANGELOG.md @@ -1,5 +1,8 @@ ## Future +### Dependencies & Infrastructure Updates +* Regenerated Pigeon files with updated version 26.0.0 for enhanced multi-platform support + ### Breaking Changes * **BREAKING**: Update `registerPeriodicTask` to use `ExistingPeriodicWorkPolicy` instead of `ExistingWorkPolicy` * This provides better type safety across all platforms From 98f2527e330082008f1eb796ea9b157b619d22b4 Mon Sep 17 00:00:00 2001 From: Sebastian Roth Date: Wed, 30 Jul 2025 11:21:44 +0100 Subject: [PATCH 5/6] docs: clean up main workmanager changelog Remove internal dependency update details from main package changelog. Keep focused on user-facing changes only - dependency updates are documented in the specific platform packages where they matter. --- workmanager/CHANGELOG.md | 7 ------- 1 file changed, 7 deletions(-) diff --git a/workmanager/CHANGELOG.md b/workmanager/CHANGELOG.md index 0599d4c6..2629438b 100644 --- a/workmanager/CHANGELOG.md +++ b/workmanager/CHANGELOG.md @@ -1,12 +1,5 @@ # Future -## Dependencies & Infrastructure Updates -* Updated Pigeon from 22.7.4 to 26.0.0 for enhanced multi-platform support -* Updated androidx.work from 2.9.0 to 2.10.2 with improved Flow-based observability and precise periodic scheduling -* Updated permission_handler in example app from 11.3.1 to 12.0.1 -* Updated dev dependencies for better compatibility -* Fixed Kotlin null safety issues with androidx.work 2.10.2 type system improvements - ## Breaking Changes * **BREAKING**: Separate `ExistingWorkPolicy` and `ExistingPeriodicWorkPolicy` enums for better type safety and API clarity * `registerPeriodicTask` now requires `ExistingPeriodicWorkPolicy` instead of `ExistingWorkPolicy` From 07fceeedb05b10015d8817026a7fbae095947ac8 Mon Sep 17 00:00:00 2001 From: Sebastian Roth Date: Wed, 30 Jul 2025 11:23:30 +0100 Subject: [PATCH 6/6] docs: remove internal implementation details from changelog - Remove Kotlin null safety fix details from Android changelog (users don't care about internal fixes) - Add changelog guidelines to CLAUDE.md emphasizing user-focused content only - Changelogs should document what matters to end users, not AI debugging process --- CLAUDE.md | 9 ++++++++- workmanager_android/CHANGELOG.md | 1 - 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index fb43274a..3f7f9327 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -25,4 +25,11 @@ - **Test edge cases**: null inputs, error conditions, boundary values ## Complex Component Testing -- **BackgroundWorker**: Cannot be unit tested due to Flutter engine dependencies - use integration tests \ No newline at end of file +- **BackgroundWorker**: Cannot be unit tested due to Flutter engine dependencies - use integration tests + +## Changelog Guidelines +- **User-focused content only**: Write from end user perspective, not internal implementation details +- **No AI agent progress**: Don't document debugging steps, build fixes, or internal development process +- **What matters to users**: Breaking changes, new features, bug fixes that affect their code +- **Example of bad changelog entry**: "Fixed Kotlin null safety issues with androidx.work 2.10.2 type system improvements" +- **Example of good changelog entry**: "Fixed periodic tasks not respecting frequency changes" \ No newline at end of file diff --git a/workmanager_android/CHANGELOG.md b/workmanager_android/CHANGELOG.md index cfe32e0b..57d9bfca 100644 --- a/workmanager_android/CHANGELOG.md +++ b/workmanager_android/CHANGELOG.md @@ -2,7 +2,6 @@ ### Dependencies & Infrastructure Updates * Updated androidx.work from 2.9.0 to 2.10.2 with improved Flow-based observability -* Fixed Kotlin null safety issues with androidx.work 2.10.2 type system improvements * Regenerated Pigeon files with updated version 26.0.0 ### Breaking Changes