3 months ago by drax7

I have a small project where I use Laravel and Vue for some interactions, a simple non SPA app. I am passing an array of items from Laravel template to Vue component like this:

<extras :items="{{ json_encode($data) }}"></extras>

In Vue component I am listing all this items, and using another child component alert that I use for modal where a user can delete an item. This is the extras component:

<template>
  <div>
    <div v-for="item in extras" :key="item.id" class="media row">
      <div class="media-left col-sm-3">
        <a href="#">
          <img v-if="item.image_path != ''" class="media-object" :src="item.image_path" :alt="item.title">
        </a>
      </div>
      <div class="media-body col-sm-6">
        <h4 class="media-heading">{{ item.title }}</h4>
        <p>{{ item.description }}</p>
      </div>
      <div class="col-sm-3 action-buttons">
        <a class="btn btn-info" :href="`/extras/${item.id}/edit`" role="button">Rediger</a>
        <alert :id="item.id"></alert>
      </div>
    </div>
  </div>
</template>
<script>
export default {
  props: ['items'],
  data () {
    return {
      extras: []
    }
  },
  created() {
      this.extras = this.items;
      this.$eventHub.$on('extras.delete',(id) => {
          this.extras = this.extras.filter(function(el) {
            return el.id !== id;
          });
      })
  }
}
</script>

And this is the alert component where I delete an item:

<template>
  <div>
    <a @click="openSimplert" class="btn btn-danger" role="button">Slett</a>
    <div :id="id" @click="closeSimplert" :class="`close-${id}`" class="modal">
      <div class="modal-content">
        <span :class="`close-${id}`" @click="closeSimplert" class="close" >&times;</span>
        <p>Er du sikker?</p>
        <div class="row">
          <div class="col-md-6">
            <button @click="deleteAction" type="button" class="btn btn-danger">Ja, slett</button>
          </div>
          <div class="col-md-6">
            <button @click="closeSimplert" type="button" :class="`close-${id}`" class="btn btn-info">Avbryt</button>
          </div>
        </div>
      </div>
    </div>
  </div>
</template>
<script>
export default {
  props: ['id'],
  data () {
    return {
      modal: {},
      close: {},
    }
  },
  mounted() {
    this.modal = document.getElementById(this.id);
  },
  methods: {
    openSimplert () {
      this.modal.style.display = "block";
    },
    closeSimplert (event) {
      let closeTarget = event.target.classList.contains(`close-${this.id}`);
      if (closeTarget) {
        this.modal.style.display = "none";
      }
    },
    deleteAction() {
      let url = `extras/${this.id}`;
      let self = this;
      axios.delete(url)
        .then(() => self.$eventHub.$emit('extras.delete', this.id))
        .catch(function (error) {
          if (error.response) {
            console.log(error.response.data);
            console.log(error.response.status);
          }
        });
      this.modal.style.display = "none";
    }
  }
}
</script>

I use eventhub for emitting the events between alert and extras component. The problem I have is that when I delete an item, item is removed from the list immediately on the list that I render, but if I go to another page, and come back again to the page with extras component, the list has the item that was deleted, only on refresh you can see that it was removed. Is there a way I can somehow persist the new items array on delete without using Vuex for state management?

3 months ago by Adam milou

Try to set on the created hook

this.extras = this.extras.length || this.items;

Sign in or create an account to reply to this topic.