第4章 组件化开发与自定义组件

组件化是微信小程序架构的核心思想,面试中高频考察组件通信、插槽机制、behaviors 三大模块。本章从实际面试场景出发,拆解回答框架与避坑要点。

组件通信方式回答框架 组件通信 父子通信 兄弟通信 跨层级通信 属性传参 事件回调 自定义事件 全局事件 getApp() globalData

问答卡片1:组件通信方式

面试问题:请列举小程序中组件间通信的几种方式,并说明各自适用场景。

面试官考察点:

  • 是否理解组件层级关系下的通信差异
  • 能否区分属性传参、事件回调、全局状态等方案
  • 是否具备实际项目中的方案选型能力

回答框架:

通信类型实现方式适用场景
父→子属性传参 (properties)静态数据、初始化配置
子→父自定义事件 triggerEvent按钮点击、表单提交
兄弟事件总线 / 全局状态列表项联动
跨层级getApp()、globalData用户登录态、主题色

示例回答:(约60字)父子通信用 properties 与 triggerEvent;兄弟通信使用全局事件总线(如 app.js 中定义的事件中心);跨层级用 getApp().globalData 或 store。优先选 properties + 事件,避免滥用全局变量导致数据流混乱。

可能追问:

  • 如何实现兄弟组件之间的直接通信而不依赖全局?
  • properties 的 observer 与 watch 有什么区别?

避坑提醒:不要频繁使用 globalData 传递局部状态;子组件改变父组件属性应通过事件上报,严禁直接修改父组件数据。
组件化面试追问路径图 组件通信 数据更新性能 (setData优化) 生命周期冲突 (attached/ready) 组件复用 (behaviors) 虚拟化列表 slot插槽

问答卡片2:插槽(slot)

面试问题:小程序自定义组件中如何使用插槽?多插槽与单个插槽的区别是什么?

面试官考察点:

  • 是否掌握 <slot> 基本用法
  • 是否了解多插槽(具名插槽)的配置方式
  • 能否说明插槽与 template 的区别

回答框架:

  1. 单插槽:组件内直接用 <slot></slot> 占位
  2. 多插槽:组件配置 multipleSlots: true,使用 name 属性区分
  3. 使用限制:默认插槽只能有一个,具名插槽可多个
  4. 数据传递:插槽内容本身可访问外部数据,但组件内部无法控制插槽内数据

示例回答:(约80字)组件内用 <slot> 或 <slot name="header"> 占位,启用 multipleSlots: true 支持多插槽。父组件通过 slot="header" 分发内容。注意:插槽内容仅外部可控制,组件内无法观察其变化。

可能追问:

  • 如何向插槽内传递数据(作用域插槽)?
  • 插槽与 wx:if 结合使用时有什么陷阱?

避坑提醒:不要忘记在组件 JSON 中声明 "component": true 和 "multipleSlots": true;插槽内的组件生命周期由父组件管理,避免在子组件中监听插槽内事件。

问答卡片3:behaviors(混合)

面试问题:请解释 behaviors 的作用,以及多个 behaviors 冲突时的处理规则。

面试官考察点:

  • 是否理解 mixin 模式的优点
  • 是否清楚属性、方法、生命周期合并规则
  • 能否举例说明 behaviors 的实际使用场景

回答框架:

  1. 定义:behaviors 是代码复用单元,可包含 properties、data、methods、生命周期
  2. 合并规则:定义阶段按引入顺序,属性/方法同名时后定义的覆盖
  3. 生命周期:所有 behaviors 的钩子都会依次执行(先引入先执行)
  4. 典型场景:表单验证、日志上报、列表分页等通用逻辑

示例回答:(约70字)behaviors 类似 mixin,可将公共逻辑抽离。例如定义一个 form-validator behavior。多个 behaviors 冲突时,同名属性或方法后引入的生效,生命周期则依次全部执行。注意避免循环依赖。

可能追问:

  • 如何调试 behaviors 中覆盖的属性?
  • behaviors 与组件继承的区别?

避坑提醒:不要过度使用 behaviors 导致数据源不清;同名方法覆盖时要通过 behaviors[0].methods.methodA 手动调用原方法;尽量保持 behaviors 数量在 3 个以内。

项目案例:电商小程序商品详情页组件化重构

项目名称:「XX商城」小程序商品模块重构
业务背景:原有商品详情页代码冗余,多个页面重复实现轮播图、价格展示、规格选择等模块,维护成本高。通过组件化拆分提高复用率。
规模指标:涉及 12 个业务页面,30+ 自定义组件,日均 PV 80 万,加载速度优化 40%。
技术栈:微信小程序原生框架 + Less + MobX(全局状态)
核心难点:
  • 规格选择组件与购物车跨页面通信
  • 多插槽实现不同页面的个性化头部 banner
  • 通过 behaviors 统一管理埋点事件
面试高频追问:
  • 为什么选择 MobX 而非 globalData?
  • 组件间频繁通信导致 setData 性能瓶颈怎么处理?
  • 如何保证 behaviors 中的埋点方法不被业务组件覆盖?
可迁移回答话术:“在重构中,我们采用父子组件通信(props + events)处理基础数据流,兄弟组件通过 MobX store 同步。对于插槽场景,先将通用头部组件化,再通过 slot 暴露可定制区域。behaviors 用于抽离埋点逻辑,并在命名上加前缀避免冲突。性能上,对高频更新的数据使用 diff 后只 setData 变化部分,并利用 computed 减少计算。”
本章小结:组件化面试重点围绕“数据流 + 代码复用 + 插槽灵活性”展开。掌握三种通信方式的选型原则、多插槽配置细节、behaviors 的合并规则,即可应对 80% 的面试问题。结合项目案例展示你的组件化设计思想,会极大提升面试通过率。