[Tạo server Node API : Vue.js + Express + MySQL] Quick Start - Part 3 : Mix All - Phát triển tính năng đăng nhập/đăng ký thành viên


Chúng ta đã bàn về Vue.js và Express ở Part1, Express và MySQL ở Part2.

Và cuối cùng ở Part3 này, tôi sẽ giải thích những code chủ yếu để tạo tính năng đăng ký thành viên và login đơn giản bằng việc sử dụng cả Vue.js, Express, MySQL.


Đăng ký

Đây là form đơn giản để nhận 3 data là ID, tên, password. Ở front-end sẽ tạo component SignUp.vue.

Ở mỗi trang nhập thì đều cho v-model directive rồi binding data nhận được. Khi phát sinh click event tại button đăng ký thì sẽ tiến hành signUp method.

<div class="input_row">
    <label for="id">ID</label>
    <input type="text" id="id" v-model="user.userid">
</div>
<div class="input_row">
    <label for="name">Name</label>
    <input type="text" id="name" v-model="user.name">
</div>
<div class="input_row">
    <label for="password">Password</label>
    <input type="password" id="password" v-model="user.password">
</div>
<button :click="signUp">Sign up</button>

Chuẩn bị một đối tượng tên là user trên data của component. Trong đối tượng này có thuộc tính userid, name, password để có thể lưu ID, tê, password.

data: function () {
    return {
        user: {
            userid: '',
            name: '',
            password: ''
        }
    }
},

Trong signUp method, gọi /api/users/signUp bằng axios rồi lưu data (this.user) đã nhập vào đối tượng. Nếu được xử lý ổn định, hiện message thành công và cho di chuyển tới trang login, còn nếu thất bại thì hiện message lỗi.

methods: {
    signUp: function (event) {
        this.$http.post('/api/users/signUp', { 
           user: this.user
        })
        .then((res) => {
            if (res.data.success == true) {
                alert(res.data.message);
                this.$router.push('/login') 
            }
            if (res.data.success == false) {
                alert(res.data.message);
            }
        })
        .catch(function (error) {
            alert('error')
        })
    }
}

Tiếp theo sẽ là phần cho vào routes/users.js của back-end.
Sau khi lưu data đã được nhập vào đối tượng user, nếu như không có data với ID tương tự trong DB thì sẽ cho vào DB, còn nếu không như vậy thì sẽ cung cấp message lỗi.

Khi cho data user vào DB, sẽ dùng package tên là bcrypt để mã hóa password.

router.post('/signUp', function (req, res) {
    const user = {
        'userid': req.body.user.userid,
        'name': req.body.user.name,
        'password': req.body.user.password
    };
    connection.query('SELECT userid FROM users WHERE userid = "' + user.userid + '"', function (err, row) {
        if (row[0] == undefined){ //  동일한 아이디가 없을경우,
            const salt = bcrypt.genSaltSync();
            const encryptedPassword = bcrypt.hashSync(user.password, salt);
            connection.query('INSERT INTO users (userid,name,password) VALUES ("' + user.userid + '","' + user.name + '","' + encryptedPassword + '")', user, function (err, row2) {
                if (err) throw err;
            });
            res.json({
                success: true,
                message: 'Sing Up Success!'
            })
        }
        else {
            res.json({
                success: false,
                message: 'Sign Up Failed Please use anoter ID'
            })
        }
    });
});

Login

Tạo login.vue trên front-end và tạo form như code dưới đây.

<div class="input_row">
    <label for="id">ID</label>
    <input type="text" id="id" v-model="user.userid">
</div>
<div class="input_row">
    <label for="password">Password</label>
    <input type="password" id="password" v-model="user.password">
</div>
<button v-on:click="login">Login</button>
<a href="/signUp">Sign up</a>

Phần Script gần như giống với đăng ký.

data: function () {
    return {
        user: {
            userid: '',
            password: ''
        }
    }
},
methods: {
    login: function (event) {
        this.$http.post('/api/users/login', {
        user: this.user
    })
    .then(
        (res) => {  //log-in succeed
            alert(res.data.message);
        },
        (err) => { // show error
            alert('Login failed! please check your id or password');
        })
        .catch(err => {
            alert(err);
        })
    }
}

Trong users.js của backend sẽ tìm kiếm người dùng giống với ID đã nhập. Nếu như có data thì sẽ check thêm password một lần nữa.

router.post('/login', function (req, res) {
    const user = {
        'userid': req.body.user.userid,
        'password': req.body.user.password
    };
    connection.query('SELECT userid, password FROM users WHERE userid = "' + user.userid + '"', function (err, row) {
        if (err) {
            res.json({ // If there is no matching ID
                success: false,
                message: 'Login failed please check your id or password!'
            })
        }
        if (row[0] !== undefined && row[0].userid === user.userid) {
            bcrypt.compare(user.password, row[0].password, function (err, res2) {
                if (res2) {
                    res.json({ // log-in succeed
                        success: true,
                        message: 'Login successful!'
                    })
                }
                else {
                    res.json({ // If there is a matching ID, but the password is wrong
                        success: false,
                        message: 'Login failed please check your id or password!'
                    })
                }
            })
        }
    })
});

Kiểm tra thông tin người dùng

Đây là trang có thể kiểm tra ID, tên của người dùng đã đăng ký.

Tạo userList.vue component trong Front-end. Gọi /api/users/, sau khi nhận thông tin người dùng từ back-end sẽ lưu array user.

data () {
    return {
        users: []
    }
},
created () {
    this.$http.get('/api/users')
    .then((response) => {
        this.users = response.data
    })
}

Lặp lại bằng với số lượng data trong users rồi xuất ra số, ID, tên.

<div v-for="(user, index) in users" :key="index" class="user-wrap">
    <h2>No. {{index + 1}}</h2>
    <dl>
        <dt>아이디</dt>
        <dd>{{user.userid}}</dd>
        <dt>이름</dt>
        <dd>{{user.name}}</dd>
    </dl>
</div>

users.js của back-end xử lý lấy toàn bộ data có trong bảng (users).

router.get('/', function (req, res) {
    connection.query('SELECT * FROM users', function (err, rows) {
        if (err) throw err;
        res.send(rows);
    });
});

Mặc dù chưa được đề cập trong bài viết này tuy nhiên nếu như thêm tính năng kiểm tra tính hợp lệ (validation test), session check thì có thể tạo ra tính năng đăng ký thành viên/login hoàn hảo hơn.


Thông tin series


🔍 Chúng tôi đang tìm kiếm FE Developer tài năng đồng hành cùng với Hivelab.

Comments

Popular posts from this blog

[React.js trong thực tiễn] Part3 : Tạo list gọi data sử dụng axios

[Activity] Một ngày tới thăm công ty mẹ Hivelab

[Activity] Hành trình du lịch Hàn Quốc của nhân viên Hivelab Vina