- API 路由统一: 移除 /api/h5/,统一 /api/pms/ 入口 - 二进制改名: api-server -> pms-api(与服务名一致) - nginx: 合并 /api/ + /pms/api/ 为 /api/pms/ - 新增 docs/API.md 接口文档 - 后端: CabinetDetail 增加 rssi/pow_fail/address/soc 等字段 - Redis 管道批量读取仓体实时数据(SOC/电压/电流/功率) - DB: 所有 TIMESTAMP 列改为 DATETIME(修复类型不匹配) - 用户管理: 新增创建时间/修改时间列,状态改用 Switch - 角色管理/用户管理: 操作按钮改为图标 - PC 设备详情: 基本信息补全 RSSI/ICCID/电源/地址 - PC 卡片: 通道统计改用 Lucide 图标,颜色统一 - PC 二维码: canvas 渲染,含编号文字,支持右键下载 - H5: 按 uni-app 规范修正导航(navigateTo 替代 reLaunch) - H5: 详情页加返回导航条 - H5: 扫码支持摄像头(jsQR)+ ?id= 参数 - H5: 底部 tabBar 在所有页面常显 - H5: 首页统计改为 6 项(设备/通道/空闲/充电/充满/故障) - H5: 下拉刷新 / 上拉加载 - 产品首页: 添加业务联系 - 文档: 清理过时文件,补充缺失规范章节
4.9 KiB
4.9 KiB
title, impact, impactDescription, type, tags
| title | impact | impactDescription | type | tags | |||||
|---|---|---|---|---|---|---|---|---|---|
| Composition and Options API Can Coexist in Same Component | LOW | Understanding coexistence helps gradual migration and library integration | best-practice |
|
Composition and Options API Can Coexist in Same Component
Impact: LOW - Vue 3 allows using both APIs in the same component via the setup() option. This is useful for gradual migration of existing Options API codebases or integrating Composition API libraries into Options API components.
However, this should be a transitional pattern. For new code, pick one API style and stick with it.
Task Checklist
- Only mix APIs when migrating existing code or integrating libraries
- Use
setup()option (not<script setup>) when mixing with Options API - Return refs/reactive from setup to make them available to Options API code
- Avoid mixing long-term - plan to fully migrate eventually
- Understand that Options API
thisis NOT available insetup()
Using Composition API in Options API Component:
import { ref, computed, onMounted } from 'vue'
import { useExternalLibrary } from 'some-composition-library'
export default {
// Options API parts
data() {
return {
legacyData: 'from options api'
}
},
computed: {
legacyComputed() {
// Can access both Options API data AND setup() returned values
return this.legacyData + ' - ' + this.newFeatureData
}
},
methods: {
legacyMethod() {
// Can call methods from both APIs
this.composableMethod()
}
},
// Composition API via setup()
setup() {
// Use composition library that doesn't have Options API equivalent
const { data: libraryData, doSomething } = useExternalLibrary()
// Create new reactive state with Composition API
const newFeatureData = ref('from composition api')
const newComputed = computed(() =>
newFeatureData.value.toUpperCase()
)
function composableMethod() {
newFeatureData.value = 'updated'
}
// IMPORTANT: Return values to make them available to Options API
return {
libraryData,
doSomething,
newFeatureData,
newComputed,
composableMethod
}
}
}
Common Migration Pattern:
// Step 1: Original Options API component
export default {
data() {
return {
users: [],
loading: false
}
},
methods: {
async fetchUsers() {
this.loading = true
this.users = await api.getUsers()
this.loading = false
}
},
mounted() {
this.fetchUsers()
}
}
// Step 2: Extract logic to composable, use via setup()
import { useUsers } from '@/composables/useUsers'
export default {
data() {
return {
// Keep some Options API data during migration
selectedUserId: null
}
},
computed: {
selectedUser() {
// Mix Options API computed with Composition API data
return this.users.find(u => u.id === this.selectedUserId)
}
},
setup() {
// New logic in Composition API
const { users, loading, fetchUsers } = useUsers()
return { users, loading, fetchUsers }
},
mounted() {
this.fetchUsers() // Available from setup()
}
}
// Step 3: Fully migrate to <script setup>
<script setup>
import { ref, computed, onMounted } from 'vue'
import { useUsers } from '@/composables/useUsers'
const { users, loading, fetchUsers } = useUsers()
const selectedUserId = ref(null)
const selectedUser = computed(() =>
users.value.find(u => u.id === selectedUserId.value)
)
onMounted(() => fetchUsers())
</script>
Important Limitations:
export default {
data() {
return { optionsData: 'hello' }
},
setup(props, context) {
// WRONG: 'this' is NOT available in setup()
console.log(this.optionsData) // undefined!
// CORRECT: Access props and context via parameters
console.log(props.someProp)
console.log(context.attrs)
console.log(context.emit)
// To access Options API data from setup,
// you generally can't - they're in separate scopes
// The Options API CAN access setup's returned values though
return { /* ... */ }
}
}
When to Use This Pattern
- Migrating large codebase: Migrate piece by piece without rewriting everything
- Integrating libraries: Some libraries (like VueUse) are Composition API only
- Team transition: Let teams learn Composition API gradually
- Options API components that need one composable: Quick integration
When NOT to Use This Pattern
- New components: Just use
<script setup>from the start - Simple components: Not worth the mental overhead
- Long-term: Plan to fully migrate; mixing adds complexity