Skip to content

Regras Prioridade D: Use com Cautela ​

Algumas funcionalidades do Vue existem para acomodar casos extremos raros ou suavizar migrações de uma base de código legado. Entretanto, ao serem utilizadas excessivamente, elas podem tornar o seu código mais difícil de manter ou até mesmo se tornarem uma fonte de bugs. Estas regras demonstram funcionalidades possivelmente arriscadas, descrevendo quando e porquê elas devem ser evitadas.

Seletores de elemento com scoped ​

Seletores de elemento devem ser evitados com scoped.

Prefira seletores de classe em vez de seletores de elemento nos estilos scoped, porque um grande número de seletores de elemento diminuem a velocidade.

Explicação Detalhada

Para definir estilos em escopo, o Vue adiciona um atributo único aos elementos componentes, algo como data-v-f3f3eg9. Então os seletores são modificados para que apenas elementos correspondentes com este atributo sejam selecionados (e.g. button[data-v-f3f3eg9]).

O problema é que um grande número de seletores elemento-atributo (e.g. button[data-v-f3f3eg9]) serão consideravelmente mais lentos do que seletores classe-atributo (e.g. .btn-close[data-v-f3f3eg9]), então seletores de classe devem ser escolhidos sempre quando possível.

Ruim

template
<template>
  <button>×</button>
</template>

<style scoped>
button {
  background-color: red;
}
</style>

Bom

template
<template>
  <button class="btn btn-close">×</button>
</template>

<style scoped>
.btn-close {
  background-color: red;
}
</style>

Comunicação pai-filho implícita ​

Props e eventos devem ser preferíveis para a comunicação entre componentes pai-filho, ao invés de this.$parent ou de realizar mutações em props.

Uma aplicação Vue ideal segue props para baixo, eventos para cima. Manter-se a esta convenção tornará os seus componentes mais fáceis de se entender. Entretanto, existem casos extremos em que a mutação de props ou this.$parent pode simplificar dois componentes já profudamente acoplados.

O problema é, há muitos outros casos simples onde esses padrões podem ser convenientes. Cuidado: não fique tentando a trocar simplicidade (estar apto a entender o fluxo do seu estado) por conveniência a curto-prazo (escrever menos código).

Ruim

js
app.component('TodoItem', {
  props: {
    todo: {
      type: Object,
      required: true
    }
  },

  template: '<input v-model="todo.text">'
})
js
app.component('TodoItem', {
  props: {
    todo: {
      type: Object,
      required: true
    }
  },

  methods: {
    removeTodo() {
      this.$parent.todos = this.$parent.todos.filter(
        (todo) => todo.id !== vm.todo.id
      )
    }
  },

  template: `
    <span>
      {{ todo.text }}
      <button @click="removeTodo">
        ×
      </button>
    </span>
  `
})

Bom

js
app.component('TodoItem', {
  props: {
    todo: {
      type: Object,
      required: true
    }
  },

  emits: ['input'],

  template: `
    <input
      :value="todo.text"
      @input="$emit('input', $event.target.value)"
    >
  `
})
js
app.component('TodoItem', {
  props: {
    todo: {
      type: Object,
      required: true
    }
  },

  emits: ['delete'],

  template: `
    <span>
      {{ todo.text }}
      <button @click="$emit('delete')">
        ×
      </button>
    </span>
  `
})
Regras Prioridade D: Use com Cautela has loaded