Commit Graph

372 Commits

Author SHA1 Message Date
0c5adf17ab Fix Cove Run import button submission in settings 2026-02-23 11:02:56 +01:00
9b19283c97 Add Cove Accounts inbox-style flow for linking accounts to jobs
- CoveAccount staging model: all Cove accounts upserted from API;
  unmatched accounts visible on /cove/accounts before job linking
- cove_importer.py: always upserts accounts, creates JobRuns only for
  accounts with a linked job (deduplication via external_id)
- routes_cove.py: GET /cove/accounts, POST link/unlink routes
- cove_accounts.html: inbox-style page with Bootstrap modals for
  creating new jobs or linking to existing ones
- Nav bar: Cove Accounts link for admin/operator when cove_enabled
- DB migration: migrate_cove_accounts_table() for staging table

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-02-23 10:40:54 +01:00
c045240001 Add manual Cove import trigger (Run import now button)
- New route POST /settings/cove/run-now calls run_cove_import()
  directly and shows result as flash message
- Settings > Integrations > Cove: "Run import now" button visible
  when partner_id is known (connection confirmed)
- Status bar shows partner ID, last import timestamp or "No import yet"

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-02-23 10:28:33 +01:00
3bd8178464 Fix Cove importer: correct API payload format and response parsing
- Login: use lowercase username/password params and id="jsonrpc"
- Login: visa is at top-level of response (not inside result)
- EnumerateAccountStatistics: use lowercase query param, RecordsCount
  instead of RecordCount, remove DisplayColumns (not needed)
- _flatten_settings: Settings items are single-key dicts like
  {"D09F00": "5"}, not {Key: ..., Value: ...} - use dict.update()
- _cove_enumerate: unwrap nested result and handle Accounts key
- _process_account: AccountId is top-level field, not from Settings

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-02-23 10:21:01 +01:00
2f1cc20263 Add Cove Data Protection full integration
- New models: SystemSettings gets 8 cove_* fields, Job gets
  cove_account_id, JobRun gets source_type and external_id
- Migration migrate_cove_integration() adds all new DB columns and
  a deduplication index on job_runs.external_id
- cove_importer.py: Cove API login, paginated EnumerateAccountStatistics,
  deduplication via external_id, JobRun creation, per-datasource
  run_object_links persistence (Files&Folders, VssMsSql, M365, etc.)
- cove_importer_service.py: background thread, same pattern as
  auto_importer_service, respects cove_import_interval_minutes
- __init__.py: starts cove_importer thread on app startup
- routes_settings.py: Cove form handling (POST), has_cove_password
  variable, new AJAX route /settings/cove/test-connection
- routes_jobs.py: new route /jobs/<id>/set-cove-account,
  cove_enabled passed to job_detail template
- settings.html: Cove card in Integrations tab with AJAX test button
- job_detail.html: Cove Integration card with Account ID input

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-02-23 10:13:34 +01:00
38f0f8954e Fix remark visibility in run alerts 2026-02-19 14:14:44 +01:00
2ee5db8882 Auto-commit local changes before build (2026-02-19 13:45:13) 2026-02-19 13:45:13 +01:00
ea244193e0 Hide non-backup 3CX informational jobs from Run Checks 2026-02-19 13:44:46 +01:00
441f5a8e50 Handle 3CX update mails as informational runs 2026-02-19 13:27:52 +01:00
e0e8ed2b0d Auto-commit local changes before build (2026-02-19 12:57:34) 2026-02-19 12:57:34 +01:00
53b028ef78 Add optional Autotask ID import toggle 2026-02-19 12:56:45 +01:00
f2c0d0b36a Auto-commit local changes before build (2026-02-16 16:58:07) 2026-02-16 16:58:07 +01:00
652da5e117 Add remarks to global search results 2026-02-16 16:57:51 +01:00
c8e7491c94 Add Daily Jobs note to search results 2026-02-16 16:54:26 +01:00
e5da01cfbb Auto-commit local changes before build (2026-02-16 16:50:14) 2026-02-16 16:50:14 +01:00
b46010dbc2 Forward global search filters to overview pages 2026-02-16 16:49:47 +01:00
f90b2bdcf6 Keep search pagination at current section 2026-02-16 16:32:23 +01:00
2beba3bc9d Auto-commit local changes before build (2026-02-16 16:27:14) 2026-02-16 16:27:14 +01:00
ded71cb50f Improve daily jobs search metadata and modal link 2026-02-16 16:26:56 +01:00
dc3eb2f73c Auto-commit local changes before build (2026-02-16 16:19:53) 2026-02-16 16:19:53 +01:00
8a8f957c9f Add per-section pagination to global search 2026-02-16 16:19:26 +01:00
fcce3b8854 Fix search template section items iteration 2026-02-16 16:09:22 +01:00
7476ebcbe3 Add role-aware global grouped search 2026-02-16 16:05:47 +01:00
dca117ed79 Add customer-to-jobs filtering navigation 2026-02-16 15:12:10 +01:00
b5cf91d5f2 Fix checkboxes auto-selecting after page reload on Inbox and Run Checks
Added autocomplete="off" attribute to all checkboxes to prevent browser from
automatically restoring checkbox states after page reload.

Changes:
- Inbox page: Added autocomplete="off" to select-all and row checkboxes
- Run Checks page: Added autocomplete="off" to select-all and row checkboxes

This fixes the issue where after deleting items, the browser would automatically
re-select the same number of checkboxes that were previously selected, causing
unwanted selections on the reloaded page.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-13 11:00:21 +01:00
6468cbbc74 Fix Autotask and internal tickets not linking to missed runs
Added ticket linking to missed runs by calling link_open_internal_tickets_to_run
after creating missed JobRun records in _ensure_missed_runs_for_job function.

Changes:
- Added import for link_open_internal_tickets_to_run in routes_run_checks.py
- Added db.session.flush() and ticket linking call after creating weekly missed runs
- Added db.session.flush() and ticket linking call after creating monthly missed runs
- Ensures missed runs receive same ticket propagation as email-based runs

This fixes the issue where missed runs were not showing linked internal tickets
or Autotask tickets, while error/warning runs from emails were working correctly.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-13 10:52:00 +01:00
2e0baa4e35 Fix copy ticket button not working in Edge on Job Details page
Moved clipboard functions (copyToClipboard, fallbackCopy, showCopyFeedback)
inside IIFE scope for proper closure access. Edge browser is stricter than
Firefox about scope resolution - functions must be in same scope as event
listeners that call them.

Previously these functions were in global scope while event listeners were
in IIFE scope, which worked in Firefox but failed silently in Edge.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-12 11:52:32 +01:00
c5cf07f4e5 Fix tickets not showing in Run Checks modal detail view
Extended /api/job-runs/<run_id>/alerts endpoint to include both:
- Tickets explicitly linked to run via ticket_job_runs (audit trail)
- Tickets linked to job via ticket_scopes (active on run date)

Previously only ticket_job_runs was queried, causing newly created
tickets to not appear in the Meldingen section of the Run Checks modal.
They would only appear after being resolved (which creates a
ticket_job_runs entry). Now both sources are queried and duplicates
are prevented.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-12 10:53:00 +01:00
35ec337c54 Add copy ticket button to Job Details and improve cross-browser copy functionality
Changes:
- Added copy ticket button (⧉) next to ticket numbers in Job Details modal
- Implemented robust cross-browser clipboard copy mechanism:
  1. Modern navigator.clipboard API (works in HTTPS contexts)
  2. Legacy document.execCommand('copy') fallback (works in older browsers)
  3. Prompt fallback as last resort
- Applied improved copy function to both Run Checks and Job Details pages
- Copy now works directly in all browsers (Firefox, Edge, Chrome) without popup

This eliminates the manual copy step in Edge that previously required a popup.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 15:04:21 +01:00
0510613708 Fix: Allow admins to view screenshots of deleted feedback items
Two fixes:
1. Improved deleted item row styling (opacity + background)
2. Allow feedback_attachment route to serve images from deleted items (admin only)

Before: Screenshots shown as links only (2026-02-10_13_29_39.png)
After: Screenshots shown as images/thumbnails

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 13:46:24 +01:00
fc99f17db3 Add admin view for deleted feedback items + permanent delete
User request: Allow admins to view deleted items and permanently
delete them (hard delete) to clean up database and remove screenshots.

Features:
1. Admin-only "Show deleted" checkbox on feedback list
2. Deleted items shown with gray background + "Deleted" badge
3. Permanent delete button (only for soft-deleted items)
4. Hard delete removes item + all attachments from database
5. Admins can view detail pages of deleted items

Backend (routes_feedback.py):
- Added show_deleted parameter (admin only)
- Modified feedback_page query to optionally include deleted items
- Added deleted_at, deleted_by to query results
- Modified feedback_detail to allow admins to view deleted items
- New route: feedback_permanent_delete (hard delete)
  - Only works on already soft-deleted items (safety check)
  - Uses db.session.delete() - CASCADE removes attachments
  - Shows attachment count in confirmation message

Frontend:
- feedback.html:
  - "Show deleted items" checkbox (auto-submits form)
  - Deleted items: gray background (table-secondary)
  - Shows deleted timestamp
  - "Permanent Delete" button in Actions column
  - Confirmation dialog warns about permanent deletion
- feedback_detail.html:
  - "Deleted" badge in header
  - Actions sidebar shows warning + "Permanent Delete" button
  - Normal actions (resolve/delete) hidden for deleted items

Benefits:
- Audit trail preserved with soft delete
- Database can be cleaned up later by removing old deleted items
- Screenshots (BYTEA) don't accumulate forever
- Two-stage safety: soft delete → permanent delete

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 13:40:53 +01:00
1a506c0713 Fix: Add FeedbackAttachment to routes_shared imports
Missing import caused NameError when creating feedback with screenshots.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 13:30:47 +01:00
451ce1ab22 Add screenshot attachment support to Feedback/Bug system
User request: Allow screenshots to be attached to bug reports
and feature requests for better documentation and reproduction.

Database:
- New model: FeedbackAttachment (file_data BYTEA, filename, mime_type, file_size)
- Links to feedback_item_id (required) and feedback_reply_id (optional)
- Migration: auto-creates table with indexes on startup
- Cascading deletes when item or reply is deleted

Backend (routes_feedback.py):
- Helper function: _validate_image_file() for security
  - Validates file type using imghdr (not just extension)
  - Enforces size limit (5MB per file)
  - Secure filename handling with werkzeug
  - Allowed: PNG, JPG, GIF, WEBP
- Updated feedback_new: accepts multiple file uploads
- Updated feedback_reply: accepts multiple file uploads
- Updated feedback_detail: fetches attachments for item + replies
- New route: /feedback/attachment/<id> to serve images

Frontend:
- feedback_new.html: file input with multiple selection
- feedback_detail.html:
  - Shows item screenshots as clickable thumbnails (max 300x200)
  - Shows reply screenshots as clickable thumbnails (max 200x150)
  - File upload in reply form
  - All images open full-size in new tab

Security:
- Access control: only authenticated users with feedback roles
- Image type verification using imghdr (header inspection)
- File size limit enforced (5MB)
- Secure filename sanitization
- Deleted items hide their attachments (404)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 13:28:41 +01:00
a919610d68 HOTFIX: Fix duplicate tickets in Run Checks popup
Critical bug: Same ticket appeared multiple times in popup
(e.g., T20260127.0061 showed 8 times).

Root Cause:
The JOIN with ticket_scopes/remark_scopes created duplicate rows
when a ticket had multiple scopes (Cartesian product).

Changes:
- Removed unnecessary JOIN ticket_scopes from tickets query
- Removed unnecessary JOIN remark_scopes from remarks query
- Added DISTINCT to prevent any duplicate rows
- Changed COALESCE(ts.resolved_at, t.resolved_at) to t.resolved_at
  (ticket_scopes JOIN removed, only ticket resolution matters)

Result: Each ticket/remark now appears exactly once in popup.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 11:47:28 +01:00
7385ecf94c Update v0.1.26 changelogs with UI text fix
Added the Settings Maintenance page text update to the official
v0.1.26 release notes before the first build.

Changes:
- Updated docs/changelog.md with User Interface subsection
- Updated changelog.py with User Interface subsection
- Both now document the test email text change (3→1, Veeam only)

All three changelogs (changelog.md, changelog.py, changelog-claude.md)
now include this UI improvement in v0.1.26.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 11:34:24 +01:00
f62c19ddf8 Update Settings Maintenance test email text
The UI text still mentioned "3 emails simulating Veeam, Synology,
and NAKIVO" but the actual behavior changed to 1 Veeam email per button.

Changes:
- Updated description: Now states "1 Veeam Backup Job email" per button
- Updated button labels: "emails (3)" → "email (1)"
- Clarified that only Veeam test emails are generated

This matches the actual implementation that was changed earlier.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 11:26:37 +01:00
1064bc8d86 Release v0.1.26 - Ticket system bug fixes
Prepared official release documentation for v0.1.26 consolidating
all ticket system bug fixes from 2026-02-10.

Changes:
- Updated docs/changelog.md with v0.1.26 release notes
  - Detailed root cause analysis of date-based logic issues
  - Complete list of fixed pages (4 locations)
  - Before/after behavior explanation
  - Testing and troubleshooting section
- Updated changelog.py with v0.1.26 entry for website display
  - Same content structured for Python data format
- Updated changelog-claude.md with release reference

Release Focus:
- Complete transition from date-based to link-based ticket queries
- Fixed resolved tickets appearing on new runs (4 pages affected)
- Preserved audit trail for historical runs
- Consistent behavior across entire application

Ready for production deployment.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 11:22:46 +01:00
d467c060dc Remove debug logging from ticket linking function
The ticket propagation issues have been resolved. Debug logging
is no longer needed in production code.

Changes:
- Removed AuditLog debug logging from link_open_internal_tickets_to_run
- Preserved debug logging code in backupchecks-system.md for future use
- Updated changelog to document removal

The debug code is available in the technical documentation if
troubleshooting is needed again in the future.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 11:14:13 +01:00
0d9159ef6f Fix Run Checks popup showing resolved tickets
The Run Checks popup modal was still showing resolved tickets
for runs where they were never actually linked. This was the last
remaining location using date-based ticket logic.

Root cause:
The /api/job-runs/<run_id>/alerts endpoint used the old date-based
logic that showed all tickets scoped to the job if active_from_date
was before the run date. This ignored whether the ticket was actually
linked to that specific run.

Changes:
- Replaced date-based query with explicit ticket_job_runs join
- Replaced date-based query with explicit remark_job_runs join
- Now only returns tickets/remarks actually linked to this run
- Removed unused run_date, job_id, ui_tz query parameters
- Simplified queries: no timezone conversions, no date comparisons

Result: Resolved tickets no longer appear in popup unless they were
linked to that run when they were still open. Completes transition
from date-based to explicit-link ticket system across entire UI.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 11:07:28 +01:00
5b940e34f2 Fix Run Checks page showing resolved ticket indicators
The Run Checks main page has ticket/remark indicators (🎫/💬) that
use queries to check if active tickets/remarks exist for each job.
These queries still used the old date-based logic.

Changes:
- Removed date-based OR clause from ticket indicator query
- Removed date-based OR clause from remark indicator query
- Simplified parameters (removed ui_tz from ticket query)
- Now consistent with Job Details and linking behavior

Result: Run Checks indicators no longer show for resolved tickets,
matching the behavior across all pages.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 10:57:14 +01:00
43502ae6f3 Fix: Show resolved tickets only on runs where they were linked
Previous fix removed ALL resolved tickets from display, breaking
audit trail. Users need to see which tickets were associated with
historical runs, even after resolution.

Solution: Two-source ticket display
1. Direct links (ticket_job_runs): Always show, even if resolved
   - Preserves audit trail
   - Shows tickets that were explicitly linked to runs
2. Active window (ticket_scopes): Only show unresolved
   - Prevents resolved tickets from appearing on NEW runs
   - Uses active_from_date without date-based resolved logic

Changes:
- Added direct_ticket_links map to fetch linked tickets per run
- Query ticket_job_runs for audit trail tickets
- Modified ticket_codes building to use both sources
- Removed date-based resolved_date comparison (resd >= rd)

Result:
- Run 1 with ticket → ticket resolved → ticket still visible on Run 1
- Run 2 created → ticket NOT shown on Run 2 (correctly filtered)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 10:53:45 +01:00
a9cae0f8f5 Fix Job Details page showing resolved tickets
The Job Details page used the same date-based logic that was causing
resolved tickets to appear for runs on the same day as the resolve date.

The linking was already fixed in ticketing_utils.py, but the display
query in routes_jobs.py still used the old logic, causing a mismatch:
- New runs were correctly NOT linked to resolved tickets
- But the UI still SHOWED resolved tickets due to the display query

Changes:
- Removed date-based OR clause from tickets query (line 201-204)
- Removed date-based OR clause from remarks query (line 239-242)
- Simplified query parameters (removed min_date and ui_tz)
- Now both linking AND display use consistent logic: resolved = hidden

Result: Resolved tickets and remarks no longer appear in Job Details
or any other view, matching the expected behavior.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 10:29:43 +01:00
1b5effc5d2 Reduce test email generation from 3 to 1 per status
User requested simpler test scenario with just 1 email per status
instead of 3, making testing and debugging easier.

Changes:
- Success: 1 email instead of 3
- Warning: 1 email instead of 3
- Error: 1 email instead of 3
- Each button now creates exactly 1 test mail
- Kept the most recent email (2026-02-09) from each set

This makes it easier to test ticket linking behavior without having
to deal with multiple runs per test cycle.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 10:14:32 +01:00
c1aeee2a8c Always log ticket linking attempts, not just when tickets found
Previous debug code only logged when tickets were found, making it
impossible to verify that the function was being called at all.

Changes:
- Move logging outside the if rows: block
- Always create audit log entry for every run import
- Log "No open tickets found" when rows is empty
- Use commit() instead of flush() to ensure persistence
- Add exception logging to catch any errors in debug code
- New event_type "ticket_link_error" for debug code failures

Now every email import will create a ticket_link_debug entry showing:
- Whether the function was called
- How many tickets were found (0 or more)
- Details of each ticket if found

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 10:10:23 +01:00
aea6a866c9 Change debug logging to write to AuditLog table
Flask logger output was not visible in Portainer logs or Logging page.
Changed to write debug info to audit_logs table instead, which is
visible on the Logging page in the UI.

Changes:
- Debug entries use event_type "ticket_link_debug"
- User field set to "system"
- Details field contains ticket info (one per line)
- Visible on Settings → Logging page

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 10:06:03 +01:00
c228d6db19 Add debug logging for ticket linking investigation
User reports that resolved internal tickets are still being linked to
new runs, even though Autotask tickets correctly stop linking. Added
debug logging to understand what the query is finding.

Changes:
- Query now returns resolved_at values for both ticket and scope
- Added logger.info statements showing found tickets and their status
- This will help diagnose whether tickets are truly resolved in DB

Temporary debug code to be removed after issue is identified.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 10:00:35 +01:00
88b267b8bd Remove date-based logic from ticket propagation
The ticket linking query had date-based logic that considered tickets
"open" for runs if:
- The ticket was unresolved, OR
- The resolved date >= run date

This caused resolved tickets to still link to new runs, which was
unexpected behavior. User confirmed tickets should ONLY link to new
runs if they are genuinely unresolved, regardless of dates.

Changes:
- Simplified query to only find tickets where resolved_at IS NULL
- Removed OR clause with date comparison
- Removed ui_tz parameter (no longer needed)
- Simplified Strategy 1 code (no extra resolved check needed)

Now tickets cleanly stop linking to new runs as soon as they are
resolved, for both internal and Autotask tickets.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 09:55:58 +01:00
caff435f96 Fix Autotask propagation to also check resolved status
The previous fix only checked if tickets were deleted, but Autotask
tickets can also be resolved (which is tracked via the internal Ticket
table, not the JobRun table).

Updated Strategy 2 to:
1. Find most recent non-deleted Autotask ticket
2. Check if its internal ticket is resolved
3. Only propagate if ticket is not deleted AND not resolved

This ensures tickets stop propagating when they are resolved in Autotask
(synced via PSA polling), matching the expected behavior.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 09:40:27 +01:00
f3b1b56b6a Fix Autotask ticket propagation to new runs
When a new run is created, Autotask tickets were not being propagated
if the associated internal ticket was resolved. This caused users to
have to manually re-link tickets on each new run.

The previous implementation relied on finding an open internal ticket
first, then using its ticket code to find a matching Autotask-linked run.
If the internal ticket was resolved, the Autotask propagation would fail.

This commit implements a two-strategy approach:
1. Strategy 1: Use internal ticket code (existing logic, improved error handling)
2. Strategy 2: Direct Autotask propagation - find most recent non-deleted
   Autotask ticket for the job, independent of internal ticket status

Now Autotask tickets remain linked across runs regardless of internal
ticket resolution status, matching the behavior of internal tickets.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-10 09:32:23 +01:00
57196948a7 Add v0.1.25 to website changelog
Update changelog.md and changelog.py with comprehensive v0.1.25 release notes
consolidating all changes from 2026-02-09:

Sections:
- Parser Enhancements: Synology (Drive Health, DSM Updates, ABB Skipped) and
  Veeam (Job Not Started)
- Maintenance Improvements: Orphaned Jobs Cleanup, Test Email Generation
- Data Privacy: Parser Registry Cleanup, Autotask Title Simplification
- Bug Fixes: Responsive Navbar Overlap Fix

This release focuses on parser coverage expansion and system maintenance
capabilities while improving data privacy practices.

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2026-02-09 17:17:47 +01:00