Практические сценарии применения Proxy
Создавайте объекты для проверки данных, logging и реактивности.
«Практические сценарии применения Proxy» — бесплатный урок JavaScript Academy на CoddyKit. Это урок 4 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения JavaScript Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс JavaScript Academy содержит 4 уроков всего.
Прокси на практике
Теперь вы объедините прокси и Reflect, чтобы решать реальные задачи: проверку, журналирование, значения по умолчанию и другие. Каждый шаблон оборачивает обычный объект, не изменяя его.
Обёртка для проверки
Обеспечьте соблюдение схемы: отклоняйте любую запись, не соответствующую rule. target остаётся чистым, потому что некорректные данные никогда в него не попадают.
function validated(obj, rules) {
return new Proxy(obj, {
set(target, prop, value, receiver) {
const rule = rules[prop];
if (rule && !rule(value)) {
throw new TypeError('invalid value for ' + prop);
}
return Reflect.set(target, prop, value, receiver);
}
});
}
const user = validated({}, { age: v => v >= 0 });
user.age = 25;
console.log(user.age);
try { user.age = -1; } catch (e) { console.log(e.message); }Обёртка для журналирования
Отслеживайте каждое чтение и запись для отладки: после журналирования передавайте операцию через Reflect.
function logged(obj) {
return new Proxy(obj, {
get(t, p, r) { console.log('GET ' + p); return Reflect.get(t, p, r); },
set(t, p, v, r) { console.log('SET ' + p + '=' + v); return Reflect.set(t, p, v, r); }
});
}
const data = logged({ count: 0 });
data.count = 5;
console.log(data.count);Значения по умолчанию
Возвращайте резервное значение (fallback) для любого отсутствующего свойства, чтобы чтение никогда не давало undefined.
function withDefault(obj, fallback) {
return new Proxy(obj, {
get(t, p, r) {
return p in t ? Reflect.get(t, p, r) : fallback;
}
});
}
const scores = withDefault({ ada: 90 }, 0);
console.log(scores.ada);
console.log(scores.unknown);Отрицательная индексация массивов
Добавьте массивам поддержку отрицательных индексов в стиле Python, преобразуя их в перехватчике get.
function negIndex(arr) {
return new Proxy(arr, {
get(t, p, r) {
const i = Number(p);
if (Number.isInteger(i) && i < 0) {
return Reflect.get(t, t.length + i, r);
}
return Reflect.get(t, p, r);
}
});
}
const list = negIndex(['a', 'b', 'c']);
console.log(list[-1]);
console.log(list[0]);Представление только для чтения
Предоставляйте объект, который можно читать, но нельзя изменять; это полезно для защиты общей конфигурации config.
function readonly(obj) {
return new Proxy(obj, {
set() { console.log('blocked write'); return false; },
deleteProperty() { console.log('blocked delete'); return false; }
});
}
const config = readonly({ apiUrl: '/api' });
config.apiUrl = '/hacked';
console.log(config.apiUrl);Подсчёт обращений
Отслеживайте, сколько раз читается каждое свойство, сохраняя counts вне target.
function counted(obj) {
const counts = {};
const proxy = new Proxy(obj, {
get(t, p, r) {
counts[p] = (counts[p] || 0) + 1;
return Reflect.get(t, p, r);
}
});
return { proxy, counts };
}
const { proxy, counts } = counted({ x: 1 });
proxy.x; proxy.x; proxy.x;
console.log(counts.x);Вычисляемые виртуальные свойства
Предоставляйте производные значения, которые не хранятся в объекте, а заново вычисляются при каждом чтении.
const rect = new Proxy({ width: 4, height: 3 }, {
get(t, p, r) {
if (p === 'area') return t.width * t.height;
return Reflect.get(t, p, r);
}
});
console.log(rect.area);
rect.width = 10;
console.log(rect.area);Ошибка при чтении неизвестных свойств
Выявляйте опечатки на раннем этапе, выдавая ошибку, когда код читает несуществующее свойство.
function strict(obj) {
return new Proxy(obj, {
get(t, p, r) {
if (typeof p === 'string' && !(p in t)) {
throw new ReferenceError('unknown property: ' + p);
}
return Reflect.get(t, p, r);
}
});
}
const o = strict({ name: 'Ada' });
console.log(o.name);
try { console.log(o.naem); } catch (e) { console.log(e.message); }Объединение аспектов
Настоящие обёртки часто объединяют проверку и журналирование в одном обработчике, а каждый перехватчик передаёт операцию через Reflect.
const account = new Proxy({ balance: 0 }, {
set(t, p, v, r) {
if (p === 'balance' && v < 0) throw new RangeError('no overdraft');
console.log(p + ' set to ' + v);
return Reflect.set(t, p, v, r);
}
});
account.balance = 100;
console.log(account.balance);
try { account.balance = -50; } catch (e) { console.log(e.message); }Почему важны эти шаблоны
Прокси добавляют сквозное поведение, проверку, журналирование, значения по умолчанию и контроль доступа, не засоряя исходный объект или код, который его вызывает. Именно так реактивные фреймворки отслеживают изменения state. Используйте прокси, когда нужен прозрачный перехват.
const observed = new Proxy({ n: 0 }, {
set(t, p, v, r) {
const ok = Reflect.set(t, p, v, r);
console.log(p + ' is now ' + t[p]);
return ok;
}
});
observed.n = 1;
observed.n = 2;Быстрая проверка
Какой перехватчик прокси следует использовать, чтобы отклонить недопустимые значения до их сохранения?
Итоги: практические случаи применения прокси
Вы применили прокси для решения реальных задач:
- Проверка в перехватчике set отклоняет некорректные данные.
- Журналирование отслеживает чтение и запись через
Reflect. - Значения по умолчанию и виртуальные свойства реализуются в перехватчике get.
- Представления только для чтения, подсчёт обращений и строгая проверка опечаток прозрачно оборачивают объекты.
Часто задаваемые вопросы
Урок «Практические сценарии применения Proxy» бесплатный?
Да — полный текст урока «Практические сценарии применения Proxy» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс JavaScript Academy, подпишись на CoddyKit PRO. Курс JavaScript Academy содержит 4 уроков всего.
Чему я научусь в уроке «Практические сценарии применения Proxy»?
Создавайте объекты для проверки данных, logging и реактивности. Ты практикуешь JavaScript Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.
Нужен ли мне опыт, чтобы начать JavaScript Academy?
Предыдущий опыт не требуется. JavaScript Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 4 из 4.
Сколько времени занимает урок «Практические сценарии применения Proxy»?
Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.
Можно ли писать и запускать код в этом уроке JavaScript Academy?
Да. Каждый урок JavaScript Academy включает встроенный редактор кода, поэтому ты пишешь и запускаешь реальный код прямо в браузере и получаешь моментальную обратную связь от AI — локальная установка не требуется.
Все уроки этого курса
- Создание Proxy
- Ловушки get и set
- API Reflect
- Практические сценарии применения Proxy