Leosac  0.8.0
Open Source Access Control
SearchBase.hpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2014-2016 Leosac
3 
4  This file is part of Leosac.
5 
6  Leosac is free software: you can redistribute it and/or modify
7  it under the terms of the GNU Affero General Public License as published by
8  the Free Software Foundation, either version 3 of the License, or
9  (at your option) any later version.
10 
11  Leosac is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  GNU Affero General Public License for more details.
15 
16  You should have received a copy of the GNU Affero General Public License
17  along with this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19 
20 #pragma once
21 
22 #include "tools/db/DBService.hpp"
23 #include "tools/log.hpp"
24 #include <nlohmann/json.hpp>
25 
26 namespace Leosac
27 {
28 namespace Module
29 {
30 namespace WebSockAPI
31 {
32 
37 {
38 };
43 {
44 };
45 
51 {
52 };
53 
60 template <typename DatabaseEntity, typename AliasOrName>
62 {
63 
64  using Query = odb::query<DatabaseEntity>;
65 
67  {
68  bool operator()(const DatabaseEntity &e1, const DatabaseEntity &e2)
69  {
70  static_assert(std::is_integral<decltype(e1.id())>::value,
71  "Id is not an integral type.");
72  ASSERT_LOG(e1.id(), "entity1 has no id.");
73  ASSERT_LOG(e2.id(), "entity2 has no id.");
74  return e1.id() < e2.id();
75  }
76  };
77 
78  using EntitySet = std::set<DatabaseEntity, DatabaseEntityComparator>;
79 
80  private:
81  template <typename T>
82  std::enable_if_t<std::is_same<T, use_alias_tag>::value, Query>
83  build_query(const std::string &partial)
84  {
85  Query q(Query::alias.like("%" + partial + "%"));
86  return std::move(q);
87  }
88 
89  template <typename T>
90  std::enable_if_t<std::is_same<T, use_name_tag>::value, Query>
91  build_query(const std::string &partial)
92  {
93  Query q(Query::name.like("%" + partial + "%"));
94  return std::move(q);
95  }
96 
97  template <typename T>
98  std::enable_if_t<std::is_same<T, use_username_tag>::value, Query>
99  build_query(const std::string &partial)
100  {
101  Query q(Query::username.like("%" + partial + "%"));
102  return std::move(q);
103  }
104 
105  void search_and_append(DBPtr db, EntitySet &entities, const std::string &partial)
106  {
107  Query q(build_query<AliasOrName>(partial));
108  auto results = db->query(q);
109  for (const auto &ap : results)
110  {
111  entities.insert(ap);
112  }
113  };
114 
115  public:
116  std::vector<DatabaseEntity> search(DBPtr db,
117  const std::string &partial_name_or_alias)
118  {
119  odb::transaction t(db->begin());
120  EntitySet entities;
121 
122  search_and_append(db, entities, partial_name_or_alias);
123 
124  // Attempt to convert each letter to CAPS so the search is
125  // a not too much case sensitive.
126  // Todo: This needs to be improved.
127  for (auto i = 0u; i < partial_name_or_alias.length(); ++i)
128  {
129  auto partial_name_copy = partial_name_or_alias;
130  partial_name_copy[i] = std::toupper(partial_name_or_alias[i]);
131  search_and_append(db, entities, partial_name_copy);
132  }
133 
134  return std::vector<DatabaseEntity>(entities.begin(), entities.end());
135  }
136 
137  private:
138  template <typename T>
139  std::enable_if_t<std::is_same<T, use_alias_tag>::value, json>
140  build_json_entry(const DatabaseEntity entity)
141  {
142  json result_json = {{"id", entity.id()}, {"alias", entity.alias()}};
143  return result_json;
144  }
145 
146  template <typename T>
147  std::enable_if_t<std::is_same<T, use_name_tag>::value, json>
148  build_json_entry(const DatabaseEntity entity)
149  {
150  json result_json = {{"id", entity.id()}, {"name", entity.name()}};
151  return result_json;
152  }
153 
154  template <typename T>
155  std::enable_if_t<std::is_same<T, use_username_tag>::value, json>
156  build_json_entry(const DatabaseEntity entity)
157  {
158  json result_json = {{"id", entity.id()}, {"username", entity.username()}};
159  return result_json;
160  }
161 
162  public:
171  json search_json(DBPtr db, const std::string &partial)
172  {
173  auto entities = search(db, partial);
174  json rep;
175  for (const auto &entity : entities)
176  {
177  rep.push_back(build_json_entry<AliasOrName>(entity));
178  }
179  return rep;
180  }
181 };
182 }
183 }
184 }
Leosac::Module::WebSockAPI::use_username_tag
Use this tag to search for entities with a "username" tag (Most likely only "User" for now ....
Definition: SearchBase.hpp:50
Leosac::Module::WebSockAPI::use_name_tag
Use this tag to search for entities with a "name".
Definition: SearchBase.hpp:42
ASSERT_LOG
#define ASSERT_LOG(cond, msg)
Definition: log.hpp:190
Leosac::Module::WebSockAPI::EntitySearchTool::build_query
std::enable_if_t< std::is_same< T, use_username_tag >::value, Query > build_query(const std::string &partial)
Definition: SearchBase.hpp:99
Leosac::DBPtr
std::shared_ptr< odb::database > DBPtr
Definition: db_fwd.hpp:31
Leosac::Module::WebSockAPI::EntitySearchTool
This is a templated class that perform case-insensitive database search against entities.
Definition: SearchBase.hpp:61
Query
odb::query< Tools::LogEntry > Query
Definition: LogEntry.cpp:36
Leosac::Module::WebSockAPI::EntitySearchTool::build_query
std::enable_if_t< std::is_same< T, use_alias_tag >::value, Query > build_query(const std::string &partial)
Definition: SearchBase.hpp:83
Leosac
This is the header file for a generated source file, GitSHA1.cpp.
Definition: APIStatusCode.hpp:22
Leosac::Module::WebSockAPI::EntitySearchTool::search_json
json search_json(DBPtr db, const std::string &partial)
Returns a JSON array with the result from the search.
Definition: SearchBase.hpp:171
Leosac::Module::WebSockAPI::EntitySearchTool::build_json_entry
std::enable_if_t< std::is_same< T, use_username_tag >::value, json > build_json_entry(const DatabaseEntity entity)
Definition: SearchBase.hpp:156
Leosac::Module::WebSockAPI::EntitySearchTool::EntitySet
std::set< DatabaseEntity, DatabaseEntityComparator > EntitySet
Definition: SearchBase.hpp:78
Leosac::Module::WebSockAPI::EntitySearchTool::DatabaseEntityComparator::operator()
bool operator()(const DatabaseEntity &e1, const DatabaseEntity &e2)
Definition: SearchBase.hpp:68
DBService.hpp
Leosac::Module::WebSockAPI::EntitySearchTool::DatabaseEntityComparator
Definition: SearchBase.hpp:66
Leosac::Module::WebSockAPI::EntitySearchTool::search_and_append
void search_and_append(DBPtr db, EntitySet &entities, const std::string &partial)
Definition: SearchBase.hpp:105
log.hpp
Leosac::Module::WebSockAPI::json
nlohmann::json json
Definition: AccessOverview.hpp:30
Leosac::Module::WebSockAPI::use_alias_tag
Use this tag to search for entities with an "alias" field.
Definition: SearchBase.hpp:36
Leosac::Module::WebSockAPI::EntitySearchTool::Query
odb::query< DatabaseEntity > Query
Definition: SearchBase.hpp:64
Leosac::Module::WebSockAPI::EntitySearchTool::build_query
std::enable_if_t< std::is_same< T, use_name_tag >::value, Query > build_query(const std::string &partial)
Definition: SearchBase.hpp:91
Leosac::Module::WebSockAPI::EntitySearchTool::build_json_entry
std::enable_if_t< std::is_same< T, use_name_tag >::value, json > build_json_entry(const DatabaseEntity entity)
Definition: SearchBase.hpp:148
Leosac::Module::WebSockAPI::EntitySearchTool::build_json_entry
std::enable_if_t< std::is_same< T, use_alias_tag >::value, json > build_json_entry(const DatabaseEntity entity)
Definition: SearchBase.hpp:140
Leosac::Module::WebSockAPI::EntitySearchTool::search
std::vector< DatabaseEntity > search(DBPtr db, const std::string &partial_name_or_alias)
Definition: SearchBase.hpp:116