گزارش پروژه طراحی وبسایت برای پیشبینی خطای نرمافزار با استفاده از یادگیری ماشین
در این پروژه، هدف اصلی طراحی یک وبسایت پیشبینی خطای نرمافزار با استفاده از یادگیری ماشین بوده است. کاربران این سیستم قادر هستند تا وارد سایت شوند، پروژههای خود را مشاهده کنند، دیتاستهای خود را با فرمت CSV بارگذاری کرده و مدلهای پیشبینی مختلف را برای دیتاستهای خود آموزش دهند. سپس میتوانند از این مدلها برای پیشبینی خطا در دادههای مختلف استفاده کنند. این گزارش به شرح معماری سیستم، انتخاب تکنولوژیها و ابزارهای مختلف استفادهشده، پرداخته و بهویژه به تطبیق آنها با نیازهای پروژه و مقالات علمی موجود اشاره میکند.
الگوهای طراحی
در این پروژه، از چندین الگوی طراحی نرمافزاری به منظور بهبود ساختار، مقیاسپذیری و نگهداری آسان استفاده شده است. اولین الگوی مورد استفاده، الگوی MVC (Model-View-Controller) است که بخشهای مختلف پروژه را به سه قسمت مدل (مدیریت دیتابیس و منطق پردازش دادهها)، نما (واسط کاربری با استفاده از فلاتر) و کنترلر (مدیریت تعاملات بین نما و مدل از طریق API) تقسیم میکند. این الگو باعث جداسازی نگرانیها و سادهتر شدن توسعه و نگهداری میشود. همچنین، با پیادهسازی معماری API برای ارتباط میان بکاند و فرانتاند، پروژه قابلیت مقیاسپذیری بیشتری پیدا کرده و هر بخش میتواند به صورت مستقل توسعه یابد.
علاوه بر این، الگوی جداسازی وظایف (Separation of Concerns) در طراحی به کار رفته است که باعث میشود هر قسمت از پروژه، مانند فرانتاند، بکاند و بخش پیشبینی، به طور جداگانه کار کند و باعث تسهیل در نگهداری و توسعه آنها در آینده میشود. این الگوها در کنار یکدیگر، به پروژه ساختاری منظم، قابل توسعه و مقیاسپذیر میدهند. همچنین از الگوی Migration نیز بهره برده شده است. با استفاده از Migration، تغییرات در ساختار دیتابیس به راحتی پیادهسازی و پیگیری میشود، بدون اینکه دادهها یا اطلاعات موجود در سیستم آسیب ببینند. این روش باعث میشود که تیم توسعه بتواند به راحتی تغییرات مورد نیاز را به صورت خودکار و بدون نیاز به مداخلات دستی اعمال کند، که در نهایت منجر به بهبود روند نگهداری و توسعه پایگاه داده و کدهای پروژه میشود.
بخش فرانتاند با فلاتر و بخش بکاند با Go و پایتون بهطور مستقل پیادهسازی شدهاند و از الگوی معماری سرویسهای وب و Microservices برای ارتباط میان این بخشها استفاده شده است. همچنین، ابزارهای کمکی در پوشه util قرار دارند که از الگوی طراحی Utility پیروی میکنند.
معماری و تکنولوژیهای استفادهشده
معماری میکروسرویسها
در این پروژه از معماری میکروسرویسها استفاده شده است که سیستم را به دو بخش اصلی تقسیم میکند: API سرور با زبان Go و پیشبینی با پایتون. این دو سرور بهصورت مستقل روی دو پورت جداگانه اجرا میشوند و با هم از طریق HTTP تعامل دارند. استفاده از این معماری به این معنی است که هر بخش میتواند بهطور مستقل توسعه یافته، آزمایش شده و مقیاسپذیر شود. این انتخاب بهویژه برای پروژههایی که نیاز به پردازش سنگین داده و مدلهای یادگیری ماشین دارند، انتخابی مناسب است. در این معماری، دیتابیس PostgreSQL برای ذخیرهسازی دادهها و ارتباطات استفاده میشود. اگرچه MySQL نیز میتوانست گزینه مناسبی باشد، اما PostgreSQL به دلیل پشتیبانی بهتر از دادههای پیچیدهتر و بهینهسازیهای پیشرفتهتری که دارد، برای پروژههایی که نیاز به دقت بالا دارند، انتخاب بهتری است.
زبانها و ابزارها
برای Backend زبان Go به دلیل سرعت بالای پردازش و پشتیبانی از همزمانی، برای توسعه API سرور انتخاب شد. این زبان با استفاده از کتابخانههایی مانند Gin برای ساخت API سریع و مقیاسپذیر بهکار گرفته شده است. همچنین، از pgx برای ارتباط با دیتابیس PostgreSQL استفاده شد. این کتابخانه به دلیل پشتیبانی از کانکشن پولها (Connection Pools) و کارایی بالا برای ارتباط با دیتابیس، گزینه مناسبی است. برای امنیت، از bcrypt برای هش کردن پسوردها بهره برده شده. این انتخابها بهویژه در پروژههای مقیاسپذیر اهمیت زیادی دارند.
برای یادگیری ماشین بهعنوان بخشی از سیستم پیشبینی، از Python استفاده شده است. کتابخانه Scikit-learn برای مدلسازی و پیشبینی خطای نرمافزار بهکار گرفته شدهاست. پایتون بهطور گستردهای برای تحقیقات و توسعه مدلهای ML استفاده میشود. اگرچه میتوان از زبانهایی مانند R یا Julia استفاده کرد که بهویژه در زمینههای خاصی مانند محاسبات علمی و دادهکاوی مناسب هستند، اما پایتون به دلیل اکوسیستم گستردهای که در اختیار دارد و وجود ابزارهای قدرتمند برای آموزش مدلها و پیشبینیها، انتخاب بهتری است.
Docker و محیطهای کانتینری
برای مدیریت محیطهای اجرایی و ایزوله کردن سرویسها از Docker استفاده شده است. Docker به ما این امکان را میدهد که محیطهای یکسان برای توسعه، تست و تولید ایجاد کنیم و بهاینترتیب فرآیند توسعه برای تیمها تسهیل میشود. برای مقیاسپذیری بهتر و مدیریت کانتینرها، میتوان از Kubernetes استفاده کرد، اما در مقیاسهای کوچک یا متوسط، Docker گزینهای عالی است.
Frontend با Flutter
برای توسعه رابط کاربری وبسایت، از Flutter استفاده شده است. این انتخاب به دلیل توانایی Flutter در توسعه سریع و مقیاسپذیر برای اپلیکیشنهای موبایل و وب انجام شده است. Flutter این امکان را فراهم میآورد که یک کد پایه برای پلتفرمهای مختلف توسعه داده شود و همزمان به کاربران تجربهای یکسان در تمامی پلتفرمها ارائه دهد. برای ارتباط با API سرور از HTTP و Dio در فلاتر استفاده شده است. Dio کتابخانهای قدرتمند و انعطافپذیر است که امکاناتی همچون مدیریت درخواستها و پاسخها، تنظیم تایماوت، ارسال درخواستهای چند بخشی و پشتیبانی از interceptors برای دستکاری درخواستها و پاسخها را فراهم میکند.
تستها و کیفیت کد
در این پروژه، تستهای واحد برای اجزای مختلف سیستم نوشته شده است. برای تستهای واحد در سرور Go از کتابخانه Testify استفاده شده است. این کتابخانه بهویژه برای نوشتن تستهای واحد ساده و مؤثر در Go بسیار مفید است. همچنین، پوشش کدها در این پروژه به 80 درصد رسیده است که نشاندهنده کیفیت بالای کد و اطمینان از عملکرد صحیح سیستم است.
CI/CD با GitHub Actions
برای پیادهسازی CI/CD از GitHub Actions استفاده شده است. این ابزار بهطور خودکار کد را برای تست، ساخت و استقرار در محیطهای مختلف اجرا میکند. استفاده از این ابزار، زمان توسعه را کاهش میدهد و به کاهش اشتباهات انسانی کمک میکند.
چالشها و راهحلها
یکی از چالشهای اصلی این پروژه، تعامل بین دو سرور Go و Python بود. این دو سرور باید بهطور مستقل از یکدیگر کار کنند، در حالی که باید دادهها و مدلهای یادگیری ماشین را بهطور یکپارچه با هم هماهنگ کنند. برای حل این مشکل، از پروتکلهای HTTP و فرمتهای JSON برای تبادل دادهها استفاده شد.
بررسی مقالات و روشهای معماری مورد استفاده
در راستای انتخاب معماری و تکنولوژیها برای این پروژه، مقالات زیر مورد بررسی قرار گرفته و به نحوه انتخابها و طراحی سیستم کمک کردند:
مقاله 1: "Software Architecture for ML-based Systems: What Exists and What Lies Ahead"
این مقاله به بررسی چالشها و بهترین شیوههای معماری نرمافزار برای سیستمهای مبتنی بر یادگیری ماشین میپردازد. طبق این مقاله، سیستمهای مبتنی بر یادگیری ماشین باید بهطور مؤثر بین زیرسیستم نرمافزاری و زیرسیستم یادگیری ماشین تفکیک شوند. این تفکیک به ما این امکان را داد که Backend و Python API را بهطور مستقل توسعه دهیم و ارتباط میان آنها را از طریق HTTP برقرار کنیم.
مقاله 2: "Engineering AI Systems: A Research Agenda"
این مقاله به بررسی 18 چالش کلیدی در زمینه معماری نرمافزار برای سیستمهای مبتنی بر یادگیری ماشین (ML) میپردازد. این چالشها شامل مسائلی مانند درک ناکافی پروژهها در زمان طراحی، مشکلات مربوط به آمادهسازی دادهها و ارزیابی کیفیت آنها، دشواریهای طراحی اجزای مربوط به یادگیری ماشین و چالشهای آزمون مدلها هستند. برای هر یک از این چالشها، راهحلهای متعددی ارائه شده که میتوانند به بهبود معماری سیستمهای نرمافزاری با اجزای ML کمک کنند. در این پروژه، تلاش شد تا این چالشها و راهحلهای مطرحشده با دقت مورد توجه قرار گیرد و در طراحی و پیادهسازی سیستم از آنها بهرهبرداری شود.
مقاله 3: "Software Engineering for Machine Learning: A Case Study"
در این مقاله به اهمیت تستهای واحد و CI/CD در توسعه سیستمهای مبتنی بر یادگیری ماشین اشاره شده است. در پروژه ما، برای اطمینان از کیفیت و عملکرد صحیح سیستم، تستهای واحد برای اجزای مختلف سیستم نوشته شدند. همچنین، استفاده از GitHub Actions بهعنوان یک ابزار CI/CD برای اطمینان از صحت کدها و استقرار آنها در محیطهای مختلف بسیار مفید بود.
جمع بندی
این پروژه با هدف طراحی و پیادهسازی یک وبسایت پیشبینی خطای نرمافزار با استفاده از یادگیری ماشین انجام شد. انتخاب معماری میکروسرویسها، زبان Go برای توسعه API، استفاده از پایتون برای یادگیری ماشین، و پیادهسازی CI/CD با GitHub Actions، همگی انتخابهایی بودهاند که عملکرد بالای سیستم و تسهیل فرآیند توسعه را تضمین کردهاند. این پروژه نشان میدهد که چگونه میتوان از ابزارهای مختلف برای پیادهسازی یک سیستم مقیاسپذیر و مؤثر استفاده کرد.
این مطلب، بخشی از تمرینهای درس معماری نرمافزار در دانشگاه شهیدبهشتی است.