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#include "func_trait.h"
7#include "exception.h"
8
10namespace internal {
11struct FuncInfo;
12}
13
14namespace traits {
15template <typename BadArg>
17template <typename BadArg>
21};
22// MSVCでexplicitな変換operatorがあるとき
23// std::is_constructible_t<Arg, ValAdaptor> が正しくtrueを返さないため、
24// decltypeで実装している
25template <typename Arg, typename = void>
26struct IsConstructibleArg : std::false_type {};
27template <>
28struct IsConstructibleArg<ValAdaptor, void> : std::true_type {};
29template <typename Arg>
31 std::void_t<decltype(std::declval<ValAdaptor>().operator Arg())>>
32 : std::true_type {};
33
34template <typename... Args>
36template <>
38 struct ArgTypesCheckResult {
40 };
41};
42template <typename FirstArg, typename... OtherArgs>
43struct FuncArgTypesIterationTrait<FirstArg, OtherArgs...> {
44 using ArgTypesCheckResult = typename std::conditional_t<
46 FuncArgTypesIterationTrait<OtherArgs...>,
48};
49template <typename... Args>
51 typename FuncArgTypesIterationTrait<Args...>::ArgTypesCheckResult;
52
53template <typename BadArg>
57};
58template <typename Ret>
59using FuncReturnTypeTrait = std::conditional_t<
60 std::disjunction_v<std::is_void<Ret>,
61 std::is_constructible<ValAdaptor, Ret>>,
64
72template <typename T>
74template <typename Ret, typename... Args>
75struct FuncSignatureTrait<Ret(Args...)> : InvokeSignatureTrait<Ret(Args...)> {
78 static constexpr bool return_void = std::is_void_v<Ret>;
79 static inline bool assertArgsNum(const CallHandle &handle) {
80 return handle.assertArgsNum(sizeof...(Args));
81 }
82 static inline std::vector<Arg> argsInfo() {
83 return std::vector<Arg>{Arg{valTypeOf<Args>()}...};
84 }
85};
86template <typename Ret, typename T, typename... Args>
87struct FuncSignatureTrait<Ret (T::*)(Args...)>
88 : FuncSignatureTrait<Ret(Args...)> {};
89template <typename Ret, typename T, typename... Args>
90struct FuncSignatureTrait<Ret (T::*)(Args...) const>
91 : FuncSignatureTrait<Ret(Args...)> {};
92template <typename Ret, typename... Args>
93struct FuncSignatureTrait<Ret (*)(Args...)> : FuncSignatureTrait<Ret(Args...)> {
94};
95
96template <typename T>
98 std::declval<std::decay_t<T>>()))>;
99
100} // namespace traits
101
106class WEBCFACE_DLL Func : protected Field {
107 public:
110
111 Func() = default;
112 Func(const Field &base);
113 Func(const Field &base, const SharedString &field)
114 : Func(Field{base, field}) {}
115
116 using Field::lastName;
117 using Field::member;
118 using Field::name;
119 using Field::nameW;
127 return this->Field::child(static_cast<SharedString &>(field));
128 }
133 [[deprecated]]
134 Func child(int index) const {
135 return this->Field::child(std::to_string(index));
136 }
145 return child(std::move(field));
146 }
152 [[deprecated]]
153 Func operator[](int index) const {
154 return child(std::to_string(index));
155 }
160 Func parent() const { return this->Field::parent(); }
161
163
164 protected:
169 const Func &setImpl(ValType return_type, std::vector<Arg> &&args,
170 std::function<FuncType> &&func_impl) const;
175 const Func &setImpl(ValType return_type, std::nullopt_t,
176 std::function<FuncType> &&func_impl) const;
177 const Func &
178 setImpl(const std::shared_ptr<internal::FuncInfo> &func_info) const;
179
184 template <typename F1>
185 static void catchAll(F1 &&f_run, const CallHandle &handle) {
186 ValAdaptor error;
187 try {
188 f_run();
189 return;
190 } catch (const std::exception &e) {
191 error = e.what();
192 } catch (const std::string &e) {
193 error = e;
194 } catch (const char *e) {
195 error = e;
196 } catch (const std::wstring &e) {
197 error = e;
198 } catch (const wchar_t *e) {
199 error = e;
200 } catch (...) {
201 error = "unknown exception";
202 }
203 handle.reject(error);
204 }
209 template <typename F1>
210 static void tryRun(F1 &&f_run, const CallHandle &handle) {
211 catchAll([&] { handle.respond(f_run()); }, handle);
212 }
213
214 public:
228 template <typename T,
229 typename traits::FuncObjTrait<
230 T>::ReturnTypeTrait::FuncReturnTypeCheckOk = traits::TraitOk,
232 traits::TraitOk>
233 const Func &set(T func) const {
234 return setImpl(
237 [func = std::move(func)](const CallHandle &handle) {
239 typename traits::FuncObjTrait<T>::ArgsTuple args_tuple;
240 argToTuple(handle.args(), args_tuple);
241 tryRun(
242 [&] {
243 if constexpr (traits::FuncObjTrait<
244 T>::return_void) {
245 std::apply(func, args_tuple);
246 return ValAdaptor();
247 } else {
248 auto ret = std::apply(func, args_tuple);
249 return ret;
250 }
251 },
252 handle);
253 }
254 });
255 }
269 template <typename T,
270 typename traits::FuncObjTrait<
271 T>::ReturnTypeTrait::FuncReturnTypeCheckOk = traits::TraitOk,
273 traits::TraitOk>
274 const Func &setAsync(T func) const {
275 return setImpl(
278 [func_p = std::make_shared<T>(std::move(func))](
279 const CallHandle &handle) {
281 typename traits::FuncObjTrait<T>::ArgsTuple args_tuple;
282 argToTuple(handle.args(), args_tuple);
283 std::thread(
284 [func_p, handle](auto args_tuple) {
285 tryRun(
286 [&] {
287 if constexpr (traits::FuncObjTrait<
288 T>::return_void) {
289 std::apply(*func_p, args_tuple);
290 return ValAdaptor();
291 } else {
292 auto ret =
293 std::apply(*func_p, args_tuple);
294 return ret;
295 }
296 },
297 handle);
298 },
299 std::move(args_tuple))
300 .detach();
301 }
302 });
303 }
314 template <typename T>
315 [[deprecated("use set() or setAsync()")]]
316 const Func &operator=(T func) const {
317 this->set(std::move(func));
318 return *this;
319 }
320
340 template <typename T,
341 typename std::enable_if_t<
342 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
343 std::nullptr_t> = nullptr>
344 const Func &set(std::vector<Arg> args, ValType return_type,
345 T callback) const {
346 auto args_size = args.size();
347 return setImpl(return_type, std::move(args),
348 [args_size, callback = std::move(callback)](
349 const CallHandle &handle) {
350 if (handle.assertArgsNum(args_size)) {
351 catchAll([&] { callback(handle); }, handle);
352 }
353 });
354 }
372 template <typename T,
373 typename std::enable_if_t<
374 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
375 std::nullptr_t> = nullptr>
376 const Func &setAsync(std::vector<Arg> args, ValType return_type,
377 T callback) const {
378 auto args_size = args.size();
379 return setImpl(
380 return_type, std::move(args),
381 [args_size,
382 callback = std::make_shared<std::function<void(FuncCallHandle)>>(
383 std::move(callback))](const CallHandle &handle) {
384 if (handle.assertArgsNum(args_size)) {
385 std::thread([callback, handle] {
386 catchAll([&] { callback->operator()(handle); }, handle);
387 }).detach();
388 }
389 });
390 }
407 template <typename T,
408 typename std::enable_if_t<
409 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
410 std::nullptr_t> = nullptr>
411 const Func &set(T callback) const {
412 return setImpl(ValType::none_, std::nullopt,
413 [base = *this, callback = std::move(callback)](
414 const CallHandle &handle) {
415 if (handle.assertArgsNum(base.args().size())) {
416 catchAll([&] { callback(handle); }, handle);
417 }
418 });
419 }
436 template <typename T,
437 typename std::enable_if_t<
438 std::is_same_v<std::invoke_result_t<T, CallHandle>, void>,
439 std::nullptr_t> = nullptr>
440 const Func &setAsync(T callback) const {
441 return setImpl(
442 ValType::none_, std::nullopt,
443 [base = *this,
444 callback = std::make_shared<std::function<void(FuncCallHandle)>>(
445 std::move(callback))](const CallHandle &handle) {
446 if (handle.assertArgsNum(base.args().size())) {
447 std::thread([callback, handle] {
448 catchAll([&] { callback->operator()(handle); }, handle);
449 }).detach();
450 }
451 });
452 }
453
462 [[deprecated("Func::hidden() does nothing since ver1.10")]]
463 const Func &hidden(bool) const {
464 return *this;
465 }
466
471 const Func &free() const;
472
485 template <typename... Args>
486 [[deprecated("use runAsync")]]
487 ValAdaptor run(Args... args) const {
488 return run({ValAdaptor(args)...});
489 }
490 [[deprecated("use runAsync")]]
491 ValAdaptor run(std::vector<ValAdaptor> &&args_vec) const {
492 auto p = runAsync(std::move(args_vec));
493 p.waitFinish();
494 if (p.found()) {
495 if (p.isError()) {
496 throw Rejection(*this, std::string(p.rejection()));
497 } else {
498 return p.response();
499 }
500 } else {
501 throw FuncNotFound(*this);
502 }
503 }
508 template <typename... Args>
509 [[deprecated("use runAsync")]]
510 ValAdaptor operator()(Args... args) const {
511 return run(args...);
512 }
513
527 template <typename... Args>
528 Promise runAsync(Args... args) const {
529 return runAsync({ValAdaptor(args)...});
530 }
531 Promise runAsync(std::vector<ValAdaptor> args_vec) const;
532
538 bool exists() const;
546 int index() const;
558 const Func &setIndex(int index) const;
559
564 ValType returnType() const;
571 std::vector<Arg> args() const;
572
573 const Arg args(std::size_t i) const { return args().at(i); }
574
588 const Func &setArgs(const std::vector<Arg> &args) const;
598 const Func &setReturnType(ValType return_type) const;
599
604 template <typename T, typename std::enable_if_t<std::is_same_v<T, Func>,
605 std::nullptr_t> = nullptr>
606 bool operator==(const T &other) const {
607 return static_cast<Field>(*this) == static_cast<Field>(other);
608 }
609 template <typename T, typename std::enable_if_t<std::is_same_v<T, Func>,
610 std::nullptr_t> = nullptr>
611 bool operator!=(const T &other) const {
612 return static_cast<Field>(*this) != static_cast<Field>(other);
613 }
614};
615
616class WEBCFACE_DLL FuncListener : protected Func {
617 ValType return_type_ = ValType::none_;
618 std::vector<Arg> args_{};
619
620 public:
621 FuncListener() = default;
622 FuncListener(const Field &base);
623 FuncListener(const Field &base, const SharedString &field)
624 : FuncListener(Field{base, field}) {}
625
628 using Field::member;
629 using Field::name;
630
635 FuncListener &listen();
642 FuncListener &listen(std::size_t args_num,
643 ValType return_type = ValType::none_) {
644 this->args_.resize(args_num);
645 this->return_type_ = return_type;
646 listen();
647 return *this;
648 }
649
656 FuncListener &setArgs(const std::vector<Arg> &args) {
657 this->args_ = args;
658 return *this;
659 }
667 this->return_type_ = type;
668 return *this;
669 }
670
679 [[deprecated("FuncListener::hidden() does nothing since ver1.10")]]
681 return *this;
682 }
693 std::optional<FuncCallHandle> fetchCall() const;
694};
695
引数の情報を表す。
Definition arg.h:30
呼び出された関数の引数の取得と戻り値のセットをするインタフェース
Definition func_result.h:318
void respond(const ValAdaptor &value) const
Definition func_result.cc:76
const std::vector< ValAdaptor > & args() const
関数の引数を取得する
Definition func_result.cc:325
void reject(const ValAdaptor &message) const
Definition func_result.cc:94
bool assertArgsNum(std::size_t expected) const
引数の数をチェックする
Definition func_result.cc:113
Definition func.h:616
FuncListener(const Field &base, const SharedString &field)
Definition func.h:623
FuncListener & setReturnType(ValType type)
戻り値の型をセットする
Definition func.h:666
FuncListener & setArgs(const std::vector< Arg > &args)
引数の情報をセットする
Definition func.h:656
FuncListener & hidden(bool)
関数を関数リストで非表示にする (他clientのentryに表示されなくする)
Definition func.h:680
FuncListener & listen(std::size_t args_num, ValType return_type=ValType::none_)
関数呼び出しの待受を開始する
Definition func.h:642
関数1つを表すクラス
Definition func.h:106
ValAdaptor operator()(Args... args) const
run()と同じ
Definition func.h:510
bool operator==(const T &other) const
Funcの参照先を比較
Definition func.h:606
const Func & setAsync(T func) const
非同期に実行される関数をセットする
Definition func.h:274
const Func & setAsync(T callback) const
引数にFuncCallHandleを取り非同期に実行される関数を登録する
Definition func.h:440
ValAdaptor run(Args... args) const
関数を実行する (同期)
Definition func.h:487
const Func & hidden(bool) const
関数を関数リストで非表示にする (他clientのentryに表示されなくする)
Definition func.h:463
const Func & setAsync(std::vector< Arg > args, ValType return_type, T callback) const
引数にFuncCallHandleを取り非同期に実行される関数を登録する
Definition func.h:376
Func operator[](StringInitializer field) const
Definition func.h:144
Func child(int index) const
Definition func.h:134
void(CallHandle) FuncType
Definition func.h:162
const Arg args(std::size_t i) const
Definition func.h:573
const Func & operator=(T func) const
関数をセットする
Definition func.h:316
Func()=default
static void catchAll(F1 &&f_run, const CallHandle &handle)
Definition func.h:185
Func child(StringInitializer field) const
「(thisの名前).(追加の名前)」を新しい名前とするField
Definition func.h:126
bool operator!=(const T &other) const
Definition func.h:611
const Func & set(std::vector< Arg > args, ValType return_type, T callback) const
引数にCallHandleを取る関数を登録する
Definition func.h:344
Func(const Field &base, const SharedString &field)
Definition func.h:113
ValAdaptor run(std::vector< ValAdaptor > &&args_vec) const
Definition func.h:491
static void tryRun(F1 &&f_run, const CallHandle &handle)
Definition func.h:210
const Func & set(T func) const
関数をセットする
Definition func.h:233
const Func & set(T callback) const
引数にCallHandleを取る関数を登録する
Definition func.h:411
Func parent() const
nameの最後のピリオドの前までを新しい名前とするField
Definition func.h:160
Func operator[](int index) const
Definition func.h:153
Promise runAsync(Args... args) const
関数を実行する (非同期)
Definition func.h:528
非同期で実行した関数の実行結果を取得するインタフェース。
Definition func_result.h:37
u8stringとstringとwstringをshared_ptrで持ち共有する
Definition encoding.h:159
SharedString のpublicなコンストラクタインタフェース (入力専用)
Definition encoding.h:215
Definition component_canvas2d.h:148
Viewを構築するときに使う一時的なViewComponent.
Definition component_view.h:292
数値、文字列などの値を相互変換するクラス
Definition val_adaptor.h:87
std::nullptr_t TraitOkType
Definition trait.h:11
std::conditional_t< std::disjunction_v< std::is_void< Ret >, std::is_constructible< ValAdaptor, Ret > >, FuncReturnTypeCheckOkTrait, This_return_type_is_not_supported_by_WebCFace_Func< Ret > > FuncReturnTypeTrait
Definition func.h:63
constexpr std::nullptr_t TraitOk
Definition trait.h:12
typename FuncArgTypesIterationTrait< Args... >::ArgTypesCheckResult FuncArgTypesTrait
Definition func.h:51
constexpr auto getInvokeSignature(T &&) -> decltype(&T::operator())
Definition func_trait.h:13
void argToTuple(const std::vector< ValAdaptor > &args, T &tuple)
ValAdaptorのリストから任意の型のタプルに変換する
Definition val_adaptor.h:423
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 exception.h:24
Funcがrejectした(例外を投げた)場合の例外
Definition exception.h:34
typename std::conditional_t< IsConstructibleArg< std::decay_t< FirstArg > >::value, FuncArgTypesIterationTrait< OtherArgs... >, FuncArgTypesIterationFailureTrait< FirstArg > >::ArgTypesCheckResult ArgTypesCheckResult
Definition func.h:47
TraitOkType FuncReturnTypeCheckOk
Definition func.h:56
static std::vector< Arg > argsInfo()
Definition func.h:82
FuncReturnTypeTrait< Ret > ReturnTypeTrait
Definition func.h:76
static bool assertArgsNum(const CallHandle &handle)
Definition func.h:79
FuncArgTypesTrait< Args... > ArgTypesTrait
Definition func.h:77
Definition func_trait.h:21
#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