mirror of
https://github.com/DarkflameUniverse/DarkflameServer.git
synced 2026-10-02 02:43:44 +00:00
What someone may do on the dashboard is now their GM level's permissions plus the grants on their account, minus its denies (PermissionGrants.h). A deny beats a grant; denies never apply to GM 9, and settings and permissions_manage stay GM 9 only. The account's grants are read with every request (like its GM level), so a change applies at once, and they are passed through every check: RouteUtils::Can, CanViewCharacter, the rank rules (self_* and manage_equal_rank), routes guarded by a permission, the templates' `can`, the API documentation, API access, API key scopes (a key never does more than its owner may now) and WebSocket subscriptions. New permission grants_manage (GM 9 by default) and the API to manage grants: GET /api/grants/catalog, GET /api/grants, POST /api/grants, POST /api/grants/:id/remove. Nobody grants or takes away what they don't hold themselves (a permission, every permission of a group, a command they may use, every command up to their own GM level), and only on accounts the rank rules let them manage (their own with self_moderation). Commands with a fixed level or a floor above GM 1 (/execute) can't be granted. Every change goes in the audit log (grant_permission, deny_permission, remove_grant). Also: the Showcase gate and the traffic subscription now check their permission by name. Check: grant a GM 2 account accounts_ban (it can ban, and the Ban button shows); deny a GM 8 account accounts_view (the accounts list is refused); give an expiry a minute ahead and see it stop; try to grant a permission your account doesn't have (refused); dWebTests PermissionGrantsTests. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
34 lines
1.1 KiB
C++
34 lines
1.1 KiB
C++
#pragma once
|
|
|
|
#include <cstdint>
|
|
#include <optional>
|
|
#include <string>
|
|
#include <vector>
|
|
|
|
#include "PermissionGrants.h"
|
|
|
|
#include "json.hpp"
|
|
|
|
struct HTTPContext;
|
|
|
|
// Server settings stored in the database and edited from the dashboard (GM 9)
|
|
void RegisterSettingsRoutes();
|
|
|
|
/**
|
|
* Save one setting the way the Settings page does: checked, stored, audited, written to the setting history and every
|
|
* server told to reload. Body: {file, name, value (null clears the web value), webWins}. revertOf: the history entry
|
|
* this undoes. Returns why it was refused, if it was.
|
|
*/
|
|
std::optional<std::string> SaveSetting(const HTTPContext& context, const nlohmann::json& body, uint64_t revertOf = 0);
|
|
|
|
// A slash command the world servers registered, with the level it needs now (as the Permissions page shows it)
|
|
struct SlashCommandNow {
|
|
PermissionGrants::Command rules; // name, level now, floor, fixed, paired permission
|
|
std::vector<std::string> aliases;
|
|
std::string help;
|
|
bool clientHandled{};
|
|
};
|
|
|
|
// Every slash command the world servers registered (empty until a world has started once)
|
|
std::vector<SlashCommandNow> CurrentSlashCommands();
|