Mercurial > hg > orthanc-databases
annotate Framework/MySQL/MySQLDatabase.cpp @ 163:4d32c9c8d6c0
Added support for TLS connections
author | Alain Mazy <alain@mazy.be> |
---|---|
date | Mon, 13 Jul 2020 11:59:29 +0200 |
parents | 275e14f57f1e |
children | 0632c2408af3 |
rev | line source |
---|---|
0 | 1 /** |
2 * Orthanc - A Lightweight, RESTful DICOM Store | |
3 * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics | |
4 * Department, University Hospital of Liege, Belgium | |
140
4cd7e45b671e
upgrade to year 2020
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
137
diff
changeset
|
5 * Copyright (C) 2017-2020 Osimis S.A., Belgium |
0 | 6 * |
7 * This program is free software: you can redistribute it and/or | |
8 * modify it under the terms of the GNU Affero General Public License | |
9 * as published by the Free Software Foundation, either version 3 of | |
10 * the License, or (at your option) any later version. | |
11 * | |
12 * This program is distributed in the hope that it will be useful, but | |
13 * WITHOUT ANY WARRANTY; without even the implied warranty of | |
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
15 * Affero General Public License for more details. | |
16 * | |
17 * You should have received a copy of the GNU Affero General Public License | |
18 * along with this program. If not, see <http://www.gnu.org/licenses/>. | |
19 **/ | |
20 | |
21 | |
22 #include "MySQLDatabase.h" | |
23 | |
24 #include "MySQLResult.h" | |
25 #include "MySQLStatement.h" | |
26 #include "MySQLTransaction.h" | |
23
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
27 #include "../Common/ImplicitTransaction.h" |
0 | 28 #include "../Common/Integer64Value.h" |
29 | |
157
275e14f57f1e
replacing deprecated std::auto_ptr by std::unique_ptr
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
152
diff
changeset
|
30 #include <Compatibility.h> // For std::unique_ptr<> |
152 | 31 #include <Logging.h> |
32 #include <OrthancException.h> | |
33 #include <Toolbox.h> | |
0 | 34 |
6 | 35 #include <errmsg.h> |
0 | 36 #include <mysqld_error.h> |
37 | |
38 #include <memory> | |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
39 #include <boost/thread.hpp> |
0 | 40 |
41 namespace OrthancDatabases | |
42 { | |
43 void MySQLDatabase::Close() | |
44 { | |
45 if (mysql_ != NULL) | |
46 { | |
47 LOG(INFO) << "Closing connection to MySQL database"; | |
48 mysql_close(mysql_); | |
49 mysql_ = NULL; | |
50 } | |
51 } | |
52 | |
53 | |
54 void MySQLDatabase::CheckErrorCode(int code) | |
55 { | |
56 if (code == 0) | |
57 { | |
58 return; | |
59 } | |
60 else | |
61 { | |
62 LogError(); | |
63 | |
64 unsigned int error = mysql_errno(mysql_); | |
65 if (error == CR_SERVER_GONE_ERROR || | |
66 error == CR_SERVER_LOST || | |
67 error == ER_QUERY_INTERRUPTED) | |
68 { | |
69 throw Orthanc::OrthancException(Orthanc::ErrorCode_DatabaseUnavailable); | |
70 } | |
71 else | |
72 { | |
73 throw Orthanc::OrthancException(Orthanc::ErrorCode_Database); | |
74 } | |
75 } | |
76 } | |
77 | |
78 | |
79 MySQLDatabase::MySQLDatabase(const MySQLParameters& parameters) : | |
80 parameters_(parameters), | |
81 mysql_(NULL) | |
82 { | |
83 } | |
84 | |
85 | |
46
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
86 MySQLDatabase::~MySQLDatabase() |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
87 { |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
88 try |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
89 { |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
90 Close(); |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
91 } |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
92 catch (Orthanc::OrthancException&) |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
93 { |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
94 // Ignore possible exceptions due to connection loss |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
95 } |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
96 } |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
97 |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
98 |
0 | 99 void MySQLDatabase::LogError() |
100 { | |
101 if (mysql_ != NULL) | |
102 { | |
103 LOG(ERROR) << "MySQL error (" << mysql_errno(mysql_) | |
104 << "," << mysql_sqlstate(mysql_) | |
105 << "): " << mysql_error(mysql_); | |
106 } | |
107 } | |
108 | |
109 | |
110 MYSQL* MySQLDatabase::GetObject() | |
111 { | |
112 if (mysql_ == NULL) | |
113 { | |
114 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); | |
115 } | |
116 else | |
117 { | |
118 return mysql_; | |
119 } | |
120 } | |
121 | |
122 | |
23
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
123 void MySQLDatabase::OpenInternal(const char* db) |
0 | 124 { |
125 if (mysql_ != NULL) | |
126 { | |
127 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); | |
128 } | |
129 | |
130 mysql_ = mysql_init(NULL); | |
131 if (mysql_ == NULL) | |
132 { | |
133 LOG(ERROR) << "Cannot initialize the MySQL connector"; | |
134 throw Orthanc::OrthancException(Orthanc::ErrorCode_InternalError); | |
135 } | |
46
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
136 |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
137 if (parameters_.GetUnixSocket().empty()) |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
138 { |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
139 // Fallback to TCP connection if no UNIX socket is provided |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
140 unsigned int protocol = MYSQL_PROTOCOL_TCP; |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
141 mysql_options(mysql_, MYSQL_OPT_PROTOCOL, (unsigned int *) &protocol); |
6a574d810b98
Compatibility with MySQL 8.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
24
diff
changeset
|
142 } |
163
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
143 |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
144 if (parameters_.IsSsl()) |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
145 { |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
146 if (parameters_.IsVerifyServerCertificates()) |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
147 { |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
148 my_bool verifyCert = 1; |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
149 mysql_options(mysql_, MYSQL_OPT_SSL_VERIFY_SERVER_CERT, (void *) &verifyCert); |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
150 mysql_optionsv(mysql_, MYSQL_OPT_SSL_CA, (void *)(parameters_.GetSslCaCertificates())); |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
151 } |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
152 |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
153 my_bool enforceTls = 1; |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
154 mysql_options(mysql_, MYSQL_OPT_SSL_ENFORCE, (void *) &enforceTls); |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
155 } |
4d32c9c8d6c0
Added support for TLS connections
Alain Mazy <alain@mazy.be>
parents:
157
diff
changeset
|
156 |
0 | 157 const char* socket = (parameters_.GetUnixSocket().empty() ? NULL : |
158 parameters_.GetUnixSocket().c_str()); | |
159 | |
160 if (mysql_real_connect(mysql_, | |
161 parameters_.GetHost().c_str(), | |
162 parameters_.GetUsername().c_str(), | |
163 parameters_.GetPassword().c_str(), db, | |
164 parameters_.GetPort(), socket, 0) == 0) | |
165 { | |
166 LogError(); | |
167 Close(); | |
168 throw Orthanc::OrthancException(Orthanc::ErrorCode_DatabaseUnavailable); | |
169 } | |
170 else | |
171 { | |
172 LOG(INFO) << "Successful connection to MySQL database"; | |
173 } | |
174 | |
175 if (mysql_set_character_set(mysql_, "utf8mb4") != 0) | |
176 { | |
177 LOG(ERROR) << "Cannot set the character set to UTF8"; | |
178 Close(); | |
179 throw Orthanc::OrthancException(Orthanc::ErrorCode_Database); | |
180 } | |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
181 } |
0 | 182 |
23
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
183 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
184 void MySQLDatabase::Open() |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
185 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
186 if (parameters_.GetDatabase().empty()) |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
187 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
188 throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
189 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
190 else |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
191 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
192 OpenInternal(parameters_.GetDatabase().c_str()); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
193 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
194 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
195 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
196 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
197 void MySQLDatabase::ClearDatabase(const MySQLParameters& parameters) |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
198 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
199 MySQLDatabase db(parameters); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
200 db.OpenRoot(); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
201 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
202 const std::string& database = parameters.GetDatabase(); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
203 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
204 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
205 MySQLTransaction t(db); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
206 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
207 if (!db.DoesDatabaseExist(t, database)) |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
208 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
209 LOG(ERROR) << "Inexistent database, please create it first: " << database; |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
210 throw Orthanc::OrthancException(Orthanc::ErrorCode_UnknownResource); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
211 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
212 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
213 db.Execute("DROP DATABASE " + database, false); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
214 db.Execute("CREATE DATABASE " + database, false); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
215 t.Commit(); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
216 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
217 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
218 |
0 | 219 |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
220 namespace |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
221 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
222 class ResultWrapper : public boost::noncopyable |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
223 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
224 private: |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
225 MYSQL_RES *result_; |
0 | 226 |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
227 public: |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
228 ResultWrapper(MySQLDatabase& mysql, |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
229 const std::string& sql) : |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
230 result_(NULL) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
231 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
232 if (mysql_real_query(mysql.GetObject(), sql.c_str(), sql.size())) |
0 | 233 { |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
234 mysql.LogError(); |
0 | 235 throw Orthanc::OrthancException(Orthanc::ErrorCode_Database); |
236 } | |
237 | |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
238 result_ = mysql_use_result(mysql.GetObject()); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
239 if (result_ == NULL) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
240 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
241 mysql.LogError(); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
242 throw Orthanc::OrthancException(Orthanc::ErrorCode_Database); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
243 } |
0 | 244 } |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
245 |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
246 ~ResultWrapper() |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
247 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
248 if (result_ != NULL) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
249 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
250 mysql_free_result(result_); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
251 result_ = NULL; |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
252 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
253 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
254 |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
255 MYSQL_RES *GetObject() |
0 | 256 { |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
257 return result_; |
0 | 258 } |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
259 }; |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
260 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
261 |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
262 |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
263 bool MySQLDatabase::LookupGlobalStringVariable(std::string& value, |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
264 const std::string& variable) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
265 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
266 ResultWrapper result(*this, "SELECT @@global." + variable); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
267 |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
268 MYSQL_ROW row = mysql_fetch_row(result.GetObject()); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
269 if (mysql_errno(mysql_) == 0 && |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
270 row && |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
271 row[0]) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
272 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
273 value = std::string(row[0]); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
274 return true; |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
275 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
276 else |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
277 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
278 return false; |
0 | 279 } |
280 } | |
281 | |
282 | |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
283 bool MySQLDatabase::LookupGlobalIntegerVariable(int64_t& value, |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
284 const std::string& variable) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
285 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
286 std::string s; |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
287 |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
288 if (LookupGlobalStringVariable(s, variable)) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
289 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
290 try |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
291 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
292 value = boost::lexical_cast<int64_t>(s); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
293 return true; |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
294 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
295 catch (boost::bad_lexical_cast&) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
296 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
297 throw Orthanc::OrthancException(Orthanc::ErrorCode_Database); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
298 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
299 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
300 else |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
301 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
302 return false; |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
303 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
304 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
305 |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
306 |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
307 bool MySQLDatabase::RunAdvisoryLockStatement(Query& query, |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
308 const std::string& lock) |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
309 { |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
310 const std::string& dbName = parameters_.GetDatabase(); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
311 |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
312 // Prepend the name of the lock by the database name. This allows |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
313 // to create a namespace for advisory locks: |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
314 // https://groups.google.com/d/msg/orthanc-users/yV3LSTh_TjI/MQIcvnMlAQAJ |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
315 std::string prefix; |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
316 prefix.reserve(dbName.size()); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
317 for (size_t i = 0; i < dbName.size(); i++) |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
318 { |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
319 if (isalnum(dbName[i]) || |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
320 dbName[i] == '$' || |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
321 dbName[i] == '_') |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
322 { |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
323 prefix.push_back(dbName[i]); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
324 } |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
325 } |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
326 |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
327 query.SetType("lock", ValueType_Utf8String); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
328 |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
329 MySQLStatement statement(*this, query); |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
330 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
331 Dictionary args; |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
332 args.SetUtf8Value("lock", prefix + "." + lock); |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
333 |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
334 bool success; |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
335 |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
336 { |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
337 MySQLTransaction t(*this); |
157
275e14f57f1e
replacing deprecated std::auto_ptr by std::unique_ptr
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
152
diff
changeset
|
338 std::unique_ptr<IResult> result(t.Execute(statement, args)); |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
339 |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
340 success = (!result->IsDone() && |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
341 result->GetField(0).GetType() == ValueType_Integer64 && |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
342 dynamic_cast<const Integer64Value&>(result->GetField(0)).GetValue() == 1); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
343 |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
344 t.Commit(); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
345 } |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
346 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
347 return success; |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
348 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
349 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
350 |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
351 bool MySQLDatabase::AcquireAdvisoryLock(const std::string& lock) |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
352 { |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
353 Query query("SELECT GET_LOCK(${lock}, 0)", false); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
354 return RunAdvisoryLockStatement(query, lock); |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
355 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
356 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
357 |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
358 bool MySQLDatabase::ReleaseAdvisoryLock(const std::string& lock) |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
359 { |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
360 Query query("SELECT RELEASE_LOCK(${lock})", false); |
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
361 return RunAdvisoryLockStatement(query, lock); |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
362 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
363 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
364 |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
365 void MySQLDatabase::AdvisoryLock(const std::string& lock) |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
366 { |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
367 if (!AcquireAdvisoryLock(lock)) |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
368 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
369 LOG(ERROR) << "The MySQL database is locked by another instance of Orthanc"; |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
370 throw Orthanc::OrthancException(Orthanc::ErrorCode_Database); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
371 } |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
372 } |
22
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
373 |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
374 |
0 | 375 bool MySQLDatabase::DoesTableExist(MySQLTransaction& transaction, |
376 const std::string& name) | |
377 { | |
378 if (mysql_ == NULL) | |
379 { | |
380 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); | |
381 } | |
382 | |
60
412e30336847
allowing dollars and underscores in MySQL database identifiers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
46
diff
changeset
|
383 if (!IsValidDatabaseIdentifier(name)) |
24
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
384 { |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
385 throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange); |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
386 } |
22
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
387 |
0 | 388 Query query("SELECT COUNT(*) FROM information_schema.TABLES WHERE " |
389 "(TABLE_SCHEMA = ${database}) AND (TABLE_NAME = ${table})", true); | |
390 query.SetType("database", ValueType_Utf8String); | |
391 query.SetType("table", ValueType_Utf8String); | |
392 | |
393 MySQLStatement statement(*this, query); | |
394 | |
395 Dictionary args; | |
396 args.SetUtf8Value("database", parameters_.GetDatabase()); | |
397 args.SetUtf8Value("table", name); | |
398 | |
157
275e14f57f1e
replacing deprecated std::auto_ptr by std::unique_ptr
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
152
diff
changeset
|
399 std::unique_ptr<IResult> result(statement.Execute(transaction, args)); |
0 | 400 return (!result->IsDone() && |
401 result->GetFieldsCount() == 1 && | |
402 result->GetField(0).GetType() == ValueType_Integer64 && | |
403 dynamic_cast<const Integer64Value&>(result->GetField(0)).GetValue() == 1); | |
404 } | |
405 | |
406 | |
22
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
407 bool MySQLDatabase::DoesDatabaseExist(MySQLTransaction& transaction, |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
408 const std::string& name) |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
409 { |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
410 if (mysql_ == NULL) |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
411 { |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
412 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
413 } |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
414 |
60
412e30336847
allowing dollars and underscores in MySQL database identifiers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
46
diff
changeset
|
415 if (!IsValidDatabaseIdentifier(name)) |
24
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
416 { |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
417 throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange); |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
418 } |
22
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
419 |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
420 Query query("SELECT COUNT(*) FROM information_schema.SCHEMATA " |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
421 "WHERE SCHEMA_NAME = ${database}", true); |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
422 query.SetType("database", ValueType_Utf8String); |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
423 |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
424 MySQLStatement statement(*this, query); |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
425 |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
426 Dictionary args; |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
427 args.SetUtf8Value("database", name); |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
428 |
157
275e14f57f1e
replacing deprecated std::auto_ptr by std::unique_ptr
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
152
diff
changeset
|
429 std::unique_ptr<IResult> result(statement.Execute(transaction, args)); |
22
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
430 return (!result->IsDone() && |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
431 result->GetFieldsCount() == 1 && |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
432 result->GetField(0).GetType() == ValueType_Integer64 && |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
433 dynamic_cast<const Integer64Value&>(result->GetField(0)).GetValue() == 1); |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
434 } |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
435 |
1e9bad493475
prevent running unit tests on a non-existing db
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
16
diff
changeset
|
436 |
144
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
437 bool MySQLDatabase::DoesTriggerExist(MySQLTransaction& transaction, |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
438 const std::string& name) |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
439 { |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
440 if (mysql_ == NULL) |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
441 { |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
442 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
443 } |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
444 |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
445 if (!IsValidDatabaseIdentifier(name)) |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
446 { |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
447 throw Orthanc::OrthancException(Orthanc::ErrorCode_ParameterOutOfRange); |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
448 } |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
449 |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
450 Query query("SELECT COUNT(*) FROM information_schema.TRIGGERS " |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
451 "WHERE TRIGGER_NAME = ${trigger}", true); |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
452 query.SetType("trigger", ValueType_Utf8String); |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
453 |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
454 MySQLStatement statement(*this, query); |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
455 |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
456 Dictionary args; |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
457 args.SetUtf8Value("trigger", name); |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
458 |
157
275e14f57f1e
replacing deprecated std::auto_ptr by std::unique_ptr
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
152
diff
changeset
|
459 std::unique_ptr<IResult> result(statement.Execute(transaction, args)); |
144
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
460 return (!result->IsDone() && |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
461 result->GetFieldsCount() == 1 && |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
462 result->GetField(0).GetType() == ValueType_Integer64 && |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
463 dynamic_cast<const Integer64Value&>(result->GetField(0)).GetValue() == 1); |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
464 } |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
465 |
740d9829f52e
handling of errors if MySQL user cannot CREATE TRIGGER
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
140
diff
changeset
|
466 |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
467 void MySQLDatabase::Execute(const std::string& sql, |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
468 bool arobaseSeparator) |
0 | 469 { |
470 if (mysql_ == NULL) | |
471 { | |
472 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); | |
473 } | |
474 | |
475 // This emulates the behavior of "CLIENT_MULTI_STATEMENTS" in | |
476 // "mysql_real_connect()", avoiding to implement a loop over | |
477 // "mysql_query()" | |
478 std::vector<std::string> commands; | |
479 Orthanc::Toolbox::TokenizeString(commands, sql, ';'); | |
480 | |
481 for (size_t i = 0; i < commands.size(); i++) | |
482 { | |
483 std::string s = Orthanc::Toolbox::StripSpaces(commands[i]); | |
484 | |
485 if (!s.empty()) | |
486 { | |
16
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
487 if (arobaseSeparator) |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
488 { |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
489 // Replace the escape character "@" by a semicolon |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
490 std::replace(s.begin(), s.end(), '@', ';'); |
9e419261f1c9
mysql storage area working
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
6
diff
changeset
|
491 } |
0 | 492 |
493 LOG(TRACE) << "MySQL: " << s; | |
494 CheckErrorCode(mysql_query(mysql_, s.c_str())); | |
495 } | |
496 } | |
497 } | |
498 | |
499 | |
500 IPrecompiledStatement* MySQLDatabase::Compile(const Query& query) | |
501 { | |
502 if (mysql_ == NULL) | |
503 { | |
504 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); | |
505 } | |
506 | |
507 return new MySQLStatement(*this, query); | |
508 } | |
509 | |
510 | |
23
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
511 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
512 namespace |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
513 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
514 class MySQLImplicitTransaction : public ImplicitTransaction |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
515 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
516 private: |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
517 MySQLDatabase& db_; |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
518 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
519 protected: |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
520 virtual IResult* ExecuteInternal(IPrecompiledStatement& statement, |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
521 const Dictionary& parameters) |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
522 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
523 return dynamic_cast<MySQLStatement&>(statement).Execute(*this, parameters); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
524 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
525 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
526 virtual void ExecuteWithoutResultInternal(IPrecompiledStatement& statement, |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
527 const Dictionary& parameters) |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
528 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
529 dynamic_cast<MySQLStatement&>(statement).ExecuteWithoutResult(*this, parameters); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
530 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
531 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
532 public: |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
533 MySQLImplicitTransaction(MySQLDatabase& db) : |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
534 db_(db) |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
535 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
536 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
537 }; |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
538 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
539 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
540 |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
541 ITransaction* MySQLDatabase::CreateTransaction(bool isImplicit) |
0 | 542 { |
543 if (mysql_ == NULL) | |
544 { | |
545 throw Orthanc::OrthancException(Orthanc::ErrorCode_BadSequenceOfCalls); | |
546 } | |
547 | |
23
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
548 if (isImplicit) |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
549 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
550 return new MySQLImplicitTransaction(*this); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
551 } |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
552 else |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
553 { |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
554 return new MySQLTransaction(*this); |
b2ff1cd2907a
handling of implicit transactions in DatabaseManager
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
22
diff
changeset
|
555 } |
0 | 556 } |
557 | |
558 | |
559 void MySQLDatabase::GlobalFinalization() | |
560 { | |
561 mysql_library_end(); | |
562 } | |
24
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
563 |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
564 |
60
412e30336847
allowing dollars and underscores in MySQL database identifiers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
46
diff
changeset
|
565 bool MySQLDatabase::IsValidDatabaseIdentifier(const std::string& s) |
24
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
566 { |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
567 for (size_t i = 0; i < s.length(); i++) |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
568 { |
60
412e30336847
allowing dollars and underscores in MySQL database identifiers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
46
diff
changeset
|
569 // https://dev.mysql.com/doc/refman/8.0/en/identifiers.html |
412e30336847
allowing dollars and underscores in MySQL database identifiers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
46
diff
changeset
|
570 if (!isalnum(s[i]) && |
412e30336847
allowing dollars and underscores in MySQL database identifiers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
46
diff
changeset
|
571 s[i] != '$' && |
412e30336847
allowing dollars and underscores in MySQL database identifiers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
46
diff
changeset
|
572 s[i] != '_') |
24
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
573 { |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
574 return false; |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
575 } |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
576 } |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
577 |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
578 return true; |
17f849b2af34
sharing plugin initialization code
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
23
diff
changeset
|
579 } |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
580 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
581 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
582 MySQLDatabase::TransientAdvisoryLock:: |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
583 TransientAdvisoryLock(MySQLDatabase& database, |
137
52b3859ee0b7
MySQL: acquiring named locks instead of numbers
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
135
diff
changeset
|
584 const std::string& lock) : |
135
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
585 database_(database), |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
586 lock_(lock) |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
587 { |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
588 bool locked = true; |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
589 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
590 for (unsigned int i = 0; i < 10; i++) |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
591 { |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
592 if (database_.AcquireAdvisoryLock(lock_)) |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
593 { |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
594 locked = false; |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
595 break; |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
596 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
597 else |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
598 { |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
599 boost::this_thread::sleep(boost::posix_time::milliseconds(500)); |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
600 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
601 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
602 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
603 if (locked) |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
604 { |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
605 LOG(ERROR) << "Cannot acquire a transient advisory lock"; |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
606 throw Orthanc::OrthancException(Orthanc::ErrorCode_Plugin); |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
607 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
608 } |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
609 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
610 |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
611 MySQLDatabase::TransientAdvisoryLock::~TransientAdvisoryLock() |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
612 { |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
613 database_.ReleaseAdvisoryLock(lock_); |
e26690365c25
MySQL: Added an advisory lock to avoid race conditions during database setup
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
67
diff
changeset
|
614 } |
0 | 615 } |