همونطور که احتمالا میدونید درمورد error handling(مدیریت خطا) توی جاوااسکریپت صحبت میکنیم. قسمت اول بصورت کلی این موضوع رو گفتیم. انواع خطاها و چند راه برای مدیریت اونها. توی قسمت دوم هم انواع system error ها رو بررسی کردیم. با من همراه باشید تا 6 نوع ارور داخلی (یا native) جاوااسکریپت رو بررسی کنیم😉
RangeError
این ارور زمانی پیش میاد که یک مقدار خارج از محدوده مقادیر تعریف شده توسط javascript باشه. مثال پایین رو ببینید:
const l = console.log const arr = [90,88] arr.length=90**99
توس جاوااسکریپت هر type محدوده مقادیر مشخصی داره که بیشتر از اون مقدار رو نمیشه در اون type قرار داد. مثلا Number type رو درنظر بگیرید، این type میتونه تا یه عدد بسیار بزرگ(1.7976931348623157e+308) رو توی خودش جا بده. ولی اگه این عدد بیشتر بشه تبدیل میشه به Infinity(نامحدود). ممکنه اکثر اوقات به این اعداد نیاز نداشته باشیم، ولی وقتی با دادههای بزرگ کار میکنیم بهتره ارورهای مربوط به اون رو هم بدونیم. کد بالا این ارور رو میده:
RangeError: Invalid array length at Object.<anonymous> (e:\Programming\personal apps\test-article\error-handling-in-js(3)\app.js:3:11) at Module._compile (node:internal/modules/cjs/loader:1376:14) at Module._extensions..js (node:internal/modules/cjs/loader:1435:10) at Module.load (node:internal/modules/cjs/loader:1207:32) at Module._load (node:internal/modules/cjs/loader:1023:12) at Function.executeUserEntryPoint [as runMain] (node:internal/modules/run_main:135:12) at node:internal/main/run_main_module:28:49
حالا بیاید ببینیم معمولا چه وقتی این اتفاق میافته و چطوری میتونیم با کد تمیز جلوی این ارور رو بگیریم یا در صورت اتفاق اونو مدیریت(error handling) کنیم.
- Invalid Array Length(طول آرایه نامعتبر): مثل این تیکه کد:
let arr = new Array(-5);
- Number Exceeds Safe Limits(وقتی تعداد از محدوده ایمن بیشتر بشه): وقتی با ()toFixed و BigInt کار میکنیم احتمال این قضیه بیشتره.
- تابع بازگشتی بیشتر از اندازه callstack: خب callstack یه اندازه مشخصی داره و اگه ما از توابع بازگشتی تو در تو بیرویه استفاده کرده باشیم همچین مشکلی پیش میاد.
- الگوهای نامعتبر RegExp
ReferenceError
این ارور زمانی اتفاق میافته که بخوایم به متغیری دسترسی پیدا کنیم که وجود نداره یا توی اون scope نیست.
مثالهای رایج این اتفاق چیه(اینا رو میگیم که متوجه بشیم چه قسمتهایی ممکنه نیاز به مدیریت خطا یا جلوگیری از اون یا به عبارتی error handling داشته باشه):
- سعی برای دسترسی به متغیری که وجود نداره:
console.log(variable);
- دسترسی به متغیری که توی اون scope نیست. مثلا فرض کنید بخوایم متغیری رو که توی یه تابع تعریف کردیم، از بیرون تابع صدا بزنیم.
- وقتی از const و let برای تعریف متغیر استفاده میکنیم باید حواسمون باشه قبل از تعریف متغیر اونو صدا نزنیم.
- اگه واسخ صدا زدن متغیری خطای تایپی داشته باشیم. مثلا اسم متغیر arr هست ولی ما اشتباهی att رو صدا بزنیم.
- درصورتی که برای تعریف متغیر از const استفاده کنیم ولی به اون مقدار اولیه ندیم(برای اینکه دلیل عمیق این خطا رو بفهمید باید hosting و TDZ رو بلد باشید. پیشنهاد می کنم مقالهای که در آخر معرفی میکنم رو بخونید)
- و در آخر حواستون باشه نمیشه آبجکت window رو توی node.js استفاده کرد.
فک کنم فهمیدن این ارور هم مشکل نبود. به همین سادگی به همین خوشمزگی: پودر کیک رشد 🙂
SyntaxError
این خطا زمانی پیش میاد که ما مشکلی در سینتکس(syntax) کد داشته باشیم. موتور جاوااسکریپت(js engine) زمانی که کد ما رو تجزیه(parse) میکنه (تا AST رو بسازه و …) درصورتی کد از نظر دستوری/سینتکس جاوااسکریپت مشکلی داشته باشه این خطا رو به ما نشون میده.
TypeError
وقتی قراره عملیاتی روی یه مقدار انجام بشه ولی type اون مقدار برای اون عملیات اشتباهه، این مشکل پیش میاد. مثلا فرض کنید ما یه عدد داشته باشیم و روی اون یه متد خاص string رو استفاده کنیم! حالا این مثال رو معمولا توی کد انجام نمیدیم ولی چیزایی که ممکنه برامون پیش بیاد ایناس:
- صدا زدن property یک شئ undefined یا null مثل
obj.prop
اما چطور ممکنه واسه همچین چیز سادهای اشتباه کنیم؟ گاهی ما توسط یه api یا ورودیهای خاص یا … ممکنه یه آبجکت بسازیم که که شاید در حالتهایی به شکل undefined یا null در بیان، در همچین حالتی بهتره اینو پیشبینی کنیم و اگه امکان null یا undefined بودن اونها وجود داشت از optional chaining استفاده کنیم تا اروری پیش نیاد. optional chaining یه سینتکس ساده است که در صورت وجود نداشتن یه پراپرتی بجای ارور دادن undefined برمیگردونه. برای استفاده از اون قبل پراپرتی باید یه علامت سوال بزاریم. مثال رو ببینین:
let person = { name: "Alice", address: { city: "New York" } }; console.log(person?.name); // Output: "Alice" console.log(person?.address?.city); // Output: "New York" console.log(person?.job?.title); // Output: undefined (error بجای)
- تلاش برای تغییر دادن مقدارهای read-only. مثلا این مثال به ارور منجر میشه، چون مقدار متغیری که با const تعریف کردیم رو نمیشه تغییر داد:
const PI = 3.14; PI = 3.14159;
- استفاده نادرست از this. همیشه مراقب این کلمه کلیدی باشید که در هر جایی چه مقداری رو داره. مثلا توی arrow function ها.
URIError
توی جاوااسکریپت این خطا وقتی اتفاق میافته که ما یکی از توابع مدیریت URI رو به شکل نادرستی استفاده کنیم. مثل ()decodeURI یا ()decodeURIComponent و … (URI چیه؟ یه string که برای پیدا کردن منابع توی اینترنت یا سیستم داخلی استفاده میشه. یه نمونه ازش همون URL هست).
InternalError
این ارور رو هم ممکنه ببینید که به مشکل داخلی موتور اجرا کننده جاوااسکریپت مربوطه، مثل بازگشت زیاد توابع بازگشتی یا توابع تو در تو که باعث سرریز یا پرشدن callstack میشه. قبلا هم این مورد رو گفتیم ولی اینجا اونو آوردم چون بسته به موتورهای مختلف جاوااسکریپت ممکنه این ارور رو بصورت InternalError یا RangeError ببینید. برای error handling این قضیه باید درمورد بازگشتهای توابع و بهینه بودنشون مطمئن بشیم یا سعی کنیم از حلقه جای بازگشتهای عمیق استفاده کنیم. از طرفی نظارت(monitoring) روی مصرف حافظه و به خوبی کنترل کردن دیتاها از این ارور جلوگیری میکنه.
مقاله تفاوت var و let و const در JavaScript که اگه تفاوتهاشو نمیدونید پیشنهاد میکنم حتما مطالعه کنید!
توی این مقاله سعی کردیم به ارورها نگاهی بندازیم تا موقع کد زدن حواسمون به اشتباهای احتمالی باشه و در صورت نیاز error handling رو به درستی در برنامه پیاده سازی کنیم.
منبع JavaScript error reference :MDN