AutoCloser.h
// AutoCloser.h
//
// Author David Barrett-Lennard
// (C)opyright Cedanet Pty Ltd 2022
#pragma once
#ifndef Ceda_cxUtils_AutoCloser_H
#define Ceda_cxUtils_AutoCloser_H
#include "cxUtils.h"
#include "Detect.h"
#include "CedaAssert.h"
#include <memory>
namespace ceda
{
///////////////////////////////////////////////////////////////////////////////////////////////////
// A smart pointer to automatically call Close() on its pointer when it destructs.
//
// Typically declared on the frame, ensuring that Close() is called, even when exceptions are
// thrown
//
// Can be used to automatically close any "T" which has a Close() method or free function
// (Streams, Files, etc)
template <typename T> using Close_method_t = decltype(std::declval<T&>().Close());
template <typename T> using has_Close_method = is_detected<Close_method_t, T>;
template<typename T>
struct Closer
{
void operator()(T* p)
{
cxAssert(p != nullptr);
if constexpr (has_Close_method<T>::value)
{
p->Close();
}
else
{
Close(p);
}
}
};
template<typename T>
using close_ptr = std::unique_ptr<T, Closer<T>>;
} // namespace ceda
#endif // include guard