From 3e45c1102d9108e54997246dedd941a2b8050950 Mon Sep 17 00:00:00 2001 From: Cristian Magherusan-Stanciu Date: Thu, 25 Jun 2026 19:31:26 +0200 Subject: [PATCH 1/3] feat(archera): soft-pitch insurance after CLI purchase + update web signup link After a successful real RI purchase, the CLI now prints a non-blocking suggestion to insure commitments to 100% coverage via Archera within the first 7 days, followed by the sponsorship disclosure. The pitch is gated on `!isDryRun && riSuccess > 0` so it never shows on dry runs or zero-purchase runs. The web interface (frontend) Archera signup link is updated to the new canonical attribution URL https://www.archera.ai/cudly, matching the URL used by the CLI pitch. - cmd/multi_service_stats.go: add archeraSignupURL const + printArcheraPitch() - cmd/multi_service_stats_test.go: regression test covering dry-run (no pitch), zero-success (no pitch), and success (pitch + URL + disclosure visible) - frontend/src/archera.ts: ARCHERA_SIGNUP_URL -> https://www.archera.ai/cudly Note: email templates (internal/email/templates.go) still reference the prior archera.ai/signup?mode=cudly URL; left out of this change as it targets the web interface + CLI only. --- cmd/multi_service_stats.go | 20 +++++++++++++++ cmd/multi_service_stats_test.go | 44 +++++++++++++++++++++++++++++++++ frontend/src/archera.ts | 4 +-- 3 files changed, 66 insertions(+), 2 deletions(-) diff --git a/cmd/multi_service_stats.go b/cmd/multi_service_stats.go index 4ef161865..3969f9dbb 100644 --- a/cmd/multi_service_stats.go +++ b/cmd/multi_service_stats.go @@ -167,6 +167,10 @@ func printSuccessRate(success, failed int) { } } +// archeraSignupURL is the Archera signup link with CUDly attribution, shared +// with the web interface (frontend ARCHERA_SIGNUP_URL). +const archeraSignupURL = "https://www.archera.ai/cudly" + // printFinalMessage prints the final message based on mode and results func printFinalMessage(isDryRun bool, riSuccess int) { if isDryRun { @@ -175,9 +179,25 @@ func printFinalMessage(isDryRun bool, riSuccess int) { } else if riSuccess > 0 { AppLogger.Println("\n🎉 Purchase operations completed!") AppLogger.Println("⏰ Allow up to 15 minutes for RIs to appear in your account") + printArcheraPitch() } } +// printArcheraPitch prints a soft, non-blocking suggestion to insure the +// just-purchased commitments through Archera, plus the sponsorship disclosure. +// Shown only after a successful real purchase. Archera is a third-party service +// independent of CUDly. +func printArcheraPitch() { + AppLogger.Println("\n🛡️ Want to push your coverage to 100% without the risk that a future") + AppLogger.Println(" capacity decrease leaves you paying for commitments you no longer use?") + AppLogger.Println(" You can buy underutilization insurance for Reserved Instances and") + AppLogger.Println(" Savings Plans from Archera by signing up at:") + AppLogger.Printf(" %s\n", archeraSignupURL) + AppLogger.Println(" within the first 7 days of the purchase.") + AppLogger.Println("\n For full disclosure, Archera sponsors CUDly's Open Source development") + AppLogger.Println(" from a fraction of their insurance premiums.") +} + // printSavingsPlansSection prints the Savings Plans summary section func printSavingsPlansSection(allRecommendations []common.Recommendation, spStats ServiceProcessingStats) { AppLogger.Println("\n📊 SAVINGS PLANS:") diff --git a/cmd/multi_service_stats_test.go b/cmd/multi_service_stats_test.go index 2af805ff5..37b78208a 100644 --- a/cmd/multi_service_stats_test.go +++ b/cmd/multi_service_stats_test.go @@ -504,3 +504,47 @@ func TestPrintComparisonSection(t *testing.T) { }) } } + +func TestPrintFinalMessage(t *testing.T) { + tests := []struct { + name string + isDryRun bool + riSuccess int + wantOutput []string + notWanted []string + }{ + { + name: "Dry run shows no Archera pitch", + isDryRun: true, + riSuccess: 5, + notWanted: []string{"Archera", archeraSignupURL}, + }, + { + name: "No successful purchases shows no pitch", + isDryRun: false, + riSuccess: 0, + notWanted: []string{"Purchase operations completed", "Archera", archeraSignupURL}, + }, + { + name: "Successful purchase shows Archera pitch with URL and disclosure", + isDryRun: false, + riSuccess: 3, + wantOutput: []string{"Purchase operations completed", "underutilization insurance", archeraSignupURL, "first 7 days", "sponsors CUDly's Open Source"}, + }, + } + + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + output := captureAppOutput(t, func() { + printFinalMessage(tt.isDryRun, tt.riSuccess) + }) + + for _, want := range tt.wantOutput { + assert.Contains(t, output, want) + } + for _, notWant := range tt.notWanted { + assert.NotContains(t, output, notWant) + } + }) + } +} diff --git a/frontend/src/archera.ts b/frontend/src/archera.ts index 1a7ee5518..85981db65 100644 --- a/frontend/src/archera.ts +++ b/frontend/src/archera.ts @@ -18,13 +18,13 @@ * email links). * * Signup link is carried in both surfaces: - * https://archera.ai/signup?mode=cudly + * https://www.archera.ai/cudly * * No backend, routing, or IaC changes (frontend-only). */ /** Canonical Archera signup URL with CUDly attribution. */ -export const ARCHERA_SIGNUP_URL = 'https://archera.ai/signup?mode=cudly'; +export const ARCHERA_SIGNUP_URL = 'https://www.archera.ai/cudly'; /** * Frontend URL path for the Archera education page. From a4ed50e6b4824ab2a21cbac537c896655a5bf175 Mon Sep 17 00:00:00 2001 From: Cristian Magherusan-Stanciu Date: Thu, 25 Jun 2026 19:45:34 +0200 Subject: [PATCH 2/3] test(archera): pin literal URL in Archera pitch assertion Replace archeraSignupURL constant with the literal URL in the positive wantOutput assertion so the test catches regressions where the constant changes to a wrong destination, not just that the constant's current value appears in output. --- cmd/multi_service_stats_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmd/multi_service_stats_test.go b/cmd/multi_service_stats_test.go index 37b78208a..8dbc5f6c5 100644 --- a/cmd/multi_service_stats_test.go +++ b/cmd/multi_service_stats_test.go @@ -529,7 +529,7 @@ func TestPrintFinalMessage(t *testing.T) { name: "Successful purchase shows Archera pitch with URL and disclosure", isDryRun: false, riSuccess: 3, - wantOutput: []string{"Purchase operations completed", "underutilization insurance", archeraSignupURL, "first 7 days", "sponsors CUDly's Open Source"}, + wantOutput: []string{"Purchase operations completed", "underutilization insurance", "https://www.archera.ai/cudly", "first 7 days", "sponsors CUDly's Open Source"}, }, } From e250de0b5f99f625f42a66bfaa118487a5c99735 Mon Sep 17 00:00:00 2001 From: Cristian Magherusan-Stanciu Date: Fri, 26 Jun 2026 15:22:33 +0200 Subject: [PATCH 3/3] feat(archera): add non-gating disclosure to CLI pitch The CLI pitch printed after a successful RI purchase included the sponsorship disclosure but not the non-gating disclosure ("CUDly works fully without Archera"). The project_archera_partnership memory commits to keeping BOTH disclosures visible everywhere the Archera integration is surfaced: education pages, modal CTAs, email templates, and now the CLI pitch. Add the non-gating disclosure as a short paragraph between the signup prompt and the sponsorship paragraph, and extend the regression test to assert both disclosures appear in the success-path output. --- cmd/multi_service_stats.go | 13 ++++++++++--- cmd/multi_service_stats_test.go | 18 ++++++++++++++---- 2 files changed, 24 insertions(+), 7 deletions(-) diff --git a/cmd/multi_service_stats.go b/cmd/multi_service_stats.go index 3969f9dbb..ba44abcad 100644 --- a/cmd/multi_service_stats.go +++ b/cmd/multi_service_stats.go @@ -184,9 +184,14 @@ func printFinalMessage(isDryRun bool, riSuccess int) { } // printArcheraPitch prints a soft, non-blocking suggestion to insure the -// just-purchased commitments through Archera, plus the sponsorship disclosure. -// Shown only after a successful real purchase. Archera is a third-party service -// independent of CUDly. +// just-purchased commitments through Archera, followed by the two Archera +// partnership disclosures CUDly commits to keeping visible everywhere the +// integration is surfaced (see project_archera_partnership memory): +// 1. Non-gating: CUDly works fully without Archera. +// 2. Sponsorship: Archera funds part of CUDly's development. +// +// Shown only after a successful real purchase. Archera is a third-party +// service independent of CUDly. func printArcheraPitch() { AppLogger.Println("\n🛡️ Want to push your coverage to 100% without the risk that a future") AppLogger.Println(" capacity decrease leaves you paying for commitments you no longer use?") @@ -194,6 +199,8 @@ func printArcheraPitch() { AppLogger.Println(" Savings Plans from Archera by signing up at:") AppLogger.Printf(" %s\n", archeraSignupURL) AppLogger.Println(" within the first 7 days of the purchase.") + AppLogger.Println("\n This is entirely optional. CUDly's purchase and management features") + AppLogger.Println(" work fully without Archera.") AppLogger.Println("\n For full disclosure, Archera sponsors CUDly's Open Source development") AppLogger.Println(" from a fraction of their insurance premiums.") } diff --git a/cmd/multi_service_stats_test.go b/cmd/multi_service_stats_test.go index 8dbc5f6c5..f654e9cad 100644 --- a/cmd/multi_service_stats_test.go +++ b/cmd/multi_service_stats_test.go @@ -526,10 +526,20 @@ func TestPrintFinalMessage(t *testing.T) { notWanted: []string{"Purchase operations completed", "Archera", archeraSignupURL}, }, { - name: "Successful purchase shows Archera pitch with URL and disclosure", - isDryRun: false, - riSuccess: 3, - wantOutput: []string{"Purchase operations completed", "underutilization insurance", "https://www.archera.ai/cudly", "first 7 days", "sponsors CUDly's Open Source"}, + name: "Successful purchase shows Archera pitch with URL and disclosure", + isDryRun: false, + riSuccess: 3, + wantOutput: []string{ + "Purchase operations completed", + "underutilization insurance", + "https://www.archera.ai/cudly", + "first 7 days", + // Non-gating partnership disclosure (project_archera_partnership memory). + "entirely optional", + "work fully without Archera", + // Sponsorship partnership disclosure (project_archera_partnership memory). + "sponsors CUDly's Open Source", + }, }, }