]> Creatis software - creaImageIO.git/blob - src2/creaImageIOSynchron.cpp
0748a861351066682f3336f1fee4dd54672f1c47
[creaImageIO.git] / src2 / creaImageIOSynchron.cpp
1 #include <creaImageIOSynchron.h>
2 #include <creaImageIOSystem.h>
3 #include <boost/filesystem.hpp>
4
5 namespace fs = boost::filesystem;
6
7 //=====================================================================
8  
9
10 namespace creaImageIO
11 {
12
13         //=====================================================================
14         #define QUERYSYNCDB(QUER,RES)                                   \
15     try                                                                 \
16       {                                                                 \
17         RES = mDB->execQuery(QUER.c_str());                             \
18       }                                                                 \
19     catch (CppSQLite3Exception& e)                                      \
20     {                                                                   \
21       GimmickError("SQLite query '"<<QUER<<"' Error : "                 \
22                    << e.errorCode() << ":"                              \
23                    << e.errorMessage() );                               \
24     }                                                                                                                                      
25         //=====================================================================
26         #define UPDATESYNCDB(UP)                                        \
27   try                                                                   \
28     {                                                                   \
29       mDB->execDML(UP.c_str());                                         \
30     }                                                                   \
31   catch (CppSQLite3Exception& e)                                        \
32     {                                                                   \
33       GimmickError("SQLite update '"<<UP<<"' Error : "                  \
34                    << e.errorCode() << ":"                              \
35                    << e.errorMessage() );                               \
36     }                           
37         //=====================================================================
38
39         Synchronizer::Synchronizer(const std::string& path)
40     {
41                 pathDB = path + "maintenance_database.db3";
42                 mDB = new CppSQLite3DB;
43                 Initialize();
44     }
45
46         //=====================================================================
47         Synchronizer::~Synchronizer()
48     {
49        
50     }
51
52         //=====================================================================
53         void Synchronizer::Initialize()
54         {    
55                 if (!fs::exists(pathDB)) 
56                 {
57                         CreateDB();
58                 }
59     
60                 // OPENING
61                 else
62                 {
63                 try
64                 {
65                 mDB->open(pathDB.c_str());
66                 }
67                 catch (CppSQLite3Exception& e)
68                 {
69                 GimmickError("Opening '"<<pathDB<<"' : "
70                      << e.errorCode() << ":" 
71                      << e.errorMessage());
72                 }
73                 }
74                 // get the ADD operations List 
75                 //UpdateAddList(pathDB);
76         }
77
78         //=====================================================================
79     void Synchronizer::CreateDB()
80     {
81                 mDB->open(pathDB.c_str());
82         // CREATING TABLES
83         std::string command;
84             command = "CREATE TABLE ";
85             command += "ADD_OPS";
86             command += "\n(\nADD_KEY INTEGER PRIMARY KEY";
87             command += ",\nPATH text";
88                 command += ",\nRECURSIVE boolean";
89                 command += ",\nFILES_ADDED int";
90                 command += ",\nREFERENCEDDB text";
91             command += "\n)";
92                 UPDATESYNCDB(command);
93
94                 command = "CREATE TABLE ";
95             command += "IGNORED_FILES";
96             command += "\n(\nID INTEGER PRIMARY KEY";
97                 command += ",\nADD_KEY integer";
98             command += ",\nPATH text";
99                 command += ",\nREMOVE boolean";
100                 command += ",\nTIME datetext";
101             command += "\n)";
102                 UPDATESYNCDB(command);
103     }
104
105         //=====================================================================
106         void Synchronizer::CleanName(std::string& str) const
107         {
108                 size_t pos;
109                 do
110                 {
111                         pos = str.find('\\');
112                         if (pos!=-1)  
113                         {
114                                 str.replace(pos, 1, "/");
115                         }
116                 }
117                 while (pos!=-1);
118         }
119
120         //=====================================================================
121         void Synchronizer::GetFileList(std::vector<AddList> & list, const std::string& refdb)
122     {
123        CleanList(refdb);
124            list=mAddList;
125     }
126
127         //=====================================================================
128         void Synchronizer::GetIgnoredFiles(const std::string& key, std::vector<std::string> &ignoreList)
129         {
130         ignoreList=GetIgnoreList(key);
131         }
132
133         //=====================================================================
134         void Synchronizer::UpdateAddList(const std::string& refdb)
135     {
136         std::string query = "SELECT * FROM ADD_OPS WHERE REFERENCEDDB = '"+refdb+"';";
137         CppSQLite3Query res;
138         QUERYSYNCDB(query, res);
139                 while (!res.eof())
140         {
141                         AddList temp = AddList(res);
142             mAddList.push_back(temp);
143                         res.nextRow();
144         }
145         }
146
147     /////////////////////////////////////////////////////////////////////////////////////////////////
148     // remove an entry of the DB
149     //@param i_table : table where to do the remove
150     // @param i_key : the add_key reference (one entry to remove for ADD_OP table, many for IGNORED_FILES table
151     //@result : -
152     /////////////////////////////////////////////////////////////////////////////////////////////////
153     void Synchronizer::RemoveEntry(const std::string i_table, const std::string i_key)
154     {
155         std::string query = "DELETE  FROM " + i_table + " WHERE ADD_KEY = '" + i_key +"'";
156         UPDATESYNCDB(query);
157         }
158
159         /////////////////////////////////////////////////////////////////////////////////////////////////
160     // remove several entries of the DB
161     // @param i_table : table where to do the remove
162         // @param i_attribute: attribute to match
163         // @param i_operand : operand to use
164     // @param i_val : the reference
165     //@result : -
166     /////////////////////////////////////////////////////////////////////////////////////////////////
167     void Synchronizer::RemoveEntries(const std::string i_table, 
168                 const std::string i_attribute, 
169                 const std::string i_operand, 
170                 const std::string i_val)
171     {
172         std::stringstream query;
173                 query<<"DELETE  FROM "<<i_table<<" WHERE "<<i_attribute<<" "<<i_operand<<" '"<<i_val<<"'";
174         UPDATESYNCDB(query.str());
175         }
176
177     /////////////////////////////////////////////////////////////////////////////////////////////////
178     // clean DataBase if an operation has no child anymore
179         // @param refdb: the database segement to clean
180     // @result : -
181     /////////////////////////////////////////////////////////////////////////////////////////////////
182     void Synchronizer::CleanList(const std::string& refdb)
183     {
184                 mAddList.clear();
185                 UpdateAddList(refdb);
186         std::vector<AddList>::iterator it_add = mAddList.begin();
187         for(;it_add <mAddList.end(); ++it_add)
188         {
189                 if(it_add->nbFiles == "0")
190                 {
191                                         RemoveEntry("ADD_OPS", it_add->key);
192                                         RemoveEntry("IGNORED_FILES", it_add->key);
193                                                 
194                 }
195         }
196                 mAddList.clear();
197                 UpdateAddList(refdb);
198     }
199
200         /////////////////////////////////////////////////////////////////////////////////////////////////
201     // Inserts a new add operation in the database
202     // @param path: the path of the directory that was added
203         // @param recursive: shows if the action was called recursively or not
204         // @param nChildren: the number of files affected by the operation
205         // @param refdb: the referenced database
206     // @result : The operation has been added
207     /////////////////////////////////////////////////////////////////////////////////////////////////
208         void Synchronizer::InsertAddOp(const std::string& path, const std::string& recursive,   const std::string& nChildren, const std::string& refdb)
209         {
210                 std::string insert;
211                 std::string pat=path.c_str();
212                 CleanName(pat);
213                 insert="INSERT INTO ADD_OPS (PATH,RECURSIVE,FILES_ADDED,REFERENCEDDB) VALUES('";
214                 insert+=pat+"','";
215                 insert+=recursive+"',";
216         insert+=nChildren+",'";
217                 insert+=refdb+"');";
218                 UPDATESYNCDB(insert);
219         }
220
221         /////////////////////////////////////////////////////////////////////////////////////////////////
222     // Inserts a new ignored file in the database
223         // @param add_key: the key of the add_op to which it corresponds
224     // @param path: the path of the directory that was added
225         // @param remove: shows if the file was removed or not
226         // @param time: the time in which the file was removed
227     // @result : The file has been inserted
228     /////////////////////////////////////////////////////////////////////////////////////////////////
229
230         void Synchronizer::InsertIgnoreFile(const std::string& addKey, const std::string& path, const std::string& remove, const std::string& time, const std::string& refdb )
231         {
232                 std::string pat=path.c_str();
233                 CleanName(pat);
234                 std::string id=GetAttribute("ID","IGNORED_FILES","PATH",pat,refdb);
235                 if(id.compare("")==0)
236                 {
237                         std::string insert;
238                         insert="INSERT INTO IGNORED_FILES (ADD_KEY,PATH,REMOVE,TIME) VALUES('";
239                         insert+=addKey+"','";
240                         insert+=pat+"','";
241                         insert+=remove+"',";
242                 insert+=time+");";
243                         UPDATESYNCDB(insert);
244                 }
245                 else            
246                 {
247                         //Gets the add key
248                         std::string ak=GetAttribute("ADD_KEY","IGNORED_FILES","ID",id,refdb);
249                         //gets the parent database to check if the file has been added to the current database
250                         std::string parentDB=GetAttribute("*","ADD_OPS","ADD_KEY",ak,refdb);
251                         //If there is no such entry, add it
252                         if(parentDB.compare("")==0)
253                         {
254                                 std::string insert;
255                                 insert="INSERT INTO IGNORED_FILES (ADD_KEY,PATH,REMOVE,TIME) VALUES('";
256                                 insert+=addKey+"','";
257                                 insert+=pat+"','";
258                                 insert+=remove+"',";
259                         insert+=time+");";
260                                 UPDATESYNCDB(insert);
261                         }
262                         else
263                         {
264                                 //Sets the new add key attribute for the file
265                                 SetAttribute("ADD_KEY","IGNORED_FILES",addKey,"ID", id,refdb);
266                                 //Sets the new remove attribute for the file
267                                 SetAttribute("REMOVE","IGNORED_FILES",remove,"ID", id,refdb);
268                                 //Sets the new time attribute for the file
269                                 SetAttribute("TIME","IGNORED_FILES",time,"ID", id,refdb);
270                         }
271                 }
272         }
273
274     /////////////////////////////////////////////////////////////////////////////////////////////////
275     // get the files name to ignore for a add operation synchronization
276     // @param : the add key
277     //@result : list (path) of ignore files
278     /////////////////////////////////////////////////////////////////////////////////////////////////
279     std::vector<std::string> Synchronizer::GetIgnoreList(const std::string &i_key)
280     {
281                 mIgnoreList.clear();
282         std::vector<std::string> i_names;
283                 std::string query = "SELECT * FROM IGNORED_FILES WHERE ADD_KEY = ";
284                 query+=i_key;
285         CppSQLite3Query res;
286         QUERYSYNCDB(query, res);
287                 while (!res.eof())
288         {
289                         RemoveList temp = RemoveList(res);
290                         if(temp.remove.compare("0")==0)
291                         {
292             mIgnoreList.push_back(temp);
293                         }
294                         res.nextRow();
295         }
296         std::vector<RemoveList>::iterator it;
297
298         for(it = mIgnoreList.begin();it != mIgnoreList.end(); ++it)
299         {
300             i_names.push_back((*it).path);
301         }
302                 return i_names;
303     }
304
305         /////////////////////////////////////////////////////////////////////////////////////////////////
306     // Gets the required attribute in the required table
307     // @param attribute: the attribute to look for
308     // @param table: the table to look in
309     // @param searchParam: the search parameter
310     // @param searchValue: the search value
311     // @result : required attribute
312     /////////////////////////////////////////////////////////////////////////////////////////////////
313     std::string Synchronizer::GetAttribute(const std::string& attribute, 
314                                         const std::string& table, 
315                                         const std::string& searchParam,
316                                         const std::string& searchValue, 
317                                         const std::string& refdb)
318     {
319         std::stringstream query;
320                 std::string result;
321                 std::string sVal=searchValue.c_str();
322                 CleanName(sVal);
323                 query<<"SELECT "<<attribute<<" FROM "<<table<<" WHERE "<<searchParam<<" = '"<<sVal;
324                 if(table.compare("ADD_OPS")==0)
325                 {
326                         query<<"' AND REFERENCEDDB = '"<<refdb<<"';";
327                 }
328                 else
329                 {
330                         query<<"';";
331                 }
332         CppSQLite3Query res;
333         QUERYSYNCDB(query.str(), res);
334                 while (!res.eof())
335         {
336                         result=res.getStringField(0);
337                         res.nextRow();
338         }
339                 return result;
340     }
341
342         /////////////////////////////////////////////////////////////////////////////////////////////////
343     // Sets the attribute value in the required table and column
344     // @param attribute: the attribute to look for
345     // @param table: the table to look in
346         // @param value: the value to set
347     // @param searchParam: the search parameter
348     // @param searchValue: the search value
349     // @result : attribute value changed
350     /////////////////////////////////////////////////////////////////////////////////////////////////
351     void Synchronizer::SetAttribute(const std::string& attribute, 
352                                 const std::string& table, 
353                                 const std::string& value,
354                                 const std::string& searchParam,
355                                 const std::string& searchValue,
356                                 const std::string& refdb)
357     {
358                 std::string val=value.c_str();
359                 std::string sVal=searchValue.c_str();
360                 CleanName(val);
361                 CleanName(sVal);
362                 std::string sql = "UPDATE ";
363                 sql+=table;
364                 sql+=" SET ";
365                 sql += attribute;
366                 sql += " = '";
367                 sql += val;
368                 sql += "' WHERE ";
369                 sql += searchParam;
370                 sql += " = '";
371                 sql += sVal;
372                 if(table.compare("ADD_OPS")==0)
373                 {
374                         sql += "' AND REFERENCEDDB = '";
375                         sql += refdb;
376                 }
377                 sql += "';";
378                 UPDATESYNCDB(sql);
379     }
380
381
382
383 /////////////////////////////////////////////////////////////////////////////////////////////////
384     // get the files name to ignore for a add operation synchronization
385     // @param : the add key
386     //@result : list (path) of ignore files
387     /////////////////////////////////////////////////////////////////////////////////////////////////
388     void Synchronizer::GetList()
389     {
390                 mList.clear();
391         std::vector<std::string> i_names;
392                 std::string query = "SELECT PATH, REMOVE FROM IGNORED_FILES";
393                 CppSQLite3Query res;
394         QUERYSYNCDB(query, res);
395                 while (!res.eof())
396         {
397                         std::string file(res.getStringField(0));
398                         std::string ignore(res.getStringField(1));
399                         mList[file] = ignore == "0"? true : false;
400                         res.nextRow();
401         }
402                 
403     }
404
405         bool Synchronizer::isIndexed(const std::string filename)
406         {
407                 bool valid = true;
408                 std::map <std::string, bool>::iterator it_list = mList.begin();
409                 for(;it_list != mList.end(); it_list++)
410                 {
411                         if(it_list->first == filename)
412                         {
413                                 valid = false;
414                                 break;
415                         }
416                 }
417                 return valid;
418         }
419 }