Paulund

VueJS CRUD - Edit Product Page

The Edit Product Page will be used to allow a user to edit a specific product. This needs to work off a URL like /product/edit/:id with being the product ID in the database. This component needs two data points, one to store the data for the product and the other to store the notification messages from the form.


data(){
    return{
        product:{},
        notifications:[]
    }
}

Get The Product

On the created lifecycle hook of Vue the component will need to fetch the product data with this ID.


created: function(){
    this.getProduct();
},

We then create the method getProduct to lookup the product by the route parameter ID and store this product data in the product data point. This needs to use Vue Resource library to get the product via the Vue router parameter. To access the Vue router parameter inside the component we need to use the code this.$route.params.id. On the return of this API call we then store the JSON in the product data point.


getProduct: function()
{
    this.$http.get('http://localhost:3000/api/product/' + this.$route.params.id).then((response) => {
        this.product = response.body;
    }, (response) => {
        // error message
    });
}

Update The Product

To update the product we need to call a PATCH method on the API to update a certain product with the data from the form. On the submit event of the form we're going to run a method to update the product.


<form v-on:submit.prevent="editProduct">

The editProduct method will need to validate the form to make sure everything is ok before sent to the API. Then we call the PATCH method passing in the product data in the form.


editProduct: function()
{
    // Validation
    var price = parseFloat(this.product.price);
    if(isNaN(price))
    {
        this.notifications.push({
            type: 'danger',
            message: 'Price must be a number'
        });
        return false;
    }

    this.$http.patch('http://localhost:3000/api/product/edit/' + this.$route.params.id, this.product, {
        headers : {
            'Content-Type' : 'application/json'
        }
    }).then((response) => {
        this.notifications.push({
            type: 'success',
            message: 'Product updated successfully'
        });
    }, (response) => {
        this.notifications.push({
            type: 'error',
            message: 'Product not updated'
        });
    });
}

Notification Element

To import the notification element in JavaScript we use the code.


import Notification from './notifications.vue';

Using the components options we can define the HTML tag to attach this component to.


components: {
    'notification' : Notification
}

In the HTML we can add the notification tag and pass in the notifications data by using v-bind:notifications.


<notification v-bind:notifications="notifications"></notification>

This now passes in all the data inside notifications into the notification component. ## Full HTML For Component


<template>
    <div id="update-product">
        <h1>Update Product</h1>

        <p><router-link :to="{ name: 'all_products' }">Return to products</router-link></p>

        <notification v-bind:notifications="notifications"></notification>

        <form v-on:submit.prevent="editProduct">
            <div class="form-group">
                <label name="product_id">ID</label>
                <input type="text" class="form-control" disabled v-model="product.id" id="product_id">
            </div>

            <div class="form-group">
                <label name="product_name">Name</label>
                <input type="text" class="form-control" v-model="product.name" id="product_name" required>
            </div>

            <div class="form-group">
                <label name="product_price">Price</label>
                <input type="text" class="form-control" v-model="product.price" id="product_price" required>
            </div>

            <div class="form-group">
                <button class="btn btn-primary">Update</button>
            </div>
        </form>
    </div>
</template>

<script>
    import Notification from './notifications.vue';

    export default{
        data(){
            return{
                product:{},
                notifications:[]
            }
        },

        created: function(){
            this.getProduct();
        },

        methods: {
            getProduct: function()
            {
                this.$http.get('http://localhost:3000/api/product/' + this.$route.params.id).then((response) => {
                    this.product = response.body;
                }, (response) => {

                });
            },

            editProduct: function()
            {
                // Validation
                var price = parseFloat(this.product.price);
                if(isNaN(price))
                {
                    this.notifications.push({
                        type: 'danger',
                        message: 'Price must be a number'
                    });
                    return false;
                }

                this.$http.patch('http://localhost:3000/api/product/edit/' + this.$route.params.id, this.product, {
                    headers : {
                        'Content-Type' : 'application/json'
                    }
                }).then((response) => {
                    this.notifications.push({
                        type: 'success',
                        message: 'Product updated successfully'
                    });
                }, (response) => {
                    this.notifications.push({
                        type: 'error',
                        message: 'Product not updated'
                    });
                });
            }
        },

        components: {
            'notification' : Notification
        }
    }
</script>