#include "../include/context.h"
namespace nodegit {
thread_local Context *Context::currentContext = nullptr;
AsyncContextCleanupHandle::AsyncContextCleanupHandle(Napi::Env env, Context *context)
: context(context)
{
// napi_add_env_cleanup_hook is N-API, unlike node::AddEnvironmentCleanupHook.
napi_add_env_cleanup_hook(env, AsyncCleanupContext, this);
}
AsyncContextCleanupHandle::~AsyncContextCleanupHandle() {
delete context;
}
void AsyncContextCleanupHandle::AsyncCleanupContext(void *data) {
std::unique_ptr cleanupHandle(static_cast(data));
Napi::Env env = cleanupHandle->context->Env();
Napi::HandleScope scope(env);
// N-API's cleanup hook cannot be deferred, so ShutdownThreadPool has to
// complete - including joining every worker thread - before we return.
// The handle released at the end of this scope owns the Context, so the
// thread pool is destroyed only after it is done shutting itself down.
cleanupHandle->context->ShutdownThreadPool();
cleanupHandle.reset();
}
Context::Context(Napi::Env env)
: env(env),
threadPool(10, this)
{
Napi::Object storage = Napi::Object::New(env);
persistentStorage = Napi::Persistent(storage);
currentContext = this;
new AsyncContextCleanupHandle(env, this);
}
Context::~Context() {
nodegit::TrackerWrap::DeleteFromList(&trackerList);
if (currentContext == this) {
currentContext = nullptr;
}
}
std::shared_ptr Context::GetCleanupHandle(std::string key) {
return cleanupHandles[key];
}
Context *Context::GetCurrentContext() {
return currentContext;
}
Napi::Value Context::GetFromPersistent(std::string key) {
Napi::Object storage = persistentStorage.Value();
return storage.Get(key);
}
void Context::QueueWorker(nodegit::AsyncWorker *worker) {
threadPool.QueueWorker(worker);
}
std::shared_ptr Context::RemoveCleanupHandle(std::string key) {
std::shared_ptr cleanupItem = cleanupHandles[key];
cleanupHandles.erase(key);
return cleanupItem;
}
void Context::SaveToPersistent(std::string key, const Napi::Value &value) {
Napi::Object storage = persistentStorage.Value();
storage.Set(key, value);
}
void Context::SaveCleanupHandle(std::string key, std::shared_ptr cleanupItem) {
cleanupHandles[key] = cleanupItem;
}
void Context::ShutdownThreadPool() {
threadPool.Shutdown();
}
}