Proqram təminatı inkişaf etdirən komandaların ən böyük tələlərindən biri — həddindən artıq mühəndislikdir (overengineering). Və bu tələ ən təhlükəli formasında səliqəsiz görünmür. Əksinə, o, məsuliyyətli mühəndislik kimi təqdim olunur: təmiz interfeyslər, təkrar istifadə olunan komponentlər, konfiqurasiya imkanları, genişləndirmə nöqtələri... Gələcəyə hazır olduğunu göstərən bir arxitektura.
Yalnız növbəti xüsusiyyət gələndə həqiqət üzə çıxır. Bir günə bitməli olan sadə bir dəyişiklik yeddi qatı keçir, üç abstraksiyanı sındırır və komandanı heç vaxt reallaşmayan tələblər üçün qurulmuş bir çərçivəni anlamağa məcbur edir. Gələcəyi düşünmək səhv deyil. Səhv, hələ heç bir sübut olmayan gələcəyi bu gün qurmağa başlamaqdır.
Niyə həddindən artıq mühəndisliyə meyl edirik?
Çox vaxt bunun arxasında keçmiş ağrılı təcrübələr dayanır. Əvvəlki layihədə təkrarlanan biznes məntiqi, çətinliklə dəyişdirilən inteqrasiya və ya bahalı yenidən yazma ehtiyacı — bu səhvləri təkrarlamaq istəməyən komandalar hər şeyi əvvəldən “gələcəyə hazır” qurmağa çalışır. Bu, ümumiyyətlə, məntiqli suallarla başlayır: “Bəs bu xüsusiyyət böyüyərsə?”, “Başqa komanda da istifadə etmək istəsə?”, “Məhsul konfiqurasiya istəsə?”. Amma xəyal edilən tələblərə real tələblərlə eyni arxitektura çəkisi veriləndə problem başlayır.
Abstraksiyanın gizli qiyməti
İki oxşar kod parçası görəndə onları ümumiləşdirmək cazibədar görünür. Lakin ilk abstraksiya adətən təmiz olur — bir neçə dublikatı aradan qaldırır. Sonra ikinci istifadə ssenarisi gəlir, fərqli yükləmə statusu tələb edir. Üçüncüsü fərqli validasiya, dördüncüsü fərqli icazələr... Tezliklə “təkrar istifadə olunan” komponent flag-lar, callback-lər, konfiqurasiya obyektləri və “escape hatch”lərlə dolur. Texniki olaraq təkrar istifadə mümkündür, amma onu təhlükəsiz dəyişdirmək üçün bütün istifadəçiləri bilmək lazımdır. Komanda mürəkkəbliyi aradan qaldırmadı — onu bir asılılıqda cəmləşdirdi.
Bəzən bir az dublikat daha düzgün seçimdir. Çünki dublikat deyir: “Bu hallar hazırda oxşar görünür, amma birlikdə dəyişib-dəyişməyəcəklərini hələ bilmirik”. Vaxtından əvvəl çəkilmiş abstraksiya isə deyir: “Biz artıq ümumi konsepti başa düşürük”. Həmin inam çox vaxt ən bahalı hissədir.
Arxitektura qatları: qoruyur, yoxsa kağız işidir?
Biznes qaydalarını HTTP sorğularından qoruyan bir xidmət qatı, qeyri-sabit üçüncü tərəf API-indən təcrid edən adapter, mürəkkəb saxlama davranışını mərkəzləşdirən repository — bunlar dəyərli sərhədlərdir. Amma “böyük sistemlərdə belə olmalıdır” düşüncəsi ilə əlavə edilən qatlar fərqli nəticə verir. Kiçik bir xüsusiyyət controller, service, repository, mapper, interface, factory, validator və adapter alır. Hər fayl kiçikdir, hər sinfin bir məsuliyyəti var. Sonra bir sahə dəyişir — yeniləmə input type, controller, interface, service, mapper, repository, test fixture və mock'dan keçməlidir. Arxitektura nizamlı görünür, amma sadə dəyişikliklər kağız işinə çevrilir.
Heç nəyi qorumayan bir qat avtomatik olaraq yaxşı arxitektura deyil. Bəzən bu sadəcə seremoniyadır. Yeni sərhəd qoymazdan əvvəl soruşun: “Bu hansı dəyişikliyi ucuzlaşdırır? Nəyi təcrid edir? Hansı uğursuzluğun qarşısını alır? Hansı təkrarlanan qərarları aradan qaldırır?”. Konkret cavab yoxdursa, arxitektura məhsul mürəkkəbliyini yox, mühəndis narahatlığını həll edir.
Çeviklik yoxsa nəzarətsiz dəyişkənlik?
Çevik sistemlər təhlükəsizlik vəd edir: daha çox qaydalar, daha çox provayder, daha çox iş axını. Amma hər seçim yeni qərarlar gətirir: “Bu tələb konfiqurasiya sahəsi olmalıdır? Yeni strategiya? Escape hatch?”. Sistem onlarla kombinasiyanı dəstəkləyə bilər, amma heç kim hansı kombinasiyaların təhlükəsiz olduğunu bilmir. Bu, faydalı çeviklik deyil, nəzarətsiz dəyişkənlikdir. Gizli xərc təkcə əlavə kod deyil — adi məhsul işini bitirmək üçün mühəndislərin qəbul etməli olduğu arxitektura qərarlarının sayıdır.
Həll yolu: mürəkkəbliyin struktur qazanmasına icazə verin
Cavab arxitekturanı, abstraksiyanı və ya təkrar istifadəni rədd etmək deyil. Daha sadə qayda var: mürəkkəbliyin struktur qazanmasına icazə verin. Cari davranışı aydın qurun. Vacib qərarları görünən saxlayın. Artıq əhəmiyyət kəsb edən sərhədləri qoruyun. Gələcək çıxarışı çətinləşdirəcək birləşmələrdən qaçın. Sonra həqiqi istifadə hallarının nəyin həqiqətən ümumi olduğunu göstərməsini gözləyin. Yaxşı ilk versiya diqqətsiz olmamalıdır — oxunaqlı, mənalı risklər ətrafında test edilmiş və gələcək refaktorinq üçün imkan verən şəkildə qurulmalıdır. Sadəcə, məhsul kifayət qədər sübut təqdim etməmiş son arxitekturanı bildiyini iddia etməməlidir.
Mənbə: Dev.to (https://dev.to/masaood/the-overengineering-trap-we-all-fall-into-2md5)



