Skip to content

Commit ebcd658

Browse files
docs(improve): add better doc
for attribute2 and update2 functions to describe the typing enhancement
1 parent 9deed5a commit ebcd658

File tree

4 files changed

+64
-11
lines changed

4 files changed

+64
-11
lines changed

src/dynamo/expression/condition-expression-builder.ts

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -287,8 +287,7 @@ function validateForOperator(operator: ConditionOperator, values?: any[]) {
287287
if (values && Array.isArray(values) && values.length) {
288288
validateValues(operator, values)
289289
} else {
290-
// TODO
291-
throw new Error('blub')
290+
throw new Error(dynamicTemplate(ERR_ARITY_DEFAULT, {parameterArity: operatorParameterArity(operator), operator}))
292291
}
293292
}
294293
}

src/dynamo/expression/logical-operator/attribute.function.ts

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,17 +5,35 @@ import {
55
ConditionExpressionDefinitionChainTyped,
66
} from '../type/condition-expression-definition-chain'
77

8-
98
/**
10-
* Use this method when accessing a top level attribute of a model
9+
* Use this method when accessing a top level attribute of a model with strict typing of the value in chained function
10+
*
11+
* ```typescript
12+
* @Model()
13+
* class Person{
14+
*
15+
* @PartitionKeyUUID()
16+
* id: string
17+
* age: number
18+
* }
19+
*
20+
* store
21+
* .scan()
22+
* .where(attribute2(Person, 'age').equals(5))
23+
* .exec()
24+
* ```
25+
*
26+
* When using the attribute2 we have type support for the equals (and all other condition functions) value,
27+
* it can only be number, because the type of age is number too, this only works when not using a custom mapper.
28+
* The downside of the strict typing is the model constructor parameter which is only required for typing reasons
1129
*/
1230
export function attribute2<T, K extends keyof T>(modelConstructor: ModelConstructor<T>, attributePath: K)
1331
: ConditionExpressionDefinitionChainTyped<T, K> {
1432
return propertyDefinitionFunction<T, K>(attributePath)
1533
}
1634

1735
/**
18-
* Use this method when accessing a top level attribute of a model
36+
* Use this method when accessing a top level attribute of a model to have type checking of the attributePath
1937
*/
2038
export function attribute<T>(attributePath: keyof T): ConditionExpressionDefinitionChain
2139

src/dynamo/expression/logical-operator/update.function.ts

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,25 @@ import {
66
} from '../type/update-expression-definition-chain'
77

88
/**
9-
* Use this method when accessing a top level attribute of a model
9+
* Use this method when accessing a top level attribute of a model with strict typing of the value in chained function
10+
*
11+
* ```typescript
12+
* @Model()
13+
* class Person{
14+
*
15+
* @PartitionKeyUUID()
16+
* id: string
17+
* age: number
18+
* }
19+
*
20+
* store.update('idValue')
21+
* .operations(update2(SimpleWithPartitionKeyModel, 'age').set(5))
22+
* .exec()
23+
* ```
24+
*
25+
* When using the update2 we have type support for the set (and all other update functions) value,
26+
* it can only be number, because the type of age is number too, this only works when not using a custom mapper.
27+
* The downside of the strict typing is the model constructor parameter which is only required for typing reasons.
1028
*/
1129
export function update2<T, K extends keyof T>(
1230
modelConstructor: ModelConstructor<T>,
@@ -16,7 +34,7 @@ export function update2<T, K extends keyof T>(
1634
}
1735

1836
/**
19-
* Use this method when accessing a top level attribute of a model
37+
* Use this method when accessing a top level attribute of a model to have type checking for attributePath
2038
*/
2139
export function update<T>(attributePath: keyof T): UpdateExpressionDefinitionChain
2240

src/dynamo/expression/param-util.ts

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import { resolveAttributeValueNameConflicts } from './functions/resolve-attribut
55
import { Expression } from './type'
66
import { UpdateActionKeyword } from './type/update-action-keyword.type'
77

8-
export function addUpdateExpression(updateExpression: Expression, params: UpdateItemInput) {
8+
export function addUpdateExpression(updateExpression: Expression, params: UpdateItemInput): void {
99
addExpression('UpdateExpression', updateExpression, params)
1010
}
1111

@@ -48,11 +48,23 @@ export function addExpression(
4848
}
4949
}
5050

51+
type UpdateExpressionsByKeyword = Record<UpdateActionKeyword, string>
5152

52-
type UpdateExpressionsByKeyword = {
53-
[key in UpdateActionKeyword]: string
54-
}
5553

54+
/**
55+
* Will merge two update expressions into one, one action keyword can only appear once in an update expression
56+
*
57+
* ```
58+
* const merged = mergeUpdateExpressions(
59+
* 'SET a, b REMOVE e, f ADD i, j DELETE m, n',
60+
* 'SET c, d REMOVE g, h ADD k, l DELETE o, p',
61+
* )
62+
* console.log(merged) -> 'SET a, b, c, d REMOVE e, f, g, h ADD i, j, k, l DELETE m, n, o, p'
63+
* ```
64+
*
65+
* @param expression1
66+
* @param expression2
67+
*/
5668
export function mergeUpdateExpressions(expression1: string, expression2: string): string {
5769
const a = splitUpdateExpressionToActionKeyword(expression1)
5870
const b = splitUpdateExpressionToActionKeyword(expression2)
@@ -61,6 +73,9 @@ export function mergeUpdateExpressions(expression1: string, expression2: string)
6173
.join(' ')
6274
}
6375

76+
/**
77+
* Will return an object containing all the update statements mapped to an update action keyword
78+
*/
6479
function splitUpdateExpressionToActionKeyword(updateExpression: string): UpdateExpressionsByKeyword {
6580
// add a whitespace at the beginning of the expression to be able to work with a more stricter regex
6681
return ` ${updateExpression}`
@@ -70,7 +85,10 @@ function splitUpdateExpressionToActionKeyword(updateExpression: string): UpdateE
7085
.reduce((u, e, i, arr) => {
7186
if (isUpdateActionKeyword(e)) {
7287
u[e] = arr[i + 1]
88+
} else {
89+
throw new Error(`unknown action keyword ${e}`)
7390
}
91+
7492
return u
7593
}, <UpdateExpressionsByKeyword>{})
7694
}

0 commit comments

Comments
 (0)