Opened 17 years ago
Closed 4 years ago
#6517 closed Bug (fixed)
MySQL: manage.py dbshell does not get charset from DATABASES setting
Reported by: | Tom Vergote | Owned by: | Manav Agarwal |
---|---|---|---|
Component: | Database layer (models, ORM) | Version: | dev |
Severity: | Normal | Keywords: | |
Cc: | julie@…, victoria@… | Triage Stage: | Ready for checkin |
Has patch: | yes | Needs documentation: | no |
Needs tests: | no | Patch needs improvement: | no |
Easy pickings: | yes | UI/UX: | no |
Description
I noticed that manage.py dbshell doesn't respect the database_options.
I ran into an issue with an application we are creating that needs to support mysql and postgre at least, we execute some sql scripts that get piped to manage.py dbshell (to avoid hardcoding psql -U xxx or mysql -u xxx and creating 2 scripts every time).
When running an utf8 database with utf8 as our charset in database_options, we ran into some weird encoding issues.
The solution for us was to learn mysql/client.py to respect the encoding settings in settings.py
Are you opposed to something like this?
Attaching small patch that fixes our problem. Let me know if it needs extending to support other backends or database_options.
Attachments (1)
Change History (19)
by , 17 years ago
Attachment: | mysql_client.patch added |
---|
comment:1 by , 17 years ago
Has patch: | set |
---|
Also please note that the read_default_file setting is respected, so it's somehow inconsistent behaviour
comment:2 by , 17 years ago
Summary: | manage.py dbshell doesn't respect database_options → manage.py dbshell does not get charset from database_options |
---|
comment:3 by , 17 years ago
Triage Stage: | Unreviewed → Design decision needed |
---|
comment:4 by , 14 years ago
Needs tests: | set |
---|---|
Severity: | → Normal |
Type: | → Bug |
comment:5 by , 13 years ago
Easy pickings: | unset |
---|---|
Triage Stage: | Design decision needed → Accepted |
UI/UX: | unset |
We should look into whether this is needed on other backends as well, not just MySQL.
comment:6 by , 12 years ago
Cc: | added |
---|
I adapted tvrg's patch to the current codebase - https://github.com/jpichon/django/compare/ticket_6517
I also tested dbshell with the sqlite3 and postgresql backends, and it works with UTF-8 characters without patching.
There are other ways to get the MySQL backend to play nicely with UTF-8 that don't require changing the code. You can add "default-character-set = utf8" to /etc/mysql/my.cnf on the server side, or create an option file with the UTF-8 charset config and update the settings to point to it in the "read_default_file" database options (as seen on https://docs.djangoproject.com/en/dev/ref/databases/#connecting-to-the-database)
[client] default-character-set = utf8
If the patch option is preferred, I'm happy to work on the tests if someone could let me know where the dbshell tests live.
comment:7 by , 12 years ago
Triage Stage: | Accepted → Design decision needed |
---|
comment:8 by , 12 years ago
Triage Stage: | Design decision needed → Accepted |
---|
Seems like a good idea to me.
comment:9 by , 9 years ago
Cc: | added |
---|---|
Owner: | changed from | to
Status: | new → assigned |
comment:10 by , 9 years ago
Summary: | manage.py dbshell does not get charset from database_options → MySQL: manage.py dbshell does not get charset from DATABASES setting |
---|
A tests can be added in tests/dbshell/test_mysql.py
.
comment:11 by , 8 years ago
Owner: | removed |
---|---|
Status: | assigned → new |
comment:12 by , 4 years ago
Easy pickings: | set |
---|
comment:13 by , 4 years ago
Owner: | set to |
---|---|
Status: | new → assigned |
comment:14 by , 4 years ago
I wrote a test which is as follows:
def test_charset_configured(self): self.assertEqual( ['mysql', '--user=someuser', '--password=somepassword', '--host=somehost', '--port=444', 'somedbname'], self.get_command_line_arguments({ 'NAME': 'somedbname', 'USER': 'someuser', 'PASSWORD': 'somepassword', 'HOST': 'somehost', 'PORT': 444, 'DEFAULT-CHARACTER-SET': 'utf8', 'OPTIONS': {}, }))
So in the above-mentioned tests, it is working fine when I am not using --default-character-set=utf8 in the list while I am including the same in the dictionary. (The above test is working fine) but IMO it should not work fine as when we are explicitly defining default-character-set to utf8 in the settings file, then it is to be mentioned in the list but as soon as I am adding the same to the list it is raising an error which means it needs a patch and after applying the patch as follows:
charset = settings_dict['OPTIONS'].get('charset',settings_dict['DEFAULT-CHARACTER-SET']) if charset: args += ["--default-character-set=%s" % charset]
The above test is getting failed and the below-mentioned test is getting successfully executed.
def test_charset_configured(self): self.assertEqual( ['mysql', '--user=someuser', '--password=somepassword', '--host=somehost', '--port=444', 'somedbname', '--default-character-set=utf8'], self.get_command_line_arguments({ 'NAME': 'somedbname', 'USER': 'someuser', 'PASSWORD': 'somepassword', 'HOST': 'somehost', 'PORT': 444, 'OPTIONS': {}, 'DEFAULT-CHARACTER-SET': 'utf8', }))
If the patch and the tests seem fine, I may create a PR
comment:16 by , 4 years ago
Patch needs improvement: | set |
---|
comment:17 by , 4 years ago
Patch needs improvement: | unset |
---|---|
Triage Stage: | Accepted → Ready for checkin |
small patch to illustrate suggestion