@@ -103,9 +103,9 @@ def rule_from_pattern(pattern, base_path=None, source=None):
103103 if striptrailingspaces :
104104 pattern = pattern [:i ]
105105 i = i - 1
106- regex = fnmatch_pathname_to_regex (pattern , directory_only , negation )
107- if anchored :
108- regex = '' . join ([ '^' , regex ] )
106+ regex = fnmatch_pathname_to_regex (
107+ pattern , directory_only , negation , anchored = bool ( anchored )
108+ )
109109 return IgnoreRule (
110110 pattern = orig_pattern ,
111111 regex = regex ,
@@ -152,13 +152,15 @@ def match(self, abs_path: Union[str, Path]):
152152
153153# Frustratingly, python's fnmatch doesn't provide the FNM_PATHNAME
154154# option that .gitignore's behavior depends on.
155- def fnmatch_pathname_to_regex (pattern , directory_only : bool , negation : bool ):
155+ def fnmatch_pathname_to_regex (
156+ pattern , directory_only : bool , negation : bool , anchored : bool = False
157+ ):
156158 """
157159 Implements fnmatch style-behavior, as though with FNM_PATHNAME flagged;
158160 the path separator will not match shell-style '*' and '.' wildcards.
159161 """
160162 i , n = 0 , len (pattern )
161-
163+
162164 seps = [re .escape (os .sep )]
163165 if os .altsep is not None :
164166 seps .append (re .escape (os .altsep ))
@@ -205,6 +207,8 @@ def fnmatch_pathname_to_regex(pattern, directory_only: bool, negation: bool):
205207 res .append ('[{}]' .format (stuff ))
206208 else :
207209 res .append (re .escape (c ))
210+ if anchored :
211+ res .insert (0 , '^' )
208212 res .insert (0 , '(?ms)' )
209213 if not directory_only :
210214 res .append ('$' )
0 commit comments