16#include "MantidKernel/DllConfig.h"
19#include <Poco/Notification.h>
20#include <Poco/NotificationCenter.h>
24#define strcasecmp _stricmp
43 return strcasecmp(lhs.c_str(),
rhs.c_str()) < 0;
67 using svc_it =
typename svcmap::iterator;
93 const std::shared_ptr<T> &
object()
const {
return m_object; }
122 const std::shared_ptr<T> &
newObject()
const {
return m_newObject; }
123 const std::shared_ptr<T> &
oldObject()
const {
return m_oldObject; }
194 virtual void add(
const std::string &
name,
const std::shared_ptr<T> &Tobject) {
195 checkForEmptyName(
name);
196 checkForNullPointer(Tobject);
198 bool success =
false;
201 std::lock_guard<std::recursive_mutex> lock(m_mutex);
206 success = datamap.insert(std::make_pair(
name, Tobject)).second;
209 std::string
error =
" add : Unable to insert Data Object : '" +
name +
"'";
211 throw std::runtime_error(
error);
213 g_log.
debug() <<
"Add Data Object " <<
name <<
" successful\n";
227 checkForNullPointer(Tobject);
230 std::unique_lock<std::recursive_mutex> lock(m_mutex);
233 auto it = datamap.find(
name);
234 if (it != datamap.end()) {
236 g_log.
debug(
"Data Object '" +
name +
"' replaced in data service.\n");
241 it->second = Tobject;
248 DataService::add(
name, Tobject);
257 std::unique_lock<std::recursive_mutex> lock(m_mutex);
259 auto it = datamap.find(
name);
260 if (it == datamap.end()) {
262 g_log.
debug(
" remove '" +
name +
"' cannot be found");
268 auto data = std::move(it->second);
276 g_log.
debug(
"Data Object '" +
name +
"' deleted from data service.");
285 void rename(
const std::string &oldName,
const std::string &newName) {
286 checkForEmptyName(newName);
287 bool caseInsensitiveMatch =
false;
289 if (!strcasecmp(oldName.c_str(), newName.c_str())) {
290 if (oldName == newName) {
291 g_log.
warning(
"Rename: The existing name matches the new name");
294 caseInsensitiveMatch =
true;
297 std::unique_lock<std::recursive_mutex> lock(m_mutex);
299 auto existingNameIter = datamap.find(oldName);
300 if (existingNameIter == datamap.end()) {
302 g_log.
warning(
" rename '" + oldName +
"' cannot be found");
306 auto existingNameObject = std::move(existingNameIter->second);
307 auto targetNameIter = caseInsensitiveMatch ? datamap.end() : datamap.find(newName);
310 if (targetNameIter != datamap.end()) {
311 auto targetNameObject = targetNameIter->second;
318 datamap.erase(existingNameIter);
320 if (targetNameIter != datamap.end()) {
321 targetNameIter->second = std::move(existingNameObject);
325 if (!(datamap.emplace(newName, std::move(existingNameObject)).second)) {
328 std::string
error =
" add : Unable to insert Data Object : '" + newName +
"'";
330 throw std::runtime_error(
error);
335 g_log.
debug(
"Data Object '" + oldName +
"' renamed to '" + newName +
"'");
344 std::lock_guard<std::recursive_mutex> lock(m_mutex);
348 g_log.
debug() <<
typeid(
this).
name() <<
" cleared.\n";
359 std::lock_guard<std::recursive_mutex> _lock(m_mutex);
361 auto it = datamap.find(
name);
362 if (it != datamap.end()) {
372 return std::all_of(listOfNames.cbegin(), listOfNames.cend(),
373 [
this](
auto const &
name) { return this->doesExist(name); });
379 std::lock_guard<std::recursive_mutex> _lock(m_mutex);
380 auto it = datamap.find(
name);
381 return it != datamap.end();
386 std::lock_guard<std::recursive_mutex> _lock(m_mutex);
388 if (showingHiddenObjects()) {
389 return datamap.size();
391 return std::count_if(datamap.cbegin(), datamap.cend(),
392 [](
const auto &it) { return !isHiddenDataServiceObject(it.first); });
407 const std::string &contain =
"")
const {
409 std::vector<std::string> foundNames;
412 if (hiddenState == DataServiceHidden::Auto) {
413 if (showingHiddenObjects()) {
414 hiddenState = DataServiceHidden::Include;
416 hiddenState = DataServiceHidden::Exclude;
421 if (hiddenState == DataServiceHidden::Include) {
423 std::lock_guard<std::recursive_mutex> _lock(m_mutex);
424 foundNames.reserve(datamap.size());
425 for (
const auto &item : datamap) {
426 if (contain.empty()) {
427 foundNames.emplace_back(item.first);
428 }
else if (item.first.find(contain) != std::string::npos) {
429 foundNames.emplace_back(item.first);
434 std::lock_guard<std::recursive_mutex> _lock(m_mutex);
435 foundNames.reserve(datamap.size());
436 for (
const auto &item : datamap) {
437 if (!isHiddenDataServiceObject(item.first)) {
439 if (contain.empty()) {
440 foundNames.emplace_back(item.first);
441 }
else if (item.first.find(contain) != std::string::npos) {
442 foundNames.emplace_back(item.first);
450 if (sortState == DataServiceSort::Sorted) {
451 std::sort(foundNames.begin(), foundNames.end());
459 std::lock_guard<std::recursive_mutex> _lock(m_mutex);
461 const bool alwaysIncludeHidden = includeHidden == DataServiceHidden::Include;
462 const bool usingAuto = includeHidden == DataServiceHidden::Auto && showingHiddenObjects();
464 const bool showingHidden = alwaysIncludeHidden || usingAuto;
466 std::vector<std::shared_ptr<T>> objects;
467 objects.reserve(datamap.size());
468 for (
const auto &it : datamap) {
469 if (showingHidden || !isHiddenDataServiceObject(it.first)) {
470 objects.emplace_back(it.second);
481 auto showingHiddenFlag = ConfigService::Instance().getValue<
bool>(
"MantidOptions.InvisibleWorkspaces");
482 return showingHiddenFlag.value_or(
false);
503 const std::string
error =
"Add Data Object with empty name";
505 throw std::runtime_error(
error);
511 const std::string
error =
"Attempt to add empty shared pointer";
513 throw std::runtime_error(
error);
const std::vector< double > & rhs
double obj
the value of the quadratic function
AddNotification is sent after an new object is added to the data service.
AddNotification(const std::string &name, const std::shared_ptr< T > &obj)
Constructor.
AfterReplaceNotification is sent after an object is replaced in the addOrReplace() function.
AfterReplaceNotification(const std::string &name, const std::shared_ptr< T > &newObj)
Constructor.
BeforeReplaceNotification is sent before an object is replaced in the addOrReplace() function.
std::shared_ptr< T > m_oldObject
const std::shared_ptr< T > & oldObject() const
BeforeReplaceNotification(const std::string &name, const std::shared_ptr< T > &obj, const std::shared_ptr< T > &newObj)
Constructor.
const std::shared_ptr< T > & newObject() const
Returns the pointer to the new object.
std::shared_ptr< T > m_newObject
shared pointer to the object
Clear notification is sent when the service is cleared.
ClearNotification()
Constructor.
Base class for DataService notifications that also stores a pointer to the object.
DataServiceNotification(const std::string &name, const std::shared_ptr< T > &obj)
Constructor.
const std::shared_ptr< T > & object() const
Returns the const pointer to the object concerned or 0 if it is a general notification.
std::shared_ptr< T > m_object
shared pointer to the object
Class for named object notifications.
NamedObjectNotification(const std::string &name)
std::string m_name
object's name
const std::string & objectName() const
Returns the name of the object.
PostDeleteNotification is sent after an object is deleted from the data service.
PostDeleteNotification(const std::string &name)
Constructor.
PreDeleteNotification is sent before an object is deleted from the data service.
PreDeleteNotification(const std::string &name, const std::shared_ptr< T > &obj)
Constructor.
Rename notification is sent when the rename method is called.
std::string m_newName
New object name.
const std::string & newObjectName() const
New name for the object.
RenameNotification(const std::string &name, const std::string &newName)
Constructor.
DataService stores instances of a given type.
virtual void add(const std::string &name, const std::shared_ptr< T > &Tobject)
Add an object to the service.
static std::string prefixToHide()
bool doesExist(const std::string &name) const
Check to see if a data object exists in the store.
void checkForNullPointer(const std::shared_ptr< T > &Tobject)
void rename(const std::string &oldName, const std::string &newName)
Rename an object within the service.
std::vector< std::string > getObjectNames(DataServiceSort sortState=DataServiceSort::Unsorted, DataServiceHidden hiddenState=DataServiceHidden::Auto, const std::string &contain="") const
Returns a vector of strings containing all object names in the ADS.
Logger g_log
Logger for this DataService.
svcmap datamap
Map of objects in the data service.
const std::string svcName
DataService name.
virtual void shutdown()
Prepare for shutdown.
std::shared_ptr< T > retrieve(const std::string &name) const
Get a shared pointer to a stored data object.
void checkForEmptyName(const std::string &name)
DataService & operator=(const DataService &)=delete
Deleted copy assignment operator.
size_t size() const
Return the number of objects stored by the data service.
std::map< std::string, std::shared_ptr< T >, CaseInsensitiveCmp > svcmap
Typedef for the map holding the names of and pointers to the data objects.
static bool showingHiddenObjects()
virtual ~DataService()=default
std::recursive_mutex m_mutex
Recursive mutex to avoid simultaneous access or notifications.
typename svcmap::const_iterator svc_constit
Const iterator for the data store map.
bool doAllWsExist(const std::vector< std::string > &listOfNames)
Checks all elements within the specified vector exist in the ADS.
virtual void addOrReplace(const std::string &name, const std::shared_ptr< T > &Tobject)
Add or replace an object to the service.
typename svcmap::iterator svc_it
Iterator for the data store map.
Poco::NotificationCenter notificationCenter
Sends notifications to observers.
DataService(const std::string &name)
Protected constructor (singleton)
std::vector< std::shared_ptr< T > > getObjects(DataServiceHidden includeHidden=DataServiceHidden::Auto) const
Get a vector of the pointers to the data objects stored by the service.
void remove(const std::string &name)
Remove an object from the service.
static bool isHiddenDataServiceObject(const std::string &name)
void clear()
Empty the service.
DataService(const DataService &)=delete
Deleted copy constructor.
Exception for when an item is not found in a collection.
The Logger class is in charge of the publishing messages from the framework through various channels.
void debug(const std::string &msg)
Logs at debug level.
void error(const std::string &msg)
Logs at error level.
void warning(const std::string &msg)
Logs at warning level.
DataServiceSort
Flag for whether to sort items before returning.
DataServiceHidden
Flag for whether to include hidden items when returning, Auto queries the class to determine this beh...
Helper class which provides the Collimation Length for SANS instruments.
bool operator()(const std::string &lhs, const std::string &rhs) const