Install
This is the repository archive. It installs, but the folder name will carry the branch suffix and updates will not flow.
Install straight from GitHub with WP-CLI:
wp plugin install https://github.com/keyvansolha/ts-charge-guide/archive/refs/heads/main.zipراهنمای انتخاب پاوربانک و شارژر و مراقبت از باتری، برای قالب amazing روی ووکامرس.
Version: 0.7.4 · Requires PHP 8.0 · Requires WooCommerce · Author: Parsa Dana, Keyvan Havestin
در یک نگاه
| موضوع | مقدار |
|---|---|
| شورتکد | [ts_charge_guide] |
| صفحه راهنما | از تنظیمات: ابزارها › راهنمای شارژ (یک برگه را جایگزین میکند) |
| مسیر REST | POST /wp-json/ts-charge/v1/recommend |
| گزینه دیتابیس | ts_charge_guide_settings |
| فایلهای دارایی | assets/style.css, assets/token-bridge.css, assets/js/*.js, assets/images/* |
| تستها | php tests/unit/run.php · php tests/unit/bootstrap.php · node tests/js/run.js (پیشنیاز: php tests/js/make-fixture.php) |
چرا افزونه است، نه قالب
این راهنما یک سطح مستقل و قابل خاموشکردن است: تنظیمات دارد، محصولات ووکامرس را میخواند، به
مخاطب عمومی سرویس میدهد و باید بدون تغییر قالب بتواند فعال یا غیرفعال شود. بنابراین کد در
wp-content/plugins/ts-charge-guide/ مینشیند و از قالب فقط توکنهای ظاهری را قرض میگیرد.
غیرفعالکردن افزونه قالب را دستنخورده رها میکند: نه هوکی جا میماند، نه CSS/JS اضافهای بار میشود.
نصب و راهاندازی
- افزونه را فعال کن (پوشه
ts-charge-guideدرwp-content/plugins/). - ابزارها › راهنمای شارژ را باز کن.
- صفحه راهنما را انتخاب کن؛ محتوای آن برگه با راهنما جایگزین میشود و سرصفحه/پاصفحه قالب
باقی میماند. جای دیگر هم میتوانی شورتکد
[ts_charge_guide]را در یک برگه بگذاری. - دستهبندی پاوربانک و دستهبندی شارژر را از درخت دستههای خود فروشگاه انتخاب کن و تعداد کارت هر دسته (۱ تا ۱۲) را تعیین کن.
- نوشتههای مجله را با شناسه (ID) بنویس — همان نوشتههایی که زیر بخش باتری بهشکل کارت مجله نمایش داده میشوند (کاما یا خط تازه، حداکثر ۶ مورد، به همان ترتیب). خانهاش خالی بماند، بخش مجله رندر نمیشود؛ شناسهای که پیدا نشود در «بررسی لحظهای» علامت میخورد و در صفحه نمایش داده نمیشود.
- اگر صفحهای که راهنما روی آن است کش میشود (WP Rocket)، پس از ذخیره، کش برگه را پاک کن.
تا وقتی هیچ دستهبندی انتخاب نشده باشد، بخش «آشنایی با چند انتخاب» رندر نمیشود؛ نه لیست پیشفرضی، نه محصول حدسی. پیام هشدار همین را در صفحه تنظیمات نشان میدهد.
داده فروشگاه از کجاست
هیچ نام، شناسه، تصویر، لینک یا قیمتی در کد نوشته نشده است:
- نگاشت «پاوربانک» و «شارژر» به دستههای واقعی فروشگاه از تنظیمات خوانده میشود
(
Settings::category_terms()). - کارت هر محصول از ووکامرس زنده خوانده میشود
(نام، پیوند یکتا، تصویر شاخص، قیمت نمایشی، موجودی، برند در صورت وجود تاکسونومی
product_brand) —CatalogAdapter. - فقط محصولات موجود: کوئری با
stock_status = instockاجرا میشود و هر ردیفی که خودِ ووکامرس «ناموجود» بداند در لایه آداپتر هم کنار گذاشته میشود. پس نه کش کهنه و نه تغییر موجودی در میانه درخواست نمیتواند کارت ناموجودی روی صفحه بیاورد.Recommendation::build()هم هر ردیف ناموجودی را که مستقیم به آن داده شود حذف میکند، بنابراین پیشنهاد نتیجه هم فقط از موجودها ساخته میشود. «پیشخرید» (onbackorder) هم مثل ناموجود کنار گذاشته میشود؛ معیار دقیقاً همان چیزی است که ووکامرسinstockمیداند. تعداد پنهانشدهها در «بررسی زنده» صفحه تنظیمات گزارش میشود تا این قاعده بیصدا چیزی را از دید خارج نکند. - نتیجه پرسشوپاسخ هم از همان کاتالوگ انتخاب میشود، نه از فهرست ثابت
(
Recommendation::build()). - کارتها مال قالباند. افزونه کارت محصول و کارت مطلب نمیسازد:
GuideViewهمان partialهای قالب را رندر میکند (THEME_COMPONENTS/product-cards/simple-card(-mobile).phpبا معیارIS_MOBILE، وTHEME_LIB_DIR . 'Blog/template/cards/blog-card.php'برای نوشتههای مجله) و استایل کارت را با هندلamazing-product-cardاز قالب میگیرد. اگر آن هندل ثبت نشده باشد (قالب دیگری فعال است)، کارتها بدون استایل میمانند — یعنی نصب این نسخه بههمراه تغییر قالب (assets/scss/product-card.scss+ ثبت هندلها) معنا دارد. - بخش مجله با شناسه، نه با نام. کدام نوشتهها زیر بخش باتری بیایند را مالک سایت در تنظیمات
مینویسد (
blog_ids، حداکثر ۶ و به همان ترتیب). هیچ مسیر، عنوان یا تصویر مقالهای در کد نیست؛ شناسهای که به نوشتهٔ منتشرشده نرسد، هم در صفحه نمایش داده نمیشود و هم در «بررسی لحظهای» علامت میخورد. با فهرست خالی، کل بخش (تیتر و کارتها) رندر نمیشود.
اثبات خالیبودن: با تنظیمات خالی، CatalogAdapter::products() آرایه خالی برمیگرداند و حتی یک
کوئری هم اجرا نمیشود (tests/unit/run.php → «with no category assigned the catalog returns nothing»).
مقیاس، کش و امنیت
- محدودسازی: هر دسته حداکثر
cards_per_kindمحصول میخواند؛ کل صفحه حداکثر ۲×۱۲ کارت. یک کوئری کوچک دیگر هم فقط «چند محصول ناموجود پنهان شد» را میشمارد (خروجیاش شناسه است، نه آبجکت محصول) و مثل بقیه در همان ترنزینت کش میشود، پس در هر ۱۵ دقیقه یک بار اجرا میشود. - کش: هر دسته در یک ترنزینت
ts_charge_guide_catalog_*با عمر ۱۵ دقیقه نگه داشته میشود؛ یک بار شکست، ۶۰ ثانیه در کش منفی میماند تا رندر بعدی کوئری را تکرار نکند. فهرست کلیدها در گزینهts_charge_guide_cache_indexاست و دکمه «پاک کردن کش محصولات راهنما» آنها را پاک میکند. - مسیر عمومی:
POST ts-charge/v1/recommendفقط سه فیلدneed/device/priorityرا میپذیرد، هر مقدار را با enum همان رابط میسنجد، بدنه بیش از ۲۰۴۸ بایت را رد میکند،no-storeبرمیگرداند و هرگز نمیگوید یک محصول «سازگار» است (certifies: false). - خروجی امن: در PHP هر مقدار برای بستر خودش escape میشود؛ در JS هیچ متن دریافتی با
innerHTMLنوشته نمیشود جزpriceواکامرس، آن هم از فیلترsafeMarkup. - بدون فونت و پالت اختصاصی: فایل فونتی همراه افزونه نیست؛ خانواده فونت قالب نام برده میشود و
رنگها از طریق
--cg-*درtoken-bridge.cssبه توکنهای قالب وصل میشوند.
قرارداد REST
POST /wp-json/ts-charge/v1/recommend
{ "need": "powerbank|charger|both", "device": "<کلید دستگاه>", "priority": "<کلید اولویت>" }
200 → { need, device, priority, heading, lead, checklist[], warning, products[], certifies: false }
products[] = { id, name, url, image, priceHtml, inStock, brand }
400 → { message: "invalid_answers" | "invalid_request" }
503 → { message: "unavailable" }
اولویت reuse («اول وسایل فعلیام را بررسی کنم») عمداً products: [] برمیگرداند: در آن مسیر
راهنما خرید پیشنهاد نمیکند.
فیلترها
| فیلتر | کار |
|---|---|
ts_charge_guide_catalog_args |
(اختیاری، در CatalogAdapter) آرگومانهای کوئری ووکامرس را پیش از اجرا تغییر میدهد. |
تستها
php tests/unit/bootstrap.php # قرارداد سرآیند افزونه (نام، نسخه، نویسنده، Text Domain)
php tests/unit/run.php # ۱۱۳ بررسی: تنظیمات، کاتالوگ، پیشنهاد، ویو، REST، نظم منابع
php tests/js/make-fixture.php # ساخت فیچر از ویو واقعی
node tests/js/run.js # ۳۸ بررسی JS روی jsdom
php tests/browser/preview.php # صفحه پیشنمایش برای اندازهگیری در مرورگر
سنجش چیدمان با کروم واقعی (عرض ۱۲۸۰/۷۶۸/۳۹۰، حالت روشن و تیره): هیچ عنصری از عرض دید عبور
نمیکند، شبکه محصولات ۳/۲/۲ ستونه است، در هر لحظه یک پنل مراقبت باتری و یک پنل عیبیابی
دیده میشود و صفحه تنها یک h1 دارد. ظاهر با صفحه زنده راهنما
(https://www.tehroonspeaker.ir/انتخاب-پاوربانک/) جزءبهجزء مقایسه شده است؛ روش کار و اختلافهای
باقیمانده در docs/reports/2026-10-07-charge-guide-audit.md آمده است.
نقشه فایلها
ts-charge-guide.php سرآیند، ثابتها، autoloader، راهاندازی روی plugins_loaded
uninstall.php پاککردن فقط گزینه و ترنزینتهای خودِ افزونه
includes/src/
App.php ساخت سرویسها و ثبت هوکها
Settings.php گزینه، پیشفرضها، sanitize، Settings API
Content.php همه متنهای راهنما (کپی رابط، نه داده فروشگاه)
CatalogAdapter.php خواندن زنده محصولات دو دسته + کش + محدودسازی
Recommendation.php نگاشت پاسخها به نتیجه (کلاس خالص)
GuideView.php رندر کامل راهنما با escape در هر sink
LandingPage.php template_include + شورتکد + تشخیص درخواست راهنما
Assets.php بارگذاری مشروط CSS و ماژولهای JS
AdminScreens.php صفحه تنظیمات + بررسی لحظهای کاتالوگ + پاککردن کش
Rest/Controller.php لایه مشترک REST (بدنه محدود، no-store، خطای کنترلشده)
Rest/RecommendController.php مسیر recommend
templates/page.php برگه راهنما با سرصفحه/پاصفحه قالب
assets/token-bridge.css اتصال --cg-* به توکنهای قالب
assets/style.css ظاهر راهنما (فقط با توکنها)
assets/js/{entry,rest,dom,wizard,panels}.js ماژولهای ES با Script Modules API
assets/images/ تصویرهای راهنما
tests/unit, tests/js, tests/browser تستها و پیشنمایش
docs/reports/ گزارشها، از جمله بازبینی نسخه ۰.۳.۰
انتشار
افزونه پوشه مستقل و مخزن خودش است (origin git@github.com:keyvansolha/ts-charge-guide.git).
پس از هر تغییر رفتار، شماره نسخه فقط در سرآیند ts-charge-guide.php بالا میرود؛ ثابت
TS_CHARGE_GUIDE_VERSION همان مقدار را میخواند و همه داراییها با همان نسخه بار میشوند. کش برگه
را بعد از انتشار (و هر تغییر محتوایی) پاک کن.