From 25d7fe0a8e4eb0d7e7ce5563c6e5d9bb474c2cf1 Mon Sep 17 00:00:00 2001 From: Alexander Nozik Date: Thu, 25 May 2023 09:51:27 +0300 Subject: [PATCH] Update actions signatures to avoid unnecessary nulls --- .../kscience/controls/spec/DeviceBase.kt | 6 +++--- .../controls/spec/DevicePropertySpec.kt | 9 ++++++--- .../kscience/controls/spec/DeviceSpec.kt | 20 ++++++++++++------- .../kscience/controls/demo/DemoDevice.kt | 3 +-- 4 files changed, 23 insertions(+), 15 deletions(-) diff --git a/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceBase.kt b/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceBase.kt index 0f5436b..034485f 100644 --- a/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceBase.kt +++ b/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceBase.kt @@ -25,9 +25,9 @@ private suspend fun DevicePropertySpec.readMeta(device: D) private suspend fun DeviceActionSpec.executeWithMeta( device: D, - item: Meta?, + item: Meta, ): Meta? { - val arg = item?.let { inputConverter.metaToObject(item) } + val arg: I = inputConverter.metaToObject(item) ?: error("Failed to convert $item with $inputConverter") val res = execute(device, arg) return res?.let { outputConverter.objectToMeta(res) } } @@ -146,7 +146,7 @@ public abstract class DeviceBase( override suspend fun execute(actionName: String, argument: Meta?): Meta? { val spec = actions[actionName] ?: error("Action with name $actionName not found") - return spec.executeWithMeta(self, argument) + return spec.executeWithMeta(self, argument ?: Meta.EMPTY) } } diff --git a/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DevicePropertySpec.kt b/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DevicePropertySpec.kt index 0e72fca..ce83edc 100644 --- a/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DevicePropertySpec.kt +++ b/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DevicePropertySpec.kt @@ -66,7 +66,7 @@ public interface DeviceActionSpec { /** * Execute action on a device */ - public suspend fun execute(device: D, input: I?): O? + public suspend fun execute(device: D, input: I): O } /** @@ -137,5 +137,8 @@ public suspend fun D.invalidate(propertySpec: DevicePropertySpec D.execute(actionSpec: DeviceActionSpec, input: I? = null): O? = - actionSpec.execute(this, input) \ No newline at end of file +public suspend fun D.execute(actionSpec: DeviceActionSpec, input: I): O = + actionSpec.execute(this, input) + +public suspend fun D.execute(actionSpec: DeviceActionSpec): O = + actionSpec.execute(this, Unit) \ No newline at end of file diff --git a/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceSpec.kt b/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceSpec.kt index eb5c978..ff7dddd 100644 --- a/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceSpec.kt +++ b/controls-core/src/commonMain/kotlin/space/kscience/controls/spec/DeviceSpec.kt @@ -12,6 +12,13 @@ import kotlin.reflect.KMutableProperty1 import kotlin.reflect.KProperty import kotlin.reflect.KProperty1 +public object UnitMetaConverter: MetaConverter{ + override fun metaToObject(meta: Meta): Unit = Unit + + override fun objectToMeta(obj: Unit): Meta = Meta.EMPTY +} + +public val MetaConverter.Companion.unit: MetaConverter get() = UnitMetaConverter @OptIn(InternalDeviceAPI::class) public abstract class DeviceSpec { @@ -165,7 +172,7 @@ public abstract class DeviceSpec { outputConverter: MetaConverter, descriptorBuilder: ActionDescriptor.() -> Unit = {}, name: String? = null, - execute: suspend D.(I?) -> O?, + execute: suspend D.(I) -> O, ): PropertyDelegateProvider, ReadOnlyProperty, DeviceActionSpec>> = PropertyDelegateProvider { _: DeviceSpec, property -> val actionName = name ?: property.name @@ -175,7 +182,7 @@ public abstract class DeviceSpec { override val inputConverter: MetaConverter = inputConverter override val outputConverter: MetaConverter = outputConverter - override suspend fun execute(device: D, input: I?): O? = withContext(device.coroutineContext) { + override suspend fun execute(device: D, input: I): O = withContext(device.coroutineContext) { device.execute(input) } } @@ -191,7 +198,7 @@ public abstract class DeviceSpec { public fun metaAction( descriptorBuilder: ActionDescriptor.() -> Unit = {}, name: String? = null, - execute: suspend D.(Meta?) -> Meta?, + execute: suspend D.(Meta) -> Meta, ): PropertyDelegateProvider, ReadOnlyProperty, DeviceActionSpec>> = action( MetaConverter.Companion.meta, @@ -209,15 +216,14 @@ public abstract class DeviceSpec { descriptorBuilder: ActionDescriptor.() -> Unit = {}, name: String? = null, execute: suspend D.() -> Unit, - ): PropertyDelegateProvider, ReadOnlyProperty, DeviceActionSpec>> = + ): PropertyDelegateProvider, ReadOnlyProperty, DeviceActionSpec>> = action( - MetaConverter.Companion.meta, - MetaConverter.Companion.meta, + MetaConverter.Companion.unit, + MetaConverter.Companion.unit, descriptorBuilder, name ) { execute() - null } } diff --git a/demo/all-things/src/main/kotlin/space/kscience/controls/demo/DemoDevice.kt b/demo/all-things/src/main/kotlin/space/kscience/controls/demo/DemoDevice.kt index 37b7b4b..dd65b78 100644 --- a/demo/all-things/src/main/kotlin/space/kscience/controls/demo/DemoDevice.kt +++ b/demo/all-things/src/main/kotlin/space/kscience/controls/demo/DemoDevice.kt @@ -68,11 +68,10 @@ class DemoDevice(context: Context, meta: Meta) : DeviceBySpec(Compa } - val resetScale by action(MetaConverter.meta, MetaConverter.meta) { + val resetScale by unitAction { write(timeScale, 5000.0) write(sinScale, 1.0) write(cosScale, 1.0) - null } override suspend fun IDemoDevice.onOpen() {