Skip to content

Commit f7890c9

Browse files
chore: Use anchors in regular expressions (#102)
1 parent bbd389d commit f7890c9

3 files changed

Lines changed: 20 additions & 17 deletions

File tree

rust/operator-binary/src/crd/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -425,7 +425,7 @@ attributed_string_type! {
425425
"Key in an OpenSearch keystore",
426426
"s3.client.default.access_key",
427427
(min_length = 1),
428-
(regex = "[A-Za-z0-9_\\-.]+")
428+
(regex = "^[A-Za-z0-9_\\-.]+$")
429429
}
430430

431431
#[cfg(test)]

rust/operator-binary/src/framework/macros/attributed_string_type.rs

Lines changed: 17 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ use strum::{EnumDiscriminants, IntoStaticStr};
33

44
/// Maximum length of label values
55
///
6-
/// Duplicates the private constant [`stackable-operator::kvp::label::value::LABEL_VALUE_MAX_LEN`]
6+
/// Duplicates the private constant [`stackable_operator::kvp::LABEL_VALUE_MAX_LEN`]
77
pub const MAX_LABEL_VALUE_LENGTH: usize = 63;
88

99
#[derive(Debug, EnumDiscriminants, Snafu)]
@@ -185,7 +185,7 @@ macro_rules! attributed_string_type {
185185
None
186186
},
187187
"pattern": match $name::REGEX {
188-
$crate::framework::macros::attributed_string_type::Regex::Expression(regex) => Some(std::format!("^{regex}$")),
188+
$crate::framework::macros::attributed_string_type::Regex::Expression(regex) => Some(regex),
189189
_ => None
190190
}
191191
})
@@ -377,24 +377,27 @@ macro_rules! attributed_string_type {
377377
.combine(attributed_string_type!(@regex $($attribute)*))
378378
};
379379
(@regex is_rfc_1035_label_name $($attribute:tt)*) => {
380-
$crate::framework::macros::attributed_string_type::Regex::Expression(stackable_operator::validation::LOWERCASE_RFC_1035_LABEL_FMT)
380+
// see https://github.com/kubernetes/kubernetes/blob/v1.35.0/staging/src/k8s.io/apimachinery/pkg/util/validation/validation.go#L228
381+
$crate::framework::macros::attributed_string_type::Regex::Expression("^[a-z]([-a-z0-9]*[a-z0-9])?$")
381382
.combine(attributed_string_type!(@regex $($attribute)*))
382383
};
383384
(@regex is_rfc_1123_dns_subdomain_name $($attribute:tt)*) => {
384-
$crate::framework::macros::attributed_string_type::Regex::Expression(stackable_operator::validation::LOWERCASE_RFC_1123_SUBDOMAIN_FMT)
385+
// see https://github.com/kubernetes/kubernetes/blob/v1.35.0/staging/src/k8s.io/apimachinery/pkg/util/validation/validation.go#L193
386+
$crate::framework::macros::attributed_string_type::Regex::Expression("^[a-z0-9]([-a-z0-9]*[a-z0-9])?(\\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*$")
385387
.combine(attributed_string_type!(@regex $($attribute)*))
386388
};
387389
(@regex is_rfc_1123_label_name $($attribute:tt)*) => {
388-
$crate::framework::macros::attributed_string_type::Regex::Expression(stackable_operator::validation::LOWERCASE_RFC_1123_LABEL_FMT)
390+
// see https://github.com/kubernetes/kubernetes/blob/v1.35.0/staging/src/k8s.io/apimachinery/pkg/util/validation/validation.go#L163
391+
$crate::framework::macros::attributed_string_type::Regex::Expression("^[a-z0-9]([-a-z0-9]*[a-z0-9])?$")
389392
.combine(attributed_string_type!(@regex $($attribute)*))
390393
};
391394
(@regex is_valid_label_value $($attribute:tt)*) => {
392395
// regular expression from stackable_operator::kvp::label::LABEL_VALUE_REGEX
393-
$crate::framework::macros::attributed_string_type::Regex::Expression("[a-z0-9A-Z]([a-z0-9A-Z-_.]*[a-z0-9A-Z]+)?")
396+
$crate::framework::macros::attributed_string_type::Regex::Expression("^[a-z0-9A-Z]([a-z0-9A-Z-_.]*[a-z0-9A-Z]+)?$")
394397
.combine(attributed_string_type!(@regex $($attribute)*))
395398
};
396399
(@regex is_uid $($attribute:tt)*) => {
397-
$crate::framework::macros::attributed_string_type::Regex::Expression("[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}")
400+
$crate::framework::macros::attributed_string_type::Regex::Expression("^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}$")
398401
.combine(attributed_string_type!(@regex $($attribute)*))
399402
};
400403

@@ -513,7 +516,7 @@ mod tests {
513516
"test",
514517
(min_length = 2), // should set the minimum length to 2
515518
(max_length = 8), // should not affect the minimum length
516-
(regex = ".{4}"), // should not affect the minimum length
519+
(regex = "^.{4}$"), // should not affect the minimum length
517520
is_rfc_1035_label_name, // should be overruled by the greater min_length
518521
is_valid_label_value // should be overruled by the greater min_length
519522
}
@@ -550,7 +553,7 @@ mod tests {
550553
"test",
551554
(min_length = 2), // should not affect the maximum length
552555
(max_length = 8), // should set the maximum length to 8
553-
(regex = ".{4}"), // should not affect the maximum length
556+
(regex = "^.{4}$"), // should not affect the maximum length
554557
is_rfc_1035_label_name, // should be overruled by the lower max_length
555558
is_valid_label_value // should be overruled by the lower max_length
556559
}
@@ -587,15 +590,15 @@ mod tests {
587590
"test",
588591
(min_length = 2), // should not affect the regular expression
589592
(max_length = 8), // should not affect the regular expression
590-
(regex = "[est]{4}") // should set the regular expression to "[est]{4}"
593+
(regex = "^[est]{4}$") // should set the regular expression to "[est]{4}"
591594
}
592595

593596
#[test]
594597
fn test_attributed_string_type_regex_with_one_constraint() {
595598
type T = RegexWithOneConstraintTest;
596599

597600
T::test_example();
598-
assert_eq!(Regex::Expression("[est]{4}"), T::REGEX);
601+
assert_eq!(Regex::Expression("^[est]{4}$"), T::REGEX);
599602
assert_eq!(
600603
Err(ErrorDiscriminants::RegexNotMatched),
601604
T::from_str("t-st").map_err(ErrorDiscriminants::from)
@@ -608,7 +611,7 @@ mod tests {
608611
"test",
609612
(min_length = 2), // should not affect the regular expression
610613
(max_length = 8), // should not affect the regular expression
611-
(regex = "[est]{4}"), // should not be combinable with is_rfc_1123_dns_subdomain_name
614+
(regex = "^[est]{4}$"), // should not be combinable with is_rfc_1123_dns_subdomain_name
612615
is_rfc_1123_dns_subdomain_name // should not be combinable with regex
613616
}
614617

@@ -679,7 +682,7 @@ mod tests {
679682
"test",
680683
(min_length = 2),
681684
(max_length = 4),
682-
(regex = "[est-]+"),
685+
(regex = "^[est-]+$"),
683686
is_rfc_1035_label_name
684687
}
685688

@@ -785,7 +788,7 @@ mod tests {
785788
"test",
786789
(min_length = 4),
787790
(max_length = 8),
788-
(regex = "[est]+")
791+
(regex = "^[est]+$")
789792
}
790793

791794
#[test]

rust/operator-binary/src/framework/types/kubernetes.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ attributed_string_type! {
1919
(min_length = 1),
2020
// see https://github.com/kubernetes/kubernetes/blob/v1.34.1/staging/src/k8s.io/apimachinery/pkg/util/validation/validation.go#L435-L451
2121
(max_length = RFC_1123_SUBDOMAIN_MAX_LENGTH),
22-
(regex = "[-._a-zA-Z0-9]+")
22+
(regex = "^[-._a-zA-Z0-9]+$")
2323
}
2424

2525
attributed_string_type! {
@@ -95,7 +95,7 @@ attributed_string_type! {
9595
(min_length = 1),
9696
// see https://github.com/kubernetes/kubernetes/blob/v1.34.1/staging/src/k8s.io/apimachinery/pkg/util/validation/validation.go#L435-L451
9797
(max_length = RFC_1123_SUBDOMAIN_MAX_LENGTH),
98-
(regex = "[-._a-zA-Z0-9]+")
98+
(regex = "^[-._a-zA-Z0-9]+$")
9999
}
100100

101101
attributed_string_type! {

0 commit comments

Comments
 (0)