闭包暴露公共接口需以函数作用域为隔离墙,仅通过返回对象提供必要能力;IIFE适用于单例,工厂函数支持多实例;返回对象即对外契约,命名应表意明确;需支持配置初始化、处理this绑定与异步时机,并提供destroy()清理资源。

在闭包中暴露公共接口,核心是用函数作用域做“隔离墙”,只把真正需要对外使用的功能,通过返回对象的属性交出去——不是所有内部东西都能露,也不是随便怎么露都行。
用 IIFE 或工厂函数划定私有边界
立即执行函数(IIFE)适合单例场景,比如全局日志器、统一请求封装;工厂函数则用于多实例,比如多个表单校验器、不同租户的配置模块。
- IIFE 内所有 let/const 声明的变量、函数默认不可见,外部只能访问 return 对象里的内容
- 工厂函数每次调用都会生成新闭包,各实例私有状态(如 cache、token、计数器)完全独立,互不干扰
- 避免把私有数据直接挂到返回对象上,例如不要写 return { data: privateCache },这等于把锁着的抽屉整个搬出去
返回对象就是你的对外契约
这个对象的每个键名,都是你向使用者承诺的能力。命名要直说“能做什么”,不说“怎么做的”。
- 行为类方法用动词开头:save、validate、reset、subscribe
- 状态或能力类用形容词或名词:isReady、version、defaults、retryCount
- 别暴露中间状态,比如不提供 getInternalCounter,而是提供 getCount 或 resetTo(0)
- 下划线前缀(如 _data)不是私有,只是命名习惯,外部仍可随意改,不能当真
支持配置初始化,让模块更灵活
硬编码初始值会让模块难复用。把配置作为参数传入,在闭包内完成初始化逻辑,同时设好默认值。
- 例如 Logger 模块接收 { level: 'warn', enabled: true },内部据此设定 level 和 enabled 变量
- 配置项要有合理默认值:config.level || 'info',降低使用门槛
- 初始化逻辑可以放在闭包开头:预加载字典、绑定事件、设置定时器等
注意 this 绑定和异步时机
暴露的方法一旦被当回调使用(比如传给 setTimeout 或 addEventListener),原始上下文容易丢失;异步操作(如 fetch)完成前,数据可能还没准备好。
- 需要保持 this 的方法,可用箭头函数、bind(this),或在返回对象里预先绑定
- 异步场景下,不要让 getData() 立刻返回未就绪的数据,应返回 Promise,或等初始化完成后再 resolve 整个模块
- 资源清理很重要,提供 destroy() 方法,在其中清除定时器、监听器、中断请求,确保卸载后能被垃圾回收

















