Skip to content
Open
Show file tree
Hide file tree
Changes from 28 commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
3b55b51
Add option to exclude Group from reports
AgostonSzepessy Dec 22, 2025
e23aee1
Move grid into vertical layout and add checkbox
AgostonSzepessy Dec 23, 2025
c75a688
Connect signals and slots
AgostonSzepessy Dec 23, 2025
316ea08
Use `CustomData` for storing excluded groups
AgostonSzepessy Dec 23, 2025
79ad4a6
Exclude groups from database reports
AgostonSzepessy Dec 23, 2025
b1fa002
Add tooltips and info for group exclusions
AgostonSzepessy Dec 23, 2025
67e81fe
Start working on including entries from excluded groups
AgostonSzepessy Dec 23, 2025
c1210d7
Add exclusion support for browser statistics
AgostonSzepessy Dec 23, 2025
09efef0
Add exclusion support for HIBP report
AgostonSzepessy Dec 23, 2025
4ffded3
Annotate whether group or entry is excluded
AgostonSzepessy Dec 23, 2025
49e945d
Add test for database reports
AgostonSzepessy Dec 23, 2025
3b3bb9a
Add test for healthcheck exclusion
AgostonSzepessy Dec 24, 2025
8df50d1
Add test for reincluding excluded group entries
AgostonSzepessy Dec 26, 2025
a27d827
Remove redundant test and cleanup
AgostonSzepessy Dec 29, 2025
2a02e02
Copilot PR feedback
AgostonSzepessy Dec 29, 2025
44daeee
Test including all entries from excluded group
AgostonSzepessy Dec 29, 2025
06f6b31
Missed Copilot feedback
AgostonSzepessy Dec 29, 2025
6042ee1
Revert "Move grid into vertical layout and add checkbox"
AgostonSzepessy Dec 29, 2025
643ad2c
Remove grid layout and add exclude checkbox
AgostonSzepessy Dec 30, 2025
1825bca
Start refactoring report widgets
AgostonSzepessy Dec 29, 2025
d7cb5b1
Factor out QSortProxyFilterModel implementations
AgostonSzepessy Dec 29, 2025
bcac630
Use `ReportsWidgetBase` for browser statistics
AgostonSzepessy Dec 29, 2025
be137a2
Use ReportsWidgetBase for HIBP report widget
AgostonSzepessy Dec 29, 2025
c9aff28
Move more methods into base class
AgostonSzepessy Dec 30, 2025
98f70f4
Refactor passkey report widget
AgostonSzepessy Dec 30, 2025
6036e7f
Fix formatting
AgostonSzepessy Dec 30, 2025
27cd97a
Fix delete plugin menu action placement
AgostonSzepessy Dec 30, 2025
ac1a170
Update translations and license dates
AgostonSzepessy Dec 31, 2025
249352a
Copilot feedback
AgostonSzepessy Dec 31, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
133 changes: 66 additions & 67 deletions share/translations/keepassxc_en.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3806,6 +3806,10 @@ Supported extensions are: %1.</source>
<source>Search toggle for this and sub groups</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Exclude from database reports</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>EditWidgetIcons</name>
Expand Down Expand Up @@ -9499,6 +9503,47 @@ This option is deprecated, use --set-key-file instead.</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>ReportsWidgetBase</name>
<message>
<source>Please wait, report is being calculated…</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Edit Entry…</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<source>Expire Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
<message numerus="yes">
<source>Delete Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
<message>
<source>Exclude Entry(s) from reports</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Exclude Group(s) from reports</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>The Group for &quot;%1&quot; is excluded. Would you like to include all Entries from there as well?</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Include Group?</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>ReportsWidgetBrowserStatistics</name>
<message>
Expand Down Expand Up @@ -9533,10 +9578,6 @@ This option is deprecated, use --set-key-file instead.</source>
<source>This entry is being excluded from reports</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Please wait, browser statistics is being calculated…</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>No entries with a URL, or none has browser extension settings saved.</source>
<translation type="unfinished"></translation>
Expand All @@ -9553,28 +9594,6 @@ This option is deprecated, use --set-key-file instead.</source>
<source>URLs</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Edit Entry…</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<source>Delete Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
<message>
<source>Exclude from reports</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<source>Expire Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
<message>
<source>Only show entries that have a URL</source>
<translation type="unfinished"></translation>
Expand All @@ -9598,6 +9617,14 @@ This option is deprecated, use --set-key-file instead.</source>
<numerusform></numerusform>
</translation>
</message>
<message>
<source> (Group Excluded)</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>The group for this entry is being excluded from reports</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>ReportsWidgetHealthcheck</name>
Expand Down Expand Up @@ -9633,10 +9660,6 @@ This option is deprecated, use --set-key-file instead.</source>
<source>This entry is being excluded from reports</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Please wait, health data is being calculated…</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Congratulations, everything is healthy!</source>
<translation type="unfinished"></translation>
Expand All @@ -9658,29 +9681,15 @@ This option is deprecated, use --set-key-file instead.</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Edit Entry…</source>
<source>Show entries that have been excluded from reports</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<source>Delete Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
<message>
<source>Exclude from reports</source>
<source> (Group Excluded)</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<source>Expire Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
<message>
<source>Show entries that have been excluded from reports</source>
<source>The group for this entry is being excluded from reports</source>
<translation type="unfinished"></translation>
</message>
</context>
Expand Down Expand Up @@ -9767,27 +9776,13 @@ This option is deprecated, use --set-key-file instead.</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Edit Entry…</source>
<source> (Group Excluded)</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<source>Delete Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
<message>
<source>Exclude from reports</source>
<source>The group for this entry is being excluded from reports</source>
<translation type="unfinished"></translation>
</message>
<message numerus="yes">
<source>Expire Entry(s)…</source>
<translation type="unfinished">
<numerusform></numerusform>
<numerusform></numerusform>
</translation>
</message>
</context>
<context>
<name>ReportsWidgetPasskeys</name>
Expand Down Expand Up @@ -9850,10 +9845,6 @@ This option is deprecated, use --set-key-file instead.</source>
<source>The passkey file will be vulnerable to theft and unauthorized use, if left unsecured. Are you sure you want to continue?</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Please wait, list of entries with passkeys is being updated…</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>No entries with passkeys.</source>
<translation type="unfinished"></translation>
Expand Down Expand Up @@ -9988,6 +9979,14 @@ This option is deprecated, use --set-key-file instead.</source>
<numerusform></numerusform>
</translation>
</message>
<message>
<source>Groups excluded from reports</source>
<translation type="unfinished"></translation>
</message>
<message>
<source>Excluding entire groups from reports isn&apos;t necessarily a problem but please exercise caution when excluding entire groups.</source>
<translation type="unfinished"></translation>
</message>
</context>
<context>
<name>SSHAgent</name>
Expand Down
1 change: 1 addition & 0 deletions src/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,7 @@ set(gui_SOURCES
gui/remote/RemoteProcess.cpp
gui/remote/RemoteSettings.cpp
gui/reports/ReportsWidget.cpp
gui/reports/ReportsWidgetBase.cpp
gui/reports/ReportsDialog.cpp
gui/reports/ReportsWidgetHealthcheck.cpp
gui/reports/ReportsPageHealthcheck.cpp
Expand Down
6 changes: 5 additions & 1 deletion src/core/DatabaseStats.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,10 @@ void DatabaseStats::gatherStats(const QList<Group*>& groups)

++groupCount;

if (group->excludeFromReports()) {
++excludedGroups;
}

for (const auto* entry : group->entries()) {
// Don't count anything in the recycle bin
if (entry->isRecycled()) {
Expand Down Expand Up @@ -107,7 +111,7 @@ void DatabaseStats::gatherStats(const QList<Group*>& groups)
++weakPasswords;
}

if (entry->excludeFromReports()) {
if (entry->excludeFromReports() || group->excludeFromReports()) {
++excludedEntries;
}

Expand Down
1 change: 1 addition & 0 deletions src/core/DatabaseStats.h
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ class DatabaseStats
int entryCount = 0; // Number of entries (across all groups)
int expiredEntries = 0; // Number of expired entries
int excludedEntries = 0; // Number of known bad entries
int excludedGroups = 0; // Number of excluded groups from reports
int weakPasswords = 0; // Number of weak or poor passwords
int shortPasswords = 0; // Number of passwords 8 characters or less in size
int uniquePasswords = 0; // Number of unique passwords
Expand Down
27 changes: 27 additions & 0 deletions src/core/Group.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1281,6 +1281,33 @@ void Group::setPreviousParentGroup(const Group* group)
setPreviousParentGroupUuid(group ? group->uuid() : QUuid());
}

void Group::setExcludeFromReports(bool excluded)
{
customData()->set(CustomData::ExcludeFromReportsLegacy, excluded ? TRUE_STR : FALSE_STR);

// Clear out the exclusion flag on entries when we set it on the
// group because it'll make it easier to individually set it for an
// entry later on
if (excluded) {
for (auto& entry : m_entries) {
entry->setExcludeFromReports(false);
}
}
}

void Group::markAllEntriesExcludedFromReports()
{
for (auto& entry : m_entries) {
entry->setExcludeFromReports(true);
}
}

bool Group::excludeFromReports() const
{
return customData()->contains(CustomData::ExcludeFromReportsLegacy)
&& customData()->value(CustomData::ExcludeFromReportsLegacy) == TRUE_STR;
}

bool Group::GroupData::operator==(const Group::GroupData& other) const
{
return equals(other, CompareItemDefault);
Expand Down
3 changes: 3 additions & 0 deletions src/core/Group.h
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,7 @@ class Group : public ModifiableObject
QString resolveCustomDataString(const QString& key, bool checkParent = true) const;
const Group* previousParentGroup() const;
QUuid previousParentGroupUuid() const;
bool excludeFromReports() const;

bool equals(const Group* other, CompareItemOptions options) const;

Expand Down Expand Up @@ -140,6 +141,8 @@ class Group : public ModifiableObject
void setMergeMode(MergeMode newMode);
void setPreviousParentGroup(const Group* group);
void setPreviousParentGroupUuid(const QUuid& uuid);
void setExcludeFromReports(bool exclude);
void markAllEntriesExcludedFromReports();

bool canUpdateTimeinfo() const;
void setUpdateTimeinfo(bool value);
Expand Down
3 changes: 3 additions & 0 deletions src/gui/group/EditGroupWidget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -126,6 +126,7 @@ void EditGroupWidget::setupModifiedTracking()
connect(m_mainUi->autoTypeSequenceInherit, SIGNAL(toggled(bool)), SLOT(setModified()));
connect(m_mainUi->autoTypeSequenceCustomRadio, SIGNAL(toggled(bool)), SLOT(setModified()));
connect(m_mainUi->autoTypeSequenceCustomEdit, SIGNAL(textChanged(QString)), SLOT(setModified()));
connect(m_mainUi->excludeReportsCheckBox, SIGNAL(stateChanged(int)), SLOT(setModified()));

// Icon tab
connect(m_editGroupWidgetIcons, SIGNAL(widgetUpdated()), SLOT(setModified()));
Expand Down Expand Up @@ -171,6 +172,7 @@ void EditGroupWidget::loadGroup(Group* group, bool create, const QSharedPointer<
m_mainUi->autoTypeSequenceCustomRadio->setChecked(true);
}
m_mainUi->autoTypeSequenceCustomEdit->setText(group->effectiveAutoTypeSequence());
m_mainUi->excludeReportsCheckBox->setChecked(m_group->excludeFromReports());

if (config()->get(Config::GUI_MonospaceNotes).toBool()) {
m_mainUi->editNotes->setFont(Font::fixedFont());
Expand Down Expand Up @@ -265,6 +267,7 @@ void EditGroupWidget::apply()

m_temporaryGroup->setSearchingEnabled(triStateFromIndex(m_mainUi->searchComboBox->currentIndex()));
m_temporaryGroup->setAutoTypeEnabled(triStateFromIndex(m_mainUi->autotypeComboBox->currentIndex()));
m_temporaryGroup->setExcludeFromReports(m_mainUi->excludeReportsCheckBox->isChecked());

if (m_mainUi->autoTypeSequenceInherit->isChecked()) {
m_temporaryGroup->setDefaultAutoTypeSequence(QString());
Expand Down
Loading
Loading