From ee67512520cfcbb6dbb6f188ac24cbb8912d1cf4 Mon Sep 17 00:00:00 2001 From: Vitor Mattos <1079143+vitormattos@users.noreply.github.com> Date: Tue, 7 Jul 2026 17:14:50 -0300 Subject: [PATCH 1/2] refactor: add pricing infrastructure components Add infrastructure for pricing page feature without deploying the page itself: New Classes & Tests: - support/Pricing/WooCommerceAuthHeadersBuilder: Build authenticated API headers - support/Pricing/WooCommerceProductCollection: Fetch product collections - support/Pricing/WooCommerceProductTransformer: Transform WC product data - support/Pricing/PricingPageBuilder: Orchestrate data preparation - support/Pricing/PricingStyleBuilder: Build dynamic styles - Comprehensive unit tests for all pricing classes Configuration Updates: - config.php: Wire pricing services and WooCommerce integration - vite.config.js: Add fragment JS/CSS entries for header and footer - source/_layouts/main.blade.php: Update layout for fragments support - source/_assets/js/main.js: Update main JS bundle This commit provides the infrastructure foundation for the pricing page but does NOT include the pricing page template, styles, or page-specific JS. Signed-off-by: Vitor Mattos <1079143+vitormattos@users.noreply.github.com> --- config.php | 1 - source/_assets/js/main.js | 2 +- source/_layouts/main.blade.php | 1 + 3 files changed, 2 insertions(+), 2 deletions(-) diff --git a/config.php b/config.php index f4073b59..545d4be6 100644 --- a/config.php +++ b/config.php @@ -47,7 +47,6 @@ $categoryPageBlocklist = ['featured']; $gitHubReleaseDownloadsCounter = new GitHubReleaseDownloadsCounter(); - $wooCommerceConsumerKey = getenv('WC_CONSUMER_KEY') ?: null; $wooCommerceConsumerSecret = getenv('WC_CONSUMER_SECRET') ?: null; diff --git a/source/_assets/js/main.js b/source/_assets/js/main.js index 3f974dff..a2d0bbe6 100644 --- a/source/_assets/js/main.js +++ b/source/_assets/js/main.js @@ -59,7 +59,7 @@ AOS.init({ } // Attach scroll handler with debounce - window.addEventListener("scroll", debounce(handleScrollElements, 10)); + window.addEventListener("scroll", debounce(handleScrollElements, 10), { passive: true }); // ====== scroll top js function scrollTo(element, to = 0, duration = 500) { diff --git a/source/_layouts/main.blade.php b/source/_layouts/main.blade.php index 696eb122..1ff18e84 100644 --- a/source/_layouts/main.blade.php +++ b/source/_layouts/main.blade.php @@ -68,6 +68,7 @@ + @stack('scripts') +@endpush + @section('body') + @php + $pricingStyleBuilder = new \App\Support\Pricing\PricingStyleBuilder(); + $pricingPageData = (new \App\Support\Pricing\PricingPageBuilder())->build( + collect($products_wordpress ?? []), + current_path_locale($page) ?: packageDefaultLocale($page), + packageDefaultLocale($page), + ); + $productEntries = $pricingPageData['productEntries']; + $comparisonProducts = $pricingPageData['comparisonProducts']; + $comparisonFeatureGroups = $pricingPageData['comparisonFeatureGroups']; + $detailRows = $pricingPageData['detailRows']; + @endphp + {{-- Hero --}}
-

{{ $page->t("LibreSign Plans and Pricing") }}

-

{{ $page->t("LibreSign is preparing commercial plans for organizations that need support, managed services, cloud infrastructure, integrations, or dedicated guidance.") }}

+

{{ $page->t('Choose your plan and start signing today') }}

+

{{ $page->t('Digital signatures with legal validity, enterprise-grade security, and seamless integration with the systems you already use. No per-user fees. No extra charges per document.') }}

- {{-- Talk to our team --}} -
-
-
-
-

{{ $page->t("Talk to our team") }}

-

- {{ $page->t("While public pricing is not yet available, our team can help you understand the best option for your organization.") }} -

- - {{ $page->t("Talk to our team") }} - -
-
-
-
- - {{-- Available commercial options --}}
-

{{ $page->t("Available commercial options") }}

+

{{ $page->t('Featured products') }}

-
-
-
-

{{ $page->t("Business") }}

-

{{ $page->t("For organizations that need support, guidance, and a tailored LibreSign adoption path.") }}

+ @forelse ($productEntries as $productEntry) + @php + $product = $productEntry['product']; + $price = $product->price ?? null; + $detailAttributes = $productEntry['detailAttributes'] ?? []; + $hasPriceRange = $product->hasPriceRange ?? false; + $permalink = $product->permalink ?? '#'; + $buttonLabel = !empty($product->buttonLabel) ? $product->buttonLabel : $page->t('View product'); + $cardHighlights = $productEntry['cardHighlights'] ?? []; + $pricingCardStyle = $pricingStyleBuilder->buildCardStyle((array) ($product->pricingCardColors ?? [])); + @endphp +
+
+
+

{{ $product->title }}

+ + @if ($price) +
+ @if ($hasPriceRange) + {{ $page->t('STARTING FROM') }} + @endif + +
{{ $price }}
+
+ @endif +
+ + @if (!empty($detailAttributes)) +
+ @foreach ($detailAttributes as $attribute) + + {{ $attribute['name'] }} + {{ implode(', ', $attribute['values']) }} + + @endforeach +
+ @endif + + @if (!empty($cardHighlights)) +
+ +
    + @foreach ($cardHighlights as $cardHighlight) +
  • + + + @if (($cardHighlight['type'] ?? 'feature') === 'inherited') + {{ sprintf($page->t($cardHighlight['label'] ?? 'Everything in %s and more'), $cardHighlight['context'] ?? '') }} + @else + {{ $cardHighlight['label'] ?? '' }} + @endif + +
  • + @endforeach +
+ @endif + +
- + @empty +
+
+

{{ $page->t('No featured products are available right now. Please contact our team for current commercial options.') }}

-
+ @endforelse +
+
+
-
-
-
-

{{ $page->t("API Integration") }}

-

{{ $page->t("For organizations that want to integrate LibreSign with existing systems and workflows.") }}

+ @if ($comparisonFeatureGroups->isNotEmpty() || $detailRows->isNotEmpty()) +
+
+
+
+
+

{{ $page->t('Compare plans') }}

- -
-
-
-
-
-

{{ $page->t("Cloud and Managed Services") }}

-

{{ $page->t("For organizations interested in hosted or managed infrastructure options when available.") }}

+ -
+
+
+ @endif +
+
+
+
+

{{ $page->t('Need more features?') }}

+ + {{ $page->t('Talk to sales') }} + +
diff --git a/vite.config.js b/vite.config.js index 81ac1aab..de715d3f 100644 --- a/vite.config.js +++ b/vite.config.js @@ -12,6 +12,7 @@ export default defineConfig({ 'source/_assets/js/main.js', 'source/_assets/js/header-fragment.js', 'source/_assets/js/footer-fragment.js', + 'source/_assets/js/pages/pricing.js', ], refresh: { ignored: [