github.com/greenpau/go-authcrunch@v1.1.4/pkg/acl/condition.go (about) 1 // Copyright 2022 Paul Greenberg greenpau@outlook.com 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package acl 16 17 import ( 18 "context" 19 "github.com/greenpau/go-authcrunch/pkg/errors" 20 "regexp" 21 "strings" 22 ) 23 24 type dataType int 25 type fieldMatchStrategy int 26 27 var ( 28 matchWithStrategyRgx *regexp.Regexp 29 matchFieldRgx *regexp.Regexp 30 31 inputDataTypes = map[string]dataType{ 32 "roles": dataTypeListStr, 33 "email": dataTypeStr, 34 "origin": dataTypeStr, 35 "name": dataTypeStr, 36 "realm": dataTypeStr, 37 "aud": dataTypeListStr, 38 "scopes": dataTypeListStr, 39 "org": dataTypeListStr, 40 "jti": dataTypeStr, 41 "iss": dataTypeStr, 42 "sub": dataTypeStr, 43 "addr": dataTypeStr, 44 "method": dataTypeStr, 45 "path": dataTypeStr, 46 } 47 48 inputDataAliases = map[string]string{ 49 "id": "jti", 50 "audience": "aud", 51 "expires": "exp", 52 "issued": "iat", 53 "issuer": "iss", 54 "subject": "sub", 55 "mail": "email", 56 "role": "roles", 57 "group": "roles", 58 "groups": "roles", 59 "scope": "scopes", 60 "organization": "org", 61 "address": "addr", 62 "ip": "addr", 63 "ipv4": "addr", 64 "http_method": "method", 65 "http_path": "path", 66 } 67 ) 68 69 const ( 70 dataTypeUnknown dataType = 0 71 dataTypeListStr dataType = 1 72 dataTypeStr dataType = 2 73 dataTypeAny dataType = 3 74 75 fieldMatchUnknown fieldMatchStrategy = 0 76 fieldMatchReserved fieldMatchStrategy = 1 77 fieldMatchExact fieldMatchStrategy = 2 78 fieldMatchPartial fieldMatchStrategy = 3 79 fieldMatchPrefix fieldMatchStrategy = 4 80 fieldMatchSuffix fieldMatchStrategy = 5 81 fieldMatchRegex fieldMatchStrategy = 6 82 fieldFound fieldMatchStrategy = 7 83 fieldNotFound fieldMatchStrategy = 8 84 fieldMatchAlways fieldMatchStrategy = 9 85 ) 86 87 type field struct { 88 name string 89 length int 90 } 91 92 type expr struct { 93 value string 94 length int 95 } 96 97 type config struct { 98 field string 99 matchStrategy fieldMatchStrategy 100 values []string 101 regexEnabled bool 102 alwaysTrue bool 103 matchAny bool 104 exprDataType dataType 105 inputDataType dataType 106 conditionType string 107 } 108 109 type aclRuleCondition interface { 110 match(context.Context, interface{}) bool 111 getConfig(context.Context) *config 112 } 113 114 // ruleAnyCondAlwaysMatchAnyInput returns positive match regardless of 115 // input fields, values, or conditions. 116 type ruleAnyCondAlwaysMatchAnyInput struct { 117 field *field 118 exprs []*expr 119 config *config 120 } 121 122 // ruleCondFieldFound returns positive match regardless of input fields, values, 123 // or conditions, because the condition is only relevant to ACL rule itself. 124 type ruleCondFieldFound struct { 125 field *field 126 exprs []*expr 127 config *config 128 } 129 130 // ruleCondFieldNotFound returns positive match regardless of input fields, values, 131 // or conditions, because the condition is only relevant to ACL rule itself. 132 type ruleCondFieldNotFound struct { 133 field *field 134 exprs []*expr 135 config *config 136 } 137 138 func (c *ruleAnyCondAlwaysMatchAnyInput) match(ctx context.Context, v interface{}) bool { 139 return true 140 } 141 142 func (c *ruleAnyCondAlwaysMatchAnyInput) getConfig(ctx context.Context) *config { 143 return c.config 144 } 145 146 func (c *ruleCondFieldFound) match(ctx context.Context, v interface{}) bool { 147 return true 148 } 149 150 func (c *ruleCondFieldFound) getConfig(ctx context.Context) *config { 151 return c.config 152 } 153 154 func (c *ruleCondFieldNotFound) match(ctx context.Context, v interface{}) bool { 155 return true 156 } 157 158 func (c *ruleCondFieldNotFound) getConfig(ctx context.Context) *config { 159 return c.config 160 } 161 162 // ruleListStrCondExactNegativeMatchListStrInput not matches a list of strings 163 // input against a list of strings where any of the input values not match at least 164 // one value of the condition using exact not match. 165 type ruleListStrCondExactNegativeMatchListStrInput struct { 166 field *field 167 exprs []*expr 168 config *config 169 } 170 171 // ruleListStrCondPartialNegativeMatchListStrInput not matches a list of strings 172 // input against a list of strings where any of the input values not match at least 173 // one value of the condition using substring not match. 174 type ruleListStrCondPartialNegativeMatchListStrInput struct { 175 field *field 176 exprs []*expr 177 config *config 178 } 179 180 // ruleListStrCondPrefixNegativeMatchListStrInput not matches a list of strings 181 // input against a list of strings where any of the input values not match at least 182 // one value of the condition using string prefix not match. 183 type ruleListStrCondPrefixNegativeMatchListStrInput struct { 184 field *field 185 exprs []*expr 186 config *config 187 } 188 189 // ruleListStrCondSuffixNegativeMatchListStrInput not matches a list of strings 190 // input against a list of strings where any of the input values not match at least 191 // one value of the condition using string suffix not match. 192 type ruleListStrCondSuffixNegativeMatchListStrInput struct { 193 field *field 194 exprs []*expr 195 config *config 196 } 197 198 // ruleListStrCondRegexNegativeMatchListStrInput not matches a list of strings 199 // input against a list of strings where any of the input values not match at least 200 // one value of the condition using regular expressions not match. 201 type ruleListStrCondRegexNegativeMatchListStrInput struct { 202 field *field 203 exprs []*regexp.Regexp 204 config *config 205 } 206 207 // ruleStrCondExactNegativeMatchListStrInput not matches a list of strings input 208 // against a string condition using exact not match. 209 type ruleStrCondExactNegativeMatchListStrInput struct { 210 field *field 211 expr *expr 212 config *config 213 } 214 215 // ruleStrCondPartialNegativeMatchListStrInput not matches a list of strings input 216 // against a string condition using substring not match. 217 type ruleStrCondPartialNegativeMatchListStrInput struct { 218 field *field 219 expr *expr 220 config *config 221 } 222 223 // ruleStrCondPrefixNegativeMatchListStrInput not matches a list of strings input 224 // against a string condition using string prefix not match. 225 type ruleStrCondPrefixNegativeMatchListStrInput struct { 226 field *field 227 expr *expr 228 config *config 229 } 230 231 // ruleStrCondSuffixNegativeMatchListStrInput not matches a list of strings input 232 // against a string condition using string suffix not match. 233 type ruleStrCondSuffixNegativeMatchListStrInput struct { 234 field *field 235 expr *expr 236 config *config 237 } 238 239 // ruleStrCondRegexNegativeMatchListStrInput not matches a list of strings input 240 // against a string condition using regular expressions not match. 241 type ruleStrCondRegexNegativeMatchListStrInput struct { 242 field *field 243 expr *regexp.Regexp 244 config *config 245 } 246 247 // ruleListStrCondExactNegativeMatchStrInput not matches an input string against a 248 // list of strings where any of the input values not match at least one value of 249 // the condition using exact not match. 250 type ruleListStrCondExactNegativeMatchStrInput struct { 251 field *field 252 exprs []*expr 253 config *config 254 } 255 256 // ruleListStrCondPartialNegativeMatchStrInput not matches an input string against 257 // a list of strings where any of the input values not match at least one value of 258 // the condition using substring not match. 259 type ruleListStrCondPartialNegativeMatchStrInput struct { 260 field *field 261 exprs []*expr 262 config *config 263 } 264 265 // ruleListStrCondPrefixNegativeMatchStrInput not matches an input string against a 266 // list of strings where any of the input values not match at least one value of 267 // the condition using string prefix not match. 268 type ruleListStrCondPrefixNegativeMatchStrInput struct { 269 field *field 270 exprs []*expr 271 config *config 272 } 273 274 // ruleListStrCondSuffixNegativeMatchStrInput not matches an input string against a 275 // list of strings where any of the input values not match at least one value of 276 // the condition using string suffix not match. 277 type ruleListStrCondSuffixNegativeMatchStrInput struct { 278 field *field 279 exprs []*expr 280 config *config 281 } 282 283 // ruleListStrCondRegexNegativeMatchStrInput not matches an input string against a 284 // list of strings where any of the input values not match at least one value of 285 // the condition using regular expressions not match. 286 type ruleListStrCondRegexNegativeMatchStrInput struct { 287 field *field 288 exprs []*regexp.Regexp 289 config *config 290 } 291 292 // ruleStrCondExactNegativeMatchStrInput not matches an input string against a 293 // string condition using exact not match. 294 type ruleStrCondExactNegativeMatchStrInput struct { 295 field *field 296 expr *expr 297 config *config 298 } 299 300 // ruleStrCondPartialNegativeMatchStrInput not matches an input string against a 301 // string condition using substring not match. 302 type ruleStrCondPartialNegativeMatchStrInput struct { 303 field *field 304 expr *expr 305 config *config 306 } 307 308 // ruleStrCondPrefixNegativeMatchStrInput not matches an input string against a 309 // string condition using string prefix not match. 310 type ruleStrCondPrefixNegativeMatchStrInput struct { 311 field *field 312 expr *expr 313 config *config 314 } 315 316 // ruleStrCondSuffixNegativeMatchStrInput not matches an input string against a 317 // string condition using string suffix not match. 318 type ruleStrCondSuffixNegativeMatchStrInput struct { 319 field *field 320 expr *expr 321 config *config 322 } 323 324 // ruleStrCondRegexNegativeMatchStrInput not matches an input string against a 325 // string condition using regular expressions not match. 326 type ruleStrCondRegexNegativeMatchStrInput struct { 327 field *field 328 expr *regexp.Regexp 329 config *config 330 } 331 332 // ruleListStrCondExactMatchListStrInput matches a list of strings input against a 333 // list of strings where any of the input values match at least one value of the 334 // condition using exact match. 335 type ruleListStrCondExactMatchListStrInput struct { 336 field *field 337 exprs []*expr 338 config *config 339 } 340 341 // ruleListStrCondPartialMatchListStrInput matches a list of strings input against 342 // a list of strings where any of the input values match at least one value of the 343 // condition using substring match. 344 type ruleListStrCondPartialMatchListStrInput struct { 345 field *field 346 exprs []*expr 347 config *config 348 } 349 350 // ruleListStrCondPrefixMatchListStrInput matches a list of strings input against a 351 // list of strings where any of the input values match at least one value of the 352 // condition using string prefix match. 353 type ruleListStrCondPrefixMatchListStrInput struct { 354 field *field 355 exprs []*expr 356 config *config 357 } 358 359 // ruleListStrCondSuffixMatchListStrInput matches a list of strings input against a 360 // list of strings where any of the input values match at least one value of the 361 // condition using string suffix match. 362 type ruleListStrCondSuffixMatchListStrInput struct { 363 field *field 364 exprs []*expr 365 config *config 366 } 367 368 // ruleListStrCondRegexMatchListStrInput matches a list of strings input against a 369 // list of strings where any of the input values match at least one value of the 370 // condition using regular expressions match. 371 type ruleListStrCondRegexMatchListStrInput struct { 372 field *field 373 exprs []*regexp.Regexp 374 config *config 375 } 376 377 // ruleStrCondExactMatchListStrInput matches a list of strings input against a 378 // string condition using exact match. 379 type ruleStrCondExactMatchListStrInput struct { 380 field *field 381 expr *expr 382 config *config 383 } 384 385 // ruleStrCondPartialMatchListStrInput matches a list of strings input against a 386 // string condition using substring match. 387 type ruleStrCondPartialMatchListStrInput struct { 388 field *field 389 expr *expr 390 config *config 391 } 392 393 // ruleStrCondPrefixMatchListStrInput matches a list of strings input against a 394 // string condition using string prefix match. 395 type ruleStrCondPrefixMatchListStrInput struct { 396 field *field 397 expr *expr 398 config *config 399 } 400 401 // ruleStrCondSuffixMatchListStrInput matches a list of strings input against a 402 // string condition using string suffix match. 403 type ruleStrCondSuffixMatchListStrInput struct { 404 field *field 405 expr *expr 406 config *config 407 } 408 409 // ruleStrCondRegexMatchListStrInput matches a list of strings input against a 410 // string condition using regular expressions match. 411 type ruleStrCondRegexMatchListStrInput struct { 412 field *field 413 expr *regexp.Regexp 414 config *config 415 } 416 417 // ruleListStrCondExactMatchStrInput matches an input string against a list of 418 // strings where any of the input values match at least one value of the condition 419 // using exact match. 420 type ruleListStrCondExactMatchStrInput struct { 421 field *field 422 exprs []*expr 423 config *config 424 } 425 426 // ruleListStrCondPartialMatchStrInput matches an input string against a list of 427 // strings where any of the input values match at least one value of the condition 428 // using substring match. 429 type ruleListStrCondPartialMatchStrInput struct { 430 field *field 431 exprs []*expr 432 config *config 433 } 434 435 // ruleListStrCondPrefixMatchStrInput matches an input string against a list of 436 // strings where any of the input values match at least one value of the condition 437 // using string prefix match. 438 type ruleListStrCondPrefixMatchStrInput struct { 439 field *field 440 exprs []*expr 441 config *config 442 } 443 444 // ruleListStrCondSuffixMatchStrInput matches an input string against a list of 445 // strings where any of the input values match at least one value of the condition 446 // using string suffix match. 447 type ruleListStrCondSuffixMatchStrInput struct { 448 field *field 449 exprs []*expr 450 config *config 451 } 452 453 // ruleListStrCondRegexMatchStrInput matches an input string against a list of 454 // strings where any of the input values match at least one value of the condition 455 // using regular expressions match. 456 type ruleListStrCondRegexMatchStrInput struct { 457 field *field 458 exprs []*regexp.Regexp 459 config *config 460 } 461 462 // ruleStrCondExactMatchStrInput matches an input string against a string condition 463 // using exact match. 464 type ruleStrCondExactMatchStrInput struct { 465 field *field 466 expr *expr 467 config *config 468 } 469 470 // ruleStrCondPartialMatchStrInput matches an input string against a string 471 // condition using substring match. 472 type ruleStrCondPartialMatchStrInput struct { 473 field *field 474 expr *expr 475 config *config 476 } 477 478 // ruleStrCondPrefixMatchStrInput matches an input string against a string 479 // condition using string prefix match. 480 type ruleStrCondPrefixMatchStrInput struct { 481 field *field 482 expr *expr 483 config *config 484 } 485 486 // ruleStrCondSuffixMatchStrInput matches an input string against a string 487 // condition using string suffix match. 488 type ruleStrCondSuffixMatchStrInput struct { 489 field *field 490 expr *expr 491 config *config 492 } 493 494 // ruleStrCondRegexMatchStrInput matches an input string against a string condition 495 // using regular expressions match. 496 type ruleStrCondRegexMatchStrInput struct { 497 field *field 498 expr *regexp.Regexp 499 config *config 500 } 501 502 func (c *ruleListStrCondExactNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 503 for _, exp := range c.exprs { 504 for _, v := range values.([]string) { 505 if v == exp.value { 506 return false 507 } 508 } 509 } 510 return true 511 } 512 513 func (c *ruleListStrCondPartialNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 514 for _, exp := range c.exprs { 515 for _, v := range values.([]string) { 516 if strings.Contains(v, exp.value) { 517 return false 518 } 519 } 520 } 521 return true 522 } 523 524 func (c *ruleListStrCondPrefixNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 525 for _, exp := range c.exprs { 526 for _, v := range values.([]string) { 527 if strings.HasPrefix(v, exp.value) { 528 return false 529 } 530 } 531 } 532 return true 533 } 534 535 func (c *ruleListStrCondSuffixNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 536 for _, exp := range c.exprs { 537 for _, v := range values.([]string) { 538 if strings.HasSuffix(v, exp.value) { 539 return false 540 } 541 } 542 } 543 return true 544 } 545 546 func (c *ruleListStrCondRegexNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 547 if c.config.matchAny { 548 for _, exp := range c.exprs { 549 for _, v := range values.([]string) { 550 if !exp.MatchString(v) { 551 return true 552 } 553 } 554 } 555 return false 556 } 557 for _, exp := range c.exprs { 558 for _, v := range values.([]string) { 559 if exp.MatchString(v) { 560 return false 561 } 562 } 563 } 564 return true 565 } 566 567 func (c *ruleStrCondExactNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 568 for _, v := range values.([]string) { 569 if v == c.expr.value { 570 return false 571 } 572 } 573 return true 574 } 575 576 func (c *ruleStrCondPartialNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 577 for _, v := range values.([]string) { 578 if strings.Contains(v, c.expr.value) { 579 return false 580 } 581 } 582 return true 583 } 584 585 func (c *ruleStrCondPrefixNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 586 for _, v := range values.([]string) { 587 if strings.HasPrefix(v, c.expr.value) { 588 return false 589 } 590 } 591 return true 592 } 593 594 func (c *ruleStrCondSuffixNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 595 for _, v := range values.([]string) { 596 if strings.HasSuffix(v, c.expr.value) { 597 return false 598 } 599 } 600 return true 601 } 602 603 func (c *ruleStrCondRegexNegativeMatchListStrInput) match(ctx context.Context, values interface{}) bool { 604 if c.config.matchAny { 605 for _, v := range values.([]string) { 606 if !c.expr.MatchString(v) { 607 return true 608 } 609 } 610 return false 611 } 612 for _, v := range values.([]string) { 613 if c.expr.MatchString(v) { 614 return false 615 } 616 } 617 return true 618 } 619 620 func (c *ruleListStrCondExactNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 621 for _, exp := range c.exprs { 622 if v.(string) == exp.value { 623 return false 624 } 625 } 626 return true 627 } 628 629 func (c *ruleListStrCondPartialNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 630 for _, exp := range c.exprs { 631 if strings.Contains(v.(string), exp.value) { 632 return false 633 } 634 } 635 return true 636 } 637 638 func (c *ruleListStrCondPrefixNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 639 for _, exp := range c.exprs { 640 if strings.HasPrefix(v.(string), exp.value) { 641 return false 642 } 643 } 644 return true 645 } 646 647 func (c *ruleListStrCondSuffixNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 648 for _, exp := range c.exprs { 649 if strings.HasSuffix(v.(string), exp.value) { 650 return false 651 } 652 } 653 return true 654 } 655 656 func (c *ruleListStrCondRegexNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 657 if c.config.matchAny { 658 for _, exp := range c.exprs { 659 if !exp.MatchString(v.(string)) { 660 return true 661 } 662 } 663 return false 664 } 665 for _, exp := range c.exprs { 666 if exp.MatchString(v.(string)) { 667 return false 668 } 669 } 670 return true 671 } 672 673 func (c *ruleStrCondExactNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 674 if v.(string) == c.expr.value { 675 return false 676 } 677 return true 678 } 679 680 func (c *ruleStrCondPartialNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 681 if strings.Contains(v.(string), c.expr.value) { 682 return false 683 } 684 return true 685 } 686 687 func (c *ruleStrCondPrefixNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 688 if strings.HasPrefix(v.(string), c.expr.value) { 689 return false 690 } 691 return true 692 } 693 694 func (c *ruleStrCondSuffixNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 695 if strings.HasSuffix(v.(string), c.expr.value) { 696 return false 697 } 698 return true 699 } 700 701 func (c *ruleStrCondRegexNegativeMatchStrInput) match(ctx context.Context, v interface{}) bool { 702 if c.expr.MatchString(v.(string)) { 703 return false 704 } 705 return true 706 } 707 708 func (c *ruleListStrCondExactMatchListStrInput) match(ctx context.Context, values interface{}) bool { 709 for _, exp := range c.exprs { 710 for _, v := range values.([]string) { 711 if v == exp.value { 712 return true 713 } 714 } 715 } 716 return false 717 } 718 719 func (c *ruleListStrCondPartialMatchListStrInput) match(ctx context.Context, values interface{}) bool { 720 for _, exp := range c.exprs { 721 for _, v := range values.([]string) { 722 if strings.Contains(v, exp.value) { 723 return true 724 } 725 } 726 } 727 return false 728 } 729 730 func (c *ruleListStrCondPrefixMatchListStrInput) match(ctx context.Context, values interface{}) bool { 731 for _, exp := range c.exprs { 732 for _, v := range values.([]string) { 733 if strings.HasPrefix(v, exp.value) { 734 return true 735 } 736 } 737 } 738 return false 739 } 740 741 func (c *ruleListStrCondSuffixMatchListStrInput) match(ctx context.Context, values interface{}) bool { 742 for _, exp := range c.exprs { 743 for _, v := range values.([]string) { 744 if strings.HasSuffix(v, exp.value) { 745 return true 746 } 747 } 748 } 749 return false 750 } 751 752 func (c *ruleListStrCondRegexMatchListStrInput) match(ctx context.Context, values interface{}) bool { 753 for _, exp := range c.exprs { 754 for _, v := range values.([]string) { 755 if exp.MatchString(v) { 756 return true 757 } 758 } 759 } 760 return false 761 } 762 763 func (c *ruleStrCondExactMatchListStrInput) match(ctx context.Context, values interface{}) bool { 764 for _, v := range values.([]string) { 765 if v == c.expr.value { 766 return true 767 } 768 } 769 return false 770 } 771 772 func (c *ruleStrCondPartialMatchListStrInput) match(ctx context.Context, values interface{}) bool { 773 for _, v := range values.([]string) { 774 if strings.Contains(v, c.expr.value) { 775 return true 776 } 777 } 778 return false 779 } 780 781 func (c *ruleStrCondPrefixMatchListStrInput) match(ctx context.Context, values interface{}) bool { 782 for _, v := range values.([]string) { 783 if strings.HasPrefix(v, c.expr.value) { 784 return true 785 } 786 } 787 return false 788 } 789 790 func (c *ruleStrCondSuffixMatchListStrInput) match(ctx context.Context, values interface{}) bool { 791 for _, v := range values.([]string) { 792 if strings.HasSuffix(v, c.expr.value) { 793 return true 794 } 795 } 796 return false 797 } 798 799 func (c *ruleStrCondRegexMatchListStrInput) match(ctx context.Context, values interface{}) bool { 800 for _, v := range values.([]string) { 801 if c.expr.MatchString(v) { 802 return true 803 } 804 } 805 return false 806 } 807 808 func (c *ruleListStrCondExactMatchStrInput) match(ctx context.Context, v interface{}) bool { 809 for _, exp := range c.exprs { 810 if v.(string) == exp.value { 811 return true 812 } 813 } 814 return false 815 } 816 817 func (c *ruleListStrCondPartialMatchStrInput) match(ctx context.Context, v interface{}) bool { 818 for _, exp := range c.exprs { 819 if strings.Contains(v.(string), exp.value) { 820 return true 821 } 822 } 823 return false 824 } 825 826 func (c *ruleListStrCondPrefixMatchStrInput) match(ctx context.Context, v interface{}) bool { 827 for _, exp := range c.exprs { 828 if strings.HasPrefix(v.(string), exp.value) { 829 return true 830 } 831 } 832 return false 833 } 834 835 func (c *ruleListStrCondSuffixMatchStrInput) match(ctx context.Context, v interface{}) bool { 836 for _, exp := range c.exprs { 837 if strings.HasSuffix(v.(string), exp.value) { 838 return true 839 } 840 } 841 return false 842 } 843 844 func (c *ruleListStrCondRegexMatchStrInput) match(ctx context.Context, v interface{}) bool { 845 for _, exp := range c.exprs { 846 if exp.MatchString(v.(string)) { 847 return true 848 } 849 } 850 return false 851 } 852 853 func (c *ruleStrCondExactMatchStrInput) match(ctx context.Context, v interface{}) bool { 854 if v.(string) == c.expr.value { 855 return true 856 } 857 return false 858 } 859 860 func (c *ruleStrCondPartialMatchStrInput) match(ctx context.Context, v interface{}) bool { 861 if strings.Contains(v.(string), c.expr.value) { 862 return true 863 } 864 return false 865 } 866 867 func (c *ruleStrCondPrefixMatchStrInput) match(ctx context.Context, v interface{}) bool { 868 if strings.HasPrefix(v.(string), c.expr.value) { 869 return true 870 } 871 return false 872 } 873 874 func (c *ruleStrCondSuffixMatchStrInput) match(ctx context.Context, v interface{}) bool { 875 if strings.HasSuffix(v.(string), c.expr.value) { 876 return true 877 } 878 return false 879 } 880 881 func (c *ruleStrCondRegexMatchStrInput) match(ctx context.Context, v interface{}) bool { 882 if c.expr.MatchString(v.(string)) { 883 return true 884 } 885 return false 886 } 887 888 func (c *ruleListStrCondExactNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 889 return c.config 890 } 891 892 func (c *ruleListStrCondPartialNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 893 return c.config 894 } 895 896 func (c *ruleListStrCondPrefixNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 897 return c.config 898 } 899 900 func (c *ruleListStrCondSuffixNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 901 return c.config 902 } 903 904 func (c *ruleListStrCondRegexNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 905 return c.config 906 } 907 908 func (c *ruleStrCondExactNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 909 return c.config 910 } 911 912 func (c *ruleStrCondPartialNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 913 return c.config 914 } 915 916 func (c *ruleStrCondPrefixNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 917 return c.config 918 } 919 920 func (c *ruleStrCondSuffixNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 921 return c.config 922 } 923 924 func (c *ruleStrCondRegexNegativeMatchListStrInput) getConfig(ctx context.Context) *config { 925 return c.config 926 } 927 928 func (c *ruleListStrCondExactNegativeMatchStrInput) getConfig(ctx context.Context) *config { 929 return c.config 930 } 931 932 func (c *ruleListStrCondPartialNegativeMatchStrInput) getConfig(ctx context.Context) *config { 933 return c.config 934 } 935 936 func (c *ruleListStrCondPrefixNegativeMatchStrInput) getConfig(ctx context.Context) *config { 937 return c.config 938 } 939 940 func (c *ruleListStrCondSuffixNegativeMatchStrInput) getConfig(ctx context.Context) *config { 941 return c.config 942 } 943 944 func (c *ruleListStrCondRegexNegativeMatchStrInput) getConfig(ctx context.Context) *config { 945 return c.config 946 } 947 948 func (c *ruleStrCondExactNegativeMatchStrInput) getConfig(ctx context.Context) *config { 949 return c.config 950 } 951 952 func (c *ruleStrCondPartialNegativeMatchStrInput) getConfig(ctx context.Context) *config { 953 return c.config 954 } 955 956 func (c *ruleStrCondPrefixNegativeMatchStrInput) getConfig(ctx context.Context) *config { 957 return c.config 958 } 959 960 func (c *ruleStrCondSuffixNegativeMatchStrInput) getConfig(ctx context.Context) *config { 961 return c.config 962 } 963 964 func (c *ruleStrCondRegexNegativeMatchStrInput) getConfig(ctx context.Context) *config { 965 return c.config 966 } 967 968 func (c *ruleListStrCondExactMatchListStrInput) getConfig(ctx context.Context) *config { 969 return c.config 970 } 971 972 func (c *ruleListStrCondPartialMatchListStrInput) getConfig(ctx context.Context) *config { 973 return c.config 974 } 975 976 func (c *ruleListStrCondPrefixMatchListStrInput) getConfig(ctx context.Context) *config { 977 return c.config 978 } 979 980 func (c *ruleListStrCondSuffixMatchListStrInput) getConfig(ctx context.Context) *config { 981 return c.config 982 } 983 984 func (c *ruleListStrCondRegexMatchListStrInput) getConfig(ctx context.Context) *config { 985 return c.config 986 } 987 988 func (c *ruleStrCondExactMatchListStrInput) getConfig(ctx context.Context) *config { 989 return c.config 990 } 991 992 func (c *ruleStrCondPartialMatchListStrInput) getConfig(ctx context.Context) *config { 993 return c.config 994 } 995 996 func (c *ruleStrCondPrefixMatchListStrInput) getConfig(ctx context.Context) *config { 997 return c.config 998 } 999 1000 func (c *ruleStrCondSuffixMatchListStrInput) getConfig(ctx context.Context) *config { 1001 return c.config 1002 } 1003 1004 func (c *ruleStrCondRegexMatchListStrInput) getConfig(ctx context.Context) *config { 1005 return c.config 1006 } 1007 1008 func (c *ruleListStrCondExactMatchStrInput) getConfig(ctx context.Context) *config { 1009 return c.config 1010 } 1011 1012 func (c *ruleListStrCondPartialMatchStrInput) getConfig(ctx context.Context) *config { 1013 return c.config 1014 } 1015 1016 func (c *ruleListStrCondPrefixMatchStrInput) getConfig(ctx context.Context) *config { 1017 return c.config 1018 } 1019 1020 func (c *ruleListStrCondSuffixMatchStrInput) getConfig(ctx context.Context) *config { 1021 return c.config 1022 } 1023 1024 func (c *ruleListStrCondRegexMatchStrInput) getConfig(ctx context.Context) *config { 1025 return c.config 1026 } 1027 1028 func (c *ruleStrCondExactMatchStrInput) getConfig(ctx context.Context) *config { 1029 return c.config 1030 } 1031 1032 func (c *ruleStrCondPartialMatchStrInput) getConfig(ctx context.Context) *config { 1033 return c.config 1034 } 1035 1036 func (c *ruleStrCondPrefixMatchStrInput) getConfig(ctx context.Context) *config { 1037 return c.config 1038 } 1039 1040 func (c *ruleStrCondSuffixMatchStrInput) getConfig(ctx context.Context) *config { 1041 return c.config 1042 } 1043 1044 func (c *ruleStrCondRegexMatchStrInput) getConfig(ctx context.Context) *config { 1045 return c.config 1046 } 1047 1048 func init() { 1049 matchWithStrategyRgx = regexp.MustCompile(`^\s*((?P<negative_match>no)\s)?((?P<match_strategy>exact|partial|prefix|suffix|regex)\s)?match\s*((?P<match_any>any)\s)?`) 1050 matchFieldRgx = regexp.MustCompile(`^\s*field\s+(?P<field_name>\S+)\s+(?P<field_exists>exists|not\s+exists)\s*$`) 1051 } 1052 1053 func (cfg *config) AsMap() map[string]interface{} { 1054 m := make(map[string]interface{}) 1055 m["field"] = cfg.field 1056 m["match_strategy"] = getMatchStrategyName(cfg.matchStrategy) 1057 if len(cfg.values) > 0 { 1058 m["values"] = cfg.values 1059 } 1060 m["regex_enabled"] = cfg.regexEnabled 1061 m["always_true"] = cfg.alwaysTrue 1062 m["expr_data_type"] = getDataTypeName(cfg.exprDataType) 1063 m["input_data_type"] = getDataTypeName(cfg.inputDataType) 1064 m["condition_type"] = cfg.conditionType 1065 m["match_any"] = cfg.matchAny 1066 return m 1067 } 1068 1069 func extractMatchStrategy(s string) fieldMatchStrategy { 1070 switch s { 1071 case "", "exact": 1072 return fieldMatchExact 1073 case "partial": 1074 return fieldMatchPartial 1075 case "prefix": 1076 return fieldMatchPrefix 1077 case "suffix": 1078 return fieldMatchSuffix 1079 case "regex": 1080 return fieldMatchRegex 1081 case "exists": 1082 return fieldFound 1083 case "not exists": 1084 return fieldNotFound 1085 } 1086 return fieldMatchUnknown 1087 } 1088 1089 func extractFieldNameValues(arr []string) (string, []string) { 1090 var k string 1091 var v []string 1092 var matchFound, fieldFound bool 1093 for i, a := range arr { 1094 if a == "match" { 1095 matchFound = true 1096 continue 1097 } 1098 if !matchFound { 1099 continue 1100 } 1101 if a == "any" && arr[i-1] == "match" { 1102 continue 1103 } 1104 if !fieldFound { 1105 k = a 1106 fieldFound = true 1107 continue 1108 } 1109 v = append(v, a) 1110 } 1111 if fieldFound { 1112 if alias, exists := inputDataAliases[k]; exists { 1113 k = alias 1114 } 1115 } 1116 return k, v 1117 } 1118 1119 func validateFieldNameValues(line, k string, v []string) error { 1120 if k == "" { 1121 return errors.ErrACLRuleConditionSyntaxMatchFieldNotFound.WithArgs(line) 1122 } 1123 if len(v) == 0 { 1124 return errors.ErrACLRuleConditionSyntaxMatchValueNotFound.WithArgs(line) 1125 } 1126 for _, s := range v { 1127 switch s { 1128 case "exact", "partial", "prefix", "suffix", "regex": 1129 return errors.ErrACLRuleConditionSyntaxReservedWordUsage.WithArgs(s, line) 1130 } 1131 } 1132 return nil 1133 } 1134 1135 func extractCondDataType(line string, inputDataType dataType, values []string) (dataType, error) { 1136 switch inputDataType { 1137 case dataTypeListStr, dataTypeStr: 1138 if len(values) == 1 { 1139 return dataTypeStr, nil 1140 } 1141 return dataTypeListStr, nil 1142 case dataTypeAny: 1143 return dataTypeAny, nil 1144 } 1145 return dataTypeUnknown, errors.ErrACLRuleConditionSyntaxCondDataType.WithArgs(line) 1146 } 1147 1148 func extractInputDataType(fieldName string) dataType { 1149 if tp, exists := inputDataTypes[fieldName]; exists { 1150 return tp 1151 } 1152 return dataTypeAny 1153 } 1154 1155 func newACLRuleCondition(ctx context.Context, tokens []string) (aclRuleCondition, error) { 1156 var inputDataType, condDataType dataType 1157 var matchStrategy fieldMatchStrategy 1158 var negativeMatch bool 1159 var fieldName string 1160 var values []string 1161 var matchAny bool 1162 1163 line := strings.Join(tokens, " ") 1164 1165 switch { 1166 case line == "match any": 1167 matchStrategy = fieldMatchAlways 1168 fieldName = "exp" 1169 inputDataType = dataTypeAny 1170 condDataType = dataTypeAny 1171 case matchFieldRgx.Match([]byte(line)): 1172 matched := matchFieldRgx.FindStringSubmatch(line) 1173 for i, k := range matchFieldRgx.SubexpNames() { 1174 if i > 0 && i <= len(matched) { 1175 switch k { 1176 case "field_exists": 1177 matchStrategy = extractMatchStrategy(matched[i]) 1178 case "field_name": 1179 fieldName = matched[i] 1180 if alias, exists := inputDataAliases[fieldName]; exists { 1181 fieldName = alias 1182 } 1183 } 1184 } 1185 } 1186 inputDataType = dataTypeAny 1187 condDataType = dataTypeAny 1188 case matchWithStrategyRgx.Match([]byte(line)): 1189 matched := matchWithStrategyRgx.FindStringSubmatch(line) 1190 for i, k := range matchWithStrategyRgx.SubexpNames() { 1191 if i > 0 && i <= len(matched) { 1192 switch k { 1193 case "match_strategy": 1194 matchStrategy = extractMatchStrategy(matched[i]) 1195 if matchStrategy == fieldMatchUnknown { 1196 matchStrategy = fieldMatchExact 1197 } 1198 case "negative_match": 1199 if matched[i] == "no" { 1200 negativeMatch = true 1201 } 1202 case "match_any": 1203 if matched[i] == "any" { 1204 matchAny = true 1205 } 1206 } 1207 } 1208 } 1209 fieldName, values = extractFieldNameValues(tokens) 1210 default: 1211 return nil, errors.ErrACLRuleConditionSyntaxMatchNotFound.WithArgs(line) 1212 } 1213 1214 if matchStrategy == fieldMatchUnknown { 1215 return nil, errors.ErrACLRuleConditionSyntaxStrategyNotFound.WithArgs(line) 1216 } 1217 1218 switch matchStrategy { 1219 case fieldMatchAlways, fieldFound, fieldNotFound: 1220 default: 1221 if err := validateFieldNameValues(line, fieldName, values); err != nil { 1222 return nil, err 1223 } 1224 inputDataType = extractInputDataType(fieldName) 1225 var err error 1226 condDataType, err = extractCondDataType(line, inputDataType, values) 1227 if err != nil { 1228 return nil, err 1229 } 1230 } 1231 1232 switch { 1233 case matchStrategy == fieldFound: 1234 // Match: Field Found, Condition Type: Any, Input Type: Any 1235 c := &ruleCondFieldFound{ 1236 config: &config{ 1237 field: fieldName, 1238 matchStrategy: fieldFound, 1239 values: values, 1240 regexEnabled: false, 1241 alwaysTrue: false, 1242 exprDataType: inputDataType, 1243 inputDataType: condDataType, 1244 conditionType: `ruleCondFieldFound`, 1245 matchAny: matchAny, 1246 }, 1247 field: &field{ 1248 name: fieldName, 1249 length: len(fieldName), 1250 }, 1251 exprs: []*expr{}, 1252 } 1253 return c, nil 1254 case matchStrategy == fieldNotFound: 1255 // Match: Field Found, Condition Type: Any, Input Type: Any 1256 c := &ruleCondFieldNotFound{ 1257 config: &config{ 1258 field: fieldName, 1259 matchStrategy: fieldNotFound, 1260 values: values, 1261 regexEnabled: false, 1262 alwaysTrue: false, 1263 exprDataType: inputDataType, 1264 inputDataType: condDataType, 1265 conditionType: `ruleCondFieldNotFound`, 1266 matchAny: matchAny, 1267 }, 1268 field: &field{ 1269 name: fieldName, 1270 length: len(fieldName), 1271 }, 1272 exprs: []*expr{}, 1273 } 1274 return c, nil 1275 case matchStrategy == fieldMatchAlways: 1276 // Match: Always, Condition Type: Any, Input Type: Any 1277 c := &ruleAnyCondAlwaysMatchAnyInput{ 1278 config: &config{ 1279 field: fieldName, 1280 matchStrategy: fieldMatchAlways, 1281 values: values, 1282 regexEnabled: false, 1283 alwaysTrue: true, 1284 exprDataType: inputDataType, 1285 inputDataType: condDataType, 1286 conditionType: `ruleAnyCondAlwaysMatchAnyInput`, 1287 matchAny: matchAny, 1288 }, 1289 field: &field{ 1290 name: fieldName, 1291 length: len(fieldName), 1292 }, 1293 exprs: []*expr{}, 1294 } 1295 return c, nil 1296 case negativeMatch && matchStrategy == fieldMatchExact && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1297 // No match: Exact, Condition Type: ListStr, Input Type: ListStr 1298 c := &ruleListStrCondExactNegativeMatchListStrInput{ 1299 config: &config{ 1300 field: fieldName, 1301 matchStrategy: fieldMatchExact, 1302 values: values, 1303 regexEnabled: false, 1304 alwaysTrue: false, 1305 exprDataType: condDataType, 1306 inputDataType: inputDataType, 1307 conditionType: `ruleListStrCondExactNegativeMatchListStrInput`, 1308 matchAny: matchAny, 1309 }, 1310 field: &field{ 1311 name: fieldName, 1312 length: len(fieldName), 1313 }, 1314 } 1315 c.exprs = []*expr{} 1316 for _, val := range values { 1317 c.exprs = append(c.exprs, &expr{ 1318 value: val, 1319 }) 1320 } 1321 return c, nil 1322 case negativeMatch && matchStrategy == fieldMatchPartial && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1323 // No match: Partial, Condition Type: ListStr, Input Type: ListStr 1324 c := &ruleListStrCondPartialNegativeMatchListStrInput{ 1325 config: &config{ 1326 field: fieldName, 1327 matchStrategy: fieldMatchPartial, 1328 values: values, 1329 regexEnabled: false, 1330 alwaysTrue: false, 1331 exprDataType: condDataType, 1332 inputDataType: inputDataType, 1333 conditionType: `ruleListStrCondPartialNegativeMatchListStrInput`, 1334 matchAny: matchAny, 1335 }, 1336 field: &field{ 1337 name: fieldName, 1338 length: len(fieldName), 1339 }, 1340 } 1341 c.exprs = []*expr{} 1342 for _, val := range values { 1343 c.exprs = append(c.exprs, &expr{ 1344 value: val, 1345 }) 1346 } 1347 return c, nil 1348 case negativeMatch && matchStrategy == fieldMatchPrefix && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1349 // No match: Prefix, Condition Type: ListStr, Input Type: ListStr 1350 c := &ruleListStrCondPrefixNegativeMatchListStrInput{ 1351 config: &config{ 1352 field: fieldName, 1353 matchStrategy: fieldMatchPrefix, 1354 values: values, 1355 regexEnabled: false, 1356 alwaysTrue: false, 1357 exprDataType: condDataType, 1358 inputDataType: inputDataType, 1359 conditionType: `ruleListStrCondPrefixNegativeMatchListStrInput`, 1360 matchAny: matchAny, 1361 }, 1362 field: &field{ 1363 name: fieldName, 1364 length: len(fieldName), 1365 }, 1366 } 1367 c.exprs = []*expr{} 1368 for _, val := range values { 1369 c.exprs = append(c.exprs, &expr{ 1370 value: val, 1371 }) 1372 } 1373 return c, nil 1374 case negativeMatch && matchStrategy == fieldMatchSuffix && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1375 // No match: Suffix, Condition Type: ListStr, Input Type: ListStr 1376 c := &ruleListStrCondSuffixNegativeMatchListStrInput{ 1377 config: &config{ 1378 field: fieldName, 1379 matchStrategy: fieldMatchSuffix, 1380 values: values, 1381 regexEnabled: false, 1382 alwaysTrue: false, 1383 exprDataType: condDataType, 1384 inputDataType: inputDataType, 1385 conditionType: `ruleListStrCondSuffixNegativeMatchListStrInput`, 1386 matchAny: matchAny, 1387 }, 1388 field: &field{ 1389 name: fieldName, 1390 length: len(fieldName), 1391 }, 1392 } 1393 c.exprs = []*expr{} 1394 for _, val := range values { 1395 c.exprs = append(c.exprs, &expr{ 1396 value: val, 1397 }) 1398 } 1399 return c, nil 1400 case negativeMatch && matchStrategy == fieldMatchRegex && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1401 // No match: Regex, Condition Type: ListStr, Input Type: ListStr 1402 c := &ruleListStrCondRegexNegativeMatchListStrInput{ 1403 config: &config{ 1404 field: fieldName, 1405 matchStrategy: fieldMatchRegex, 1406 values: values, 1407 regexEnabled: true, 1408 alwaysTrue: false, 1409 exprDataType: condDataType, 1410 inputDataType: inputDataType, 1411 conditionType: `ruleListStrCondRegexNegativeMatchListStrInput`, 1412 matchAny: matchAny, 1413 }, 1414 field: &field{ 1415 name: fieldName, 1416 length: len(fieldName), 1417 }, 1418 } 1419 c.exprs = []*regexp.Regexp{} 1420 for _, val := range values { 1421 re, err := regexp.Compile(val) 1422 if err != nil { 1423 return nil, err 1424 } 1425 c.exprs = append(c.exprs, re) 1426 } 1427 return c, nil 1428 case negativeMatch && matchStrategy == fieldMatchExact && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1429 // No match: Exact, Condition Type: Str, Input Type: ListStr 1430 c := &ruleStrCondExactNegativeMatchListStrInput{ 1431 config: &config{ 1432 field: fieldName, 1433 matchStrategy: fieldMatchExact, 1434 values: values, 1435 regexEnabled: false, 1436 alwaysTrue: false, 1437 exprDataType: condDataType, 1438 inputDataType: inputDataType, 1439 conditionType: `ruleStrCondExactNegativeMatchListStrInput`, 1440 matchAny: matchAny, 1441 }, 1442 field: &field{ 1443 name: fieldName, 1444 length: len(fieldName), 1445 }, 1446 } 1447 c.expr = &expr{ 1448 value: values[0], 1449 } 1450 return c, nil 1451 case negativeMatch && matchStrategy == fieldMatchPartial && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1452 // No match: Partial, Condition Type: Str, Input Type: ListStr 1453 c := &ruleStrCondPartialNegativeMatchListStrInput{ 1454 config: &config{ 1455 field: fieldName, 1456 matchStrategy: fieldMatchPartial, 1457 values: values, 1458 regexEnabled: false, 1459 alwaysTrue: false, 1460 exprDataType: condDataType, 1461 inputDataType: inputDataType, 1462 conditionType: `ruleStrCondPartialNegativeMatchListStrInput`, 1463 matchAny: matchAny, 1464 }, 1465 field: &field{ 1466 name: fieldName, 1467 length: len(fieldName), 1468 }, 1469 } 1470 c.expr = &expr{ 1471 value: values[0], 1472 } 1473 return c, nil 1474 case negativeMatch && matchStrategy == fieldMatchPrefix && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1475 // No match: Prefix, Condition Type: Str, Input Type: ListStr 1476 c := &ruleStrCondPrefixNegativeMatchListStrInput{ 1477 config: &config{ 1478 field: fieldName, 1479 matchStrategy: fieldMatchPrefix, 1480 values: values, 1481 regexEnabled: false, 1482 alwaysTrue: false, 1483 exprDataType: condDataType, 1484 inputDataType: inputDataType, 1485 conditionType: `ruleStrCondPrefixNegativeMatchListStrInput`, 1486 matchAny: matchAny, 1487 }, 1488 field: &field{ 1489 name: fieldName, 1490 length: len(fieldName), 1491 }, 1492 } 1493 c.expr = &expr{ 1494 value: values[0], 1495 } 1496 return c, nil 1497 case negativeMatch && matchStrategy == fieldMatchSuffix && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1498 // No match: Suffix, Condition Type: Str, Input Type: ListStr 1499 c := &ruleStrCondSuffixNegativeMatchListStrInput{ 1500 config: &config{ 1501 field: fieldName, 1502 matchStrategy: fieldMatchSuffix, 1503 values: values, 1504 regexEnabled: false, 1505 alwaysTrue: false, 1506 exprDataType: condDataType, 1507 inputDataType: inputDataType, 1508 conditionType: `ruleStrCondSuffixNegativeMatchListStrInput`, 1509 matchAny: matchAny, 1510 }, 1511 field: &field{ 1512 name: fieldName, 1513 length: len(fieldName), 1514 }, 1515 } 1516 c.expr = &expr{ 1517 value: values[0], 1518 } 1519 return c, nil 1520 case negativeMatch && matchStrategy == fieldMatchRegex && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1521 // No match: Regex, Condition Type: Str, Input Type: ListStr 1522 c := &ruleStrCondRegexNegativeMatchListStrInput{ 1523 config: &config{ 1524 field: fieldName, 1525 matchStrategy: fieldMatchRegex, 1526 values: values, 1527 regexEnabled: true, 1528 alwaysTrue: false, 1529 exprDataType: condDataType, 1530 inputDataType: inputDataType, 1531 conditionType: `ruleStrCondRegexNegativeMatchListStrInput`, 1532 matchAny: matchAny, 1533 }, 1534 field: &field{ 1535 name: fieldName, 1536 length: len(fieldName), 1537 }, 1538 } 1539 re, err := regexp.Compile(values[0]) 1540 if err != nil { 1541 return nil, err 1542 } 1543 c.expr = re 1544 return c, nil 1545 case negativeMatch && matchStrategy == fieldMatchExact && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 1546 // No match: Exact, Condition Type: ListStr, Input Type: Str 1547 c := &ruleListStrCondExactNegativeMatchStrInput{ 1548 config: &config{ 1549 field: fieldName, 1550 matchStrategy: fieldMatchExact, 1551 values: values, 1552 regexEnabled: false, 1553 alwaysTrue: false, 1554 exprDataType: condDataType, 1555 inputDataType: inputDataType, 1556 conditionType: `ruleListStrCondExactNegativeMatchStrInput`, 1557 matchAny: matchAny, 1558 }, 1559 field: &field{ 1560 name: fieldName, 1561 length: len(fieldName), 1562 }, 1563 } 1564 c.exprs = []*expr{} 1565 for _, val := range values { 1566 c.exprs = append(c.exprs, &expr{ 1567 value: val, 1568 }) 1569 } 1570 return c, nil 1571 case negativeMatch && matchStrategy == fieldMatchPartial && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 1572 // No match: Partial, Condition Type: ListStr, Input Type: Str 1573 c := &ruleListStrCondPartialNegativeMatchStrInput{ 1574 config: &config{ 1575 field: fieldName, 1576 matchStrategy: fieldMatchPartial, 1577 values: values, 1578 regexEnabled: false, 1579 alwaysTrue: false, 1580 exprDataType: condDataType, 1581 inputDataType: inputDataType, 1582 conditionType: `ruleListStrCondPartialNegativeMatchStrInput`, 1583 matchAny: matchAny, 1584 }, 1585 field: &field{ 1586 name: fieldName, 1587 length: len(fieldName), 1588 }, 1589 } 1590 c.exprs = []*expr{} 1591 for _, val := range values { 1592 c.exprs = append(c.exprs, &expr{ 1593 value: val, 1594 }) 1595 } 1596 return c, nil 1597 case negativeMatch && matchStrategy == fieldMatchPrefix && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 1598 // No match: Prefix, Condition Type: ListStr, Input Type: Str 1599 c := &ruleListStrCondPrefixNegativeMatchStrInput{ 1600 config: &config{ 1601 field: fieldName, 1602 matchStrategy: fieldMatchPrefix, 1603 values: values, 1604 regexEnabled: false, 1605 alwaysTrue: false, 1606 exprDataType: condDataType, 1607 inputDataType: inputDataType, 1608 conditionType: `ruleListStrCondPrefixNegativeMatchStrInput`, 1609 matchAny: matchAny, 1610 }, 1611 field: &field{ 1612 name: fieldName, 1613 length: len(fieldName), 1614 }, 1615 } 1616 c.exprs = []*expr{} 1617 for _, val := range values { 1618 c.exprs = append(c.exprs, &expr{ 1619 value: val, 1620 }) 1621 } 1622 return c, nil 1623 case negativeMatch && matchStrategy == fieldMatchSuffix && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 1624 // No match: Suffix, Condition Type: ListStr, Input Type: Str 1625 c := &ruleListStrCondSuffixNegativeMatchStrInput{ 1626 config: &config{ 1627 field: fieldName, 1628 matchStrategy: fieldMatchSuffix, 1629 values: values, 1630 regexEnabled: false, 1631 alwaysTrue: false, 1632 exprDataType: condDataType, 1633 inputDataType: inputDataType, 1634 conditionType: `ruleListStrCondSuffixNegativeMatchStrInput`, 1635 matchAny: matchAny, 1636 }, 1637 field: &field{ 1638 name: fieldName, 1639 length: len(fieldName), 1640 }, 1641 } 1642 c.exprs = []*expr{} 1643 for _, val := range values { 1644 c.exprs = append(c.exprs, &expr{ 1645 value: val, 1646 }) 1647 } 1648 return c, nil 1649 case negativeMatch && matchStrategy == fieldMatchRegex && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 1650 // No match: Regex, Condition Type: ListStr, Input Type: Str 1651 c := &ruleListStrCondRegexNegativeMatchStrInput{ 1652 config: &config{ 1653 field: fieldName, 1654 matchStrategy: fieldMatchRegex, 1655 values: values, 1656 regexEnabled: true, 1657 alwaysTrue: false, 1658 exprDataType: condDataType, 1659 inputDataType: inputDataType, 1660 conditionType: `ruleListStrCondRegexNegativeMatchStrInput`, 1661 matchAny: matchAny, 1662 }, 1663 field: &field{ 1664 name: fieldName, 1665 length: len(fieldName), 1666 }, 1667 } 1668 c.exprs = []*regexp.Regexp{} 1669 for _, val := range values { 1670 re, err := regexp.Compile(val) 1671 if err != nil { 1672 return nil, err 1673 } 1674 c.exprs = append(c.exprs, re) 1675 } 1676 return c, nil 1677 case negativeMatch && matchStrategy == fieldMatchExact && condDataType == dataTypeStr && inputDataType == dataTypeStr: 1678 // No match: Exact, Condition Type: Str, Input Type: Str 1679 c := &ruleStrCondExactNegativeMatchStrInput{ 1680 config: &config{ 1681 field: fieldName, 1682 matchStrategy: fieldMatchExact, 1683 values: values, 1684 regexEnabled: false, 1685 alwaysTrue: false, 1686 exprDataType: condDataType, 1687 inputDataType: inputDataType, 1688 conditionType: `ruleStrCondExactNegativeMatchStrInput`, 1689 matchAny: matchAny, 1690 }, 1691 field: &field{ 1692 name: fieldName, 1693 length: len(fieldName), 1694 }, 1695 } 1696 c.expr = &expr{ 1697 value: values[0], 1698 } 1699 return c, nil 1700 case negativeMatch && matchStrategy == fieldMatchPartial && condDataType == dataTypeStr && inputDataType == dataTypeStr: 1701 // No match: Partial, Condition Type: Str, Input Type: Str 1702 c := &ruleStrCondPartialNegativeMatchStrInput{ 1703 config: &config{ 1704 field: fieldName, 1705 matchStrategy: fieldMatchPartial, 1706 values: values, 1707 regexEnabled: false, 1708 alwaysTrue: false, 1709 exprDataType: condDataType, 1710 inputDataType: inputDataType, 1711 conditionType: `ruleStrCondPartialNegativeMatchStrInput`, 1712 matchAny: matchAny, 1713 }, 1714 field: &field{ 1715 name: fieldName, 1716 length: len(fieldName), 1717 }, 1718 } 1719 c.expr = &expr{ 1720 value: values[0], 1721 } 1722 return c, nil 1723 case negativeMatch && matchStrategy == fieldMatchPrefix && condDataType == dataTypeStr && inputDataType == dataTypeStr: 1724 // No match: Prefix, Condition Type: Str, Input Type: Str 1725 c := &ruleStrCondPrefixNegativeMatchStrInput{ 1726 config: &config{ 1727 field: fieldName, 1728 matchStrategy: fieldMatchPrefix, 1729 values: values, 1730 regexEnabled: false, 1731 alwaysTrue: false, 1732 exprDataType: condDataType, 1733 inputDataType: inputDataType, 1734 conditionType: `ruleStrCondPrefixNegativeMatchStrInput`, 1735 matchAny: matchAny, 1736 }, 1737 field: &field{ 1738 name: fieldName, 1739 length: len(fieldName), 1740 }, 1741 } 1742 c.expr = &expr{ 1743 value: values[0], 1744 } 1745 return c, nil 1746 case negativeMatch && matchStrategy == fieldMatchSuffix && condDataType == dataTypeStr && inputDataType == dataTypeStr: 1747 // No match: Suffix, Condition Type: Str, Input Type: Str 1748 c := &ruleStrCondSuffixNegativeMatchStrInput{ 1749 config: &config{ 1750 field: fieldName, 1751 matchStrategy: fieldMatchSuffix, 1752 values: values, 1753 regexEnabled: false, 1754 alwaysTrue: false, 1755 exprDataType: condDataType, 1756 inputDataType: inputDataType, 1757 conditionType: `ruleStrCondSuffixNegativeMatchStrInput`, 1758 matchAny: matchAny, 1759 }, 1760 field: &field{ 1761 name: fieldName, 1762 length: len(fieldName), 1763 }, 1764 } 1765 c.expr = &expr{ 1766 value: values[0], 1767 } 1768 return c, nil 1769 case negativeMatch && matchStrategy == fieldMatchRegex && condDataType == dataTypeStr && inputDataType == dataTypeStr: 1770 // No match: Regex, Condition Type: Str, Input Type: Str 1771 c := &ruleStrCondRegexNegativeMatchStrInput{ 1772 config: &config{ 1773 field: fieldName, 1774 matchStrategy: fieldMatchRegex, 1775 values: values, 1776 regexEnabled: true, 1777 alwaysTrue: false, 1778 exprDataType: condDataType, 1779 inputDataType: inputDataType, 1780 conditionType: `ruleStrCondRegexNegativeMatchStrInput`, 1781 matchAny: matchAny, 1782 }, 1783 field: &field{ 1784 name: fieldName, 1785 length: len(fieldName), 1786 }, 1787 } 1788 re, err := regexp.Compile(values[0]) 1789 if err != nil { 1790 return nil, err 1791 } 1792 c.expr = re 1793 return c, nil 1794 case matchStrategy == fieldMatchExact && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1795 // Match: Exact, Condition Type: ListStr, Input Type: ListStr 1796 c := &ruleListStrCondExactMatchListStrInput{ 1797 config: &config{ 1798 field: fieldName, 1799 matchStrategy: fieldMatchExact, 1800 values: values, 1801 regexEnabled: false, 1802 alwaysTrue: false, 1803 exprDataType: condDataType, 1804 inputDataType: inputDataType, 1805 conditionType: `ruleListStrCondExactMatchListStrInput`, 1806 matchAny: matchAny, 1807 }, 1808 field: &field{ 1809 name: fieldName, 1810 length: len(fieldName), 1811 }, 1812 } 1813 c.exprs = []*expr{} 1814 for _, val := range values { 1815 c.exprs = append(c.exprs, &expr{ 1816 value: val, 1817 }) 1818 } 1819 return c, nil 1820 case matchStrategy == fieldMatchPartial && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1821 // Match: Partial, Condition Type: ListStr, Input Type: ListStr 1822 c := &ruleListStrCondPartialMatchListStrInput{ 1823 config: &config{ 1824 field: fieldName, 1825 matchStrategy: fieldMatchPartial, 1826 values: values, 1827 regexEnabled: false, 1828 alwaysTrue: false, 1829 exprDataType: condDataType, 1830 inputDataType: inputDataType, 1831 conditionType: `ruleListStrCondPartialMatchListStrInput`, 1832 matchAny: matchAny, 1833 }, 1834 field: &field{ 1835 name: fieldName, 1836 length: len(fieldName), 1837 }, 1838 } 1839 c.exprs = []*expr{} 1840 for _, val := range values { 1841 c.exprs = append(c.exprs, &expr{ 1842 value: val, 1843 }) 1844 } 1845 return c, nil 1846 case matchStrategy == fieldMatchPrefix && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1847 // Match: Prefix, Condition Type: ListStr, Input Type: ListStr 1848 c := &ruleListStrCondPrefixMatchListStrInput{ 1849 config: &config{ 1850 field: fieldName, 1851 matchStrategy: fieldMatchPrefix, 1852 values: values, 1853 regexEnabled: false, 1854 alwaysTrue: false, 1855 exprDataType: condDataType, 1856 inputDataType: inputDataType, 1857 conditionType: `ruleListStrCondPrefixMatchListStrInput`, 1858 matchAny: matchAny, 1859 }, 1860 field: &field{ 1861 name: fieldName, 1862 length: len(fieldName), 1863 }, 1864 } 1865 c.exprs = []*expr{} 1866 for _, val := range values { 1867 c.exprs = append(c.exprs, &expr{ 1868 value: val, 1869 }) 1870 } 1871 return c, nil 1872 case matchStrategy == fieldMatchSuffix && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1873 // Match: Suffix, Condition Type: ListStr, Input Type: ListStr 1874 c := &ruleListStrCondSuffixMatchListStrInput{ 1875 config: &config{ 1876 field: fieldName, 1877 matchStrategy: fieldMatchSuffix, 1878 values: values, 1879 regexEnabled: false, 1880 alwaysTrue: false, 1881 exprDataType: condDataType, 1882 inputDataType: inputDataType, 1883 conditionType: `ruleListStrCondSuffixMatchListStrInput`, 1884 matchAny: matchAny, 1885 }, 1886 field: &field{ 1887 name: fieldName, 1888 length: len(fieldName), 1889 }, 1890 } 1891 c.exprs = []*expr{} 1892 for _, val := range values { 1893 c.exprs = append(c.exprs, &expr{ 1894 value: val, 1895 }) 1896 } 1897 return c, nil 1898 case matchStrategy == fieldMatchRegex && condDataType == dataTypeListStr && inputDataType == dataTypeListStr: 1899 // Match: Regex, Condition Type: ListStr, Input Type: ListStr 1900 c := &ruleListStrCondRegexMatchListStrInput{ 1901 config: &config{ 1902 field: fieldName, 1903 matchStrategy: fieldMatchRegex, 1904 values: values, 1905 regexEnabled: true, 1906 alwaysTrue: false, 1907 exprDataType: condDataType, 1908 inputDataType: inputDataType, 1909 conditionType: `ruleListStrCondRegexMatchListStrInput`, 1910 matchAny: matchAny, 1911 }, 1912 field: &field{ 1913 name: fieldName, 1914 length: len(fieldName), 1915 }, 1916 } 1917 c.exprs = []*regexp.Regexp{} 1918 for _, val := range values { 1919 re, err := regexp.Compile(val) 1920 if err != nil { 1921 return nil, err 1922 } 1923 c.exprs = append(c.exprs, re) 1924 } 1925 return c, nil 1926 case matchStrategy == fieldMatchExact && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1927 // Match: Exact, Condition Type: Str, Input Type: ListStr 1928 c := &ruleStrCondExactMatchListStrInput{ 1929 config: &config{ 1930 field: fieldName, 1931 matchStrategy: fieldMatchExact, 1932 values: values, 1933 regexEnabled: false, 1934 alwaysTrue: false, 1935 exprDataType: condDataType, 1936 inputDataType: inputDataType, 1937 conditionType: `ruleStrCondExactMatchListStrInput`, 1938 matchAny: matchAny, 1939 }, 1940 field: &field{ 1941 name: fieldName, 1942 length: len(fieldName), 1943 }, 1944 } 1945 c.expr = &expr{ 1946 value: values[0], 1947 } 1948 return c, nil 1949 case matchStrategy == fieldMatchPartial && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1950 // Match: Partial, Condition Type: Str, Input Type: ListStr 1951 c := &ruleStrCondPartialMatchListStrInput{ 1952 config: &config{ 1953 field: fieldName, 1954 matchStrategy: fieldMatchPartial, 1955 values: values, 1956 regexEnabled: false, 1957 alwaysTrue: false, 1958 exprDataType: condDataType, 1959 inputDataType: inputDataType, 1960 conditionType: `ruleStrCondPartialMatchListStrInput`, 1961 matchAny: matchAny, 1962 }, 1963 field: &field{ 1964 name: fieldName, 1965 length: len(fieldName), 1966 }, 1967 } 1968 c.expr = &expr{ 1969 value: values[0], 1970 } 1971 return c, nil 1972 case matchStrategy == fieldMatchPrefix && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1973 // Match: Prefix, Condition Type: Str, Input Type: ListStr 1974 c := &ruleStrCondPrefixMatchListStrInput{ 1975 config: &config{ 1976 field: fieldName, 1977 matchStrategy: fieldMatchPrefix, 1978 values: values, 1979 regexEnabled: false, 1980 alwaysTrue: false, 1981 exprDataType: condDataType, 1982 inputDataType: inputDataType, 1983 conditionType: `ruleStrCondPrefixMatchListStrInput`, 1984 matchAny: matchAny, 1985 }, 1986 field: &field{ 1987 name: fieldName, 1988 length: len(fieldName), 1989 }, 1990 } 1991 c.expr = &expr{ 1992 value: values[0], 1993 } 1994 return c, nil 1995 case matchStrategy == fieldMatchSuffix && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 1996 // Match: Suffix, Condition Type: Str, Input Type: ListStr 1997 c := &ruleStrCondSuffixMatchListStrInput{ 1998 config: &config{ 1999 field: fieldName, 2000 matchStrategy: fieldMatchSuffix, 2001 values: values, 2002 regexEnabled: false, 2003 alwaysTrue: false, 2004 exprDataType: condDataType, 2005 inputDataType: inputDataType, 2006 conditionType: `ruleStrCondSuffixMatchListStrInput`, 2007 matchAny: matchAny, 2008 }, 2009 field: &field{ 2010 name: fieldName, 2011 length: len(fieldName), 2012 }, 2013 } 2014 c.expr = &expr{ 2015 value: values[0], 2016 } 2017 return c, nil 2018 case matchStrategy == fieldMatchRegex && condDataType == dataTypeStr && inputDataType == dataTypeListStr: 2019 // Match: Regex, Condition Type: Str, Input Type: ListStr 2020 c := &ruleStrCondRegexMatchListStrInput{ 2021 config: &config{ 2022 field: fieldName, 2023 matchStrategy: fieldMatchRegex, 2024 values: values, 2025 regexEnabled: true, 2026 alwaysTrue: false, 2027 exprDataType: condDataType, 2028 inputDataType: inputDataType, 2029 conditionType: `ruleStrCondRegexMatchListStrInput`, 2030 matchAny: matchAny, 2031 }, 2032 field: &field{ 2033 name: fieldName, 2034 length: len(fieldName), 2035 }, 2036 } 2037 re, err := regexp.Compile(values[0]) 2038 if err != nil { 2039 return nil, err 2040 } 2041 c.expr = re 2042 return c, nil 2043 case matchStrategy == fieldMatchExact && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 2044 // Match: Exact, Condition Type: ListStr, Input Type: Str 2045 c := &ruleListStrCondExactMatchStrInput{ 2046 config: &config{ 2047 field: fieldName, 2048 matchStrategy: fieldMatchExact, 2049 values: values, 2050 regexEnabled: false, 2051 alwaysTrue: false, 2052 exprDataType: condDataType, 2053 inputDataType: inputDataType, 2054 conditionType: `ruleListStrCondExactMatchStrInput`, 2055 matchAny: matchAny, 2056 }, 2057 field: &field{ 2058 name: fieldName, 2059 length: len(fieldName), 2060 }, 2061 } 2062 c.exprs = []*expr{} 2063 for _, val := range values { 2064 c.exprs = append(c.exprs, &expr{ 2065 value: val, 2066 }) 2067 } 2068 return c, nil 2069 case matchStrategy == fieldMatchPartial && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 2070 // Match: Partial, Condition Type: ListStr, Input Type: Str 2071 c := &ruleListStrCondPartialMatchStrInput{ 2072 config: &config{ 2073 field: fieldName, 2074 matchStrategy: fieldMatchPartial, 2075 values: values, 2076 regexEnabled: false, 2077 alwaysTrue: false, 2078 exprDataType: condDataType, 2079 inputDataType: inputDataType, 2080 conditionType: `ruleListStrCondPartialMatchStrInput`, 2081 matchAny: matchAny, 2082 }, 2083 field: &field{ 2084 name: fieldName, 2085 length: len(fieldName), 2086 }, 2087 } 2088 c.exprs = []*expr{} 2089 for _, val := range values { 2090 c.exprs = append(c.exprs, &expr{ 2091 value: val, 2092 }) 2093 } 2094 return c, nil 2095 case matchStrategy == fieldMatchPrefix && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 2096 // Match: Prefix, Condition Type: ListStr, Input Type: Str 2097 c := &ruleListStrCondPrefixMatchStrInput{ 2098 config: &config{ 2099 field: fieldName, 2100 matchStrategy: fieldMatchPrefix, 2101 values: values, 2102 regexEnabled: false, 2103 alwaysTrue: false, 2104 exprDataType: condDataType, 2105 inputDataType: inputDataType, 2106 conditionType: `ruleListStrCondPrefixMatchStrInput`, 2107 matchAny: matchAny, 2108 }, 2109 field: &field{ 2110 name: fieldName, 2111 length: len(fieldName), 2112 }, 2113 } 2114 c.exprs = []*expr{} 2115 for _, val := range values { 2116 c.exprs = append(c.exprs, &expr{ 2117 value: val, 2118 }) 2119 } 2120 return c, nil 2121 case matchStrategy == fieldMatchSuffix && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 2122 // Match: Suffix, Condition Type: ListStr, Input Type: Str 2123 c := &ruleListStrCondSuffixMatchStrInput{ 2124 config: &config{ 2125 field: fieldName, 2126 matchStrategy: fieldMatchSuffix, 2127 values: values, 2128 regexEnabled: false, 2129 alwaysTrue: false, 2130 exprDataType: condDataType, 2131 inputDataType: inputDataType, 2132 conditionType: `ruleListStrCondSuffixMatchStrInput`, 2133 matchAny: matchAny, 2134 }, 2135 field: &field{ 2136 name: fieldName, 2137 length: len(fieldName), 2138 }, 2139 } 2140 c.exprs = []*expr{} 2141 for _, val := range values { 2142 c.exprs = append(c.exprs, &expr{ 2143 value: val, 2144 }) 2145 } 2146 return c, nil 2147 case matchStrategy == fieldMatchRegex && condDataType == dataTypeListStr && inputDataType == dataTypeStr: 2148 // Match: Regex, Condition Type: ListStr, Input Type: Str 2149 c := &ruleListStrCondRegexMatchStrInput{ 2150 config: &config{ 2151 field: fieldName, 2152 matchStrategy: fieldMatchRegex, 2153 values: values, 2154 regexEnabled: true, 2155 alwaysTrue: false, 2156 exprDataType: condDataType, 2157 inputDataType: inputDataType, 2158 conditionType: `ruleListStrCondRegexMatchStrInput`, 2159 matchAny: matchAny, 2160 }, 2161 field: &field{ 2162 name: fieldName, 2163 length: len(fieldName), 2164 }, 2165 } 2166 c.exprs = []*regexp.Regexp{} 2167 for _, val := range values { 2168 re, err := regexp.Compile(val) 2169 if err != nil { 2170 return nil, err 2171 } 2172 c.exprs = append(c.exprs, re) 2173 } 2174 return c, nil 2175 case matchStrategy == fieldMatchExact && condDataType == dataTypeStr && inputDataType == dataTypeStr: 2176 // Match: Exact, Condition Type: Str, Input Type: Str 2177 c := &ruleStrCondExactMatchStrInput{ 2178 config: &config{ 2179 field: fieldName, 2180 matchStrategy: fieldMatchExact, 2181 values: values, 2182 regexEnabled: false, 2183 alwaysTrue: false, 2184 exprDataType: condDataType, 2185 inputDataType: inputDataType, 2186 conditionType: `ruleStrCondExactMatchStrInput`, 2187 matchAny: matchAny, 2188 }, 2189 field: &field{ 2190 name: fieldName, 2191 length: len(fieldName), 2192 }, 2193 } 2194 c.expr = &expr{ 2195 value: values[0], 2196 } 2197 return c, nil 2198 case matchStrategy == fieldMatchPartial && condDataType == dataTypeStr && inputDataType == dataTypeStr: 2199 // Match: Partial, Condition Type: Str, Input Type: Str 2200 c := &ruleStrCondPartialMatchStrInput{ 2201 config: &config{ 2202 field: fieldName, 2203 matchStrategy: fieldMatchPartial, 2204 values: values, 2205 regexEnabled: false, 2206 alwaysTrue: false, 2207 exprDataType: condDataType, 2208 inputDataType: inputDataType, 2209 conditionType: `ruleStrCondPartialMatchStrInput`, 2210 matchAny: matchAny, 2211 }, 2212 field: &field{ 2213 name: fieldName, 2214 length: len(fieldName), 2215 }, 2216 } 2217 c.expr = &expr{ 2218 value: values[0], 2219 } 2220 return c, nil 2221 case matchStrategy == fieldMatchPrefix && condDataType == dataTypeStr && inputDataType == dataTypeStr: 2222 // Match: Prefix, Condition Type: Str, Input Type: Str 2223 c := &ruleStrCondPrefixMatchStrInput{ 2224 config: &config{ 2225 field: fieldName, 2226 matchStrategy: fieldMatchPrefix, 2227 values: values, 2228 regexEnabled: false, 2229 alwaysTrue: false, 2230 exprDataType: condDataType, 2231 inputDataType: inputDataType, 2232 conditionType: `ruleStrCondPrefixMatchStrInput`, 2233 matchAny: matchAny, 2234 }, 2235 field: &field{ 2236 name: fieldName, 2237 length: len(fieldName), 2238 }, 2239 } 2240 c.expr = &expr{ 2241 value: values[0], 2242 } 2243 return c, nil 2244 case matchStrategy == fieldMatchSuffix && condDataType == dataTypeStr && inputDataType == dataTypeStr: 2245 // Match: Suffix, Condition Type: Str, Input Type: Str 2246 c := &ruleStrCondSuffixMatchStrInput{ 2247 config: &config{ 2248 field: fieldName, 2249 matchStrategy: fieldMatchSuffix, 2250 values: values, 2251 regexEnabled: false, 2252 alwaysTrue: false, 2253 exprDataType: condDataType, 2254 inputDataType: inputDataType, 2255 conditionType: `ruleStrCondSuffixMatchStrInput`, 2256 matchAny: matchAny, 2257 }, 2258 field: &field{ 2259 name: fieldName, 2260 length: len(fieldName), 2261 }, 2262 } 2263 c.expr = &expr{ 2264 value: values[0], 2265 } 2266 return c, nil 2267 case matchStrategy == fieldMatchRegex && condDataType == dataTypeStr && inputDataType == dataTypeStr: 2268 // Match: Regex, Condition Type: Str, Input Type: Str 2269 c := &ruleStrCondRegexMatchStrInput{ 2270 config: &config{ 2271 field: fieldName, 2272 matchStrategy: fieldMatchRegex, 2273 values: values, 2274 regexEnabled: true, 2275 alwaysTrue: false, 2276 exprDataType: condDataType, 2277 inputDataType: inputDataType, 2278 conditionType: `ruleStrCondRegexMatchStrInput`, 2279 matchAny: matchAny, 2280 }, 2281 field: &field{ 2282 name: fieldName, 2283 length: len(fieldName), 2284 }, 2285 } 2286 re, err := regexp.Compile(values[0]) 2287 if err != nil { 2288 return nil, err 2289 } 2290 c.expr = re 2291 return c, nil 2292 2293 } 2294 return nil, errors.ErrACLRuleConditionSyntaxUnsupported.WithArgs(line) 2295 } 2296 2297 func getMatchStrategyName(s fieldMatchStrategy) string { 2298 switch s { 2299 case fieldMatchExact: 2300 return "fieldMatchExact" 2301 case fieldMatchPartial: 2302 return "fieldMatchPartial" 2303 case fieldMatchPrefix: 2304 return "fieldMatchPrefix" 2305 case fieldMatchSuffix: 2306 return "fieldMatchSuffix" 2307 case fieldMatchRegex: 2308 return "fieldMatchRegex" 2309 case fieldFound: 2310 return "fieldFound" 2311 case fieldNotFound: 2312 return "fieldNotFound" 2313 case fieldMatchAlways: 2314 return "fieldMatchAlways" 2315 case fieldMatchReserved: 2316 return "fieldMatchReserved" 2317 } 2318 return "fieldMatchUnknown" 2319 } 2320 func getDataTypeName(s dataType) string { 2321 switch s { 2322 case dataTypeListStr: 2323 return "dataTypeListStr" 2324 case dataTypeStr: 2325 return "dataTypeStr" 2326 case dataTypeAny: 2327 return "dataTypeAny" 2328 } 2329 return "dataTypeUnknown" 2330 }