github.com/everdrone/grab@v0.1.7-0.20230416223925-40674b995521/internal/utils/regex_test.go (about)

     1  package utils
     2  
     3  import (
     4  	"reflect"
     5  	"regexp"
     6  	"testing"
     7  )
     8  
     9  func TestHasNamedCaptures(t *testing.T) {
    10  	tests := []struct {
    11  		Name      string
    12  		Regex     string
    13  		Want      bool
    14  		WantNames []string
    15  	}{
    16  		{
    17  			Name:      "no named captures",
    18  			Regex:     "^foo\\s+(bar)?(?:baz)$",
    19  			Want:      false,
    20  			WantNames: []string{"", ""},
    21  		},
    22  		{
    23  			Name:      "named captures",
    24  			Regex:     "^(?P<foo>foo)$",
    25  			Want:      true,
    26  			WantNames: []string{"", "foo"},
    27  		},
    28  	}
    29  
    30  	for _, test := range tests {
    31  		t.Run(test.Name, func(t *testing.T) {
    32  			re, err := regexp.Compile(test.Regex)
    33  			if err != nil {
    34  				t.Fatal(err)
    35  			}
    36  			got, gotNames := HasNamedCaptures(re)
    37  
    38  			if got != test.Want {
    39  				t.Errorf("got: %v, want: %v", got, test.Want)
    40  			}
    41  			if !reflect.DeepEqual(gotNames, test.WantNames) {
    42  				t.Errorf("got: %v, want: %v", gotNames, test.WantNames)
    43  			}
    44  		})
    45  	}
    46  }
    47  
    48  /*
    49  // MARK: - With named captures:
    50  		   with find ALL:
    51  
    52  	re := "(?P<first>foo)\s*(?P<second>bar)"
    53  	s := "foo bar foo bar"
    54  	capture := "first"
    55  	matches := [
    56  		["foo bar", "foo", "bar"],
    57  		["foo bar", "foo", "bar"],
    58  	]
    59  	names := ["", "first", "second"]
    60  	output := ["foo", "foo"]
    61  
    62  // MARK: - With named captures:
    63  		   with find ONE:
    64  
    65  	re := "(?P<first>foo)\s*(?P<second>bar)"
    66  	s := "foo bar foo bar"
    67  	capture := "first"
    68  	matches := ["foo bar", "foo", "bar"]
    69  	names := ["", "first", "second"]
    70  	output := ["foo"]
    71  
    72  // MARK: - With capture groups:
    73  		   with find ALL:
    74  
    75  	re := "(foo)\s*(bar)"
    76  	s := "foo bar foo bar"
    77  	capture := 1
    78  	matches := [
    79  		["foo bar", "foo", "bar"],
    80  		["foo bar", "foo", "bar"],
    81  	]
    82  	names := ["", "", ""]
    83  	output := ["foo", "foo"]
    84  
    85  // MARK: - With capture groups:
    86  		   with find ONE:
    87  
    88  	re := "(foo)\s*(bar)"
    89  	s := "foo bar foo bar"
    90  	capture := 1
    91  	matches := ["foo bar", "foo", "bar"]
    92  	names := ["", "", ""]
    93  	output := ["foo"]
    94  */
    95  
    96  func TestGetCaptures(t *testing.T) {
    97  	tests := []struct {
    98  		Name    string
    99  		Regex   string
   100  		FindAll bool
   101  		String  string
   102  		Capture string
   103  		Want    []string
   104  		WantErr string
   105  	}{
   106  		{
   107  			Name:    "all with no named captures",
   108  			Regex:   "(foo\\d)\\s*(bar)",
   109  			FindAll: true,
   110  			Capture: "1",
   111  			String:  "foo1 bar foo2 bar",
   112  			Want:    []string{"foo1", "foo2"},
   113  			WantErr: "",
   114  		},
   115  		{
   116  			Name:    "one no named captures",
   117  			Regex:   "(foo\\d)\\s*(bar)",
   118  			FindAll: false,
   119  			Capture: "1",
   120  			String:  "foo1 bar foo2 bar",
   121  			Want:    []string{"foo1"},
   122  			WantErr: "",
   123  		},
   124  		{
   125  			Name:    "all with named captures",
   126  			Regex:   "(?P<first>foo\\d)\\s*(?P<second>bar)",
   127  			FindAll: true,
   128  			Capture: "first",
   129  			String:  "foo1 bar foo2 bar",
   130  			Want:    []string{"foo1", "foo2"},
   131  			WantErr: "",
   132  		},
   133  		{
   134  			Name:    "one no named captures",
   135  			Regex:   "(?P<first>foo\\d)\\s*(?P<second>bar)",
   136  			FindAll: false,
   137  			Capture: "first",
   138  			String:  "foo1 bar foo2 bar",
   139  			Want:    []string{"foo1"},
   140  			WantErr: "",
   141  		},
   142  
   143  		// MARK: - Failing tests
   144  
   145  		{
   146  			Name:    "named with number capture input",
   147  			Regex:   "(?P<first>foo\\d)\\s*(?P<second>bar)",
   148  			FindAll: false,
   149  			Capture: "0",
   150  			String:  "foo1 bar foo2 bar",
   151  			Want:    nil,
   152  			WantErr: "capture `0` not found in expression `(?P<first>foo\\d)\\s*(?P<second>bar)`",
   153  		},
   154  		{
   155  			Name:    "named with existing number capture input",
   156  			Regex:   "(?P<first>foo\\d)\\s*(?P<second>bar)",
   157  			FindAll: false,
   158  			Capture: "1",
   159  			String:  "foo1 bar foo2 bar",
   160  			Want:    nil,
   161  			WantErr: "capture `1` not found in expression `(?P<first>foo\\d)\\s*(?P<second>bar)`",
   162  		},
   163  		{
   164  			Name:    "named when using non-named captures",
   165  			Regex:   "(foo\\d)\\s*(bar)",
   166  			FindAll: false,
   167  			Capture: "first",
   168  			String:  "foo1 bar foo2 bar",
   169  			Want:    nil,
   170  			WantErr: "capture group `first` is not a number",
   171  		},
   172  		{
   173  			Name:    "no captures",
   174  			Regex:   "(foo\\d)\\s*(bar)",
   175  			FindAll: false,
   176  			Capture: "1",
   177  			String:  "baz qux",
   178  			Want:    nil,
   179  			WantErr: "no captures found for pattern `(foo\\d)\\s*(bar)`, capture `1`",
   180  		},
   181  		{
   182  			Name:    "no captures with find all",
   183  			Regex:   "(foo\\d)\\s*(bar)",
   184  			FindAll: true,
   185  			Capture: "1",
   186  			String:  "baz qux bez qux",
   187  			Want:    nil,
   188  			WantErr: "no captures found for pattern `(foo\\d)\\s*(bar)`, capture `1`",
   189  		},
   190  	}
   191  
   192  	for _, tt := range tests {
   193  		t.Run(tt.Name, func(t *testing.T) {
   194  			re, err := regexp.Compile(tt.Regex)
   195  			if err != nil {
   196  				t.Fatal(err)
   197  			}
   198  
   199  			got, err := GetCaptures(re, tt.FindAll, tt.Capture, tt.String)
   200  			if err != nil && tt.WantErr == "" {
   201  				t.Errorf("got: %v, want no error", err)
   202  			}
   203  
   204  			if err == nil && tt.WantErr != "" {
   205  				t.Errorf("got no error, want: %v", tt.WantErr)
   206  			}
   207  
   208  			if err != nil && tt.WantErr != "" {
   209  				if err.Error() != tt.WantErr {
   210  					t.Errorf("got: %v, want: %v", err, tt.WantErr)
   211  				}
   212  			}
   213  
   214  			if !reflect.DeepEqual(got, tt.Want) {
   215  				t.Errorf("got: %#v, want: %#v", got, tt.Want)
   216  			}
   217  		})
   218  	}
   219  }