it-roy-ru.com

подключиться к БД с помощью psycopg2 без пароля

У меня есть локальная база данных postgres, к которой я могу получить доступ без пароля

$ psql -d mwt
psql (8.4.12)
Type "help" for help.

mwt=# SELECT * from vatid;
  id   | requester_vatid |...
  -----+-----------------|...   
  1719 | IT00766780266   |...

Я хочу получить доступ к этой базе данных из Django. Поэтому я положил в DATABASES

DATABASES = {
    'default': {
        'ENGINE': 'Django.db.backends.postgresql_psycopg2',
        'NAME': 'mwt',
        'USER': 'shaoran',
        'Host': 'localhost'
    }
}

Так как мне не нужен пароль для доступа к моей тестовой базе данных, я не указал значение PASSWORD в настройках.

$ ./manage.py Shell
>>> from polls.models import Vatid
>>> Vatid.objects.all()
  connection_factory=connection_factory, async=async)
  OperationalError: fe_sendauth: no password supplied

Я пытался использовать PASSWORD: '', но получаю то же сообщение об ошибке. Я пытался использовать PASSWORD: None, но это тоже не помогло.

Я искал документацию по Django по этому поводу, но не могу найти ничего полезного. Можно ли настроить Django.db.backends.postgresql_psycopg2 для принятия пустого пароля?

40
Pablo

Проверьте свой pg_hba.conf, чтобы разрешить подключение от localhost пользователем shaoran, затем либо введите пароль shaoran в настройках Django, либо доверяйте пользователю pg_hba.conf

Тот факт, что вы можете подключиться через psql, заключается в том, что psql -d mwt использует некоторые значения подключения по умолчанию, которые установлены как надежные в pg_hba.conf. Например, на моей машине хост по умолчанию - local socket вместо localhost

12
okm

Удивительно, но ответ - вообще не указывать хост. Если вы сделаете это,

DATABASES = {
    'default': {
        'ENGINE': 'Django.db.backends.postgresql_psycopg2',
        'NAME': 'mwt',
    }
}

Затем psycopg2 подключится через сокет Unix таким же образом, как psql. Когда вы указываете Host, psycopg2 будет соединяться с TCP/IP, который требует пароль.

57
joerick

Чтобы избежать использования пароля в Django settings.py, измените md5 на trust в этой строке pg_hba.conf:

Host    all             all             127.0.0.1/32            trust

Для подробного понимания конфигураций безопасности postgres прочитайте этот документ.

Чтобы найти этот файл:

Sudo -u postgres psql -c 'SHOW hba_file;'
24
b_dev

Поскольку кто-то сталкивается с той же проблемой и находит решение только после объединения различных частей из приведенных здесь ответов и других результатов испытаний Google, я решил составить, надеюсь, полный ответ:

Первое, что нужно отметить:

И внесение 'Host' или опускание его в settings.py являются жизнеспособными вариантами. Однако то, что вы указали 'Host' или нет, влияет на настройку конфигурации postgresql.

Пропуск 'Host' как в ответ Джоерика приводит к тому, что psycopg2 пытается соединиться через доменный сокет Unix. С другой стороны, если ваша конфигурация содержит ключ 'Host', psycopg2 попытается подключиться через IPv4/6 localhost. Это имеет большое значение, так как конфигурация аутентификации postgresql (/etc/postgresql/x.x/main/pg_hba.conf) специфична для любого из этих способов подключения.

Взять домой сообщение: 

Обязательно выберите тип подключения, который вы также настроили в своей конфигурации аутентификации postgresql.

Второе, на что следует обратить внимание:

Конфигурация аутентификации postgresql (/etc/postgresql/x.x/main/pg_hba.conf) заботится о порядке записей.

Документы на самом деле очень ясно об этом, (все же мне удалось попасть в ловушку local all all peer):

Запись first с соответствующим типом соединения, адресом клиента, запрошенной базой данных и именем пользователя используется для выполнения аутентификации. Не существует «резервных» или «резервных копий»: если выбрана одна запись и аутентификация не пройдена, последующие записи не рассматриваются. Если не найдено ни одной записи, доступ запрещен.

Взять домой сообщение: 

Убедитесь, что любое конкретное правило имеет ДО ДО более широких правил.


Теперь, когда мы знаем все это, вот как получить доступ без пароля, один раз с 'Host' (так через localhost) и один раз без (так через сокет Unix).


Соединение через localhost

Укажите 'Host': 'localhost' в конфигурации базы данных вашего settings.py:

# ...
'Host': 'localhost',
# ...

'PASSWORD' не нужен и может быть опущен.

Правило, которое вам нужно установить в конфигурации аутентификации postgresql (/etc/postgresql/x.x/main/pg_hba.conf), относится к TYPE Host

Следите за порядком правил. Таким образом, если у вас есть пользователь my_user, который должен иметь доступ к базе данных my_database без пароля, правильная конфигурация будет выглядеть следующим образом:

# RIGHT WAY...
Host my_database my_user 127.0.0.1/32 trust
Host my_database my_user ::1/128 trust
# ...
Host all all 127.0.0.1/32 peer
# ...

Инвертирование порядка приведет к ошибке no password supplied.


Подключение через доменный сокет Unix

Не вставляйте ключ 'Host' в свои настройки .'PASSWORD' тоже не нужен.

В конфигурации аутентификации postgresql доступ через доменные сокеты Unix управляется с помощью правил TYPE local.

Если «my_user» должен получить доверенный (пароль не требуется) доступ к базе данных «my_database», вам нужна строка, подобная этой:

local my_database my_user trust

Относительно того, где поместить эту строку, правило здесь состоит в том, что вам нужно поместить ее перед любым правилом более широким в терминах DATABASE и USER. Чтобы быть в безопасности, я рекомендую поместить его в начало/etc/postgresql/x.x/main/pg_hba.conf. Если ваш файл pg_hba.conf выглядит так:

# RIGHT WAY...
local my_database my_user trust
# ...
local all all peer
# ...

тебе хорошо идти без пароля. Однако, если это выглядит так: 

# WRONG WAY! ...
local all all peer
# ...
local my_database my_user trust
# ...

вам нужно будет предоставить пароль.


Конечная нота: 

Не забудьте перезапустить службу postgresql после изменения /etc/postgresql/x.x/pg_hba.conf:

Sudo service postgresql restart

Надеюсь, это было полезно. Удачного кодирования!

3
jojo

Я живу только с 'local all all peer'. Строка соединения должна быть без Хоста, пользователя и пароля: postgres: /// mydbname.

Без окружения модуль выглядит так:

DATABASES = {
    'default': {'NAME': 'mydatabase', 'USER': '', 'PASSWORD': '', 'Host': '', 'PORT': '', 'ENGINE': 'Django.db.backends.postgresql_psycopg2'}
}

С модулем окружения:

import environ
env = environ.Env()
DATABASES = {
    'default': env.db('DATABASE_URL', default='postgres:///mydatabase'),
}

где файл .env не содержит настройки DATABASE_URL.

Только для пользователя 'postgres' я использую md5, но только из psql/pgadmin3, а не из кода Django.

# /etc/postgresql/version/cluster/pg_hba.conf:
local all postgres md5
local all all peer
0
mirek