Repository: typedorm/typedorm (ts)

Issue:
Incorrect type on filter operation CONTAINS
`CONTAINS` operation forces, same set type on the value, which should instead be a scalar type that the list contains.

i.e for String Sets, the value for the `CONTAINS` operation should be `String` 

Pull request:
fix(core): in filter and condition expression, correctly infer value types
closes #146

Patch:
diff --git a/packages/common/public-api.ts b/packages/common/public-api.ts
index e89a9b9..0ba0815 100644
--- a/packages/common/public-api.ts
+++ b/packages/common/public-api.ts
@@ -23,6 +23,7 @@ export * from './src/helpers/is-primary-key';
 export * from './src/helpers/nested-attributes-type';
 export * from './src/utils/get-entity-definition';
 export * from './src/helpers/invalid-type';
+export * from './src/helpers/resolve-scalar-type';
 
 // exceptions
 export * from './src/exceptions';
diff --git a/packages/common/src/helpers/resolve-scalar-type.ts b/packages/common/src/helpers/resolve-scalar-type.ts
new file mode 100644
index 0000000..ac8d0e9
--- /dev/null
+++ b/packages/common/src/helpers/resolve-scalar-type.ts
@@ -0,0 +1,10 @@
+import {InvalidType} from './invalid-type';
+import {ScalarType} from './scalar-type';
+
+export type ResolveScalarType<T extends any> = T extends ScalarType
+  ? ScalarType
+  : T extends any[]
+  ? T[0] extends ScalarType
+    ? T[0]
+    : InvalidType<[T[0], 'can not be resolved to a scalar type']>
+  : InvalidType<[T, 'can not be resolved to a scalar type']>;
diff --git a/packages/core/src/classes/expression/condition-options-type.ts b/packages/core/src/classes/expression/condition-options-type.ts
index 8e92cbb..6751c73 100644
--- a/packages/core/src/classes/expression/condition-options-type.ts
+++ b/packages/core/src/classes/expression/condition-options-type.ts
@@ -4,6 +4,7 @@ import {
   ConditionType,
   ATTRIBUTE_TYPE,
   RequireAtLeastOne,
+  ResolveScalarType,
 } from '@typedorm/common';
 
 type AttributeConditionOptions<Entity> =
@@ -16,13 +17,13 @@ type AttributeConditionOptions<Entity> =
             | Extract<
                 ConditionType.FunctionOperator,
                 'CONTAINS' | 'BEGINS_WITH'
-              >]: Entity[enKey];
+              >]: ResolveScalarType<Entity[enKey]>;
         } &
           // if between operator, value must be an array of two items
           {
             [key in Extract<ConditionType.RangeOperator, 'BETWEEN'>]: [
-              Entity[enKey],
-              Entity[enKey]
+              ResolveScalarType<Entity[enKey]>,
+              ResolveScalarType<Entity[enKey]>
             ];
           } &
           // for 'IN' operator value must be a list of scalar type
@@ -30,7 +31,7 @@ type AttributeConditionOptions<Entity> =
             [key in Extract<
               ConditionType.RangeOperator,
               'IN'
-            >]: Entity[enKey][];
+            >]: ResolveScalarType<Entity[enKey]>[];
           } &
           // for 'ATTRIBUTE_TYPE' value must be one of the given enum values
           {
@@ -46,7 +47,7 @@ type AttributeConditionOptions<Entity> =
               'SIZE'
             >]: RequireOnlyOne<
               {
-                [key in ConditionType.SimpleOperator]: Entity[enKey];
+                [key in ConditionType.SimpleOperator]: number;
               }
             >;
           }
diff --git a/packages/core/src/classes/expression/filter-options-type.ts b/packages/core/src/classes/expression/filter-options-type.ts
index 3a7d450..6126999 100644
--- a/packages/core/src/classes/expression/filter-options-type.ts
+++ b/packages/core/src/classes/expression/filter-options-type.ts
@@ -4,6 +4,7 @@ import {
   NonKeyAttributesWithReturnType,
   RequireAtLeastOne,
   RequireOnlyOne,
+  ResolveScalarType,
 } from '@typedorm/common';
 
 type AttributeFilterOptions<Entity, PrimaryKey> =
@@ -16,16 +17,18 @@ type AttributeFilterOptions<Entity, PrimaryKey> =
             | Extract<
                 FilterType.FunctionOperator,
                 'CONTAINS' | 'BEGINS_WITH'
-              >]: Entity[enKey];
+              >]: ResolveScalarType<Entity[enKey]>;
         } &
           {
             [key in Extract<FilterType.RangeOperator, 'BETWEEN'>]: [
-              Entity[enKey],
-              Entity[enKey]
+              ResolveScalarType<Entity[enKey]>,
+              ResolveScalarType<Entity[enKey]>
             ];
           } &
           {
-            [key in Extract<FilterType.RangeOperator, 'IN'>]: Entity[enKey][];
+            [key in Extract<FilterType.RangeOperator, 'IN'>]: ResolveScalarType<
+              Entity[enKey]
+            >[];
           } &
           {
             [key in Extract<
@@ -39,7 +42,7 @@ type AttributeFilterOptions<Entity, PrimaryKey> =
               'SIZE'
             >]: RequireOnlyOne<
               {
-                [key in FilterType.SimpleOperator]: Entity[enKey];
+                [key in FilterType.SimpleOperator]: number;
               }
             >;
           }


Test patch:
diff --git a/packages/core/src/classes/expression/__test__/expression-input-parser.spec.ts b/packages/core/src/classes/expression/__test__/expression-input-parser.spec.ts
index 5f1dc3a..c173dda 100644
--- a/packages/core/src/classes/expression/__test__/expression-input-parser.spec.ts
+++ b/packages/core/src/classes/expression/__test__/expression-input-parser.spec.ts
@@ -109,7 +109,7 @@ test('parses filter with size operator', () => {
   const parsedFilter = expInputParser.parseToFilter<User, UserPrimaryKey>({
     status: {
       SIZE: {
-        EQ: '1',
+        EQ: 1,
       },
     },
   });