Skip to content

Commit c35a284

Browse files
authored
Merge pull request #2625 from creideiki/mysql-mixin
Add MySQL/MariaDB support to the SQL mixin
2 parents b95f9e6 + a709a0e commit c35a284

File tree

5 files changed

+37
-14
lines changed

5 files changed

+37
-14
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ Please refer to the [NEWS](NEWS.md) for a list of changes which have an affect o
1818
### Core
1919
- Drop support for Python 3.8 (fixes #2616, PR#2617 by Sebastian Wagner).
2020
- `intelmq.lib.splitreports`: Handle bot parameter `chunk_size` values empty string, due to missing parameter typing checks (PR#2604 by Sebastian Wagner).
21+
- `intelmq.lib.mixins.sql` Add Support for MySQL (PR#2625 by Karl-Johan Karlsson).
2122

2223
### Development
2324

@@ -45,6 +46,7 @@ Please refer to the [NEWS](NEWS.md) for a list of changes which have an affect o
4546
- Add new parameter `templating` for additional template variables.
4647
- Add new parameter `allowed_fieldnames` for csv field specification.
4748
- Add new parameter `fieldnames_translation` for naming csv headers (PR#2610 by Lukas Heindl, fixes #2586).
49+
- `intelmq.bots.outputs.sql.output`: Add Support for MySQL (PR#2625 by Karl-Johan Karlsson).
4850

4951
### Documentation
5052
- Fix and refresh links to mailing lists (PR#2609 by Kamil Mańkowski)

docs/user/bots.md

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -2905,8 +2905,7 @@ Order of operation: `strip -> replace -> split`. These three methods can be comb
29052905

29062906
### Generic DB Lookup <div id="intelmq.bots.experts.generic_db_lookup.expert" />
29072907

2908-
This bot is capable for enriching intelmq events by lookups to a database. Currently only PostgreSQL and SQLite are
2909-
supported.
2908+
This bot is capable for enriching intelmq events by lookups to a database. Currently PostgreSQL, SQLite, MSSQL, and MySQL/MariaDB are supported.
29102909

29112910
If more than one result is returned, a ValueError is raised.
29122911

@@ -2918,7 +2917,7 @@ If more than one result is returned, a ValueError is raised.
29182917

29192918
**`engine`**
29202919

2921-
(required, string) Allowed values: `postgresql` or `sqlite`.
2920+
(required, string) Allowed values: `postgresql`, `sqlite`, `mssql`, or `mysql`.
29222921

29232922
**`database`**
29242923

@@ -2928,23 +2927,25 @@ If more than one result is returned, a ValueError is raised.
29282927

29292928
(optional, string) Name of the table. Defaults to `contacts`.
29302929

2931-
*PostgreSQL specific parameters*
2930+
*Database server (i.e. not SQLite) specific parameters*
29322931

29332932
**`host`**
29342933

2935-
(optional, string) Hostname of the PostgreSQL server. Defaults to `localhost`.
2934+
(optional, string) Hostname of the database server. Defaults to `localhost`.
29362935

29372936
**`port`**
29382937

2939-
(optional, integer) Port of the PostgreSQL server. Defaults to 5432.
2938+
(optional, integer) Port of the database server. Defaults to 5432 (which is the default for PostgreSQL).
29402939

29412940
**`user`**
29422941

2943-
(optional, string) Username for accessing PostgreSQL. Defaults to `intelmq`.
2942+
(optional, string) Username for accessing the database server. Defaults to `intelmq`.
29442943

29452944
**`password`**
29462945

2947-
(optional, string) Password for accessing PostgreSQL. Defaults to ?.
2946+
(optional, string) Password for accessing the database server. Defaults to ?.
2947+
2948+
*PostgreSQL specific parameters*
29482949

29492950
**`sslmode`**
29502951

@@ -5294,7 +5295,7 @@ Client certificates are not supported. If `http_verify_cert` is true, TLS certif
52945295

52955296
### SQL <div id="intelmq.bots.outputs.sql.output" />
52965297

5297-
SQL is the bot responsible to send events to a PostgreSQL, SQLite, or MSSQL Database.
5298+
SQL is the bot responsible to send events to a PostgreSQL, SQLite, MSSQL, or MySQL/MariaDB database.
52985299

52995300
!!! note
53005301
When activating autocommit, transactions are not used. See: <http://initd.org/psycopg/docs/connection.html#connection.autocommit>
@@ -5311,7 +5312,7 @@ The parameters marked with 'PostgreSQL' will be sent to libpq via psycopg2. Chec
53115312

53125313
**`engine`**
53135314

5314-
(required, string) Allowed values are `postgresql`, `sqlite`, or `mssql`.
5315+
(required, string) Allowed values are `postgresql`, `sqlite`, `mssql`, or `mysql`.
53155316

53165317
**`database`**
53175318

@@ -5343,7 +5344,7 @@ The parameters marked with 'PostgreSQL' will be sent to libpq via psycopg2. Chec
53435344

53445345
**`sslmode`**
53455346

5346-
(optional, string) Database sslmode, Allowed values: `disable`, `allow`, `prefer`, `require`, `verify-ca` or `verify-full`. See: <https://www.postgresql.org/docs/current/static/images/libpq-connect.html#libpq-connect-sslmode>. Defaults to `require`.
5347+
(optional, string, PostgreSQL only) Database sslmode, Allowed values: `disable`, `allow`, `prefer`, `require`, `verify-ca` or `verify-full`. See: <https://www.postgresql.org/docs/current/static/images/libpq-connect.html#libpq-connect-sslmode>. Defaults to `require`.
53475348

53485349
**`table`**
53495350

intelmq/bots/outputs/sql/REQUIREMENTS.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,3 +3,4 @@
33

44
psycopg2-binary>=2.5.5
55
pymssql>=2.2
6+
PyMySQL>=0.10

intelmq/bots/outputs/sql/output.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ def g(obj):
2424

2525

2626
class SQLOutputBot(OutputBot, SQLMixin):
27-
"""Send events to a PostgreSQL or SQLite database"""
27+
"""Send events to an SQL database"""
2828
autocommit = True
2929
database = "intelmq-events"
3030
engine = None

intelmq/lib/mixins/sql.py

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,12 +16,13 @@ class SQLMixin:
1616
You do not have to bother:
1717
* connecting database in the self.init() method, just call super().init(), self.cur will be set
1818
* catching exceptions, just call self.execute() instead of self.cur.execute()
19-
* self.format_char will be set to '%s' in PostgreSQL and to '?' in SQLite
19+
* self.format_char will be set to '?' in SQLite and '%s' otherwise
2020
"""
2121

2222
POSTGRESQL = "postgresql"
2323
SQLITE = "sqlite"
2424
MSSQL = "mssql"
25+
MYSQL = "mysql"
2526
_default_engine = "postgresql"
2627
engine = None
2728
# overwrite the default value from the OutputBot
@@ -40,7 +41,8 @@ def _init_sql(self):
4041
self._engine_name = getattr(self, 'engine', self._default_engine).lower()
4142
engines = {SQLMixin.POSTGRESQL: (self._init_postgresql, "%s"),
4243
SQLMixin.SQLITE: (self._init_sqlite, "?"),
43-
SQLMixin.MSSQL: (self._init_mssql, "%s")}
44+
SQLMixin.MSSQL: (self._init_mssql, "%s"),
45+
SQLMixin.MYSQL: (self._init_mysql, "%s")}
4446
for key, val in engines.items():
4547
if self._engine_name == key:
4648
val[0]()
@@ -110,6 +112,23 @@ def _init_mssql(self):
110112
},
111113
autocommitable=True)
112114

115+
def _init_mysql(self):
116+
try:
117+
import pymysql
118+
except ImportError:
119+
raise exceptions.MissingDependencyError("pymysql")
120+
121+
self._connect(pymysql,
122+
{"database": self.database,
123+
"user": self.user,
124+
"password": self.password,
125+
"host": self.host,
126+
"port": self.port,
127+
"connect_timeout": getattr(self, 'connect_timeout', 5)
128+
},
129+
autocommitable=True)
130+
self.cur.execute("SET sql_mode = CONCAT_WS(',', (SELECT @@sql_mode), 'ANSI_QUOTES')")
131+
113132
def execute(self, query: str, values: tuple, rollback=False):
114133
try:
115134
self.logger.debug('Executing %r.', (query, values))

0 commit comments

Comments
 (0)