# HG changeset patch # User Sebastien Jodogne # Date 1435675583 -7200 # Node ID 6406f5493d92761e6950d2198c9cb2c86c02d9a3 # Parent f9cd40166269a5b38e507b8dca0ce3831d8aaabc refactoring: Lua toolbox diff -r f9cd40166269 -r 6406f5493d92 OrthancServer/LuaScripting.cpp --- a/OrthancServer/LuaScripting.cpp Tue Jun 30 16:04:05 2015 +0200 +++ b/OrthancServer/LuaScripting.cpp Tue Jun 30 16:46:23 2015 +0200 @@ -47,9 +47,6 @@ #include #include -static const char* RECEIVED_INSTANCE_FILTER = "ReceivedInstanceFilter"; -static const char* ON_STORED_INSTANCE = "OnStoredInstance"; - namespace Orthanc { @@ -58,7 +55,7 @@ { if (operation == "delete") { - LOG(INFO) << "Lua script to delete instance " << parameters["Instance"].asString(); + LOG(INFO) << "Lua script to delete resource " << parameters["Resource"].asString(); return new DeleteInstanceCommand(context_); } @@ -75,7 +72,7 @@ } std::string modality = parameters["Modality"].asString(); - LOG(INFO) << "Lua script to send instance " << parameters["Instance"].asString() + LOG(INFO) << "Lua script to send resource " << parameters["Resource"].asString() << " to modality " << modality << " using Store-SCU"; return new StoreScuCommand(context_, localAet, Configuration::GetModalityUsingSymbolicName(modality), true); @@ -84,7 +81,7 @@ if (operation == "store-peer") { std::string peer = parameters["Peer"].asString(); - LOG(INFO) << "Lua script to send instance " << parameters["Instance"].asString() + LOG(INFO) << "Lua script to send resource " << parameters["Resource"].asString() << " to peer " << peer << " using HTTP"; OrthancPeerParameters parameters; @@ -94,7 +91,7 @@ if (operation == "modify") { - LOG(INFO) << "Lua script to modify instance " << parameters["Instance"].asString(); + LOG(INFO) << "Lua script to modify resource " << parameters["Resource"].asString(); DicomModification modification; OrthancRestApi::ParseModifyRequest(modification, parameters); @@ -104,7 +101,7 @@ if (operation == "call-system") { - LOG(INFO) << "Lua script to call system command on " << parameters["Instance"].asString(); + LOG(INFO) << "Lua script to call system command on " << parameters["Resource"].asString(); const Json::Value& argsIn = parameters["Arguments"]; if (argsIn.type() != Json::arrayValue) @@ -147,6 +144,62 @@ } + void LuaScripting::InitializeJob() + { + lua_.Execute("_InitializeJob()"); + } + + + void LuaScripting::SubmitJob(const std::string& description) + { + Json::Value operations; + LuaFunctionCall call2(lua_, "_AccessJob"); + call2.ExecuteToJson(operations); + + if (operations.type() != Json::arrayValue) + { + throw OrthancException(ErrorCode_InternalError); + } + + ServerJob job; + ServerCommandInstance* previousCommand = NULL; + + for (Json::Value::ArrayIndex i = 0; i < operations.size(); ++i) + { + if (operations[i].type() != Json::objectValue || + !operations[i].isMember("Operation")) + { + throw OrthancException(ErrorCode_InternalError); + } + + const Json::Value& parameters = operations[i]; + std::string operation = parameters["Operation"].asString(); + + ServerCommandInstance& command = job.AddCommand(ParseOperation(operation, operations[i])); + + if (!parameters.isMember("Resource")) + { + throw OrthancException(ErrorCode_InternalError); + } + + std::string resource = parameters["Resource"].asString(); + if (resource.empty()) + { + previousCommand->ConnectOutput(command); + } + else + { + command.AddInput(resource); + } + + previousCommand = &command; + } + + job.SetDescription(description); + context_.GetScheduler().Submit(job); + } + + LuaScripting::LuaScripting(ServerContext& context) : context_(context) { lua_.Execute(Orthanc::EmbeddedResources::LUA_TOOLBOX); @@ -160,11 +213,13 @@ const std::string& remoteAet, const std::string& calledAet) { - if (lua_.IsExistingFunction(ON_STORED_INSTANCE)) + static const char* NAME = "OnStoredInstance"; + + if (lua_.IsExistingFunction(NAME)) { - lua_.Execute("_InitializeJob()"); + InitializeJob(); - LuaFunctionCall call(lua_, ON_STORED_INSTANCE); + LuaFunctionCall call(lua_, NAME); call.PushString(instanceId); call.PushJson(simplifiedTags); call.PushJson(metadata); @@ -172,51 +227,7 @@ call.PushJson(calledAet); call.Execute(); - Json::Value operations; - LuaFunctionCall call2(lua_, "_AccessJob"); - call2.ExecuteToJson(operations); - - if (operations.type() != Json::arrayValue) - { - throw OrthancException(ErrorCode_InternalError); - } - - ServerJob job; - ServerCommandInstance* previousCommand = NULL; - - for (Json::Value::ArrayIndex i = 0; i < operations.size(); ++i) - { - if (operations[i].type() != Json::objectValue || - !operations[i].isMember("Operation")) - { - throw OrthancException(ErrorCode_InternalError); - } - - const Json::Value& parameters = operations[i]; - std::string operation = parameters["Operation"].asString(); - - ServerCommandInstance& command = job.AddCommand(ParseOperation(operation, operations[i])); - - if (!parameters.isMember("Instance")) - { - throw OrthancException(ErrorCode_InternalError); - } - - std::string instance = parameters["Instance"].asString(); - if (instance.empty()) - { - previousCommand->ConnectOutput(command); - } - else - { - command.AddInput(instance); - } - - previousCommand = &command; - } - - job.SetDescription(std::string("Lua script: ") + ON_STORED_INSTANCE); - context_.GetScheduler().Submit(job); + SubmitJob(std::string("Lua script: ") + NAME); } } @@ -244,22 +255,72 @@ } + + void LuaScripting::OnStableResource(const ServerIndexChange& change) + { + const char* name; + + switch (change.GetChangeType()) + { + case ChangeType_StablePatient: + name = "OnStablePatient"; + break; + + case ChangeType_StableStudy: + name = "OnStableStudy"; + break; + + case ChangeType_StableSeries: + name = "OnStableSeries"; + break; + + default: + throw OrthancException(ErrorCode_InternalError); + } + + + Json::Value tags; + //if (context_.GetIndex().LookupResource(tags, change.GetPublicId(), change.GetResourceType())) + { + boost::mutex::scoped_lock lock(mutex_); + + if (lua_.IsExistingFunction(name)) + { + InitializeJob(); + + LuaFunctionCall call(lua_, name); + call.PushString(change.GetPublicId()); + call.PushJson(tags); + call.Execute(); + + SubmitJob(std::string("Lua script: ") + name); + } + } + } + + + void LuaScripting::SignalChange(const ServerIndexChange& change) { - boost::mutex::scoped_lock lock(mutex_); - - // TODO + if (change.GetChangeType() == ChangeType_StablePatient || + change.GetChangeType() == ChangeType_StableStudy || + change.GetChangeType() == ChangeType_StableSeries) + { + OnStableResource(change); + } } bool LuaScripting::FilterIncomingInstance(const Json::Value& simplified, const std::string& remoteAet) { + static const char* NAME = "ReceivedInstanceFilter"; + boost::mutex::scoped_lock lock(mutex_); - if (lua_.IsExistingFunction(RECEIVED_INSTANCE_FILTER)) + if (lua_.IsExistingFunction(NAME)) { - LuaFunctionCall call(lua_, RECEIVED_INSTANCE_FILTER); + LuaFunctionCall call(lua_, NAME); call.PushJson(simplified); call.PushString(remoteAet); diff -r f9cd40166269 -r 6406f5493d92 OrthancServer/LuaScripting.h --- a/OrthancServer/LuaScripting.h Tue Jun 30 16:04:05 2015 +0200 +++ b/OrthancServer/LuaScripting.h Tue Jun 30 16:46:23 2015 +0200 @@ -52,6 +52,12 @@ IServerCommand* ParseOperation(const std::string& operation, const Json::Value& parameters); + void InitializeJob(); + + void SubmitJob(const std::string& description); + + void OnStableResource(const ServerIndexChange& change); + boost::mutex mutex_; LuaContext lua_; ServerContext& context_; diff -r f9cd40166269 -r 6406f5493d92 Resources/Toolbox.lua --- a/Resources/Toolbox.lua Tue Jun 30 16:04:05 2015 +0200 +++ b/Resources/Toolbox.lua Tue Jun 30 16:46:23 2015 +0200 @@ -32,81 +32,92 @@ end -function SendToModality(instanceId, modality, localAet) - if instanceId == nil then - error('Cannot send a nonexistent instance') +function SendToModality(resourceId, modality, localAet) + if resourceId == nil then + error('Cannot send a nonexistent resource') end table.insert(_job, { Operation = 'store-scu', - Instance = instanceId, + Resource = resourceId, Modality = modality, LocalAet = localAet }) - return instanceId + return resourceId end -function SendToPeer(instanceId, peer) - if instanceId == nil then - error('Cannot send a nonexistent instance') +function SendToPeer(resourceId, peer) + if resourceId == nil then + error('Cannot send a nonexistent resource') end table.insert(_job, { Operation = 'store-peer', - Instance = instanceId, + Resource = resourceId, Peer = peer }) - return instanceId + return resourceId end -function Delete(instanceId) - if instanceId == nil then - error('Cannot delete a nonexistent instance') +function Delete(resourceId) + if resourceId == nil then + error('Cannot delete a nonexistent resource') end table.insert(_job, { Operation = 'delete', - Instance = instanceId + Resource = resourceId }) return nil -- Forbid chaining end -function ModifyInstance(instanceId, replacements, removals, removePrivateTags) - if instanceId == nil then - error('Cannot modify a nonexistent instance') +function ModifyResource(resourceId, replacements, removals, removePrivateTags) + if resourceId == nil then + error('Cannot modify a nonexistent resource') end - if instanceId == '' then - error('Cannot modify twice an instance'); + if resourceId == '' then + error('Cannot modify twice an resource'); end table.insert(_job, { Operation = 'modify', - Instance = instanceId, + Resource = resourceId, Replace = replacements, Remove = removals, RemovePrivateTags = removePrivateTags }) + return '' -- Chain with another operation end -function CallSystem(instanceId, command, args) - if instanceId == nil then - error('Cannot modify a nonexistent instance') +function ModifyInstance(resourceId, replacements, removals, removePrivateTags) + return ModifyResource(resourceId, replacements, removals, removePrivateTags) +end + + +-- This function is only applicable to individual instances +function CallSystem(resourceId, command, args) + if resourceId == nil then + error('Cannot execute a system call on a nonexistent resource') + end + + if command == nil then + error('No command was specified for system call') end table.insert(_job, { Operation = 'call-system', - Instance = instanceId, + Resource = resourceId, Command = command, Arguments = args }) - return instanceId + return resourceId end