Vue μμ Error Boundaryλ‘ μλ¬ μ²λ¦¬νκΈ°
π Error Boundary λ?
μ΄μ μ μ κΉ React
곡λΆν λ 곡μ λ¬Έμμ Error Boundary
λΌλ κΈ°λ²μ΄ μκ°λμ΄ μμμ΅λλ€.
Error Boundary
λ μ»΄ν¬λνΈμμ λ°μν μλ¬λ₯Ό λ€λ£¨λ νλμ λ°©λ²μΌλ‘
μλ¬λ₯Ό μ²λ¦¬νλ μ»΄ν¬λνΈ(Error Boundary
)λ₯Ό λ§λ€μ΄ μ±μ μ€νμ λ¬Έμ κ° μκΈ°μ§ μλλ‘ νλ κ²μ
λλ€.
Vue
μλ ν΄λΉ κΈ°λ²μ΄ μμκΉ κΆκΈν΄μ μ°Ύμλ΄€μλλ° μ΄λ₯Ό μκ°νλ κΈμ΄ μμ΄μ μ 리ν΄λ΄€μ΅λλ€.
π Vue μμ Error Boundary μ¬μ©νκΈ°
Vue 2.5 λ²μ μμλ errorCaputred
λΌλ ν
μ μ§μνκΈ° μμνμ΅λλ€.
ν΄λΉ ν μμλ μμ μ»΄ν¬λνΈμμ λ°μν μλ¬λ₯Ό κ°μ§ν΄ μ²λ¦¬ν μ μμ΅λλ€.
Error Boundary
λ₯Ό ꡬννλ λ°©λ²μ λ€μκ³Ό κ°μ΅λλ€.
λ¨Όμ errorCaptured
ν
μ μ¬μ©ν΄ Error Boundary
μ»΄ν¬λνΈλ₯Ό μ μν©λλ€.
// ErrorBoundary.vue
<script lang="ts">
import { Component, Vue } from 'vue-property-decorator'
@Component({
name: 'ErrorBoundary',
})
export default class ErrorBoundary extends Vue {
private hasError = false;
public errorCaptured () {
this.hasError = true
}
public render(h: any) {
return this.hasError ? h('li', 'something wrong') : this.$slots.default[0];
}
}
</script>
κ·Έλ¦¬κ³ μΌλΆλ‘ μλ¬λ₯Ό λ°μμν€λλ‘ λ λλ§νλ μμ λ₯Ό μμ±ν©λλ€.
// CarListItem.vue
<template>
<li>
μ΄λ¦: {{ carInfo.name }}
κ°κ²© : {{ numberWithCommas(carInfo.price) }}
</li>
</template>
<script lang="ts">
import { Component, Vue, Prop } from 'vue-property-decorator'
@Component({
name: 'CarListItem'
})
export default class CarListItem extends Vue {
@Prop({ required: true }) readonly carInfo!: { id: number; name: string; price: number; }
public numberWithCommas(x: number) {
return x.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ",");
}
}
</script>
// CarList.vue
<template>
<ul>
<template v-for="carInfo in carInfos">
<error-boundary :key="carInfo.id">
<car-list-item :carInfo="carInfo" />
</error-boundary>
</template>
</ul>
</template>
<script lang="ts">
import { Component, Vue } from 'vue-property-decorator'
import CarListItem from './CarListItem.vue'
import ErrorBoundary from './ErrorBoundary.vue'
@Component({
name: 'CarList',
components: { CarListItem, ErrorBoundary }
})
export default class CarList extends Vue {
private carInfos = [
{ id: 1, name: 'a', price: null },
{ id: 2, name: 'b', price: 1232321 },
{ id: 3, name: 'c', price: 123212323 },
]
}
</script>
μμ μμ null
μ λν΄μ μ κ·μμ μνν μ μκΈ° λλ¬Έμ μλ¬κ° λ°μνκ³ ,
ErrorBoundary
λλΆμ UI Fallback μ μ§μ ν μ μκ² λ©λλ€.
νλ©΄μλ λ€μκ³Ό κ°μ΄ λμ€κ² λ©λλ€.
π Vue μμ μλ¬ λ°μ κ·μΉ
Vue μλ μ μ config.errorHandler
κ° μ‘΄μ¬νμ¬ λ°μν λͺ¨λ μλ¬λ ν΄λΉ νΈλ€λ¬λ‘ μ²λ¦¬ κ°λ₯ν©λλ€.
μ΄λ₯Ό ν΅ν΄ ν κ³³μμ μλ¬μ λν μ²λ¦¬μ ν΅κ³λ±μ μνν μ μκ²λ©λλ€.
λ§μ½ errorCaptured
ν
μ΄ μ‘΄μ¬νλ€λ©΄ λͺ¨λ errorCaptured
ν
μ΄ νΈμΆλλ©°
μ΅μ’
μ μΌλ‘ config.errorHandler
μ λλ¬ν©λλ€.
λ§μ½ errorCaptured
μμ false
λ₯Ό λ°ννλ€λ©΄ μλ¬κ° μ λ¬λλ κ²μ λ§μ μ μμ΅λλ€.
π μ μ μ¬ν
DOM μ΄λ²€νΈ νΈλ€λ¬
Dom
μ μ§μ v-on
μΌλ‘ μ΄λ²€νΈ νΈλ€λ¬λ₯Ό ν λΉν λ€ ν΄λΉ νΈλ€λ¬μμ λ°μν μλ¬λ
Error Boundary
μμ κ°μ§νμ§ λͺ»νλ λ¬Έμ κ° μμ΅λλ€.
ν΄λΉ μ΄μμ λν΄μ μ μλ μ¬νμ΄ μ΄λ―Έ Github μ μ‘΄μ¬νλλ°..
Vue μ μ£Όμ κ°λ°μ Evan You
λ λ€μκ³Ό κ°μ΄ λ€ κ°μ§ κ²½μ°μ λν΄μ errorCaputred
λ₯Ό ν΅ν΄
μ²λ¦¬ν μ μλ€κ³ μΈκΈνμ΅λλ€.
- render functions
- watcher callbacks
- lifecycle hooks
- component event handlers
PR
λ μ²λ¦¬λμκ³ ν΄μ ν
μ€νΈ ν΄λ΄€λλ Dom
μ ν λΉλ μ΄λ²€νΈ νΈλ€λ¬ μλ¬λ errorCaptured
μμ
μ²λ¦¬λ₯Ό λͺ»νλ κ²μΌλ‘ 보μ λλ€. (μ΄ λΆλΆμ μΆκ°μ μΈ νμΈμ΄ νμν΄λ³΄μ)
ν¨μν μ»΄ν¬λνΈ μ¬μ© μ
Vue μμλ ν¨μν μ»΄ν¬λνΈλΌλ κΈ°λ₯μ μ 곡ν©λλ€.
ν¨μν μ»΄ν¬λνΈλ eager-render
λκΈ° λλ¬Έμ κ°μ template
μ€μ½νμ μλ λ€λ₯Έ μ»΄ν¬λνΈμ
errorCaptured
μμ μλ¬λ₯Ό λ°μ μ²λ¦¬ν μ μμ΅λλ€.
μ΄λ Vue μ ν¨μν μ»΄ν¬λνΈμ μ€κ³ λ°©μμ λ°λ₯Έ κ²°κ³Όλ‘
Vue μ ν¨μν μ»΄ν¬λνΈ μ€κ³ κ΅¬μ‘°κ° λ³κ²½λμ§ μλ μ΄μ λ³νμ§ μμ κ²μΌλ‘ 보μ λλ€.
π μ°Έκ³ μλ£
'π archive' μΉ΄ν κ³ λ¦¬μ λ€λ₯Έ κΈ
[Vue.js] μμμ ν¨κ» 보λ λμ μ»΄ν¬λνΈ (0) | 2022.03.01 |
---|---|
[Vue.js] computed μμ± μ¬μ© μ μ£Όμν μ λ€ (0) | 2022.02.23 |
[Vue.js] ν¨μν μ»΄ν¬λνΈ μ΄λͺ¨μ λͺ¨ (0) | 2022.02.20 |
[Vue.js] v-deep μμ±μ λν΄μ (0) | 2022.02.20 |
[Vue.js] mixin μ½λ μ€νμΌ κ°μ΄λ (0) | 2022.02.20 |
π¬ λκΈ