Commit Graph

260 Commits

Author SHA1 Message Date
johnnyq
3ee183a09a Document templates stage 2, filled in from the client: placeholders [Client], [Website], [Site], [Address], [Site Phone], [Contact], [First Name], [Contact Email], [Contact Phone], [Agent], [Date], [Month], [Quarter] and [Year] are filled in across a template's name, summary and content when a document is made, using the client's primary site and contact unless another or none is picked; tables of records [Contacts], [Locations], [Assets], [Servers], [Workstations], [Network Equipment], [Printers], [Networks], [Domains], [Certificates], [Licenses], [Vendors] and [Services] put in the client's current records, as a table on a line of their own (an empty row when there are none) or as names in a sentence, all made safe; any other bracketed word is a fill-in asked for when a document is made, set up on the template page as text, date, list or yes/no, required or with help, renamed along with the template text, reset or removed, and dragged into order, with answers checked by ticketFillInAnswers and blanks left in the document; the template page gets Fill-ins and Filled in from the client cards with each kind of word marked in its own colour, and the editor gets a button for each placeholder and table to insert it at the cursor (js/document_template_form.js); New document for a client and Document from template draw the site and contact pickers and fill-ins once the template and client are picked (agent/ajax.php document_template_asks, agent/js/document_template_make.js) and open larger; copying a template copies its fill-ins; Draft it with AI is told the placeholders and tables; migration 3.2.6 adds document_template_fill_ins; fixed the fill-in add and reset messages showing raw HTML around the bracketed name on document and ticket templates; changelog updated 2026-10-18 19:47:57 -04:00
johnnyq
81c80d8965 Canned responses stages 3 and 4: agents keep canned responses of their own in Your account > Canned Responses (on the standard list with Yours and Shared tabs, how often they used each, change, copy, archive and delete their own, Copy to yours from a shared one), offered to them alone and first in the picker as Yours; Save your reply as a canned response at the foot of the picker opens the draft with the ticket's contact, first name, client, ticket number, subject, link and agent swapped back to placeholders (canned_response_unfill, text only, a one-word subject left alone), offered on the ticket's category with a switch to put it back as written, and saves it in JSON without leaving the ticket so the reply stays and the new one goes straight into the picker; Admin > Canned Responses gains an Agents' own tab showing whose each is with Share with everyone, copies made there are shared, and admins can share their own or tick Share when saving a reply; files go with a response (Files tab, up to ten of the ticket attachment kinds, kept in uploads/canned_responses/<id>/, streamed by agent/canned_response_file.php to those who may use it), shown as chips under the picker with an x to leave one off, copied onto the ticket with the reply and sent with its email on a ticket and in Update & Reply; migration 3.2.4 adds canned_response_user_id and canned_response_created_by and the canned_response_files table, existing responses staying shared; the response window moves to includes/canned_response_form.php for the admin and account windows; export and import (functions/canned_response_transfer.php) of one, some or every shared response as a versioned JSON file with categories by name, what it sets up, status by name and files as base64, importing as shared with categories matched or made and leave, add as well or replace (keeping use and archived state), everything made safe and refused files named; an MSP starter pack of 27 canned responses in Starter Content loaded through the same import, with Update for the ones already added, and the Update button now driven by the pack registry; new Canned Responses report under Service Desk by response and by agent, filtered by client and by the agent who used it, admins seeing every agent's own; changelog updated 2026-10-18 15:36:00 -04:00
johnnyq
a65029431c Canned responses stage 2: the picker above a reply box is a searchable list by name or what a response says, each with a line of it and what it sets up, Enter picking the first, and typing / in the reply box offers the same responses narrowed as you type; a response can set up the reply on a new Sets up tab - reply as an internal note, public note or email reply (a public note when there is nobody to email), the status after it and minutes added to the time worked (migration 3.2.3 adds canned_response_reply_type, canned_response_ticket_status and canned_response_minutes) - applied as it goes in with a line under the picker saying what was set, still changeable before sending, and shown on Admin > Canned Responses; sending a reply a response went into with something still in square brackets asks first, Fill them in selecting the first one to type over or Send anyway; Update & Reply on the tickets list gets the picker with the responses for the tickets' categories and every ticket, fills in [First Name], [Ticket], [Ticket Link] and the other placeholders for each ticket as it is sent, its email too, and counts a response picked into it as used on each; new agent/includes/inc_canned_response_picker.php and agent/js/canned_response_picker.js, the / menu from itflowCannedAutocompleter() in js/app.js, get_canned_response answering what a response sets up, cannedResponsePickerGroups() and cannedResponsePlaceholders() split from cannedResponseFill(); fixes clicking Send on a reply that didn't go clearing its time worked; changelog updated 2026-10-18 12:59:36 -04:00
johnnyq
86381b775c Canned responses stage 1: Admin > Canned Responses on the standard list showing what each says, the ticket categories it is offered on, how often it has gone into a reply and when it last did, searched, filtered by where it is offered (a category or every ticket), sorted by name, use or last use, paged, with Active and Archived tabs; a response can be offered on several ticket categories or on every ticket (migration 3.2.2 moves canned_response_category_id into canned_response_categories, one whose category had been deleted staying on every ticket, and adds canned_response_uses); one shared add and edit window with the placeholders under the editor to click in where the cursor is; Copy, Archive and Restore alongside Delete; [Contact], [First Name], [Client], [Ticket], [Subject], [Ticket Link], [Asset], [Site], [Project], [Agent] (the agent replying), [Date], [Month], [Quarter] and [Year] filled in from the ticket as a response goes into a reply after the client access check, anything else in brackets left for the agent to fill in; the picker lists the ticket's own category first then every ticket's, and each reply records which responses went into it; Admin > Categories counts the canned responses on a ticket category, links to them and moves them on merge through link-table support in categoryKinds(); new functions/canned_response.php and js/canned_response_form.js; changelog updated 2026-10-18 11:53:51 -04:00
johnnyq
3dc1205a55 Ticket templates stage 2: fill-ins - words in square brackets other than the ones filled in from the ticket, like [Employee Name] or [Start Date], are asked for when a ticket is raised from a template on New Ticket, once for all tickets in the New Tickets windows of the assets and clients lists, and once on a recurring ticket for every ticket it raises, then filled in wherever they appear in the subject, details and tasks and kept on the ticket in a Fill-ins card where a blank one can be answered later and goes in where it is still waiting, with each change in the ticket's history; on the template's page each fill-in can be made text, a date, a list of choices or yes or no, required, given help, renamed along with its text and tasks, added without being in the text, and dragged into order (migration 3.2.0 adds ticket_template_fill_ins, ticket_fill_ins and recurring_ticket_fill_ins, and task_templates.task_template_when_fill_in and task_template_when_value); a template's task can be for one answer only, dropping out of New Ticket as answers are given and kept when its answer is not given or no longer offered; project template tickets keep their fill-ins unanswered to answer on the ticket; addTasksFromTicketTemplate replaced by ticketTemplateAddTasks; fixes Add Task adding a row for every time the New Ticket or recurring ticket window had been opened, and Save doing nothing when a required field was empty on a tab that was not showing; changelog updated 2026-10-18 00:44:01 -04:00
johnnyq
5d9b48e83e Roles stage 2: refusals now say why, naming the role and what it lacks, as a Not for your role card in place of a page with the layout and Back, inside the window for a window, back on the page with a message for a handler or Admin, and as a 403 JSON error from ajax.php, no longer leaving a stale not permitted message on the next page; actions a role can't do are no longer offered, covering the clients bulk menu at Read keeping Send Email, asset bulk tools and ticks at Read, asset bulk Delete below Full, editing an asset's recurring tickets at Read, report links for roles without that report with the dashboard Profit card opening Transactions instead, Credentials in All Client Docs, a contact's Assets, Documents, Files and Services tabs and a document's linked records for roles without Support, shared-link notifications for roles without Support, and the client delete window only included where Delete Client is offered; role window warns when modules are given with Clients at None; user quick look shows what the agent can open from their role and the user form shows the picked role's access; changelog updated 2026-10-17 20:44:50 -04:00
johnnyq
5e87f6fa25 Roles stage 1: Admin > Roles rebuilt showing each role's access per module as level-colored pills or Admin - everything, its agents with a link to Users filtered by role, search, Current and Archived tabs, and Edit, Copy, Archive, Restore and Delete greyed out with the reason when blocked; one role window for New, Edit and Copy with an Admin switch and a None, Read, Modify or Full level per module, each level listing what it allows, Reports limited to None and Read, and a copy dropping the Built-in description prefix; hardcoded role 3 checks replaced by guards so admin can't be taken off your own role or the only admins' role, archive needs no active agents, delete needs no agents at all, and names are unique in any case with the description optional; Administrator role can now be opened and renamed; role names escaped in flash messages, fixing an XSS; audit log records what changed on a role; lookupUserPermission reads the role's levels once per request instead of one query per check; new functions/roles.php, shared role_form.php and js/role_form.js; database 3.1.6 removes orphaned and duplicate user_role_permissions rows, clamps levels to 3 and adds a primary key on role and module; changelog updated 2026-10-17 20:43:45 -04:00
johnnyq
2b087c8f46 Categories stage 2: every form and Bulk Action window picks a category the same way through categoryPicker and categoryOptionsHtml, in the kind's order with each category's color, icon and description, keeping a record's archived category marked (archived) and a status, type or referral that isn't a category marked (not set up) so saving changes neither; the + beside a category picker is admins only and opens the category window stacked over the form, saving in the background as JSON, picking the new category and leaving the form as it was, with a taken name shown in the window, on every form that picks one including a ticket's quote and invoice, Unbilled Time, payment providers, canned responses, the mileage setting and the Bulk Action windows; stacked windows shade the one underneath; agent/post/category.php removed so the window posts to admin/post.php from any page; typed referrals go through categoryEnsure, taking an existing referral's spelling in any case, matching archived ones and no longer making an empty referral on client add, edit and import; fixes the + reloading the page and losing the form, the quote made from a ticket creating an expense category, and a stray < in the license template type picker; changelog updated 2026-10-17 20:41:26 -04:00
johnnyq
8a992039fb Categories stage 1: Admin > Categories rebuilt with the ten kinds in a side nav with counts and what each is for, each category shown as it looks on records (icon or dot in its color, asset statuses as their badge) with its description and what uses it linked to the filtered lists, search, sort by name, most used or order, Current and Archived tabs, Edit, Merge into, Archive, Restore and Delete only while unused, bulk merge, archive, restore and delete, drag or Move up and Move down ordering for the ordered kinds, names in use that are not categories listed with Add, one shared category window with live preview, color swatches or none and searchable icons or none, names unique per kind and held to their column length, renaming a kind kept by name carries the new name onto its records, merge moves every reference including budget months folded per month, payment provider fees and the mileage setting, all without touching record updated_at, database 3.1.5 normalizing category colors to #rrggbb and icons to fa-name, seed data in hex, new functions/categories.php, agent + window handler routed through the same validation, note-type icons fixed in pickers, Settings > Defaults payment methods read from Payment Methods, changelog updated 2026-10-17 15:22:59 -04:00
johnnyq
95dd3ef9c5 Tags stage 2: tags on five more record kinds (tickets, documents, [kind], [kind], [kind]) working like the other seven with tag pills and + picker on list, page and quick look, Tags field in New and Edit, list tag filter and tag-name search, Bulk Action Tags, export tag filter and Tags column; tickets list shows + only once a ticket has a tag, Tags under More filters with its own chip, board cards show tags, tag changes written to ticket history and merging moves non-archived tags; document tag filter in client Files and at top level across all folders excluding uploads, bulk Tags only tags ticked documents, cross-client document tags open a global search; global search matches tag names, shows the matching tag on each result and adds a Tags group; API tags read, update and create endpoints plus a tags list on every record read, per-kind permission checks and tag creation limited to admin keys; Tags starter pack and demo data cover the new kinds; changelog breaking change for tag-name matching in searches and upgrade note now 2.7.9 to 3.1.4; stage 1 tag test updated for twelve kinds 2026-10-17 15:17:14 -04:00
johnnyq
b5dc8883f1 Tags stage 1: Admin > Tags rebuilt with the seven kinds in a side nav with counts, each tag shown as it looks with its description, how many records have it (and how many of those are archived) linking to the list filtered by it, and the recurring invoice lines that count by it, search by name or description, sort by name or most used, Current and Archived tabs, Edit, Merge into, Archive, Restore and Delete per tag and bulk merge, archive, restore and delete; new shared tag window with live preview, description, color swatches or any color or hex, searchable icon grid or any Font Awesome icon by name, and kind changeable only while unused; merge window that moves records onto the kept tag once each and repoints recurring seat lines; archiving now works, with archived tags kept on their records but left out of record forms, the tag picker and the list and export filters unless already chosen; tag names unique within their kind, though tags that already share a name can still be saved; delete refused while a recurring seat line counts by the tag; record forms let admins type a new tag inline, replacing the + admin window that reloaded the page and failed for non-admins, and every kind now saves through one tagSetForRecord that keeps only its own kind's tags, each once, fixing the error on a tag sent twice for clients, contacts and assets; typing an archived tag's name restores it, and the picker refuses putting an archived tag on more records; recurring line window keeps its tag once archived; pills pick dark or white text by luminance and carry the description; removes the legacy agent tag handler and tag_model files; database 3.1.3 adds tag_description and normalises stored tag colors to hex and icons to bare names; changelog updated 2026-10-17 13:59:13 -04:00
johnnyq
afaaa5fc32 Taxes stage 1: Admin > Taxes rebuilt (renamed from Tax Rates) listing each rate with its whole percent, parts, description, registration number and usage (invoices, quotes, recurring invoices, products, clients), Current and Archived tabs showing what replaced a rate, Restore, Make default, and Delete only for a rate never used; rates made of parts (state and county, GST and QST) with parts charged on top of the ones above, the whole rate shown as typed, four decimal places and a registration number per rate or part printed with the company details on invoices, quotes and PDFs; changing the percent or parts of a rate on a sent invoice or quote makes a new rate of the same name and archives the old one, so billed lines keep the old rate while products, client rates, the default, recurring invoices and optionally drafts move to the new one, and archiving offers to move whatever still uses it; How lines are taxed settings for the default rate, taxing billed time, trips and expenses, and discounts taken off before tax (on by default, shared across lines by amount, paid, cancelled and answered documents never recalculated); clients get their own tax rate and tax exempt with certificate number and expiry on the Billing tab, new lines defaulting to the client's rate then the product's then the default and to no tax for exempt clients, exempt badge on the client header and overview, a warning with Take the tax off on open documents that still carry taxed lines for an exempt client, and Tax exempt with the certificate under the client on untaxed documents; totals, PDFs, guest and portal views show tax by part; Unbilled Time can bill at each client's usual rate and the ticket, Add Tickets, Add Expenses and Add Trips windows start on it; API client fields for rate and exemption and tax_id default on invoice item create; Tax Collected shows exact percents; demo taxes get parts and registration numbers, demo clients their rates and two nonprofits exemptions; database 3.1.1 makes tax_percent decimal(9,4) and adds tax description, registration and replaced-by, tax_components, client rate and exemption columns and the tax settings; new functions/tax.php and js/tax_form.js; changelog updated 2026-10-17 13:00:54 -04:00
johnnyq
e84e3e7e49 Client portal stage 2: billing in the portal - invoices and quotes open in the portal with PDF download and print, Pay invoices pays several invoices as one Stripe card payment with a saved card or a new card on a checkout page (one payment per invoice under a shared reference, booked once under a lock, one receipt and one paid notification), quotes accepted or declined with the contact's name and a note plus signed copy or PO upload, payments list with printable receipts, statement with aging and the shared statement PDF, recurring invoice page with autopay, Cards and autopay on one page, quotes waiting and past-due invoices on home, Ask us links prefill a ticket subject; shared billingQuoteAnswer and billingQuoteAddFiles used by the guest links too, new functions/billing_pay.php, Stripe-aware CSP for card pages with js/portal_stripe.js, nightly Stripe fee reconciled once per payment reference, Stripe refund limited to the payment's own amount, old add_payment_by_provider removed 2026-10-17 02:12:05 -04:00
johnnyq
c6eadf3fa3 Client portal stage 1, look, home and tickets: a new light shell with the company logo or initials on the theme colour, sections shown by what each contact may open (Home, Tickets, Billing for billing contacts, Your IT for technical contacts, custom links), New ticket and an account menu with a dark mode switch kept in a cookie, a bottom tab bar and slide-in menu on phones, and the welcome banner removed; a rebuilt home showing what needs the contact (tickets waiting on their reply or to confirm, approvals, past-due invoices), open tickets, balance with Pay invoices, renewals in the next 45 days, their devices with warranty status and the company phone and email; tickets rebuilt with Open, Waiting on you, Resolved, Closed and All tabs with counts, search, paging and the whole company's tickets for primary and technical contacts with a Mine filter, the old all-tickets page redirecting there; a ticket page with progress steps, the conversation oldest first, approvals, details alongside, replies with drag and drop attachments, It's fixed, close or reopen and rating; New Ticket with priority, category, device and attachments; fixes downloading files from internal notes, files on closed tickets not downloading, new tickets linking to another client's device or a non-ticket category, empty replies and tickets being accepted, PHP warnings on Pay invoices and Recurring invoices with no payment provider, and Bootstrap icons and the editor setup blocked by the portal CSP, which now allows data: images; new js/portal.js and portal helpers in client/functions.php, ticketPortalStatusHtml removed; changelog updated 2026-10-17 01:28:27 -04:00
johnnyq
df668d83e6 Accounts Reconcile: reconcile an account against its bank or card statement from the account's menu on Accounts or Transactions - enter the statement's ending date and balance (what is owed, for a card) and notes, starting from where the last statement ended or the opening balance, with lines brought in from bank statements pre-ticked; tick what cleared with the cleared balance and difference updating as you go, each tick saved immediately so a statement can be finished later, pills for money in, money out, not ticked and ticked, search, tick and untick all shown, a bar keeping the difference and Finish in view, and Finish only once the difference is nothing; change the statement, discard it, or add a missing line with New Expense, New Income or New Transfer starting on the account; a history of reconciled statements with ending balance, lines cleared, money in and out and who reconciled it, with Undo on the latest putting it back in progress with its ticks; Transactions marks cleared lines linking to their statement, adds an Uncleared pill and a filter for one statement's lines, the export adds a Cleared column, and Accounts shows where each account is reconciled to; a cleared payment, other income, expense, transfer or reimbursement keeps its amount, date and account and can't be deleted until its statement is undone, which also blocks deleting its invoice or client (including through the API), refunding a cleared Stripe payment, bulk set account and bulk delete on cleared lines, and undoing a cleared reimbursement, with quick looks and edit windows showing where it cleared; the opening balance locks once an account has a reconciled statement and a ticked line moved to another account comes off its statement; reconciling needs write Financial access and undoing full access; new functions/reconcile.php, agent/reconcile.php, agent/post/reconcile.php and js/reconcile.js with ticking through agent/ajax.php; database 3.0.8 adds account_reconciliations and the reconciliation id on payments, revenues and expenses; demo data reconciles Operating Checking and the Business Visa monthly through last month; CHANGELOG updated 2026-10-16 23:12:22 -04:00
johnnyq
47969cd3c2 Income Import Deposits: bring the money in on a bank statement in as payments on invoices, other income or transfers from the Income list's menu, reading the same CSV as the expense statement import with the columns kept on the account for both sides and a link from each side's review to the other without uploading again; each deposit is matched by an invoice number in its text or reference, the payer remembered from last time, a client's name in it, the only invoice or the oldest of one client's invoices owing the amount or everything one client owes together, a payment provider payout or a transfer from another account, and anything else as other income for a category and client; payments pay the client's oldest invoices first with one deposit paying several and a short one leaving the last part paid, picking a client ticks the invoices it pays and each line says what it pays off, two deposits on one invoice don't pay it twice and more than they owe blocks the import; deposits imported before are locked, ones matching a payment, other income, transfer or a day's payments entered by hand within 4 days are left out and linked when left out, and a payout into the payment provider's own account counts as recorded; every ticked deposit is checked before any is saved, invoices get their status and history, receipts can be emailed, the payment method is read from the text, and payments and other income say they came from a bank statement on their quick look; payments need write Sales access and client scope applies; remembered payers window with forget; the statement columns step moved to a shared include and the sign guess now reads deposit and charge words on the lines; new functions/income_import.php, agent/income_import.php, js/income_import.js and agent/post/income_import.php; database 3.0.6 adds payment_import_key, revenue_import_key and the income_import_rules table; CHANGELOG updated 2026-10-16 21:44:14 -04:00
johnnyq
a2a0823163 Trips stage 2: mileage money - Trips and Mileage in Admin > Settings > Invoice with miles or kilometers, the rate an agent is paid back for their own vehicle and the expense category it goes under, and what a trip bills a client as a trip charge, a rate a mile beyond the distance the charge covers and the invoice line name; the trip form has In their own vehicle starting as the driver's latest trip and Bill the client starting as the ticket is billable, each showing what it pays back or bills; the list gets To pay back and To bill pills, an owed card (Owed to you for agents without financial access), who is owed what and marks on each row; Pay Mileage pays one driver for the ticked trips at the usual or a past rate as a mileage expense per client paid personally by them under the mileage category to a Mileage vendor made on first use, paid back there and then from an account or later with Reimburse; Unbilled Time has Travel to bill beside the expenses at an editable price going on the client's invoice with their tickets and expenses, billing every client includes trips and Not billable writes them off; the invoice gets a Travel card with Add Trips and Take off Invoice, and deleting the line or invoice makes a trip to bill again; paid back and billed trips keep their distance, driver, vehicle, client and billable and can't be deleted, and deleting the mileage expense puts its trips back to pay; bulk Set Vehicle, Set Billable and Pay Mileage; the trip quick look shows what it pays back and bills and the mileage expense lists its trips; dashboard Trips to bill and Mileage to pay back, client overview Trips to bill and the Unbilled Time count include trips; export Vehicle, Paid Back and Billing columns; the Mileage report and dashboard chart follow the unit and the report rate starts at the mileage rate; demo data with recent trips in own vehicles and billable when trips bill; database 3.0.4 with trip_own_vehicle, trip_expense_id, trip_billable, trip_invoice_id, trip_invoice_item_id and the mileage and trip billing settings; CHANGELOG updated 2026-10-16 20:35:51 -04:00
johnnyq
53d0f8a841 Expenses stage 4: getting expenses in - Import Statement from the expenses menu brings a card or bank CSV in as expenses, reading lines before the header, commas, semicolons or tabs, Windows text and amounts like (12.00), 12.00 CR or 1.234,56, guessing the date and its format, description, memo, amount or money out and in columns, sign and reference and remembering them per account so the next statement goes straight to the review, matching each line to a vendor from what was picked for that merchant last time or a vendor name in the text (shortened names too) with its last category, suggesting a new vendor named from the line when nothing matches, locking lines imported before so a statement never comes in twice, leaving out lines that look entered by hand within 4 days and linking them, leaving out money in unless ticked, filling in the same merchant's other lines, bulk category and client and billing on, making new vendors once and opening the account's expenses for those dates, with remembered merchants to see or forget; paid personally expenses with who paid them that count as spent on their date but move no balance until paid back, a To reimburse pill with what each agent is owed, Reimburse paying back the ticked expenses from one account on one date as a Reimbursement in Transactions with undo for full financial access, quick look, list, vendor page, bulk, export and dashboard showing who paid and whether they were paid back, database 3.0.2 with expense_import_key, expense_paid_by, expense_reimbursement_id, expense_import_rules, reimbursements and account_import_map, CHANGELOG updated 2026-10-16 19:12:03 -04:00
johnnyq
8d5e5091ad Expenses stage 3: billable expenses and pass-through costs - mark an expense for a client billable with a markup (default in Admin > Settings > Invoice), expenses to bill sit beside the time in Unbilled Time and go on a new or draft invoice with the tickets as a line each at a price that can be changed, the invoice gets an Expenses card with cost against billed and the margin plus an Add Expenses window, taking one off or deleting its line or invoice makes it to bill again (paid invoices keep it, cancelled ones keep the line), the quick look and list link billed expenses to their invoice with To bill and Billed pills and Bulk Set Billable, recurring expenses can be billed on each time or covered by one of the client's recurring invoices with a Costs card showing the monthly margin, expenses to bill counted in the menu, dashboard and client overview, export Billing and Billed On columns, demo data with recent client expenses to bill, database 3.0.1 2026-10-16 18:36:43 -04:00
johnnyq
775edc53d8 Products makeover stage 1: products and services with cost and margin, the vendor they are bought from with its part number, internal notes and default billing of one time, monthly, quarterly or yearly per user or per device that fills in Billed on quotes and Counted on recurring invoices, a per-product Track stock switch so only tracked items move stock and refuse to be invoiced past the shelf while untracked ones are ordered as needed, rebuilt Products list with what catalog lines bring in each month on recurring, sales over 90 days with the top seller and stock value at cost, tabs for Services, Products, Recurring and Stocked, a vendor filter and part number search, a new product page with price, margin, 12 month sales, monthly recurring, stock with recent moves, recurring invoices, open quotes, invoices and history tabs, inline notes and Copy, one New and Edit window with live margin, rebuilt Add Stock, import by column heading with update by code for price lists, export with cost, margin, billing, vendor, part number and stock, agent-only margin on invoices, quotes and recurring invoices, a Products tab on our vendors' pages, search results opening the product page, billing defaults in the starter catalog and costs and vendors in the demo data. Fixes bulk Restore of archived products doing nothing, deleted products leaving stock behind, Add Stock recording zero units or a missing expense, and a backslash before an apostrophe in agent names in billing history. Adds DB 2.9.4 with product cost, vendor, part number, notes, frequency, seat source and track stock set for products with stock history plus product keys on line and stock tables, functions/products.php with productSave() as the one write path, productUsage() and billingMargin(), agent/product.php, a shared product_form.php, copy_product and product_set_notes handlers, removes product_model.php, and updates the 26.11 changelog 2026-10-16 15:23:05 -04:00
johnnyq
2fcdd6006b Invoices, quotes and recurring invoices makeover stage 4: quote lines billed one time or each month, quarter or year with a Billed choice on the add-a-line row and in Edit Line, quotes grouped into One-time, Each month, Each quarter and Each year with a total for each on the page, PDF and client view, lines dragged within their own group, Start Billing on accepted quotes putting one-time lines on a draft invoice due on the client's terms and each recurring part on a new recurring invoice from a chosen date, emailed or left as drafts, or added to one of the client's recurring invoices of the same frequency, with an option to bill the first period on the invoice, an Invoiced as card on the quote linking every invoice and recurring invoice it became including ones it added lines to, From links back on invoices and recurring invoices, monthly amounts in the quotes list and its totals, search, client portal, quote email, Send and Copy windows, quotes export and client export, and Quotes Pipeline valuing quotes at up front plus a year of recurring lines. Fixes Make Invoice invoicing a quote twice or one never accepted, and its audit entry using the current quote prefix instead of the quote's own. Adds DB 2.9.3 with item_frequency, quote_monthly_amount, invoice_quote_id and recurring_invoice_quote_id, linking invoices to their quotes from history, quoteConvert() as the one invoicing path claiming the quote in a transaction, quoteLineGroups(), quoteAmountText() and quoteMadeFrom(), reportCsv() totals written as given, and updates the 26.11 changelog 2026-10-16 14:14:53 -04:00
johnnyq
1a51fc8dd6 Invoices, quotes and recurring invoices makeover stage 3: Unbilled Time page under Billing and in each client's menu with a count, listing every client's billable resolved or closed tickets not yet invoiced with time logged, hours to bill, rate, amount and oldest waiting, invoicing many clients at once onto a new draft each or each one's newest draft, and per client reviewing each ticket's hours before billing onto a new or existing draft with a line per ticket or one for all, live totals, and Not billable to write tickets off, Billing Time settings under Admin Settings Invoice for rounding to 6, 12, 15 or 30 minutes or the hour, nearest or always up, a per-ticket minimum and the line name, defaulting to the nearest 15 minutes, rebuilt ticket Invoice window showing time by agent, hours to bill and the client or default rate with add-to-draft and an open ticket warning, Add Tickets on an invoice now adds lines for the tickets' time with an option to attach without lines, client overview, dashboard and Unbilled Work report linking to it and counting unbilled time the same way, ticket billing written to ticket history instead of an internal note, invoices from tickets and copies due on the client's terms including On Receipt. Fixes ticket invoice line placed near the top of existing invoices, a ticket billable twice from two windows, no rate when the client had none set, and no hours filled in for tickets with 100 hours or more. Adds DB 2.9.2, billingTimeInvoice() as the one billing path with ticket claiming, billingUnbilledSql() and related helpers, unbilled_invoice, unbilled_invoice_clients and unbilled_write_off handlers, js/unbilled_time.js, and updates the 26.11 changelog 2026-10-16 13:42:06 -04:00
johnnyq
422088fb60 Invoices, quotes and recurring invoices makeover stage 2: per user, per device and per license recurring lines that take their quantity from the client's contacts (all or tagged), devices (ticked types or tagged, lost/stolen/retired left out) or a license's seats (in use or bought), counted again for every invoice with an optional contract minimum, set from a Counted choice on the add row or the full Quantity from section in Edit Line with a live count, marked on each line and listed in a new Seats card with Update now when the client has changed, quarterly frequency alongside monthly and yearly counted as a third in MRR on the dashboard, client pages, client portal and reports, period words {month} {quarter} {year} {period} filled into scope, notes and lines, schedule card showing the period the next invoice covers, recurring_invoice_anchor_day so month-end schedules return to the 31st after a short month, nightly run and Invoice Now consolidated into recurringInvoiceGenerate() which claims the run so it is billed once, refreshes seat counts and takes taxes at current rates, nightly run now bills runs missed by up to 7 days, Invoice Now bills the next run early and moves the schedule on from that run instead of restarting from today, recurring email goes to non-archived primary and billing contacts once per address and stays a draft when outgoing mail is not set up. Fixes portal recurring card ignoring yearly-only clients and counting archived ones, edit recurring invoice resetting the billing day. Adds DB 2.9.1, recurring_invoice_sync and recurring_seat_count handlers, itflowBillingSeatForm(), and updates the 26.11 changelog 2026-10-16 13:09:59 -04:00
johnnyq
fee0a5cb80 Invoices, quotes and recurring invoices makeover stage 1: one shared document page for all three with inline line editing (product pick, live line totals, drag to reorder, lines locked once paid or answered), shared New/Edit form, late recurring invoices offer to skip to the next date without billing missed runs, Add Payment shows remaining balance and account balances, Batch Payment lists the invoices it will pay, Add Tickets takes several at once, new PDF layout for invoices, quotes and packing slips with pay/answer QR codes and paid/answered stamps, Letter or A4 by country, guest invoice Pay Now with other open invoices, guest quote Accept/Decline then signed copy or PO upload. Line amounts rounded to the cent on save, expired quotes can no longer be accepted from the link, Batch Payment skips non-billable invoices, recurring list creation-date filter removed. Fixes discount reset to zero on invoice/quote edit, stock not moving on invoice item quantity change, invoice status not updating on payment edit, autopay left behind on recurring invoice delete. Consolidates line items, totals, statuses and PDFs into functions/billing.php, includes/billing_paper.php, agent/post/billing.php and functions/billing_pdf.php with a single billing_items_order ajax reorder; removes the three item edit modals, link_invoice_to_ticket, guest_quote_upload_file_modal.php and js/product_autocomplete.js 2026-10-16 12:37:50 -04:00
johnnyq
c51323b88e Rebuild guest sharing as Shared Links (functions/share.php, DB 2.9.0) with one Share window for credentials, documents and files plus secure notes and login requests that clients answer through an encrypted form and agents save to credentials, choices for expiry, view limit, a passphrase or a code emailed to the recipient with lockout after five wrong tries, optional 2FA codes, notify on open, email or copy or QR, the link secret kept after the # and only its hash stored, login, note and request payloads sealed with AES-256-GCM under a key derived from the secret and request keys held under the vault, a rebuilt guest page (guest/share.php, js/guest_share.js, guest/share_ajax.php) with click to reveal so link scanners cannot use up one-time links, copy buttons, rotating 2FA codes limited to the browser that opened it and a destroy button, POST-only file downloads confined to the client folder, a Shared Links page per client and under All Client Docs with open, sent back and ended filters, a quick look with access history by address and browser, turn off one, ticked or every open link for a client, secrets wiped when links end and ended links kept for 90 days, sharing policy under Admin Settings Security, old links still working until they expire, removal of share_modal.php, share_modal.js, credential_share.php, share_generate_link, get_share_totp_token and deactivate_shared_item, and an updated 26.11 changelog 2026-10-16 01:33:36 -04:00
johnnyq
15844faa9b Rebuild all reports on a shared framework (functions/reports.php, inc_report.php, inc_report_layout.php, js/reports.js) with period, client and agent filters, sortable tables, CSV export of any table and clean print layouts, add Client Review (QBR), Renewals & Expirations, Asset Lifecycle, Documentation Coverage, Customer Satisfaction, Open Ticket Aging, Client Profitability, Quotes Pipeline and Mileage reports, make Budget vs Actual editable with save and copy-last-year, rename reports to say what they show, enforce module and feature access on every report page, exclude transfers from income via dashboardRevenueSql, limit portal ticket ratings to Good or Bad, seed ratings and Windows 10 holdouts in demo data, link Client Review from the client menu, and update the 26.11 changelog 2026-10-16 00:04:40 -04:00
johnnyq
3ec52974db Calendar modernization: calendar page rebuilt to load only the dates on screen with show or hide toggles for each calendar and for built-in sources (scheduled tickets, project start and due dates, service reviews, recurring tickets, renewals, invoices due), a filter for one agent, quick looks on click, drag to reschedule tickets and events that do not repeat, and a To schedule panel for dragging open unscheduled tickets onto the calendar; events get a shared add/edit form with repeats every N days/weeks/months/years with an optional end date and single skipped occurrences, a client site, location or meeting link, agents, client contacts and guest emails as attendees, iCalendar invitations with updates and cancellations sent to invited attendees, an event quick look with map and join links, .ics download and resend; each agent gets a personal subscription link for their schedule (their own or the whole team, busy only option, respects role and client access, stops when the account is disabled) with setup help for Google, Outlook, Apple, Nextcloud and Thunderbird; shared calendar feeds and invites now publish timed events with TZID and VTIMEZONE so repeating events keep their time across DST, with INTERVAL, UNTIL and EXDATE support; managing calendars is limited to admins; ticket schedule logic moved into functions/ticket.php and shared with the calendar, the schedule dialog shows the assigned agent's day, and ticket visit calendar files are rebuilt without zapcal as one-hour published events; mail queue sends invitations and cancellations as a text/calendar part and other calendar files as invite.ics; dashboard schedule shows only events the agent is on or added, client overview Coming up and client sidebar count use upcoming events, sites and contacts get New event shortcuts, demo data uses repeating events and attendees; database update 2.8.8 adds event repeat interval, until, skip, sequence and created by, attendee user and invited at, user_calendar_feeds, and widens email_queue.email_cal_str to text 2026-10-15 19:17:17 -04:00
johnnyq
fecd1cabff Credentials makeover: rebuilt credentials list with kind icons, username copy, password show/copy and live 2FA code buttons fetched on demand, where it opens, what it is for (asset, contact, vendors, licenses, services), password age pills and last used, filters for Starred, With 2FA, No 2FA, Not changed in 90 days and Shared with counts, search across notes, second link, tags, asset and contact, open straight to a credential with ?open=ID; new credential quick look with login, age, last viewed by, links with unlink, notes, open share links with turn off, and history; tabbed new/edit form with password generator (passphrase or random), strength meter, 2FA secret that accepts spaces or an otpauth:// link and shows the current code to check, copy buttons on both links, prefill from asset, contact or vendor; new Change password window that dates and logs the change; new Share window from anywhere (contact or email, 1 hour to 1 month, gone after opened once by default, link copied); same login controls on asset and contact pages and quick looks, vendor Logins tab, license page and quick look, service quick look, client overview favourites and search; credential pickers show icons and say when a credential moves from another asset or contact; client overview Passwords due for a change attention item and Active share links limited to live links; rotation report with selectable span, per client counts and oldest first; more export columns; demo data gets 2FA secrets, varied password ages and logins attached to their assets. Fixes passwords being blanked when the vault session had expired, other clients' assets, contacts and tags accepted on save, bulk star using the wrong permission, credential links to assets and contacts not checking the client, the edit or link permission, or which asset or contact an unlink was for, credentials left pointing at deleted assets and contacts, share links left open after a credential was deleted, import carrying values between rows and accepting any file type, 2FA secrets saved with spaces or lowercase giving no code, the service quick look listing credentials without credential access and repeating assets, an asset login with only a username being lost, and the API not dating new passwords. Adds functions/credential.php and js/credentials.js; removes credential_model.php and the old credential show password/OTP scripts. No DB change. 2026-10-14 23:33:29 -04:00
johnnyq
9e55d52432 Vendors overhaul for daily MSP work: new vendor page built around calling them, with Call support (dials the extension), Email, Support site, a star, and a New menu (case/ticket with them, license from them, asset bought from them, portal login, document, upload, or expense and recurring expense for our own vendors), Support card (phone, hours, SLA, email, site), Account card (account number, PIN shown as dots with show and copy, account manager name, direct line and email), blur-to-save notes, an Also used by list of the agent's other clients with the same vendor by name or template, and tabs for Cases (open first, with their ticket number), Licenses (soonest renewal first), Assets (serial, order ref, warranty status), Domains (registrar, web host, DNS, mail), Services, Logins, Documents, Files and History; our own vendors show spend this year, last year and in all, recent expenses and recurring expenses; new vendor quick look; rebuilt vendors list with starred first, initials tiles coloured by vendor name, support line, hours and SLA, account number and PIN, chips for open cases, licenses, assets, domains, services and logins, an Ours / Clients' switch with an all-clients view in All Client Docs, wider search (account manager, emails, tags), tag filter and bulk Tags/Archive/Restore/Delete; shared tabbed vendor form (Details, Support, Account, Notes) with star, tags and start from template that fills every field; Add a Template to Clients to roll one vendor out to many clients, skipping those that have it; Admin Vendor Templates shows how many clients use each template and has Add to clients; vendor tags (tag type 6) with vendor tags in the Tags starter pack; ticket vendor block shows their ticket number, support line, hours, SLA, account number and PIN with copy buttons; vendor tiles in every vendor picker and quick look links across tickets, licenses, assets, domains, services and expense lists; search opens the vendor page; CSV export adds tags, open cases, account manager and PIN; logins, documents and files can be linked to a vendor and ones made from a vendor's page are linked to it; demo vendors get tags, a star and an account manager; database update 2.8.2 adds vendor_tags and vendor_contact_phone_country_code, vendor_contact_phone, vendor_contact_email (db.sql updated) and clears references to vendors that no longer exist; ticket vendor now validated against the ticket's client and removing a vendor from a ticket is logged as such; deleting a vendor from a template no longer unlinks every other vendor from that template; deleting a vendor clears it from assets, licenses, tickets and domains, and vendors with expenses, recurring expenses or payment provider fees are archived rather than deleted; vendor websites without a scheme open correctly; domain form vendor names escaped; new vendor templates keep the phone country code and pushing a template update with nothing ticked no longer errors; vendors API accepts the account manager fields; new functions/vendor.php (VENDOR_USES, vendorCan/vendorEnforce with client vendors on module_client and ours on module_financial, tile, link, website, PIN, form, tags, counts, delete check, reference clearing, also used by, spend, history), credential|vendor and file|vendor link relations, tag module_ours for our own vendors, handlers add_vendor_template_to_clients, favorite_vendor, unfavorite_vendor and ajax vendor_set_notes, vendor_model.php removed 2026-10-14 22:49:05 -04:00
johnnyq
6ff9dbe9a4 Files and documents everywhere else: asset and contact quick looks list their documents and files with the same tiles and rows as the document page, files opening their quick look instead of a raw download; client overview share links show document and file tiles and open the document page or file quick look; service quick look shows linked documents as tiles and leaves out archived ones, service add and edit document pickers carry an icon and summary; global search shows file and document type tiles in the palette and on the results page, and a file result opens its folder narrowed to that file; quote attachments show their tile and size, open the file quick look and download through file.php instead of linking straight into the uploads folder; ticket attachments show their file type tile; client portal documents list shows the document tile, folder and summary with the last updated date; removed unused modals/asset/asset_documents.php 2026-10-14 20:47:30 -04:00
johnnyq
234afd25fb Contacts overhaul: rebuilt contacts list with role tabs and counts, avatars, flag pills, hover copy on phone/mobile/email, inline location picker, linked asset/credential/license/ticket chips and tag filter; contact page rebuilt to match the asset page with header actions, Reach/Details/Quick notes cards and tabbed Assets, Credentials, Tickets, Recurring, Licenses, Documents, Files, Services and Notes; add and edit contact share one tabbed form (Details, Roles, Access, Notes) with field icons, role switches, password generator, duplicate email check and photo removal; contact quick look redone to match the asset quick look; contact avatars now used everywhere a contact appears - contact pickers, ticket header, contact card, client replies, ticket list, kanban, assets, clients list, client header, overview key contacts, credentials, documents, services, invoice/quote/statement recipients, license users and global search - with each contact keeping the same colour throughout; ticket contact pickers show the name with title and role underneath; fixes: permission checks on the add contact modal and contact page/list actions, contact location limited to the contact's own client on add/edit/bulk assign, contacts list no longer selects user account columns, archived assets and credentials left off the contact page and quick look, saving a contact with the client portal disabled no longer clears their portal login method, replacing a photo no longer tries to delete a directory, sort column whitelisted, list counts and tags batched instead of per row, recurring ticket menu markup, undefined index notices, contacts list no longer scrolls sideways on phones, Edit Service shows avatars on unselected contacts and assets, license user labels toggle their checkbox; new functions/contact.php helpers (contactAvatar, contactLink, contactFlagPills, contactPhoneLink, contactAvatarData, contactOptionDescription), shared contact_form.php, contact_location quick pick, removed unused assetContactAvatar and clientOverviewPersonInitials 2026-10-14 18:33:18 -04:00
johnnyq
032e555f87 Replace copy buttons with hover over copy buttons 2026-10-14 17:27:27 -04:00
johnnyq
fb084ae504 Assets: change status, location and assigned contact in place on the assets list, the asset page and the quick look, using the same quick pickers as tickets (location and contact only offer the asset's own client's); Add/Edit/Copy form split into tabs (Details, Assignment, Network, Purchase, Login or History, Notes) that jumps to a required field left empty on another tab; Printers tab on the assets list with New Printer and a Printers export filter; asset quick look rebuilt as a compact asset page: header with type icon and status, IP/MAC/serial with copy, warranty, location, contact and rack on a few lines, connect buttons, counted tabs showing only what has something in them and reopening on the last one used, open tickets first with a link to the rest, Open asset in the footer. Fixes bulk assign contact/location changing assets of a different client, quick look notes saving the underlying page's asset notes over the connected asset's, and a query per license on the quick look. No DB change 2026-10-14 17:15:17 -04:00
johnnyq
ec205ca633 Agent picker for project managers and recurring tickets: pick the manager on the project page and projects list, and the agent on recurring tickets, inline like ticket assignees 2026-10-13 13:56:47 -04:00
johnnyq
67e511a914 Tags everywhere: the same tag pills on every list and detail page, and an inline tag picker that saves as you tick (single records and bulk, with make-a-tag for admins) in place of the Assign Tags modals 2026-10-13 13:22:58 -04:00
johnnyq
69484a8a2e Replace Tom Select with ITFlow's own select picker: native select stays the source of truth, search, checklists for multi selects, add-your-own for tag fields, phone sheet, and client/agent/contact avatars, tag and category colours, priority dots and asset icons in the options 2026-10-13 12:41:29 -04:00
johnnyq
81062aea0e Client overview redesign with technical and financial sections; client header on all client pages gets initials, industry, tags, open tickets and balance due, and an expandable panel matching the overview 2026-10-10 15:51:07 -04:00
johnnyq
362a6dcfd2 Client side nav: coloured initials and client name under an All clients link, aligned with the menu, click to switch clients 2026-10-10 13:49:47 -04:00
johnnyq
3e36185198 Rebuild dashboard: needs-attention rail, your day (tickets, schedule, time, team workload), finance with cash flow forecast, receivables aging and top clients 2026-10-09 16:55:07 -04:00
johnnyq
bab3d73c86 Rebuild notifications: bell panel and full page
- Bell opens a dropdown panel instead of a modal: Unread/All tabs, grouped
  by day, type icons, relative times, click-through marks read, per-row
  read/unread, mark all as read
- Unread badge refreshes every minute while the tab is visible
- Notifications page rebuilt on the same backend: search, type filter,
  date range, read/unread toggles, proper empty states
- Hide notifications for clients/modules the user cannot access
- Normalise relative notification links so they work from /admin pages
- Remove the old notifications modal and dismiss handlers
2026-10-09 15:52:40 -04:00
johnnyq
f7e5655e05 Rebuild global search as a live search palette
- Press / or Ctrl+K (or click the top bar box) for results as you type,
  grouped by type, with keyboard navigation and recent clients when empty
- Ticket/invoice/quote numbers jump to the top; Enter opens immediately
- Phone, IP (any interface) and MAC matching; app pages offered by name
- Full results page rebuilt on the same search: totals, links into each
  list page, ticket conversation and document text matches
- Passwords no longer rendered into the results page; reveal/copy go
  through the audited endpoint
- Fix stray }); breaking inline scripts on asset and contact pages
2026-10-08 17:40:46 -04:00
johnnyq
49106e2a80 UI fixes: confirm irreversible actions, keep reply drafts guarded, re-enable CSP on portal recurring invoices
- Add confirm-link to 14 one-click delete/disable links (asset, contact,
  files, templates, logo, MFA, calendar event, disable user, cancel schedule)
- confirm_modal.js treats btn-danger / btn-outline-danger as destructive
- Replace per-editor window.onbeforeunload with one guard over all editors
- New js/autosubmit.js replaces inline onchange in the portal; CSP back on
  recurring_invoices.php
- Fix blank user name in disable_user audit log
2026-10-08 16:47:12 -04:00
johnnyq
2c8fb8753c Fix Copy Paste Buttons in certain areas 2026-10-06 22:21:22 -04:00
johnnyq
c3018b7584 Restore the ability to manually typc a value in select boxes with data-tags=true including add ticket watcher 2026-10-01 15:11:58 -04:00
johnnyq
b15ef69bf4 Fix pretty content js helper in modals, fixes the issue with images going out of the boundry of the modal window 2026-09-29 17:22:53 -04:00
johnnyq
5f62218818 Fix TinyMCE Modal Focus, fixed Link Editing and extra ... action button, plus fix tinymce disappears once modal is closed then reopened 2026-09-29 17:07:02 -04:00
Wrongecho
e5d1fe2362 Fix copying text in the dynamic modals (api, credenials) 2026-09-10 14:43:28 +00:00
johnnyq
e7015d1595 Fix undefined item name when selecting from product list in quote or recurring invoice 2026-09-03 18:35:46 -04:00
johnnyq
0c690c4e51 Fix 3 Digit octet fix on IP address for IMask plugin 2026-09-01 18:24:46 -04:00
johnnyq
f6e03b2196 Add Chevron to show top client collapse 2026-08-29 00:46:30 -04:00