Branch data Line data Source code
1 : : // Copyright 2026 HPActor Contributors
2 : : //
3 : : // Licensed under the Apache License, Version 2.0 (the "License");
4 : : // you may not use this file except in compliance with the License.
5 : : // You may obtain a copy of the License at
6 : : //
7 : : // http://www.apache.org/licenses/LICENSE-2.0
8 : : //
9 : : // Unless required by applicable law or agreed to in writing, software
10 : : // distributed under the License is distributed on an "AS IS" BASIS,
11 : : // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 : : // See the License for the specific language governing permissions and
13 : : // limitations under the License.
14 : :
15 : : #pragma once
16 : :
17 : : #include <hpactor/actor/abstract_actor.hpp>
18 : : #include <hpactor/actor/actor_context.hpp>
19 : : #include <hpactor/actor/drain_config.hpp>
20 : : #include <hpactor/actor/lifecycle_actor.hpp>
21 : : #include <hpactor/cli/cli_config.hpp>
22 : : #include <hpactor/config/topology_model.hpp>
23 : : #include <hpactor/core/actor_registry.hpp>
24 : : #include <hpactor/core/mailbox.hpp>
25 : : #include <hpactor/core/proto_type_registry.hpp>
26 : : #include <hpactor/hpactor_config.hpp>
27 : : #include <hpactor/log/log_config.hpp>
28 : : #include <hpactor/log/log_field.hpp>
29 : : #include <hpactor/log/logger.hpp>
30 : : #include <hpactor/mailbox/dead_letter_queue.hpp>
31 : : #include <hpactor/mailbox/mpsc_actor_mailbox.hpp>
32 : : #include <hpactor/metrics/metrics_config.hpp>
33 : : #include <hpactor/metrics/metrics_event.hpp>
34 : : #include <hpactor/metrics/metrics_ring_buffer.hpp>
35 : : #include <hpactor/net/actor_location_cache.hpp>
36 : : #include <hpactor/net/frame.hpp>
37 : : #include <hpactor/net/gossip_membership.hpp>
38 : : #include <hpactor/net/http_client.hpp>
39 : : #include <hpactor/net/registrar.hpp>
40 : : #include <hpactor/net/service_discovery.hpp>
41 : : #include <hpactor/net/static_discovery.hpp>
42 : : #include <hpactor/net/tcp_transport.hpp>
43 : : #include <hpactor/ref/actor_ref.hpp>
44 : : #include <hpactor/rpc/rpc_channel.hpp>
45 : : #include <hpactor/sched/dispatch_policy.hpp>
46 : : #include <hpactor/sched/scheduler.hpp>
47 : : #include <hpactor/tracing/trace_config.hpp>
48 : : #include <hpactor/tracing/trace_manager.hpp>
49 : : #include <hpactor/types/types.hpp>
50 : :
51 : : #include <atomic>
52 : : #include <chrono>
53 : : #include <memory>
54 : : #include <mutex>
55 : : #include <thread>
56 : : #include <unordered_map>
57 : :
58 : : namespace hpactor {
59 : :
60 : : // Forward declarations
61 : : class AsyncActor;
62 : : class ActorTypeRegistry;
63 : :
64 : : namespace log {
65 : : class LogManager;
66 : : class Logger;
67 : : } // namespace log
68 : :
69 : : namespace cli {
70 : : class CliActor;
71 : : } // namespace cli
72 : :
73 : : // Scheduler interface forward declaration
74 : : namespace sched {
75 : : class IScheduler;
76 : : class HybridScheduler;
77 : : } // namespace sched
78 : :
79 : : // -----------------------------------------------------------------------------
80 : : // MailboxDefaults - system-wide default mailbox configuration
81 : : // -----------------------------------------------------------------------------
82 : : struct MailboxDefaults {
83 : : #define HPACTOR_MAILBOX_FIELD(name, type, toml, def) type name{def};
84 : : #include <hpactor/config/mailbox_fields.def>
85 : : #undef HPACTOR_MAILBOX_FIELD
86 : : };
87 : :
88 : : // -----------------------------------------------------------------------------
89 : : // Config - configuration for ActorSystem
90 : : // -----------------------------------------------------------------------------
91 : : struct Config {
92 : : // ── Shared system fields (generated from config/system_fields.def) ──
93 : : #define HPACTOR_SYSTEM_FIELD(name, type, toml, def) type name{def};
94 : : #include <hpactor/config/system_fields.def>
95 : : #undef HPACTOR_SYSTEM_FIELD
96 : :
97 : : // ── Config-only fields ──
98 : : EndPoint endpoint = LocalEndpoint;
99 : :
100 : : // TLS and pool config (used if enable_network=true)
101 : : net::TlsConfig tls = {};
102 : : net::PoolConfig pool = {};
103 : : net::RegistrarConfig registrar = {};
104 : :
105 : : // HTTP subsystem (requires enable_network = true)
106 : : bool enable_http_client = false;
107 : :
108 : : // Coroutine scheduling (requires HPACTOR_SUPPORT_COROUTINES=1 at compile
109 : : // time) When true, actors use coroutine-based execution instead of
110 : : // behavior-based. Default: false (behavior-based scheduling).
111 : : bool use_coroutines = false;
112 : :
113 : : // CLI configuration
114 : : cli::CliConfig cli;
115 : :
116 : : // Service discovery backend. nullptr = auto-select based on enable_network
117 : : // and registrar config (backward compatible).
118 : : std::shared_ptr<net::IServiceDiscovery> service_discovery = nullptr;
119 : :
120 : : // Gossip configuration. Used when creating GossipMembership internally.
121 : : net::GossipConfig gossip = {};
122 : :
123 : : // Mailbox defaults — applied to every actor spawned via this system
124 : : MailboxDefaults mailbox;
125 : :
126 : : // Dead-letter queue configuration
127 : : mailbox::DeadLetterConfig dead_letters;
128 : :
129 : : // Shutdown configuration
130 : : DrainConfig shutdown_drain{DrainPolicy::Drain,
131 : : std::chrono::milliseconds{30'000}};
132 : : uint32_t ingress_timeout_ms{5000};
133 : : uint32_t cluster_leave_timeout_ms{10000};
134 : : bool shutdown_force_after_timeout{true};
135 : :
136 : : // Timer backend selection
137 : : sched::TimerBackend timer_backend = sched::TimerBackend::TimingWheel;
138 : :
139 : : // Start scheduler workers in paused state (for deterministic testing).
140 : : // When true, workers are created but blocked until resume_workers() is
141 : : // called.
142 : : bool scheduler_start_paused = false;
143 : :
144 : : // Distributed tracing configuration
145 : : tracing::TraceConfig tracing;
146 : : };
147 : :
148 : : // -----------------------------------------------------------------------------
149 : : // ActorTypeDef - definition of an actor type
150 : : // -----------------------------------------------------------------------------
151 : : struct ActorTypeDef {
152 : : std::string name;
153 : : ActorType id;
154 : : };
155 : :
156 : : // Shutdown phase enumeration
157 : : enum class ShutdownPhase : uint8_t {
158 : : Running,
159 : : DrainingIngress,
160 : : DrainingActors,
161 : : LeavingCluster,
162 : : FlushingTelemetry,
163 : : Stopped,
164 : : ForcedStop,
165 : : };
166 : :
167 : : struct ShutdownOptions {
168 : 0 : std::chrono::milliseconds ingress_timeout{5'000};
169 : 0 : std::chrono::milliseconds actor_drain_timeout{30'000};
170 : 0 : std::chrono::milliseconds cluster_leave_timeout{10'000};
171 : : bool force_after_timeout{true};
172 : : };
173 : :
174 : : // -----------------------------------------------------------------------------
175 : : // ActorSystem - the actor environment containing schedulers, registry, etc.
176 : : // -----------------------------------------------------------------------------
177 : : class ActorSystem {
178 : : public:
179 : : explicit ActorSystem(const Config& config);
180 : : ~ActorSystem();
181 : :
182 : : // Non-copyable, non-movable
183 : : ActorSystem(const ActorSystem&) = delete;
184 : : ActorSystem& operator=(const ActorSystem&) = delete;
185 : : ActorSystem(ActorSystem&&) = delete;
186 : : ActorSystem& operator=(ActorSystem&&) = delete;
187 : :
188 : : // Spawn actors at system level
189 : : template <typename T, typename... Args> Actor spawn(Args&&... args);
190 : :
191 : : // Spawn a pre-constructed actor with configuration from ActorDef.
192 : : // Used by BootstrapEngine for TOML-based topology bootstrapping.
193 : : Actor spawn_configured(std::shared_ptr<AbstractActor> actor,
194 : : const struct config::ActorDef& def);
195 : :
196 : : // Load topology from TOML file (convenience entry point)
197 : : result<void> load_topology(const std::string& toml_path);
198 : :
199 : : // Actor registry
200 : : void register_actor(const std::string& name, Actor actor);
201 : : Actor resolve_actor(const std::string& name);
202 : : void unregister_actor(const std::string& name);
203 : :
204 : : // Actor type registration
205 : : void register_actor_type(const ActorTypeDef& def);
206 : : ActorTypeDef get_actor_type(ActorType type) const;
207 : :
208 : : // Clock
209 : 32 : Clock& clock() {
210 : 32 : return clock_;
211 : : }
212 : :
213 : : // System actor
214 : : Actor system_actor() {
215 : : return system_actor_;
216 : : }
217 : :
218 : : // Registry access
219 : 9 : actor_registry& registry() {
220 : 9 : return registry_;
221 : : }
222 : :
223 : : // Proto type registry
224 : 0 : ProtoTypeRegistry& proto_registry() {
225 : 0 : return proto_registry_;
226 : : }
227 : : const ProtoTypeRegistry& proto_registry() const {
228 : : return proto_registry_;
229 : : }
230 : :
231 : : // Node ID
232 : 31 : EndPoint endpoint() const {
233 : 31 : return endpoint_;
234 : : }
235 : :
236 : : // Check if actor system is running
237 : 2 : bool is_running() const {
238 : 2 : return running_.load(std::memory_order_acquire);
239 : : }
240 : :
241 : : // Get scheduler for direct scheduling operations
242 : 31 : sched::IScheduler* scheduler() {
243 : 31 : return scheduler_.get();
244 : : }
245 : :
246 : : // Runtime coroutine toggle (requires HPACTOR_SUPPORT_COROUTINES=1 at
247 : : // compile time). Default: false (behavior-based scheduling).
248 : 353 : bool use_coroutines() const {
249 : 353 : return config_.use_coroutines;
250 : : }
251 : :
252 : : // RPC channel for remote calls
253 : 0 : RpcChannel& rpc_channel() {
254 : 0 : return *rpc_channel_;
255 : : }
256 : :
257 : : // HTTP client for outbound HTTP requests
258 : 0 : net::HttpClient& http_client() {
259 : 0 : return *http_client_;
260 : : }
261 : :
262 : : // Distributed tracing
263 : 690 : tracing::TraceManager* trace_manager() noexcept {
264 : 690 : return trace_manager_.get();
265 : : }
266 : :
267 : : const tracing::TraceManager* trace_manager() const noexcept {
268 : : return trace_manager_.get();
269 : : }
270 : :
271 : : void apply_tracing_config(const tracing::TraceConfig& config);
272 : :
273 : : // Internal actor lookup (used by scheduler)
274 : : std::shared_ptr<AbstractActor> get_actor(ActorId id);
275 : :
276 : : // Get metrics ring buffer (nullptr if metrics disabled)
277 : 4 : auto* metrics_ring_buffer() const {
278 : 4 : return metrics_ring_buffer_.get();
279 : : }
280 : :
281 : : // Get CLI actor (nullptr if CLI disabled or not yet spawned)
282 : : cli::CliActor* cli_actor() const;
283 : :
284 : : // Get actor's mailbox (used by scheduler)
285 : : mailbox::MPSCActorMailbox<TypedMessage>* get_mailbox(ActorId id);
286 : :
287 : : // Get the number of live actors in this system
288 : : size_t actor_count() const;
289 : :
290 : : // Enumerate all actors. Callback receives (ActorId, AbstractActor&).
291 : : // The callback must not spawn or kill actors (lock is held).
292 : : void for_each_actor(std::function<void(ActorId, AbstractActor&)> callback) const;
293 : :
294 : : // Deliver message to local actor
295 : : void deliver_local(ActorId target, TypedMessage msg);
296 : :
297 : : // Deliver message to local actor with priority and deadline for scheduling
298 : : // priority: 0-3 (0 = highest)
299 : : // deadline_ns: absolute deadline in nanoseconds (INT64_MAX = no deadline)
300 : : void deliver_local(ActorId target, TypedMessage msg, uint8_t priority,
301 : : int64_t deadline_ns);
302 : :
303 : : // Bounded admission delivery — returns an EnqueueResult describing the
304 : : // outcome. Returns ActorNotFound when the target actor does not exist,
305 : : // Rejected when the mailbox is at hard capacity.
306 : : mailbox::EnqueueResult
307 : : try_deliver_local(ActorId target, TypedMessage msg, uint8_t priority = 0,
308 : : int64_t deadline_ns = INT64_MAX,
309 : : mailbox::DeliveryOptions options = {});
310 : :
311 : : // Dead-letter queue
312 : : bool dead_letter(mailbox::DeadLetterRecord record) noexcept;
313 : : mailbox::DeadLetterQueueSnapshot dead_letter_snapshot() const noexcept;
314 : : bool pop_dead_letter(mailbox::DeadLetterRecord& out) noexcept;
315 : :
316 : : // Build a MailboxConfig from system-wide defaults in Config::mailbox.
317 : : mailbox::MailboxConfig mailbox_config_for_spawn() const;
318 : :
319 : : // Build a MailboxConfig for a specific ActorDef, falling back to system
320 : : // defaults when ActorDef fields are zero.
321 : : mailbox::MailboxConfig
322 : : mailbox_config_for_actor_def(const config::ActorDef& def) const;
323 : :
324 : : // Deliver a remote message (from WireFrame) to the target actor's mailbox.
325 : : // Bridges the transport layer to the unified deliver_local() sink.
326 : : void deliver_remote(const net::WireFrame& frame);
327 : :
328 : : // Called by IServiceDiscovery when a remote node becomes unreachable.
329 : : // Finds all actors linked to the dead endpoint and delivers DownMsg.
330 : : void on_node_dead(EndPoint dead_ep);
331 : :
332 : : // Emit a backpressure signal to the sender actor, delivered through
333 : : // the sender's ActorContext::handle_backpressure() handler.
334 : : void signal_backpressure(const mailbox::BackpressureSignal& signal);
335 : :
336 : : // Enqueue an I/O completion to be delivered to an actor
337 : : // Called by EventLoop when async operations complete
338 : : void enqueue_completion(net::OpCompletion completion);
339 : :
340 : : // Network access
341 : : net::Transport* transport() {
342 : : return transport_.get();
343 : : }
344 : :
345 : : // Return the transport for sending to a remote endpoint.
346 : : // Currently returns the single transport_ for all remote endpoints, since
347 : : // TcpTransport handles per-endpoint routing internally via its pools_ map.
348 : : // The endpoint parameter is reserved for future multi-transport scenarios.
349 : : // Returns nullptr if networking is not enabled.
350 : : net::Transport* get_transport_for(const EndPoint& endpoint);
351 : :
352 : : net::UdpRegistrar* registrar() {
353 : : return registrar_.get();
354 : : }
355 : :
356 : : // Remote actor spawning (main/non-actor context only)
357 : : result<ActorRef>
358 : : spawn_remote(const std::string& node_name, const std::string& actor_type,
359 : : const StreamBuffer& args);
360 : :
361 : : AsyncActor
362 : : spawn_remote_async(const std::string& node_name,
363 : : const std::string& actor_type, const StreamBuffer& args);
364 : :
365 : : // Actor type registry for remote spawning
366 : : ActorTypeRegistry& actor_type_registry() {
367 : : return *actor_type_registry_;
368 : : }
369 : : const ActorTypeRegistry& actor_type_registry() const {
370 : : return *actor_type_registry_;
371 : : }
372 : :
373 : : // ── Shutdown ───────────────────────────────────────────────────────────
374 : :
375 : : // Node shutdown — drives the full phase machine.
376 : : // Overload with no arguments uses default ShutdownOptions{}.
377 : : result<void> shutdown();
378 : : result<void> shutdown(const ShutdownOptions& opts);
379 : :
380 : : // Current shutdown phase
381 : : ShutdownPhase shutdown_phase() const noexcept;
382 : :
383 : : // Health/readiness gating
384 : : bool is_ready() const noexcept;
385 : : bool is_draining() const noexcept;
386 : :
387 : : // Per-actor drain config override (for admin/CLI use)
388 : : void set_drain_config(ActorId target, DrainConfig cfg);
389 : :
390 : : private:
391 : : Config config_;
392 : : EndPoint endpoint_;
393 : : Clock clock_;
394 : : actor_registry registry_;
395 : : std::unordered_map<ActorType, ActorTypeDef> actor_types_;
396 : : Actor system_actor_;
397 : :
398 : : // Actor registry - maps ActorId to actor instance
399 : : std::unordered_map<ActorId, std::shared_ptr<AbstractActor>> actors_;
400 : : mutable std::mutex actors_mutex_;
401 : :
402 : : // Actor mailboxes - maps ActorId to mailbox
403 : : std::unordered_map<ActorId, std::unique_ptr<mailbox::MPSCActorMailbox<TypedMessage>>> mailboxes_;
404 : : std::mutex mailboxes_mutex_;
405 : :
406 : : // Actor contexts - maps ActorId to context
407 : : std::unordered_map<ActorId, std::unique_ptr<ActorContext>> actor_contexts_;
408 : : std::mutex actor_contexts_mutex_;
409 : :
410 : : // Actor ID generator
411 : : std::atomic<uint64_t> next_actor_id_{1};
412 : :
413 : : // Running flag for network thread loop
414 : : std::atomic<bool> running_{true};
415 : :
416 : : // Shutdown state
417 : : std::atomic<ShutdownPhase> shutdown_phase_{ShutdownPhase::Running};
418 : : std::atomic<bool> is_ready_{true};
419 : :
420 : : // Scheduler
421 : : std::unique_ptr<sched::IScheduler> scheduler_;
422 : :
423 : : // Network components (owned)
424 : : std::unique_ptr<net::TcpTransport> transport_;
425 : : std::shared_ptr<net::UdpRegistrar> registrar_;
426 : : std::shared_ptr<net::IServiceDiscovery> discovery_;
427 : : std::shared_ptr<net::ActorLocationCache> location_cache_;
428 : : uint64_t cache_purge_timer_ = 0;
429 : : std::unique_ptr<net::EventLoop> network_loop_;
430 : : std::thread network_thread_;
431 : :
432 : : // Actor type registry for remote spawning (owned via pointer to avoid
433 : : // circular dep)
434 : : std::unique_ptr<ActorTypeRegistry> actor_type_registry_;
435 : :
436 : : // RPC channel for remote calls (after transport_ creation)
437 : : std::unique_ptr<RpcChannel> rpc_channel_;
438 : : // HTTP client for outbound HTTP calls
439 : : std::unique_ptr<net::HttpClient> http_client_;
440 : :
441 : : // HTTP gateway actor (DaemonActor, spawned when enable_http_gateway = true)
442 : : Actor http_gateway_actor_{nullptr};
443 : :
444 : : // CLI actor (DaemonActor, spawned when cli.enabled = true)
445 : : std::shared_ptr<cli::CliActor> cli_actor_;
446 : :
447 : : // Metrics configuration and ring buffer
448 : : metrics::MetricsConfig metrics_config_;
449 : : std::shared_ptr<metrics::MpscRingBuffer<metrics::MetricEvent>> metrics_ring_buffer_;
450 : :
451 : : // Logging subsystem
452 : : log::LogConfig logging_config_;
453 : : std::unique_ptr<log::LogManager> log_manager_;
454 : : log::Logger* logger_ = nullptr;
455 : :
456 : : // Dead-letter queue
457 : : std::unique_ptr<mailbox::DeadLetterQueue> dead_letters_;
458 : :
459 : : // Tracing subsystem
460 : : tracing::TraceConfig tracing_config_;
461 : : std::unique_ptr<tracing::TraceManager> trace_manager_;
462 : :
463 : : // Proto type registry for protobuf message serialization
464 : : ProtoTypeRegistry proto_registry_;
465 : :
466 : : // Pending remote spawns awaiting response
467 : : std::unordered_map<uint64_t, std::shared_ptr<AsyncActor>> pending_spawns_;
468 : : std::mutex pending_spawns_mutex_;
469 : : };
470 : :
471 : : // -----------------------------------------------------------------------------
472 : : // Template implementations
473 : : // -----------------------------------------------------------------------------
474 : :
475 : : template <typename T, typename... Args>
476 : 108 : Actor ActorSystem::spawn(Args&&... args) {
477 : 216 : ActorId id(next_actor_id_.fetch_add(1));
478 : 108 : auto actor = std::make_shared<T>(nullptr, *this, std::forward<Args>(args)...);
479 : 108 : actor->set_address(ActorAddress(endpoint_, actor->type(), id, 0));
480 : : if constexpr (requires { T::kActorTypeName; }) {
481 : : actor->set_type_name(T::kActorTypeName);
482 : : } else {
483 : 216 : actor->set_type_name("unknown");
484 : : }
485 : :
486 : : {
487 : 108 : std::lock_guard<std::mutex> lock(actors_mutex_);
488 : 108 : actors_.emplace(id, actor);
489 : 108 : }
490 : :
491 : : // Create mailbox
492 : : {
493 : 108 : std::lock_guard<std::mutex> lock(mailboxes_mutex_);
494 : 108 : mailboxes_.emplace(
495 : : id, std::make_unique<mailbox::MPSCActorMailbox<TypedMessage>>(
496 : 108 : id, scheduler_.get(), mailbox_config_for_spawn()));
497 : 108 : }
498 : :
499 : : // Create actor context and set it on the actor
500 : 108 : auto actor_ctx = std::make_unique<ActorContext>(Actor(actor), this);
501 : 108 : actor->set_context(actor_ctx.get());
502 : 108 : actor_contexts_.emplace(id, std::move(actor_ctx));
503 : :
504 : : // Set scheduler and mailbox on actor
505 : 108 : actor->set_scheduler(scheduler_.get());
506 : 108 : actor->set_mailbox(mailboxes_[id].get());
507 : :
508 : : // Wire metrics ring buffer to actor and mailbox
509 : 108 : if (metrics_ring_buffer_) [[unlikely]] {
510 : 108 : auto* mbox = mailboxes_[id].get();
511 : 108 : mbox->set_metrics_ring_buffer(metrics_ring_buffer_.get());
512 : 108 : actor->set_metrics_ring_buffer(metrics_ring_buffer_.get());
513 : : }
514 : :
515 : : // Wire logger to actor and mailbox
516 : 108 : if (logger_) [[unlikely]] {
517 : 108 : auto* mbox = mailboxes_[id].get();
518 : 108 : mbox->set_logger(logger_);
519 : 108 : actor->set_logger(logger_);
520 : : }
521 : :
522 : : // Register with scheduler based on dispatch policy.
523 : : // Cooperative actors go onto the work-stealing pool. Dedicated actors
524 : : // are registered with the scheduler but NOT placed on the cooperative
525 : : // pool — they manage their own threads or use DedicatedThreadPool.
526 : 108 : switch (actor->dispatch_policy()) {
527 : 97 : case sched::DispatchPolicy::Cooperative:
528 : 97 : scheduler_->notify_ready(id, 0, INT64_MAX);
529 : 97 : break;
530 : 9 : case sched::DispatchPolicy::DedicatedThread:
531 : 18 : scheduler_->register_dedicated_thread(
532 : 9 : id, actor->dispatch_hints().cpu_affinity);
533 : 9 : break;
534 : 2 : case sched::DispatchPolicy::DedicatedPool:
535 : 2 : scheduler_->register_dedicated_pool(id, actor->dispatch_hints().pool_size);
536 : 2 : break;
537 : : }
538 : :
539 : : // Activate the actor (DaemonActor starts its thread here, etc.)
540 : 108 : actor->on_activate();
541 : :
542 : : // Transition lifecycle to ACTIVE if actor has lifecycle management
543 : 108 : if (auto* lc = actor->as_lifecycle()) {
544 : 25 : lc->transition(LifecycleState::kActive);
545 : : }
546 : :
547 : 108 : HPACTOR_LOG_INFO(log::LogCategory::kActor, id,
548 : : static_cast<uint32_t>(log::LogEventId::kActorSpawned),
549 : : "actor spawned",
550 : : log::field_lit("type", actor->type_name().data()));
551 : :
552 : 108 : if (metrics_ring_buffer_) [[unlikely]] {
553 : 108 : metrics::MetricEvent evt{};
554 : 108 : evt.actor_id = id;
555 : 108 : evt.event_type = metrics::MetricEventType::kActorSpawned;
556 : 108 : evt.value_hi = 1;
557 : 108 : metrics_ring_buffer_->try_push(evt);
558 : : }
559 : :
560 : 108 : return Actor(actor);
561 : 108 : }
562 : :
563 : : } // namespace hpactor
|