Repository: conan-io/conan-center-index

Issue:
[request] continuable/4.0.0
### Package Details
  * Package Name/Version: **continuable/4.0.0**
  * Website: **https://naios.github.io/continuable**
  * Source code: **https://github.com/Naios/continuable**


### Description Of The Library / Tool
C++14 asynchronous allocation aware futures (supporting then, exception handling, coroutines and connections).  Header only.

The source code contains a recipe.  Since it's CMake and header only it should be an easy port.


Discussion:

Resolving patch:
diff --git a/recipes/continuable/all/conanfile.py b/recipes/continuable/all/conanfile.py
new file mode 100644
--- /dev/null
+++ b/recipes/continuable/all/conanfile.py
@@ -0,0 +1,92 @@
+import os
+
+from conans import ConanFile, tools
+from conans.errors import ConanInvalidConfiguration
+
+
+required_conan_version = ">=1.28.0"
+
+
+class ContinuableConan(ConanFile):
+    name = "continuable"
+    description = "C++14 asynchronous allocation aware futures (supporting then, exception handling, coroutines and connections)"
+    topics = "asynchronous", "future", "coroutines", "header-only"
+    url = "https://github.com/conan-io/conan-center-index"
+    homepage = "https://github.com/Naios/continuable"
+    license = "MIT"
+    settings = "os", "compiler"
+    no_copy_source = True
+    requires = (
+        "function2/4.1.0",
+    )
+    options = {
+        # Exceptions are disabled and `std::error_condition` is used as error_type. See tutorial-chaining-continuables-fail for details.
+        "no_exceptions": [True, False],
+        # Exceptions are disabled and the type defined by `CONTINUABLE_WITH_CUSTOM_ERROR_TYPE` is used as error_type.
+        # See tutorial-chaining-continuables-fail for details.
+        "custom_error_type": [True, False],
+        # Allows unhandled exceptions in asynchronous call hierarchies. See tutorial-chaining-continuables-fail for details.
+        "unhandled_exceptions": [True, False],
+        # Allows to customize the final callback which can be used to implement custom unhandled asynchronous exception handlers.
+        "custom_final_callback": [True, False],
+        # Don"t decorate the used type erasure, which is done to keep type names minimal for better error messages in debug builds.
+        "immediate_types": [True, False],
+    }
+    default_options = {
+        "no_exceptions": False,
+        "custom_error_type": False,
+        "unhandled_exceptions": False,
+        "custom_final_callback": False,
+        "immediate_types": False
+    }
+
+    @property
+    def _source_subfolder(self):
+        return "source_subfolder"
+
+    def validate(self):
+        minimal_cpp_standard = "14"
+        if self.settings.compiler.cppstd:
+            tools.check_min_cppstd(self, minimal_cpp_standard)
+        minimal_version = {
+            "gcc": "5",
+            "clang": "3.4",
+            "apple-clang": "10",
+            "Visual Studio": "14"
+        }
+        compiler = str(self.settings.compiler)
+        if compiler not in minimal_version:
+            self.output.warn(
+                "%s recipe lacks information about the %s compiler standard version support" % (self.name, compiler))
+            self.output.warn(
+                "%s requires a compiler that supports at least C++%s" % (self.name, minimal_cpp_standard))
+            return
+        version = tools.Version(self.settings.compiler.version)
+        if version < minimal_version[compiler]:
+            raise ConanInvalidConfiguration("%s requires a compiler that supports at least C++%s" % (self.name, minimal_cpp_standard))
+
+    def source(self):
+        tools.get(**self.conan_data["sources"][self.version])
+        extracted_dir = "continuable-" + self.version
+        os.rename(extracted_dir, self._source_subfolder)
+
+    def package(self):
+        self.copy(pattern="LICENSE.txt", dst="licenses", src=self._source_subfolder)
+        self.copy(pattern="*", dst=os.path.join("include", "continuable"), src=os.path.join(self._source_subfolder, "include", "continuable"))
+
+    def package_info(self):
+        if self.settings.os == "Linux":
+            self.cpp_info.system_libs.append("pthread")
+        if self.options.no_exceptions:
+            self.cpp_info.defines.append("CONTINUABLE_WITH_NO_EXCEPTIONS")
+        if self.options.custom_error_type:
+            self.cpp_info.defines.append("CONTINUABLE_WITH_CUSTOM_ERROR_TYPE")
+        if self.options.unhandled_exceptions:
+            self.cpp_info.defines.append("CONTINUABLE_WITH_UNHANDLED_EXCEPTIONS")
+        if self.options.custom_final_callback:
+            self.cpp_info.defines.append("CONTINUABLE_WITH_CUSTOM_FINAL_CALLBACK")
+        if self.options.immediate_types:
+            self.cpp_info.defines.append("CONTINUABLE_WITH_IMMEDIATE_TYPES")
+
+    def package_id(self):
+        self.info.header_only()


Test patch:
diff --git a/recipes/continuable/all/test_package/CMakeLists.txt b/recipes/continuable/all/test_package/CMakeLists.txt
new file mode 100644
--- /dev/null
+++ b/recipes/continuable/all/test_package/CMakeLists.txt
@@ -0,0 +1,14 @@
+cmake_minimum_required(VERSION 3.1)
+project(test_package)
+
+include(${CMAKE_BINARY_DIR}/conanbuildinfo.cmake)
+conan_basic_setup()
+
+add_executable(${PROJECT_NAME} test_package.cpp)
+set_target_properties(
+    ${PROJECT_NAME} PROPERTIES
+
+    CXX_STANDARD 14
+    CXX_STANDARD_REQUIRED ON
+)
+target_link_libraries(${PROJECT_NAME} ${CONAN_LIBS})
diff --git a/recipes/continuable/all/test_package/conanfile.py b/recipes/continuable/all/test_package/conanfile.py
new file mode 100644
--- /dev/null
+++ b/recipes/continuable/all/test_package/conanfile.py
@@ -0,0 +1,17 @@
+from conans import ConanFile, CMake, tools
+import os
+
+
+class TestPackageConan(ConanFile):
+    settings = "os", "compiler", "build_type", "arch"
+    generators = "cmake"
+
+    def build(self):
+        cmake = CMake(self)
+        cmake.configure()
+        cmake.build()
+
+    def test(self):
+        if not tools.cross_building(self.settings):
+            bin_path = os.path.join("bin", "test_package")
+            self.run(bin_path, run_environment=True)
diff --git a/recipes/continuable/all/test_package/test_package.cpp b/recipes/continuable/all/test_package/test_package.cpp
new file mode 100644
--- /dev/null
+++ b/recipes/continuable/all/test_package/test_package.cpp
@@ -0,0 +1,9 @@
+#include <string>
+
+#include "continuable/continuable.hpp"
+
+int main(int, char**) {
+    cti::make_ready_continuable<std::string>("<html>...</html>");
+
+    return 0;
+}