johnnyq
|
980f394ee2
|
Send mail again on installs first set up with Microsoft 365 or Google OAuth on 26.11: cast the SMTP host to a string at both sendQueueEmail call sites, since it is NULL until a host is saved and the typed argument threw a TypeError that ended the mail queue run before anything was sent; catch any Throwable around each send so one failing email is marked failed and the rest still go out, where only PHPMailer's own Exception was caught and an Error left the email as Sending; add the changelog entries. Fix reported by toto707 on the forum
|
2026-11-10 16:25:07 -05:00 |
|
johnnyq
|
1cafa86aaa
|
Point the Client portal tab's notice to Modules, where the client portal is switched on, instead of Settings > Client Portal, and give the sign-in field in the Turn on portal access window a sign-in icon so it doesn't show two keys
|
2026-11-10 15:47:40 -05:00 |
|
johnnyq
|
a85bcc1169
|
Add a Client portal view to Admin > Users listing every contact with a portal login across all clients, with their client, how they sign in, two-step status and last sign-in, searchable by name, email or client, sortable, paged, and filterable by client and by sign-in (password, Microsoft 365, no two-step, never signed in, access off); add row and bulk actions to email a password link or the invite again, turn off two-step sign-in, forget remembered browsers, and turn portal access off or back on, each logged against the contact; add the portal user helpers in functions/portal.php, have the portal's People page turn access off through the same function, which now also forgets remembered browsers, and keep the Users search to the side being looked at; add the changelog entries
|
2026-11-10 15:30:10 -05:00 |
|
johnnyq
|
a7a052729e
|
Show only the picked client's contacts in the contract form and use the standard pickers across the contract modals: the form put every client's contacts in the page and hid the others with the hidden attribute, which Safari ignores on an option, so New Contract from the Contracts page listed them all there; it now renders only the contract's client's contacts and fetches them from get_client_contacts when a client is picked, with the primary picked; make every select in the contract and contract template modals a picker, with avatars and titles for contacts and owners, except frequency and tax in the recurring invoice modal, which match the recurring invoice form; add the changelog entries
|
2026-11-10 13:54:07 -05:00 |
|
johnnyq
|
4000e6bcc6
|
Drop contract_templates.company_id in database 3.6.3 where it exists: the 2.3.7 migration shipped in v25.11 creating it as INT NOT NULL with no default and was later changed to leave it out, so installs that updated on v25.11 kept a column nothing used, which the debug page listed as extra and which made adding a contract template fail in strict SQL mode; add the changelog entries and say in CONTRIBUTING why a shipped migration must not be edited
|
2026-11-10 12:51:38 -05:00 |
|
johnnyq
|
a737c04a7d
|
Remove Hosting Coming Soon as its live now
|
2026-11-09 17:35:53 -05:00 |
|
johnnyq
|
a6d3b465df
|
Update Changelog and App Version
|
2026-11-09 15:43:02 -05:00 |
|
johnnyq
|
6ecc27e7ca
|
Version ITFlow's scripts and stylesheets so browsers fetch the new copies after an update instead of needing a cache clear: add staticFileUrl() in functions/app.php, which adds ?v= and the file's modification time to the address, and send every script and stylesheet tag through it, libs included, with page-relative addresses changed to start from the site root; add js/tinymce_defaults.js to set TinyMCE's cache_suffix so the plugins, theme and skins it loads itself are versioned too; load ticket collision detection only when a ticket is shown, so a ticket that isn't found no longer throws a script error; add changelog entries and a CONTRIBUTING rule that new tags must use staticFileUrl()
|
2026-11-09 01:22:35 -05:00 |
|
johnnyq
|
076f4295be
|
Bug fixes
|
2026-11-07 12:26:58 -05:00 |
|
johnnyq
|
1c741b808b
|
Bump Version
|
2026-11-07 12:06:20 -05:00 |
|
johnnyq
|
29a0b9b303
|
Update Chnagelog
|
2026-11-07 01:27:56 -05:00 |
|
johnnyq
|
53e6564f76
|
Stop row actions menus being cut off on short lists - a list's table scrolls sideways inside .table-responsive, which also clipped a row's menu at the bottom of the list when it had only a row or two, hiding its last options; new js/bootstrap_defaults.js, loaded right after Bootstrap on agent pages and the client portal, sets Bootstrap's dropdown default to Popper's fixed strategy so menus open over the page and still turn upward when there's no room below, covering every list, the board, modals and the portal, with navbar menus unaffected; changelog updated
|
2026-11-06 18:51:50 -05:00 |
|
johnnyq
|
2a36534583
|
Add demo mode for a public demo like demo.itflow.org - $config_demo_mode = true; in config.php puts one-click sign-in buttons for Admin, Technician, Accountant and a client portal contact on the sign-in page and a demo notice on every page, and the new Demo Reset cron job rebuilds the demo nightly at 2:00 AM from db.sql with all starter content, the demo clients and the demo accounts, empties uploads except the logo and signs everyone out, keeping the company details, timezone and cron schedules; visitors can try everything except users and roles, their own sign-in details, mail, payment, AI and texting settings, API keys, backups, updates, cron, log forwarding, company, module and portal settings, custom links, starter content and share links, Debug is closed, guest links open only for someone signed in, queued email is cancelled with the reason, no sign-in alert emails are sent, certificate checks reach only public addresses on port 443, and the domain and certificate refreshers are left out; new functions/demo.php and cron/demo_reset.php, no database change, changelog, CONTRIBUTING and README updated
|
2026-11-06 17:46:40 -05:00 |
|
johnnyq
|
79e616614a
|
Set up a hosted instance and connect it in one command - Add Instance takes the address it will have, and the instance page gives a ready setup_cli command with the connection code and the client's company name, address, phone, website, tax ID, currency and primary contact as the first admin; setup_cli gains --manager-code and --manager-required (connects after setup, writes the managed line to config.php, exits 3 if it set up but could not connect), --ask-missing, --generate-password, --json and ITFLOW_SETUP_ environment variables for any option, and shows the cron job as a crontab line and for a hosting panel with the full PHP path; Managed Instances shows a connected instance whose cron has never run as Waiting for its cron job with the command to add, and the Managed Instances job says so in its notification; new managedSetupCommand(), the cron command in the instance report and the waiting state in managedInstanceHealth(), changelog updated
|
2026-11-06 14:29:27 -05:00 |
|
johnnyq
|
172cd4933e
|
Turn cron on by default for new installs so adding the cron job is the only step - database 3.6.2 changes the default of settings.config_enable_cron to 1 and nothing else, so an existing install keeps its setting on or off, and setup/seed_data.php sets it for both setup paths; Get started's cron step is now Add the cron job with a line for hosting control panels such as Jabali, HestiaCP and cPanel, and shows Turn cron back on only when someone has switched it off; the setup page and setup_cli no longer say cron ships off, CONTRIBUTING's master switch section explains the new default, changelog updated
|
2026-11-06 14:26:50 -05:00 |
|
johnnyq
|
b391e2ce6c
|
Add Skyetel text messaging with two-way ticket texting, text to ticket for contacts, Text reply on tickets, a Texts inbox for unmatched numbers, verification codes and spam (codes masked, limited to credential access, every reveal audited, wiped after a day), STOP/START/HELP handling, a text log with retry and cancel in Maintenance > Text Messages, the Text Messages cron job, and texts to clients about their tickets, visits, visit reminders and invoices with per-contact opt-in from the contact, by text or in the client portal, quiet hours, and new settings in Tickets and Notifications (database 3.6.0 and 3.6.1)
|
2026-11-06 00:08:10 -05:00 |
|
johnnyq
|
87cdf79b28
|
Make managed mode off by default and turned on per side in config.php - $config_enable_managed_instances = true; adds Admin > Managed Instances, the api/managed endpoints and the Managed Instances cron job, and $config_enable_managed_by = true; (or $config_manager_required = true;) adds Admin > Managed By, the Manager Check-in cron job and support sign-in; with a side off its menu entry, pages, modal, post handler and cron job are gone, the manager endpoints answer 503 so instances keep their connection and retry, a connected instance stops checking in and its locks, read-only and suspended lift while its connection is kept, any open support session is ended, and the support user still takes no seat; new managerEnabled(), managedEnabled() and managedConnected(), the cron registry and health check leave out the jobs of a side that is off, changelog updated
|
2026-11-05 20:17:42 -05:00 |
|
johnnyq
|
b5ceeb4eaf
|
Bill sign-ups through the API and follow up when an invoice is paid - a lead that pays an invoice in full becomes a client however it is paid (online, autopay, a recorded payment or a batch), with the new A lead that pays an invoice becomes a client switch in Admin > Settings > Invoices and billing, on by default; a non-billable open ticket tied to an invoice (one raised through the API with ticket_invoice_id, or a quote's tickets once it becomes the invoice) gets an internal note when the invoice is paid in full, goes from On Hold back to Open, and its assigned agent is notified in the app and by email, while billable tickets whose time is on an invoice are left alone; new API endpoints recurring_invoices/create (lines from products or spelled out, the client's currency, frequency, start date, optional first invoice made at once and emailed to the primary and billing contacts, or marked Sent so its link can be paid, the answer including the invoice reference, amount, due date and pay link), recurring_invoices/read and portal_invites/create (sent from the company rather than the key's agent); tickets/create takes ticket_status (an active status other than Resolved and Closed), ticket_invoice_id (one of the client's own invoices) and ticket_notify agents to tell only the team; database 3.5.9 adds settings.config_invoice_paid_lead_to_client; invoicePaidFollowUp() runs from triggerCustomAction() on invoice_pay, with recurringInvoiceCreate(), billingInvoiceIssue() and the paid kind of ticketAgentEmailContent() in support; the Clients list reads each contract's term, so Renews soon shows again and its PHP warning is gone; changelog updated
|
2026-11-05 19:00:16 -05:00 |
|
johnnyq
|
294352fd8b
|
Let the API raise a ticket from a ticket template - tickets/create takes ticket_template_id, giving the ticket the template's subject and details when none are sent, its category, priority, billing and agent unless sent, and its tags, due time and tasks (the ones the answers call for), with the template's fill-ins answered from ticket_fill_ins and its placeholders filled in, and a missing or archived template, fill-ins that aren't an object, a required fill-in left out or a choice not on a list refused with 400 and the reason; ticket_notify sends the contact and watchers the Ticket Created email when Email clients about their tickets is on, tells the new-ticket address and notifies the assigned agent in the app and by email; the answer now includes ticket_reference, ticket_url (the contact's link to the ticket) and, from a template, ticket_tasks; canned responses now fill in a ticket's template fill-in answers such as [Hostname] alongside [Contact] and [Ticket], never over a built-in placeholder of the same name, and the canned response form says so; contacts/create and locations/create no longer write a PHP warning for each field left out; the new-ticket agent email reads raised through the API; changelog updated
|
2026-11-05 17:39:22 -05:00 |
|
johnnyq
|
1649db51a5
|
Add secure link sharing for the client IT documentation PDF: new Export shared-link type started from Export Data (Share a link, carrying over the ticked sections) or Shared Links (Share the IT documentation), PDF built at share time with the sharing agent's permissions and stored in uploads/shares encrypted with the link-derived key, deleted when the link is ended, expires or is used up and swept by the nightly prune, PDF password required and the sharing protection policy applied when passwords and 2FA secrets are included, guest page with Download the PDF and a password hint, download notification and client audit entry, section picker takes an id prefix and preselected sections, changelog updated
|
2026-11-05 16:03:43 -05:00 |
|
johnnyq
|
3b5c11c552
|
Add managed mode, so one ITFlow can manage others - Admin > Managed Instances adds an instance and gives a one-time connection code (a week) that the other ITFlow pastes into the new Admin > Managed By, after which it checks in every minute from the new Manager Check-in cron job with a health report (versions, update waiting and whether it has security fixes, cron, last backup, errors today, agents against the seat limit, clients, storage) and takes back what the manager sets; the manager lists each instance's version, health, seats and last check-in with a page per instance showing what needs a look, its requests and everything it reported, can update it by hand or automatically after a set number of days (security releases straight away, not retried for six hours after a failure), set its seat limit and white-label key (locked on the instance while set), make it read-only (look, export and download only, across agents, portal, guest links and the API) or suspended (a notice with the manager's message and contact, 503 for the API) with other cron jobs paused until it is active again, sign in to it as support through a signed one-time two-minute link into a two-hour session that takes no seat, can't open the vault and can't set passwords or make API keys, and remove it, while the new Managed Instances job notifies when one stops checking in and closes requests never answered; instances only call the manager, can disconnect unless config.php sets $config_manager_required, and the Update page and queue_update defer to the manager; database 3.5.8 adds managed_instances, managed_instance_commands, settings.config_manager_keys and settings.config_managed, the logic is in the new functions/managed.php with api/managed/enroll.php, api/managed/checkin.php, login_support.php and includes/managed_blocked.php, cronJobClaim() takes a paused reason that leaves a due job due, getAgentUserLimit() and getActiveAgentUserCount() honour the manager's limit and leave out the support user, the vault helpers read a missing session key as empty, the audit log knows the new types and actions, and the email parser no longer logs an App Logs error every minute while parsing is switched off; changelog updated
|
2026-11-05 15:22:41 -05:00 |
|
johnnyq
|
d7bc1bccf7
|
Make Maintenance > Update easier to follow - it opens with where the install stands (up to date, an update available, updating, the database still to finish, checking) and the one button for it, Update ITFlow in place of Queue Update, with what's new below it (the release notes between this install and the latest, read from the changelog by the update check, developer notes and commits folded away), what to do first including the ITFlow files changed on this install that updating would put back, the update shown running with the page refreshing itself and then when it finished or what stopped it, and this install's version, branch, database, commit, last check, last update, cron and the command to update from a shell alongside; database 3.5.7 adds settings.config_update_details, written by cron/update_check.php through the new updateCheckDetails(), updateChangelogSections() and updateChangelogHtml() render the release notes escaped, cron/app_update.php asks for a fresh check after an update, changelog updated
|
2026-11-05 14:25:19 -05:00 |
|
johnnyq
|
c11de9a599
|
Drop the phone formats build script from scripts/ - it is a maintainer tool, not one for installs - and say in functions/phone_formats.php where its rules came from (libphonenumber v9.0.43's PhoneNumberMetadata.xml), how they were taken and to make it again from a newer release rather than edit it by hand; changelog updated
|
2026-11-05 13:24:59 -05:00 |
|
johnnyq
|
3143cdb115
|
Fix phone numbers keeping the 0 dialled at home after the country code (+49 0172 1234567) and click-to-call dialling it - formatPhoneNumber() now writes every country's numbers with Google libphonenumber's rules from the new functions/phone_formats.php, built by scripts/phone_formats_build.php from libphonenumber v9.0.43, taking off the national prefix and a typed-in country code where what is left is still a number of that country, with the international format after the code and the national format without it, German landlines split after their area code, Italy keeping its 0 and North America unchanged; the new phoneDialNumber() gives tel: links +code and the number without its prefix, used by contactPhoneLink(), vendorDialNumber() and every hand-built tel: link on the agent side, the client portal and the guest ticket page, and the ticket quick look now dials the extension after a pause instead of running it into the number; changelog updated
|
2026-11-05 13:16:06 -05:00 |
|
johnnyq
|
cf2c9c2d9b
|
Let clients pay the card fee - turn on Clients pay the card fee on Stripe in Admin > Payment Providers with Stripe's percent and fixed rate, and each card payment in the client portal, through an invoice's link, by autopay or from Charge Saved Card is grossed up so Stripe's fee comes out of it, with one fee per payment shared over its invoices; the fee is shown before paying (Pay invoices, checkout, the guest pay page, invoice pages, autopay and the Charge Saved Card window) and goes on each invoice as a Card Fee line with no tax when the payment is booked, carried in the PaymentIntent's itflow_fees metadata and checked against the amount received to the cent; a client can be let off it with No card fee on their Billing tab, refunding a card payment takes its Card Fee line back off, autopay and Charge Saved Card now compare cents instead of whole dollars, database 3.5.6 adds the provider and client columns, changelog updated
|
2026-11-05 12:47:06 -05:00 |
|
johnnyq
|
5918cc59d4
|
Bump app version
|
2026-11-04 14:46:01 -05:00 |
|
johnnyq
|
e0f2b229ff
|
Update changelog
|
2026-11-04 14:41:50 -05:00 |
|
johnnyq
|
e472c95a11
|
Record Stripe fees every 15 minutes instead of once a night - a new Payment Provider Fees cron job runs the fee recorder that Nightly Tasks used to, Nightly Tasks no longer does, the recorder holds a lock so the job and Record fees now can't both record the same fee, and the payment provider screens no longer say fees are recorded each night
|
2026-11-04 14:38:32 -05:00 |
|
johnnyq
|
66d08c00be
|
Fix Transactions Money in and Money out on All accounts counting every transfer twice - a transfer is money moved between your own accounts, so across all accounts both of its lines are now left out of the totals, the Money in and Money out pills and their export, while the Transfers pill still lists them and a single account's view still counts them as money in and out of that account
|
2026-11-04 14:29:01 -05:00 |
|
johnnyq
|
aff6812036
|
Security: hold an agent who must set up MFA to the set up page on every request, not just at sign in, and fix the client portal two-step gate, which a path added to the URL or a second action sent with the set up one got past - both now go through requestIsMfaSetup(), which checks the script actually running and every key in the request; View as contact is refused while an agent still owes MFA set up, and agents are emailed when MFA is turned on
|
2026-11-04 14:01:40 -05:00 |
|
johnnyq
|
9b92261e8c
|
Security: end a user's other sessions when their password changes - each session carries a stamp of the password it signed in with and the agent and client portal checks sign out any that no longer match, covering a self change, an admin setting it, the incident-response reset, portal reset links and invites, and View as contact; a portal self change keeps the browser that made it on a new session id
|
2026-11-04 13:50:17 -05:00 |
|
johnnyq
|
08d353ab65
|
Update changelog
|
2026-11-04 13:35:07 -05:00 |
|
johnnyq
|
6e0acd2d31
|
Security: stop a backup restore from carrying .htaccess, .user.ini or .htpasswd files into uploads or writing into the backup storage directory, always rewrite the backup storage guard instead of only when missing, and rewrite the shipped deny-all guards in uploads/backups, canned_responses, expenses and tmp after every restore
|
2026-11-04 13:25:42 -05:00 |
|
johnnyq
|
5151dd62fa
|
Update Sponsor name
|
2026-11-04 12:08:40 -05:00 |
|
Wrongecho
|
16ee56c044
|
Add cron notification for expiring api keys
|
2026-11-03 14:42:26 +00:00 |
|
Wrongecho
|
12a7a28a9d
|
Products API - Add update endpoint
|
2026-11-03 14:32:23 +00:00 |
|
johnnyq
|
278df4e7b3
|
Speed up Transactions, Reconcile and the transactions export again by reading the ledger lines first and joining each to its account with STRAIGHT_JOIN instead of letting the optimizer look lines up through a temporary index, and stop billable expenses waiting to be invoiced from slowing every page: database update 3.5.5 indexes expenses.expense_refund_of_id so the side menu count, the invoice page, Add Expenses and the expense quick look no longer check each waiting expense against every expense; 26.11.2 changelog updated
|
2026-11-02 16:29:18 -05:00 |
|
johnnyq
|
469f3df2e7
|
Update App version
|
2026-11-02 16:06:55 -05:00 |
|
johnnyq
|
06f6a81a79
|
Update Changelog
|
2026-11-02 16:04:20 -05:00 |
|
johnnyq
|
c24d13bfe8
|
Speed up Transactions, the Transfers pill, Reconcile and the transactions export: database update 3.5.4 indexes transfers.transfer_expense_id so the ledger no longer checks every expense against every transfer, accountLedgerSql() takes a with_balance flag so the running balance is only worked out where it shows (one account in date order and its export), and the Transfers summary cards come from the same pass as the pill counts and totals
|
2026-11-02 15:59:11 -05:00 |
|
johnnyq
|
87d8fdcdf8
|
Update license
|
2026-10-31 17:07:01 -04:00 |
|
johnnyq
|
228e37a01a
|
Update License
|
2026-10-31 16:55:47 -04:00 |
|
johnnyq
|
916d2d72d4
|
Update Sponsor URL
|
2026-10-31 16:06:00 -04:00 |
|
johnnyq
|
e04699734a
|
Add All Sponsors as of Oct 2026
|
2026-10-31 13:57:19 -04:00 |
|
johnnyq
|
80ba3094d0
|
Update ITFlow Version and README
|
2026-10-29 15:07:03 -04:00 |
|
johnnyq
|
aeff485fa5
|
Update hosting link
|
2026-10-29 15:03:12 -04:00 |
|
johnnyq
|
74497de30a
|
README: rewrite for 26.11 with the ITFlow logo, a dashboard screenshot that follows GitHub's light or dark mode, a grid of eight screenshots from the demo (tickets board, ticket, client overview, assets, contract, invoices, calendar and client portal), a short why and what's new in 26.11, features grouped by service desk, client documentation, contracts and billing, client portal and team, requirements, the install script and both ways to update, and the community, contributing, supporters, security and license sections brought up to date; screenshots and logo in .github/readme
|
2026-10-29 14:58:47 -04:00 |
|
johnnyq
|
3ff116f0d3
|
Database updates: keep junk values from stopping the 26.11 update - 3.0.3 sets trip miles of a billion or more to 0 before trip_miles becomes decimal(10,1), 3.1.1 sets tax rates of 100,000% or more to 0 before tax_percent becomes decimal(9,4), and 3.5.0 leaves out a client rate of 100,000,000 or more when making Standard terms and skips clients already given them by a run that stopped part way, so an update that failed at any of these resumes cleanly when run again
|
2026-10-29 13:45:59 -04:00 |
|
johnnyq
|
e6382145ef
|
Bump ITFlow Version
|
2026-10-29 11:57:18 -04:00 |
|
johnnyq
|
8e24607a0a
|
Contracts: refuse impossible dates (2026-02-30) when adding, editing, activating, renewing, cancelling or starting from a template instead of failing on save; keep each term to the day of the month it started on or the last day of a shorter month so month-end contracts no longer drift (PHP, nightly renewal, the Renew window, templates, Standard terms and contract_form.js); withdraw signing requests still waiting on the client or a countersignature when a contract is cancelled, when it ends nightly or when its client is archived (singly or in bulk), and refuse signing or countersigning on ended, cancelled or archived-client contracts through the link, the portal and Countersign; leave archived clients' contracts alone nightly (no renewing, ending or reminders), keep them out of the all-clients list, Due soon and the side menu count, and refuse sending them to sign; count a self-renewing contract as due soon and remind about it only when its notice date falls within its term, so Standard terms and monthly contracts with 30 days' notice no longer remind every term; keep drawing and adding prepaid hours on a cancelled contract until its last day; refuse deleting a contract once tickets drew on its prepaid hours or it was signed by both, showing why in place of Delete; changelog updated
|
2026-10-28 23:51:45 -04:00 |
|