Repository: pypi/warehouse

Issue:
Missing long_description sometimes results in "UNKNOWN" project description on Warehouse
Some packages get a nice banner when there's no long_description ([example](https://pypi.org/project/ncep-client/1.0.0/)):

![image](https://user-images.githubusercontent.com/9433472/38142711-5a3520de-3435-11e8-8378-13d54471cf80.png)

but some just get "UNKNOWN" ([example](https://test.pypi.org/project/some/0.2/) on testPyPI):

![image](https://user-images.githubusercontent.com/9433472/38142730-6974c900-3435-11e8-8dbd-076e2e9e75d5.png)

The package with the banner only has an sdist, the one with `UNKNOWN` has both an sdist and a wheel, and the wheel was uploaded first. Both were uploaded within the last couple of days.


Discussion:
Sounds like a bug in the stripping of ``UNKNOWN`` during upload.
https://github.com/pypa/readme_renderer/pull/69 will help with this once it's merged/released.
This looks like a duplicate of (or related to) #69.
@anowlcalledjosh How did you generate the wheel for [this release](https://test.pypi.org/project/some/0.2/#files)? It's a little weird because it contains a description with extra newlines at the end:

```
$ cat some-0.2.dist-info/DESCRIPTION.rst
UNKNOWN


$ cat some-0.2.dist-info/METADATA
Metadata-Version: 2.0
Name: some
Version: 0.2
Summary: UNKNOWN
Home-page: UNKNOWN
Author: UNKNOWN
Author-email: UNKNOWN
License: UNKNOWN
Platform: UNKNOWN

UNKNOWN

```

which is throwing off this check: https://github.com/pypa/warehouse/blob/090c9c9f59941d819092d3f8ca555dc01400b452/warehouse/forklift/legacy.py#L721-L726

@di That particular release was with an almost empty setup.py (and no setup.cfg). I reproduced it with the following package versions:

- pip           9.0.3  
- pkg-resources 0.0.0  
- setuptools    39.0.1 
- wheel         0.31.0

and a setup.py that looks like this:

```python
from setuptools import setup

setup(
    name="some-test",
    version="0.0.1",
)
```

and the command `python setup.py bdist_wheel`.

(With wheel 0.31.0, the DESCRIPTION.rst file is not generated any more, but METADATA still ends with a couple of blank lines.)

If I specify a single-line long_description in setup.py, the generated description still ends with two blank lines; however, giving a longer long_description, for example:

```python
    long_description="""foo bar

    this is a test

    it has multiple lines"""
```

results in only a single trailing blank line:

```
$ cat dist/some_test-0.0.1.dist-info/METADATA
Metadata-Version: 2.0
Name: some-test
Version: 0.0.1
Summary: UNKNOWN
Home-page: UNKNOWN
Author: UNKNOWN
Author-email: UNKNOWN
License: UNKNOWN
Platform: UNKNOWN

foo bar

this is a test

it has multiple lines

```

Resolving patch:
diff --git a/warehouse/forklift/legacy.py b/warehouse/forklift/legacy.py
--- a/warehouse/forklift/legacy.py
+++ b/warehouse/forklift/legacy.py
@@ -722,7 +722,7 @@ def file_upload(request):
     # string "UNKNOWN". This is basically never what anyone actually wants so
     # we'll just go ahead and delete anything whose value is UNKNOWN.
     for key in list(request.POST):
-        if request.POST.get(key) == "UNKNOWN":
+        if str(request.POST.get(key)).strip() == "UNKNOWN":
             del request.POST[key]
 
     # We require protocol_version 1, it's the only supported version however


Test patch:
diff --git a/tests/unit/forklift/test_legacy.py b/tests/unit/forklift/test_legacy.py
--- a/tests/unit/forklift/test_legacy.py
+++ b/tests/unit/forklift/test_legacy.py
@@ -1074,11 +1074,14 @@ def test_upload_fails_without_file(self, pyramid_config, db_request):
         assert resp.status_code == 400
         assert resp.status == "400 Upload payload does not have a file."
 
-    def test_upload_cleans_unknown_values(self, pyramid_config, db_request):
+    @pytest.mark.parametrize("value", [('UNKNOWN'), ('UNKNOWN\n\n')])
+    def test_upload_cleans_unknown_values(
+            self, pyramid_config, db_request, value):
+
         pyramid_config.testing_securitypolicy(userid=1)
         db_request.POST = MultiDict({
             "metadata_version": "1.2",
-            "name": "UNKNOWN",
+            "name": value,
             "version": "1.0",
             "filetype": "sdist",
             "md5_digest": "a fake md5 digest",