برنامههای افزودنی به امتیازات ویژه در مرورگر دسترسی دارند و آنها را به یک هدف جذاب برای مهاجمان تبدیل میکند. اگر یک برنامه افزودنی در معرض خطر قرار گیرد، هر کاربر آن افزونه در برابر نفوذ مخرب و ناخواسته آسیب پذیر می شود. با استفاده از این اقدامات، یک برنامه افزودنی را ایمن نگه دارید و از کاربران آن محافظت کنید.
از حساب های توسعه دهنده محافظت کنید
کد برنامه افزودنی از طریق حساب های گوگل آپلود و به روز می شود. اگر حسابهای توسعهدهندگان به خطر بیفتد، مهاجم میتواند کدهای مخرب را مستقیماً به همه کاربران ارسال کند. با ایجاد حسابهای ویژه برنامهنویس و فعال کردن احراز هویت دو مرحلهای ، ترجیحاً با یک کلید امنیتی ، از این حسابها محافظت کنید.
گروه ها را انتخابی نگه دارید
اگر از انتشار گروهی استفاده می کنید، گروه را محدود به توسعه دهندگان مورد اعتماد نگه دارید. درخواست عضویت افراد ناشناس را نپذیرید.
هرگز از HTTP استفاده نکنید
هنگام درخواست یا ارسال داده، از اتصال HTTP اجتناب کنید. فرض کنید هر اتصال HTTP دارای استراق سمع یا تغییراتی است. HTTPS همیشه باید ترجیح داده شود، زیرا دارای امنیت داخلی است که اکثر حملات مرد میانی را دور میزند.
حداقل مجوزها را درخواست کنید
مرورگر Chrome دسترسی یک برنامه افزودنی را به امتیازاتی که صریحاً در مانیفست درخواست شده اند محدود می کند. برنامههای افزودنی باید مجوزهای خود را فقط با ثبت APIها و وبسایتهایی که به آنها وابسته هستند، به حداقل برسانند. کد دلخواه باید به حداقل برسد.
محدود کردن امتیازات افزونه ها، آنچه را که یک مهاجم بالقوه می تواند از آن سوء استفاده کند، محدود می کند.
XMLHttpRequest متقاطع
یک برنامه افزودنی فقط می تواند از XMLHttpRequest برای دریافت منابع از خود و از دامنه های مشخص شده در مجوزها استفاده کند.
{
"name": "Very Secure Extension",
"version": "1.0",
"description": "Example of a Secure Extension",
"permissions": [
"/*",
"https://*.google.com/"
],
"manifest_version": 2
}
این برنامه افزودنی با فهرست کردن "/*"
و "https://*google.com/"
در مجوزها، درخواست دسترسی به هر چیزی در developer.chrome.com و زیر دامنههای Google را میدهد. اگر برنامه افزودنی به خطر بیفتد، همچنان فقط اجازه تعامل با وبسایتهایی را خواهد داشت که با الگوی مطابقت مطابقت دارند. مهاجم نمی تواند به "https://user_bank_info.com"
دسترسی داشته باشد یا با "https://malicious_website.com"
تعامل داشته باشد.
محدود کردن فیلدهای مانیفست
گنجاندن ثبت نامهای غیر ضروری در مانیفست آسیبپذیریها را ایجاد میکند و یک برنامه افزودنی را بیشتر نمایان میکند. فیلدهای مانیفست را به آنهایی که برنامه افزودنی به آنها متکی است محدود کنید و فیلد خاصی را ثبت کنید.
قابلیت اتصال خارجی
از فیلد externally_connectable
برای اعلام اینکه برنامه افزودنی با کدام برنامههای افزودنی خارجی و صفحات وب تبادل اطلاعات میکند، استفاده کنید. محدود کردن افرادی که برنامه افزودنی می تواند به صورت خارجی با منابع قابل اعتماد ارتباط برقرار کند.
{
"name": "Super Safe Extension",
"externally_connectable": {
"ids": [
"iamafriendlyextensionhereisdatas"
],
"matches": [
"/*",
"https://*google.com/"
],
"accepts_tls_channel_id": false
},
...
}
منابع قابل دسترس وب
در دسترس قرار دادن منابع توسط وب، تحت web_accessible_resources
، یک برنامه افزودنی را توسط وب سایت ها و مهاجمان قابل شناسایی می کند.
{
...
"web_accessible_resources": [
"images/*.png",
"style/secure_extension.css",
"script/secure_extension.js"
],
...
}
هرچه منابع قابل دسترس وب بیشتر در دسترس باشد، مهاجم بالقوه می تواند از راه های بیشتری بهره برداری کند. این فایل ها را به حداقل برسانید.
یک خط مشی امنیتی محتوای صریح را در نظر بگیرید
برای جلوگیری از حملات اسکریپت بین سایتی، یک خط مشی امنیتی محتوا برای برنامه افزودنی در مانیفست قرار دهید. اگر برنامه افزودنی فقط منابع را از خودش بارگیری می کند موارد زیر را ثبت کنید:
{
"name": "Very Secure Extension",
"version": "1.0",
"description": "Example of a Secure Extension",
"content_security_policy": "default-src 'self'"
"manifest_version": 2
}
اگر برنامه افزودنی نیاز به اسکریپت هایی از میزبان های خاص داشته باشد، می توان آنها را گنجاند:
{
"name": "Very Secure Extension",
"version": "1.0",
"description": "Example of a Secure Extension",
"content_security_policy": "default-src 'self' https://extension.resource.com"
"manifest_version": 2
}
از API های اجرایی اجتناب کنید
APIهایی که کد را اجرا می کنند باید با جایگزین های امن تری جایگزین شوند.
document.write() و innerHTML
اگرچه ممکن است ایجاد پویا عناصر HTML با document.write()
و innerHTML
سادهتر باشد، اما پسوند و صفحات وب که پسوند به آنها وابسته است، برای مهاجمانی که اسکریپتهای مخرب را وارد میکنند باز میماند. در عوض، به صورت دستی گره های DOM ایجاد کنید و از innerText
برای درج محتوای پویا استفاده کنید.
function constructDOM() {
let newTitle = document.createElement('h1');
newTitle.innerText = host;
document.appendChild(newTitle);
}
eval()
تا حد امکان از استفاده از eval()
برای جلوگیری از حملات خودداری کنید، زیرا eval()
هر کدی را که به آن ارسال می شود را اجرا می کند که ممکن است مخرب باشد.
var xhr = new XMLHttpRequest();
xhr.open("GET", "https://api.example.com/data.json", true);
xhr.onreadystatechange = function() {
if (xhr.readyState == 4) {
// WARNING! Might be evaluating an evil script!
var resp = eval("(" + xhr.responseText + ")");
...
}
}
xhr.send();
در عوض، روشهای ایمنتر و سریعتر مانند JSON.parse()
ترجیح دهید.
var xhr = new XMLHttpRequest();
xhr.open("GET", "https://api.example.com/data.json", true);
xhr.onreadystatechange = function() {
if (xhr.readyState == 4) {
// JSON.parse does not evaluate the attacker's scripts.
var resp = JSON.parse(xhr.responseText);
}
}
xhr.send();
از اسکریپت های محتوا با دقت استفاده کنید
در حالی که اسکریپت های محتوا در دنیایی منزوی زندگی می کنند، از حملات مصون نیستند:
- اسکریپت های محتوا تنها بخشی از یک برنامه افزودنی است که مستقیماً با صفحه وب در تعامل است. به همین دلیل، صفحات وب متخاصم ممکن است بخشهایی از DOM را که اسکریپت محتوا به آن وابسته است دستکاری کرده یا از رفتار استاندارد وب شگفتانگیز، مانند موارد نامگذاری شده، سوء استفاده کنند.
- برای تعامل با DOM صفحات وب، اسکریپت های محتوا باید در همان فرآیند رندر صفحه وب اجرا شوند. این باعث میشود اسکریپتهای محتوا در برابر نشت دادهها از طریق حملات کانال جانبی (مثلاً Spectre ) آسیبپذیر شوند و اگر یک صفحه وب مخرب فرآیند رندر را به خطر بیندازد، توسط مهاجم تحت کنترل قرار میگیرد.
کارهای حساس باید در یک فرآیند اختصاصی انجام شوند، مانند اسکریپت پسزمینه برنامه افزودنی. از قرار دادن تصادفی امتیازات برنامه افزودنی در اسکریپت های محتوا اجتناب کنید:
- فرض کنید که پیامهای یک اسکریپت محتوا ممکن است توسط یک مهاجم ساخته شده باشد (مثلاً تمام ورودیها را اعتبارسنجی و پاکسازی کنید و از اسکریپتهای خود در برابر اسکریپتهای بین سایتی محافظت کنید).
- فرض کنید هرگونه داده ارسال شده به اسکریپت محتوا ممکن است به صفحه وب نشت کند. داده های حساس (مثلاً اسرار از برنامه افزودنی، داده های سایر منابع وب، تاریخچه مرور) را به اسکریپت های محتوا ارسال نکنید.
- دامنه اقدامات ممتازی را که میتوانند توسط اسکریپتهای محتوا ایجاد شوند، محدود کنید. به اسکریپتهای محتوا اجازه ندهید درخواستهایی را برای URLهای دلخواه ایجاد کنند یا آرگومانهای دلخواه را به APIهای برنامههای افزودنی ارسال کنند (مثلاً اجازه ندهید URLهای دلخواه برای
fetch
یاchrome.tabs.create
API) ارسال شوند.
ورودی ها را ثبت و ضدعفونی کنید
با محدود کردن شنوندگان به آنچه برنامه افزودنی انتظار دارد، اعتبارسنجی فرستنده داده های دریافتی و پاکسازی همه ورودی ها، از یک برنامه افزودنی در برابر اسکریپت های مخرب محافظت کنید.
یک برنامه افزودنی فقط باید برای runtime.onRequestExternal
ثبت نام کند، در صورتی که انتظار ارتباط از یک وب سایت یا برنامه افزودنی خارجی را داشته باشد. همیشه تأیید کنید که فرستنده با منبع قابل اعتماد مطابقت دارد.
// The ID of an external extension
const kFriendlyExtensionId = "iamafriendlyextensionhereisdatas";
chrome.runtime.onMessageExternal.addListener(
function(request, sender, sendResponse) {
if (sender.id === kFriendlyExtensionId)
doSomething();
});
حتی پیامهایی که از طریق رویداد runtime.onMessage از خود برنامه افزودنی میآیند نیز باید مورد بررسی قرار گیرند تا اطمینان حاصل شود که MessageSender از یک اسکریپت محتوای در معرض خطر نیست.
chrome.runtime.onMessage.addListener(function(request, sender, sendResponse) {
if (request.allowedAction)
console.log("This is an allowed action.");
});
با پاکسازی ورودی های کاربر و داده های دریافتی، حتی از خود برنامه افزودنی و منابع تایید شده، از اجرای اسکریپت مهاجم توسط یک برنامه افزودنی جلوگیری کنید. از APIهای اجرایی اجتناب کنید .
function sanitizeInput(input) {
return input.replace(/&/g, '&').replace(/</g, '<').replace(/"/g, '"');
}