63- آموزش جاوااسکریپت | پروژه عملی : قسمت 4 از 5 : مدیریت پاکسازی پروفایل و نمایش هشدار در جستوجوی کاربران GitHub
در این بخش، پاکسازی پروفایل هنگام خالی شدن فیلد جستوجو و نمایش هشدار برای کاربر نامعتبر را با JavaScript پیادهسازی میکنیم. همچنین از ایجاد هشدارهای تکراری جلوگیری میکنیم و پیام خطا را بعد از ۳ ثانیه بهصورت خودکار حذف میکنیم.
مدیریت پاکسازی پروفایل و نمایش پیامهای خطا در کلاس UI
تا این مرحله، امکان جستوجوی کاربران GitHub پیادهسازی شده و با تایپ نام کاربری، اطلاعات پروفایل در صفحه رندر میشود. با این حال، هنوز دو سناریوی مهم در تجربه کاربری (UX) باقی مانده است:
- در صورت پاک شدن متن جستوجو توسط کاربر، اطلاعات پروفایل قبلی باید از صفحه پاک شود.
- در صورتی که کاربری با نام واردشده پیدا نشود، باید یک پیام هشدار (Alert) مناسب به کاربر نشان داده شود.
در این بخش، این دو قابلیت را قدمبهقدم پیادهسازی و مدیریت میکنیم.
قدم اول: پاکسازی پروفایل هنگام خالی شدن فیلد جستوجو
اگر کاربر ورودی جستوجو را بهطور کامل پاک کند، در حال حاضر اطلاعات پروفایل قبلی در صفحه باقی میماند. برای رفع این مشکل، رفتار خالی شدن ورودی را مدیریت میکنیم.
۱. فراخوانی متد در فایل app.js
در فایل app.js، در قسمتی از شرط که ورودی فیلد خالی است، متد clearProfile را از نمونهٔ کلاس UI فراخوانی میکنیم:
// Clear profile
ui.clearProfile();
۲. پیادهسازی متد clearProfile در فایل ui.js
حال فایل ui.js را باز کرده و در انتهای کلاس UI این متد را اضافه میکنیم. تنها کاری که باید انجام دهیم، خالی کردن innerHTML عنصر پروفایل است:
// Clear profile in UI
clearProfile() {
this.profile.innerHTML = '';
}
نکته UX: گاهی اوقات تنها یک خط کد ساده میتواند تجربه کاربری و رفتار رابط کاربری را به شکل قابل توجهی بهبود دهد.
قدم دوم: نمایش پیام هشدار (Alert) برای کاربر ناموجود
اگر نام کاربری تایپشده در GitHub وجود نداشته باشد، باید یک باکس هشدار مناسب نمایش داده شود.
۱. فراخوانی showAlert در app.js
در فایل app.js، در بخشی که پاسخ API نشاندهنده پیدا نشدن کاربر است، متد showAlert را صدا میزنیم. این متد دو آرگومان دریافت میکند:
- متن پیام (
User not found) - کلاسهای استایلدهی (کلاسهای آماده Bootstrap یعنی
alert alert-danger)
// Show alert
ui.showAlert('User not found', 'alert alert-danger');
۲. پیادهسازی ساختار اولیه showAlert در ui.js
در فایل ui.js (زیر متد showProfile) متد showAlert را ایجاد میکنیم. این متد با استفاده از DOM Manipulation خالص یک عنصر div میسازد و آن را در مکان مناسب صفحه قرار میدهد:
// Show alert message
showAlert(message, className) {
// ۱. ساخت عنصر div
const div = document.createElement('div');
// ۲. انتساب کلاسها به عنصر ساختهشده
div.className = className;
// ۳. اضافه کردن متن پیام با ساخت Text Node
div.appendChild(document.createTextNode(message));
// ۴. انتخاب والد و عنصر مرجع برای تعیین محل درج هشدار
const container = document.querySelector('.searchContainer');
const search = document.querySelector('.search');
// ۵. درج هشدار قبل از باکس جستوجو
container.insertBefore(div, search);
}
چرا انتخاب والد با .searchContainer انجام شد؟
اگر ساختار HTML صفحه را بررسی کنید، ممکن است بیش از یک عنصر با کلاس container وجود داشته باشد (برای مثال یک کانتینر کلی و یک کانتینر مخصوص جستوجو). در صورتی که فقط از querySelector('.container') استفاده شود، جاوااسکریپت اولین کانتینر را انتخاب میکند و هشدار در محل نادرستی رندر خواهد شد. بنابراین از کلاس مشخصتر .searchContainer استفاده میکنیم.
متد insertBefore نیز عنصر پیام (div) را دقیقاً قبل از فرم جستوجو (search) در داخل والد (container) قرار میدهد.
قدم سوم: رفع باگ تکثیر هشدارهای تکراری (Stacking Alerts)
اگر کد بالا را با تایپ کاراکترهای نامعتبر تست کنیم، با هر بار زدن کلید، یک هشدار جدید به صفحه اضافه شده و هشدارها پشت سر هم روی صفحه تکرار میشوند:
[ User not found ]
[ User not found ]
[ User not found ]
ما فقط به یک هشدار نیاز داریم؛ بنابراین قبل از نمایش هر پیام جدید، باید پیامهای قبلی را پاکسازی کنیم.
۱. ساخت متد clearAlert در ui.js
در انتهای فایل ui.js، یک متد کمکی برای حذف هشدار جاری اضافه میکنیم:
// Clear alert message
clearAlert() {
const currentAlert = document.querySelector('.alert');
if (currentAlert) {
currentAlert.remove();
}
}
نکته: شرط
if (currentAlert)الزامی است؛ زیرا در بار اول که هشداری در صفحه نیست، مقدارnullخواهد بود و فراخوانی مستقیم.remove()باعث بروز خطا در برنامه میشود.
۲. فراخوانی clearAlert در ابتدای showAlert
اکنون در خط اول متد showAlert، متد پاکسازی را صدا میزنیم:
showAlert(message, className) {
// حذف هشدارهای قبلی در صورت وجود
this.clearAlert();
const div = document.createElement('div');
div.className = className;
div.appendChild(document.createTextNode(message));
const container = document.querySelector('.searchContainer');
const search = document.querySelector('.search');
container.insertBefore(div, search);
}
قدم چهارم: حذف خودکار هشدار بعد از ۳ ثانیه
پیام هشدار نباید برای همیشه در صفحه باقی بماند و باید پس از مدتی ناپدید شود. برای این منظور، از تابع setTimeout استفاده میکنیم و زمان آن را روی ۳۰۰۰ میلیثانیه (۳ ثانیه) تنظیم میکنیم.
کد متد showAlert بهصورت نهایی به شکل زیر درمیآید:
showAlert(message, className) {
// حذف هشدار قبلی
this.clearAlert();
// ساخت و درج هشدار جدید
const div = document.createElement('div');
div.className = className;
div.appendChild(document.createTextNode(message));
const container = document.querySelector('.searchContainer');
const search = document.querySelector('.search');
container.insertBefore(div, search);
// حذف خودکار پس از ۳ ثانیه
setTimeout(() => {
this.clearAlert();
}, 3000);
}
نکته فنی: استفاده از Arrow Function در
setTimeoutباعث میشود مقدارthisحفظ شده و به همان نمونه کلاسUIاشاره کند تا دسترسی بهthis.clearAlert()بدون مشکل انجام گیرد.
جمعبندی ساختار کلاس UI تا این مرحله
فایل ui.js در پایان این مراحل به صورت زیر سازماندهی شده است:
class UI {
constructor() {
this.profile = document.getElementById('profile');
}
// Show user profile in UI
showProfile(user) {
this.profile.innerHTML = `
<!-- markup مربوط به نمایش اطلاعات کاربر -->
`;
}
// Show alert message
showAlert(message, className) {
this.clearAlert();
const div = document.createElement('div');
div.className = className;
div.appendChild(document.createTextNode(message));
const container = document.querySelector('.searchContainer');
const search = document.querySelector('.search');
container.insertBefore(div, search);
// Timeout after 3 sec
setTimeout(() => {
this.clearAlert();
}, 3000);
}
// Clear alert message
clearAlert() {
const currentAlert = document.querySelector('.alert');
if (currentAlert) {
currentAlert.remove();
}
}
// Clear profile in UI
clearProfile() {
this.profile.innerHTML = '';
}
}
گام بعدی
در حال حاضر اطلاعات پایهٔ کاربر مدیریت شده است، اما لیست مخازن (Repositories) هنوز نمایش داده نمیشود. اطلاعات Repos در Endpoint اصلی کاربر قرار ندارد و باید از آدرس اختصاصی مخازن (/users/:username/repos) دریافت شود. در بخش بعدی، درخواست و نمایش مخازن کاربر را پیادهسازی خواهیم کرد.