کارت جستجوی ذخیرهشده (SavedQueryCard)
نمایش یک query ذخیرهشده — نام، توضیح، فیلترهای فعال، تعداد اجرا، آخرین اجرا، Run + Favorite
معرفی
SavedQueryCard نمایش یک filter preset / query ذخیرهشده است — کاربر روی Run کلیک میکند و نتایج با همان فیلترهای ذخیرهشده دوباره اجرا میشود. مناسب صفحهی My Saved Searches در پنل افکارسنجی + sidebarهای جستجوی ذخیرهشده.
چه زمانی استفاده کنیم:
- صفحهی جستجوهای ذخیرهی من — grid چندتایی
- panel سمتراست داشبورد — لیست quick-runها
- مرور هیستوری گزارشسازی که هر گزارش از یک query تولید شد
چه زمانی استفاده نکنیم:
- ایجاد یک query جدید با فیلترهای زنده → از
FilterPanel+useFilterPresets(این کارت نمایش است، آن hook ذخیره/بازخوانی است) - نتایج خود query (لیست پست/concept/etc.) → از
DataTable، یا برای پستهاEntityCollectionباentity="post" - جستجوی fuzzy لحظهای → از
SearchInputیاCommandPalette
گزارش هفتگی — منتقدان سازنده
نظرات منتقد سازنده در شبکههای اجتماعی، 7 روز اخیر
زمین بازی
گزارش هفتگی — منتقدان سازنده
نظرات منتقد سازنده در شبکههای اجتماعی، 7 روز اخیر
استفاده
import { SavedQueryCard } from '@partodata/ui'
const [starred, setStarred] = React.useState(false)
<SavedQueryCard
name="گزارش هفتگی — منتقدان سازنده"
description="نظرات منتقد سازنده در شبکههای اجتماعی، 7 روز اخیر"
filters={[
{ label: 'گرایش', value: 'منتقد سازنده' },
{ label: 'پلتفرم', value: 'تلگرام، توییتر' },
{ label: 'بازه', value: '7 روز' },
]}
runCount={48}
lastRun="2 روز پیش"
onRun={() => execute(query)}
favorite={{ starred, onChange: setStarred }}
/>ترکیب با useFilterPresets:
import { useFilterPresets, FilterProvider } from '@partodata/ui'
import { formatJalaliDate } from '@partodata/ui/server'
function SavedSearches() {
const presets = useFilterPresets({ storageKey: 'comments-app:filters' })
return presets.presets.map((p) => (
<SavedQueryCard
key={p.id}
name={p.name}
lastRun={formatJalaliDate(new Date(p.updatedAt), 'd MMMM yyyy')}
onRun={() => presets.load(p.id)}
/>
))
}نکنید
toLocaleDateString('fa') را برای نمایش تاریخ به کار نبرید — کدپوینت واقعی فارسی تولید میکند که کپی/پیست، Ctrl+F و
صفحهخوان را میشکند. عدد فارسی باید فقط از طریق فونت (ss01) رندر شود؛ formatJalaliDate رقم لاتین برمیگرداند و
فونت آن را فارسی نمایش میدهد.
راهنمای استفاده
بکنید
filtersرا به 3-5 chip محدود کنید — اگر بیش از 5 فیلتر فعال است، نشان «+3 فیلتر دیگر» درdescriptionبنویسید -lastRunرا بهصورت نسبی پاس بدهید (2 روز پیش،همین الان) — کاربر سریعتر decay میفهمد - برای فیلترهای پر-استفادهfavorite={{ starred: true, ... }}بگذارید تا کاربر mark کند
نکنید
onRunرا همگام نگذارید روی DB heavy — همیشه async/queue بسازید چون کاربر روی Run کلیک میکند و انتظار feedback سریع دارد - این کارت برای rule هشدار نیست — برای آنAlertRuleCardبسازید
جدول ویژگیها
دسترسیپذیری
- دکمه favorite (ستاره)
aria-labelپویا دارد (star/unstar) به همراهaria-pressed={starred}تا screen reader وضعیت toggle را اعلام کند. - آیکون Search و Clock و Play همگی
aria-hidden="true"هستند — معنا از طریق label و متن کنار آنها منتقل میشود. - دکمهی Run یک
<button>استاندارد با focus ring است؛ کلید Enter/Space آن را فعال میکند. - ترتیب tab منطقی است: متن کارت → favorite → Run، تا کاربر کیبورد بدون trap بهسرعت به action برسد.
lastRunبهصورت متن نسبی (مثل «2 روز پیش») رندر میشود — اگر دقت ثانیه نیاز است،titleبا ISO time به consumer اضافه شود.- وقتی
isRunningست است، ریشهی کارتaria-busy="true"میگیرد تا صفحهخوان بداند یک عملیات در حال اجراست، و دکمهی Run باdisabledواقعی از فعالسازی دوباره جلوگیری میکند — نه فقط ظاهری.
کامپوننتهای مرتبط
- ذخیره و بازخوانی state preset →
useFilterPresetshook - alert ذخیرهشده بهجای جستجو →
AlertRuleCard - اجرای فیلتر زنده →
FilterPanel+FilterProvider - نتایج همان query →
DataTable، یا برای پستهاEntityCollectionباentity="post"