Skip to content

Commit 88969d7

Browse files
Do not report a doubled quote across field boundaries
The pattern required a doubled quote character in the middle, so it could match from a delimiter inside one quoted field to a quote in another one, and reported a double quoted format for '",","",","'. Match whole quoted fields instead and test their bodies for a doubled quote separately. Only look behind the delimiter, because the trailing one is consumed, so that consecutive fields are all matched.
1 parent 92b3133 commit 88969d7

1 file changed

Lines changed: 8 additions & 11 deletions

File tree

Lib/csv.py

Lines changed: 8 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -328,20 +328,17 @@ def _guess_quote_and_delimiter(self, data, delimiters):
328328
delim = ''
329329
skipinitialspace = 0
330330

331-
# if we see an extra quote between delimiters, we've got a
332-
# double quoted format
331+
# A doubled quote character inside a quoted field means
332+
# a double quoted format. Match whole fields, so that a match
333+
# cannot slide across field boundaries.
333334
dq_regexp = re.compile(
334-
r"(?:%(delim)s|^) *+%(quote)s" # ,"
335-
r"[^%(quote)s]*+%(quote)s%(quote)s" # the doubled quote
336-
r"(?:%(quote)s%(quote)s|[^%(quote)s]++)*+" # the rest of the field
337-
r"%(quote)s(?:%(delim)s|$)" # ",
335+
r"(?:(?<=%(delim)s)|^) *+%(quote)s" # ,"
336+
r"((?:%(quote)s%(quote)s|[^%(quote)s]++)*+)" # the body
337+
r"%(quote)s(?:%(delim)s|$)" # ",
338338
% {'delim': re.escape(delim), 'quote': quotechar},
339339
re.MULTILINE)
340-
341-
if dq_regexp.search(data):
342-
doublequote = True
343-
else:
344-
doublequote = False
340+
dquotechar = quotechar * 2
341+
doublequote = any(dquotechar in m[1] for m in dq_regexp.finditer(data))
345342

346343
return (quotechar, doublequote, delim, skipinitialspace)
347344

0 commit comments

Comments
 (0)