MySQL / MariaDB хэширует пароли базы данных для PHP (7.x) mysqli_connect?

Пожалуйста, извините вопрос новичка. Предложения, ссылки и дальнейшее чтение приветствуются.

Я беспокоюсь о безопасности на веб-страницах и ищу лучшие практики.
При использовании PHP для подключения к базам данных MariaDB / MySQL большинство рекомендаций размещают пароли базы данных прямо на странице PHP (или на включенной странице). Это безопасно? Есть ли лучшие «лучшие практики»?

Я искал документы, переполнение стека, а также веб-сайты с такими ключевыми словами, как «хэш-пароли MySQL MariaDB PHP7» и т. Д., Но ответы все о клиентах, которые заходят на веб-страницу, а не о PHP, взаимодействующем напрямую с MariaDB. MySQL Docs говорит, что пароли хешируются для хранения, но это не помогает моему файлу PHP. PHP документы не предоставляйте много полезной информации и реальных примеров.

Итак, мои вопросы:

  1. Насколько высок риск того, что пользователь HTTP загрузит мои исходные файлы и увидит эти пароли? (Я понимаю, что PHP анализирует страницы, поэтому обычный пользователь не увидит необработанный код или не сможет загрузить PHP — и что безопасность ssh, PHP, MariaDB и т. Д. — это отдельный вопрос.)

  2. Я понимаю, что могу хэшировать пароль, но что хорошего в этом, если пароль находится прямо на той же странице? (Или я что-то упустил?)

  3. Лучше / безопаснее поместить переменные базы данных в файл, или использовать
    include("super-sensitive-info.php") и положить переменные
    там? Могу ли я (должен ли я) хэшировать или зашифровать либо этот файл, либо
    пароли, и все же сделать его пригодным для использования? Могу ли я (должен ли я) скрыть этот файл, например, .super-sensitive-info.php), а затем использовать безопасность сервера для ограничения доступа?

  4. И использование специальных символов доставило мне неприятности, например, $password = "pa$$w@rd"; должен выглядеть так $password = "pa\$\$w\@rd";в соответствии с типичной практикой кода в кавычках? Или я пропустил заметку, что я не должен использовать специальные символы для SQL?

Для создания простого примера, скажем, у меня есть два файла, выглядящих примерно так. Есть ли способ лучше? Или это все?

сверхчувствительный-info.php

$user = "username"$password = "password"// $password = "pa\$\$w\@rd"; // (e.g. if database pw is "pa$$w@rd"?
$database_name = "database_name"
// I can hash it, but this seems only useful for client logins and such,
// unless I can hash this entire file....
// $hashed_password = password_hash($password, PASSWORD_DEFAULT);

index.php

include("super-sensitive-info.php")

$db = mysqli_connect('localhost',$user,$password,$database_name)
or die('Error connecting to MySQL server: ' . mysqli_connect_error());

$query = "SELECT * FROM episodes";

0

Решение

Для некоторых из лучших практик взгляните на наиболее часто используемый код фреймворка.

Короче говоря, @ chris85 предложил наиболее важные моменты. И обычно это имеет структуру папок:

config/config.local.php
public/index.php

добавлять config/*.local.php Git игнорировать:

$ echo "config/*.local.php">>.gitignore

В config.php:

return [
'db' => [
'username' => '...',
...
]
];

В index.php:

$config = require '../config.php';
$db = DbConnect($config['db']);
echo json_encode($db->getAllEpisodes());

Служите своей странице из общей папки:

$ php -S localhost:8000 -t ./public/
0

Другие решения

Вы путаете способ, которым аутентифицирующий объект (обычно сервер) проверяет предоставленный ему пароль, и способ, которым объект, который должен подтвердить свои учетные данные (обычно клиент), хранит свой пароль. Сервер, в вашем примере, база данных mysql хранит пароли в виде хэшей — так что, даже если данные утекут, невозможно определить, какой это оригинальный пароль. Важной особенностью является то, что когда клиент желает пройти аутентификацию, он должен представить открытый текст пароля, чтобы сервер мог повторить процесс хеширования. Если пароль был хеширован на клиенте и отправлен на сервер, то проверка будет основываться на точном соответствии между тем, что клиент представил, и тем, что было сохранено на сервере. Хеш открытого текста имеет становиться пароль — это очень небезопасно.

В случае экземпляра PHP / MySQL, да, ваш PHP нуждается в открытом тексте пароля и должен предоставить ему базу данных для аутентификации. Существуют и другие подходы, но обычно они применяются только там, где вы управляете кодом на обоих концах аутентификации. В результате открытый текст пароля может быть более открытым, чем хешированный пароль.

Вы не можете хранить пароль, используемый PHP для подключения к хэш-базе данных.

Прежде чем рассматривать способы защиты открытого текста, вы должны постараться свести к минимуму контексты, в которых он может быть использован. MySQL может аутентифицироваться с использованием сертификатов x509 (и это поддерживается на стороне PHP MySQLi) но на самом деле это просто очень большой пароль. Рекомендуется настроить учетные записи в mysql таким образом, чтобы к ним можно было получить доступ только с определенных адресов (или с локального хоста в случае одного узла PHP / mysql).

GRANT ALL ON yourdb.* TO 'phpuser'@'192.168.0.%';

..но не очень удобно, если вы не контролируете инфраструктуру.

Насколько высок риск для пользователя HTTP скачивать мои исходные файлы?

Это трудно определить количественно, когда вы знать как и кем управляется инфраструктура. Но вы, похоже, игнорируете другие маршруты, по которым данные могут быть отфильтрованы.

Что касается защиты пароля ….

  • Как уже говорили другие, если вы храните пароль в файле, то хорошей идеей будет убедиться, что файл находится за пределами корня документа.

  • Присвоение имени файлу, содержащему пароль с расширением .php, должно означать, что если веб-сервер будет указывать непосредственно на файл, он попытается выполнить его, а не возвращать содержимое http-клиенту. Попытка скрыть файл является безопасностью по неизвестности и, следовательно, не очень хорошая идея, знак-проводки Наличие пароля не является хорошей практикой.

  • в случае Apache (и некоторых других веб-серверов) префикс имени файла с помощью «.ht» обычно не дает веб-серверу напрямую обращаться к нему.

  • Вы можете хранить имя пользователя и пароль MySQL как PHP настройка ini (и, следовательно, также в файлах .htaccess). Для злоумышленника это довольно очевидное место для поиска пароля, но в некоторых случаях может быть уместным.

Шифрование пароля означает, что вам нужно найти безопасное место для хранения ключа шифрования, а не безопасное место для хранения пароля.

я пропустил заметку, что я не должен использовать специальные символы для SQL?

Ваш пароль базы данных обычно не появляется в инструкциях SQL (кроме GRANT...IDENTIFIED BY....). Независимо от того, вы можете использовать специальные символы, если они надлежащим образом экранированы. Но специальные символы не имеют значения для пароля — причина, по которой некоторые системы настаивают на них, заключается в том, что люди выбирают пароли, которые легко угадать. Слово естественного языка имеет примерно половину энтропии на символ по сравнению со случайно сгенерированным паролем с использованием печатных символов из кодировки ASCII — так что случайный пароль из 10 символов столь же надежен, как и пароль из 20 символов, основанный на словах. И компьютеры очень хорошо запоминают большие объемы данных. Рекомендуется использовать случайные пароли в подобных ситуациях.

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

Иногда желательно вообще не хранить пароль в файловой системе — это позволяет избежать риска появления пароля при загрузке в систему контроля версий и в резервные копии. Другие места, где вы можете поместить пароль, находятся в окружении или в общей памяти. У Linux есть хорошая виртуальная возможность HSM с хранилище ключей ядра но запуск в оболочке каждый раз, когда вы хотите получить пароль для подключения к базе данных, довольно неэффективен (AFAIK — нет расширения PHP, связывающего API)

0

Вам не хватает очень важной защиты для PHP: «привязки» или «экранирования» параметров, которые приходят от пользователя (или взломанного URL), а затем помещаются в SQL-запрос.

Читайте о «SQL-инъекции».

0
По вопросам рекламы [email protected]