skills/vendix-frontend-standard-module/SKILL.md
Standard mobile-first admin list module layout for Vendix: stats, sticky search/header, Card wrapper, and ResponsiveDataView. Trigger: When creating or refactoring STORE_ADMIN, SUPER_ADMIN, or other private admin list modules.
npx skillsauth add rzyfront/vendix vendix-frontend-standard-moduleInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
ResponsiveDataViewComponent.app-sticky-header pattern.apps/frontend/src/app/private/modules/store/products/products.component.tsapps/frontend/src/app/private/modules/store/products/components/product-list/product-list.component.htmlapps/frontend/src/app/private/modules/store/orders/components/orders-list/orders-list.component.htmlapps/frontend/src/app/private/modules/store/settings/roles/store-roles-settings.component.tsapps/frontend/src/app/private/modules/store/settings/roles/components/store-roles-list.component.tsProducts is a strong reference for list layout and product cards, but it is not a perfect forms or signals reference. For forms, prefer settings/general and typed subscription pages.
The parent page owns stats and module-level state. The child list component owns search/filter UI and the data view.
<div class="w-full">
<div class="stats-container sticky top-0 z-20 bg-background md:static md:bg-transparent">
<app-stats
title="Products"
[value]="stats().total"
smallText="Products in catalog"
iconName="package"
iconBgColor="bg-blue-100"
iconColor="text-blue-500"
/>
</div>
<app-product-list
[items]="products()"
[loading]="loading()"
(edit)="onEdit($event)"
(delete)="onDelete($event)"
/>
</div>
| Layer | Element | Common Classes |
| --- | --- | --- |
| 1 | Stats | stats-container sticky top-0 z-20 bg-background md:static md:bg-transparent |
| 2 | Search/filter | sticky top-[99px] z-10 bg-background ... md:static md:bg-transparent |
| 3 | Data | px-2 pb-2 pt-3 md:p-4 inside the card |
top-[99px] is common in current standard list modules with sticky stats. It is not universal; adjust only if the actual stats/header height changes.
<app-card [responsive]="true" [padding]="false">
<div
class="sticky top-[99px] z-10 bg-background px-2 py-1.5 -mt-[5px]
md:mt-0 md:static md:bg-transparent md:px-6 md:py-4 md:border-b md:border-border"
>
<div class="flex flex-col gap-2 md:flex-row md:justify-between md:items-center md:gap-4">
<h2 class="text-[13px] font-bold text-gray-600 tracking-wide md:text-lg md:font-semibold md:text-text-primary">
Products ({{ items().length }})
</h2>
<div class="flex items-center gap-2 w-full md:w-auto">
<app-inputsearch
class="flex-1 md:w-64 shadow-[0_2px_8px_rgba(0,0,0,0.07)] md:shadow-none rounded-[10px]"
placeholder="Search..."
(searchChange)="onSearch($event)"
/>
</div>
</div>
</div>
<div class="px-2 pb-2 pt-3 md:p-4">
<app-responsive-data-view
[data]="filteredItems()"
[columns]="columns"
[actions]="actions"
[cardConfig]="cardConfig"
[loading]="loading()"
[sortable]="true"
/>
</div>
</app-card>
<div class="w-full">; parent layouts already provide spacing.app-card [responsive]="true" [padding]="false" around list content when matching current store modules.ResponsiveDataViewComponent for mixed desktop/mobile data lists.input(), output(), signal(), computed(), and inject() for new Angular code.smallText on stats where meaningful; it is recommended and common, but StatsComponent does not require it in code.app-sticky-header InsteadUse app-sticky-header for form/detail pages with save/cancel actions, such as product create/edit and settings pages. List modules usually use sticky stats plus sticky search instead.
vendix-frontend-data-display - Table, ItemList, and ResponsiveDataView configurationvendix-frontend-stats-cards - StatsComponent and .stats-containervendix-frontend-sticky-header - Reusable sticky header for form/detail pagesvendix-zoneless-signals - Angular 20 signals and zoneless rulesdevelopment
Mobile app development rules for Vendix Expo/React Native project. Trigger: When editing, creating, or modifying any file under apps/mobile, or when developing mobile-specific features.
development
Feature gating by store subscription state: global store write guard, AI feature gate, Redis feature resolution, quota consumption, frontend paywall interceptor, banner, and subscription UI states. Trigger: When adding feature gates, paywalls, subscription-based access control, protecting store write operations, AI feature gates, or rollout flags.
testing
SaaS subscription billing for Vendix stores: plan pricing, invoices, Wompi platform payments, manual payments, partner commissions, payouts, proration, and dunning. Trigger: When creating SaaS invoices, working with partner rev-share, margin/surcharge pricing, invoice sequence allocation, partner payout batches, subscription payments, manual payments, or dunning flows.
development
Periodic quota counters with Redis, UTC period keys, Lua-based idempotent AI quota consumption, request-id deduplication, and post-success consumption. Trigger: When building quota counters, enforcing monthly/daily feature caps, or reusing AI quota patterns for uploads, emails, exports, or rate-limited features.