Skip to content

feat: CRM page listing trial prospects by MRR potential - #6589

Open
ukutaht wants to merge 1 commit into
masterfrom
trial-prospects-ui
Open

feat: CRM page listing trial prospects by MRR potential#6589
ukutaht wants to merge 1 commit into
masterfrom
trial-prospects-ui

Conversation

@ukutaht

@ukutaht ukutaht commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

Surfaces the trial_prospects table in CRM.

Changes

Please describe the changes made in the pull request here.

Below you'll find a checklist. For each item on the list, check one option and delete the other.

Tests

  • Automated tests have been added

Changelog

  • This PR does not make a user-facing change

Documentation

  • This change does not need a documentation update

Dark mode

  • The UI has been tested both in dark and light mode

The daily scoring worker has been filling the `trial_prospects` table with
no way to read it. This surfaces it in customer support so the CS team can
prioritise outreach by estimated revenue potential, sortable by MRR and
trial start date.

Ranking and pagination live in Plausible.CustomerSupport.TrialProspects
alongside the scoring rules they depend on — the over-top-tier-first order
only makes sense next to the rule that leaves those rows with a null MRR.
@ukutaht
ukutaht requested review from a team and apata August 10, 2026 15:48

# Over-the-top-tier (Custom/Enterprise) prospects rank first
defp order_prospects(q, "mrr", direction) do
order_by(q, [p], [{^direction, p.over_top_tier}, {^direction, p.estimated_mrr}])

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
order_by(q, [p], [{^direction, p.over_top_tier}, {^direction, p.estimated_mrr}])
order_by(q, [p], [{^direction, p.estimated_mrr}])

Because PG ranks null value higher than integer, this simpler order by should give us the enterprise candidates top or bottom depending on sort direction.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we actually want them on top always, we need order_by(q, [p], [{:desc, p.over_top_tier}, {^direction, p.estimated_mrr}]) according to my testing.

<div class="flex items-center justify-between">
<h2 class="text-xl font-bold sm:text-2xl">🔥 Trial prospects</h2>
<p class="text-sm text-gray-500 dark:text-gray-400">
{@total_entries} active trials — ranked by estimated MRR potential

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
{@total_entries} active trials — ranked by estimated MRR potential
{@total_entries} prospects

I suggest to clarify this, because the query also covers recently expired trials.
I removed ranking string because it may be misleading when table is sorted by something else.

Alternatively, maybe something like
{@total_entries} prospects — ranked by {Phoenix.Naming.humanize(@sort_by)} {Phoenix.Naming.humanize(@sort_direction)}?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants