Description
Chatwoot Client Portal by ICT Shift turns your WordPress site into a Chatwoot-backed support portal.
Built by ICT Shift.
Give clients a familiar, branded support area inside WordPress while your team continues working in Chatwoot.
Ideal for businesses that want to:
- Let logged-in users view and reply to support tickets without leaving your website
- Offer contact-style intake pages for non-logged-in visitors
- Keep omnichannel conversations centralized in Chatwoot inboxes (email, livechat, WhatsApp, and more)
- Sync useful customer context from WordPress and commerce plugins into Chatwoot contact records
For help with Chatwoot setup, self-hosting, or hosting guidance, you can contact ICT Shift at https://www.ictshift.com/.
Plugin support is also available in the WordPress.org support forum.
Features:
- Ticket list and detail shortcodes
- Dedicated new-ticket shortcode/form
- Reply support with optional attachments
- Ticket status display and update flow
- Floating livechat widget + embedded chat modes
- Logged-in user livechat identity (
setUser) with optional identity validation (identifier_hash) - Contact sync to Chatwoot from WordPress profile, WooCommerce, and FluentCart (best effort)
- Multi-inbox filtering support
- Webhook-based synchronization support
- Translation-ready text domain
Shortcodes:
[ictss_support_tickets]– ticket list view (+ New Ticket button)[ictss_support_ticket]– ticket conversation detail view (?ictss_ticket_id=)[ictss_support_new_ticket]– dedicated new ticket form[ictss_support_live_chat_full][ictss_support_live_chat_box]
Ticket list shortcode
[ictss_support_tickets]
Shows the ticket list only and includes the “+ New Ticket” header button.
Optional ticket list attributes:
new_ticket_url– override the “+ New Ticket” button URLticket_detail_url– override ticket detail page URL
Example:
[ictss_support_tickets new_ticket_url="https://example.com/new-ticket" ticket_detail_url="https://example.com/ticket-details"]
Ticket detail shortcode
[ictss_support_ticket]
Shows a selected ticket conversation using ?ictss_ticket_id= and includes a “Back to My Tickets” button.
Optional ticket detail attributes:
tickets_url– override the back-to-list button URLshow_unassigned_assignee="yes|no"(defaultno) – whenyes, always show Assigned asUnassignedif no agent is set
New ticket shortcode
[ictss_support_new_ticket]
Optional new ticket attributes:
show_attachments="yes|no"(defaultyes)show_priority="yes|no"(defaultno)inbox_id– override the Chatwoot inbox used for ticket creationmail_to– override mail transport recipient(s) for this page onlyrequire_login="yes|no"(defaultyes) – set tonofor public/contact intake pagestickets_url– override the “Back to My Tickets” button URL after successful submitdebug_console="yes|no"(defaultno) – for admins, logs submit diagnostics to browser console (helpful for mail transport troubleshooting)
Examples:
- Support intake:
[ictss_support_new_ticket show_attachments="yes" show_priority="yes"] - Contact intake (public form):
[ictss_support_new_ticket show_attachments="no" show_priority="no" require_login="no"]
When require_login="no", the form is available to non-logged-in visitors. Enable hCaptcha in plugin settings for public intake protection.
Recommended page setup:
- My Tickets page:
[ictss_support_tickets]and[ictss_support_ticket](can be the same page) - New Ticket page:
[ictss_support_new_ticket](can also be a separate page)
Optional URL overrides:
- Ticket list:
new_ticket_url,ticket_detail_url - Ticket detail:
tickets_url(back to list button) - New ticket:
tickets_url(back to list button after successful submit)
After submit, users are informed that a new ticket can take a few minutes to appear in the ticket list.
Theme compatibility notes:
- Supported compatibility targets: Astra, Divi, BeTheme, and default WordPress themes.
- BeTheme compatibility includes field/button normalization for the new-ticket form (including public contact intake pages).
- Divi compatibility includes suppression of inherited hover pseudo-icons on ICTSS buttons in WooCommerce-themed contexts.
External Services
This plugin relies on external services for support portal functionality and optional anti-bot verification.
Chatwoot
This plugin connects to a Chatwoot instance to provide support ticket, livechat, contact sync, and webhook functionality. The Chatwoot base URL is configured by the site owner in plugin settings and can point to either a self-hosted Chatwoot server or the Chatwoot cloud service.
- What it is: Chatwoot is an open-source customer support platform. This plugin uses the Chatwoot REST API to sync contacts, create tickets, post replies, and receive webhook events.
- Data sent: contact identity and profile data (name, email, phone, optional custom attributes), conversation and ticket metadata, message content, and optional file attachments.
- When data is sent: when loading the livechat widget/embed, creating support tickets, replying to tickets, syncing contacts, loading debug/API diagnostics, and processing webhook events.
- Browser storage: when the livechat widget or embed is enabled, Chatwoot and optional identity/session-reset flows may use browser cookies and local/session storage to maintain chat session state.
- Service URL: Determined by the Base URL configured in plugin settings (e.g. https://app.chatwoot.com/ for Chatwoot cloud, or a custom domain for self-hosted deployments).
If using Chatwoot cloud (app.chatwoot.com):
- Terms of service: https://www.chatwoot.com/terms-of-service
- Privacy policy: https://www.chatwoot.com/privacy-policy
If using a self-hosted Chatwoot instance:
- The data controller is the operator of that server. The site owner is responsible for ensuring appropriate terms and privacy policies are in place for their own Chatwoot deployment. Chatwoot’s privacy policy and terms of service do not automatically apply to self-hosted instances.
- Chatwoot is open-source (MIT licensed): https://github.com/chatwoot/chatwoot
hCaptcha (optional)
This plugin optionally integrates hCaptcha for anti-spam/bot protection on public ticket and contact intake forms.
- What it is: hCaptcha is a third-party CAPTCHA service. It is only loaded when hCaptcha is explicitly enabled in plugin settings.
- Data sent: a challenge response token and visitor IP address (
remoteip) for server-side verification, and the hCaptcha widget JavaScript for browser-side challenge rendering. - When data is sent: only when hCaptcha is enabled in plugin settings AND a visitor submits a public form that requires CAPTCHA verification.
- Service URL: https://www.hcaptcha.com/
- Terms of service: https://www.hcaptcha.com/terms.html
- Privacy policy: https://www.hcaptcha.com/privacy.html
Site owners are responsible for obtaining any consent required in their jurisdiction before enabling external-service features.
Screenshots

Chat widget conversation inside WordPress 
Chat widget embedded inside WordPress page 
Settings – General tab 
Settings – Submit Ticket tab 
Settings – Ticket Details tab 
Settings – Ticket List tab 
Submit new ticket form 
Ticket detail email HTML rendering 
Ticket detail livechat conversation 
Ticket detail multiple downloads 
Ticket detail multiple uploads 
Ticket list view
Installation
- Upload the plugin folder to
/wp-content/plugins/. - Activate the plugin through the Plugins screen in WordPress.
- Go to Settings > Chatwoot Client Portal by ICT Shift.
- Configure settings by tab:
- General: Base URL, Account ID, API Token, Website Token, widget/embed toggles, livechat identity options, contact sync, revenue currency prefix options.
- Cron Sync: Scheduled contact refresh enable/interval/scope, sync status overview, manual batch/full runs, emergency stop, manual contact sync test, Chatwoot attribute key reference.
- Ticket list: Inbox IDs, Tickets List Page URL, New Ticket Page URL.
- Ticket details: Ticket Detail Page URL, refresh interval, reply transport, attachment fallback options.
- Submit ticket: New Ticket Transport, New Ticket Inbox ID, mail recipient/routing, hCaptcha and Public Inbox Identifier.
- Webhooks: Webhook token and webhook URL.
- Debug: embedded troubleshooting panel (WP_DEBUG-aware).
- Save changes on each tab after editing.
- Add shortcodes to your portal pages.
FAQ
-
Does this plugin require Chatwoot?
-
Yes. A working Chatwoot instance is required.
-
Which channels are supported?
-
Ticket list/detail relies on configured Chatwoot inbox data, including email and other supported inbox channels. Livechat identity settings apply only to website widget/embed flows.
-
How do I prevent livechat impersonation?
-
Enable identity validation in your Chatwoot website inbox and in plugin settings, then use the same shared secret.
-
Can I sync WooCommerce and FluentCart fields?
-
Yes. Enable contact sync in plugin settings. The plugin syncs core profile fields and selected commerce attributes when available, including total revenue fields:
–ictss_total_revenue_woo
–ictss_total_revenue_fluentcart
You can also configure revenue display prefix in Settings > Chatwoot Client Portal by ICT Shift > General using Show Currency Prefix for Revenue and Revenue Currency Prefix (for example:EUR,$,USD). -
How can I still expose extra customer context in Chatwoot contact records?
-
The plugin stores fallback context in Chatwoot contact additional attributes during contact sync (for example: FluentCRM URL, latest WooCommerce/FluentCart order summaries, and latest FluentBoards tracked time when available).
-
How can I show synced values in Chatwoot’s Attributes tab?
-
Create Contact Attributes in Chatwoot settings with keys:
ictss_wp_user_url,ictss_fluentcrm_url,ictss_wc_last_order_summary,ictss_fc_last_order_summary,ictss_fluentcart_order_url,ictss_fb_last_time,ictss_fb_last_task(Text type is fine). The plugin will mirror values tocustom_attributeswhen data exists.If WooCommerce / FluentCRM / FluentBoards is not installed, sync still works; those specific values are simply skipped.
-
Can I test contact sync on production without WP_DEBUG?
-
Yes. In Settings -> Chatwoot Client Portal by ICT Shift -> Cron Sync, use the Manual Sync Now form (enter a WordPress user email). The same tab shows latest sync status (including scheduler health and progress), supports Run Cron Batch Now with skip breakdown, Sync All Now (All Batches) for catch-up, and Emergency Stop Cron for lock/abort recovery.
-
Can I control how scheduled sync selects users?
-
Yes. In Cron Sync, choose scope as all users, commerce users (WooCommerce or FluentCart), WooCommerce-only, or FluentCart-only. You can also set interval (hourly, twice daily, daily). Scheduled sync runs in batches and auto-continues in the background with short-delay follow-up batches until the active cycle is complete.
-
How are local phone numbers normalized for Chatwoot?
-
Phone sync is strict E.164. The plugin first tries country/profile hints from WordPress/commerce data. The Default Phone Country Code setting is fallback-only and is used only if no hint resolves a country. If country still cannot be resolved, local phone updates are skipped to avoid wrong-country values.
-
How do I choose the correct FluentCRM contact URL route?
-
In Settings -> Chatwoot Client Portal by ICT Shift -> General, set FluentCRM Contact Route to
subscribersorcontacts.How to verify: open a contact in FluentCRM and inspect the browser URL hash after
#/.
Examples:
–#/subscribers/38/-> choosesubscribers
–#/contacts/38-> choosecontacts -
How are company/city/country synced to Chatwoot contact details?
-
The plugin mirrors these values to Chatwoot
additional_attributesfor compatibility with Chatwoot contact sync behavior:
– company ->additional_attributes.company_name
– city ->additional_attributes.city
– country (ISO code when available) ->additional_attributes.countryWooCommerce and FluentCart billing fields are used as source values when present.
-
What happens when require_login=”no” is used on the new ticket shortcode?
-
The form is available for non-logged-in visitors and is suitable for contact-style intake pages. In this mode, the “Back to My Tickets” success button is not shown for non-logged-in users.
-
What happens on uninstall?
-
By default, uninstall removes plugin options, plugin transients, local conversation cache posts (
ictss_conversation), andchatwoot_contact_iduser meta mappings.If you need to preserve data, define
ICTSS_PRESERVE_DATAastruebefore uninstall.
Reviews
There are no reviews for this plugin.
Contributors & Developers
“Chatwoot Client Portal by ICT Shift” is open source software. The following people have contributed to this plugin.
ContributorsTranslate “Chatwoot Client Portal by ICT Shift” into your language.
Interested in development?
Browse the code, check out the SVN repository, or subscribe to the development log by RSS.
Changelog
2.0.12
- Removed duplicate screenshot files from plugin package assets to reduce plugin ZIP size.
- Kept WordPress.org listing screenshots in the repository root
/assetsdirectory.
2.0.11
- Updated plugin page documentation for clearer setup and usage guidance.
- Fixed screenshot visibility in the WordPress.org plugin listing.
- Improved readme text formatting and encoding for cleaner display in the plugin directory.
2.0.10
- Hardened new-ticket mail attachment handling by attaching uploaded files in-memory during send flow, avoiding temporary file writes while preserving attachment names.
- Excluded local docs/page-export artifacts from release packaging output to keep submission ZIPs clean and deterministic.
2.0.9
- Refactored shortcode/admin/webhook/API diagnostics logging to remove file-wide
error_logsuppressions and keep only narrow, WP_DEBUG-gated log helpers. - Completed shortcode request/upload hardening pass by fixing stale helper usage and keeping nonce-gated upload normalization paths explicit.
- Reduced suppression surface in settings/debug flows and narrowed SQL suppression scope where PHPCS allows line-level scoping.
- Reworked runtime contact/conversation lookup paths to avoid slow
meta_queryusage in hot flows by using bounded paged scans and deterministic conversation indexing. - Standardized request filtering to explicit sanitizing filters across runtime handlers (no unsafe raw filter usage) while preserving strict validation and context-aware output escaping.
- Added strict reviewer-facing development directives for WordPress-native methods first, sanitize/validate/escape lifecycle, nonce/capability fail-closed enforcement, and mandatory pre-submission pattern scans.
2.0.8
- Strengthened WordPress.org submission hardening for nonce verification and request sanitization reviews by aligning guarded superglobal reads with explicit checker-safe validation/sanitization paths.
- Added security-sniff coverage to local PHPCS ruleset (
WordPress.Security.NonceVerificationandWordPress.Security.ValidatedSanitizedInput) so recurring review points fail locally before release. - Improved release preflight pattern checks for settings slug/title detection to avoid brittle formatting dependencies during release validation.
2.0.7
- Hardened shortcode/admin/AJAX request handling by removing raw input filter patterns and enforcing immediate sanitization plus strict scalar validation for POST/GET reads.
- Refined nonce and permission guard flows across form submits and AJAX endpoints to keep security checks explicit and non-bypassable.
- Applied submission-readiness cleanup for WordPress.org review consistency across request, upload, and output handling paths.
2.0.6
- Restored shortcode hardening updates and fixed ticket-list first-load filtering by normalizing invalid/empty status query values to
all. - Prevented a regression where opening the ticket list with an empty
ictss_statusquery parameter could show “No tickets found” while searches still returned tickets.
2.0.5
- Hotfix: restored ticket-list shortcode request handling to the previous stable path to resolve a production regression where valid users could see “No tickets found.”
- Kept webhook authentication/security hardening introduced in 2.0.4 unchanged.
2.0.4
- Added progressive webhook authentication modes: token-only (default), token-or-signature transition mode, and signature-required strict mode.
- Added optional Chatwoot signature verification support with timestamp freshness checks and delivery replay protection.
- Hardened webhook diagnostics by redacting sensitive payload fields and trimming stored debug payload data.
2.0.3
- Hardened nonce, capability, and request sanitization checks across ticket forms, admin actions, webhook tools, and livechat identity AJAX handlers.
- Tightened upload request handling so file arrays are only processed through verified nonce-gated paths.
- Refreshed submission-readiness validation and packaging after WordPress.org review fixes.
2.0.2
- Removed legacy Chatwoot sidebar integration from plugin settings and runtime bootstrap.
- Cleaned documentation to remove deprecated sidebar-token and sidebar-endpoint instructions.
- Kept contact-context sync guidance focused on Chatwoot contact attributes/additional attributes.
2.0.1
- Clarified External Services section to correctly distinguish self-hosted Chatwoot deployments from Chatwoot cloud. Self-hosted instances are now documented separately, noting that the data controller is the server operator and that chatwoot.com terms/privacy do not automatically apply.
2.0.0
- Added contributor username to readme.txt Contributors header.
- Added External Services section to readme.txt documenting Chatwoot and hCaptcha integrations (data sent, terms, privacy links).
- Added .distignore entry to exclude design PSD assets from distribution archive.
- Removed DONOTCACHEPAGE global define, replacing with targeted nocache_headers() calls scoped to debug-mode form renders only.
- Refactored all GET parameter reads to use filter_input(INPUT_GET) via private helpers, removing direct $_GET superglobal access.
- Wrapped all inline script content in (new Function(wp_json_encode(…)))() boundary for safe dynamic JS injection.
- Removed JSON_UNESCAPED_UNICODE and JSON_UNESCAPED_SLASHES flags from JSON-encoded inline script output.
- Renamed livechat embed shortcodes from ict_shift_support_live_chat_* to ictss_support_live_chat_* for prefix consistency.
- Ensured all $_FILES access is routed through the allowlisted get_uploaded_files_from_field() helper.
1.9.9
- Added stronger release preflight checks for WordPress.org submission readiness (external-services docs and packaging exclusions).
- Hardened attachment upload handling by accepting only real uploaded temp files in multipart upload paths.
- Improved settings/admin compliance messaging and nonce handling for ticket status updates.
- Fixed frontend asset loading reliability for ICTSS shortcodes to prevent missing styling in builder/theme render paths.
- Removed explicit textdomain loading call to align with current WordPress.org plugin directory guidance.
1.9.8
- Improved ticket-list performance by reducing unnecessary enrichment calls and adding enrichment caching.
- Hardened release/package validation flow and resolved remaining plugin-check findings for submission readiness.
- Added compatibility hardening for BeTheme and Divi, including button/form UI normalization.
- Added public intake behavior refinement for
require_login="no"and asset cache-busting for CSS/JS updates.
1.9.7
- Added livechat identity controls (auto-identify, optional identity validation hash, auth-session reset)
- Added WordPress/WooCommerce/FluentCart contact sync service
- Added debug status panel and manual one-time contact sync action
- Fixed settings tab save behavior so tab saves no longer clear other-tab values
