forked from aws/aws-dynamodb-encryption-python
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathhypothesis_strategies.py
87 lines (67 loc) · 3.43 KB
/
hypothesis_strategies.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
# -*- coding: utf-8 -*-
# Copyright 2018 Amazon.com, Inc. or its affiliates. All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"). You
# may not use this file except in compliance with the License. A copy of
# the License is located at
#
# http://aws.amazon.com/apache2.0/
#
# or in the "license" file accompanying this file. This file is
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
# ANY KIND, either express or implied. See the License for the specific
# language governing permissions and limitations under the License.
"""Hypothesis strategies for use in tests."""
from decimal import Decimal
import hypothesis
from boto3.dynamodb.types import Binary
from hypothesis.strategies import binary, booleans, deferred, dictionaries, fractions, just, lists, none, sets, text
SLOW_SETTINGS = hypothesis.settings(
suppress_health_check=(
hypothesis.HealthCheck.too_slow,
hypothesis.HealthCheck.data_too_large,
hypothesis.HealthCheck.large_base_example,
# Hypothesis requires that we acknowledge that the example_table fixure
# is not reset between examples generated by hypothesis.given.
# This is the desired behavior for example_table, so supress this check
hypothesis.HealthCheck.function_scoped_fixture,
),
deadline=None,
)
VERY_SLOW_SETTINGS = hypothesis.settings(SLOW_SETTINGS, max_examples=1000)
MAX_ITEM_BYTES = 400 * 1024 * 1024
# _MIN_NUMBER = Decimal('1E-128') # The DDB min is 1E-130, but DYNAMODB_CONTEXT Emin is -128
# _MAX_NUMBER = Decimal('9.9999999999999999999999999999999999999E+125')
# boto3 does not correctly handle conversion of large edge case values at this time
_MIN_NUMBER = Decimal("1E-38")
_MAX_NUMBER = Decimal("9.{}E37".format("9" * 37))
ddb_string = text(min_size=1, max_size=MAX_ITEM_BYTES)
ddb_string_set = sets(ddb_string, min_size=1)
def _ddb_fraction_to_decimal(val):
"""Hypothesis does not support providing a custom Context, so working around that."""
return Decimal(val.numerator) / Decimal(val.denominator)
def _negative(val):
return val * Decimal("-1")
ddb_positive_numbers = fractions(min_value=_MIN_NUMBER, max_value=_MAX_NUMBER).map(_ddb_fraction_to_decimal)
ddb_negative_numbers = ddb_positive_numbers.map(_negative)
ddb_number = ddb_negative_numbers | just(Decimal("0")) | ddb_positive_numbers
ddb_number_set = sets(ddb_number, min_size=1)
ddb_binary = binary(min_size=1, max_size=MAX_ITEM_BYTES).map(Binary)
ddb_binary_set = sets(ddb_binary, min_size=1)
ddb_boolean = booleans()
ddb_null = none()
ddb_scalar_types = ddb_string | ddb_number | ddb_binary | ddb_boolean | ddb_null
ddb_set_types = ddb_string_set | ddb_number_set | ddb_binary_set
ddb_attribute_names = text(min_size=1, max_size=255)
# List and Map types have a max depth of 32
# https://github.com/aws/aws-dynamodb-encryption-python/issues/141
ddb_map_type = deferred(
lambda: dictionaries(
keys=ddb_attribute_names, values=(ddb_scalar_types | ddb_set_types | ddb_list_type | ddb_map_type), min_size=1
)
)
ddb_list_type = deferred(lambda: lists(ddb_scalar_types | ddb_set_types | ddb_list_type | ddb_map_type, min_size=1))
ddb_document_types = ddb_map_type | ddb_list_type
ddb_attribute_values = ddb_scalar_types | ddb_set_types | ddb_list_type
ddb_items = dictionaries(keys=ddb_attribute_names, values=ddb_attribute_values, min_size=1)
material_descriptions = deferred(lambda: dictionaries(keys=text(), values=text(), min_size=1))