storj.io/minio@v0.0.0-20230509071714-0cbc90f649b1/pkg/wildcard/match.go (about)

     1  /*
     2   * MinIO Cloud Storage, (C) 2015, 2016 MinIO, Inc.
     3   *
     4   * Licensed under the Apache License, Version 2.0 (the "License");
     5   * you may not use this file except in compliance with the License.
     6   * You may obtain a copy of the License at
     7   *
     8   *     http://www.apache.org/licenses/LICENSE-2.0
     9   *
    10   * Unless required by applicable law or agreed to in writing, software
    11   * distributed under the License is distributed on an "AS IS" BASIS,
    12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13   * See the License for the specific language governing permissions and
    14   * limitations under the License.
    15   */
    16  
    17  package wildcard
    18  
    19  // MatchSimple - finds whether the text matches/satisfies the pattern string.
    20  // supports only '*' wildcard in the pattern.
    21  // considers a file system path as a flat name space.
    22  func MatchSimple(pattern, name string) bool {
    23  	if pattern == "" {
    24  		return name == pattern
    25  	}
    26  	if pattern == "*" {
    27  		return true
    28  	}
    29  	// Does only wildcard '*' match.
    30  	return deepMatchRune([]rune(name), []rune(pattern), true)
    31  }
    32  
    33  // Match -  finds whether the text matches/satisfies the pattern string.
    34  // supports  '*' and '?' wildcards in the pattern string.
    35  // unlike path.Match(), considers a path as a flat name space while matching the pattern.
    36  // The difference is illustrated in the example here https://play.golang.org/p/Ega9qgD4Qz .
    37  func Match(pattern, name string) (matched bool) {
    38  	if pattern == "" {
    39  		return name == pattern
    40  	}
    41  	if pattern == "*" {
    42  		return true
    43  	}
    44  	// Does extended wildcard '*' and '?' match.
    45  	return deepMatchRune([]rune(name), []rune(pattern), false)
    46  }
    47  
    48  func deepMatchRune(str, pattern []rune, simple bool) bool {
    49  	for len(pattern) > 0 {
    50  		switch pattern[0] {
    51  		default:
    52  			if len(str) == 0 || str[0] != pattern[0] {
    53  				return false
    54  			}
    55  		case '?':
    56  			if len(str) == 0 && !simple {
    57  				return false
    58  			}
    59  		case '*':
    60  			return deepMatchRune(str, pattern[1:], simple) ||
    61  				(len(str) > 0 && deepMatchRune(str[1:], pattern, simple))
    62  		}
    63  		str = str[1:]
    64  		pattern = pattern[1:]
    65  	}
    66  	return len(str) == 0 && len(pattern) == 0
    67  }