Subject: bug#24450: [PATCHv2] Re: pypi importer outputs strange character series in optional dependency case.

From: Ricardo Wurmus <[email-masked]>
Date: Tue, 11 Jun 2019 13:56:46 +0200

Hi Maxim,

>>> +  (call-with-input-file metadata
>>> +    (lambda (port)
>>> +      (let loop ((requirements '()))
>>> +        (let ((line (read-line port)))
>>> +          ;; Stop at the first 'Provides-Extra' section: the non-optional
>>> +          ;; requirements appear before the optional ones.
>>> +          (if (eof-object? line)
>>> +              (reverse (delete-duplicates requirements))
>>> +              (cond
>>> +               ((and (requires-dist-header? line) (not (extra? line)))
>>> +                (loop (cons (specification->requirement-name
>>> +                             (requires-dist-value line))
>>> +                            requirements)))
>>> +               (else
>>> +                (loop requirements)))))))))
>>> +
>>
>> As before you can simplify the nested let and merge “if” and "cond“.
>
> Oh, I get it now, I think:
>
> --8<---------------cut here---------------start------------->8---
>
>    (call-with-input-file metadata
>      (lambda (port)
>        (let loop ((requirements '()))
> -        (let ((line (read-line port)))
> -          ;; Stop at the first 'Provides-Extra' section: the non-optional
> -          ;; requirements appear before the optional ones.
> -          (if (eof-object? line)
> -              (reverse (delete-duplicates requirements))
> -              (cond
> -               ((and (requires-dist-header? line) (not (extra? line)))
> -                (loop (cons (specification->requirement-name
> -                             (requires-dist-value line))
> -                            requirements)))
> -               (else
> -                (loop requirements)))))))))
> +        (match (read-line port)
> +          (line
> +           ;; Stop at the first 'Provides-Extra' section: the non-optional
> +           ;; requirements appear before the optional ones.
> +           (cond
> +            ((eof-object? line)
> +             (reverse (delete-duplicates requirements)))
> +            ((and (requires-dist-header? line) (not (extra? line)))
> +             (loop (cons (specification->requirement-name
> +                          (requires-dist-value line))
> +                         requirements)))
> +            (else
> +             (loop requirements)))))))))
>
>  (define (guess-requirements source-url wheel-url archive)
>    "Given SOURCE-URL, WHEEL-URL and a ARCHIVE of the package, return a list
> --8<---------------cut here---------------end--------------->8---

Not quite.  Your ‘match’ expression here doesn’t do anything that a
‘let’ wouldn’t have done.  It really just binds the return value of
(read-line port) to ‘line’; that’s the same as (let ((line (read-line
port))) …).

I gave a match example using predicate matchers in a previous reply.  In
any case, using ‘cond’ inside of a let would be just fine.  If you
wanted to go with ‘match’, though, you’d replace the ‘cond’.

--
Ricardo