Repository: joke2k/django-environ

Issue:
Unspecified database properties default to `None` rather than the empty string
Using django-environ v0.4.0 on Python v2.7.10.

**STR:**
```bash
$ DATABASE_URL='mysql://root@localhost/test_db'
$ python
>>> import json
>>> import environ
>>> env = environ.Env()
>>> print(json.dumps(env.db_url('DATABASE_URL'), indent=2))
```
(Travis' MySQL setup has no password, hence the `DATABASE_URL` value above.)

**Expected:**
```json
{
  "ENGINE": "django.db.backends.mysql",
  "NAME": "test_db",
  "HOST": "localhost",
  "USER": "root",
  "PASSWORD": "",
  "PORT": ""
}
```
...or else:
```json
{
  "ENGINE": "django.db.backends.mysql",
  "NAME": "test_db",
  "HOST": "localhost",
  "USER": "root"
}
```
Django has defaults for those properties - which are the empty string: [docs](https://docs.djangoproject.com/en/1.8/ref/settings/#password)

**Actual:**
```json
{
  "ENGINE": "django.db.backends.mysql",
  "NAME": "test_db",
  "HOST": "localhost",
  "USER": "root",
  "PASSWORD": null,
  "PORT": null
}
```


Discussion:

Patch:
diff --git a/environ/environ.py b/environ/environ.py
index ca07f93..601523d 100644
--- a/environ/environ.py
+++ b/environ/environ.py
@@ -330,7 +330,7 @@ class Env(object):
 
         >>> from environ import Env
         >>> Env.db_url_config('sqlite:////full/path/to/your/file.sqlite')
-        {'ENGINE': 'django.db.backends.sqlite3', 'HOST': None, 'NAME': '/full/path/to/your/file.sqlite', 'PASSWORD': None, 'PORT': None, 'USER': None}
+        {'ENGINE': 'django.db.backends.sqlite3', 'HOST': '', 'NAME': '/full/path/to/your/file.sqlite', 'PASSWORD': '', 'PORT': '', 'USER': ''}
         >>> Env.db_url_config('postgres://uf07k1i6d8ia0v:wegauwhgeuioweg@ec2-107-21-253-135.compute-1.amazonaws.com:5431/d8r82722r2kuvn')
         {'ENGINE': 'django.db.backends.postgresql_psycopg2', 'HOST': 'ec2-107-21-253-135.compute-1.amazonaws.com', 'NAME': 'd8r82722r2kuvn', 'PASSWORD': 'wegauwhgeuioweg', 'PORT': 5431, 'USER': 'uf07k1i6d8ia0v'}
 
@@ -364,11 +364,11 @@ class Env(object):
 
         # Update with environment configuration.
         config.update({
-            'NAME': path,
-            'USER': url.username,
-            'PASSWORD': url.password,
-            'HOST': url.hostname,
-            'PORT': _cast_int(url.port),
+            'NAME': path or '',
+            'USER': url.username or '',
+            'PASSWORD': url.password or '',
+            'HOST': url.hostname or '',
+            'PORT': _cast_int(url.port) or '',
         })
 
         if url.query:


Test patch:
diff --git a/environ/test.py b/environ/test.py
index 7f66c34..6761f00 100644
--- a/environ/test.py
+++ b/environ/test.py
@@ -157,7 +157,7 @@ class EnvTests(BaseTests):
         self.assertEqual(mysql_config['HOST'], 'us-cdbr-east.cleardb.com')
         self.assertEqual(mysql_config['USER'], 'bea6eb0')
         self.assertEqual(mysql_config['PASSWORD'], '69772142')
-        self.assertEqual(mysql_config['PORT'], None)
+        self.assertEqual(mysql_config['PORT'], '')
 
         mysql_gis_config = self.env.db('DATABASE_MYSQL_GIS_URL')
         self.assertEqual(mysql_gis_config['ENGINE'], 'django.contrib.gis.db.backends.mysql')
@@ -165,7 +165,7 @@ class EnvTests(BaseTests):
         self.assertEqual(mysql_gis_config['HOST'], '127.0.0.1')
         self.assertEqual(mysql_gis_config['USER'], 'user')
         self.assertEqual(mysql_gis_config['PASSWORD'], 'password')
-        self.assertEqual(mysql_gis_config['PORT'], None)
+        self.assertEqual(mysql_gis_config['PORT'], '')
 
         sqlite_config = self.env.db('DATABASE_SQLITE_URL')
         self.assertEqual(sqlite_config['ENGINE'], 'django.db.backends.sqlite3')
@@ -276,7 +276,18 @@ class DatabaseTestSuite(unittest.TestCase):
         self.assertEqual(url['HOST'], 'us-cdbr-east.cleardb.com')
         self.assertEqual(url['USER'], 'bea6eb025ca0d8')
         self.assertEqual(url['PASSWORD'], '69772142')
-        self.assertEqual(url['PORT'], None)
+        self.assertEqual(url['PORT'], '')
+
+    def test_mysql_no_password(self):
+        url = 'mysql://travis@localhost/test_db'
+        url = Env.db_url_config(url)
+
+        self.assertEqual(url['ENGINE'], 'django.db.backends.mysql')
+        self.assertEqual(url['NAME'], 'test_db')
+        self.assertEqual(url['HOST'], 'localhost')
+        self.assertEqual(url['USER'], 'travis')
+        self.assertEqual(url['PASSWORD'], '')
+        self.assertEqual(url['PORT'], '')
 
     def test_empty_sqlite_url(self):
         url = 'sqlite://'
@@ -309,7 +320,7 @@ class DatabaseTestSuite(unittest.TestCase):
 
         self.assertEqual(url['ENGINE'], 'ldapdb.backends.ldap')
         self.assertEqual(url['HOST'], 'ldap.nodomain.org')
-        self.assertEqual(url['PORT'], None)
+        self.assertEqual(url['PORT'], '')
         self.assertEqual(url['NAME'], 'ldap://ldap.nodomain.org')
         self.assertEqual(url['USER'], 'cn=admin,dc=nodomain,dc=org')
         self.assertEqual(url['PASSWORD'], 'some_secret_password')