Skip to content

Commit d02cdda

Browse files
authored
Merge pull request #10716 from Icinga/drop-thread-local-variable-apiuser
Remove `AuthenticatedApiUser` thread-local variable & pass it as arg instead
2 parents f5d5357 + 3b80153 commit d02cdda

File tree

6 files changed

+94
-63
lines changed

6 files changed

+94
-63
lines changed

lib/icinga/apiactions.cpp

Lines changed: 74 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,11 @@ Dictionary::Ptr ApiActions::CreateResult(int code, const String& status,
5454
return result;
5555
}
5656

57-
Dictionary::Ptr ApiActions::ProcessCheckResult(const ConfigObject::Ptr& object,
58-
const Dictionary::Ptr& params)
57+
Dictionary::Ptr ApiActions::ProcessCheckResult(
58+
const ConfigObject::Ptr& object,
59+
const ApiUser::Ptr&,
60+
const Dictionary::Ptr& params
61+
)
5962
{
6063
using Result = Checkable::ProcessingResult;
6164

@@ -141,8 +144,11 @@ Dictionary::Ptr ApiActions::ProcessCheckResult(const ConfigObject::Ptr& object,
141144
return ApiActions::CreateResult(500, "Unexpected result (" + std::to_string(static_cast<int>(result)) + ") for object '" + checkable->GetName() + "'. Please submit a bug report at https://github.com/Icinga/icinga2");
142145
}
143146

144-
Dictionary::Ptr ApiActions::RescheduleCheck(const ConfigObject::Ptr& object,
145-
const Dictionary::Ptr& params)
147+
Dictionary::Ptr ApiActions::RescheduleCheck(
148+
const ConfigObject::Ptr& object,
149+
const ApiUser::Ptr&,
150+
const Dictionary::Ptr& params
151+
)
146152
{
147153
Checkable::Ptr checkable = static_pointer_cast<Checkable>(object);
148154

@@ -166,8 +172,11 @@ Dictionary::Ptr ApiActions::RescheduleCheck(const ConfigObject::Ptr& object,
166172
return ApiActions::CreateResult(200, "Successfully rescheduled check for object '" + checkable->GetName() + "'.");
167173
}
168174

169-
Dictionary::Ptr ApiActions::SendCustomNotification(const ConfigObject::Ptr& object,
170-
const Dictionary::Ptr& params)
175+
Dictionary::Ptr ApiActions::SendCustomNotification(
176+
const ConfigObject::Ptr& object,
177+
const ApiUser::Ptr&,
178+
const Dictionary::Ptr& params
179+
)
171180
{
172181
Checkable::Ptr checkable = static_pointer_cast<Checkable>(object);
173182

@@ -189,8 +198,11 @@ Dictionary::Ptr ApiActions::SendCustomNotification(const ConfigObject::Ptr& obje
189198
return ApiActions::CreateResult(200, "Successfully sent custom notification for object '" + checkable->GetName() + "'.");
190199
}
191200

192-
Dictionary::Ptr ApiActions::DelayNotification(const ConfigObject::Ptr& object,
193-
const Dictionary::Ptr& params)
201+
Dictionary::Ptr ApiActions::DelayNotification(
202+
const ConfigObject::Ptr& object,
203+
const ApiUser::Ptr&,
204+
const Dictionary::Ptr& params
205+
)
194206
{
195207
Checkable::Ptr checkable = static_pointer_cast<Checkable>(object);
196208

@@ -207,8 +219,11 @@ Dictionary::Ptr ApiActions::DelayNotification(const ConfigObject::Ptr& object,
207219
return ApiActions::CreateResult(200, "Successfully delayed notifications for object '" + checkable->GetName() + "'.");
208220
}
209221

210-
Dictionary::Ptr ApiActions::AcknowledgeProblem(const ConfigObject::Ptr& object,
211-
const Dictionary::Ptr& params)
222+
Dictionary::Ptr ApiActions::AcknowledgeProblem(
223+
const ConfigObject::Ptr& object,
224+
const ApiUser::Ptr&,
225+
const Dictionary::Ptr& params
226+
)
212227
{
213228
Checkable::Ptr checkable = static_pointer_cast<Checkable>(object);
214229

@@ -269,8 +284,11 @@ Dictionary::Ptr ApiActions::AcknowledgeProblem(const ConfigObject::Ptr& object,
269284
return ApiActions::CreateResult(200, "Successfully acknowledged problem for object '" + checkable->GetName() + "'.");
270285
}
271286

272-
Dictionary::Ptr ApiActions::RemoveAcknowledgement(const ConfigObject::Ptr& object,
273-
const Dictionary::Ptr& params)
287+
Dictionary::Ptr ApiActions::RemoveAcknowledgement(
288+
const ConfigObject::Ptr& object,
289+
const ApiUser::Ptr&,
290+
const Dictionary::Ptr& params
291+
)
274292
{
275293
Checkable::Ptr checkable = static_pointer_cast<Checkable>(object);
276294

@@ -293,8 +311,11 @@ Dictionary::Ptr ApiActions::RemoveAcknowledgement(const ConfigObject::Ptr& objec
293311
return ApiActions::CreateResult(200, "Successfully removed acknowledgement for object '" + checkable->GetName() + "'.");
294312
}
295313

296-
Dictionary::Ptr ApiActions::AddComment(const ConfigObject::Ptr& object,
297-
const Dictionary::Ptr& params)
314+
Dictionary::Ptr ApiActions::AddComment(
315+
const ConfigObject::Ptr& object,
316+
const ApiUser::Ptr&,
317+
const Dictionary::Ptr& params
318+
)
298319
{
299320
Checkable::Ptr checkable = static_pointer_cast<Checkable>(object);
300321

@@ -332,8 +353,11 @@ Dictionary::Ptr ApiActions::AddComment(const ConfigObject::Ptr& object,
332353
+ "'.", additional);
333354
}
334355

335-
Dictionary::Ptr ApiActions::RemoveComment(const ConfigObject::Ptr& object,
336-
const Dictionary::Ptr& params)
356+
Dictionary::Ptr ApiActions::RemoveComment(
357+
const ConfigObject::Ptr& object,
358+
const ApiUser::Ptr&,
359+
const Dictionary::Ptr& params
360+
)
337361
{
338362
ConfigObjectsSharedLock lock (std::try_to_lock);
339363

@@ -366,8 +390,11 @@ Dictionary::Ptr ApiActions::RemoveComment(const ConfigObject::Ptr& object,
366390
return ApiActions::CreateResult(200, "Successfully removed comment '" + commentName + "'.");
367391
}
368392

369-
Dictionary::Ptr ApiActions::ScheduleDowntime(const ConfigObject::Ptr& object,
370-
const Dictionary::Ptr& params)
393+
Dictionary::Ptr ApiActions::ScheduleDowntime(
394+
const ConfigObject::Ptr& object,
395+
const ApiUser::Ptr&,
396+
const Dictionary::Ptr& params
397+
)
371398
{
372399
Checkable::Ptr checkable = static_pointer_cast<Checkable>(object);
373400

@@ -536,8 +563,11 @@ Dictionary::Ptr ApiActions::ScheduleDowntime(const ConfigObject::Ptr& object,
536563
downtimeName + "' for object '" + checkable->GetName() + "'.", additional);
537564
}
538565

539-
Dictionary::Ptr ApiActions::RemoveDowntime(const ConfigObject::Ptr& object,
540-
const Dictionary::Ptr& params)
566+
Dictionary::Ptr ApiActions::RemoveDowntime(
567+
const ConfigObject::Ptr& object,
568+
const ApiUser::Ptr&,
569+
const Dictionary::Ptr& params
570+
)
541571
{
542572
ConfigObjectsSharedLock lock (std::try_to_lock);
543573

@@ -589,24 +619,29 @@ Dictionary::Ptr ApiActions::RemoveDowntime(const ConfigObject::Ptr& object,
589619
}
590620
}
591621

592-
Dictionary::Ptr ApiActions::ShutdownProcess(const ConfigObject::Ptr&,
593-
[[maybe_unused]] const Dictionary::Ptr& params)
622+
Dictionary::Ptr ApiActions::ShutdownProcess(
623+
const ConfigObject::Ptr&,
624+
const ApiUser::Ptr&,
625+
[[maybe_unused]] const Dictionary::Ptr& params
626+
)
594627
{
595628
Application::RequestShutdown();
596629

597630
return ApiActions::CreateResult(200, "Shutting down Icinga 2.");
598631
}
599632

600-
Dictionary::Ptr ApiActions::RestartProcess(const ConfigObject::Ptr&,
601-
[[maybe_unused]] const Dictionary::Ptr& params)
633+
Dictionary::Ptr ApiActions::RestartProcess(
634+
const ConfigObject::Ptr&,
635+
const ApiUser::Ptr&,
636+
[[maybe_unused]] const Dictionary::Ptr& params
637+
)
602638
{
603639
Application::RequestRestart();
604640

605641
return ApiActions::CreateResult(200, "Restarting Icinga 2.");
606642
}
607643

608-
Dictionary::Ptr ApiActions::GenerateTicket(const ConfigObject::Ptr&,
609-
const Dictionary::Ptr& params)
644+
Dictionary::Ptr ApiActions::GenerateTicket(const ConfigObject::Ptr&, const ApiUser::Ptr&, const Dictionary::Ptr& params)
610645
{
611646
if (!params->Contains("cn"))
612647
return ApiActions::CreateResult(400, "Option 'cn' is required");
@@ -654,7 +689,11 @@ Value ApiActions::GetSingleObjectByNameUsingPermissions(const String& type, cons
654689
return objs.at(0);
655690
};
656691

657-
Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, const Dictionary::Ptr& params)
692+
Dictionary::Ptr ApiActions::ExecuteCommand(
693+
const ConfigObject::Ptr& object,
694+
const ApiUser::Ptr& apiUser,
695+
const Dictionary::Ptr& params
696+
)
658697
{
659698
ApiListener::Ptr listener = ApiListener::GetInstance();
660699

@@ -718,11 +757,11 @@ Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, cons
718757
nullptr, MacroProcessor::EscapeCallback(), nullptr, false
719758
);
720759

721-
if (!ActionsHandler::AuthenticatedApiUser)
760+
if (!apiUser)
722761
BOOST_THROW_EXCEPTION(std::invalid_argument("Can't find API user."));
723762

724763
/* Get endpoint */
725-
Endpoint::Ptr endpointPtr = GetSingleObjectByNameUsingPermissions(Endpoint::GetTypeName(), resolved_endpoint, ActionsHandler::AuthenticatedApiUser);
764+
Endpoint::Ptr endpointPtr = GetSingleObjectByNameUsingPermissions(Endpoint::GetTypeName(), resolved_endpoint, apiUser);
726765

727766
if (!endpointPtr)
728767
return ApiActions::CreateResult(404, "Can't find a valid endpoint for '" + resolved_endpoint + "'.");
@@ -780,7 +819,7 @@ Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, cons
780819
Dictionary::Ptr execParams = new Dictionary();
781820

782821
if (command_type == "CheckCommand") {
783-
CheckCommand::Ptr cmd = GetSingleObjectByNameUsingPermissions(CheckCommand::GetTypeName(), resolved_command, ActionsHandler::AuthenticatedApiUser);
822+
CheckCommand::Ptr cmd = GetSingleObjectByNameUsingPermissions(CheckCommand::GetTypeName(), resolved_command, apiUser);
784823

785824
if (!cmd)
786825
return ApiActions::CreateResult(404, "Can't find a valid " + command_type + " for '" + resolved_command + "'.");
@@ -792,7 +831,7 @@ Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, cons
792831
cmd->Execute(checkable, cr, listener->GetWaitGroup(), execMacros, false);
793832
}
794833
} else if (command_type == "EventCommand") {
795-
EventCommand::Ptr cmd = GetSingleObjectByNameUsingPermissions(EventCommand::GetTypeName(), resolved_command, ActionsHandler::AuthenticatedApiUser);
834+
EventCommand::Ptr cmd = GetSingleObjectByNameUsingPermissions(EventCommand::GetTypeName(), resolved_command, apiUser);
796835

797836
if (!cmd)
798837
return ApiActions::CreateResult(404, "Can't find a valid " + command_type + " for '" + resolved_command + "'.");
@@ -804,7 +843,7 @@ Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, cons
804843
cmd->Execute(checkable, execMacros, false);
805844
}
806845
} else if (command_type == "NotificationCommand") {
807-
NotificationCommand::Ptr cmd = GetSingleObjectByNameUsingPermissions(NotificationCommand::GetTypeName(), resolved_command, ActionsHandler::AuthenticatedApiUser);
846+
NotificationCommand::Ptr cmd = GetSingleObjectByNameUsingPermissions(NotificationCommand::GetTypeName(), resolved_command, apiUser);
808847

809848
if (!cmd)
810849
return ApiActions::CreateResult(404, "Can't find a valid " + command_type + " for '" + resolved_command + "'.");
@@ -821,7 +860,7 @@ Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, cons
821860
MacroProcessor::EscapeCallback(), nullptr, false
822861
);
823862

824-
User::Ptr user = GetSingleObjectByNameUsingPermissions(User::GetTypeName(), resolved_user, ActionsHandler::AuthenticatedApiUser);
863+
User::Ptr user = GetSingleObjectByNameUsingPermissions(User::GetTypeName(), resolved_user, apiUser);
825864

826865
if (!user)
827866
return ApiActions::CreateResult(404, "Can't find a valid user for '" + resolved_user + "'.");
@@ -840,7 +879,7 @@ Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, cons
840879
MacroProcessor::EscapeCallback(), nullptr, false
841880
);
842881

843-
Notification::Ptr notification = GetSingleObjectByNameUsingPermissions(Notification::GetTypeName(), resolved_notification, ActionsHandler::AuthenticatedApiUser);
882+
Notification::Ptr notification = GetSingleObjectByNameUsingPermissions(Notification::GetTypeName(), resolved_notification, apiUser);
844883

845884
if (!notification)
846885
return ApiActions::CreateResult(404, "Can't find a valid notification for '" + resolved_notification + "'.");
@@ -853,7 +892,7 @@ Dictionary::Ptr ApiActions::ExecuteCommand(const ConfigObject::Ptr& object, cons
853892
});
854893

855894
cmd->Execute(notification, user, cr, NotificationType::NotificationCustom,
856-
ActionsHandler::AuthenticatedApiUser->GetName(), "", execMacros, false);
895+
apiUser->GetName(), "", execMacros, false);
857896
}
858897
}
859898

lib/icinga/apiactions.hpp

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -18,20 +18,20 @@ namespace icinga
1818
class ApiActions
1919
{
2020
public:
21-
static Dictionary::Ptr ProcessCheckResult(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
22-
static Dictionary::Ptr RescheduleCheck(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
23-
static Dictionary::Ptr SendCustomNotification(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
24-
static Dictionary::Ptr DelayNotification(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
25-
static Dictionary::Ptr AcknowledgeProblem(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
26-
static Dictionary::Ptr RemoveAcknowledgement(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
27-
static Dictionary::Ptr AddComment(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
28-
static Dictionary::Ptr RemoveComment(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
29-
static Dictionary::Ptr ScheduleDowntime(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
30-
static Dictionary::Ptr RemoveDowntime(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
31-
static Dictionary::Ptr ShutdownProcess(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
32-
static Dictionary::Ptr RestartProcess(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
33-
static Dictionary::Ptr GenerateTicket(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
34-
static Dictionary::Ptr ExecuteCommand(const ConfigObject::Ptr& object, const Dictionary::Ptr& params);
21+
static Dictionary::Ptr ProcessCheckResult(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
22+
static Dictionary::Ptr RescheduleCheck(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
23+
static Dictionary::Ptr SendCustomNotification(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
24+
static Dictionary::Ptr DelayNotification(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
25+
static Dictionary::Ptr AcknowledgeProblem(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
26+
static Dictionary::Ptr RemoveAcknowledgement(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
27+
static Dictionary::Ptr AddComment(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
28+
static Dictionary::Ptr RemoveComment(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
29+
static Dictionary::Ptr ScheduleDowntime(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
30+
static Dictionary::Ptr RemoveDowntime(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
31+
static Dictionary::Ptr ShutdownProcess(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
32+
static Dictionary::Ptr RestartProcess(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
33+
static Dictionary::Ptr GenerateTicket(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
34+
static Dictionary::Ptr ExecuteCommand(const ConfigObject::Ptr& object, const ApiUser::Ptr& apiUser, const Dictionary::Ptr& params);
3535

3636
private:
3737
static Dictionary::Ptr CreateResult(int code, const String& status, const Dictionary::Ptr& additional = nullptr);

lib/remote/actionshandler.cpp

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,6 @@
1212

1313
using namespace icinga;
1414

15-
thread_local ApiUser::Ptr ActionsHandler::AuthenticatedApiUser;
16-
1715
REGISTER_URLHANDLER("/v1/actions", ActionsHandler);
1816

1917
bool ActionsHandler::HandleRequest(
@@ -80,11 +78,6 @@ bool ActionsHandler::HandleRequest(
8078

8179
bool verbose = false;
8280

83-
ActionsHandler::AuthenticatedApiUser = user;
84-
Defer a ([]() {
85-
ActionsHandler::AuthenticatedApiUser = nullptr;
86-
});
87-
8881
if (params)
8982
verbose = HttpUtility::GetLastParameter(params, "verbose");
9083

@@ -111,7 +104,7 @@ bool ActionsHandler::HandleRequest(
111104
}
112105

113106
try {
114-
results.emplace_back(action->Invoke(obj, params));
107+
results.emplace_back(action->Invoke(obj, user, params));
115108
} catch (const std::exception& ex) {
116109
Dictionary::Ptr fail = new Dictionary({
117110
{ "code", 500 },

lib/remote/actionshandler.hpp

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,6 @@ class ActionsHandler final : public HttpHandler
1414
public:
1515
DECLARE_PTR_TYPEDEFS(ActionsHandler);
1616

17-
static thread_local ApiUser::Ptr AuthenticatedApiUser;
18-
1917
bool HandleRequest(
2018
const WaitGroup::Ptr& waitGroup,
2119
const HttpApiRequest& request,

lib/remote/apiaction.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,9 @@ ApiAction::ApiAction(std::vector<String> types, Callback action)
1313
: m_Types(std::move(types)), m_Callback(std::move(action))
1414
{ }
1515

16-
Value ApiAction::Invoke(const ConfigObject::Ptr& target, const Dictionary::Ptr& params)
16+
Value ApiAction::Invoke(const ConfigObject::Ptr& target, const ApiUser::Ptr& user, const Dictionary::Ptr& params)
1717
{
18-
return m_Callback(target, params);
18+
return m_Callback(target, user, params);
1919
}
2020

2121
const std::vector<String>& ApiAction::GetTypes() const

lib/remote/apiaction.hpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
#include "base/value.hpp"
1010
#include "base/dictionary.hpp"
1111
#include "base/configobject.hpp"
12+
#include "remote/apiuser.hpp"
1213
#include <vector>
1314
#include <boost/algorithm/string/replace.hpp>
1415

@@ -25,11 +26,11 @@ class ApiAction final : public Object
2526
public:
2627
DECLARE_PTR_TYPEDEFS(ApiAction);
2728

28-
typedef std::function<Value(const ConfigObject::Ptr& target, const Dictionary::Ptr& params)> Callback;
29+
typedef std::function<Value(const ConfigObject::Ptr& target, const ApiUser::Ptr&, const Dictionary::Ptr& params)> Callback;
2930

3031
ApiAction(std::vector<String> registerTypes, Callback function);
3132

32-
Value Invoke(const ConfigObject::Ptr& target, const Dictionary::Ptr& params);
33+
Value Invoke(const ConfigObject::Ptr& target, const ApiUser::Ptr& user, const Dictionary::Ptr& params);
3334

3435
const std::vector<String>& GetTypes() const;
3536

0 commit comments

Comments
 (0)