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
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
/// Evaluates to a protobuf map [`FieldBuilder`](crate::fields::FieldBuilder).
///
/// Use [`enum_map`](crate::enum_map) or [`msg_map`](crate::msg_map) if the values for the map are messages or enums.
/// The first argument is the name of the field, followed by `<$key_type, $value_type>`, which are two idents describing the field types.
/// The last, optional argument is a closure that will receive three arguments, the first being a [`MapValidator`](crate::validators::map::MapValidator) instance, and the other two being the field validator instances for the given key/value types.
/// # Examples
/// ```
/// use protoschema::map;
/// // Without validator
/// let my_field = map!("my_map", <int64, string>);
/// // With validator
/// let my_field2 = map!("my_map_with_validator",
/// <int64, string>,
/// |map_validator, keys_validator, values_validator|
/// map_validator.min_pairs(2).keys(keys_validator.gt(0)).values(values_validator.min_len(1))
/// );
///
/// // For common or rpc types, use their name in snake case
/// let my_field_3 = map!("well_known_types_map", <string, duration>);
/// let my_field_4 = map!("well_known_types_map", <string, http_request>);
/// let my_field_5 = map!("well_known_types_map", <string, money>);
/// ```
/// Evaluates to a protobuf map field, where the values are of the specified enum type.
///
/// The first argument is the name of the field, followed by `<$key_type, $enum_ident>`, where $key_type is a plain ident for the type of the keys, and the $enum_ident is an ident pointing to a [`EnumBuilder`](crate::enums::EnumBuilder) instance.
/// The last, optional argument is a closure that will receive three arguments, the first being a [`MapValidator`](crate::validators::map::MapValidator) instance, and the other two being the field validator instances for the given key type and the [`EnumValidator`](crate::validators::enums::EnumValidator) builder.
/// # Examples
/// ```
/// use protoschema::{enum_map, Package};
///
/// let pkg = Package::new("my_pkg");
/// let file = pkg.new_file("my_file");
/// let my_enum = file.new_enum("my_enum");
/// // Without validator
/// let my_field = enum_map!("my_map", <int64, my_enum>);
/// // With validator
/// let my_field2 = enum_map!("my_map_with_validator",
/// <int64, my_enum>,
/// |map_validator, keys_validator, values_validator|
/// map_validator.min_pairs(2).keys(keys_validator.gt(0)).values(values_validator.defined_only())
/// );
/// ```
/// Evaluates to a protobuf map field, where the values are of the specified message type.
///
/// The first argument is the name of the field, followed by `<$key_type, $msg_ident>`, where $key_type is a plain ident for the type of the keys, and the $msg_ident is an ident pointing to a [`MessageBuilder`](crate::messages::MessageBuilder) instance.
/// The last, optional argument is a closure that will receive three arguments, the first being a [`MapValidator`](crate::validators::map::MapValidator) instance, and the other two being the field validator instances for the given key type and the [`MessageValidator`](crate::validators::message::MessageValidator) builder.
///
/// You only need to use this for custom messages. For well known types such as those from google.type or google.rpc or google.protobuf which have their dedicated field macro (i.e. http_request!), you can use [`map`] directly.
/// # Examples
/// ```
/// use protoschema::{Package, msg_map, cel_rule};
///
/// let pkg = Package::new("my_pkg");
/// let file = pkg.new_file("my_file");
/// let my_msg = file.new_message("my_msg");
/// // Without validator
/// let my_field = msg_map!("my_map", <int64, my_msg>);
/// // With validator
/// let my_field2 = msg_map!("my_map_with_validator",
/// <int64, my_msg>,
/// |map_validator, keys_validator, values_validator|
/// map_validator.min_pairs(2).keys(keys_validator.gt(0)).values(values_validator.cel([
/// cel_rule!(
/// id = "passwords_not_matching",
/// msg = "the two passwords do not match",
/// expr = "this.password == this.repeated_password"
/// )
/// ]))
/// );
/// ```