Aria
2.0.0
C++23 MVVM framework (C++20 minimum) — reactive, coroutine-first, ABI-layered
Toggle main menu visibility
Loading...
Searching...
No Matches
view_model_scope.hpp
Go to the documentation of this file.
1
#pragma once
2
3
// ViewModelScope — wires CoroutineScope into a ViewModel so that destroying
4
// the VM cancels every coroutine launched into it AND waits for them to
5
// exit before VM teardown returns.
6
//
7
// Usage (inside a ViewModel subclass):
8
//
9
// class MyVm : public ViewModel {
10
// public:
11
// MyVm() { scope_.attach(*this); }
12
//
13
// void start_polling() {
14
// scope_.launch([this](async::CancellationToken tok) -> async::Task<void> {
15
// while (!tok.is_cancelled()) {
16
// co_await schedule_after(timer_, 1s);
17
// tok.throw_if_cancelled();
18
// poll_data();
19
// }
20
// });
21
// }
22
// private:
23
// binding::ViewModelScope scope_;
24
// };
25
//
26
// Declare the scope after the VM members used by its work (members are
27
// destroyed in reverse order). Its destructor cancels and joins before those
28
// members are torn down. If work touches state destroyed by a custom VM
29
// destructor body, call cancel_and_join() at the start of that body.
30
//
31
// When MyVm is destroyed: the scope calls
32
// `cancel_and_join()` (bounded by `kJoinTimeoutMs`, default 5 s). It
33
// cancels the source synchronously, then blocks until every wrapper
34
// coroutine has decremented the inflight counter to zero. If any
35
// coroutine is stuck on a non-cancellable await, the leak is reported
36
// through the async error sink (see <aria/async/async_error_sink.hpp>)
37
// and teardown returns rather than blocking process shutdown
38
// indefinitely.
39
40
#include "
aria/async/cancellation.hpp
"
41
#include "
aria/async/scope.hpp
"
42
#include "
aria/binding/view_model.hpp
"
43
44
#include <chrono>
45
#include <cstddef>
46
#include <memory>
47
#include <utility>
48
49
namespace
aria::binding
{
50
51
class
ViewModelScope
{
52
public
:
58
static
constexpr
std::chrono::milliseconds
kJoinTimeoutMs
{5000};
59
60
ViewModelScope
() : state_(
std
::make_shared<State>()) {}
61
62
~ViewModelScope
() { shutdown_(*state_); }
63
ViewModelScope
(
const
ViewModelScope
&) =
delete
;
64
ViewModelScope
&
operator=
(
const
ViewModelScope
&) =
delete
;
65
ViewModelScope
(
ViewModelScope
&&) =
delete
;
66
ViewModelScope
&
operator=
(
ViewModelScope
&&) =
delete
;
67
74
void
attach
(
ViewModel
& vm) {
75
auto
keep = state_;
76
vm.
add_destroy_hook
([keep]()
noexcept
{
77
// Structured-concurrency boundary: cancel + wait. If any
78
// coroutine is stuck, CoroutineScope reports the leak
79
// through the async error sink (see scope.hpp).
80
shutdown_(*keep);
81
});
82
}
83
84
[[nodiscard]]
async::CancellationToken
token
() const noexcept {
85
return
state_->scope.token();
86
}
87
[[nodiscard]]
bool
is_cancelled
() const noexcept {
88
return
state_->scope.is_cancelled();
89
}
90
[[nodiscard]] std::size_t
inflight_count
() const noexcept {
91
return
state_->scope.inflight_count();
92
}
93
95
void
cancel
() noexcept { state_->scope.cancel(); }
96
99
bool
cancel_and_join
(std::chrono::milliseconds timeout =
kJoinTimeoutMs
)
noexcept
{
100
return
state_->scope.cancel_and_join(timeout);
101
}
102
103
template
<
typename
Fn>
104
void
launch
(Fn factory) { state_->scope.launch(std::move(factory)); }
105
106
void
launch_simple
(
async::Task<void>
task) {
107
state_->scope.launch_simple(std::move(task));
108
}
109
110
private
:
111
struct
State {
112
async::CoroutineScope
scope;
113
bool
teardown_started =
false
;
114
};
115
static
void
shutdown_(State& state)
noexcept
{
116
if
(std::exchange(state.teardown_started,
true
))
return
;
117
state.scope.cancel_and_join(
kJoinTimeoutMs
);
118
}
119
std::shared_ptr<State> state_;
120
};
121
122
}
// namespace aria::binding
cancellation.hpp
aria::async::CancellationToken
Definition
cancellation.hpp:182
aria::async::CoroutineScope
Definition
scope.hpp:75
aria::async::Task
Definition
task.hpp:78
aria::binding::ViewModel
Base class for view models.
Definition
view_model.hpp:32
aria::binding::ViewModel::add_destroy_hook
void add_destroy_hook(std::function< void()> hook)
aria::binding::ViewModelScope::inflight_count
std::size_t inflight_count() const noexcept
Definition
view_model_scope.hpp:90
aria::binding::ViewModelScope::is_cancelled
bool is_cancelled() const noexcept
Definition
view_model_scope.hpp:87
aria::binding::ViewModelScope::launch
void launch(Fn factory)
Definition
view_model_scope.hpp:104
aria::binding::ViewModelScope::ViewModelScope
ViewModelScope(ViewModelScope &&)=delete
aria::binding::ViewModelScope::operator=
ViewModelScope & operator=(ViewModelScope &&)=delete
aria::binding::ViewModelScope::launch_simple
void launch_simple(async::Task< void > task)
Definition
view_model_scope.hpp:106
aria::binding::ViewModelScope::operator=
ViewModelScope & operator=(const ViewModelScope &)=delete
aria::binding::ViewModelScope::ViewModelScope
ViewModelScope(const ViewModelScope &)=delete
aria::binding::ViewModelScope::ViewModelScope
ViewModelScope()
Definition
view_model_scope.hpp:60
aria::binding::ViewModelScope::kJoinTimeoutMs
static constexpr std::chrono::milliseconds kJoinTimeoutMs
Default timeout for cancel_and_join() invoked from the VM's destroy-hook.
Definition
view_model_scope.hpp:58
aria::binding::ViewModelScope::cancel
void cancel() noexcept
Request cancellation only (non-blocking).
Definition
view_model_scope.hpp:95
aria::binding::ViewModelScope::token
async::CancellationToken token() const noexcept
Definition
view_model_scope.hpp:84
aria::binding::ViewModelScope::cancel_and_join
bool cancel_and_join(std::chrono::milliseconds timeout=kJoinTimeoutMs) noexcept
Cancel + synchronously wait for all in-flight coroutines to exit, with the given timeout.
Definition
view_model_scope.hpp:99
aria::binding::ViewModelScope::attach
void attach(ViewModel &vm)
Tie this scope's lifetime to the ViewModel's destructor.
Definition
view_model_scope.hpp:74
aria::binding::ViewModelScope::~ViewModelScope
~ViewModelScope()
Definition
view_model_scope.hpp:62
aria::binding
Definition
binding_engine.hpp:25
std
Definition
validation_key.hpp:110
scope.hpp
view_model.hpp
modules
binding
include
aria
binding
view_model_scope.hpp
Generated by
1.18.0