WebCFace 2.9.0
Web-based Communication Framework & Dashboard-like UI
Loading...
Searching...
No Matches
func.h
Go to the documentation of this file.
1#pragma once
3#include "func_result.h"
4#include "arg.h"
5#include "trait.h"
6
8namespace internal {
9struct FuncInfo;
10}
11
12namespace traits {
13template <typename T>
14constexpr auto getInvokeSignature(T &&) -> decltype(&T::operator()) {
15 return &T::operator();
16}
17template <typename Ret, typename... Args>
18constexpr auto getInvokeSignature(Ret (*p)(Args...)) {
19 return p;
20}
21template <typename T>
23 decltype(getInvokeSignature(std::declval<std::decay_t<T>>()));
24
25template <bool>
27template <>
28struct FuncArgTypeCheck<true> {
30};
31template <typename... Args>
33 : FuncArgTypeCheck<(std::is_convertible_v<ValAdaptor, Args> && ...)> {};
34
35template <bool>
37template <>
38struct FuncReturnTypeCheck<true> {
40};
41template <typename Ret>
43 : FuncReturnTypeCheck<std::is_same_v<Ret, void> ||
44 std::is_constructible_v<ValAdaptor, Ret>> {};
45
46template <typename T>
55template <typename Ret, typename... Args>
56struct FuncSignatureTrait<Ret(Args...)> {
59 static constexpr bool return_void = std::is_same_v<Ret, void>;
60 static inline bool assertArgsNum(const CallHandle &handle) {
61 return handle.assertArgsNum(sizeof...(Args));
62 }
63 static inline std::vector<Arg> argsInfo() {
64 return std::vector<Arg>{Arg{valTypeOf<Args>()}...};
65 }
66 using ReturnType = Ret;
67 using ArgsTuple = std::tuple<std::decay_t<Args>...>;
68};
69template <typename Ret, typename T, typename... Args>
70struct FuncSignatureTrait<Ret (T::*)(Args...)>
71 : FuncSignatureTrait<Ret(Args...)> {};
72template <typename Ret, typename T, typename... Args>
73struct FuncSignatureTrait<Ret (T::*)(Args...) const>
74 : FuncSignatureTrait<Ret(Args...)> {};
75template <typename Ret, typename... Args>
76struct FuncSignatureTrait<Ret (*)(Args...)> : FuncSignatureTrait<Ret(Args...)> {
77};
78
86template <typename T>
88
89} // namespace traits
90
95class WEBCFACE_DLL Func : protected Field {
96 public:
99
100 Func() = default;
101 Func(const Field &base);
102 Func(const Field &base, const SharedString &field)
103 : Func(Field{base, field}) {}
104
105 using Field::lastName;
106 using Field::member;
107 using Field::name;
108 using Field::nameW;
113 Func child(std::string_view field) const {
114 return this->Field::child(field);
115 }
120 Func child(std::wstring_view field) const {
121 return this->Field::child(field);
122 }
127 [[deprecated]]
128 Func child(int index) const {
129 return this->Field::child(std::to_string(index));
130 }
135 Func operator[](std::string_view field) const { return child(field); }
140 Func operator[](std::wstring_view field) const { return child(field); }
145 Func operator[](const char *field) const { return child(field); }
149 Func operator[](const wchar_t *field) const { return child(field); }
155 [[deprecated]]
156 Func operator[](int index) const {
157 return child(std::to_string(index));
158 }
163 Func parent() const { return this->Field::parent(); }
164
166
167 protected:
172 const Func &setImpl(ValType return_type, std::vector<Arg> &&args,
173 std::function<FuncType> &&func_impl) const;
178 const Func &setImpl(ValType return_type, std::nullopt_t,
179 std::function<FuncType> &&func_impl) const;
180 const Func &
181 setImpl(const std::shared_ptr<internal::FuncInfo> &func_info) const;
182
187 template <typename F1>
188 static void catchAll(F1 &&f_run, const CallHandle &handle) {
189 ValAdaptor error;
190 try {
191 f_run();
192 return;
193 } catch (const std::exception &e) {
194 error = e.what();
195 } catch (const std::string &e) {
196 error = e;
197 } catch (const char *e) {
198 error = e;
199 } catch (const std::wstring &e) {
200 error = e;
201 } catch (const wchar_t *e) {
202 error = e;
203 } catch (...) {
204 error = "unknown exception";
205 }
206 handle.reject(error);
207 }
212 template <typename F1>
213 static void tryRun(F1 &&f_run, const CallHandle &handle) {
214 catchAll([&] { handle.respond(f_run()); }, handle);
215 }
216
217 public:
231 template <typename T,
233 ReturnTypeSupportedByWebCFaceFunc = traits::TraitOk,
235 ArgTypesSupportedByWebCFaceFunc = traits::TraitOk>
236 const Func &set(T func) const {
237 return setImpl(
240 [func = std::move(func)](const CallHandle &handle) {
242 typename traits::FuncObjTrait<T>::ArgsTuple args_tuple;
243 argToTuple(handle.args(), args_tuple);
244 tryRun(
245 [&] {
246 if constexpr (traits::FuncObjTrait<
247 T>::return_void) {
248 std::apply(func, args_tuple);
249 return ValAdaptor::emptyVal();
250 } else {
251 auto ret = std::apply(func, args_tuple);
252 return ret;
253 }
254 },
255 handle);
256 }
257 });
258 }
272 template <typename T,
274 ReturnTypeSupportedByWebCFaceFunc = traits::TraitOk,
276 ArgTypesSupportedByWebCFaceFunc = traits::TraitOk>
277 const Func &setAsync(T func) const {
278 return setImpl(
281 [func_p = std::make_shared<T>(std::move(func))](
282 const CallHandle &handle) {
284 typename traits::FuncObjTrait<T>::ArgsTuple args_tuple;
285 argToTuple(handle.args(), args_tuple);
286 std::thread(
287 [func_p, handle](auto args_tuple) {
288 tryRun(
289 [&] {
290 if constexpr (traits::FuncObjTrait<
291 T>::return_void) {
292 std::apply(*func_p, args_tuple);
293 return ValAdaptor::emptyVal();
294 } else {
295 auto ret =
296 std::apply(*func_p, args_tuple);
297 return ret;
298 }
299 },
300 handle);
301 },
302 std::move(args_tuple))
303 .detach();
304 }
305 });
306 }
317 template <typename T>
318 [[deprecated("use set() or setAsync()")]] const Func &
319 operator=(T func) const {
320 this->set(std::move(func));
321 return *this;
322 }
323
343 template <typename T,
344 typename std::enable_if_t<
345 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
346 std::nullptr_t> = nullptr>
347 const Func &set(std::vector<Arg> args, ValType return_type,
348 T callback) const {
349 auto args_size = args.size();
350 return setImpl(return_type, std::move(args),
351 [args_size, callback = std::move(callback)](
352 const CallHandle &handle) {
353 if (handle.assertArgsNum(args_size)) {
354 catchAll([&] { callback(handle); }, handle);
355 }
356 });
357 }
375 template <typename T,
376 typename std::enable_if_t<
377 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
378 std::nullptr_t> = nullptr>
379 const Func &setAsync(std::vector<Arg> args, ValType return_type,
380 T callback) const {
381 auto args_size = args.size();
382 return setImpl(
383 return_type, std::move(args),
384 [args_size,
385 callback = std::make_shared<std::function<void(FuncCallHandle)>>(
386 std::move(callback))](const CallHandle &handle) {
387 if (handle.assertArgsNum(args_size)) {
388 std::thread([callback, handle] {
389 catchAll([&] { callback->operator()(handle); }, handle);
390 }).detach();
391 }
392 });
393 }
410 template <typename T,
411 typename std::enable_if_t<
412 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
413 std::nullptr_t> = nullptr>
414 const Func &set(T callback) const {
415 return setImpl(ValType::none_, std::nullopt,
416 [base = *this, callback = std::move(callback)](
417 const CallHandle &handle) {
418 if (handle.assertArgsNum(base.args().size())) {
419 catchAll([&] { callback(handle); }, handle);
420 }
421 });
422 }
439 template <typename T,
440 typename std::enable_if_t<
441 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
442 std::nullptr_t> = nullptr>
443 const Func &setAsync(T callback) const {
444 return setImpl(
445 ValType::none_, std::nullopt,
446 [base = *this,
447 callback = std::make_shared<std::function<void(FuncCallHandle)>>(
448 std::move(callback))](const CallHandle &handle) {
449 if (handle.assertArgsNum(base.args().size())) {
450 std::thread([callback, handle] {
451 catchAll([&] { callback->operator()(handle); }, handle);
452 }).detach();
453 }
454 });
455 }
456
465 [[deprecated("Func::hidden() does nothing since ver1.10")]]
466 const Func &hidden(bool) const {
467 return *this;
468 }
469
474 const Func &free() const;
475
488 template <typename... Args>
489 [[deprecated("use runAsync")]]
490 ValAdaptor run(Args... args) const {
491 return run({ValAdaptor(args)...});
492 }
493 [[deprecated("use runAsync")]]
494 ValAdaptor run(std::vector<ValAdaptor> &&args_vec) const {
495 auto p = runAsync(std::move(args_vec));
496 p.waitFinish();
497 if (p.found()) {
498 if (p.isError()) {
499 throw std::runtime_error(p.rejection());
500 } else {
501 return p.response();
502 }
503 } else {
504 throw FuncNotFound(*this);
505 }
506 }
511 template <typename... Args>
512 [[deprecated("use runAsync")]]
513 ValAdaptor operator()(Args... args) const {
514 return run(args...);
515 }
516
530 template <typename... Args>
531 Promise runAsync(Args... args) const {
532 return runAsync({ValAdaptor(args)...});
533 }
534 Promise runAsync(std::vector<ValAdaptor> args_vec) const;
535
541 bool exists() const;
549 int index() const;
561 const Func &setIndex(int index) const;
562
567 ValType returnType() const;
574 std::vector<Arg> args() const;
575
576 const Arg args(std::size_t i) const { return args().at(i); }
577
591 const Func &setArgs(const std::vector<Arg> &args) const;
601 const Func &setReturnType(ValType return_type) const;
602
607 template <typename T, typename std::enable_if_t<std::is_same_v<T, Func>,
608 std::nullptr_t> = nullptr>
609 bool operator==(const T &other) const {
610 return static_cast<Field>(*this) == static_cast<Field>(other);
611 }
612 template <typename T, typename std::enable_if_t<std::is_same_v<T, Func>,
613 std::nullptr_t> = nullptr>
614 bool operator!=(const T &other) const {
615 return static_cast<Field>(*this) != static_cast<Field>(other);
616 }
617};
618
619class WEBCFACE_DLL FuncListener : protected Func {
620 ValType return_type_ = ValType::none_;
621 std::vector<Arg> args_{};
622
623 public:
624 FuncListener() = default;
625 FuncListener(const Field &base);
626 FuncListener(const Field &base, const SharedString &field)
627 : FuncListener(Field{base, field}) {}
628
631 using Field::member;
632 using Field::name;
633
638 FuncListener &listen();
645 FuncListener &listen(std::size_t args_num,
646 ValType return_type = ValType::none_) {
647 this->args_.resize(args_num);
648 this->return_type_ = return_type;
649 listen();
650 return *this;
651 }
652
659 FuncListener &setArgs(const std::vector<Arg> &args) {
660 this->args_ = args;
661 return *this;
662 }
670 this->return_type_ = type;
671 return *this;
672 }
673
682 [[deprecated("FuncListener::hidden() does nothing since ver1.10")]]
684 return *this;
685 }
696 std::optional<FuncCallHandle> fetchCall() const;
697};
698
引数の情報を表す。
Definition arg.h:30
呼び出された関数の引数の取得と戻り値のセットをするインタフェース
Definition func_result.h:323
void respond(const ValAdaptor &value) const
Definition func_result.cc:83
const std::vector< ValAdaptor > & args() const
関数の引数を取得する
Definition func_result.cc:332
void reject(const ValAdaptor &message) const
Definition func_result.cc:101
bool assertArgsNum(std::size_t expected) const
引数の数をチェックする
Definition func_result.cc:123
Definition func.h:619
FuncListener(const Field &base, const SharedString &field)
Definition func.h:626
FuncListener & setReturnType(ValType type)
戻り値の型をセットする
Definition func.h:669
FuncListener & setArgs(const std::vector< Arg > &args)
引数の情報をセットする
Definition func.h:659
FuncListener & hidden(bool)
関数を関数リストで非表示にする (他clientのentryに表示されなくする)
Definition func.h:683
FuncListener & listen(std::size_t args_num, ValType return_type=ValType::none_)
関数呼び出しの待受を開始する
Definition func.h:645
関数1つを表すクラス
Definition func.h:95
ValAdaptor operator()(Args... args) const
run()と同じ
Definition func.h:513
Func child(std::wstring_view field) const
「(thisの名前).(追加の名前)」を新しい名前とするField (wstring)
Definition func.h:120
bool operator==(const T &other) const
Funcの参照先を比較
Definition func.h:609
const Func & setAsync(T func) const
非同期に実行される関数をセットする
Definition func.h:277
const Func & setAsync(T callback) const
引数にFuncCallHandleを取り非同期に実行される関数を登録する
Definition func.h:443
ValAdaptor run(Args... args) const
関数を実行する (同期)
Definition func.h:490
const Func & hidden(bool) const
関数を関数リストで非表示にする (他clientのentryに表示されなくする)
Definition func.h:466
Func child(std::string_view field) const
「(thisの名前).(追加の名前)」を新しい名前とするField
Definition func.h:113
const Func & setAsync(std::vector< Arg > args, ValType return_type, T callback) const
引数にFuncCallHandleを取り非同期に実行される関数を登録する
Definition func.h:379
Func child(int index) const
Definition func.h:128
void(CallHandle) FuncType
Definition func.h:165
Func operator[](std::string_view field) const
Definition func.h:135
const Arg args(std::size_t i) const
Definition func.h:576
const Func & operator=(T func) const
関数をセットする
Definition func.h:319
Func()=default
static void catchAll(F1 &&f_run, const CallHandle &handle)
Definition func.h:188
bool operator!=(const T &other) const
Definition func.h:614
Func operator[](const wchar_t *field) const
Definition func.h:149
Func operator[](std::wstring_view field) const
Definition func.h:140
const Func & set(std::vector< Arg > args, ValType return_type, T callback) const
引数にCallHandleを取る関数を登録する
Definition func.h:347
Func(const Field &base, const SharedString &field)
Definition func.h:102
ValAdaptor run(std::vector< ValAdaptor > &&args_vec) const
Definition func.h:494
static void tryRun(F1 &&f_run, const CallHandle &handle)
Definition func.h:213
const Func & set(T func) const
関数をセットする
Definition func.h:236
const Func & set(T callback) const
引数にCallHandleを取る関数を登録する
Definition func.h:414
Func parent() const
nameの最後のピリオドの前までを新しい名前とするField
Definition func.h:163
Func operator[](int index) const
Definition func.h:156
Func operator[](const char *field) const
Definition func.h:145
Promise runAsync(Args... args) const
関数を実行する (非同期)
Definition func.h:531
非同期で実行した関数の実行結果を取得するインタフェース。
Definition func_result.h:50
u8stringとstringとwstringをshared_ptrで持ち共有する
Definition encoding.h:67
Definition component_canvas2d.h:139
Viewを構築するときに使う一時的なViewComponent.
Definition component_view.h:286
数値、文字列などの値を相互変換するクラス
Definition val_adaptor.h:87
static const ValAdaptor & emptyVal()
Definition val_adaptor.cc:6
std::nullptr_t TraitOkType
Definition trait.h:11
decltype(getInvokeSignature(std::declval< std::decay_t< T > >())) InvokeSignature
Definition func.h:23
constexpr std::nullptr_t TraitOk
Definition trait.h:12
constexpr auto getInvokeSignature(T &&) -> decltype(&T::operator())
Definition func.h:14
void argToTuple(const std::vector< ValAdaptor > &args, T &tuple)
ValAdaptorのリストから任意の型のタプルに変換する
Definition val_adaptor.h:331
ValType
引数や戻り値の型を表すenum
Definition val_adaptor.h:21
ValType valTypeOf()
TのValTypeを得る
Definition val_adaptor.h:34
ClientDataの参照とメンバ名とデータ名を持つクラス
Definition field.h:71
Field parent() const
nameの最後のピリオドの前までを新しい名前とするField
Definition field.cc:33
Field child(const SharedString &field) const
Definition field.cc:42
Funcの実行ができなかった場合発生する例外
Definition func_result.h:32
TraitOkType ArgTypesSupportedByWebCFaceFunc
Definition func.h:29
TraitOkType ReturnTypeSupportedByWebCFaceFunc
Definition func.h:39
static std::vector< Arg > argsInfo()
Definition func.h:63
static bool assertArgsNum(const CallHandle &handle)
Definition func.h:60
std::tuple< std::decay_t< Args >... > ArgsTuple
Definition func.h:67
#define WEBCFACE_DLL
Definition webcface-config.h:69
#define WEBCFACE_NS_END
Definition webcface-config.h:118
#define WEBCFACE_NS_BEGIN
Definition webcface-config.h:117
#define WEBCFACE_CALL_FP
Definition webcface-config.h:107