使用getter修改对象属性值是否存在问题?API中布尔属性设置的最佳实践咨询
使用Getter修改对象状态:是否有最佳实践避免违反约定?
问题描述
我想在API中实现一种简单易用的方式来设置/取消设置对象的布尔类型属性,于是想到用getter语法来修改属性,示例代码如下:
class TEST{ active = true; get inactive(){ return !this.active; } get setInactive(){ this.active = false; return false; } get setActive(){ this.active = true; return true; } }
从技术层面来说,这些属性虽然是getter,但它们的名称表明其实际作用是修改属性值。以下代码运行正常:
let obj = new TEST(); console.log( obj ); obj.setInactive; console.log( obj ); obj.setActive; console.log( obj )
输出结果为:
TEST { active: true } TEST { active: false } TEST { active: true }
但我能预见到一个问题:行业内有个广泛遵循的约定——getter函数除了极少数无关紧要的情况外,绝不应该改变对象的状态。这个约定可能会导致开发者在未检查getter实际行为的情况下,就假设可以安全地遍历所有getter函数并获取其值。
所以想请教:是否有相关的最佳实践规范来避免此类用法?
回答
首先必须明确:你现在的写法严重违反了JavaScript社区的通用约定,这会给其他开发者(甚至未来的你自己)埋下巨大的坑。Getter的核心语义就是“获取值”,任何有副作用的操作(比如修改对象状态)都不应该出现在Getter里,这是共识级别的最佳实践。
针对你想要的“简单易用的布尔属性设置方式”,给你推荐几种更合规的实现思路:
1. 标准Setter方法(最稳妥)
这是最符合开发者直觉的方案,明确告诉使用者这是一个会修改状态的操作,完全不会有歧义:
class TEST { active = true; get inactive() { return !this.active; } setActive() { this.active = true; return true; } setInactive() { this.active = false; return false; } } // 使用方式 const obj = new TEST(); obj.setInactive(); // 明确的方法调用,没人会误解这是只读操作
2. 链式调用的流畅API(进阶)
如果希望API更优雅,可以让设置方法返回实例本身,支持链式操作,适合需要连续调用多个方法的场景:
class TEST { active = true; get inactive() { return !this.active; } activate() { this.active = true; return this; } deactivate() { this.active = false; return this; } } // 使用方式 const obj = new TEST(); obj.deactivate().logStatus().doSomethingElse();
3. 利用Setter语法(备选方案)
如果偏好属性式的调用风格,可以用JavaScript的setter语法,但注意setter需要配合赋值操作触发,虽然可行,但语义上不如直接调用方法清晰,不推荐作为首选:
class TEST { active = true; get inactive() { return !this.active; } set setActive(_) { this.active = true; } set setInactive(_) { this.active = false; } } // 使用方式 const obj = new TEST(); obj.setActive = null; // 通过赋值触发setter逻辑
为什么绝对不能用Getter做状态修改?
除了你提到的遍历风险,还有这些隐藏问题:
- 调试困难:当对象状态莫名改变时,很难追踪到是某个Getter调用导致的副作用
- 意外触发:在模板渲染、JSON序列化、对象克隆等场景中,框架/工具可能会自动读取所有属性,意外触发状态修改
- 违反最小惊讶原则:开发者看到Getter的第一反应是“这是只读的,不会改变任何东西”,你的写法会彻底打破这个预期
内容的提问来源于stack exchange,提问作者JohnRC
相关产品推荐
相关产品推荐

