Zabezpečení je jedním z nejdůležitějších prvků správně navrženého databázového prostředí. Existuje mnoho používaných útočných vektorů, přičemž SQL injection je pravděpodobně nejoblíbenější. Můžete navrhnout vrstvy obrany v kódu aplikace, ale co můžete dělat na vrstvě databáze? Dnes bychom vám rádi ukázali, jak snadno můžete implementovat SQL firewall nad MySQL pomocí ProxySQL. V druhé části tohoto blogu vysvětlíme, jak můžete vytvořit seznam povolených dotazů, které mají povolen přístup k databázi.
Nejprve chceme nasadit ProxySQL. Nejjednodušší způsob, jak to udělat, je použít ClusterControl. Pomocí několika kliknutí jej můžete nasadit do svého clusteru.
Definujte, kam jej nasadit, můžete buď vybrat stávajícího hostitele v clusteru nebo si zapište libovolnou IP nebo název hostitele. Nastavte přihlašovací údaje pro správce a monitorovací uživatele.
Poté můžete v databázi vytvořit nového uživatele pro použití s ProxySQL nebo můžete importovat jeden ze stávajících. Musíte také definovat databázové uzly, které chcete zahrnout do ProxySQL. Odpovězte, zda používáte implicitní transakce nebo ne a jste připraveni nasadit ProxySQL. Za několik minut je ProxySQL s konfigurací připravenou na základě vašeho vstupu připraven k použití.
Vzhledem k tomu, že naším problémem je zabezpečení, chceme být schopni sdělit ProxySQL, jak zacházet s nevhodnými dotazy. Podívejme se na pravidla dotazů, základní mechanismus, který řídí, jak ProxySQL zpracovává provoz, který jím prochází. Seznam pravidel dotazu může vypadat takto:
Aplikují se od nejnižšího ID výše.
Zkusme vytvořit pravidlo dotazu, které povolí pouze SELECT dotazy pro konkrétního uživatele:
Na začátek seznamu pravidel přidáváme pravidlo dotazu. Chystáme se spárovat vše, co není SELECT (všimněte si, že je povolena možnost Negate Match Pattern). Pravidlo dotazu bude použito pouze v případě, že uživatelské jméno je „devuser“. Pokud jsou splněny všechny podmínky, uživatel uvidí chybu jako v poli „Chybová zpráva“.
[email protected]:~# mysql -u devuser -h 10.0.0.144 -P6033 -ppass
mysql: [Warning] Using a password on the command line interface can be insecure.
Welcome to the MySQL monitor. Commands end with ; or \g.
Your MySQL connection id is 3024
Server version: 5.5.30 (ProxySQL)
Copyright (c) 2009-2019 Percona LLC and/or its affiliates
Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.
Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
mysql> create schema myschema;
ERROR 1148 (42000): The query is not allowed
mysql> SELECT 1;
+---+
| 1 |
+---+
| 1 |
+---+
1 row in set (0.01 sec)
mysql> SELECT * FROM sbtest.sbtest1 LIMIT 1\G
*************************** 1. row ***************************
id: 1
k: 503019
c: 18034632456-32298647298-82351096178-60420120042-90070228681-93395382793-96740777141-18710455882-88896678134-41810932745
pad: 43683718329-48150560094-43449649167-51455516141-06448225399
1 row in set (0.00 sec)
Další příklad, tentokrát se pokusíme předejít nehodám souvisejícím se situací Bobby Tables.
S tímto pravidlem dotazu se vaše tabulka „studenti“ být vynechán Bobbym:
mysql> use school;
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -A
Database changed
mysql> INSERT INTO students VALUES (1, 'Robert');DROP TABLE students;--
Query OK, 1 row affected (0.01 sec)
ERROR 1148 (42000): Only superuser can execute DROP TABLE;
Jak vidíte, Bobbymu se nepodařilo odstranit náš stůl ‚studenti‘. Byl jen pěkně zasunutý do stolu.