Tasarım Sistemleri Performansı Nasıl Etkiler?
Tasarım sistemi bir organizasyonun UI bileşenlerini, stil kararlarını ve görsel kurallarını tek bir kaynakta toplayan yapıdır. Tutarlılık sağlar, geliştirme hızını artırır ve tasarım ile kod arasındaki uyumsuzlukları azaltır. Ancak bu yapı, frontend performansını doğrudan etkileyen bir dizi teknik karar içerir. Hangi token formatının seçildiği, bileşen kütüphanesinin nasıl paketlendiği, ikonların nasıl servis edildiği — bunların her biri her sayfanın yükleme maliyetine sessizce yansır.
Tasarım sistemlerinin performans boyutu çoğu zaman geri planda kalır. Bir ekip yeni bir bileşen kütüphanesi entegre ederken öncelikli odak API tutarlılığı, erişilebilirlik ve dokümantasyondur; bundle boyutu genellikle sonradan fark edilir. Oysa tasarım sistemi kararları uygulamanın tüm sayfalarına yayıldığından, küçük görünen bir maliyet çok sayıda sayfada çarpım etkisi yaratır. Performans açısından bir tasarım sistemini değerlendirmek, bu kararları görünür kılmakla başlar.
Token formatı CSS değişkeni ile JS tüketimi arasındaki maliyet farkını belirler
Tasarım tokenları renk, tipografi, boşluk ve gölge gibi görsel kararları merkezi değişkenler olarak tanımlar. Bu tokenlar iki farklı biçimde tüketilebilir: CSS özel değişkenleri (--color-primary: #16a34a) veya JavaScript nesneleri aracılığıyla. İki yaklaşım arasındaki performans farkı belirgindir.
CSS değişkenleri tarayıcı tarafından doğal olarak işlenir ve herhangi bir JavaScript yükü gerektirmez. Bir stil dosyasına dahil edilen tokenlar, sayfanın CSS'i parse edildiğinde kullanıma hazır olur. Öte yandan JavaScript tabanlı token tüketimi — CSS-in-JS kütüphaneleri bu modeli sıkça kullanır — runtime'da ek işlem gerektirir. Her bileşen render edildiğinde tokenlar JavaScript üzerinden hesaplanır, class adları dinamik olarak üretilir ve DOM'a enjekte edilir. Bu işlem CPU maliyeti taşır ve özellikle çok sayıda bileşenin bir arada render edildiği sayfalarda ölçülebilir gecikmeye yol açar.
CSS-in-JS kütüphaneleri bu maliyeti azaltmak için derleme zamanı çıktısı veya statik ekstraksiyon gibi optimizasyonlar sunar; ancak bu optimizasyonların etkinliği kütüphane seçimine ve yapılandırmaya bağlıdır. Emotion veya styled-components'ın runtime modunda çalışmasıyla derleme zamanında statik CSS çıkartılması arasında JavaScript parse ve execute maliyeti açısından kayda değer bir fark oluşur. Tasarım sistemini kurarken token tüketiminin hangi modda gerçekleşeceğini baştan netleştirmek, sonradan yapılacak optimizasyon çabasından çok daha verimlidir.
Bileşen kütüphanesinin paketleme yapısı tree shaking'in sınırını çizer
Bir tasarım sistemi genellikle onlarca, büyük organizasyonlarda yüzlerce bileşen içerir. Uygulamanın bu bileşenlerin yalnızca bir bölümünü kullandığı düşünüldüğünde, kütüphanenin nasıl paketlendiği bundle boyutunu doğrudan belirler.
Kütüphane tek bir büyük dosyaya derlenmişse — monolitik bundle — tree shaking etkili çalışamaz. Bundler, kullanılmayan bileşenleri atamaz çünkü tüm kod tek bir modül olarak görünür. Bu durumda yalnızca beş bileşen kullanan bir uygulama, kütüphanenin tamamını yüklemek zorunda kalır. Kütüphanenin her bileşeni ayrı bir modül olarak dışa aktarması ve ES modül formatında derlenmesi bu sorunu büyük ölçüde çözer. Bundler, gerçekte kullanılan bileşenleri grafikten izleyebilir ve kalanları atar.
package.json içindeki "sideEffects": false bildirimi bu süreçte kritik bir rol oynar. Bu alan eksik olduğunda bundler, kütüphanede global yan etkiler olabileceğini varsayarak tree shaking'i kısıtlar. Bileşen kütüphaneleri oluşturan ekipler için bu ayar bir ihmal değil, kasıtlı bir taahhüttür: kütüphanenin tüm export'larının saf olduğunu, global state değiştirmediğini ve güvenle atılabileceğini bildirir. Tüketiciler açısından ise bu, kütüphaneden ne kadarının gerçekten bundle'a dahil edildiğini bundle analizi ile doğrulayarak güvence altına almak anlamına gelir.
İkon sisteminin seçimi her sayfada tekrarlayan bir ağırlık üretir
İkonlar tasarım sisteminin en sık değişen ve en fazla sayfada görünen öğelerinden biridir. Servis yöntemi üç ana kategoriye ayrılır: icon font, SVG sprite ve bireysel SVG dosyaları. Her birinin performans profili farklıdır.
Icon font yaklaşımında tüm ikonlar tek bir font dosyasına paketlenir. Bu dosya genellikle 50–200 KB arasında değişir ve sayfada yalnızca birkaç ikon kullanılıyor olsa bile tamamı indirilir. Ayrıca ikonlar metin olarak render edildiğinden ekran okuyucular için erişilebilirlik düzenlemeleri gerektirir ve alt piksel rendering tutarsızlıkları yaşanabilir. SVG sprite ise tüm ikonları tek bir SVG dosyasında toplar ve <use> referansıyla kullanılır. Tek bir HTTP isteğiyle önbelleklenir; ancak benzer şekilde kullanılmayan ikonlar da dosyaya dahildir.
Bireysel SVG dosyaları veya inline SVG yaklaşımında yalnızca kullanılan ikonlar yüklenir. Bu yöntem code splitting ile birleştirildiğinde sayfaya özgü ikon yükünü minimize eder. Dezavantajı, çok sayıda küçük dosya yerine HTTP istek sayısının artması ve yapılandırmanın daha dikkatli yönetilmesi gerekmesidir. HTTP/2 ortamlarında bu dezavantaj büyük ölçüde azalır; ancak her ortamın protokol desteğini teyit etmek gerekir.
Uygulamada genellikle en çok kullanılan birkaç ikon için SVG sprite, sayfa bazında kullanılan özgün ikonlar için bireysel SVG kombinasyonu iyi bir denge kurar. Tasarım sistemi bunu otomatikleştiren bir araç zinciri sunuyorsa — ikonları kullanıma göre sınıflandıran ve bundle'a dahil edilecek olanları seçen — tercih edilmesi gereken strateji de netleşir.
Versiyonlama stratejisi tüm uygulamaların güncelleme maliyetini şekillendirir
Tasarım sistemleri zaman içinde gelişir: yeni bileşenler eklenir, mevcut bileşenlerin API'si değişir, token değerleri güncellenir. Bu değişikliklerin tüketici uygulamalara nasıl yansıdığı hem geliştirici deneyimini hem de performansı etkiler.
Semantic versioning uygulayan bir tasarım sistemi, kırıcı değişiklikleri major sürüm artışıyla işaretler. Tüketici uygulamalar güncellemeyi istedikleri zaman yapabilir; bu kontrollü bir geçiş sağlar. Ancak uygulamalar farklı sürümlere bağlı kalmaya devam ederse, monorepo yapılarında birden fazla sürüm aynı bundle'a dahil olabilir. Aynı kütüphanenin iki farklı major versiyonu tek bir uygulamada aktif olduğunda bundle boyutu katlanır. Bu durumu önlemek için tüketici uygulamaların düzenli olarak güncel sürüme taşınması veya belirli bir maksimum sürüm farkı politikasının oluşturulması gerekir.
Tasarım sisteminin her yeni sürümünde bundle boyutu etkisini ölçmek bu sürecin parçası olmalıdır. Yeni bir bileşen eklenmesi veya mevcut bir bileşenin yeni bir bağımlılık edinmesi, tüm tüketici uygulamaların bundle'ını etkiler. Sistemi yayınlayan ekip bu etkiyi raporlamalı; tüketici ekipler güncelleme kararını bu veriye dayanarak vermelidir.
Critical path üzerindeki tasarım sistemi yükü LCP'yi doğrudan etkiler
Bir sayfanın ilk render'ında hangi stillerin ve bileşenlerin kritik yolda yer aldığı, LCP değerini doğrudan belirler. Tasarım sistemi CSS'inin tamamı tek bir büyük dosyada geliyorsa bu dosya render engelleyen bir kaynak haline gelir. Sayfa, bu CSS yüklenip parse edilmeden görsel içeriğini gösteremez.
Bu sorunu yönetmenin birkaç yolu vardır. Tasarım sistemi bileşenlerine ait CSS'i chunk'lara bölmek ve yalnızca ilgili sayfanın bileşenlerini yüklemek başlangıç yükünü azaltır. Alternatif olarak, tüm tasarım sistemi CSS'ini küçük bir temel dosyaya indirgemek ve bileşen bazında ek stilleri lazy olarak yüklemek de uygulanabilir. Bu kararlar tasarım sistemi mimarisinin erken aşamasında alınmalıdır; sonradan refactor etmek çok daha maliyetlidir.
Tasarım sistemi fontlarının nasıl yüklendiği de kritik yolun bir parçasıdır. Sistem font ağırlıklarını ve stillerini merkezi olarak yönetiyorsa, her uygulamanın gerçekte ihtiyaç duyduğu font varyasyonlarını ayrıca yapılandırması gerekir. Tüm ağırlıkları içeren bir font setinin tüm sayfalara yüklenmesi, tipografi tutarlılığı adına ödenen gereksiz bir bant genişliği maliyetidir.
Tasarım sistemi ile performans arasındaki gerilim yapısal bir çelişki değildir. İkisi aynı anda iyi yapılabilir; ancak bu birlikte düşünmeyi gerektirir. Token formatı seçimi, kütüphane paketleme kararı, ikon servis stratejisi ve versiyonlama politikası — bunların her biri hem tasarım sistemi kalitesini hem de son kullanıcının deneyimini belirleyen teknik kararlardır. Performansı bu kararların dışında tutmak, her sayfada taşınan ve çoğu zaman fark edilmeyen bir ağırlık birikimine yol açar.
Tasarım sistemlerinin performans maliyeti yalnızca ilk yüklemede değil, güncelleme döngülerinde de ortaya çıkar. Bir sistemin yeni bir bileşen versiyonu yayınlandığında, tüketici uygulamaların bu güncellemeyi alması için yeniden build alması gerekir. Eğer tasarım sistemi CSS veya JS çıktısı içerik hash'li versioned asset olarak yönetiliyorsa, değişen dosyalar yeni hash ile yayınlanır ve tarayıcı önceki versiyonu önbellekten kullanmaya devam edemez. Bu zorunlu önbellek yenilemesi, büyük bir tasarım sistemi dosyasının sık güncellendiği senaryolarda kullanıcıların her güncelleme sonrasında bu dosyayı yeniden indirmesi anlamına gelir. Bu maliyeti azaltmanın yolu, tasarım sistemi çıktısını stabil parçalara bölmek ve yalnızca değişen bölümlerin hash'ini güncellemektir.
Tasarım sisteminin dokümantasyon sitesi veya Storybook gibi bileşen gezgini, performans testleri için de değerli bir araçtır. Bu ortamlarda bireysel bileşenlerin render maliyeti, DOM boyutu ve CSS boyutu ayrıca ölçülebilir. Üretim uygulamasına dahil edilmeden önce bir bileşenin tarayıcı maliyetini bu izole ortamda gözlemlemek, regresyonları erken yakalamanın pratik bir yoludur. Özellikle animasyon veya dinamik stil içeren bileşenler için reflow ve repaint maliyetinin bu ortamda profil edilmesi, üretim ortamına erişmeden sorunları gündeme taşır.