-
Notifications
You must be signed in to change notification settings - Fork 55
fix: add command whitelist validation for notification actions #1388
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fix: add command whitelist validation for notification actions #1388
Conversation
|
[APPROVALNOTIFIER] This PR is NOT APPROVED This pull-request has been approved by: yixinshark The full list of commands accepted by this bot can be found here. DetailsNeeds approval from an approver in each of these files:Approvers can indicate their approval by writing |
Reviewer's guide (collapsed on small PRs)Reviewer's GuideAdds a DConfig-based whitelist of allowed shell commands for notification actions and validates notification action commands against this whitelist before executing them. Sequence diagram for notification action command validation and executionsequenceDiagram
actor User
participant App
participant NotificationServer
participant NotificationManager
participant DConfig
participant QProcess
User->>App: TriggerNotificationAction
App->>NotificationServer: ActionInvoked(entity, actionKey)
NotificationServer->>NotificationManager: doActionInvoked(entity, actionKey)
NotificationManager->>NotificationManager: ParseActionArguments
NotificationManager->>NotificationManager: Extract cmd and args
NotificationManager->>DConfig: create(org.deepin.dde.shell, org.deepin.dde.shell.notification)
DConfig-->>NotificationManager: DConfigInstance
NotificationManager->>DConfig: value(safeCommands)
DConfig-->>NotificationManager: safeCommands
NotificationManager->>NotificationManager: Check cmd in safeCommands
alt CommandNotWhitelisted
NotificationManager-->>NotificationServer: LogWarningAndReturn
else CommandWhitelisted
NotificationManager->>QProcess: setProgram(cmd)
NotificationManager->>QProcess: setArguments(args)
NotificationManager->>QProcess: start()
QProcess-->>NotificationManager: ExecutionResult
NotificationManager-->>NotificationServer: ActionHandled
end
Class diagram for NotificationManager command execution with DConfig whitelistclassDiagram
class NotificationManager {
+void doActionInvoked(NotifyEntity entity, QString actionKey)
}
class DConfig {
+static DConfig* create(QString domain, QString name)
+QVariant value(QString key)
}
class QProcess {
+void setProgram(QString program)
+void setArguments(QStringList arguments)
+void start()
}
class NotifyEntity {
+QString appName
+QString summary
+QString body
+QStringList actions
}
NotificationManager --> DConfig : uses
NotificationManager --> QProcess : creates_and_uses
NotificationManager --> NotifyEntity : parameter
Flow diagram for notification action command whitelist validationflowchart TD
A[Start doActionInvoked] --> B[Check entity and action type]
B --> C[Extract args list]
C --> D{args is empty}
D -->|Yes| E[Return without executing]
D -->|No| F[cmd = args.takeFirst]
F --> G[Create DConfig with org.deepin.dde.shell and org.deepin.dde.shell.notification]
G --> H[Read safeCommands from DConfig]
H --> I{safeCommands contains cmd}
I -->|No| J[Log warning command not allowed]
J --> K[Return without executing]
I -->|Yes| L[Initialize QProcess]
L --> M[Set program to cmd]
M --> N[Set arguments to remaining args]
N --> O[Start QProcess]
O --> P[Return after starting process]
E --> P
K --> P
File-Level Changes
Tips and commandsInteracting with Sourcery
Customizing Your ExperienceAccess your dashboard to:
Getting Help
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hey - I've found 1 issue, and left some high level feedback:
- Creating a new DConfig instance on every action invocation may be unnecessary overhead; consider caching the config or the
safeCommandslist at the class level and refreshing it only when the config changes. - If the
safeCommandslist is missing or empty, the current logic will block all commands; consider explicitly handling this case (e.g., with a clear fallback or error) so behavior is intentional and easier to diagnose. - The warning log prints the entire
safeCommandslist on each blocked command, which may be noisy and expose internal configuration; consider logging only the rejected command and perhaps the list size or a config version instead.
Prompt for AI Agents
Please address the comments from this code review:
## Overall Comments
- Creating a new DConfig instance on every action invocation may be unnecessary overhead; consider caching the config or the `safeCommands` list at the class level and refreshing it only when the config changes.
- If the `safeCommands` list is missing or empty, the current logic will block all commands; consider explicitly handling this case (e.g., with a clear fallback or error) so behavior is intentional and easier to diagnose.
- The warning log prints the entire `safeCommands` list on each blocked command, which may be noisy and expose internal configuration; consider logging only the rejected command and perhaps the list size or a config version instead.
## Individual Comments
### Comment 1
<location> `panels/notification/server/notificationmanager.cpp:536-537` </location>
<code_context>
if (!args.isEmpty()) {
QString cmd = args.takeFirst(); // 命令
+ QScopedPointer<DConfig> config(DConfig::create("org.deepin.dde.shell", "org.deepin.dde.shell.notification"));
+ QStringList safeCommands = config->value("safeCommands").toStringList();
+
+ if (!safeCommands.contains(cmd)) {
</code_context>
<issue_to_address>
**issue (bug_risk):** Guard against DConfig::create() returning nullptr before dereferencing `config`.
If `DConfig::create()` returns `nullptr`, `config->value(...)` will dereference a null pointer and crash. Please check `config` before use and either treat a null config as "no safe commands" (deny all) or fall back to a reasonable default.
</issue_to_address>Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.
| QScopedPointer<DConfig> config(DConfig::create("org.deepin.dde.shell", "org.deepin.dde.shell.notification")); | ||
| QStringList safeCommands = config->value("safeCommands").toStringList(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
issue (bug_risk): Guard against DConfig::create() returning nullptr before dereferencing config.
If DConfig::create() returns nullptr, config->value(...) will dereference a null pointer and crash. Please check config before use and either treat a null config as "no safe commands" (deny all) or fall back to a reasonable default.
48d4672 to
58b6112
Compare
Add safeCommands whitelist in dconfig with default safe commands Validate commands against whitelist before execution Log: add command whitelist validation for notification actions
58b6112 to
b037c00
Compare
|
/forcemerge |
|
This pr force merged! (status: blocked) |
Add safeCommands whitelist in dconfig with default safe commands
Validate commands against whitelist before execution
Log: add command whitelist validation for notification actions
Summary by Sourcery
Validate notification action commands against a configurable whitelist before executing them.
Bug Fixes:
Enhancements: