//
-// Copyright (c) 2016-2017 Vinnie Falco (vinnie dot falco at gmail dot com)
+// Copyright (c) 2016-2019 Vinnie Falco (vinnie dot falco at gmail dot com)
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
#ifndef BOOST_BEAST_TYPE_TRAITS_HPP
#define BOOST_BEAST_TYPE_TRAITS_HPP
+#ifndef BOOST_BEAST_DOXYGEN
+
#include <boost/beast/core/detail/config.hpp>
-#include <boost/beast/core/file_base.hpp>
-#include <boost/beast/core/detail/type_traits.hpp>
-#include <boost/asio/buffer.hpp>
-#include <type_traits>
+#include <boost/beast/core/detail/is_invocable.hpp>
+#include <boost/config/pragma_message.hpp>
+#include <type_traits.hpp>
+
+BOOST_PRAGMA_MESSAGE("<boost/beast/core/type_traits.hpp> is DEPRECATED and will be removed in a future release.")
namespace boost {
namespace beast {
-//------------------------------------------------------------------------------
-//
-// Handler concepts
-//
-//------------------------------------------------------------------------------
-
-/** Determine if `T` meets the requirements of @b CompletionHandler.
+/** Determine if `T` meets the requirements of <em>CompletionHandler</em>.
This trait checks whether a type meets the requirements for a completion
handler, and is also callable with the specified signature.
else the type will be `std::false_type`.
@par Example
-
Use with `static_assert`:
-
@code
struct handler
{
void operator()(error_code&);
};
-
static_assert(is_completion_handler<handler, void(error_code&)>::value,
"Not a completion handler");
@endcode
*/
template<class T, class Signature>
#if BOOST_BEAST_DOXYGEN
-using is_completion_handler = std::integral_constant<bool, ...>;
+using is_completion_handler = __see_below__
#else
using is_completion_handler = std::integral_constant<bool,
- std::is_copy_constructible<typename std::decay<T>::type>::value &&
+ std::is_move_constructible<typename std::decay<T>::type>::value &&
detail::is_invocable<T, Signature>::value>;
#endif
-//------------------------------------------------------------------------------
-//
-// Stream concepts
-//
-//------------------------------------------------------------------------------
-
-/** Determine if `T` has the `get_executor` member function.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` has the member
- function with the correct signature, else type will be `std::false_type`.
-
- @par Example
-
- Use with tag dispatching:
-
- @code
- template<class T>
- void maybe_hello(T& t, std::true_type)
- {
- boost::asio::post(
- t.get_executor(),
- []
- {
- std::cout << "Hello, world!" << std::endl;
- });
- }
-
- template<class T>
- void maybe_hello(T&, std::false_type)
- {
- // T does not have get_executor
- }
-
- template<class T>
- void maybe_hello(T& t)
- {
- maybe_hello(t, has_get_executor<T>{});
- }
- @endcode
-
- Use with `static_assert`:
-
- @code
- struct stream
- {
- using executor_type = boost::asio::io_context::executor_type;
- executor_type get_executor() noexcept;
- };
-
- static_assert(has_get_executor<stream>::value, "Missing get_executor member");
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct has_get_executor : std::integral_constant<bool, ...>{};
-#else
-template<class T, class = void>
-struct has_get_executor : std::false_type {};
-
-template<class T>
-struct has_get_executor<T, beast::detail::void_t<decltype(
- std::declval<T&>().get_executor(),
- (void)0)>> : std::true_type {};
-#endif
-
-/** Returns `T::lowest_layer_type` if it exists, else `T`
-
- This will contain a nested `type` equal to `T::lowest_layer_type`
- if it exists, else `type` will be equal to `T`.
-
- @par Example
-
- Declaring a wrapper:
-
- @code
- template<class Stream>
- struct stream_wrapper
- {
- using next_layer_type = typename std::remove_reference<Stream>::type;
- using lowest_layer_type = typename get_lowest_layer<stream_type>::type;
- };
- @endcode
-
- Defining a metafunction:
-
- @code
- /// Alias for `std::true_type` if `T` wraps another stream
- template<class T>
- using is_stream_wrapper : std::integral_constant<bool,
- ! std::is_same<T, typename get_lowest_layer<T>::type>::value> {};
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct get_lowest_layer;
-#else
-template<class T, class = void>
-struct get_lowest_layer
-{
- using type = T;
-};
-
-template<class T>
-struct get_lowest_layer<T, detail::void_t<
- typename T::lowest_layer_type>>
-{
- using type = typename T::lowest_layer_type;
-};
-#endif
-
-/** Determine if `T` meets the requirements of @b AsyncReadStream.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` meets the requirements,
- else the type will be `std::false_type`.
-
- @par Example
-
- Use with `static_assert`:
-
- @code
- template<class AsyncReadStream>
- void f(AsyncReadStream& stream)
- {
- static_assert(is_async_read_stream<AsyncReadStream>::value,
- "AsyncReadStream requirements not met");
- ...
- @endcode
-
- Use with `std::enable_if` (SFINAE):
-
- @code
- template<class AsyncReadStream>
- typename std::enable_if<is_async_read_stream<AsyncReadStream>::value>::type
- f(AsyncReadStream& stream);
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct is_async_read_stream : std::integral_constant<bool, ...>{};
-#else
-template<class T, class = void>
-struct is_async_read_stream : std::false_type {};
-
-template<class T>
-struct is_async_read_stream<T, detail::void_t<decltype(
- std::declval<T>().async_read_some(
- std::declval<detail::MutableBufferSequence>(),
- std::declval<detail::ReadHandler>()),
- (void)0)>> : std::integral_constant<bool,
- has_get_executor<T>::value
- > {};
-#endif
-
-/** Determine if `T` meets the requirements of @b AsyncWriteStream.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` meets the requirements,
- else the type will be `std::false_type`.
-
- @par Example
-
- Use with `static_assert`:
-
- @code
- template<class AsyncWriteStream>
- void f(AsyncWriteStream& stream)
- {
- static_assert(is_async_write_stream<AsyncWriteStream>::value,
- "AsyncWriteStream requirements not met");
- ...
- @endcode
-
- Use with `std::enable_if` (SFINAE):
-
- @code
- template<class AsyncWriteStream>
- typename std::enable_if<is_async_write_stream<AsyncWriteStream>::value>::type
- f(AsyncWriteStream& stream);
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct is_async_write_stream : std::integral_constant<bool, ...>{};
-#else
-template<class T, class = void>
-struct is_async_write_stream : std::false_type {};
-
-template<class T>
-struct is_async_write_stream<T, detail::void_t<decltype(
- std::declval<T>().async_write_some(
- std::declval<detail::ConstBufferSequence>(),
- std::declval<detail::WriteHandler>()),
- (void)0)>> : std::integral_constant<bool,
- has_get_executor<T>::value
- > {};
-#endif
-
-/** Determine if `T` meets the requirements of @b SyncReadStream.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` meets the requirements,
- else the type will be `std::false_type`.
-
- @par Example
-
- Use with `static_assert`:
-
- @code
- template<class SyncReadStream>
- void f(SyncReadStream& stream)
- {
- static_assert(is_sync_read_stream<SyncReadStream>::value,
- "SyncReadStream requirements not met");
- ...
- @endcode
-
- Use with `std::enable_if` (SFINAE):
-
- @code
- template<class SyncReadStream>
- typename std::enable_if<is_sync_read_stream<SyncReadStream>::value>::type
- f(SyncReadStream& stream);
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct is_sync_read_stream : std::integral_constant<bool, ...>{};
-#else
-template<class T, class = void>
-struct is_sync_read_stream : std::false_type {};
-
-template<class T>
-struct is_sync_read_stream<T, detail::void_t<decltype(
- std::declval<std::size_t&>() = std::declval<T>().read_some(
- std::declval<detail::MutableBufferSequence>()),
- std::declval<std::size_t&>() = std::declval<T>().read_some(
- std::declval<detail::MutableBufferSequence>(),
- std::declval<boost::system::error_code&>()),
- (void)0)>> : std::true_type {};
-#endif
-
-/** Determine if `T` meets the requirements of @b SyncWriteStream.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` meets the requirements,
- else the type will be `std::false_type`.
-
- @par Example
-
- Use with `static_assert`:
-
- @code
- template<class SyncReadStream>
- void f(SyncReadStream& stream)
- {
- static_assert(is_sync_read_stream<SyncReadStream>::value,
- "SyncReadStream requirements not met");
- ...
- @endcode
-
- Use with `std::enable_if` (SFINAE):
-
- @code
- template<class SyncReadStream>
- typename std::enable_if<is_sync_read_stream<SyncReadStream>::value>::type
- f(SyncReadStream& stream);
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct is_sync_write_stream : std::integral_constant<bool, ...>{};
-#else
-template<class T, class = void>
-struct is_sync_write_stream : std::false_type {};
-
-template<class T>
-struct is_sync_write_stream<T, detail::void_t<decltype(
- std::declval<std::size_t&>() = std::declval<T&>().write_some(
- std::declval<detail::ConstBufferSequence>()),
- std::declval<std::size_t&>() = std::declval<T&>().write_some(
- std::declval<detail::ConstBufferSequence>(),
- std::declval<boost::system::error_code&>()),
- (void)0)>> : std::true_type {};
-#endif
-
-/** Determine if `T` meets the requirements of @b AsyncStream.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` meets the requirements,
- else the type will be `std::false_type`.
-
- @par Example
-
- Use with `static_assert`:
-
- @code
- template<class AsyncStream>
- void f(AsyncStream& stream)
- {
- static_assert(is_async_stream<AsyncStream>::value,
- "AsyncStream requirements not met");
- ...
- @endcode
-
- Use with `std::enable_if` (SFINAE):
-
- @code
- template<class AsyncStream>
- typename std::enable_if<is_async_stream<AsyncStream>::value>::type
- f(AsyncStream& stream);
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct is_async_stream : std::integral_constant<bool, ...>{};
-#else
-template<class T>
-using is_async_stream = std::integral_constant<bool,
- is_async_read_stream<T>::value && is_async_write_stream<T>::value>;
-#endif
-
-/** Determine if `T` meets the requirements of @b SyncStream.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` meets the requirements,
- else the type will be `std::false_type`.
-
- @par Example
-
- Use with `static_assert`:
-
- @code
- template<class SyncStream>
- void f(SyncStream& stream)
- {
- static_assert(is_sync_stream<SyncStream>::value,
- "SyncStream requirements not met");
- ...
- @endcode
-
- Use with `std::enable_if` (SFINAE):
-
- @code
- template<class SyncStream>
- typename std::enable_if<is_sync_stream<SyncStream>::value>::type
- f(SyncStream& stream);
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct is_sync_stream : std::integral_constant<bool, ...>{};
-#else
-template<class T>
-using is_sync_stream = std::integral_constant<bool,
- is_sync_read_stream<T>::value && is_sync_write_stream<T>::value>;
-#endif
-
-//------------------------------------------------------------------------------
-//
-// File concepts
-//
-//------------------------------------------------------------------------------
-
-/** Determine if `T` meets the requirements of @b File.
-
- Metafunctions are used to perform compile time checking of template
- types. This type will be `std::true_type` if `T` meets the requirements,
- else the type will be `std::false_type`.
-
- @par Example
-
- Use with `static_assert`:
-
- @code
- template<class File>
- void f(File& file)
- {
- static_assert(is_file<File>::value,
- "File requirements not met");
- ...
- @endcode
-
- Use with `std::enable_if` (SFINAE):
-
- @code
- template<class File>
- typename std::enable_if<is_file<File>::value>::type
- f(File& file);
- @endcode
-*/
-#if BOOST_BEAST_DOXYGEN
-template<class T>
-struct is_file : std::integral_constant<bool, ...>{};
-#else
-template<class T, class = void>
-struct is_file : std::false_type {};
-
-template<class T>
-struct is_file<T, detail::void_t<decltype(
- std::declval<bool&>() = std::declval<T const&>().is_open(),
- std::declval<T&>().close(std::declval<error_code&>()),
- std::declval<T&>().open(
- std::declval<char const*>(),
- std::declval<file_mode>(),
- std::declval<error_code&>()),
- std::declval<std::uint64_t&>() = std::declval<T&>().size(
- std::declval<error_code&>()),
- std::declval<std::uint64_t&>() = std::declval<T&>().pos(
- std::declval<error_code&>()),
- std::declval<T&>().seek(
- std::declval<std::uint64_t>(),
- std::declval<error_code&>()),
- std::declval<std::size_t&>() = std::declval<T&>().read(
- std::declval<void*>(),
- std::declval<std::size_t>(),
- std::declval<error_code&>()),
- std::declval<std::size_t&>() = std::declval<T&>().write(
- std::declval<void const*>(),
- std::declval<std::size_t>(),
- std::declval<error_code&>()),
- (void)0)>> : std::integral_constant<bool,
- std::is_default_constructible<T>::value &&
- std::is_destructible<T>::value
- > {};
-#endif
-
} // beast
} // boost
#endif
+
+#endif