fork of go-gitdiff with jj support

Slightly simplify patch header parsing (#34)

Use standard string functions instead of removing leading whitespace in
a custom loop. This also makes the distinction between the two types of
mail header parsing a bit clearer.

authored by Billy Keyes and committed by GitHub dc43dbf8 071689e9

Changed files
+31 -27
gitdiff
+27 -27
gitdiff/patch_header.go
··· 190 190 // prefix and appendix material should use `PatchHeader.SubjectPrefix 191 191 // + PatchHeader.Title + "\n" + PatchHeader.Body + "\n" + 192 192 // PatchHeader.BodyAppendix`. 193 - func ParsePatchHeader(s string) (*PatchHeader, error) { 194 - r := bufio.NewReader(strings.NewReader(s)) 193 + func ParsePatchHeader(header string) (*PatchHeader, error) { 194 + header = strings.TrimSpace(header) 195 195 196 - var line string 197 - for { 198 - var err error 199 - line, err = r.ReadString('\n') 200 - if err == io.EOF { 201 - break 202 - } 203 - if err != nil { 204 - return nil, err 205 - } 196 + if header == "" { 197 + return &PatchHeader{}, nil 198 + } 206 199 207 - line = strings.TrimSpace(line) 208 - if len(line) > 0 { 209 - break 210 - } 200 + var firstLine, rest string 201 + if idx := strings.IndexByte(header, '\n'); idx >= 0 { 202 + firstLine = header[:idx] 203 + rest = header[idx+1:] 204 + } else { 205 + firstLine = header 206 + rest = "" 211 207 } 212 208 213 209 switch { 214 - case strings.HasPrefix(line, mailHeaderPrefix): 215 - return parseHeaderMail(line, r) 216 - case strings.HasPrefix(line, mailMinimumHeaderPrefix): 217 - r = bufio.NewReader(strings.NewReader(s)) 218 - return parseHeaderMail("", r) 219 - case strings.HasPrefix(line, prettyHeaderPrefix): 220 - return parseHeaderPretty(line, r) 210 + case strings.HasPrefix(firstLine, mailHeaderPrefix): 211 + return parseHeaderMail(firstLine, strings.NewReader(rest)) 212 + 213 + case strings.HasPrefix(firstLine, mailMinimumHeaderPrefix): 214 + // With a minimum header, the first line is part of the actual mail 215 + // content and needs to be parsed as part of the "rest" 216 + return parseHeaderMail("", strings.NewReader(header)) 217 + 218 + case strings.HasPrefix(firstLine, prettyHeaderPrefix): 219 + return parseHeaderPretty(firstLine, strings.NewReader(rest)) 221 220 } 221 + 222 222 return nil, errors.New("unrecognized patch header format") 223 223 } 224 224 ··· 233 233 234 234 h := &PatchHeader{} 235 235 236 - prettyLine = prettyLine[len(prettyHeaderPrefix):] 236 + prettyLine = strings.TrimPrefix(prettyLine, prettyHeaderPrefix) 237 237 if i := strings.IndexByte(prettyLine, ' '); i > 0 { 238 238 h.SHA = prettyLine[:i] 239 239 } else { ··· 297 297 h.Title = title 298 298 299 299 if title != "" { 300 - // Don't check for an appendix 300 + // Don't check for an appendix, pretty headers do not contain them 301 301 body, _ := scanMessageBody(s, indent, false) 302 302 if s.Err() != nil { 303 303 return nil, s.Err() ··· 374 374 375 375 h := &PatchHeader{} 376 376 377 - if len(mailLine) > len(mailHeaderPrefix) { 378 - mailLine = mailLine[len(mailHeaderPrefix):] 377 + if strings.HasPrefix(mailLine, mailHeaderPrefix) { 378 + mailLine = strings.TrimPrefix(mailLine, mailHeaderPrefix) 379 379 if i := strings.IndexByte(mailLine, ' '); i > 0 { 380 380 h.SHA = mailLine[:i] 381 381 }
+4
gitdiff/patch_header_test.go
··· 414 414 Title: expectedTitle, 415 415 }, 416 416 }, 417 + "empty": { 418 + Input: "", 419 + Header: PatchHeader{}, 420 + }, 417 421 } 418 422 419 423 for name, test := range tests {