#pragma once

#include <mutex>
#include <optional>
#include <queue>
#include <utility>

namespace ta::foundation
{
template <class T>
class CommandQueue
{
public:
    void push(T value)
    {
        std::lock_guard lock(mutex_);
        queue_.push(std::move(value));
    }

    std::optional<T> try_pop()
    {
        std::lock_guard lock(mutex_);
        if (queue_.empty())
            return std::nullopt;
        T value = std::move(queue_.front());
        queue_.pop();
        return value;
    }

    [[nodiscard]] bool empty() const
    {
        std::lock_guard lock(mutex_);
        return queue_.empty();
    }

private:
    mutable std::mutex mutex_;
    std::queue<T> queue_;
};
}
