1 #pragma once 2 3 #include <mbgl/actor/mailbox.hpp> 4 #include <mbgl/actor/message.hpp> 5 6 #include <memory> 7 8 namespace mbgl { 9 10 /* 11 An `ActorRef<O>` is a *non*-owning, weak reference to an actor of type `O`. You can send it 12 messages just like an `Actor<O>`. It's a value object: safe to copy and pass between actors 13 via messages. 14 15 An `ActorRef<O>` does not extend the lifetime of the corresponding `Actor<O>`. That's determined 16 entirely by whichever object owns the `Actor<O>` -- the actor's "supervisor". 17 18 It's safe for a `Ref` to outlive its `Actor` -- the reference is "weak", and does not extend 19 the lifetime of the owning Actor, and sending a message to a `Ref` whose `Actor` has died is 20 a no-op. (In the future, a dead-letters queue or log may be implemented.) 21 */ 22 23 template <class Object> 24 class ActorRef { 25 public: ActorRef(Object & object_,std::weak_ptr<Mailbox> weakMailbox_)26 ActorRef(Object& object_, std::weak_ptr<Mailbox> weakMailbox_) 27 : object(&object_), 28 weakMailbox(std::move(weakMailbox_)) { 29 } 30 31 template <typename Fn, class... Args> invoke(Fn fn,Args &&...args)32 void invoke(Fn fn, Args&&... args) { 33 if (auto mailbox = weakMailbox.lock()) { 34 mailbox->push(actor::makeMessage(*object, fn, std::forward<Args>(args)...)); 35 } 36 } 37 38 template <typename Fn, class... Args> ask(Fn fn,Args &&...args)39 auto ask(Fn fn, Args&&... args) { 40 // Result type is deduced from the function's return type 41 using ResultType = typename std::result_of<decltype(fn)(Object, Args...)>::type; 42 43 std::promise<ResultType> promise; 44 auto future = promise.get_future(); 45 46 if (auto mailbox = weakMailbox.lock()) { 47 mailbox->push( 48 actor::makeMessage( 49 std::move(promise), *object, fn, std::forward<Args>(args)... 50 ) 51 ); 52 } else { 53 promise.set_exception(std::make_exception_ptr(std::runtime_error("Actor has gone away"))); 54 } 55 56 return future; 57 } 58 59 private: 60 Object* object; 61 std::weak_ptr<Mailbox> weakMailbox; 62 }; 63 64 } // namespace mbgl 65