@aglyn/plugins-crm
The CRM plugin for Aglyn: leads, contacts, companies, deals, tasks and reports, managed in the Aglyn console. Install it if you are running or building on the Aglyn platform and want its CRM.
Published to npm from the Aglyn monorepo. Versions follow semantic versioning.
Install
npm install @aglyn/plugins-crm
Peer dependencies:
@mui/material@mui/x-data-gridfirebasefirebase-adminnextreact
None is optional. firebase-admin and next are used by the server half (@aglyn/plugins-crm/server).
What's in it
This package is a first-party Aglyn plugin. It is loaded through Aglyn's plugin manager: the apps read its entry in the monorepo's plugins.config.json, import the module each surface names, and call the registrar declared for that surface. It is not a standalone library; installing it on its own loads nothing.
The CRM is console-only. Its records live in Firestore and it has no canvas component, so it adds nothing to a published page and declares no site registrar.
In the console
registerCrmConsole() registers:
- A CRM nav item and hub at
/crm, with the sections Contacts, Leads, Companies, Deals, Tasks, Reports, Fields and Settings as routes beneath it. The old/contactsaddress redirects to the hub. The hub is code-split, requires thedata.managepermission, and sits behind thecrmfeature flag. - Dashboard widgets "Tasks due" and "CRM at a glance" in both the
hostDashboard(one site) andorgDashboard(whole organization) slots. - A "Saves to contact fields" widget in the
formContactFieldsslot, a zone the forms plugin hosts on a form's page. - Four zones the CRM hosts for other plugins to draw in: one for booking a meeting from a record, one that says which campaign or link a record came from, one before a contact's or a lead's Send email for another way to write to the person, such as answering them in a sequence's thread, and
crmRecordActions(AGL-4098), any other act on a contact from its header, such as starting a quote. - The CRM's record routes, so other surfaces can link to a record.
- Record count sources for
lead(the leads a site captured) andcontact(the organization's, a count that crosses sites) (plugin-record-counts), which a campaign's conversion report divides by.
On the server
registerCrmConsoleApi() from @aglyn/plugins-crm/server (the consoleApi surface) registers routes under the crm prefix for contact stage and field updates, contact creation and merge, lead conversion, deal stages, tasks, one-to-one email and a contact's email history, erasing a person, organization-level activity, recipes, and the workspace's inbound email capture address. Contacts, companies, leads, deals and tasks are imported and exported through the platform's transfer framework, and activities, pipelines and custom fields exported: registerCrmConsoleServerDeclarations() registers each resource's server half (src/lib/transfer/) and the console registrar its name in the import wizard and export dialog. It also registers the CRM on two core seams, so another plugin can read a record's facts or file an item on a record's timeline without importing this package.
At the console's boot it also registers the CRM's setup writers on the plugin-resource-drafts seam (crm-pipeline, crm-field, crm-picklist-values) and the build operations Aglyn AI plans with them (plugin-ai-capabilities): a pipeline with its stages, a custom field, and values added to a picklist or a Choice field (src/lib/model/crm-picklist-setup-content.ts), saved live under the console's rules (src/lib/model/crm-setup-content.ts, src/lib/server/crm-setup-writers.server.ts).
At the console's boot (registerCrmConsoleServerDeclarations) it registers a membership detacher (plugin-membership-detach): when the plugin that keeps a container — a campaign — removes it, the container comes off every lead and every contact facet that names it, and the records stay.
Entry points
| import | contents |
|---|---|
@aglyn/plugins-crm | BUNDLE_ID, registerCrmConsole, CRM_CONSOLE_SECTIONS, crmRoutes(basePath) for building links into the hub, and the useContactFieldDefinitions hook |
@aglyn/plugins-crm/server | registerCrmConsoleApi and the route handlers |
@aglyn/plugins-crm/* | any module under src/lib/ |
Usage
The registrars are normally called by Aglyn's generated plugin loaders. Called directly:
// Console app
import { registerCrmConsole } from '@aglyn/plugins-crm'
registerCrmConsole()
// Server-only API dispatcher
import { registerCrmConsoleApi } from '@aglyn/plugins-crm/server'
registerCrmConsoleApi()
How it fits
A plugin may import the tenant runtime, the renderer, the Besigner logic, the core and the shared packages. It never imports another plugin, and the core never imports a plugin. The CRM depends on @aglyn/aglyn, the tenant packages (@aglyn/tenant-runtime, @aglyn/tenant-data-admin, @aglyn/tenant-feature-instance) and several @aglyn/shared-* packages. Where it meets bookings, forms or campaigns it does so through zones and core seams: one plugin hosts a zone, another registers a widget in it, and the core carries the contract.
License
Apache-2.0. Source: https://github.com/aglyn/aglyn/tree/main/libs/plugins/crm