diff --git a/hll/dynamodb-mapper/dynamodb-mapper-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/model/MapperTypes.kt b/hll/dynamodb-mapper/dynamodb-mapper-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/model/MapperTypes.kt index 06860dbf113..64ed31b5d31 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/model/MapperTypes.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/model/MapperTypes.kt @@ -84,69 +84,69 @@ public object MapperTypes { public object Values { public fun valueConverter(value: Type): TypeRef = TypeRef(MapperPkg.Hl.Values, "ValueConverter", genericArgs = listOf(value)) public val ItemToValueConverter: TypeRef = TypeRef(MapperPkg.Hl.Values, "ItemToValueConverter") - public val NullableConverter: TypeRef = TypeRef(MapperPkg.Hl.Values, "NullableConverter") + public val NullableValueConverter: TypeRef = TypeRef(MapperPkg.Hl.Values, "NullableValueConverter") public object Collections { - public val ListConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "ListConverter") - public val MapConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "MapConverter") - - public val StringSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "StringSetConverter") - public val CharSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "CharSetConverter") - public val CharArraySetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "CharArraySetConverter") - - public val ByteSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "ByteSetConverter") - public val DoubleSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "DoubleSetConverter") - public val FloatSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "FloatSetConverter") - public val IntSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "IntSetConverter") - public val LongSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "LongSetConverter") - public val ShortSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "ShortSetConverter") - - public val UByteSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "UByteSetConverter") - public val UIntSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "UIntSetConverter") - public val ULongSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "ULongSetConverter") - public val UShortSetConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "UShortSetConverter") + public val ListValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "ListValueConverter") + public val MapValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "MapValueConverter") + + public val StringSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "StringSetValueConverter") + public val CharSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "CharSetValueConverter") + public val CharArraySetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "CharArraySetValueConverter") + + public val ByteSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.Byte") + public val DoubleSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.Double") + public val FloatSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.Float") + public val IntSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.Int") + public val LongSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.Long") + public val ShortSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.Short") + + public val UByteSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.UByte") + public val UIntSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.UInt") + public val ULongSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.ULong") + public val UShortSetValueConverter: TypeRef = TypeRef(MapperPkg.Hl.CollectionValues, "NumberSetValueConverters.UShort") } public object Scalars { - public fun enumConverter(enumType: Type): TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "EnumConverter", genericArgs = listOf(enumType)) - - public val BooleanConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "BooleanConverter") - public val StringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "StringConverter") - public val CharConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "CharConverter") - public val CharArrayConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "CharArrayConverter") - - public val ByteConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "ByteConverter") - public val ByteArrayConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "ByteArrayConverter") - public val DoubleConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "DoubleConverter") - public val FloatConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "FloatConverter") - public val IntConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "IntConverter") - public val LongConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "LongConverter") - public val ShortConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "ShortConverter") - public val UByteConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "UByteConverter") - public val UIntConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "UIntConverter") - public val ULongConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "ULongConverter") - public val UShortConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "UShortConverter") + public fun enumValueConverter(enumType: Type): TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "EnumValueConverter", genericArgs = listOf(enumType)) + + public val BooleanValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "BooleanValueConverter") + public val ByteArrayValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "ByteArrayValueConverter") + public val StringValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "StringValueConverter") + public val CharValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "CharValueConverter") + public val CharArrayValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "CharArrayValueConverter") + + public val ByteValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.Byte") + public val DoubleValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.Double") + public val FloatValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.Float") + public val IntValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.Int") + public val LongValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.Long") + public val ShortValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.Short") + public val UByteValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.UByte") + public val UIntValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.UInt") + public val ULongValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.ULong") + public val UShortValueConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberValueConverters.UShort") public val BooleanToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "BooleanToStringConverter") - public val CharArrayToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "TextConverters.CharArrayToStringConverter") - public val CharToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "TextConverters.CharToStringConverter") - public val StringToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "TextConverters.StringToStringConverter") - public val ByteToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.ByteToStringConverter") - public val DoubleToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.DoubleToStringConverter") - public val FloatToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.FloatToStringConverter") - public val IntToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.IntToStringConverter") - public val LongToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.LongToStringConverter") - public val ShortToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.ShortToStringConverter") - public val UByteToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.UByteToStringConverter") - public val UIntToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.UIntToStringConverter") - public val ULongToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.ULongToStringConverter") - public val UShortToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberConverters.UShortToStringConverter") + public val CharArrayToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "TextConverters.CharArrayToString") + public val CharToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "TextConverters.CharToString") + public val StringToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "TextConverters.String") + public val ByteToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.Byte") + public val DoubleToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.Double") + public val FloatToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.Float") + public val IntToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.Int") + public val LongToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.Long") + public val ShortToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.Short") + public val UByteToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.UByte") + public val UIntToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.UInt") + public val ULongToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.ULong") + public val UShortToStringConverter: TypeRef = TypeRef(MapperPkg.Hl.ScalarValues, "NumberToStringConverters.UShort") } public object SmithyTypes { - public val DefaultInstantConverter: TypeRef = TypeRef(MapperPkg.Hl.SmithyTypeValues, "InstantConverter.Default") - public val UrlConverter: TypeRef = TypeRef(MapperPkg.Hl.SmithyTypeValues, "UrlConverter") - public val DefaultDocumentConverter: TypeRef = TypeRef(MapperPkg.Hl.SmithyTypeValues, "DocumentConverter.Default") + public val DefaultInstantValueConverter: TypeRef = TypeRef(MapperPkg.Hl.SmithyTypeValues, "InstantValueConverter.Default") + public val UrlValueConverter: TypeRef = TypeRef(MapperPkg.Hl.SmithyTypeValues, "UrlValueConverter") + public val DefaultDocumentValueConverter: TypeRef = TypeRef(MapperPkg.Hl.SmithyTypeValues, "DocumentValueConverter.Default") } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper-ops-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/operations/rendering/OperationRenderer.kt b/hll/dynamodb-mapper/dynamodb-mapper-ops-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/operations/rendering/OperationRenderer.kt index 900aee48df4..0a6adf391c8 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-ops-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/operations/rendering/OperationRenderer.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-ops-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/operations/rendering/OperationRenderer.kt @@ -106,17 +106,17 @@ internal class OperationRenderer( requestMembers(MemberCodegenBehavior.PassThrough) { write("#L = this@convert.#L", name, highLevel.name) } requestMembers(MemberCodegenBehavior.MapKeys) { write( - "this@convert.#L?.let { #L = schema.converter.convertTo(it, schema.keyAttributeNames).#T(schema.keyAttributeNames) }", + "this@convert.#L?.let { #L = schema.converter.convertRight(it).#T(schema.keyAttributeNames) }", highLevel.name, name, MapperTypes.Model.intersectKeys, ) } requestMembers(MemberCodegenBehavior.MapAll) { - write("this@convert.#L?.let { #L = schema.converter.convertTo(it) }", highLevel.name, name) + write("this@convert.#L?.let { #L = schema.converter.convertRight(it) }", highLevel.name, name) } requestMembers(MemberCodegenBehavior.ListMapAll) { - write("#L = this@convert.#L?.map { schema.converter.convertTo(it) }", name, highLevel.name) + write("#L = this@convert.#L?.map { schema.converter.convertRight(it) }", name, highLevel.name) } requestMembers(MemberCodegenBehavior.Hoist) { write("this.#1L = #1L", name) } @@ -168,7 +168,7 @@ internal class OperationRenderer( responseMembers(MemberCodegenBehavior.MapKeys, MemberCodegenBehavior.MapAll) { write( - "#L = this@convert.#L?.#T()?.let(schema.converter::convertFrom)", + "#L = this@convert.#L?.#T()?.let(schema.converter::convertLeft)", highLevel.name, name, MapperTypes.Model.toItem, @@ -177,7 +177,7 @@ internal class OperationRenderer( responseMembers(MemberCodegenBehavior.ListMapAll) { write( - "#L = this@convert.#L?.map { schema.converter.convertFrom(it.#T()) }", + "#L = this@convert.#L?.map { schema.converter.convertLeft(it.#T()) }", highLevel.name, name, MapperTypes.Model.toItem, diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/annotations/rendering/SchemaRenderer.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/annotations/rendering/SchemaRenderer.kt index 194a5266d48..9ee874a4009 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/annotations/rendering/SchemaRenderer.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-codegen/src/main/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/codegen/annotations/rendering/SchemaRenderer.kt @@ -5,7 +5,9 @@ package aws.sdk.kotlin.hll.dynamodbmapper.codegen.annotations.rendering import aws.sdk.kotlin.hll.codegen.model.* -import aws.sdk.kotlin.hll.codegen.rendering.* +import aws.sdk.kotlin.hll.codegen.rendering.BuilderRenderer +import aws.sdk.kotlin.hll.codegen.rendering.RenderContext +import aws.sdk.kotlin.hll.codegen.rendering.RendererBase import aws.sdk.kotlin.hll.codegen.util.visibility import aws.sdk.kotlin.hll.dynamodbmapper.* import aws.sdk.kotlin.hll.dynamodbmapper.codegen.annotations.AnnotationsProcessorOptions @@ -176,19 +178,19 @@ internal class SchemaRenderer( when { type.nullable -> { - writeInline("#T(", MapperTypes.Values.NullableConverter) + writeInline("#T(", MapperTypes.Values.NullableValueConverter) renderValueConverter(ksType.makeNotNullable()) writeInline(")") } - ksType.isEnum -> writeInline("#T()", MapperTypes.Values.Scalars.enumConverter(type)) + ksType.isEnum -> writeInline("#T()", MapperTypes.Values.Scalars.enumValueConverter(type)) // FIXME Handle multi-module codegen rather than assuming nested classes will be in the same [ctx.pkg] ksType.isUserClass -> writeInline("#T", TypeRef(ctx.pkg, "${ksType.declaration.simpleName.asString()}ValueConverter")) type.isGenericFor(Types.Kotlin.Collections.List) -> { val listElementType = ksType.singleArgument() - writeInline("#T(", MapperTypes.Values.Collections.ListConverter) + writeInline("#T(", MapperTypes.Values.Collections.ListValueConverter) renderValueConverter(listElementType) writeInline(")") } @@ -200,7 +202,7 @@ internal class SchemaRenderer( checkNotNull(it.type?.resolve()) { "Failed to resolved argument type for $it" } } - writeInline("#T(#T, ", MapperTypes.Values.Collections.MapConverter, keyType.mapKeyConverter) + writeInline("#T(#T, ", MapperTypes.Values.Collections.MapValueConverter, keyType.mapKeyConverter) renderValueConverter(valueType) writeInline(")") } @@ -210,25 +212,25 @@ internal class SchemaRenderer( else -> writeInline( "#T", when (type) { - Types.Smithy.Instant -> MapperTypes.Values.SmithyTypes.DefaultInstantConverter - Types.Smithy.Url -> MapperTypes.Values.SmithyTypes.UrlConverter - Types.Smithy.Document -> MapperTypes.Values.SmithyTypes.DefaultDocumentConverter - - Types.Kotlin.Boolean -> MapperTypes.Values.Scalars.BooleanConverter - Types.Kotlin.String -> MapperTypes.Values.Scalars.StringConverter - Types.Kotlin.CharArray -> MapperTypes.Values.Scalars.CharArrayConverter - Types.Kotlin.Char -> MapperTypes.Values.Scalars.CharConverter - Types.Kotlin.Byte -> MapperTypes.Values.Scalars.ByteConverter - Types.Kotlin.ByteArray -> MapperTypes.Values.Scalars.ByteArrayConverter - Types.Kotlin.Short -> MapperTypes.Values.Scalars.ShortConverter - Types.Kotlin.Int -> MapperTypes.Values.Scalars.IntConverter - Types.Kotlin.Long -> MapperTypes.Values.Scalars.LongConverter - Types.Kotlin.Double -> MapperTypes.Values.Scalars.DoubleConverter - Types.Kotlin.Float -> MapperTypes.Values.Scalars.FloatConverter - Types.Kotlin.UByte -> MapperTypes.Values.Scalars.UByteConverter - Types.Kotlin.UInt -> MapperTypes.Values.Scalars.UIntConverter - Types.Kotlin.UShort -> MapperTypes.Values.Scalars.UShortConverter - Types.Kotlin.ULong -> MapperTypes.Values.Scalars.ULongConverter + Types.Smithy.Instant -> MapperTypes.Values.SmithyTypes.DefaultInstantValueConverter + Types.Smithy.Url -> MapperTypes.Values.SmithyTypes.UrlValueConverter + Types.Smithy.Document -> MapperTypes.Values.SmithyTypes.DefaultDocumentValueConverter + + Types.Kotlin.Boolean -> MapperTypes.Values.Scalars.BooleanValueConverter + Types.Kotlin.String -> MapperTypes.Values.Scalars.StringValueConverter + Types.Kotlin.CharArray -> MapperTypes.Values.Scalars.CharArrayValueConverter + Types.Kotlin.Char -> MapperTypes.Values.Scalars.CharValueConverter + Types.Kotlin.Byte -> MapperTypes.Values.Scalars.ByteValueConverter + Types.Kotlin.ByteArray -> MapperTypes.Values.Scalars.ByteArrayValueConverter + Types.Kotlin.Short -> MapperTypes.Values.Scalars.ShortValueConverter + Types.Kotlin.Int -> MapperTypes.Values.Scalars.IntValueConverter + Types.Kotlin.Long -> MapperTypes.Values.Scalars.LongValueConverter + Types.Kotlin.Double -> MapperTypes.Values.Scalars.DoubleValueConverter + Types.Kotlin.Float -> MapperTypes.Values.Scalars.FloatValueConverter + Types.Kotlin.UByte -> MapperTypes.Values.Scalars.UByteValueConverter + Types.Kotlin.UInt -> MapperTypes.Values.Scalars.UIntValueConverter + Types.Kotlin.UShort -> MapperTypes.Values.Scalars.UShortValueConverter + Types.Kotlin.ULong -> MapperTypes.Values.Scalars.ULongValueConverter else -> error("Unsupported attribute type $type") }, @@ -266,19 +268,19 @@ internal class SchemaRenderer( private val KSType.setValueConverter: Type get() = when (Type.from(this)) { - Types.Kotlin.String -> MapperTypes.Values.Collections.StringSetConverter - Types.Kotlin.Char -> MapperTypes.Values.Collections.CharSetConverter - Types.Kotlin.CharArray -> MapperTypes.Values.Collections.CharArraySetConverter - Types.Kotlin.Byte -> MapperTypes.Values.Collections.ByteSetConverter - Types.Kotlin.Double -> MapperTypes.Values.Collections.DoubleSetConverter - Types.Kotlin.Float -> MapperTypes.Values.Collections.FloatSetConverter - Types.Kotlin.Int -> MapperTypes.Values.Collections.IntSetConverter - Types.Kotlin.Long -> MapperTypes.Values.Collections.LongSetConverter - Types.Kotlin.Short -> MapperTypes.Values.Collections.ShortSetConverter - Types.Kotlin.UByte -> MapperTypes.Values.Collections.UByteSetConverter - Types.Kotlin.UInt -> MapperTypes.Values.Collections.UIntSetConverter - Types.Kotlin.ULong -> MapperTypes.Values.Collections.ULongSetConverter - Types.Kotlin.UShort -> MapperTypes.Values.Collections.UShortSetConverter + Types.Kotlin.String -> MapperTypes.Values.Collections.StringSetValueConverter + Types.Kotlin.Char -> MapperTypes.Values.Collections.CharSetValueConverter + Types.Kotlin.CharArray -> MapperTypes.Values.Collections.CharArraySetValueConverter + Types.Kotlin.Byte -> MapperTypes.Values.Collections.ByteSetValueConverter + Types.Kotlin.Double -> MapperTypes.Values.Collections.DoubleSetValueConverter + Types.Kotlin.Float -> MapperTypes.Values.Collections.FloatSetValueConverter + Types.Kotlin.Int -> MapperTypes.Values.Collections.IntSetValueConverter + Types.Kotlin.Long -> MapperTypes.Values.Collections.LongSetValueConverter + Types.Kotlin.Short -> MapperTypes.Values.Collections.ShortSetValueConverter + Types.Kotlin.UByte -> MapperTypes.Values.Collections.UByteSetValueConverter + Types.Kotlin.UInt -> MapperTypes.Values.Collections.UIntSetValueConverter + Types.Kotlin.ULong -> MapperTypes.Values.Collections.ULongSetValueConverter + Types.Kotlin.UShort -> MapperTypes.Values.Collections.UShortSetValueConverter else -> error("Unsupported set element $this") } diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/plugins/SchemaGeneratorPluginTest.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/plugins/SchemaGeneratorPluginTest.kt index ac261b9fb4f..98b5eaaba4d 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/plugins/SchemaGeneratorPluginTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/kotlin/aws/sdk/kotlin/hll/dynamodbmapper/plugins/SchemaGeneratorPluginTest.kt @@ -110,25 +110,25 @@ class SchemaGeneratorPluginTest { "id", User::id, UserBuilder::id::set, - IntConverter, + NumberValueConverters.Int, ), AttributeDescriptor( "fName", User::givenName, UserBuilder::givenName::set, - StringConverter, + StringValueConverter, ), AttributeDescriptor( "lName", User::surname, UserBuilder::surname::set, - StringConverter, + StringValueConverter, ), AttributeDescriptor( "age", User::age, UserBuilder::age::set, - IntConverter, + NumberValueConverters.Int, ), ), ) @@ -141,7 +141,7 @@ class SchemaGeneratorPluginTest { """ object UserSchema : ItemSchema.PartitionKey { override val converter: UserConverter = UserConverter - override val partitionKey: KeySpec = aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec.Number("id") + override val partitionKey: KeySpec = KeySpec.Number("id") } """.trimIndent(), ) @@ -177,25 +177,25 @@ class SchemaGeneratorPluginTest { "id", BuilderNotRequired::id, BuilderNotRequired::id::set, - IntConverter, + NumberValueConverters.Int, ), AttributeDescriptor( "fName", BuilderNotRequired::givenName, BuilderNotRequired::givenName::set, - StringConverter, + StringValueConverter, ), AttributeDescriptor( "lName", BuilderNotRequired::surname, BuilderNotRequired::surname::set, - StringConverter, + StringValueConverter, ), AttributeDescriptor( "age", BuilderNotRequired::age, BuilderNotRequired::age::set, - IntConverter, + NumberValueConverters.Int, ), ), ) @@ -419,7 +419,7 @@ class SchemaGeneratorPluginTest { """ public object CustomUserSchema : ItemSchema.PartitionKey { override val converter: MyCustomUserConverter = MyCustomUserConverter - override val partitionKey: KeySpec = aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec.Number("id") + override val partitionKey: KeySpec = KeySpec.Number("id") } """.trimIndent(), ) @@ -575,7 +575,7 @@ class SchemaGeneratorPluginTest { """ object RenamedPartitionKeySchema : ItemSchema.PartitionKey { override val converter: RenamedPartitionKeyConverter = RenamedPartitionKeyConverter - override val partitionKey: KeySpec = aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec.Number("user_id") + override val partitionKey: KeySpec = KeySpec.Number("user_id") } """.trimIndent(), ) diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/custom-item-converter/CustomItemConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/custom-item-converter/CustomItemConverter.kt index 0cbe80001a2..84e5706873c 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/custom-item-converter/CustomItemConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/custom-item-converter/CustomItemConverter.kt @@ -8,8 +8,8 @@ package my.custom.item.converter import aws.sdk.kotlin.hll.dynamodbmapper.items.AttributeDescriptor import aws.sdk.kotlin.hll.dynamodbmapper.items.ItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import aws.smithy.kotlin.runtime.ExperimentalApi import org.example.CustomUser @@ -22,25 +22,25 @@ public object MyCustomUserConverter : ItemConverter by SimpleItemCon "id", CustomUser::id, CustomUser::id::set, - IntConverter, + NumberValueConverters.Int, ), AttributeDescriptor( "myCustomFirstName", CustomUser::givenName, CustomUser::givenName::set, - StringConverter, + StringValueConverter, ), AttributeDescriptor( "myCustomLastName", CustomUser::surname, CustomUser::surname::set, - StringConverter, + StringValueConverter, ), AttributeDescriptor( "myCustomAge", CustomUser::age, CustomUser::age::set, - IntConverter, + NumberValueConverters.Int, ), ), ) diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/ListsTest.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/ListsTest.kt index 8cf3451e7f7..e134caa2b53 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/ListsTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/ListsTest.kt @@ -36,8 +36,8 @@ public class ListsTest { nullableListNullableElement = null, ) - val item = ListsConverter.convertTo(lists) - val converted = ListsConverter.convertFrom(item) + val item = ListsConverter.convertRight(lists) + val converted = ListsConverter.convertLeft(item) assertEquals(lists, converted) } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/MapsTest.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/MapsTest.kt index 9ae8a945924..e4056fcfa94 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/MapsTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/MapsTest.kt @@ -40,8 +40,8 @@ public class MapsTest { nullableMapNullableValue = null, ) - val item = MapsConverter.convertTo(maps) - val converted = MapsConverter.convertFrom(item) + val item = MapsConverter.convertRight(maps) + val converted = MapsConverter.convertLeft(item) assertEquals(maps, converted) } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/NullableItemTest.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/NullableItemTest.kt index 1c5b89d5a90..c025ca09f90 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/NullableItemTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/NullableItemTest.kt @@ -22,8 +22,8 @@ public class NullableItemTest { instant = Instant.now(), ) - val item = NullableItemConverter.convertTo(nullable) - val converted = NullableItemConverter.convertFrom(item) + val item = NullableItemConverter.convertRight(nullable) + val converted = NullableItemConverter.convertLeft(item) assertEquals(nullable, converted) } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/PrimitivesTest.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/PrimitivesTest.kt index 7c62575deef..1f928bbf883 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/PrimitivesTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/PrimitivesTest.kt @@ -39,8 +39,8 @@ public class PrimitivesTest { document = Document.Number(5), ) - val item = PrimitivesConverter.convertTo(primitive) - val converted = PrimitivesConverter.convertFrom(item) + val item = PrimitivesConverter.convertRight(primitive) + val converted = PrimitivesConverter.convertLeft(item) assertEquals(primitive, converted) } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/SetsTest.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/SetsTest.kt index a5acb0beac3..90c76e04528 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/SetsTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/standard-item-converters/test/SetsTest.kt @@ -31,8 +31,8 @@ public class SetsTest { nullableSet = null, ) - val item = SetsConverter.convertTo(sets) - val converted = SetsConverter.convertFrom(item) + val item = SetsConverter.convertRight(sets) + val converted = SetsConverter.convertLeft(item) assertEquals(sets, converted) } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/tests/UserTest.kt b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/tests/UserTest.kt index bead735690a..34368015d37 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/tests/UserTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper-schema-generator-plugin/src/test/resources/tests/UserTest.kt @@ -16,7 +16,7 @@ class UserTest { @Test fun testConversion() { val user = User(123, "Steve", "Rogers", 84) - val converted = UserConverter.convertTo(user) + val converted = UserConverter.convertRight(user) assertEquals( itemOf( @@ -28,7 +28,7 @@ class UserTest { converted, ) - val unconverted = UserConverter.convertFrom(converted) + val unconverted = UserConverter.convertLeft(converted) assertEquals(user, unconverted) } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/api/dynamodb-mapper.api b/hll/dynamodb-mapper/dynamodb-mapper/api/dynamodb-mapper.api index abda34f87ed..72175f49af3 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/api/dynamodb-mapper.api +++ b/hll/dynamodb-mapper/dynamodb-mapper/api/dynamodb-mapper.api @@ -635,43 +635,25 @@ public final class aws/sdk/kotlin/hll/dynamodbmapper/items/AttributeDescriptorKt public static final fun AttributeDescriptor (Ljava/lang/String;Lkotlin/jvm/functions/Function1;Lkotlin/jvm/functions/Function2;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/dynamodbmapper/items/AttributeDescriptor; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentConverter : aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter { - public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/items/DocumentConverter; - public fun convertFrom (Laws/sdk/kotlin/hll/dynamodbmapper/model/Item;)Laws/smithy/kotlin/runtime/content/Document; - public synthetic fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Laws/smithy/kotlin/runtime/content/Document;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public fun convertTo (Laws/smithy/kotlin/runtime/content/Document;Ljava/util/Set;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public synthetic fun convertTo (Ljava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; - public synthetic fun convertTo (Ljava/lang/Object;Ljava/util/Set;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; -} - -public final class aws/sdk/kotlin/hll/dynamodbmapper/items/HeterogeneousItemConverter : aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter { +public final class aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentItemConverterKt { + public static final fun getDocumentItemConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +} + +public final class aws/sdk/kotlin/hll/dynamodbmapper/items/HeterogeneousItemConverter : aws/sdk/kotlin/hll/mapping/core/converters/Converter { public fun (Lkotlin/jvm/functions/Function1;Ljava/lang/String;Ljava/util/Map;)V - public fun convertFrom (Laws/sdk/kotlin/hll/dynamodbmapper/model/Item;)Ljava/lang/Object; - public synthetic fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Ljava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Ljava/lang/Object;Ljava/util/Set;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; + public fun convertLeft (Laws/sdk/kotlin/hll/dynamodbmapper/model/Item;)Ljava/lang/Object; + public synthetic fun convertLeft (Ljava/lang/Object;)Ljava/lang/Object; + public fun convertRight (Ljava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; + public synthetic fun convertRight (Ljava/lang/Object;)Ljava/lang/Object; + public fun getLeft ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; + public fun getRight ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; public final fun getSubConverters ()Ljava/util/Map; public final fun getTypeAttribute ()Ljava/lang/String; public final fun getTypeMapper ()Lkotlin/jvm/functions/Function1; } -public abstract interface class aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter : aws/sdk/kotlin/hll/mapping/core/converters/Converter { - public fun convertTo (Ljava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; - public abstract fun convertTo (Ljava/lang/Object;Ljava/util/Set;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public static synthetic fun convertTo$default (Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter;Ljava/lang/Object;Ljava/util/Set;ILjava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; -} - -public final class aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter$DefaultImpls { - public static fun convertTo (Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter;Ljava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public static synthetic fun convertTo$default (Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter;Ljava/lang/Object;Ljava/util/Set;ILjava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; -} - public abstract interface class aws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema { - public abstract fun getConverter ()Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter; + public abstract fun getConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; public abstract fun getKeyAttributeNames ()Ljava/util/Set; } @@ -694,10 +676,10 @@ public final class aws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$PartitionK } public final class aws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchemaKt { - public static final fun ItemSchema (Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$PartitionKey; - public static final fun ItemSchema (Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$CompositeKey; - public static final fun withKeySpec (Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$PartitionKey; - public static final fun withKeySpec (Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$CompositeKey; + public static final fun ItemSchema (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$PartitionKey; + public static final fun ItemSchema (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$CompositeKey; + public static final fun withKeySpec (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$PartitionKey; + public static final fun withKeySpec (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;Laws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec;)Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema$CompositeKey; } public abstract interface class aws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec { @@ -721,14 +703,15 @@ public abstract interface class aws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec$ public abstract interface class aws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec$String : aws/sdk/kotlin/hll/dynamodbmapper/items/KeySpec { } -public final class aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverter : aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter { +public final class aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverter : aws/sdk/kotlin/hll/mapping/core/converters/Converter { public fun (Lkotlin/jvm/functions/Function0;Lkotlin/jvm/functions/Function1;[Laws/sdk/kotlin/hll/dynamodbmapper/items/AttributeDescriptor;)V - public fun convertFrom (Laws/sdk/kotlin/hll/dynamodbmapper/model/Item;)Ljava/lang/Object; - public synthetic fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Ljava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Ljava/lang/Object;Ljava/util/Set;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; + public fun convertLeft (Laws/sdk/kotlin/hll/dynamodbmapper/model/Item;)Ljava/lang/Object; + public synthetic fun convertLeft (Ljava/lang/Object;)Ljava/lang/Object; + public fun convertRight (Ljava/lang/Object;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; + public synthetic fun convertRight (Ljava/lang/Object;)Ljava/lang/Object; public final fun getDescriptors ()Ljava/util/Map; + public fun getLeft ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; + public fun getRight ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; } public abstract interface class aws/sdk/kotlin/hll/dynamodbmapper/model/Index : aws/sdk/kotlin/hll/dynamodbmapper/model/IndexSpec, aws/sdk/kotlin/hll/dynamodbmapper/model/ItemSource, aws/sdk/kotlin/hll/dynamodbmapper/operations/IndexOperations { @@ -1266,147 +1249,143 @@ public final class aws/sdk/kotlin/hll/dynamodbmapper/pipeline/SerializeInputKt { public static final fun SerializeInput (Ljava/lang/Object;Laws/sdk/kotlin/hll/dynamodbmapper/items/ItemSchema;)Laws/sdk/kotlin/hll/dynamodbmapper/pipeline/SerializeInput; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/ItemToValueConverter : aws/sdk/kotlin/hll/mapping/core/converters/Converter { - public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/ItemToValueConverter; - public fun convertFrom (Laws/sdk/kotlin/services/dynamodb/model/AttributeValue;)Laws/sdk/kotlin/hll/dynamodbmapper/model/Item; - public synthetic fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Laws/sdk/kotlin/hll/dynamodbmapper/model/Item;)Laws/sdk/kotlin/services/dynamodb/model/AttributeValue; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/ItemValueConverterKt { + public static final fun getItemValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverter : aws/sdk/kotlin/hll/mapping/core/converters/SplittingConverter { - public fun (Lkotlin/reflect/KClass;)V - public fun convertFrom (Laws/sdk/kotlin/services/dynamodb/model/AttributeValue;)Laws/sdk/kotlin/hll/mapping/core/util/Either; - public synthetic fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Ljava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/util/Either; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/NullableValueConverterKt { + public static final fun NullableValueConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static synthetic fun NullableValueConverter$default (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILjava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun asNullable (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static synthetic fun asNullable$default (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILjava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getNullValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListConverterKt { - public static final fun ListConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getListConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListValueConverterKt { + public static final fun ListValueConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static synthetic fun ListValueConverter$default (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILjava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getAttributeValueListValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapConverterKt { - public static final fun MapConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun MapConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getMapConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapValueConverterKt { + public static final fun MapValueConverterByEntryConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static synthetic fun MapValueConverterByEntryConverter$default (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILjava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun MapValueConverterByKeyAndValueConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static synthetic fun MapValueConverterByKeyAndValueConverter$default (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILjava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun MapValueConverterByValueConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static synthetic fun MapValueConverterByValueConverter$default (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILjava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getAttributeValueMapValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetConverters { - public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetConverters; - public final fun getStringListToAttributeValueNumberSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getStringSetToAttributeValueNumberSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetValueConverters { + public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetValueConverters; + public final fun getByte ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getDouble ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getFloat ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getInt ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getLong ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getShort ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getString ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getStringList ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUByte ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUInt ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getULong ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUShort ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static synthetic fun of$default (Laws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetValueConverters;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILjava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetConvertersKt { - public static final fun getByteSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getDoubleSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getFloatSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getIntSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getLongSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getShortSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getUByteSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getUIntSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getULongSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getUShortSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; -} - -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetConvertersKt { +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetValueConvertersKt { public static final fun getByteArraySetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getCharArraySetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getCharSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getStringListToAttributeValueStringSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getStringSetConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getCharArraySetValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getCharSetValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getStringListValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getStringSetValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanConverterKt { - public static final fun getBooleanConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanValueConverterKt { public static final fun getBooleanToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getBooleanValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +} + +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayValueConverterKt { + public static final fun getByteArrayValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +} + +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberToStringConverters { + public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberToStringConverters; + public final fun getAuto ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getByte ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getDouble ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getFloat ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getInt ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getLong ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getShort ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUByte ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUInt ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getULong ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUShort ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +} + +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberValueConverters { + public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberValueConverters; + public final fun getAuto ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getByte ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getDouble ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getFloat ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getInt ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getLong ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getShort ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUByte ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUInt ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getULong ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getUShort ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayConverterKt { - public static final fun getByteArrayConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; -} - -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/EnumConverter : aws/sdk/kotlin/hll/mapping/core/converters/Converter { - public fun (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)V - public fun convertFrom (Laws/sdk/kotlin/services/dynamodb/model/AttributeValue;)Ljava/lang/Enum; - public synthetic fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Ljava/lang/Enum;)Laws/sdk/kotlin/services/dynamodb/model/AttributeValue; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; -} - -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberConverters { - public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberConverters; - public final fun getAutoNumberToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getByteToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getDoubleToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getFloatToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getIntToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getLongToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getShortToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getStringToAttributeValueNumberConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getUByteToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getUIntToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getULongToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getUShortToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; -} - -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberConvertersKt { - public static final fun getAutoNumberConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getByteConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getDoubleConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getFloatConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getIntConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getLongConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getShortConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getUByteConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getUIntConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getULongConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getUShortConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberValueConvertersKt { + public static final fun getNumericalStringValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextConverters { public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextConverters; - public final fun getCharArrayToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getCharToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun getStringToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getChar ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getCharArray ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public final fun getString ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextConvertersKt { - public static final fun getCharArrayConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getCharConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun getStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextValueConvertersKt { + public static final fun getCharArrayValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getCharValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getStringValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentConverter : aws/sdk/kotlin/hll/mapping/core/converters/Converter { - public static final field Companion Laws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentConverter$Companion; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverter : aws/sdk/kotlin/hll/mapping/core/converters/Converter { + public static final field Companion Laws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverter$Companion; public fun ()V - public fun (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)V - public synthetic fun (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILkotlin/jvm/internal/DefaultConstructorMarker;)V - public fun convertFrom (Laws/sdk/kotlin/services/dynamodb/model/AttributeValue;)Laws/smithy/kotlin/runtime/content/Document; - public synthetic fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; - public fun convertTo (Laws/smithy/kotlin/runtime/content/Document;)Laws/sdk/kotlin/services/dynamodb/model/AttributeValue; - public synthetic fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; + public fun (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Lkotlin/jvm/functions/Function1;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)V + public synthetic fun (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Lkotlin/jvm/functions/Function1;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;ILkotlin/jvm/internal/DefaultConstructorMarker;)V + public fun convertLeft (Laws/sdk/kotlin/services/dynamodb/model/AttributeValue;)Laws/smithy/kotlin/runtime/content/Document; + public synthetic fun convertLeft (Ljava/lang/Object;)Ljava/lang/Object; + public fun convertRight (Laws/smithy/kotlin/runtime/content/Document;)Laws/sdk/kotlin/services/dynamodb/model/AttributeValue; + public synthetic fun convertRight (Ljava/lang/Object;)Ljava/lang/Object; + public fun getLeft ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; + public fun getRight ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentConverter$Companion { - public final fun getDefault ()Laws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentConverter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverter$Companion { + public final fun getDefault ()Laws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConverter { - public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConverter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverter { + public static final field INSTANCE Laws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverter; public final fun getDefault ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; public final fun getEpochMs ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; public final fun getEpochS ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; public final fun getIso8601 ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlConverterKt { - public static final fun getUrlConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlValueConverterKt { public static final fun getUrlToStringConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun getUrlValueConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentItemConverter.kt similarity index 80% rename from hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentConverter.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentItemConverter.kt index b5ae1f3699c..dfd54725333 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/DocumentItemConverter.kt @@ -7,32 +7,29 @@ package aws.sdk.kotlin.hll.dynamodbmapper.items import aws.sdk.kotlin.hll.dynamodbmapper.model.Item import aws.sdk.kotlin.hll.dynamodbmapper.model.toItem import aws.sdk.kotlin.hll.dynamodbmapper.util.NULL_ATTR +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.reversedBy import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import aws.smithy.kotlin.runtime.ExperimentalApi import aws.smithy.kotlin.runtime.InternalApi import aws.smithy.kotlin.runtime.content.Document import aws.smithy.kotlin.runtime.util.toNumber -// FIXME Combine with DocumentValueConverter or refactor to commonize as much code as possible -@ExperimentalApi -public object DocumentConverter : ItemConverter { - override fun convertFrom(to: Item): Document = to +private val docToItem = MonoConverter { + require(it is Document.Map) // only + it.mapValues { (_, value) -> toAttributeValue(value) }.toItem() +} + +private val itemToDoc = MonoConverter { + it .mapValues { (_, attr) -> fromAttributeValue(attr) } .let(Document::Map) - - override fun convertTo(from: Document, onlyAttributes: Set?): Item { - require(from is Document.Map) - - val map = if (onlyAttributes == null) { - from - } else { - from.filterKeys { it in onlyAttributes } - } - - return map.mapValues { (_, value) -> toAttributeValue(value) }.toItem() - } } +// FIXME Combine with DocumentValueConverter or refactor to commonize as much code as possible +@ExperimentalApi +public val DocumentItemConverter: ItemConverter = docToItem reversedBy itemToDoc + @OptIn(InternalApi::class) private fun fromAttributeValue(attr: AttributeValue): Document? = when (attr) { is AttributeValue.Null -> null diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/HeterogeneousItemConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/HeterogeneousItemConverter.kt index 39bfbbf9801..1a3d619317b 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/HeterogeneousItemConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/HeterogeneousItemConverter.kt @@ -6,6 +6,7 @@ package aws.sdk.kotlin.hll.dynamodbmapper.items import aws.sdk.kotlin.hll.dynamodbmapper.model.Item import aws.sdk.kotlin.hll.dynamodbmapper.model.buildItem +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import aws.smithy.kotlin.runtime.ExperimentalApi @@ -101,23 +102,20 @@ public class HeterogeneousItemConverter( public val typeAttribute: String, public val subConverters: Map>, ) : ItemConverter { - override fun convertFrom(to: Item): T { - val attr = to[typeAttribute] ?: error("Missing $typeAttribute") + override val left: MonoConverter = MonoConverter { item -> + val attr = item[typeAttribute] ?: error("Missing $typeAttribute") val typeValue = attr.asSOrNull() ?: error("No string value for $attr") val converter = subConverters[typeValue] ?: error("No converter for $typeValue") - return converter.convertFrom(to) + converter.convertLeft(item) } - override fun convertTo(from: T, onlyAttributes: Set?): Item { - val typeValue = typeMapper(from) + override val right: MonoConverter = MonoConverter { obj -> + val typeValue = typeMapper(obj) val converter = subConverters[typeValue] ?: error("No converter for $typeValue") - return buildItem { - if (onlyAttributes?.contains(typeAttribute) != false) { - put(typeAttribute, AttributeValue.S(typeValue)) - } - - putAll(converter.convertTo(from, onlyAttributes)) + buildItem { + put(typeAttribute, AttributeValue.S(typeValue)) + putAll(converter.convertRight(obj)) } } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter.kt index be343fc4ae0..ad5c754b404 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/ItemConverter.kt @@ -13,7 +13,4 @@ import aws.smithy.kotlin.runtime.ExperimentalApi * @param T The type of objects which will be converted */ @ExperimentalApi -public interface ItemConverter : Converter { - public fun convertTo(from: T, onlyAttributes: Set? = null): Item - public override fun convertTo(from: T): Item = convertTo(from, null) -} +public typealias ItemConverter = Converter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverter.kt index 9e4d0fb457d..aa9aeb95bee 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverter.kt @@ -6,6 +6,7 @@ package aws.sdk.kotlin.hll.dynamodbmapper.items import aws.sdk.kotlin.hll.dynamodbmapper.model.Item import aws.sdk.kotlin.hll.dynamodbmapper.model.buildItem +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import aws.smithy.kotlin.runtime.ExperimentalApi @@ -36,7 +37,7 @@ public class SimpleItemConverter( } } - override fun convertFrom(to: Item): T { + override val left: MonoConverter = MonoConverter { val builder = builderFactory() /** @@ -50,17 +51,17 @@ public class SimpleItemConverter( * ``` */ fun AttributeDescriptor.fromAttributeValue(attr: AttributeValue) = - builder.setter(converter.convertFrom(attr)) + builder.setter(converter.convertLeft(attr)) - to.forEach { (name, attr) -> + it.forEach { (name, attr) -> // TODO make behavior for unknown attributes configurable (ignore, exception, other?) - descriptors[name]?.fromAttributeValue(attr) + this.descriptors[name]?.fromAttributeValue(attr) } - return builder.build() + builder.build() } - override fun convertTo(from: T, onlyAttributes: Set?): Item { + override val right: MonoConverter = MonoConverter { /** * This is a convenience function to keep the compile-time safety for type param `A`. Without this, the compiler * can't track generic types across multiple statements: @@ -72,16 +73,12 @@ public class SimpleItemConverter( * ``` */ fun AttributeDescriptor.toAttributeValue() = - converter.convertTo(getter(from)) + converter.convertRight(getter(it)) - val descriptors = if (onlyAttributes == null) { - this.descriptors.values - } else { - this.descriptors.filterKeys(onlyAttributes::contains).values - } - - return buildItem { - descriptors.forEach { desc -> put(desc.name, desc.toAttributeValue()) } + buildItem { + this@SimpleItemConverter.descriptors.values.forEach { desc -> + put(desc.name, desc.toAttributeValue()) + } } } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/model/internal/TableImpl.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/model/internal/TableImpl.kt index 8754ab2386a..c570e943212 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/model/internal/TableImpl.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/model/internal/TableImpl.kt @@ -22,8 +22,7 @@ internal fun tableImpl( name: String, schema: ItemSchema.PartitionKey, ): Table.PartitionKey { - val tableName = name // shadowed below - val specImpl = TableSpecPartitionKeyImpl(mapper, tableName, schema) + val specImpl = TableSpecPartitionKeyImpl(mapper, name, schema) val opsImpl = TableOperationsImpl(specImpl) return object : Table.PartitionKey, diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/ItemToValueConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/ItemToValueConverter.kt deleted file mode 100644 index c2adda57125..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/ItemToValueConverter.kt +++ /dev/null @@ -1,27 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values - -import aws.sdk.kotlin.hll.dynamodbmapper.model.Item -import aws.sdk.kotlin.hll.dynamodbmapper.model.toItem -import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Converts between [Item] and [AttributeValue]. - * This converter is typically chained following an [ItemConverter] using the [andThenTo] extension function. - */ -@ExperimentalApi -public object ItemToValueConverter : ValueConverter { - /** - * Convert from [AttributeValue] to [Item] - */ - override fun convertFrom(to: AttributeValue): Item = to.asM().toItem() - - /** - * Convert [from] [Item] to [AttributeValue] - */ - override fun convertTo(from: Item): AttributeValue = AttributeValue.M(from) -} diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/ItemValueConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/ItemValueConverter.kt new file mode 100644 index 00000000000..85792815ae1 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/ItemValueConverter.kt @@ -0,0 +1,19 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values + +import aws.sdk.kotlin.hll.dynamodbmapper.items.ItemConverter +import aws.sdk.kotlin.hll.dynamodbmapper.model.Item +import aws.sdk.kotlin.hll.dynamodbmapper.model.toItem +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.services.dynamodb.model.AttributeValue +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * Converts between [Item] and [AttributeValue]. This converter is typically chained following an [ItemConverter] using + * the `+` operator. + */ +@ExperimentalApi +public val ItemValueConverter: ValueConverter = Converter(AttributeValue::M) { it.asM().toItem() } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverter.kt deleted file mode 100644 index 90a22dfa670..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverter.kt +++ /dev/null @@ -1,46 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values - -import aws.sdk.kotlin.hll.dynamodbmapper.util.NULL_ATTR -import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.SplittingConverter -import aws.sdk.kotlin.hll.mapping.core.converters.mergeBy -import aws.sdk.kotlin.hll.mapping.core.util.Either -import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import aws.smithy.kotlin.runtime.ExperimentalApi -import kotlin.reflect.KClass - -/** - * Converts between potentially `null` values and - * [DynamoDB `NULL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Null). - * Note that this class is a [SplittingConverter] and the logic for handling non-null values is undefined in this class. - * Thus, it is typically used in conjunction with the [NullableConverter] factory function or via [mergeBy]. - * @param V The non-nullable type - */ -@ExperimentalApi -public class NullableConverter(klass: KClass) : SplittingConverter { - override fun convertTo(from: V?): Either = when (from) { - null -> Either.Left(NULL_ATTR) - else -> Either.Right(from) - } - - override fun convertFrom(to: AttributeValue): Either = when (to) { - is AttributeValue.Null -> Either.Left(null) - else -> Either.Right(to) - } -} - -/** - * Initializes a new [NullableConverter] for the given reified type [V] - */ -@ExperimentalApi -public inline fun NullableConverter(): NullableConverter = NullableConverter(V::class) - -@ExperimentalApi -@Suppress("ktlint:standard:function-naming") -public inline fun NullableConverter( - delegate: Converter, -): Converter = NullableConverter().mergeBy(delegate) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableValueConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableValueConverter.kt new file mode 100644 index 00000000000..0f682a52b22 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableValueConverter.kt @@ -0,0 +1,60 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values + +import aws.sdk.kotlin.hll.dynamodbmapper.util.NULL_ATTR +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.reversedBy +import aws.sdk.kotlin.services.dynamodb.model.AttributeValue +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * Converts between `null` values and + * [DynamoDB `NULL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Null). + * This converter is not generally useful on its own and is typically combined with a type-specific non-nullable + * delegate in a [NullableValueConverter]. + */ +@ExperimentalApi +public val NullValueConverter: ValueConverter = + MonoConverter { NULL_ATTR } reversedBy MonoConverter { + require(it is AttributeValue.Null) + null + } + +/** + * Creates a converter between potentially-`null` values and + * [DynamoDB `NULL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Null). + * @param V The non-nullable type + * @param delegate The delegate converter for non-null values + * @param nullValueConverter A [Converter] for `null` values. The default is [NullValueConverter]. + */ +@ExperimentalApi +@Suppress("ktlint:standard:function-naming") +public fun NullableValueConverter( + delegate: ValueConverter, + nullValueConverter: ValueConverter = NullValueConverter, +): ValueConverter { + val right = MonoConverter { from -> + when (from) { + null -> nullValueConverter.convertRight(from) + else -> delegate.convertRight(from) + } + } + + val left = MonoConverter { from -> + when (from) { + is AttributeValue.Null -> nullValueConverter.convertLeft(from) + else -> delegate.convertLeft(from) + } + } + + return Converter(right, left) +} + +@ExperimentalApi +public fun ValueConverter.asNullable( + nullValueConverter: ValueConverter = NullValueConverter, +): ValueConverter = NullableValueConverter(this, nullValueConverter) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListConverter.kt deleted file mode 100644 index d5003c9c011..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListConverter.kt +++ /dev/null @@ -1,38 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values.collections - -import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapFrom -import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Converts between [List] and - * [DynamoDB `L` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.List). - * Note that the lists must contain already-converted [AttributeValue] elements. This converter is typically chained - * with another converter which handles converting elements to [AttributeValue] either by using the factory function - * [ListConverter] or using the [mapFrom] extension method. - * - * For example: - * - * ```kotlin - * val intListConv = ListConverter(IntConverter) // ValueConverter> - * val intListConv2 = ListConverter.mapFrom(IntConverter) // same as above - * ``` - */ -@ExperimentalApi -public val ListConverter: ValueConverter> = Converter(AttributeValue::L, AttributeValue::asL) - -/** - * Creates a new list converter using the given [elementConverter] as a delegate - * @param F The type of elements in the list - * @param elementConverter A converter for transforming between values of [F] and [AttributeValue] - */ -@ExperimentalApi -@Suppress("ktlint:standard:function-naming") -public fun ListConverter(elementConverter: Converter): ValueConverter> = - ListConverter.mapFrom(elementConverter) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListValueConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListValueConverter.kt new file mode 100644 index 00000000000..19d3cb85b66 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListValueConverter.kt @@ -0,0 +1,35 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values.collections + +import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.collections.ListMappingConverter +import aws.sdk.kotlin.hll.mapping.core.converters.plus +import aws.sdk.kotlin.services.dynamodb.model.AttributeValue +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * Converts between [List] and + * [DynamoDB `L` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.List). + * Note that the lists must contain already-converted [AttributeValue] elements. This converter is typically chained + * with another converter which handles mapping elements to [AttributeValue], such as by using the factory function + * [ListValueConverter]. + */ +@ExperimentalApi +public val AttributeValueListValueConverter: ValueConverter> = + Converter(AttributeValue::L, AttributeValue::asL) + +/** + * Creates a new list converter using the given [delegate] as a delegate + * @param E The type of elements in the list + * @param delegate A converter for transforming between values of [E] and [AttributeValue] + */ +@ExperimentalApi +@Suppress("ktlint:standard:function-naming") +public fun ListValueConverter( + delegate: ValueConverter, + attributeValueListValueConverter: ValueConverter> = AttributeValueListValueConverter, +): ValueConverter> = ListMappingConverter(delegate) + attributeValueListValueConverter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapConverter.kt deleted file mode 100644 index ef0b62d2b14..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapConverter.kt +++ /dev/null @@ -1,52 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values.collections - -import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapFrom -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapKeysFrom -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapValuesFrom -import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Converts between [Map] and - * [DynamoDB `M` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.Map). - * Note that the maps must contain [String] keys and already-converted [AttributeValue] values. This converter is - * typically chained with another converter which handles converting values to [AttributeValue] either by using the - * factory function [MapConverter] or by using the [mapFrom]/[mapValuesFrom]/[mapKeysFrom] extension methods. - * - * ```kotlin - * val instantMapConv = MapConverter(InstantConverter.Default) // ValueConverter> - * val instantMapConv2 = MapConverter.mapValuesFrom(InstantConverter.Default) // same as above - * ``` - */ -@ExperimentalApi -public val MapConverter: ValueConverter> = Converter(AttributeValue::M, AttributeValue::asM) - -/** - * Creates a new map converter using the given [keyConverter] and [valueConverter] as delegates - * @param K The type of keys in the map - * @param V The type of values in the map - * @param keyConverter A converter for transforming between [K] keys and [String] keys - * @param valueConverter A converter for transforming between [V] values and [AttributeValue] - */ -@ExperimentalApi -@Suppress("ktlint:standard:function-naming") -public fun MapConverter( - keyConverter: Converter, - valueConverter: ValueConverter, -): ValueConverter> = MapConverter.mapFrom(keyConverter, valueConverter) - -/** - * Creates a new string-keyed map converter using the given [valueConverter] as a delegate - * @param V The type of values in the map - * @param valueConverter A converter for transforming between [V] values and [AttributeValue] - */ -@ExperimentalApi -@Suppress("ktlint:standard:function-naming") -public fun MapConverter(valueConverter: ValueConverter): ValueConverter> = - MapConverter.mapValuesFrom(valueConverter) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapValueConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapValueConverter.kt new file mode 100644 index 00000000000..837ed525387 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapValueConverter.kt @@ -0,0 +1,74 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values.collections + +import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.collections.MapMappingConverter +import aws.sdk.kotlin.hll.mapping.core.converters.plus +import aws.sdk.kotlin.services.dynamodb.model.AttributeValue +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * Converts between [Map] and + * [DynamoDB `M` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.Map). + * Note that the maps must contain [String] keys and already-converted [AttributeValue] values. This converter is + * typically chained with another converter which handles converting values to [AttributeValue] either by using the + * factory function [MapValueConverter] or by using the [mapFrom]/[mapValuesFrom]/[mapKeysFrom] extension methods. + * + * ```kotlin + * val instantMapConv = MapValueConverter(InstantConverter.Default) // ValueConverter> + * val instantMapConv2 = MapValueConverter.mapValuesFrom(InstantConverter.Default) // same as above + * ``` + */ +@ExperimentalApi +public val AttributeValueMapValueConverter: ValueConverter> = + Converter(AttributeValue::M, AttributeValue::asM) + +/** + * Creates a new map converter using the given [keyConverter] and [valueConverter] as delegates + * @param K The type of keys in the map + * @param V The type of values in the map + * @param entryConverter A converter for transforming between entries of type `Pair` and type + * `Pair` + */ +@ExperimentalApi +@JvmName("MapValueConverterByEntryConverter") +@Suppress("ktlint:standard:function-naming") +public fun MapValueConverter( + entryConverter: Converter, Pair>, + attributeValueMapValueConverter: ValueConverter> = AttributeValueMapValueConverter, +): ValueConverter> = MapMappingConverter(entryConverter) + attributeValueMapValueConverter + +/** + * Creates a new map converter using the given [keyConverter] and [valueConverter] as delegates + * @param K The type of keys in the map + * @param V The type of values in the map + * @param keyConverter A converter for transforming between [K] keys and [String] keys + * @param valueConverter A converter for transforming between [V] values and [AttributeValue] + */ +@ExperimentalApi +@JvmName("MapValueConverterByKeyAndValueConverter") +@Suppress("ktlint:standard:function-naming") +public fun MapValueConverter( + keyConverter: Converter, + valueConverter: ValueConverter, + attributeValueMapValueConverter: ValueConverter> = AttributeValueMapValueConverter, +): ValueConverter> = + MapMappingConverter(keyConverter, valueConverter) + attributeValueMapValueConverter + +/** + * Creates a new string-keyed map converter using the given [valueConverter] as a delegate + * @param V The type of values in the map + * @param valueConverter A converter for transforming between [V] values and [AttributeValue] + */ +@ExperimentalApi +@JvmName("MapValueConverterByValueConverter") +@Suppress("ktlint:standard:function-naming") +public fun MapValueConverter( + valueConverter: ValueConverter, + attributeValueMapValueConverter: ValueConverter> = AttributeValueMapValueConverter, +): ValueConverter> = + MapMappingConverter(Converter.identity(), valueConverter) + attributeValueMapValueConverter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetConverters.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetConverters.kt deleted file mode 100644 index f65098c46f1..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetConverters.kt +++ /dev/null @@ -1,118 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values.collections - -import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.* -import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenFrom -import aws.sdk.kotlin.hll.mapping.core.converters.collections.CollectionTypeConverters -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapFrom -import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Namespace for containing various conversion utilities dealing with numerical set conversion - */ -@ExperimentalApi -public object NumberSetConverters { - /** - * Converts between a [List] of [String] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ - public val StringListToAttributeValueNumberSetConverter: ValueConverter> = - Converter(AttributeValue::Ns, AttributeValue::asNs) - - /** - * Converts between a [Set] of [String] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ - public val StringSetToAttributeValueNumberSetConverter: ValueConverter> = - StringListToAttributeValueNumberSetConverter.andThenFrom(CollectionTypeConverters.SetToListConverter()) - - /** - * Creates a [ValueConverter] which converts between a [Set] of [N] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - * @param N The type of high-level values which will be converted - */ - public fun of(numberToStringConverter: Converter): ValueConverter> = - StringSetToAttributeValueNumberSetConverter.mapFrom(numberToStringConverter) -} - -/** - * Converts between a [Set] of [Byte] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val ByteSetConverter: ValueConverter> = NumberSetConverters.of(NumberConverters.ByteToStringConverter) - -/** - * Converts between a [Set] of [Double] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val DoubleSetConverter: ValueConverter> = - NumberSetConverters.of(NumberConverters.DoubleToStringConverter) - -/** - * Converts between a [Set] of [Float] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val FloatSetConverter: ValueConverter> = - NumberSetConverters.of(NumberConverters.FloatToStringConverter) - -/** - * Converts between a [Set] of [Int] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val IntSetConverter: ValueConverter> = NumberSetConverters.of(NumberConverters.IntToStringConverter) - -/** - * Converts between a [Set] of [Long] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val LongSetConverter: ValueConverter> = NumberSetConverters.of(NumberConverters.LongToStringConverter) - -/** - * Converts between a [Set] of [Short] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val ShortSetConverter: ValueConverter> = - NumberSetConverters.of(NumberConverters.ShortToStringConverter) - -/** - * Converts between a [Set] of [UByte] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val UByteSetConverter: ValueConverter> = - NumberSetConverters.of(NumberConverters.UByteToStringConverter) - -/** - * Converts between a [Set] of [UInt] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val UIntSetConverter: ValueConverter> = NumberSetConverters.of(NumberConverters.UIntToStringConverter) - -/** - * Converts between a [Set] of [ULong] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val ULongSetConverter: ValueConverter> = - NumberSetConverters.of(NumberConverters.ULongToStringConverter) - -/** - * Converts between a [Set] of [UShort] elements and - * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) - */ -@ExperimentalApi -public val UShortSetConverter: ValueConverter> = - NumberSetConverters.of(NumberConverters.UShortToStringConverter) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetValueConverters.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetValueConverters.kt new file mode 100644 index 00000000000..5f3ea0d5ee0 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/NumberSetValueConverters.kt @@ -0,0 +1,125 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values.collections + +import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.Byte +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.Double +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.Float +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.Int +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.Long +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.Short +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.String +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.UByte +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.UInt +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.ULong +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.NumberSetValueConverters.UShort +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberToStringConverters +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.collections.SetMappingConverter +import aws.sdk.kotlin.hll.mapping.core.converters.collections.SetToListConverter +import aws.sdk.kotlin.hll.mapping.core.converters.plus +import aws.sdk.kotlin.services.dynamodb.model.AttributeValue +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * Namespace for containing various conversion utilities dealing with numerical set conversion + */ +@ExperimentalApi +public object NumberSetValueConverters { + /** + * Converts between a [List] of [String] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + public val StringList: ValueConverter> = + Converter(AttributeValue::Ns, AttributeValue::asNs) + + /** + * Converts between a [Set] of [String] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + public val String: ValueConverter> = SetToListConverter() + StringList + + /** + * Creates a [ValueConverter] which converts between a [Set] of [N] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + * @param N The type of high-level values which will be converted + */ + public fun of( + numberConverter: Converter, + stringSetValueConverter: ValueConverter> = String, + ): ValueConverter> = + SetMappingConverter(numberConverter) + stringSetValueConverter + + /** + * Converts between a [Set] of [Byte] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val Byte: ValueConverter> = of(NumberToStringConverters.Byte) + + /** + * Converts between a [Set] of [Double] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val Double: ValueConverter> = of(NumberToStringConverters.Double) + + /** + * Converts between a [Set] of [Float] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val Float: ValueConverter> = of(NumberToStringConverters.Float) + + /** + * Converts between a [Set] of [Int] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val Int: ValueConverter> = of(NumberToStringConverters.Int) + + /** + * Converts between a [Set] of [Long] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val Long: ValueConverter> = of(NumberToStringConverters.Long) + + /** + * Converts between a [Set] of [Short] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val Short: ValueConverter> = of(NumberToStringConverters.Short) + + /** + * Converts between a [Set] of [UByte] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val UByte: ValueConverter> = of(NumberToStringConverters.UByte) + + /** + * Converts between a [Set] of [UInt] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val UInt: ValueConverter> = of(NumberToStringConverters.UInt) + + /** + * Converts between a [Set] of [ULong] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val ULong: ValueConverter> = of(NumberToStringConverters.ULong) + + /** + * Converts between a [Set] of [UShort] elements and + * [DynamoDB `NS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) + */ + @ExperimentalApi + public val UShort: ValueConverter> = of(NumberToStringConverters.UShort) +} diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetConverters.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetValueConverters.kt similarity index 67% rename from hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetConverters.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetValueConverters.kt index 3ff20e92b81..7726d3de7bb 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetConverters.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/PrimitiveSetValueConverters.kt @@ -7,9 +7,9 @@ package aws.sdk.kotlin.hll.dynamodbmapper.values.collections import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.TextConverters import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenFrom -import aws.sdk.kotlin.hll.mapping.core.converters.collections.CollectionTypeConverters -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapFrom +import aws.sdk.kotlin.hll.mapping.core.converters.collections.SetMappingConverter +import aws.sdk.kotlin.hll.mapping.core.converters.collections.SetToListConverter +import aws.sdk.kotlin.hll.mapping.core.converters.plus import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import aws.smithy.kotlin.runtime.ExperimentalApi @@ -19,8 +19,8 @@ import aws.smithy.kotlin.runtime.ExperimentalApi */ @ExperimentalApi public val ByteArraySetConverter: ValueConverter> = Converter( - convertTo = { from: Set -> AttributeValue.Bs(from.toList()) }, - convertFrom = { to: AttributeValue -> to.asBs().toSet() }, + right = { from -> AttributeValue.Bs(from.toList()) }, + left = { to -> to.asBs().toSet() }, ) /** @@ -28,7 +28,7 @@ public val ByteArraySetConverter: ValueConverter> = Converter( * [DynamoDB `SS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) */ @ExperimentalApi -public val StringListToAttributeValueStringSetConverter: ValueConverter> = +public val StringListValueConverter: ValueConverter> = Converter(AttributeValue::Ss, AttributeValue::asSs) /** @@ -36,21 +36,21 @@ public val StringListToAttributeValueStringSetConverter: ValueConverter> = - StringListToAttributeValueStringSetConverter.andThenFrom(CollectionTypeConverters.SetToListConverter()) +public val StringSetValueConverter: ValueConverter> = + SetToListConverter() + StringListValueConverter /** * Converts between a [Set] of [CharArray] elements and * [DynamoDB `SS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) */ @ExperimentalApi -public val CharArraySetConverter: ValueConverter> = - StringSetConverter.mapFrom(TextConverters.CharArrayToStringConverter) +public val CharArraySetValueConverter: ValueConverter> = + SetMappingConverter(TextConverters.CharArray) + StringSetValueConverter /** * Converts between a [Set] of [Char] elements and * [DynamoDB `SS` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.SetTypes) */ @ExperimentalApi -public val CharSetConverter: ValueConverter> = - StringSetConverter.mapFrom(TextConverters.CharToStringConverter) +public val CharSetValueConverter: ValueConverter> = + SetMappingConverter(TextConverters.Char) + StringSetValueConverter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanValueConverter.kt similarity index 87% rename from hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanConverter.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanValueConverter.kt index 1b663b12344..bf3a3053461 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/BooleanValueConverter.kt @@ -14,7 +14,7 @@ import aws.smithy.kotlin.runtime.ExperimentalApi * [DynamoDB `BOOL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Boolean) */ @ExperimentalApi -public val BooleanConverter: ValueConverter = Converter(AttributeValue::Bool, AttributeValue::asBool) +public val BooleanValueConverter: ValueConverter = Converter(AttributeValue::Bool, AttributeValue::asBool) /** * Converts between [Boolean] and [String] diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayValueConverter.kt similarity index 84% rename from hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayConverter.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayValueConverter.kt index a0e49973d81..b56ecaaabd9 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ByteArrayValueConverter.kt @@ -14,4 +14,4 @@ import aws.smithy.kotlin.runtime.ExperimentalApi * [DynamoDB `B` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Binary) */ @ExperimentalApi -public val ByteArrayConverter: ValueConverter = Converter(AttributeValue::B, AttributeValue::asB) +public val ByteArrayValueConverter: ValueConverter = Converter(AttributeValue::B, AttributeValue::asB) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/EnumConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/EnumConverter.kt deleted file mode 100644 index 2dc2897c11e..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/EnumConverter.kt +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values.scalars - -import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenFrom -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Converts between [Enum] and - * [DynamoDB `S` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.String) - * @param E The [Enum] type to convert - */ -@ExperimentalApi -public class EnumConverter>( - private val enumToStringConverter: Converter, -) : ValueConverter by StringConverter.andThenFrom(enumToStringConverter) - -/** - * Instantiates a new [ValueConverter] for enums of type [E] - * @param E The [Enum] type for which to create a [ValueConverter] - */ -@ExperimentalApi -public inline fun > EnumConverter(): EnumConverter = - EnumConverter( - enumToStringConverter = Converter( - convertTo = { from: E -> from.name }, - convertFrom = { to: String -> enumValueOf(to) }, - ), - ) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/EnumValueConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/EnumValueConverter.kt new file mode 100644 index 00000000000..4d0e183d707 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/EnumValueConverter.kt @@ -0,0 +1,19 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values.scalars + +import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.plus +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * Instantiates a new [ValueConverter] for enums of type [E] + * @param E The [Enum] type for which to create a [ValueConverter] + */ +@ExperimentalApi +@Suppress("ktlint:standard:function-naming") +public inline fun > EnumValueConverter(): ValueConverter = + Converter({ it.name }, { enumValueOf(it) }) + StringValueConverter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberConverters.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberConverters.kt deleted file mode 100644 index 865ffea0ea2..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberConverters.kt +++ /dev/null @@ -1,192 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values.scalars - -import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenTo -import aws.sdk.kotlin.hll.mapping.core.converters.validatingFrom -import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Namespace for containing various conversion utilities dealing with number conversion - */ -@ExperimentalApi -public object NumberConverters { - /** - * Converts between [String] instances which contains numbers and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ - public val StringToAttributeValueNumberConverter: ValueConverter = - Converter(AttributeValue::N, AttributeValue::asN) - - /** - * Creates a [ValueConverter] which converts between number type [N] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ - public fun of(numberToStringConverter: Converter): ValueConverter = - numberToStringConverter.andThenTo(StringToAttributeValueNumberConverter) - - /** - * Converts between [Number] and [String] values - */ - public val AutoNumberToStringConverter: Converter = Converter( - convertTo = Number::toString, - convertFrom = { to: String -> - when { - '.' in to -> to.toDouble() - else -> when (val longNumber = to.toLong()) { - in Int.MIN_VALUE..Int.MAX_VALUE -> longNumber.toInt() - else -> longNumber - } - } - }, - ) - - /** - * Converts between [Byte] and [String] values - */ - public val ByteToStringConverter: Converter = Converter(Byte::toString, String::toByte) - - /** - * Converts between [Double] and [String] values. Because - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - * do not support them, this converter throws exceptions for non-finite numbers such as [Double.NEGATIVE_INFINITY], - * [Double.POSITIVE_INFINITY], and [Double.NaN]. - */ - public val DoubleToStringConverter: Converter = - Converter(Double::toString, String::toDouble).validatingFrom { from: Double -> - require(from.isFinite()) { "Cannot convert $from: only finite numbers are supported" } - } - - /** - * Converts between [Float] and [String] values. Because - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - * do not support them, this converter throws exceptions for non-finite numbers such as [Float.NEGATIVE_INFINITY], - * [Float.POSITIVE_INFINITY], and [Float.NaN]. - */ - public val FloatToStringConverter: Converter = - Converter(Float::toString, String::toFloat).validatingFrom { from: Float -> - require(from.isFinite()) { "Cannot convert $from: only finite numbers are supported" } - } - - /** - * Converts between [Int] and [String] values - */ - public val IntToStringConverter: Converter = Converter(Int::toString, String::toInt) - - /** - * Converts between [Long] and [String] values - */ - public val LongToStringConverter: Converter = Converter(Long::toString, String::toLong) - - /** - * Converts between [Short] and [String] values - */ - public val ShortToStringConverter: Converter = Converter(Short::toString, String::toShort) - - /** - * Converts between [UByte] and [String] values - */ - public val UByteToStringConverter: Converter = Converter(UByte::toString, String::toUByte) - - /** - * Converts between [UInt] and [String] values - */ - public val UIntToStringConverter: Converter = Converter(UInt::toString, String::toUInt) - - /** - * Converts between [ULong] and [String] values - */ - public val ULongToStringConverter: Converter = Converter(ULong::toString, String::toULong) - - /** - * Converts between [UShort] and [String] values - */ - public val UShortToStringConverter: Converter = Converter(UShort::toString, String::toUShort) -} - -/** - * Converts between [Number] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number). - * When converting attribute values into number values, the following concrete subclasses of [Number] will be returned: - * * [Double] — If the number contains any fractional component - * * [Int] — If the number is in the range of [Int.MIN_VALUE] and [Int.MAX_VALUE] (inclusive) - * * [Long] — Anything else - */ -@ExperimentalApi -public val AutoNumberConverter: ValueConverter = - NumberConverters.of(NumberConverters.AutoNumberToStringConverter) - -/** - * Converts between [Byte] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val ByteConverter: ValueConverter = NumberConverters.of(NumberConverters.ByteToStringConverter) - -/** - * Converts between [Double] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val DoubleConverter: ValueConverter = NumberConverters.of(NumberConverters.DoubleToStringConverter) - -/** - * Converts between [Float] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val FloatConverter: ValueConverter = NumberConverters.of(NumberConverters.FloatToStringConverter) - -/** - * Converts between [Int] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val IntConverter: ValueConverter = NumberConverters.of(NumberConverters.IntToStringConverter) - -/** - * Converts between [Long] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val LongConverter: ValueConverter = NumberConverters.of(NumberConverters.LongToStringConverter) - -/** - * Converts between [Short] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val ShortConverter: ValueConverter = NumberConverters.of(NumberConverters.ShortToStringConverter) - -/** - * Converts between [UByte] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val UByteConverter: ValueConverter = NumberConverters.of(NumberConverters.UByteToStringConverter) - -/** - * Converts between [UInt] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val UIntConverter: ValueConverter = NumberConverters.of(NumberConverters.UIntToStringConverter) - -/** - * Converts between [ULong] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val ULongConverter: ValueConverter = NumberConverters.of(NumberConverters.ULongToStringConverter) - -/** - * Converts between [UShort] and - * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - */ -@ExperimentalApi -public val UShortConverter: ValueConverter = NumberConverters.of(NumberConverters.UShortToStringConverter) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberToStringConverters.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberToStringConverters.kt new file mode 100644 index 00000000000..559779b510c --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberToStringConverters.kt @@ -0,0 +1,92 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values.scalars + +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter + +public object NumberToStringConverters { + /** + * Converts between [Number] and [String] values + */ + public val Auto: Converter = + Converter(Number::toString) { + when { + '.' in it -> it.toDouble() + else -> when (val longNumber = it.toLong()) { + in kotlin.Int.MIN_VALUE..kotlin.Int.MAX_VALUE -> longNumber.toInt() + else -> longNumber + } + } + } + + /** + * Converts between [kotlin.Byte] and [String] values + */ + public val Byte: Converter = Converter(kotlin.Byte::toString, String::toByte) + + /** + * Converts between [kotlin.Double] and [String] values. Because + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + * do not support them, this converter throws exceptions for non-finite numbers such as [Double.NEGATIVE_INFINITY], + * [Double.POSITIVE_INFINITY], and [Double.NaN]. + */ + public val Double: Converter = run { + val doubleToString = MonoConverter { + require(it.isFinite()) { "Cannot convert $it: only finite numbers are supported" } + it.toString() + } + Converter(doubleToString, String::toDouble) + } + + /** + * Converts between [kotlin.Float] and [String] values. Because + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + * do not support them, this converter throws exceptions for non-finite numbers such as [Float.NEGATIVE_INFINITY], + * [Float.POSITIVE_INFINITY], and [Float.NaN]. + */ + public val Float: Converter = run { + val floatToString = MonoConverter { + require(it.isFinite()) { "Cannot convert $it: only finite numbers are supported" } + it.toString() + } + Converter(floatToString, String::toFloat) + } + + /** + * Converts between [kotlin.Int] and [String] values + */ + public val Int: Converter = Converter(kotlin.Int::toString, String::toInt) + + /** + * Converts between [kotlin.Long] and [String] values + */ + public val Long: Converter = Converter(kotlin.Long::toString, String::toLong) + + /** + * Converts between [kotlin.Short] and [String] values + */ + public val Short: Converter = Converter(kotlin.Short::toString, String::toShort) + + /** + * Converts between [kotlin.UByte] and [String] values + */ + public val UByte: Converter = Converter(kotlin.UByte::toString, String::toUByte) + + /** + * Converts between [kotlin.UInt] and [String] values + */ + public val UInt: Converter = Converter(kotlin.UInt::toString, String::toUInt) + + /** + * Converts between [kotlin.ULong] and [String] values + */ + public val ULong: Converter = Converter(kotlin.ULong::toString, String::toULong) + + /** + * Converts between [kotlin.UShort] and [String] values + */ + public val UShort: Converter = Converter(kotlin.UShort::toString, String::toUShort) +} diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberValueConverters.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberValueConverters.kt new file mode 100644 index 00000000000..e5dd68af347 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/NumberValueConverters.kt @@ -0,0 +1,104 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values.scalars + +import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.plus +import aws.sdk.kotlin.services.dynamodb.model.AttributeValue +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * Namespace for containing various conversion utilities dealing with number conversion + */ +@ExperimentalApi +public object NumberValueConverters { + /** + * Converts between [Number] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number). + * When converting attribute values into number values, the following concrete subclasses of [Number] will be returned: + * * [kotlin.Double] — If the number contains any fractional component + * * [kotlin.Int] — If the number is in the range of [kotlin.Int.MIN_VALUE] and [kotlin.Int.MAX_VALUE] (inclusive) + * * [kotlin.Long] — Anything else + */ + @ExperimentalApi + public val Auto: ValueConverter = NumberToStringConverters.Auto + NumericalStringValueConverter + + /** + * Converts between [kotlin.Byte] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val Byte: ValueConverter = NumberToStringConverters.Byte + NumericalStringValueConverter + + /** + * Converts between [kotlin.Double] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val Double: ValueConverter = NumberToStringConverters.Double + NumericalStringValueConverter + + /** + * Converts between [kotlin.Float] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val Float: ValueConverter = NumberToStringConverters.Float + NumericalStringValueConverter + + /** + * Converts between [kotlin.Int] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val Int: ValueConverter = NumberToStringConverters.Int + NumericalStringValueConverter + + /** + * Converts between [kotlin.Long] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val Long: ValueConverter = NumberToStringConverters.Long + NumericalStringValueConverter + + /** + * Converts between [kotlin.Short] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val Short: ValueConverter = NumberToStringConverters.Short + NumericalStringValueConverter + + /** + * Converts between [kotlin.UByte] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val UByte: ValueConverter = NumberToStringConverters.UByte + NumericalStringValueConverter + + /** + * Converts between [kotlin.UInt] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val UInt: ValueConverter = NumberToStringConverters.UInt + NumericalStringValueConverter + + /** + * Converts between [kotlin.ULong] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val ULong: ValueConverter = NumberToStringConverters.ULong + NumericalStringValueConverter + + /** + * Converts between [kotlin.UShort] and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ + @ExperimentalApi + public val UShort: ValueConverter = NumberToStringConverters.UShort + NumericalStringValueConverter +} + +/** + * Converts between [String] instances which contains numbers and + * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + */ +public val NumericalStringValueConverter: ValueConverter = Converter(AttributeValue::N, AttributeValue::asN) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextConverters.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextValueConverters.kt similarity index 58% rename from hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextConverters.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextValueConverters.kt index df119cf0433..74a6009d6e1 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextConverters.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/TextValueConverters.kt @@ -6,7 +6,7 @@ package aws.sdk.kotlin.hll.dynamodbmapper.values.scalars import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenTo +import aws.sdk.kotlin.hll.mapping.core.converters.plus import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import aws.smithy.kotlin.runtime.ExperimentalApi @@ -16,19 +16,21 @@ import aws.smithy.kotlin.runtime.ExperimentalApi @ExperimentalApi public object TextConverters { /** - * Converts between [CharArray] and [String] + * Converts between [kotlin.CharArray] and [kotlin.String] */ - public val CharArrayToStringConverter: Converter = Converter(CharArray::concatToString, String::toCharArray) + public val CharArray: Converter = + Converter(kotlin.CharArray::concatToString, kotlin.String::toCharArray) /** - * Converts between [Char] and [String] + * Converts between [kotlin.Char] and [kotlin.String] */ - public val CharToStringConverter: Converter = Converter(Char::toString, String::single) + public val Char: Converter = + Converter(kotlin.Char::toString, kotlin.String::single) /** - * Converts between [String] and [String] + * Converts between [kotlin.String] and [kotlin.String] */ - public val StringToStringConverter: Converter = Converter({ it }, { it }) + public val String: Converter = Converter.identity() } /** @@ -36,19 +38,18 @@ public object TextConverters { * [DynamoDB `S` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.String) */ @ExperimentalApi -public val StringConverter: ValueConverter = Converter(AttributeValue::S, AttributeValue::asS) +public val StringValueConverter: ValueConverter = Converter(AttributeValue::S, AttributeValue::asS) /** * Converts between [CharArray] and * [DynamoDB `S` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.String) */ @ExperimentalApi -public val CharArrayConverter: ValueConverter = - TextConverters.CharArrayToStringConverter.andThenTo(StringConverter) +public val CharArrayValueConverter: ValueConverter = TextConverters.CharArray + StringValueConverter /** * Converts between [Char] and * [DynamoDB `S` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.String) */ @ExperimentalApi -public val CharConverter: ValueConverter = TextConverters.CharToStringConverter.andThenTo(StringConverter) +public val CharValueConverter: ValueConverter = TextConverters.Char + StringValueConverter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentConverter.kt deleted file mode 100644 index 1d36c8383ae..00000000000 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentConverter.kt +++ /dev/null @@ -1,67 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.dynamodbmapper.values.smithytypes - -import aws.sdk.kotlin.hll.dynamodbmapper.values.NullableConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.ListConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.MapConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.AutoNumberConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.BooleanConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapFrom -import aws.sdk.kotlin.hll.mapping.core.converters.collections.mapValuesFrom -import aws.sdk.kotlin.hll.mapping.core.converters.mergeBy -import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import aws.smithy.kotlin.runtime.ExperimentalApi -import aws.smithy.kotlin.runtime.content.Document - -/** - * Converts between [Document] and various DynamoDB value types. The following conversions are performed: - * * `null` ↔ [DynamoDB `NULL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Null) - * * [Document.Number] ↔ [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) - * * [Document.String] ↔ [DynamoDB `S` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.String) - * * [Document.Boolean] ↔ [DynamoDB `BOOL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Boolean) - * * [Document.List] ↔ [DynamoDB `L` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.List) - * * [Document.Map] ↔ [DynamoDB `M` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.Map) - */ -@ExperimentalApi -public class DocumentConverter( - private val numberConverter: ValueConverter = AutoNumberConverter, - private val stringConverter: ValueConverter = StringConverter, - private val booleanConverter: ValueConverter = BooleanConverter, - nullableConverter: NullableConverter = NullableConverter(), - listConverter: ValueConverter> = ListConverter, - mapConverter: ValueConverter> = MapConverter, -) : ValueConverter { - private val nullableConverter = nullableConverter.mergeBy(this) - private val listConverter = listConverter.mapFrom(this.nullableConverter) - private val mapConverter = mapConverter.mapValuesFrom(this.nullableConverter) - - @ExperimentalApi - public companion object { - /** - * The default instance of [DocumentConverter] - */ - public val Default: DocumentConverter = DocumentConverter() - } - - override fun convertFrom(to: AttributeValue): Document = when (to) { - is AttributeValue.N -> Document.Number(numberConverter.convertFrom(to)) - is AttributeValue.S -> Document.String(stringConverter.convertFrom(to)) - is AttributeValue.Bool -> Document.Boolean(booleanConverter.convertFrom(to)) - is AttributeValue.L -> Document.List(listConverter.convertFrom(to)) - is AttributeValue.M -> Document.Map(mapConverter.convertFrom(to)) - else -> throw IllegalArgumentException("Documents do not support ${to::class.qualifiedName} values") - } - - override fun convertTo(from: Document): AttributeValue = when (from) { - is Document.Number -> numberConverter.convertTo(from.value) - is Document.String -> stringConverter.convertTo(from.value) - is Document.Boolean -> booleanConverter.convertTo(from.value) - is Document.List -> listConverter.convertTo(from.value) - is Document.Map -> mapConverter.convertTo(from.value) - } -} diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverter.kt new file mode 100644 index 00000000000..59a99205df7 --- /dev/null +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverter.kt @@ -0,0 +1,73 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.dynamodbmapper.values.smithytypes + +import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.asNullable +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.AttributeValueListValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.collections.AttributeValueMapValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.BooleanValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.collections.ListMappingConverter +import aws.sdk.kotlin.hll.mapping.core.converters.collections.MapMappingConverter +import aws.sdk.kotlin.hll.mapping.core.converters.plus +import aws.sdk.kotlin.services.dynamodb.model.AttributeValue +import aws.smithy.kotlin.runtime.ExperimentalApi +import aws.smithy.kotlin.runtime.content.Document + +/** + * Converts between [Document] and various DynamoDB value types. The following conversions are performed: + * * `null` ↔ [DynamoDB `NULL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Null) + * * [Document.Number] ↔ [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) + * * [Document.String] ↔ [DynamoDB `S` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.String) + * * [Document.Boolean] ↔ [DynamoDB `BOOL` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Boolean) + * * [Document.List] ↔ [DynamoDB `L` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.List) + * * [Document.Map] ↔ [DynamoDB `M` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Document.Map) + */ +@ExperimentalApi +public class DocumentValueConverter( + private val numberValueConverter: ValueConverter = NumberValueConverters.Auto, + private val stringValueConverter: ValueConverter = StringValueConverter, + private val booleanValueConverter: ValueConverter = BooleanValueConverter, + nullWrapper: (ValueConverter) -> ValueConverter = { it.asNullable() }, + attributeValueListValueConverter: ValueConverter> = AttributeValueListValueConverter, + attributeValueMapValueConverter: ValueConverter> = AttributeValueMapValueConverter, +) : ValueConverter { + private val nullableConverter = nullWrapper(this) + private val listValueConverter = ListMappingConverter(nullableConverter) + attributeValueListValueConverter + private val mapValueConverter = MapMappingConverter(Converter.identity(), nullableConverter) + attributeValueMapValueConverter + + @ExperimentalApi + public companion object { + /** + * The default instance of [DocumentValueConverter] + */ + public val Default: DocumentValueConverter = DocumentValueConverter() + } + + override val left: MonoConverter = MonoConverter { + when (it) { + is AttributeValue.N -> Document.Number(numberValueConverter.convertLeft(it)) + is AttributeValue.S -> Document.String(stringValueConverter.convertLeft(it)) + is AttributeValue.Bool -> Document.Boolean(booleanValueConverter.convertLeft(it)) + is AttributeValue.L -> Document.List(listValueConverter.convertLeft(it)) + is AttributeValue.M -> Document.Map(mapValueConverter.convertLeft(it)) + else -> throw IllegalArgumentException("Documents do not support ${it::class.qualifiedName} values") + } + } + + override val right: MonoConverter = MonoConverter { + when (it) { + is Document.Number -> numberValueConverter.convertRight(it.value) + is Document.String -> stringValueConverter.convertRight(it.value) + is Document.Boolean -> booleanValueConverter.convertRight(it.value) + is Document.List -> listValueConverter.convertRight(it.value) + is Document.Map -> mapValueConverter.convertRight(it.value) + } + } +} diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverter.kt similarity index 78% rename from hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConverter.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverter.kt index 9513032b386..49c8b2ecdd1 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverter.kt @@ -5,10 +5,11 @@ package aws.sdk.kotlin.hll.dynamodbmapper.values.smithytypes import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.LongConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.smithytypes.InstantValueConverter.EpochS import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenTo +import aws.sdk.kotlin.hll.mapping.core.converters.plus import aws.smithy.kotlin.runtime.ExperimentalApi import aws.smithy.kotlin.runtime.time.Instant import aws.smithy.kotlin.runtime.time.TimestampFormat @@ -19,14 +20,14 @@ import aws.smithy.kotlin.runtime.time.fromEpochMilliseconds * Provides access to [ValueConverter] types for various [Instant] representations */ @ExperimentalApi -public object InstantConverter { +public object InstantValueConverter { /** * Converts between [Instant] and * [DynamoDB `N` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.Number) * containing the number of milliseconds since the Unix epoch */ public val EpochMs: ValueConverter = - Converter(Instant::epochMilliseconds, Instant::fromEpochMilliseconds).andThenTo(LongConverter) + Converter(Instant::epochMilliseconds, Instant::fromEpochMilliseconds) + NumberValueConverters.Long /** * Converts between [Instant] and @@ -34,7 +35,7 @@ public object InstantConverter { * containing the number of seconds since the Unix epoch */ public val EpochS: ValueConverter = - Converter(Instant::epochSeconds, Instant::fromEpochSeconds).andThenTo(LongConverter) + Converter(Instant::epochSeconds, Instant::fromEpochSeconds) + NumberValueConverters.Long /** * Converts between [Instant] and @@ -43,9 +44,9 @@ public object InstantConverter { */ public val Iso8601: ValueConverter = Converter( - convertTo = { from: Instant -> from.format(TimestampFormat.ISO_8601_FULL) }, - convertFrom = Instant::fromIso8601, - ).andThenTo(StringConverter) + { it.format(TimestampFormat.ISO_8601_FULL) }, + Instant::fromIso8601, + ) + StringValueConverter /** * The default converter for [Instant] values, which is an instance of [EpochS] diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlConverter.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlValueConverter.kt similarity index 77% rename from hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlConverter.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlValueConverter.kt index a727fda3283..c763f64e0ff 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlConverter.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/src/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlValueConverter.kt @@ -5,9 +5,9 @@ package aws.sdk.kotlin.hll.dynamodbmapper.values.smithytypes import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenTo +import aws.sdk.kotlin.hll.mapping.core.converters.plus import aws.smithy.kotlin.runtime.ExperimentalApi import aws.smithy.kotlin.runtime.net.url.Url @@ -22,4 +22,4 @@ public val UrlToStringConverter: Converter = Converter(Url::toStrin * [DynamoDB `S` values](https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.NamingRulesDataTypes.html#HowItWorks.DataTypes.String) */ @ExperimentalApi -public val UrlConverter: ValueConverter = UrlToStringConverter.andThenTo(StringConverter) +public val UrlValueConverter: ValueConverter = UrlToStringConverter + StringValueConverter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/expressions/KeyFilterTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/expressions/KeyFilterTest.kt index a3ee5160946..8be4ba6109c 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/expressions/KeyFilterTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/expressions/KeyFilterTest.kt @@ -6,10 +6,10 @@ package aws.sdk.kotlin.hll.dynamodbmapper.expressions import aws.sdk.kotlin.hll.dynamodbmapper.expressions.internal.FilterImpl import aws.sdk.kotlin.hll.dynamodbmapper.expressions.internal.toExpression -import aws.sdk.kotlin.hll.dynamodbmapper.items.ItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.items.ItemSchema import aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec import aws.sdk.kotlin.hll.dynamodbmapper.model.Item +import aws.sdk.kotlin.hll.mapping.core.converters.Converter import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertFailsWith @@ -60,7 +60,4 @@ class KeyFilterTest { } } -object DummyConverter : ItemConverter { - override fun convertFrom(to: Item) = error("Not needed") - override fun convertTo(from: Any, onlyAttributes: Set?) = error("Not needed") -} +val DummyConverter = Converter({ error("Not needed") }, { error("Not needed") }) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverterTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverterTest.kt index 1b580fbc3f2..5baab9c825d 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverterTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/items/SimpleItemConverterTest.kt @@ -4,9 +4,10 @@ */ package aws.sdk.kotlin.hll.dynamodbmapper.items -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.BooleanConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.model.intersectKeys +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.BooleanValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertTrue @@ -17,20 +18,20 @@ class SimpleItemConverterTest { val converter = SimpleItemConverter( ::ProductBuilder, ProductBuilder::build, - AttributeDescriptor("id", Product::id, ProductBuilder::id::set, IntConverter), - AttributeDescriptor("name", Product::name, ProductBuilder::name::set, StringConverter), - AttributeDescriptor("in-stock", Product::inStock, ProductBuilder::inStock::set, BooleanConverter), + AttributeDescriptor("id", Product::id, ProductBuilder::id::set, NumberValueConverters.Int), + AttributeDescriptor("name", Product::name, ProductBuilder::name::set, StringValueConverter), + AttributeDescriptor("in-stock", Product::inStock, ProductBuilder::inStock::set, BooleanValueConverter), ) val foo = Product(42, "Foo 2.0", inStock = true) - val item = converter.convertTo(foo) + val item = converter.convertRight(foo) assertEquals(3, item.size) assertEquals(42, item.getValue("id").asN().toInt()) assertEquals("Foo 2.0", item.getValue("name").asS()) assertTrue(item.getValue("in-stock").asBool()) - val unconverted = converter.convertFrom(item) + val unconverted = converter.convertLeft(item) assertEquals(foo, unconverted) } @@ -39,13 +40,13 @@ class SimpleItemConverterTest { val converter = SimpleItemConverter( ::ProductBuilder, ProductBuilder::build, - AttributeDescriptor("id", Product::id, ProductBuilder::id::set, IntConverter), - AttributeDescriptor("name", Product::name, ProductBuilder::name::set, StringConverter), - AttributeDescriptor("in-stock", Product::inStock, ProductBuilder::inStock::set, BooleanConverter), + AttributeDescriptor("id", Product::id, ProductBuilder::id::set, NumberValueConverters.Int), + AttributeDescriptor("name", Product::name, ProductBuilder::name::set, StringValueConverter), + AttributeDescriptor("in-stock", Product::inStock, ProductBuilder::inStock::set, BooleanValueConverter), ) val foo = Product(42, "Foo 2.0", inStock = true) - val item = converter.convertTo(foo, setOf("id", "name")) + val item = converter.convertRight(foo).intersectKeys(setOf("id", "name")) assertEquals(2, item.size) assertEquals(42, item.getValue("id").asN().toInt()) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverterTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableValueConverterTest.kt similarity index 58% rename from hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverterTest.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableValueConverterTest.kt index 1f2f01d470a..e892ddf4ec2 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableConverterTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/NullableValueConverterTest.kt @@ -4,14 +4,14 @@ */ package aws.sdk.kotlin.hll.dynamodbmapper.values -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.sdk.kotlin.hll.mapping.core.converters.andThenTo +import aws.sdk.kotlin.hll.mapping.core.converters.plus import kotlin.test.Test -class NullableConverterTest : ValueConvertersTest() { +class NullableValueConverterTest : ValueConvertersTest() { @Test - fun testNullConverter() = given(NullableConverter(stringReverseConverter)) { + fun testNullConverter() = given(NullableValueConverter(stringReverseConverter)) { "foo" inDdbIs "oof" "bar" inDdbIs "rab" null inDdbIs theSame @@ -19,4 +19,4 @@ class NullableConverterTest : ValueConvertersTest() { } } -private val stringReverseConverter = Converter(String::reversed, String::reversed).andThenTo(StringConverter) +private val stringReverseConverter = Converter(String::reversed, String::reversed) + StringValueConverter diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/ValueConvertersTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/ValueConvertersTest.kt index 2077b365a7f..f8e8d2f7271 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/ValueConvertersTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/ValueConvertersTest.kt @@ -7,7 +7,6 @@ package aws.sdk.kotlin.hll.dynamodbmapper.values import aws.sdk.kotlin.hll.dynamodbmapper.util.attr import aws.sdk.kotlin.hll.dynamodbmapper.util.dynamicAttr import aws.sdk.kotlin.services.dynamodb.model.AttributeValue -import kotlin.jvm.JvmName import kotlin.test.assertContentEquals import kotlin.test.assertEquals import kotlin.test.assertTrue @@ -55,12 +54,12 @@ abstract class ValueConvertersTest { steps.forEach { (direction, highLevel, lowLevel) -> when (direction) { Direction.TO_ATTRIBUTE_VALUE -> { - val result = runCatching { converter.convertTo(highLevel.requireInput()) } + val result = runCatching { converter.convertRight(highLevel.requireInput()) } lowLevel.assert(result, "Test $index failed converting to attribute value") } Direction.FROM_ATTRIBUTE_VALUE -> { - val result = runCatching { converter.convertFrom(lowLevel.requireInput()) } + val result = runCatching { converter.convertLeft(lowLevel.requireInput()) } highLevel.assert(result, "Test $index failed converting from attribute value") } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListConverterTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListValueConverterTest.kt similarity index 64% rename from hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListConverterTest.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListValueConverterTest.kt index cc67cfde4d4..87012d71474 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListConverterTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/ListValueConverterTest.kt @@ -7,12 +7,13 @@ package aws.sdk.kotlin.hll.dynamodbmapper.values.collections import aws.sdk.kotlin.hll.dynamodbmapper.util.attr import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConvertersTest +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import kotlin.test.Test -class ListConverterTest : ValueConvertersTest() { +class ListValueConverterTest : ValueConvertersTest() { @Test - fun testListConverter() = given(ListConverter(FooConverter)) { + fun testListConverter() = given(ListValueConverter(FooConverter)) { listOf(Foo("apple", 1), Foo("banana", 2), Foo("cherry", 3)) inDdbIs listOf( mapOf("bar" to "apple", "baz" to 1), mapOf("bar" to "banana", "baz" to 2), @@ -28,17 +29,19 @@ class ListConverterTest : ValueConvertersTest() { private data class Foo(val bar: String, val baz: Int) private object FooConverter : ValueConverter { - override fun convertFrom(to: AttributeValue): Foo { - val map = to.asM() + override val left: MonoConverter = MonoConverter { value -> + val map = value.asM() val bar = map.getValue("bar").asS() val baz = map.getValue("baz").asN().toInt() - return Foo(bar, baz) + Foo(bar, baz) } - override fun convertTo(from: Foo) = AttributeValue.M( - mapOf( - "bar" to attr(from.bar), - "baz" to attr(from.baz), - ), - ) + override val right: MonoConverter = MonoConverter { obj -> + AttributeValue.M( + mapOf( + "bar" to attr(obj.bar), + "baz" to attr(obj.baz), + ), + ) + } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapConverterTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapValueConverterTest.kt similarity index 66% rename from hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapConverterTest.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapValueConverterTest.kt index a9e65525349..0d8deede145 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapConverterTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/MapValueConverterTest.kt @@ -7,12 +7,13 @@ package aws.sdk.kotlin.hll.dynamodbmapper.values.collections import aws.sdk.kotlin.hll.dynamodbmapper.util.attr import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConverter import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConvertersTest +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import kotlin.test.Test -class MapConverterTest : ValueConvertersTest() { +class MapValueConverterTest : ValueConvertersTest() { @Test - fun testMapConverter() = given(MapConverter(BarConverter)) { + fun testMapConverter() = given(MapValueConverter(BarConverter)) { mapOf("short" to Bar(false, "meh"), "long" to Bar(true, "m", "e", "h")) inDdbIs mapOf( "short" to listOf(false, "meh"), "long" to listOf(true, "m", "e", "h"), @@ -27,12 +28,15 @@ private data class Bar(val foo: Boolean, val baz: List) { } private object BarConverter : ValueConverter { - override fun convertFrom(to: AttributeValue): Bar { - val list = to.asL() + override val left: MonoConverter = MonoConverter { value -> + val list = value.asL() val foo = list.first().asBool() val baz = list.drop(1).map { it.asS() } - return Bar(foo, baz) + Bar(foo, baz) } - override fun convertTo(from: Bar) = AttributeValue.L(listOf(attr(from.foo)) + from.baz.map(::attr)) + override val right: MonoConverter = MonoConverter { obj -> + val list = listOf(attr(obj.foo)) + obj.baz.map(::attr) + AttributeValue.L(list) + } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/SetConvertersTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/SetValueConvertersTest.kt similarity index 72% rename from hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/SetConvertersTest.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/SetValueConvertersTest.kt index 8b2a32b19f1..c8c75865d33 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/SetConvertersTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/collections/SetValueConvertersTest.kt @@ -10,7 +10,7 @@ import kotlin.test.Test private val emptyNumberSet = AttributeValue.Ns(listOf()) -class SetConvertersTest : ValueConvertersTest() { +class SetValueConvertersTest : ValueConvertersTest() { @Test fun testByteArraySetConverter() = given(ByteArraySetConverter) { setOf(byteArrayOf(1, 1, 2, 3), byteArrayOf(5, 8), byteArrayOf(13, 21, 34, 55, 89)) inDdbIs theSame @@ -18,73 +18,73 @@ class SetConvertersTest : ValueConvertersTest() { } @Test - fun testByteSetConverter() = given(ByteSetConverter) { + fun testByteSetConverter() = given(NumberSetValueConverters.Byte) { setOf(1.toByte(), 5.toByte(), Byte.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testCharSetConverter() = given(CharSetConverter) { + fun testCharSetConverter() = given(CharSetValueConverter) { setOf('a', 'b', 'A', 'B') inDdbIs setOf("a", "b", "A", "B") setOf() inDdbIs AttributeValue.Ss(listOf()) } @Test - fun testDoubleSetConverter() = given(DoubleSetConverter) { + fun testDoubleSetConverter() = given(NumberSetValueConverters.Double) { setOf(1.0, -3.14159, Double.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testFloatSetConverter() = given(FloatSetConverter) { + fun testFloatSetConverter() = given(NumberSetValueConverters.Float) { setOf(1.0f, -3.14159f, Float.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testIntSetConverter() = given(IntSetConverter) { + fun testIntSetConverter() = given(NumberSetValueConverters.Int) { setOf(392, -5_129_352, Int.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testLongSetConverter() = given(LongSetConverter) { + fun testLongSetConverter() = given(NumberSetValueConverters.Long) { setOf(392L, -5_129_352_000_000_000L, Long.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testShortSetConverter() = given(ShortSetConverter) { + fun testShortSetConverter() = given(NumberSetValueConverters.Short) { setOf(392.toShort(), (-1024).toShort(), Short.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun tesStringSetConverter() = given(StringSetConverter) { + fun tesStringSetConverter() = given(StringSetValueConverter) { setOf("The", "quick", "brown", "fox", "jumped", "over", "the", "lazy", "dogs") inDdbIs theSame setOf() inDdbIs AttributeValue.Ss(listOf()) } @Test - fun testUByteSetConverter() = given(UByteSetConverter) { + fun testUByteSetConverter() = given(NumberSetValueConverters.UByte) { setOf(1.toUByte(), (Byte.MAX_VALUE.toInt() + 1).toUByte(), UByte.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testUIntSetConverter() = given(UIntSetConverter) { + fun testUIntSetConverter() = given(NumberSetValueConverters.UInt) { setOf(392u, Int.MAX_VALUE.toUInt() + 1u, UInt.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testULongSetConverter() = given(ULongSetConverter) { + fun testULongSetConverter() = given(NumberSetValueConverters.ULong) { setOf(392uL, Long.MAX_VALUE.toULong() + 1uL, ULong.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } @Test - fun testUShortSetConverter() = given(UShortSetConverter) { + fun testUShortSetConverter() = given(NumberSetValueConverters.UShort) { setOf(392.toUShort(), (Short.MAX_VALUE.toInt() + 1).toUShort(), UShort.MAX_VALUE) inDdbIs theSame setOf() inDdbIs emptyNumberSet } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ScalarConvertersTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ScalarValueConvertersTest.kt similarity index 72% rename from hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ScalarConvertersTest.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ScalarValueConvertersTest.kt index 18a2ecb9053..22821e6aed2 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ScalarConvertersTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/scalars/ScalarValueConvertersTest.kt @@ -8,42 +8,42 @@ import aws.sdk.kotlin.hll.dynamodbmapper.values.ValueConvertersTest import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import kotlin.test.Test -class ScalarConvertersTest : ValueConvertersTest() { +class ScalarValueConvertersTest : ValueConvertersTest() { @Test - fun testBooleanConverter() = given(BooleanConverter) { + fun testBooleanConverter() = given(BooleanValueConverter) { true inDdbIs theSame false inDdbIs theSame } @Test - fun testByteArrayConverter() = given(ByteArrayConverter) { + fun testByteArrayConverter() = given(ByteArrayValueConverter) { byteArrayOf() inDdbIs theSame "Foo".encodeToByteArray() inDdbIs theSame ByteArray(1024) { it.toByte() } inDdbIs theSame } @Test - fun testByteConverter() = given(ByteConverter) { + fun testByteConverter() = given(NumberValueConverters.Byte) { 1.toByte() inDdbIs theSame 47.toByte() inDdbIs theSame Byte.MIN_VALUE inDdbIs theSame } @Test - fun testCharArrayConverter() = given(CharArrayConverter) { + fun testCharArrayConverter() = given(CharArrayValueConverter) { charArrayOf() inDdbIs "" charArrayOf('G', 'u', 'i', 'n', 'e', 'a', ' ', 'p', 'i', 'g') inDdbIs "Guinea pig" } @Test - fun testCharConverter() = given(CharConverter) { + fun testCharConverter() = given(CharValueConverter) { '!' inDdbIs "!" 'X' inDdbIs "X" '7' inDdbIs "7" } @Test - fun testDoubleConverter() = given(DoubleConverter) { + fun testDoubleConverter() = given(NumberValueConverters.Double) { (-1.41421) inDdbIs theSame 2.71828 inDdbIs theSame 3.14159 inDdbIs theSame @@ -53,7 +53,7 @@ class ScalarConvertersTest : ValueConvertersTest() { } @Test - fun testEnumConverter() = given(EnumConverter()) { + fun testEnumConverter() = given(EnumValueConverter()) { Suit.HEARTS inDdbIs "HEARTS" Suit.DIAMONDS inDdbIs "DIAMONDS" Suit.CLUBS inDdbIs "CLUBS" @@ -61,7 +61,7 @@ class ScalarConvertersTest : ValueConvertersTest() { } @Test - fun testFloatConverter() = given(FloatConverter) { + fun testFloatConverter() = given(NumberValueConverters.Float) { (-1.73205f) inDdbIs theSame 1.61803f inDdbIs theSame 2.68545f inDdbIs theSame @@ -70,28 +70,28 @@ class ScalarConvertersTest : ValueConvertersTest() { } @Test - fun testIntConverter() = given(IntConverter) { + fun testIntConverter() = given(NumberValueConverters.Int) { 0 inDdbIs theSame 1_000_000 inDdbIs theSame Int.MIN_VALUE inDdbIs theSame } @Test - fun testLongConverter() = given(LongConverter) { + fun testLongConverter() = given(NumberValueConverters.Long) { 31_536_000L inDdbIs theSame 9_460_730_472_580_800L inDdbIs theSame Long.MIN_VALUE inDdbIs theSame } @Test - fun testShortConverter() = given(ShortConverter) { + fun testShortConverter() = given(NumberValueConverters.Short) { 1.toShort() inDdbIs theSame 47.toShort() inDdbIs theSame Short.MIN_VALUE inDdbIs theSame } @Test - fun testStringConverter() = given(StringConverter) { + fun testStringConverter() = given(StringValueConverter) { "The quick brown fox jumped over the lazy dogs" inDdbIs theSame "Jackdaws love my big sphinx of quartz" inDdbIs theSame """ @@ -101,28 +101,28 @@ class ScalarConvertersTest : ValueConvertersTest() { } @Test - fun testUByteConverter() = given(UByteConverter) { + fun testUByteConverter() = given(NumberValueConverters.UByte) { 1.toUByte() inDdbIs 1 47.toUByte() inDdbIs 47 UByte.MAX_VALUE inDdbIs UByte.MAX_VALUE.toInt() } @Test - fun testUIntConverter() = given(UIntConverter) { + fun testUIntConverter() = given(NumberValueConverters.UInt) { 0u inDdbIs 0 1_000_000u inDdbIs 1_000_000 UInt.MAX_VALUE inDdbIs UInt.MAX_VALUE.toLong() } @Test - fun testULongConverter() = given(ULongConverter) { + fun testULongConverter() = given(NumberValueConverters.ULong) { 31_536_000uL inDdbIs 31_536_000L 9_460_730_472_580_800uL inDdbIs 9_460_730_472_580_800L ULong.MAX_VALUE inDdbIs AttributeValue.N(ULong.MAX_VALUE.toString()) } @Test - fun testUShortConverter() = given(UShortConverter) { + fun testUShortConverter() = given(NumberValueConverters.UShort) { 1.toUShort() inDdbIs 1 47.toUShort() inDdbIs 47 UShort.MAX_VALUE inDdbIs UShort.MAX_VALUE.toInt() diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverterTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverterTest.kt index e0daa9843d1..7b94d57d1e1 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverterTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/DocumentValueConverterTest.kt @@ -10,7 +10,7 @@ import kotlin.test.Test class DocumentValueConverterTest : ValueConvertersTest() { @Test - fun testKitchenSink() = given(DocumentConverter.Default) { + fun testKitchenSink() = given(DocumentValueConverter.Default) { val expectedDocument = buildDocument { "name" to "Ian" "pets" to buildList { diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConvertersTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverterTest.kt similarity index 84% rename from hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConvertersTest.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverterTest.kt index cd49217b39d..09326a0f5d3 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantConvertersTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/InstantValueConverterTest.kt @@ -13,22 +13,22 @@ private val MS_TIME = Instant.fromEpochSeconds(1234567890L, 123000000) // 2009-0 private val MICRO_TIME = Instant.fromEpochSeconds(1234567890L, 123456000) // 2009-02-13T23:31:30.123456Z private val NS_TIME = Instant.fromEpochSeconds(1234567890L, 123456789) // 2009-02-13T23:31:30.123456789Z -class InstantConvertersTest : ValueConvertersTest() { +class InstantValueConverterTest : ValueConvertersTest() { @Test - fun testEpochS() = given(InstantConverter.EpochS) { + fun testEpochS() = given(InstantValueConverter.EpochS) { WHOLE_TIME inDdbIs 1234567890L NS_TIME inDdbIs 1234567890L whenGoing Direction.TO_ATTRIBUTE_VALUE } @Test - fun testEpochMs() = given(InstantConverter.EpochMs) { + fun testEpochMs() = given(InstantValueConverter.EpochMs) { WHOLE_TIME inDdbIs 1234567890000L NS_TIME inDdbIs 1234567890123L whenGoing Direction.TO_ATTRIBUTE_VALUE MS_TIME inDdbIs 1234567890123L whenGoing Direction.FROM_ATTRIBUTE_VALUE } @Test - fun testIso8601() = given(InstantConverter.Iso8601) { + fun testIso8601() = given(InstantValueConverter.Iso8601) { WHOLE_TIME inDdbIs "2009-02-13T23:31:30Z" MS_TIME inDdbIs "2009-02-13T23:31:30.123Z" MICRO_TIME inDdbIs "2009-02-13T23:31:30.123456Z" diff --git a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlConverterTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlValueConverterTest.kt similarity index 79% rename from hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlConverterTest.kt rename to hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlValueConverterTest.kt index 6c57585379d..1817de5926a 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlConverterTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/common/test/aws/sdk/kotlin/hll/dynamodbmapper/values/smithytypes/UrlValueConverterTest.kt @@ -10,9 +10,9 @@ import kotlin.test.Test private const val URL = "https://foo.bar.baz/qux?quux=corge#grault" -class UrlConverterTest : ValueConvertersTest() { +class UrlValueConverterTest : ValueConvertersTest() { @Test - fun testUrlConverter() = given(UrlConverter) { + fun testUrlConverter() = given(UrlValueConverter) { Url.parse(URL) inDdbIs URL } } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/DynamoDbMapperTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/DynamoDbMapperTest.kt index 5568cead1bd..476f92a242c 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/DynamoDbMapperTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/DynamoDbMapperTest.kt @@ -10,8 +10,8 @@ import aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.operations.scanPaginated import aws.sdk.kotlin.hll.dynamodbmapper.testutils.DdbLocalTest -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import aws.sdk.kotlin.runtime.http.interceptors.businessmetrics.AwsBusinessMetric import aws.sdk.kotlin.services.dynamodb.scan import aws.sdk.kotlin.services.dynamodb.withConfig @@ -35,8 +35,8 @@ class DynamoDbMapperTest : DdbLocalTest() { private val dummyConverter = SimpleItemConverter( ::DummyData, { this }, - AttributeDescriptor("foo", DummyData::foo, DummyData::foo::set, StringConverter), - AttributeDescriptor("bar", DummyData::bar, DummyData::bar::set, IntConverter), + AttributeDescriptor("foo", DummyData::foo, DummyData::foo::set, StringValueConverter), + AttributeDescriptor("bar", DummyData::bar, DummyData::bar::set, NumberValueConverters.Int), ) private val dummySchema = ItemSchema(dummyConverter, KeySpec.String("foo"), KeySpec.Number("bar")) @@ -72,7 +72,7 @@ class DynamoDbMapperTest : DdbLocalTest() { interceptor.reset() // Original client can be closed, mapper is unaffected - lowLevelAccess { close() } + lowLevelAccess { close() } table.scanPaginated { }.collect() interceptor.assertMetric(AwsBusinessMetric.DDB_MAPPER) } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/DeleteItemTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/DeleteItemTest.kt index 8c56a0d6eb2..ce9749252c3 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/DeleteItemTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/DeleteItemTest.kt @@ -10,8 +10,8 @@ import aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.model.itemOf import aws.sdk.kotlin.hll.dynamodbmapper.testutils.DdbLocalTest -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import aws.sdk.kotlin.services.dynamodb.model.ReturnConsumedCapacity import aws.sdk.kotlin.services.dynamodb.model.ReturnValue import kotlinx.coroutines.test.runTest @@ -27,8 +27,8 @@ class DeleteItemTest : DdbLocalTest() { private val converter = SimpleItemConverter( ::Item, { this }, - AttributeDescriptor("id", Item::id, Item::id::set, StringConverter), - AttributeDescriptor("value", Item::value, Item::value::set, IntConverter), + AttributeDescriptor("id", Item::id, Item::id::set, StringValueConverter), + AttributeDescriptor("value", Item::value, Item::value::set, NumberValueConverters.Int), ) private val schema = ItemSchema(converter, KeySpec.String("id")) } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/GetItemTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/GetItemTest.kt index 9e88245103e..9fb730e62be 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/GetItemTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/GetItemTest.kt @@ -11,8 +11,8 @@ import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.model.Table import aws.sdk.kotlin.hll.dynamodbmapper.model.itemOf import aws.sdk.kotlin.hll.dynamodbmapper.testutils.DdbLocalTest -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import aws.sdk.kotlin.services.dynamodb.model.ReturnConsumedCapacity import kotlinx.coroutines.test.runTest import kotlin.test.assertEquals @@ -29,8 +29,8 @@ class GetItemTest : DdbLocalTest() { private val pkConverter = SimpleItemConverter( ::PkItem, { this }, - AttributeDescriptor("id", PkItem::id, PkItem::id::set, IntConverter), - AttributeDescriptor("value", PkItem::value, PkItem::value::set, StringConverter), + AttributeDescriptor("id", PkItem::id, PkItem::id::set, NumberValueConverters.Int), + AttributeDescriptor("value", PkItem::value, PkItem::value::set, StringValueConverter), ) private val pkSchema = ItemSchema(pkConverter, KeySpec.Number("id")) @@ -39,9 +39,9 @@ class GetItemTest : DdbLocalTest() { private val ckConverter = SimpleItemConverter( ::CkItem, { this }, - AttributeDescriptor("id", CkItem::id, CkItem::id::set, StringConverter), - AttributeDescriptor("version", CkItem::version, CkItem::version::set, IntConverter), - AttributeDescriptor("value", CkItem::value, CkItem::value::set, StringConverter), + AttributeDescriptor("id", CkItem::id, CkItem::id::set, StringValueConverter), + AttributeDescriptor("version", CkItem::version, CkItem::version::set, NumberValueConverters.Int), + AttributeDescriptor("value", CkItem::value, CkItem::value::set, StringValueConverter), ) private val ckSchema = ItemSchema(ckConverter, KeySpec.String("id"), KeySpec.Number("version")) } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PaginatedScanTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PaginatedScanTest.kt index 71acfb4034d..6fb7fc60d35 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PaginatedScanTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PaginatedScanTest.kt @@ -5,12 +5,14 @@ package aws.sdk.kotlin.hll.dynamodbmapper.operations -import aws.sdk.kotlin.hll.dynamodbmapper.items.* -import aws.sdk.kotlin.hll.dynamodbmapper.model.Item +import aws.sdk.kotlin.hll.dynamodbmapper.items.AttributeDescriptor +import aws.sdk.kotlin.hll.dynamodbmapper.items.ItemSchema +import aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec +import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.model.itemOf import aws.sdk.kotlin.hll.dynamodbmapper.testutils.DdbLocalTest -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import kotlinx.coroutines.flow.map import kotlinx.coroutines.flow.toSet import kotlinx.coroutines.test.runTest @@ -41,20 +43,13 @@ class PaginatedScanTest : DdbLocalTest() { override fun toString() = "$rankName of $suit" // Easier when debugging big outputs } - private val converter = object : ItemConverter { - val delegate = SimpleItemConverter( - ::Card, - { this }, - AttributeDescriptor("rank", Card::rank, Card::rank::set, IntConverter), - AttributeDescriptor("suit", Card::suit, Card::suit::set, StringConverter), - AttributeDescriptor("description", Card::description, Card::description::set, StringConverter), - ) - - override fun convertFrom(to: Item): Card = delegate.convertFrom(to) - - override fun convertTo(from: Card, onlyAttributes: Set?): Item = - delegate.convertTo(from, null) // Ignore `onlyAttributes` arg to mock badly-behaved converter - } + private val converter = SimpleItemConverter( + ::Card, + { this }, + AttributeDescriptor("rank", Card::rank, Card::rank::set, NumberValueConverters.Int), + AttributeDescriptor("suit", Card::suit, Card::suit::set, StringValueConverter), + AttributeDescriptor("description", Card::description, Card::description::set, StringValueConverter), + ) private val schema = ItemSchema(converter, KeySpec.String("suit"), KeySpec.Number("rank")) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PutItemTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PutItemTest.kt index 389b9a6f755..95d4f9d99ae 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PutItemTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/PutItemTest.kt @@ -10,8 +10,8 @@ import aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.testutils.DdbLocalTest import aws.sdk.kotlin.hll.dynamodbmapper.testutils.getItem -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import kotlinx.coroutines.test.runTest import kotlin.test.assertEquals import kotlin.test.assertNotNull @@ -25,8 +25,8 @@ class PutItemTest : DdbLocalTest() { private val converter = SimpleItemConverter( ::Item, { this }, - AttributeDescriptor("id", Item::id, Item::id::set, StringConverter), - AttributeDescriptor("value", Item::value, Item::value::set, IntConverter), + AttributeDescriptor("id", Item::id, Item::id::set, StringValueConverter), + AttributeDescriptor("value", Item::value, Item::value::set, NumberValueConverters.Int), ) private val schema = ItemSchema(converter, KeySpec.String("id")) } diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/QueryTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/QueryTest.kt index fce2dedfdfd..e894ea1300a 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/QueryTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/QueryTest.kt @@ -11,8 +11,8 @@ import aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.model.itemOf import aws.sdk.kotlin.hll.dynamodbmapper.testutils.DdbLocalTest -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter import kotlinx.coroutines.flow.toList import kotlinx.coroutines.test.runTest import kotlin.test.assertContentEquals @@ -34,11 +34,11 @@ class QueryTest : DdbLocalTest() { private val empConverter = SimpleItemConverter( ::NamedEmp, { this }, - AttributeDescriptor("companyId", NamedEmp::companyId, NamedEmp::companyId::set, StringConverter), - AttributeDescriptor("empId", NamedEmp::empId, NamedEmp::empId::set, StringConverter), - AttributeDescriptor("name", NamedEmp::name, NamedEmp::name::set, StringConverter), - AttributeDescriptor("title", NamedEmp::title, NamedEmp::title::set, StringConverter), - AttributeDescriptor("tenureYears", NamedEmp::tenureYears, NamedEmp::tenureYears::set, IntConverter), + AttributeDescriptor("companyId", NamedEmp::companyId, NamedEmp::companyId::set, StringValueConverter), + AttributeDescriptor("empId", NamedEmp::empId, NamedEmp::empId::set, StringValueConverter), + AttributeDescriptor("name", NamedEmp::name, NamedEmp::name::set, StringValueConverter), + AttributeDescriptor("title", NamedEmp::title, NamedEmp::title::set, StringValueConverter), + AttributeDescriptor("tenureYears", NamedEmp::tenureYears, NamedEmp::tenureYears::set, NumberValueConverters.Int), ) private val namedEmpSchema = ItemSchema(empConverter, KeySpec.String("companyId"), KeySpec.String("empId")) @@ -54,10 +54,10 @@ class QueryTest : DdbLocalTest() { private val titleConverter = SimpleItemConverter( ::TitleEmp, { this }, - AttributeDescriptor("title", TitleEmp::title, TitleEmp::title::set, StringConverter), - AttributeDescriptor("name", TitleEmp::name, TitleEmp::name::set, StringConverter), - AttributeDescriptor("empId", TitleEmp::empId, TitleEmp::empId::set, StringConverter), - AttributeDescriptor("companyId", TitleEmp::companyId, TitleEmp::companyId::set, StringConverter), + AttributeDescriptor("title", TitleEmp::title, TitleEmp::title::set, StringValueConverter), + AttributeDescriptor("name", TitleEmp::name, TitleEmp::name::set, StringValueConverter), + AttributeDescriptor("empId", TitleEmp::empId, TitleEmp::empId::set, StringValueConverter), + AttributeDescriptor("companyId", TitleEmp::companyId, TitleEmp::companyId::set, StringValueConverter), ) private val titleSchema = ItemSchema(titleConverter, KeySpec.String("title"), KeySpec.String("name")) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/ScanTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/ScanTest.kt index 8758d4f0b99..4e2fc01d6b2 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/ScanTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/operations/ScanTest.kt @@ -10,9 +10,9 @@ import aws.sdk.kotlin.hll.dynamodbmapper.items.KeySpec import aws.sdk.kotlin.hll.dynamodbmapper.items.SimpleItemConverter import aws.sdk.kotlin.hll.dynamodbmapper.model.itemOf import aws.sdk.kotlin.hll.dynamodbmapper.testutils.DdbLocalTest -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.IntConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringConverter -import aws.sdk.kotlin.hll.dynamodbmapper.values.smithytypes.InstantConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.NumberValueConverters +import aws.sdk.kotlin.hll.dynamodbmapper.values.scalars.StringValueConverter +import aws.sdk.kotlin.hll.dynamodbmapper.values.smithytypes.InstantValueConverter import aws.smithy.kotlin.runtime.time.Instant import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.map @@ -34,10 +34,10 @@ class ScanTest : DdbLocalTest() { private val converter = SimpleItemConverter( ::Product, { this }, - AttributeDescriptor("id", Product::id, Product::id::set, IntConverter), - AttributeDescriptor("name", Product::name, Product::name::set, StringConverter), - AttributeDescriptor("modelNumber", Product::modelNumber, Product::modelNumber::set, StringConverter), - AttributeDescriptor("released", Product::released, Product::released::set, InstantConverter.Iso8601), + AttributeDescriptor("id", Product::id, Product::id::set, NumberValueConverters.Int), + AttributeDescriptor("name", Product::name, Product::name::set, StringValueConverter), + AttributeDescriptor("modelNumber", Product::modelNumber, Product::modelNumber::set, StringValueConverter), + AttributeDescriptor("released", Product::released, Product::released::set, InstantValueConverter.Iso8601), ) private val schema = ItemSchema(converter, KeySpec.Number("id")) diff --git a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/pipeline/internal/OperationTest.kt b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/pipeline/internal/OperationTest.kt index d758cb581f4..efc5bb76ff5 100644 --- a/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/pipeline/internal/OperationTest.kt +++ b/hll/dynamodb-mapper/dynamodb-mapper/jvm/test/aws/sdk/kotlin/hll/dynamodbmapper/pipeline/internal/OperationTest.kt @@ -12,7 +12,11 @@ import aws.sdk.kotlin.hll.dynamodbmapper.items.withKeySpec import aws.sdk.kotlin.hll.dynamodbmapper.model.Item import aws.sdk.kotlin.hll.dynamodbmapper.model.PersistenceSpec import aws.sdk.kotlin.hll.dynamodbmapper.model.itemOf -import aws.sdk.kotlin.hll.dynamodbmapper.pipeline.* +import aws.sdk.kotlin.hll.dynamodbmapper.pipeline.HReqContext +import aws.sdk.kotlin.hll.dynamodbmapper.pipeline.Interceptor +import aws.sdk.kotlin.hll.dynamodbmapper.pipeline.InterceptorAny +import aws.sdk.kotlin.hll.dynamodbmapper.pipeline.LReqContext +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter import aws.sdk.kotlin.services.dynamodb.model.AttributeValue import io.mockk.* import kotlinx.coroutines.test.runTest @@ -167,8 +171,13 @@ class OperationTest { private data class Foo(val value: String) private val fooConverter = object : ItemConverter { - override fun convertFrom(to: Item): Foo = Foo(to["foo"]!!.asS()) - override fun convertTo(from: Foo, onlyAttributes: Set?): Item = itemOf("foo" to AttributeValue.S(from.value)) + override val left: MonoConverter = MonoConverter { item -> + Foo(item["foo"]!!.asS()) + } + + override val right: MonoConverter = MonoConverter { obj -> + itemOf("foo" to AttributeValue.S(obj.value)) + } } private val fooSchema = fooConverter.withKeySpec(KeySpec.String("foo")) @@ -178,9 +187,9 @@ private data class LFooResponse(val foo: Item) private data class HFooResponse(val foo: Foo) private fun HFooRequest.convert(table: String, schema: ItemSchema) = - LFooRequest(table, schema.converter.convertTo(foo)) + LFooRequest(table, schema.converter.convertRight(foo)) private fun LFooResponse.convert(schema: ItemSchema) = - HFooResponse(schema.converter.convertFrom(foo)) + HFooResponse(schema.converter.convertLeft(foo)) private suspend fun dummyInvoke(req: LFooRequest) = LFooResponse(req.foo) diff --git a/hll/hll-codegen/src/main/kotlin/aws/sdk/kotlin/hll/codegen/core/TemplateProcessor.kt b/hll/hll-codegen/src/main/kotlin/aws/sdk/kotlin/hll/codegen/core/TemplateProcessor.kt index d91df6df871..06a5f6b271f 100644 --- a/hll/hll-codegen/src/main/kotlin/aws/sdk/kotlin/hll/codegen/core/TemplateProcessor.kt +++ b/hll/hll-codegen/src/main/kotlin/aws/sdk/kotlin/hll/codegen/core/TemplateProcessor.kt @@ -81,7 +81,7 @@ private class ImportingTypeProcessor(private val pkg: String, private val import if (existingImport == null) { imports += ImportDirective("${type.pkg}.${type.baseName}") - } else if (existingImport.fullName != type.fullName) { + } else if (existingImport.fullName != "${type.pkg}.${type.baseName}") { append(type.pkg) append('.') } diff --git a/hll/hll-mapping-core/README.md b/hll/hll-mapping-core/README.md new file mode 100644 index 00000000000..06d8874c878 --- /dev/null +++ b/hll/hll-mapping-core/README.md @@ -0,0 +1,157 @@ +# HLL Converters + +This module provides a framework for typed data mapping, including base interfaces and some reusable implementations. +This document describes the theory behind the conversion framework and how it may be applied. + +## Terminology + +In the context of this library, the following terms are used: + +* **Converter** — an object capable of bidirectional data mapping between two types, referred to as **left** and + **right**. A **converter** may be implemented as two symmetrical **mono-converters** +* **Mono-converter** — an object capable of data mapping from one type into another type. A mono-converter which + performs the _reverse_ data mapping of another mono-converter is said to be **symmetrical** to the other and vice + versa. **Symmetrical** **mono-converters** are the typical implementation of **converters**, which would then perform + data mapping by delegating to the appropriate **mono-converter** for the transformation direction. +* **Left** — the name for the type on one side of a bidirectional data mapping. By convention, this is typically used to + represent types that are closer to your application or business logic. One may think of **left** types as "my" types. +* **Right** — the name for the type on one side of a bidirectional data mapping. By convention, this is typically used + to represent types that are farther away from your application or business logic. One may think of **right** types as + "their" types. + +## Interfaces + +These two Kotlin interfaces form the basis of typed data mapping: + +```kotlin +fun interface MonoConverter { + fun convert(from: A): B +} + +interface Converter { + val right: MonoConverter + val left: MonoConverter + + fun convertRight(from: L): R = right.convert(from) + fun convertLeft(from: R): L = left.convert(from) +} +``` + +`MonoConverter` (i.e., the mono-converter [described above](#terminology)) is a generic type which maps from `A` to `B`. +`A` is the source type of the conversion (i.e., the input) while `B` is the destination type (i.e., the output). + +`Converter` (i.e., the converter [described above](#terminology)) is a generic type which maps between `L` (the left +type) and `R` (the right type). Implementations are encouraged (but not required) to utilize symmetrical mono-converters +and accept the default implementations of `convertLeft` and `convertRight`. This will maximize the converter's +flexibility when used in [the composition operations described below](#composing-converters). + +### Example usage + +A simple converter that maps between a string and a boolean could be implemented as follows: + +```kotlin +val stringToBoolean = MonoConverter { input: String -> + when (input.lowercase()) { + "yes", "true" -> true + "no", "false" -> false + else -> error("Cannot convert '$input' to Boolean!") + } +} +println(stringToBoolean.convert("yes")) // Prints true +println(stringToBoolean.convert("maybe?")) // Throws exception + +val booleanToString = MonoConverter { input: Boolean -> + when (input) { + true -> "yes" + false -> "no" + } +} + +val converter = Converter(stringToBoolean, booleanToString) +println(converter.convertRight("no")) // Prints false +println(converter.convertLeft(false)) // Prints "no" +``` + +In the preceding code, `stringToBoolean` is a mono-converter that turns `"true"` and `"yes"` into `true` and turns +`"false"` and `"no"` into `false`. Conversely, `booleanToString` turns `true` into `"yes"` and `false` into `"no"`. +`stringToBoolean` and `booleanToString` are symmetrical (i.e., they perform the reverse mapping of each other) and so +they may be combined into a bidirectional converter. + +The factory function `Converter` accepts two symmetrical mono-converters and returns a converter implementation that +delegates to them. The resulting converter uses the first argument (`stringToBoolean`) for rightward conversion and the +second argument (`booleanToString`) for leftward conversion. + +## Composing converters + +Sometimes data transformations are complex or share common logic with other transformations. In these cases, simpler +converters may be reused by composing them. There are two primary forms of composition: + +### Chaining + +Converters may be "chained" together in a series of sequential transformations. In a chain, the output of one converter +becomes the input to another: + +![](docs/img/chaining-converter.png) + +The `+` operator is used to chain individual converters together: + +```kotlin +operator fun Converter.plus(next: Converter): Converter +``` + +Note that the result of chaining two converters is itself a new converter. + +This operator function introduces a new generic variable `M` which represents the **middle** data type. Because a +chained converter passes data from one delegate to the next, the joining types of the converters must be the same. In +other words, the left type of one converter and the right type of the other converter must match. + +The following example shows how to combine to existing converters: + +```kotlin +val shortToInt: Converter = ... +val intToLong: Converter = ... + +val shortToLong: Converter = shortToInt + intToLong +``` + +In the preceding example, `shortToLong` is a chained converter which converts rightward by turning `Short` into `Int` +by delegating to `shortToInt` and then turning the resulting `Int` into `Long` by delegating to `intToLong`. Conversely, +it converts leftward by turning `Long` into `Int` by delegating to `intToLong` and then turning the resulting `Int` into +`Short` by delegating to `shortToInt`. + +Because a chaining operation yields a new converter, it may be further chained with more converters. For example: + +```kotlin +val byteToShort: Converter = ... +val shortToInt: Converter = ... +val intToLong: Converter = ... + +val byteToLong: Converter = byteToShort + shortToInt + intToLong +``` + +### Element mapping + +Converters may be wrapped by a collection converter in order to transform collection elements from one type to another: + +![](docs/img/element-mapping-converter.png) + +Collection converters are typically built using factory functions which accept one or more delegate converters as +arguments. For example: + +```kotlin +fun ListMappingConverter(delegate: Converter): Converter, List> +``` + +The preceding function creates a converter which transforms between `List` and `List` by mapping over each element +and using the delegate converter to transform between element types `L` and `R`. + +The following example illustrates composing an element converter with a list mapping converter: + +```kotlin +val intToLong: Converter = ... +val intListToLongList: Converter, List> = ListMappingConverter(intToLong) +``` + +In the preceding example, `intToLong` is passed as a delegate to the `ListMappingConverter` factory function and a list +mapping converter is returned. When a list is transformed through this converter, each element is passed to the delegate +for individual transformation in either direction. diff --git a/hll/hll-mapping-core/api/hll-mapping-core.api b/hll/hll-mapping-core/api/hll-mapping-core.api index c5289eab9dd..8509abc1b98 100644 --- a/hll/hll-mapping-core/api/hll-mapping-core.api +++ b/hll/hll-mapping-core/api/hll-mapping-core.api @@ -1,121 +1,57 @@ -public abstract interface class aws/sdk/kotlin/hll/mapping/core/converters/Converter : aws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom, aws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo { +public abstract interface class aws/sdk/kotlin/hll/mapping/core/converters/Converter { + public static final field Companion Laws/sdk/kotlin/hll/mapping/core/converters/Converter$Companion; + public fun convertLeft (Ljava/lang/Object;)Ljava/lang/Object; + public fun convertRight (Ljava/lang/Object;)Ljava/lang/Object; + public abstract fun getLeft ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; + public abstract fun getRight ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; } -public final class aws/sdk/kotlin/hll/mapping/core/converters/ConverterKt { - public static final fun Converter (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun andThenFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun andThenTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun validatingFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Lkotlin/jvm/functions/Function1;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun validatingTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Lkotlin/jvm/functions/Function1;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; -} - -public abstract interface class aws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom { - public abstract fun convertFrom (Ljava/lang/Object;)Ljava/lang/Object; -} - -public final class aws/sdk/kotlin/hll/mapping/core/converters/ConvertsFromKt { - public static final fun andThenConvertsFrom (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public static final fun firstValidatingTo (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;Lkotlin/jvm/functions/Function1;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; +public final class aws/sdk/kotlin/hll/mapping/core/converters/Converter$Companion { + public final fun identity ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public abstract interface class aws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo { - public abstract fun convertTo (Ljava/lang/Object;)Ljava/lang/Object; +public final class aws/sdk/kotlin/hll/mapping/core/converters/Converter$DefaultImpls { + public static fun convertLeft (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Ljava/lang/Object;)Ljava/lang/Object; + public static fun convertRight (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Ljava/lang/Object;)Ljava/lang/Object; } -public final class aws/sdk/kotlin/hll/mapping/core/converters/ConvertsToKt { - public static final fun andThenConvertsTo (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public static final fun firstValidatingFrom (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Lkotlin/jvm/functions/Function1;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; +public final class aws/sdk/kotlin/hll/mapping/core/converters/ConverterKt { + public static final fun Converter (Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun plus (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public abstract interface class aws/sdk/kotlin/hll/mapping/core/converters/SplittingConverter : aws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom, aws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo { +public abstract interface class aws/sdk/kotlin/hll/mapping/core/converters/MonoConverter { + public static final field Companion Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter$Companion; + public abstract fun convert (Ljava/lang/Object;)Ljava/lang/Object; } -public final class aws/sdk/kotlin/hll/mapping/core/converters/SplittingConverterKt { - public static final fun mergeBy (Laws/sdk/kotlin/hll/mapping/core/converters/SplittingConverter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; +public final class aws/sdk/kotlin/hll/mapping/core/converters/MonoConverter$Companion { + public final fun identity ()Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; } -public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionTypeConverters { - public static final field INSTANCE Laws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionTypeConverters; +public final class aws/sdk/kotlin/hll/mapping/core/converters/MonoConverterKt { + public static final fun plus (Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;)Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; + public static final fun reversedBy (Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } -public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverters { - public static final field INSTANCE Laws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverters; - public final fun mapConvertsFrom (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun mapConvertsTo (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; +public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionConvertersKt { + public static final fun SetToListConverter ()Laws/sdk/kotlin/hll/mapping/core/converters/Converter; } public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConvertersKt { - public static final fun mapFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; -} - -public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverters { - public static final field INSTANCE Laws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverters; - public final fun mapConvertsFrom (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun mapConvertsKeysFrom (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun mapConvertsKeysTo (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public final fun mapConvertsTo (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public final fun mapConvertsValuesFrom (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun mapConvertsValuesTo (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public final fun ofKeys (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun ofKeys (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun ofKeys (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public final fun ofValues (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun ofValues (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun ofValues (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; + public static final fun ListMappingConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun ListMappingMonoConverter (Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;)Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; } public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConvertersKt { - public static final fun mapFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapKeysFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapKeysTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapValuesFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapValuesTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; -} - -public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverters { - public static final field INSTANCE Laws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverters; - public final fun mapConvertsFrom (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun mapConvertsTo (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom; - public final fun of (Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo;)Laws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo; + public static final fun MapMappingConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun MapMappingConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun MapMappingMonoConverter (Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;)Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; + public static final fun MapMappingMonoConverter (Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;)Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; } public final class aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConvertersKt { - public static final fun mapFrom (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; - public static final fun mapTo (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; -} - -public abstract interface class aws/sdk/kotlin/hll/mapping/core/util/Either { - public static final field Companion Laws/sdk/kotlin/hll/mapping/core/util/Either$Companion; -} - -public final class aws/sdk/kotlin/hll/mapping/core/util/Either$Companion { - public final fun Left (Ljava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/util/Either$Left; - public final fun Right (Ljava/lang/Object;)Laws/sdk/kotlin/hll/mapping/core/util/Either$Right; -} - -public abstract interface class aws/sdk/kotlin/hll/mapping/core/util/Either$Left : aws/sdk/kotlin/hll/mapping/core/util/Either { - public abstract fun getValue ()Ljava/lang/Object; -} - -public abstract interface class aws/sdk/kotlin/hll/mapping/core/util/Either$Right : aws/sdk/kotlin/hll/mapping/core/util/Either { - public abstract fun getValue ()Ljava/lang/Object; -} - -public final class aws/sdk/kotlin/hll/mapping/core/util/EitherKt { - public static final fun fold (Laws/sdk/kotlin/hll/mapping/core/util/Either;Lkotlin/jvm/functions/Function1;Lkotlin/jvm/functions/Function1;)Ljava/lang/Object; - public static final fun map (Laws/sdk/kotlin/hll/mapping/core/util/Either;Lkotlin/jvm/functions/Function1;)Laws/sdk/kotlin/hll/mapping/core/util/Either; - public static final fun merge (Laws/sdk/kotlin/hll/mapping/core/util/Either;)Ljava/lang/Object; + public static final fun SetMappingConverter (Laws/sdk/kotlin/hll/mapping/core/converters/Converter;)Laws/sdk/kotlin/hll/mapping/core/converters/Converter; + public static final fun SetMappingMonoConverter (Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter;)Laws/sdk/kotlin/hll/mapping/core/converters/MonoConverter; } diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/Converter.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/Converter.kt index cbb024960e6..198c5f45e6e 100644 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/Converter.kt +++ b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/Converter.kt @@ -4,77 +4,64 @@ */ package aws.sdk.kotlin.hll.mapping.core.converters +import aws.sdk.kotlin.hll.mapping.core.converters.internal.ConverterImpl import aws.smithy.kotlin.runtime.ExperimentalApi /** - * Models two-way conversion between a type [T] and a type [F] - * @param F The type being converted from - * @param T The type being converted to + * A type for two-way conversion between a **left** type [L] and **right** type [R]. As a general convention, **left** + * is for types which are closer to user code and business logic. Conversely, **right** is for types which are farther + * from user code and business logic. Alternatively, one may think of **left** types as "my" types and **right** types + * as "their" types. Note that these distinctions are often subjective so consult documentation in the library which + * uses this converter for more details and context. + * @param L The **left** type + * @param R The **right** type */ @ExperimentalApi -public interface Converter : - ConvertsTo, - ConvertsFrom +public interface Converter { + public companion object { + public fun identity(): Converter = Converter({ it }, { it }) + } -/** - * Creates a new two-way converter from symmetrical one-way converters - * @param F The type being converted from - * @param T The type being converted to - * @param convertTo A converter instance for converting one-way from [F] to [T] - * @param convertFrom A converter instance for converting one-way from [T] to [F] - */ -@ExperimentalApi -public fun Converter(convertTo: ConvertsTo, convertFrom: ConvertsFrom): Converter = - object : Converter, ConvertsTo by convertTo, ConvertsFrom by convertFrom { } + /** + * Gets a [MonoConverter] that converts from **left** type [L] to **right** type [R] + */ + public val right: MonoConverter -/** - * Chains this converter with another converter, yielding a new converter which performs a two-stage conversion. (Note - * that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps in their actual - * implementation.) - * @param F The source type of this converter - * @param T The target type of this converter and the source type of the given [converter] - * @param T2 The target type of the given [converter] - * @param converter The converter to chain together with this converter. Note that the source type of the given - * [converter] must be the same as the target type of this converter. - */ -@ExperimentalApi -public fun Converter.andThenTo(converter: Converter): Converter = - Converter(this.andThenConvertsTo(converter), converter.andThenConvertsFrom(this)) + /** + * Gets a [MonoConverter] that converts from **right** type [R] to **left** type [L] + */ + public val left: MonoConverter -/** - * Chains this converter with another converter, yielding a new converter which performs a two-stage conversion. (Note - * that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps in their actual - * implementation.) - * @param F The source type of this converter and the target type of the given [converter] - * @param F2 The source type of the given [converter] - * @param T The target type of this converter - * @param converter The converter to chain together with this converter. Note that the target type of the given - * [converter] must be the same as the source type of this converter. - */ -@ExperimentalApi -public fun Converter.andThenFrom(converter: Converter): Converter = - Converter(converter.andThenConvertsTo(this), this.andThenConvertsFrom(converter)) + /** + * Converts a **left** value into a **right** value + */ + public fun convertRight(from: L): R = right.convert(from) + + /** + * Converts a **right** value into a **left** value + */ + public fun convertLeft(from: R): L = left.convert(from) +} /** - * Adds validation before conversions by running [validate] on [F] values before converting them to type [T]. Validators - * are expected to throw an exception if the expected condition is not met. - * @param F The type being converted from - * @param T The type being converted to - * @param validate A function which accepts an [F] value and throws an exception if the expected condition is not - * met + * Creates a new two-way converter from symmetrical one-way converters + * @param L The type being converted from + * @param R The type being converted to + * @param right A converter instance for converting one-way from [L] to [R] + * @param left A converter instance for converting one-way from [R] to [L] */ @ExperimentalApi -public fun Converter.validatingFrom(validate: (F) -> Unit): Converter = - Converter(this.firstValidatingFrom(validate), this) +public fun Converter(right: MonoConverter, left: MonoConverter): Converter = + ConverterImpl(right, left) /** - * Adds validation before conversions by running [validate] on [T] values before converting them to type [F]. Validators - * are expected to throw an exception if the expected condition is not met. - * @param F The type being converted to - * @param T The type being converted from - * @param validate A function which accepts a [T] value and throws an exception if the expected condition is not - * met + * Chains this converter with a subsequent converter, yielding a new converter which performs two-stage transformations. + * @param L The **left** type of this converter + * @param M The **middle** type, which is the **right** type of this converter and the **left** type of the next + * converter + * @param R The **right** type of the next converter + * @param next The subsequent converter to chain */ @ExperimentalApi -public fun Converter.validatingTo(validate: (T) -> Unit): Converter = - Converter(this, this.firstValidatingTo(validate)) +public operator fun Converter.plus(next: Converter): Converter = + Converter(this.right + next.right, next.left + this.left) diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom.kt deleted file mode 100644 index 7f81d9aee9f..00000000000 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/ConvertsFrom.kt +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.mapping.core.converters - -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Models one-way conversion from a type [T] to a type [F]. This type is similar to [ConvertsTo] but models conversion - * in the opposite direction. - * @param F The type being converted to - * @param T The type being converted from - */ -@ExperimentalApi -public fun interface ConvertsFrom { - /** - * Converts a single value from type [T] to type [F] - * @param to The value to convert - */ - public fun convertFrom(to: T): F -} - -/** - * Chains this converter with another converter, yielding a new converter which performs a two-stage conversion. (Note - * that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps in their actual - * implementation.) - * @param F The source type of this converter and the target type of the given [converter] - * @param F2 The source type of the given [converter] - * @param T The target type of this converter - * @param converter The converter to chain together with this converter. Note that the target type of the given - * [converter] must be the same as the source type of this converter. - */ -@ExperimentalApi -public fun ConvertsFrom.andThenConvertsFrom(converter: ConvertsFrom): ConvertsFrom = - ConvertsFrom { to: T -> converter.convertFrom(this.convertFrom(to)) } - -/** - * Adds validation before a conversion by running [validate] on [T] values before converting them to type [F]. - * Validators are expected to throw an exception if the expected condition is not met. - * @param F The type being converted to - * @param T The type being converted from - * @param validate A function which accepts a [T] value and throws an exception if the expected condition is not met - */ -@ExperimentalApi -public fun ConvertsFrom.firstValidatingTo(validate: (T) -> Unit): ConvertsFrom = - ConvertsFrom { to: T -> - validate(to) - this.convertFrom(to) - } diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo.kt deleted file mode 100644 index b7c4e02eb85..00000000000 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/ConvertsTo.kt +++ /dev/null @@ -1,49 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.mapping.core.converters - -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Models one-way conversion from a type [F] to a type [T] - * @param F The type being converted from - * @param T The type being converted to - */ -@ExperimentalApi -public fun interface ConvertsTo { - /** - * Converts a single value from type [F] to type [T] - * @param from The value to convert - */ - public fun convertTo(from: F): T -} - -/** - * Chains this converter with another converter, yielding a new converter which performs a two-stage conversion. (Note - * that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps in their actual - * implementation.) - * @param F The source type of this converter - * @param T The target type of this converter and the source type of the given [converter] - * @param T2 The target type of the given [converter] - * @param converter The converter to chain together with this converter. Note that the source type of the given - * [converter] must be the same as the target type of this converter. - */ -@ExperimentalApi -public fun ConvertsTo.andThenConvertsTo(converter: ConvertsTo): ConvertsTo = - ConvertsTo { from: F -> converter.convertTo(this.convertTo(from)) } - -/** - * Adds validation before a conversion by running [validate] on [F] values before converting them to type [T]. - * Validators are expected to throw an exception if the expected condition is not met. - * @param F The type being converted from - * @param T The type being converted to - * @param validate A function which accepts an [F] value and throws an exception if the expected condition is not met - */ -@ExperimentalApi -public fun ConvertsTo.firstValidatingFrom(validate: (F) -> Unit): ConvertsTo = - ConvertsTo { from: F -> - validate(from) - this.convertTo(from) - } diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/MonoConverter.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/MonoConverter.kt new file mode 100644 index 00000000000..8fa64eaac57 --- /dev/null +++ b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/MonoConverter.kt @@ -0,0 +1,46 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters + +import aws.smithy.kotlin.runtime.ExperimentalApi + +/** + * A type for one-way conversion from values of type [A] to values of type [B]. A symmetrical pair of one-way converters + * form the two halves of a [Converter] which provides two-way conversion. + * @param A the type to convert from + * @param B the type to convert to + */ +@ExperimentalApi +public fun interface MonoConverter { + public companion object { + public fun identity(): MonoConverter = MonoConverter { it } + } + + /** + * Convert a value from type [A] to type [B] + */ + public fun convert(from: A): B +} + +/** + * Chains this converter with a subsequent converter, yielding a new converter which performs two-stage transformations. + * @param A The "from" type of this converter + * @param B The middle type, which is the "to" type of this converter and the "from" type of the next converter + * @param C The "to" type of the next converter + * @param next The subsequent converter to chain + */ +@ExperimentalApi +public operator fun MonoConverter.plus(next: MonoConverter): MonoConverter = + MonoConverter { next.convert(this.convert(it)) } + +/** + * Pairs this one-way converter with a symmetrical one-way converter to form a two-way [Converter] + * @param A The "from" type of this converter and the "to" type of the other converter + * @param B The "from" type of the other converter and the "to" type of this converter + * @param other The other converter to pair with + */ +@ExperimentalApi +public infix fun MonoConverter.reversedBy(other: MonoConverter): Converter = + Converter(this, other) diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/SplittingConverter.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/SplittingConverter.kt deleted file mode 100644 index 6bdce1186e6..00000000000 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/SplittingConverter.kt +++ /dev/null @@ -1,53 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.mapping.core.converters - -import aws.sdk.kotlin.hll.mapping.core.util.Either -import aws.sdk.kotlin.hll.mapping.core.util.map -import aws.sdk.kotlin.hll.mapping.core.util.merge -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Models partial, asymmetrical conversion between a type [F] and a type [T], where some condition internal to the - * converter splits the possible pathways data make take through conversion logic. One of these branches will be more - * complex and involve converting types [F] and [T] to types [F2] and [T2] (respectively). The remaining conversion - * between [F2] and [T2] will typically be delegated to another converter. - * - * Because they are partial and asymmetrical, [SplittingConverter] instances are typically not very useful on their own. - * Most often they are combined with another [Converter] via the [mergeBy] extension method, forming a complete, - * symmetrical converter between [F] and [T]. - * - * Splitting converters use the [Either] type to denote values which may follow the simple branch ([Either.Left]) or the - * complex branch ([Either.Right]). - * - * @param F The overall type being converted from - * @param F2 The intermediate type being converted from on the complex branch - * @param T2 The intermediate type being converted to on the complex branch - * @param T The overall type being converted to - */ -@ExperimentalApi -public interface SplittingConverter : - ConvertsTo>, - ConvertsFrom, T> - -/** - * Merges this [SplittingConverter] by delegating to a [Converter] instance that converts between types [F2] and [T2]. - * After the merge, a new [Converter] will be returned which fully converts between types [F] and [T]. - * @param F The overall type being converted from - * @param F2 The intermediate type being converted from on the complex branch, which is also the source type of - * [converter] - * @param T2 The intermediate type being converted to on the complex branch, which is also the target type of - * [converter] - * @param T The overall type being converted to - * @param converter A [Converter] between types [F2] and [T2] - */ -@ExperimentalApi -public fun SplittingConverter.mergeBy( - converter: Converter, -): Converter = - Converter( - convertTo = { from: F -> this@mergeBy.convertTo(from).map(converter::convertTo).merge() }, - convertFrom = { to: T -> this@mergeBy.convertFrom(to).map(converter::convertFrom).merge() }, - ) diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionConverters.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionConverters.kt new file mode 100644 index 00000000000..e4dd80cbffa --- /dev/null +++ b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionConverters.kt @@ -0,0 +1,12 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters.collections + +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.smithy.kotlin.runtime.ExperimentalApi + +@ExperimentalApi +@Suppress("ktlint:standard:function-naming") +public fun SetToListConverter(): Converter, List> = Converter({ it.toList() }, { it.toSet() }) diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionTypeConverters.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionTypeConverters.kt deleted file mode 100644 index 5c9cb9b288e..00000000000 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/CollectionTypeConverters.kt +++ /dev/null @@ -1,23 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.mapping.core.converters.collections - -import aws.sdk.kotlin.hll.mapping.core.converters.Converter -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Namespace for containing various conversion utilities dealing with mapping between collection types (e.g., [Set] to - * [List]) - */ -@ExperimentalApi -public object CollectionTypeConverters { - /** - * Creates a [Converter] which transforms between [Set] and [List] instances (both of some type [T]) - * @param T The type of elements in the [Set]/[List] - */ - @Suppress("ktlint:standard:function-naming") - public inline fun SetToListConverter(): Converter, List> = - Converter(Set::toList, List::toSet) -} diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverters.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverters.kt index addfd5aa23e..7bee52d427e 100644 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverters.kt +++ b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverters.kt @@ -4,95 +4,29 @@ */ package aws.sdk.kotlin.hll.mapping.core.converters.collections -import aws.sdk.kotlin.hll.mapping.core.converters.* +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.reversedBy import aws.smithy.kotlin.runtime.ExperimentalApi /** - * Namespace for containing various conversion utilities dealing with [List] mapping + * Creates a list-mapping [MonoConverter] which turns values of type `List` into values of type `List` + * @param A The element type to convert from + * @param B The element type to convert to + * @param delegate A [MonoConverter] from type [A] to type [B] to use for each list element */ @ExperimentalApi -public object ListMappingConverters { - /** - * Creates a one-way converter for transforming [List] with elements of type [T] to [List] with elements of type [F] - * @param F The type being converted to - * @param T The type being converted from - * @param elementConverter A one-way converter of [T] elements to [F] elements - */ - public fun of(elementConverter: ConvertsFrom): ConvertsFrom, List> = - ConvertsFrom { to: List -> to.map(elementConverter::convertFrom) } - - /** - * Chains this list converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param F The source element type of this converter and the target type of the given [elementConverter] - * @param F2 The source type of the given [elementConverter] - * @param T The target type of this converter - * @param elementConverter The element converter to chain together with this list converter. Note that the target - * type of the given [elementConverter] must be the same as the source element type of this converter. - */ - public fun ConvertsFrom, T>.mapConvertsFrom( - elementConverter: ConvertsFrom, - ): ConvertsFrom, T> = this.andThenConvertsFrom(of(elementConverter)) - - /** - * Creates a one-way converter for transforming [List] with elements of type [F] to [List] with elements of type [T] - * @param F The type being converted from - * @param T The type being converted to - * @param elementConverter A one-way converter of [F] elements to [T] elements - */ - public fun of(elementConverter: ConvertsTo): ConvertsTo, List> = - ConvertsTo { from: List -> from.map(elementConverter::convertTo) } - - /** - * Chains this list converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param F The source type of this converter - * @param T The target element type of this converter and the source type of the given [elementConverter] - * @param T2 The target type of the given [elementConverter] - * @param elementConverter The element converter to chain together with this list converter. Note that the source - * type of the given [elementConverter] must be the same as the target element type of this converter. - */ - public fun ConvertsTo>.mapConvertsTo( - elementConverter: ConvertsTo, - ): ConvertsTo> = this.andThenConvertsTo(of(elementConverter)) - - /** - * Creates a two-way converter for transforming between a [List] with elements of type [F] and a [List] with - * elements of type [T] - * @param F The type being converted from - * @param T The type being converted to - * @param elementConverter A [Converter] for transforming between elements of type [F] and [T] - */ - public fun of(elementConverter: Converter): Converter, List> = - Converter(of(elementConverter as ConvertsTo), of(elementConverter as ConvertsFrom)) -} - -/** - * Chains this list converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source element type of this converter and the target type of the given [elementConverter] - * @param F2 The source type of the given [elementConverter] - * @param T The target type of this converter - * @param elementConverter The element converter to chain together with this list converter. Note that the target type - * of the given [elementConverter] must be the same as the source element type of this converter. - */ -@ExperimentalApi -public fun Converter, T>.mapFrom(elementConverter: Converter): Converter, T> = - this.andThenFrom(ListMappingConverters.of(elementConverter)) +@Suppress("ktlint:standard:function-naming") +public fun ListMappingMonoConverter(delegate: MonoConverter): MonoConverter, List> = + MonoConverter { it.map(delegate::convert) } /** - * Chains this list converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source type of this converter - * @param T The target element type of this converter and the source type of the given [elementConverter] - * @param T2 The target type of the given [elementConverter] - * @param elementConverter The element converter to chain together with this list converter. Note that the source type - * of the given [elementConverter] must be the same as the target element type of this converter. + * Creates a list-mapping [Converter] which performs two-way conversions between values of type `List` and values of + * type `List` + * @param L The **left** element type + * @param R The **right** element type */ @ExperimentalApi -public fun Converter>.mapTo(elementConverter: Converter): Converter> = - this.andThenTo(ListMappingConverters.of(elementConverter)) +@Suppress("ktlint:standard:function-naming") +public fun ListMappingConverter(delegate: Converter): Converter, List> = + ListMappingMonoConverter(delegate.right) reversedBy ListMappingMonoConverter(delegate.left) diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverters.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverters.kt index 9e65fb5bba5..04075c96a56 100644 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverters.kt +++ b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverters.kt @@ -4,387 +4,80 @@ */ package aws.sdk.kotlin.hll.mapping.core.converters.collections -import aws.sdk.kotlin.hll.mapping.core.converters.* +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.reversedBy import aws.smithy.kotlin.runtime.ExperimentalApi /** - * Namespace for containing various conversion utilities dealing with [Map] mapping + * Creates a map-mapping [MonoConverter] which turns values of type `Map` into values of type `Map` + * @param AK The key type to convert from + * @param AV The value type to convert from + * @param BK The key type to convert to + * @param BV The value type to convert to + * @param delegate A [MonoConverter] from type `Pair` to type `Pair` to use for each map entry */ @ExperimentalApi -public object MapMappingConverters { - /** - * Creates a one-way converter for transforming [Map] with keys of type [TK] to [Map] with keys of type [FK]. The - * values of the map are unchanged. - * @param FK The type of keys being converted to - * @param TK The type of keys being converted from - * @param V The type of values - * @param keyConverter A one-way converter of [TK] keys to [FK] keys - */ - public fun ofKeys(keyConverter: ConvertsFrom): ConvertsFrom, Map> = - ConvertsFrom { to: Map -> - to.mapKeys { e: Map.Entry -> keyConverter.convertFrom(e.key) } - } - - /** - * Chains this map converter with a key converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param FK The type of keys being converted from - * @param FK2 The type of keys being converted to - * @param V The type of values - * @param T The target type of this converter - * @param keyConverter The key converter to chain together with this map converter. Note that the target type of the - * given [keyConverter] must be the same as the source key type of this converter. - */ - public fun ConvertsFrom, T>.mapConvertsKeysFrom( - keyConverter: ConvertsFrom, - ): ConvertsFrom, T> = this.andThenConvertsFrom(ofKeys(keyConverter)) - - /** - * Creates a one-way converter for transforming [Map] with values of type [TV] to [Map] with values of type [FV]. - * The keys of the map are unchanged. - * @param K The type of keys - * @param FV The type of values being converted to - * @param TV The type of values being converted from - * @param valueConverter A one-way converter of [TV] values to [FV] values - */ - public fun ofValues( - valueConverter: ConvertsFrom, - ): ConvertsFrom, Map> = - ConvertsFrom { to: Map -> - to.mapValues { e: Map.Entry -> valueConverter.convertFrom(e.value) } - } - - /** - * Chains this map converter with a value converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param K The type of keys - * @param FV The type of values being converted to - * @param FV2 The type of values being converted from - * @param T The target type of this converter - * @param valueConverter The value converter to chain together with this map converter. Note that the target type of - * the given [valueConverter] must be the same as the source value type of this converter. - */ - public fun ConvertsFrom, T>.mapConvertsValuesFrom( - valueConverter: ConvertsFrom, - ): ConvertsFrom, T> = this.andThenConvertsFrom(ofValues(valueConverter)) - - /** - * Creates a one-way converter for transforming [Map] with keys of type [TK] and values of type [TV] to [Map] with - * keys of type [FK] and values of type [FV] - * @param FK The type of keys being converted to - * @param FV The type of values being converted to - * @param TK The type of keys being converted from - * @param TV The type of values being converted from - * @param entryConverter A one-way converter of [TK]/[TV] pairs to [FK]/[FV] pairs - */ - public fun of( - entryConverter: ConvertsFrom, Pair>, - ): ConvertsFrom, Map> = - ConvertsFrom { to: Map -> - to.entries.associate { e: Map.Entry -> entryConverter.convertFrom(e.toPair()) } - } - - /** - * Chains this map converter with an entry converter, yielding a new converter which performs a two stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param FK The type of keys being converted to - * @param FV The type of values being converted to - * @param FK2 The type of keys being converted from - * @param FV2 The type of values being converted from - * @param entryConverter The entry converter to chain together with this map converter. Note that the target types - * of the given [entryConverter] must be the same as the source types of this converter. - */ - public fun ConvertsFrom, T>.mapConvertsFrom( - entryConverter: ConvertsFrom, Pair>, - ): ConvertsFrom, T> = this.andThenConvertsFrom(of(entryConverter)) - - /** - * Creates a one-way converter for transforming [Map] with keys of type [FK] to [Map] with keys of type [TK]. The - * values of the map are unchanged. - * @param FK The type of keys being converted from - * @param TK The type of keys being converted to - * @param V The type of values - * @param keyConverter A one-way converter of [FK] keys to [TK] keys - */ - public fun ofKeys( - keyConverter: ConvertsTo, - ): ConvertsTo, Map> = - ConvertsTo { from: Map -> - from.mapKeys { e: Map.Entry -> keyConverter.convertTo(e.key) } - } - - /** - * Chains this map converter with a key converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param F The source type of this converter - * @param TK The type of keys being converted from - * @param TK2 The type of keys being converted to - * @param V The type of values - * @param keyConverter The key converter to chain together with this map converter. Note that the source type of the - * given [keyConverter] must be the same as the target key type of this converter. - */ - public fun ConvertsTo>.mapConvertsKeysTo( - keyConverter: ConvertsTo, - ): ConvertsTo> = this.andThenConvertsTo(ofKeys(keyConverter)) - - /** - * Creates a one-way converter for transforming [Map] with values of type [FV] to [Map] with values of type [TV]. - * The keys of the map are unchanged. - * @param K The type of keys - * @param FV The type of values being converted from - * @param TV The type of values being converted to - * @param valueConverter A one-way converter of [FV] values to [TV] values - */ - public fun ofValues( - valueConverter: ConvertsTo, - ): ConvertsTo, Map> = - ConvertsTo { from: Map -> - from.mapValues { e: Map.Entry -> valueConverter.convertTo(e.value) } - } - - /** - * Chains this map converter with a value converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param F The source type of this converter - * @param K The type of keys - * @param TV The type of values being converted from - * @param TV2 The type of values being converted to - * @param valueConverter The value converter to chain together with this map converter. Note that the source type of - * the given [valueConverter] must be the same as the target value type of this converter. - */ - public fun ConvertsTo>.mapConvertsValuesTo( - valueConverter: ConvertsTo, - ): ConvertsTo> = this.andThenConvertsTo(ofValues(valueConverter)) - - /** - * Creates a one-way converter for transforming [Map] with keys of type [FK] and values of type [FV] to [Map] with - * keys of type [TK] and values of type [TV] - * @param FK The type of keys being converted from - * @param FV The type of values being converted from - * @param TK The type of keys being converted to - * @param TV The type of values being converted to - * @param entryConverter A one-way converter of [FK]/[FV] pairs to [TK]/[TV] pairs - */ - public fun of( - entryConverter: ConvertsTo, Pair>, - ): ConvertsTo, Map> = - ConvertsTo { from: Map -> - from.entries.associate { e -> entryConverter.convertTo(e.toPair()) } - } - - /** - * Chains this map converter with an entry converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical - * steps in their actual implementation.) - * @param F The source type of this converter - * @param TK The type of keys being converted from - * @param TV The type of values being converted from - * @param TK2 The type of keys being converted to - * @param TV2 The type of values being converted to - * @param entryConverter The entry converter to chain together with this map converter. Note that the source types - * of the given [entryConverter] must be the same as the target types of this converter. - */ - public fun ConvertsTo>.mapConvertsTo( - entryConverter: ConvertsTo, Pair>, - ): ConvertsTo> = this.andThenConvertsTo(of(entryConverter)) - - /** - * Creates a two-way converter for transforming between [Map] with keys of type [FK] and [Map] with keys of type - * [TK]. The values of maps are unchanged. - * @param FK The type of keys being converted from - * @param TK The type of keys being converted to - * @param V The type of values - * @param keyConverter A converter for transforming between keys of type [FK] and [TK] - */ - public fun ofKeys( - keyConverter: Converter, - ): Converter, Map> = - Converter(ofKeys(keyConverter as ConvertsTo), ofKeys(keyConverter as ConvertsFrom)) - - /** - * Creates a two-way converter for transforming between [Map] with values of type [FV] and [Map] with values of type - * [TV]. The keys of the map are unchanged. - * @param K The type of keys - * @param FV The type of values being converted from - * @param TV The type of values being converted to - * @param valueConverter A converter for transforming between values of type [FV] and [TV] - */ - public fun ofValues( - valueConverter: Converter, - ): Converter, Map> = - Converter(ofValues(valueConverter as ConvertsTo), ofValues(valueConverter as ConvertsFrom)) - - /** - * Creates a two-way converter for transforming between [Map] with keys of type [FK] and values of type [FV] to - * [Map] with keys of type [TK] and values of type [TV] - * @param FK The type of keys being converted from - * @param FV The type of values being converted from - * @param TK The type of keys being converted to - * @param TV The type of values being converted to - * @param entryConverter A converter for transforming between [FK]/[FV] pairs and [TK]/[TV] pairs - */ - public fun of( - entryConverter: Converter, Pair>, - ): Converter, Map> = - Converter( - of(entryConverter as ConvertsTo, Pair>), - of(entryConverter as ConvertsFrom, Pair>), - ) +@Suppress("ktlint:standard:function-naming") +public fun MapMappingMonoConverter( + delegate: MonoConverter, Pair>, +): MonoConverter, Map> = MonoConverter { from -> + from.map { entry -> + delegate.convert(entry.toPair()) + }.toMap() } /** - * Chains this map converter with a key converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param FK The type of keys being converted to - * @param FK2 The type of keys being converted from - * @param V The type of values - * @param T The target type of this converter - * @param keyConverter The key converter to chain together with this map converter. Note that the target key type of the - * given [keyConverter] must be the same as the source key type of this converter. - */ -@ExperimentalApi -public fun Converter, T>.mapKeysFrom( - keyConverter: Converter, -): Converter, T> = this.andThenFrom(MapMappingConverters.ofKeys(keyConverter)) - -/** - * Chains this map converter with a key converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source type of this converter - * @param TK The type of keys being converted from - * @param TK2 The type of keys being converted to - * @param V The type of values - * @param keyConverter The key converter to chain together with this map converter. Note that the source key type of the - * given [keyConverter] must be the same as the target key type of this converter. - */ -@ExperimentalApi -public fun Converter>.mapKeysTo( - keyConverter: Converter, -): Converter> = this.andThenTo(MapMappingConverters.ofKeys(keyConverter)) - -/** - * Chains this map converter with a value converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param K The type of keys - * @param FV The type of values being converted to - * @param FV2 The type of values being converted from - * @param T The target type of this converter - * @param valueConverter The value converter to chain together with this map converter. Note that the target value type - * of the given [valueConverter] must be the same as the source value type of this converter. - */ -@ExperimentalApi -public fun Converter, T>.mapValuesFrom( - valueConverter: Converter, -): Converter, T> = this.andThenFrom(MapMappingConverters.ofValues(valueConverter)) - -/** - * Chains this map converter with a value converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source type of this converter - * @param K The type of keys - * @param TV The type of values being converted from - * @param TV2 The type of values being converted to - * @param valueConverter The value converter to chain together with this map converter. Note that the source value type - * of the given [valueConverter] must be the same as the target value type of this converter. + * Creates a map-mapping [MonoConverter] which turns values of type `Map` into values of type `Map` + * @param AK The key type to convert from + * @param AV The value type to convert from + * @param BK The key type to convert to + * @param BV The value type to convert to + * @param keyDelegate A [MonoConverter] from type [AK] to type [BK] to use for each map key + * @param valueDelegate A [MonoConverter] from type [AV] to type [BV] to use for each map value */ @ExperimentalApi -public fun Converter>.mapValuesTo( - valueConverter: Converter, -): Converter> = this.andThenTo(MapMappingConverters.ofValues(valueConverter)) - -/** - * Convenience function for combining independent converters into `Converter, Pair>`, suitable for - * use as a map entry converter - * @param F1 The first type of value being converted from - * @param T1 The first type of value being converted to - * @param F2 The second type of value being converted from - * @param T2 The second type of value being converted to - * @param other The converter to zip with this one - */ -private fun Converter.zip(other: Converter) = Converter( - convertTo = { from: Pair -> this.convertTo(from.first) to other.convertTo(from.second) }, - convertFrom = { to: Pair -> this.convertFrom(to.first) to other.convertFrom(to.second) }, -) - -/** - * Chains this map converter with an entry converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param FK The type of keys being converted to - * @param FV The type of values being converted to - * @param FK2 The type of keys being converted from - * @param FV2 The type of values being converted from - * @param T The target type of this converter - * @param entryConverter The entry converter to chain together with this map converter. Note that the target types of - * the given [entryConverter] must be the same as the source types of this converter. - */ -@ExperimentalApi -public fun Converter, T>.mapFrom( - entryConverter: Converter, Pair>, -): Converter, T> = this.andThenFrom(MapMappingConverters.of(entryConverter)) - -/** - * Chains this map converter with a key converter and a value converter, yielding a new converter which performs a - * two-stage mapping conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of - * multiple logical steps in their actual implementation.) - * @param FK The type of keys being converted to - * @param FV The type of values being converted to - * @param FK2 The type of keys being converted from - * @param FV2 The type of values being converted from - * @param T The target type of this converter - * @param keyConverter The key converter to chain together with this map converter. Note that the target key type of the - * given [keyConverter] must be the same as the source key type of this converter. - * @param valueConverter The value converter to chain together with this map converter. Note that the target value type - * of the given [valueConverter] must be the same as the source value type of this converter. - */ -@ExperimentalApi -public fun Converter, T>.mapFrom( - keyConverter: Converter, - valueConverter: Converter, -): Converter, T> = mapFrom(keyConverter.zip(valueConverter)) +@Suppress("ktlint:standard:function-naming") +public fun MapMappingMonoConverter( + keyDelegate: MonoConverter, + valueDelegate: MonoConverter, +): MonoConverter, Map> = MonoConverter { from -> + from.map { (key, value) -> + keyDelegate.convert(key) to valueDelegate.convert(value) + }.toMap() +} /** - * Chains this map converter with an entry converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source type of this converter - * @param TK The type of keys being converted from - * @param TV The type of values being converted from - * @param TK2 The type of keys being converted to - * @param TV2 The type of values being converted to - * @param entryConverter The entry converter to chain together with this map converter. Note that the source types of - * the given [entryConverter] must be the same as the target types of this converter. + * Creates a map-mapping [Converter] which performs two-way conversions between values of type `Map` and values + * of type `Map` + * @param LK The **left** key type + * @param LV The **left** value type + * @param RK The **right** key type + * @param RV The **right** value type + * @param delegate A [Converter] between values of type `Pair` and type `Pair` to use for each map entry */ @ExperimentalApi -public fun Converter>.mapTo( - entryConverter: Converter, Pair>, -): Converter> = this.andThenTo(MapMappingConverters.of(entryConverter)) +@Suppress("ktlint:standard:function-naming") +public fun MapMappingConverter( + delegate: Converter, Pair>, +): Converter, Map> = + MapMappingMonoConverter(delegate.right) reversedBy MapMappingMonoConverter(delegate.left) /** - * Chains this map converter with a key converter and a value converter, yielding a new converter which performs a - * two-stage mapping conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of - * multiple logical steps in their actual implementation.) - * @param F The source type of this converter - * @param TK The type of keys being converted from - * @param TV The type of values being converted from - * @param TK2 The type of keys being converted to - * @param TV2 The type of values being converted to - * @param keyConverter The key converter to chain together with this map converter. Note that the source key type of the - * given [keyConverter] must be the same as the target key type of this converter. - * @param valueConverter The value converter to chain together with this map converter. Note that the source value type - * of the given [valueConverter] must be the same as the target value type of this converter. + * Creates a map-mapping [Converter] which performs two-way conversions between values of type `Map` and values + * of type `Map` + * @param LK The **left** key type + * @param LV The **left** value type + * @param RK The **right** key type + * @param RV The **right** value type + * @param keyDelegate A [Converter] between values of type [LK] and type [RK] to use for each map key + * @param valueDelegate A [Converter] between values of type [LV] to type [RV] to use for each map value */ @ExperimentalApi -public fun Converter>.mapTo( - keyConverter: Converter, - valueConverter: Converter, -): Converter> = mapTo(keyConverter.zip(valueConverter)) +@Suppress("ktlint:standard:function-naming") +public fun MapMappingConverter( + keyDelegate: Converter, + valueDelegate: Converter, +): Converter, Map> = + MapMappingMonoConverter(keyDelegate.right, valueDelegate.right) reversedBy + MapMappingMonoConverter(keyDelegate.left, valueDelegate.left) diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverters.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverters.kt index b97585779bd..4fbf3a2d2e2 100644 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverters.kt +++ b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverters.kt @@ -4,95 +4,29 @@ */ package aws.sdk.kotlin.hll.mapping.core.converters.collections -import aws.sdk.kotlin.hll.mapping.core.converters.* +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.reversedBy import aws.smithy.kotlin.runtime.ExperimentalApi /** - * Namespace for containing various conversion utilities dealing with [Set] mapping + * Creates a set-mapping [MonoConverter] which turns values of type `Set` into values of type `Set` + * @param A The element type to convert from + * @param B The element type to convert to + * @param delegate A [MonoConverter] from type [A] to type [B] to use for each set element */ @ExperimentalApi -public object SetMappingConverters { - /** - * Creates a one-way converter for transforming [Set] with elements of type [T] to [Set] with elements of type [F] - * @param F The type being converted to - * @param T The type being converted from - * @param elementConverter A one-way converter of [T] values to [F] values - */ - public fun of(elementConverter: ConvertsFrom): ConvertsFrom, Set> = - ConvertsFrom { to: Set -> to.map(elementConverter::convertFrom).toSet() } - - /** - * Chains this set converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source element type of this converter and the target type of the given [elementConverter] - * @param F2 The source type of the given [elementConverter] - * @param T The target type of this converter - * @param elementConverter The element converter to chain together with this set converter. Note that the target type - * of the given [elementConverter] must be the same as the source element type of this converter. - */ - public fun ConvertsFrom, T>.mapConvertsFrom( - elementConverter: ConvertsFrom, - ): ConvertsFrom, T> = this.andThenConvertsFrom(of(elementConverter)) - - /** - * Creates a one-way converter for transforming [Set] with elements of type [F] to [Set] with elements of type [T] - * @param F The type being converted from - * @param T The type being converted to - * @param elementConverter A one-way converter of [F] values to [T] values - */ - public fun of(elementConverter: ConvertsTo): ConvertsTo, Set> = - ConvertsTo { from: Set -> from.map(elementConverter::convertTo).toSet() } - - /** - * Chains this set converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source type of this converter - * @param T The target element type of this converter and the source type of the given [elementConverter] - * @param T2 The target type of the given [elementConverter] - * @param elementConverter The element converter to chain together with this set converter. Note that the source type - * of the given [elementConverter] must be the same as the target element type of this converter. - */ - public fun ConvertsTo>.mapConvertsTo( - elementConverter: ConvertsTo, - ): ConvertsTo> = this.andThenConvertsTo(of(elementConverter)) - - /** - * Creates a two-way converter for transforming between a [Set] with elements of type [F] and a [Set] with elements - * of type [T] - * @param F The type being converted from - * @param T The type being converted to - * @param elementConverter A [Converter] for transforming between values of type [F] and [T] - */ - public fun of(elementConverter: Converter): Converter, Set> = - Converter(of(elementConverter as ConvertsTo), of(elementConverter as ConvertsFrom)) -} - -/** - * Chains this set converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source element type of this converter and the target type of the given [elementConverter] - * @param F2 The source type of the given [elementConverter] - * @param T The target type of this converter - * @param elementConverter The element converter to chain together with this set converter. Note that the target type - * of the given [elementConverter] must be the same as the source element type of this converter. - */ -@ExperimentalApi -public fun Converter, T>.mapFrom(elementConverter: Converter): Converter, T> = - this.andThenFrom(SetMappingConverters.of(elementConverter)) +@Suppress("ktlint:standard:function-naming") +public fun SetMappingMonoConverter(delegate: MonoConverter): MonoConverter, Set> = + MonoConverter { it.map(delegate::convert).toSet() } /** - * Chains this set converter with an element converter, yielding a new converter which performs a two-stage mapping - * conversion. (Note that these two "stages" are conceptual. Each of these stages may consist of multiple logical steps - * in their actual implementation.) - * @param F The source type of this converter - * @param T The target element type of this converter and the source type of the given [elementConverter] - * @param T2 The target type of the given [elementConverter] - * @param elementConverter The element converter to chain together with this set converter. Note that the source type - * of the given [elementConverter] must be the same as the target element type of this converter. + * Creates a set-mapping [Converter] which performs two-way conversions between values of type `Set` and values of + * type `Set` + * @param L The **left** element type + * @param R The **right** element type */ @ExperimentalApi -public fun Converter>.mapTo(elementConverter: Converter): Converter> = - this.andThenTo(SetMappingConverters.of(elementConverter)) +@Suppress("ktlint:standard:function-naming") +public fun SetMappingConverter(delegate: Converter): Converter, Set> = + SetMappingMonoConverter(delegate.right) reversedBy SetMappingMonoConverter(delegate.left) diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/internal/ConverterImpl.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/internal/ConverterImpl.kt new file mode 100644 index 00000000000..e66d0889043 --- /dev/null +++ b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/converters/internal/ConverterImpl.kt @@ -0,0 +1,13 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters.internal + +import aws.sdk.kotlin.hll.mapping.core.converters.Converter +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter + +internal class ConverterImpl( + override val right: MonoConverter, + override val left: MonoConverter, +) : Converter diff --git a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/util/Either.kt b/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/util/Either.kt deleted file mode 100644 index b6b79d2ec81..00000000000 --- a/hll/hll-mapping-core/common/src/aws/sdk/kotlin/hll/mapping/core/util/Either.kt +++ /dev/null @@ -1,100 +0,0 @@ -/* - * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. - * SPDX-License-Identifier: Apache-2.0 - */ -package aws.sdk.kotlin.hll.mapping.core.util - -import aws.smithy.kotlin.runtime.ExperimentalApi - -/** - * Represents a value which may be one of two possible types: [L] or [R]. An instance of this type will be either [Left] - * or [Right]. - * - * By convention [Either] is **right-biased**, meaning that [Right] values are the default values to operate on (e.g., - * via [map]) and [Left] value are typically unmodified. This lends itself to using [R]/[Right] for values which may - * require more processing and using [L]/[Left] for values which are relatively "final". - * - * @param L The type of [Left] values - * @param R The type of [Right] values - */ -@ExperimentalApi -public sealed interface Either { - /** - * The left side of an [Either] - * @param L The type of values held in this class - */ - @ExperimentalApi - public interface Left : Either { - /** - * An [L] value - */ - public val value: L - } - - /** - * The right side of an [Either] - * @param R The type of values held in this class - */ - @ExperimentalApi - public interface Right : Either { - /** - * An [R] value - */ - public val value: R - } - - @ExperimentalApi - public companion object { - /** - * Creates a new [Left] with the given [value] - * @param L The type of values held in this class - * @param value An [L] value - */ - public fun Left(value: L): Left = LeftImpl(value) - - /** - * Creates a new [Right] with the given [value] - * @param R The type of values held in this class - * @param value An [R] value - */ - public fun Right(value: R): Right = RightImpl(value) - } -} - -private data class LeftImpl(override val value: L) : Either.Left - -private data class RightImpl(override val value: R) : Either.Right - -/** - * Map the right value of this [Either] to a new value. Left values are unmodified. - * @param L The type of left value - * @param R The current type of right value - * @param R2 The new type of right value - * @param func A mapping function which turns an [R] into an [R2] - */ -@ExperimentalApi -public inline fun Either.map(func: (right: R) -> R2): Either = when (this) { - is Either.Left -> this - is Either.Right -> Either.Right(func(value)) -} - -/** - * Transform this [Either] into a value of type [T] via specialized mapping functions for both left and right values - * @param L The current type of left value - * @param R The current type of right value - * @param T The type of output value - * @param ifLeft A function for converting [L] values to [T] - * @param ifRight A function for converting [R] values to [T] - */ -@ExperimentalApi -public inline fun Either.fold(ifLeft: (left: L) -> T, ifRight: (right: R) -> T): T = when (this) { - is Either.Left -> ifLeft(value) - is Either.Right -> ifRight(value) -} - -/** - * Returns the left value or right value - * @param T The type of values in left/right - */ -@ExperimentalApi -public fun Either.merge(): T = fold({ it }, { it }) diff --git a/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/ConverterTest.kt b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/ConverterTest.kt new file mode 100644 index 00000000000..fb4706e1c18 --- /dev/null +++ b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/ConverterTest.kt @@ -0,0 +1,25 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters + +import kotlin.test.Test +import kotlin.test.assertEquals + +class ConverterTest { + @Test + fun testPlus() { + val first = Converter({ it.toShort() }, { it.toByte() }) + val second = Converter({ it.toInt() }, { it.toShort() }) + + val chain = first + second + assertEquals(42, chain.convertRight(42.toByte())) + assertEquals(42.toByte(), chain.convertLeft(42)) + + val third = Converter({ it.toLong() }, { it.toInt() }) + val longerChain = chain + third + assertEquals(42L, longerChain.convertRight(42.toByte())) + assertEquals(42.toByte(), longerChain.convertLeft(42L)) + } +} diff --git a/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/MonoConverterTest.kt b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/MonoConverterTest.kt new file mode 100644 index 00000000000..82386931f0b --- /dev/null +++ b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/MonoConverterTest.kt @@ -0,0 +1,23 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters + +import kotlin.test.Test +import kotlin.test.assertEquals + +class MonoConverterTest { + @Test + fun testPlus() { + val first = MonoConverter { it.toShort() } + val second = MonoConverter { it.toInt() } + + val chain = first + second + assertEquals(42, chain.convert(42.toByte())) + + val third = MonoConverter { it.toLong() } + val longerChain = chain + third + assertEquals(42L, longerChain.convert(42.toByte())) + } +} diff --git a/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverterTest.kt b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverterTest.kt new file mode 100644 index 00000000000..588a8513f96 --- /dev/null +++ b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/ListMappingConverterTest.kt @@ -0,0 +1,22 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters.collections + +import aws.sdk.kotlin.hll.mapping.core.converters.testutils.NumberToWordConverter +import kotlin.test.Test +import kotlin.test.assertEquals + +class ListMappingConverterTest { + @Test + fun testListMapping() { + val converter = ListMappingConverter(NumberToWordConverter) + + val left = listOf(1, 1, 2, 3, 5, 8) + val right = listOf("one", "one", "two", "three", "five", "eight") + + assertEquals(right, converter.convertRight(left)) + assertEquals(left, converter.convertLeft(right)) + } +} diff --git a/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverterTest.kt b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverterTest.kt new file mode 100644 index 00000000000..47b8ed8a773 --- /dev/null +++ b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/MapMappingConverterTest.kt @@ -0,0 +1,23 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters.collections + +import aws.sdk.kotlin.hll.mapping.core.converters.testutils.AnimalEmojiConverter +import aws.sdk.kotlin.hll.mapping.core.converters.testutils.NumberToWordConverter +import kotlin.test.Test +import kotlin.test.assertEquals + +class MapMappingConverterTest { + @Test + fun testMapMapping() { + val converter = MapMappingConverter(AnimalEmojiConverter, NumberToWordConverter) + + val left = mapOf("horse" to 5, "bat" to 3, "eagle" to 10) + val right = mapOf("🐎" to "five", "🦇" to "three", "🦅" to "ten") + + assertEquals(right, converter.convertRight(left)) + assertEquals(left, converter.convertLeft(right)) + } +} diff --git a/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverterTest.kt b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverterTest.kt new file mode 100644 index 00000000000..043b19cef99 --- /dev/null +++ b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/collections/SetMappingConverterTest.kt @@ -0,0 +1,22 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters.collections + +import aws.sdk.kotlin.hll.mapping.core.converters.testutils.NumberToWordConverter +import kotlin.test.Test +import kotlin.test.assertEquals + +class SetMappingConverterTest { + @Test + fun testSetMapping() { + val converter = SetMappingConverter(NumberToWordConverter) + + val left = setOf(1, 1, 2, 3, 5, 8) + val right = setOf("one", "one", "two", "three", "five", "eight") + + assertEquals(right, converter.convertRight(left)) + assertEquals(left, converter.convertLeft(right)) + } +} diff --git a/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/testutils/AnimalEmojiConverter.kt b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/testutils/AnimalEmojiConverter.kt new file mode 100644 index 00000000000..7a113fceed2 --- /dev/null +++ b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/testutils/AnimalEmojiConverter.kt @@ -0,0 +1,38 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters.testutils + +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.reversedBy + +private val emojiToAnimalConverter = MonoConverter { + when (it) { + "🐜" -> "ant" + "🦇" -> "bat" + "🐊" -> "crocodile" + "🐕" -> "dog" + "🦅" -> "eagle" + "🐟" -> "fish" + "🦒" -> "giraffe" + "🐎" -> "horse" + else -> error("""Unknown animal emoji "$it"""") + } +} + +private val animalToEmojiConverter = MonoConverter { + when (it) { + "ant" -> "🐜" + "bat" -> "🦇" + "crocodile" -> "🐊" + "dog" -> "🐕" + "eagle" -> "🦅" + "fish" -> "🐟" + "giraffe" -> "🦒" + "horse" -> "🐎" + else -> error("""Unknown animal name "$it"""") + } +} + +val AnimalEmojiConverter = animalToEmojiConverter reversedBy emojiToAnimalConverter diff --git a/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/testutils/NumberToWordConverter.kt b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/testutils/NumberToWordConverter.kt new file mode 100644 index 00000000000..0ab551d69bb --- /dev/null +++ b/hll/hll-mapping-core/common/test/aws/sdk/kotlin/hll/mapping/core/converters/testutils/NumberToWordConverter.kt @@ -0,0 +1,44 @@ +/* + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0 + */ +package aws.sdk.kotlin.hll.mapping.core.converters.testutils + +import aws.sdk.kotlin.hll.mapping.core.converters.MonoConverter +import aws.sdk.kotlin.hll.mapping.core.converters.reversedBy + +private val numberToWordConverter = MonoConverter { + when (it) { + 0 -> "zero" + 1 -> "one" + 2 -> "two" + 3 -> "three" + 4 -> "four" + 5 -> "five" + 6 -> "six" + 7 -> "seven" + 8 -> "eight" + 9 -> "nine" + 10 -> "ten" + else -> error("Unsupported number value $it") + } +} + +private val wordToNumberConverter = MonoConverter { + when (it) { + "zero" -> 0 + "one" -> 1 + "two" -> 2 + "three" -> 3 + "four" -> 4 + "five" -> 5 + "six" -> 6 + "seven" -> 7 + "eight" -> 8 + "nine" -> 9 + "ten" -> 10 + else -> error("""Unknown number string "$it"""") + } +} + +val NumberToWordConverter = numberToWordConverter reversedBy wordToNumberConverter diff --git a/hll/hll-mapping-core/docs/img/chaining-converter.png b/hll/hll-mapping-core/docs/img/chaining-converter.png new file mode 100644 index 00000000000..6f1f08fbc60 Binary files /dev/null and b/hll/hll-mapping-core/docs/img/chaining-converter.png differ diff --git a/hll/hll-mapping-core/docs/img/element-mapping-converter.png b/hll/hll-mapping-core/docs/img/element-mapping-converter.png new file mode 100644 index 00000000000..69fd7be332d Binary files /dev/null and b/hll/hll-mapping-core/docs/img/element-mapping-converter.png differ