Search code examples
vue.jsvue-componentvue-props

How to deal with missing props?


I want to implement a props checker function, which is used to handle the situation with unexpected props problem. Below is an example,

<GrandFater :scope="scope" :id="id" v-bind="$attrs" @error="error" v-on="$listeners">
  <Father>
    <GrandSon />
  <Father/>
<GrandFather />

Then, in the component GrandSon, I will pass these two props to a function to make further process, let's say authorize. Now, what I want to do is to implement a props checker function to check whether the two props is valid. For example, the prop scope is a string, but it cannot be missed and it also cannot be an empty string.

It cannot be missed means it must be declared in <GrandFather> component, such as

<GrandFater :id="id" v-bind="$attrs" @error="error" v-on="$listeners">
  <Father>
    <GrandSon />
  <Father/>
<GrandFather />

In above example, the prop scope missed and I want to capture the error in my function.

class GrandFather extends Vue {
  @Prop({ type: String }) id!: string;

  @Prop({ type: String }) scope!: string;

  mounted(){
    if(propChecker(this)) return;
    authorize(this);
  }
}

In another JS file, I implement the propChecker like this:

export function parameterChecker(vm) {
  let error: String = "";

  switch (vm) {
    case !vm.id:
      error = "Parameter Id missing.";
      break;
    case !vm.id.trim():
      error = "Parameter Id cannot be empty.";
      break;
    case !vm.scope:
      error = "Parameter scope missing.";
      break;
    case !vm.scope.trim():
      error = "Parameter scope cannot be empty.";
      break;
    default:
      return false;
  }

  vm.$emit("error", error);

  return true;
}

But now the question is if I miss a prop, such as scope, it will report an error:

[Vue warn]: Error in mounted hook: "TypeError: Cannot read properties of undefined (reading 'trim')".

Now the question is how could I implement my goal, and why this error will happen?


Solution

  • I would recommend using the prop validation (see the website here).

    You can pass the props of your component using the props object which also contains object. Then you can either specify default parameters (if those aren't pass) or even use the required prop (which will throw an error if the props isn't pass).

    All props are optional by default, unless required: true is specified.

    Example :

    props: {
       myFirstProp: {
          type: Object,
          default: () => {scope: null},
          required: true,
       },
       mySecondProp: {
          type: String,
          default: 'defaultValue'
       },
       myThirdProp: {
          type: Boolean,
          default: true
       },
    }