27 #include <basic/message_listening/MessageListenerFactory.hh>
28 #include <basic/message_listening/MessageListener.hh>
29 #include <basic/message_listening/DbMoverMessageListener.hh>
30 #include <basic/message_listening/util.hh>
32 #include <basic/Tracer.hh>
33 #include <basic/database/sql_utils.hh>
34 #include <basic/options/option.hh>
35 #include <basic/options/keys/out.OptionKeys.gen.hh>
37 #include <utility/string_util.hh>
38 #include <utility/mpi_util.hh>
39 #include <utility/exit.hh>
40 #include <utility/pointer/owning_ptr.hh>
42 #include <cppdb/frontend.h>
43 #include <cppdb/errors.h>
45 #include <boost/uuid/uuid.hpp>
46 #include <boost/uuid/uuid_io.hpp>
59 using std::stringstream;
62 using cppdb::cppdb_error;
63 using utility::sql_database::sessionOP;
66 using basic::message_listening::request_data_from_head_node;
67 using basic::message_listening::send_data_to_head_node;
68 using basic::message_listening::DATABASE_PROTOCOL_AND_BATCH_ID_TAG;
69 using cppdb::statement;
78 static Tracer
TR(
"protocols.features.util");
91 using namespace basic::message_listening;
101 MPI_Comm_rank( MPI_COMM_WORLD, (
int*)(&rank) );
110 string listener_data=
"";
114 DbMoverMessageListenerOP listener(utility::pointer::dynamic_pointer_cast<DbMoverMessageListener,MessageListener>(MessageListenerFactory::get_instance()->get_listener(DATABASE_PROTOCOL_AND_BATCH_ID_TAG)));
115 if(!listener->max_batch_id_set())
117 std::string select_max =
"SELECT MAX(batch_id) FROM batches;";
118 cppdb::statement stmt(basic::database::safely_prepare_statement(select_max,db_session));
119 cppdb::result res(basic::database::safely_read_from_database(stmt));
121 Size max_batch_id(0);
126 listener->set_max_batch_id(max_batch_id);
132 listener_data = request_data_from_head_node(DATABASE_PROTOCOL_AND_BATCH_ID_TAG, identifier);
134 <<
"Requesting data on '" << identifier <<
"' "
135 <<
"from the DATABASE_PROTOCOL_AND_BATCH_ID_TAG message listener on head node." << std::endl;
138 MessageListenerOP listener(
139 MessageListenerFactory::get_instance()->get_listener(
140 DATABASE_PROTOCOL_AND_BATCH_ID_TAG));
141 listener->request(identifier,listener_data);
144 <<
"Requesting data on '" << identifier <<
"' "
145 <<
"from the DATABASE_PROTOCOL_AND_BATCH_ID_TAG message listener." << std::endl;
150 protocol_id = ids.first;
151 batch_id = ids.second;
152 TR <<
"Received protocol_id='" << protocol_id <<
"' and batch_id='" << batch_id <<
"'" << std::endl;
157 protocol_id = protocol_features->report_features(protocol_id, db_session);
158 }
catch (cppdb_error error){
159 stringstream err_msg;
161 <<
"Failed to set the protocol id for batch "
162 <<
"'" << identifier <<
"'" << endl
163 <<
"Error Message:" << endl << error.what() << endl;
164 utility_exit_with_message(err_msg.str());
168 <<
"Initialize the protocol_id='" << protocol_id <<
"' "
169 <<
"and tell it to the head node." << std::endl;
172 TR <<
"Send the protocol_id '" << protocol_id <<
"' to the head node." << std::endl;
173 utility::send_string_to_node(0,
serialize_ids(protocol_id, identifier, batch_id));
175 MessageListenerOP listener(
176 MessageListenerFactory::get_instance()->get_listener(
177 DATABASE_PROTOCOL_AND_BATCH_ID_TAG));
178 listener->receive(
serialize_ids(protocol_id, identifier, batch_id));
182 TR <<
"done with protocol" <<std::endl;
186 batch_features->report_features(batch_id, protocol_id, identifier,
"", db_session);
187 }
catch (cppdb_error error){
188 stringstream err_msg;
190 <<
"Failed to set the batch id for batch '" << identifier <<
"' "
191 <<
"with protocol_id '" << protocol_id <<
"'" << endl
192 <<
"Error Message:" << endl << error.what() << endl;
193 utility_exit_with_message(err_msg.str());
200 TR <<
"Initializing protocol table" << endl;
203 }
catch (cppdb_error error){
204 stringstream err_msg;
206 <<
"Failed to set the protocol id for batch "
207 <<
"'" << identifier <<
"'" << endl
208 <<
"Error Message:" << endl << error.what() << endl;
209 utility_exit_with_message(err_msg.str());
216 TR <<
"Initializing batch table" << endl;
219 std::string select_max =
"SELECT MAX(batch_id) FROM batches;";
220 cppdb::statement stmt(basic::database::safely_prepare_statement(select_max,db_session));
221 cppdb::result res(basic::database::safely_read_from_database(stmt));
223 Size max_batch_id(0);
231 std::map< std::string, Size >::const_iterator
234 max_batch_id = std::max(max_batch_id, i->second);
236 batch_id = max_batch_id + 1;
240 batch_features->report_features(
241 batch_id, protocol_id, identifier,
"", db_session);
242 }
catch (cppdb_error error){
243 stringstream err_msg;
245 <<
"Failed to set the batch id for batch '" << identifier <<
"' "
246 <<
"with protocol_id '" << protocol_id <<
"'" << endl
247 <<
"Error Message:" << endl << error.what() << endl;
248 utility_exit_with_message(err_msg.str());
256 return pair<Size, Size>(protocol_id, batch_id);
264 if(tokens.size() != 2){
265 utility_exit_with_message(
"failed to deserialize the message from master node. Message was: " + data +
" You will get this message if trying to run ReportToDB mover in MPI mode with only on processor.");
267 int protocol_id=utility::string2int(tokens[1]);
268 int batch_id=utility::string2int(tokens[2]);
269 return pair<Size, Size>(protocol_id, batch_id);
279 utility::to_string(protocol_id) +
" " +
281 utility::to_string(batch_id);
289 boost::uuids::uuid struct_id,
294 "SELECT batch_id FROM structures WHERE struct_id = ?;");
295 statement stmt(basic::database::safely_prepare_statement(stmt_str, db_session));
296 stmt.bind(1, struct_id);
297 result res(basic::database::safely_read_from_database(stmt));
300 stringstream err_msg;
302 <<
"No batch_id found for struct_id '"
303 << to_string(struct_id) <<
"'";
304 utility_exit_with_message(err_msg.str());