ProgramlamaBackend geliştirici

Kullanıcı hatalarının (Custom Errors) TypeScript'teki mekanizmasını açıklayın. Kullanıcı hatası sınıflarını nasıl doğru bir şekilde tanımlamalıyız, türlerini belirtmenin amacı nedir ve 'instanceof' ile hata serileştirmesiyle ilgili tuzaklardan nasıl kaçınabiliriz?

Hintsage yapay zeka asistanı ile mülakatları geçin

Cevap.

Sorunun geçmişi: JavaScript'te standart hatalar Error sınıfı aracılığıyla tanımlanır. Büyük TypeScript projelerinde durumları doğru bir şekilde ele almak için kendi hata hiyerarşimizi kullanmak önemlidir; ancak türler, kalıtım ve 'instanceof' davranışı ile ilgili bazı incelikler vardır.

Sorun: Error'dan kalıtım alındığında zorluklar ortaya çıkabilir: prototip kaybolur, 'instanceof' yanlış çalışır, türler hatalı tanımlanabilir, serileştirme genellikle stack trace kaybı ile sonuçlanır. Özelliklerin açıkça belirtilmemesi hata işleme sırasında hatalara yol açabilir.

Çözüm: Kullanıcı hatalarını Error sınıfını genişleterek doğru bir şekilde tanımlamak. Adını açıkça yazmak, prototipi manuel olarak geri yüklemek (bu, ES5 için ve CommonJS'ye derlendiğinde önemlidir) ve hataların alanlarını türlendirmek gereklidir.

Kod örneği:

class ValidationError extends Error { code: number; constructor(message: string, code: number = 400) { super(message); Object.setPrototypeOf(this, ValidationError.prototype); this.name = 'ValidationError'; this.code = code; } } function process(user: string) { if (!user) throw new ValidationError('Kullanıcı gerekli', 401); }

Ana özellikler:

  • Transpile işlemine rağmen 'instanceof' desteklemek için açıkça prototipi geri yüklemek.
  • Kullanıcı hatası özelliklerinin türlendirilmesi.
  • Her mantıksal hata grubu için ayrı bir sınıf.

Kurnaz Sorular.

Object.setPrototypeOf(this, ...) çağrısını neden atlayamayız?

Object.setPrototypeOf(this, Class.prototype) çağrılmadığında, 'instanceof' ValidationError ES5/CommonJS veya Babel'e derlendiğinde çalışmayacaktır. Bu, catch bloklarının ValidationError hatasını yakalamamasına neden olur.

class CustomErr extends Error {} const err = new CustomErr('mesaj'); console.log(err instanceof CustomErr); // setPrototypeOf olmadan false

Kullanıcı hatasında name alanını atlayabilir miyiz?

Eğer this.name özelliği ayarlanmazsa, hata yığınları ve loglardaki görüntü yanlış olacak, bu da hata sebeplerini bulmayı ve sınıflandırmayı zorlaştıracaktır.

Hataların serileştirilebilir olması gerekiyor mu, eğer öyleyse nasıl?

Hatalar düzgün bir şekilde serileştirilmeli (örneğin, günlükleme veya ağ üzerinden iletim için), aksi takdirde JSON.stringify(new Error()) message ve stack dönmeyecektir. toJSON yöntemini geçersiz kılmak gereklidir.

class SerializableError extends Error { toJSON() { return { name: this.name, message: this.message, stack: this.stack }; } }

Tipik hatalar ve anti-paternlere

  • Object.setPrototypeOf'un eksikliği, instanceof'ın yanlış çalışmasına neden olur.
  • name ve kullanıcı özelliklerinin göz ardı edilmesi.
  • toJSON uygulanmadan hata serileştirilmesi: stack/message kaybolur.

Hayat örneği

Olumsuz durum

Projede basitçe class MyError extends Error yapıldı, prototip geri yüklenmedi. Hatalar if (err instanceof MyError) ile yakalanmaya çalışıldı, ancak bu çalışmadı ve kod önemli durumları sessizce atlattı.

Artılar:

  • Kod derli toplu görünüyordu.
  • Boilerplate yoktu.

Eksiler:

  • instanceof çalışmadı.
  • İstisnalar uygun şekilde günlüğe alınmadı.
  • ts->js transpiler değiştiğinde uyumsuzluk yaşandı.

Olumlu durum

Doğru bir CustomError uygulandı, açıkça name, code ve toJSON belirlendi, farklı hata türlerinin işlenmesi için testler yapıldı. Günlüklerde ve catch işleyicilerde hata yapıları daha anlaşılır hale geldi, bu da hata bulma süresini azalttı.

Artılar:

  • Net bir hata hiyerarşisi.
  • Güvenilir serileştirme.
  • Tarayıcı ve Node.js arasında çapraz platform uyumluluğu.

Eksiler:

  • Her CustomError sınıfında şablon mantığı ortaya çıktı.