Thứ tư, ngày 22 tháng 11 năm 2017

Xây dựng ứng dụng sử dụng Web API hỗ trợ các thao tác CRUD

Ngày đăng: 1/11/2013, 11:57:51PM | Lượt xem: 5,582
Hot!

Bài viết này nhằm hướng dẫn lập trình viên cách xây dựng các thủ tục CRUD bằng cách xây dựng HTTP Service sử dụng công nghệ ASP.NET Web API.

CRUD là “Create, Read, Update, Delete”, đó là các thao tác tương tác với CSDL gồm tạo mới, đọc dữ liệu, cập nhật và xóa. Các HTTP Service thường cài đặt CRUD thông qua các API dạng REST hoặc tựa như REST.

Chúng ta sẽ xây dựng một ứng dụng dùng để quản lý danh sách thông tin liên lạc (contacts), mỗi contact sẽ gồm có: tên, số điện thoại và email. HTTP Service mà chúng ta xây dựng sẽ hỗ trợ các phương thức như sau:

action

HTTP method

url tương ứng
Lấy danh sách tất cả các Contacts GET /api/contacts
Lấy một contact bằng id GET api/contacts/id
Tạo contact mới POST api/contacts
Cập nhật contact PUT api/contacts/id
Xóa contact DELETE api/contacts/id

Có bốn phương thức HTTP (HTTP Methods) chính có thể áp dụng vào các thao tác CRUD như sau:

·         GET: dùng để lấy tài nguyên về từ server

·         PUT: dùng để cập nhật tài nguyên, chúng ta cũng có thể sử dụng phương thức này để tạo tài nguyên mới.

·         POST: tạo tài nguyên mới.

·         DELETE: xóa tài nguyên được quy định ở chuỗi URI

Tạo dự án Web API có tên là CrudWebApiEx

Bạn cần nhớ là đã cài đặt ASP.NET MVC 4 Beta trở lên để có thể tạo được dự án Web API, ở đây chúng ta tạo dự án sử dụng ngôn ngữ lập trình C#.  Khi bạn tạo dự án ASP.NET MVC 4 Application mới, bạn lưu ý chọn Web API trong hộp thoại New ASP.NET MVC 4 Project trước khi tạo dự án.

 

Thêm model mới

Một model là một đối tượng dùng để biểu diễn dữ liệu. Trong Web API, bạn có thể dùng các đối tượng CLR để làm model, và khi trả về cho client, dữ liệu sẽ được kết xuất ra JSON  hoặc XML.

Chúng ta sẽ tạo một model có tên là Contact để lưu thông tin liên lạc.

public class Contact
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public string Phone { get; set; }
        public string Email { get; set; }
    }

Tạo IContactRepository và ContactRepository

Vì đây là một ví dụ, nên chúng ta sẽ chỉ sử dụng bộ nhớ hệ thống để lưu dữ liệu thay vì sử dụng một CSDL dữ liệu của SQL Server hay SQL CE.

Chúng ta sử dụng mẫu Repository để cài đặt các dịch vụ truy xuất dữ liệu và tách nó ra khỏi HTTP Service, như vậy sẽ giúp cho dự án chúng ta rõ ràng hơn, đơn giản hơn và dễ kiểm thử.

Cài đặt cho IContactRepository:

namespace CrudWebApiEx.Models
{
    public interface IContactRepository
    {
        IQueryable<Contact> GetAll();
        Contact Get(int id);
        Contact Add(Contact item);
        void Remove(int id);
        bool Update(Contact item);
    }
}

Cài đặt cho ContactRepository:

namespace CrudWebApiEx.Models
{
    public class ContactRepository : IContactRepository
    {
        private readonly List<Contact> _contacts = new List<Contact>();
        private int _nextId = 1;
 
        public ContactRepository()
        {
            this.Add(new Contact() { Name = "Alice", Email = "alice@example.com" });
            this.Add(new Contact() { Name = "Bob", Email = "bob@example.com" });
            this.Add(new Contact() { Name = "Charles", Email = "charles@example.com" });
        }
 
        public IQueryable<Contact> GetAll()
        {
            return _contacts.AsQueryable();
        }
        public Contact Get(int id)
        {
            return _contacts.Find(c => c.Id == id);
        }
        public Contact Add(Contact contact)
        {
            contact.Id = _nextId++;
            _contacts.Add(contact);
            return contact;
        }
        public void Remove(int id)
        {
            Contact contact = _contacts.Find(c => c.Id == id);
            _contacts.Remove(contact);
        }
        public bool Update(Contact contact)
        {
            int index = _contacts.FindIndex(c => c.Id == contact.Id);
            if (index == -1)
            {
                return false;
            }
            _contacts.RemoveAt(index);
            _contacts.Add(contact);
            return true;
        }
    }
}

Repository sẽ lưu các contact trong bộ nhớ cục bộ, do đó khi khởi động lại ứng dụng, thì toàn bộ thông tin bạn lưu sẽ biến mất. Bạn nên lưu dữ liệu ở bên ngoài như dùng SQL Server hoặc Cloud Storage. Và với Repository Pattern, bạn sẽ dễ dàng thay đổi khi cần.

Xây dựng Web API Controller (ContactsController)

Trong dự án bạn mới tạo sẽ có hai controller, HomeController và ValuesController, HomeController là controller truyền thống của ASP.NET MVC, còn ValuesController là controller kế thừa từ ApiController.

Bây giờ thì bạn hãy xóa ValuesController đi và theo các bước sau để tạo ContactsController:

Ở Solution Explorer nhấp chuột phải vào thư mục Controllers và chọn Add -> Controller

 

Ở hộp thoại Add Controller, chọn template là Empty API controller 

 

Khi đã tạo được ContactsController, chúng ta thêm một trường để lưu ContactRepository

public class ContactsController : ApiController
{
    static readonly IContactRepository _repository = new ContactRepository();
}

Các thủ tục để lấy tài nguyên

Chúng ta cần hỗ trợ hai thủ tục để lấy dữ liệu về

Phương thức để lấy danh sách các contact

public IEnumerable<Contact> GetAllContacts()
{
    return _repository.GetAll();
}
 

Do phương thức bắt đầu bởi cụm “Get” , phương thức này sẽ được ánh xạ với các requests dạng GET. Hơn nữa, phương thức này không có tham số,  do đó nó được ánh xạ với URI /api/contacts.

Dưới đây là phương thức lấy tài nguyên theo ID:

public Contact GetContact(int id)
{
    Contact contact = _repository.Get(id);
    if (contact == null)
    {
        throw new HttpResponseException(HttpStatusCode.NotFound);
    }
    return contact;
}

Phương thức này cũng có tên bắt đầu bởi “Get” nhưng nhận tham số có tên là id, do đó nó được ánh xạ với URI là /api/contact/id.

Trong trường hợp không lấy được contact với id được gởi lên tương ứng thì phương thức này sẽ gởi trả về lỗi 404 (lỗi không tìm thấy tài nguyên).

Tạo contact

Để tạo contact, client sẽ gởi một request theo phương thức POST, với thông tin của contact mới nằm trong thông điệp gởi lên.

Phương thức được cài đặt như sau:

public HttpResponseMessage<Contact> PostContact(Contact contact)
        {
            contact = _repository.Add(contact);
            var response = new HttpResponseMessage<Contact>(contact,
                HttpStatusCode.Created);
 
            string uri = Url.Route(null, new { id = contact.Id });
            response.Headers.Location = new Uri(Request.RequestUri, uri);
            return response;
        }

Trong mã cài đặt của phương thức này, chúng ta sẽ trả về HttpStatusCode là 201 (Created) và URI của tài nguyên vừa mới được tạo bằng cách sử dụng Url.Route để phát sinh ra URI tương ứng.

Cập nhật contact

Để cập nhật một tài nguyên, thì cần phải gởi request theo phương thức PUT, do đó chỉ cần định nghĩa một phương thức bắt đầu bởi “Put..”

public void PutContact(int id, Contact contact)
{
    contact.Id = id;
    if (!_repository.Update(contact))
    {
        throw new HttpResponseException(HttpStatusCode.NotFound);
    }
}

Phương thức này nhận hai tham số, id của contact, và thông tin cần cập nhật của contact. Tham số id được lấy từ đường dẫn URI và tham số contact được lấy từ thông điệp của request.

Xóa contact

Để xóa một tài nguyên, bạn cần định nghĩa phương thức bắt đầu bằng “Delete…”

public HttpResponseMessage DeleteContact(int id)
{
    _repository.Remove(id);
    return new HttpResponseMessage(HttpStatusCode.NoContent);
}
 Theo đặc tả của HTTP, phương thức Delete phải là “idempotent”, nghĩa là có thể áp dụng nhiều lần và trả về kết quả tương tự. Và như thế, thì bạn phải cài đặt làm sao, cho dù phương delete được gởi lên trong khi contact cần xóa đã bị xóa rồi thì vẫn không trả về mã lỗi.

Nếu một request dạng DELETE được xử lý thành thông, có thể trả về mã 200 (OK) và 202 (Accepted) – tức là khi việc xóa đang còn bị trì hoãn, hoặc trả về mã 204. Trong trường hợp của phương thức mà chúng ta cài đặt, phương thức sẽ trả về mã 204.

Toàn bộ phần hướng dẫn ở trên được người viết biên dịch từ trang web ASP.NET, tuy nhiên, nếu chỉ như vậy thì chúng ta sẽ chỉ mới biết cách cài đặt Http Service mà chưa nắm được cách sử dụng chúng.Trong phần tiếp theo, chúng ta sẽ được hướng dẫn để sử dụng javascript để tương tác với Http Service.

Tạo action Contact của HomeController

Chúng ta cần tạo một trang web giúp quản lý contact, và ở đây chúng ta tận dụng HomeController có sẵn:

namespace CrudWebApiEx.Controllers
{
    public class HomeController : Controller
    {
        public ActionResult Index()
        {
            return View();
        }
 
        public ActionResult Contact()
        {
            return View();
        }
    }
}

Mã HTML của Contact.cshtml

Chúng sẽ có một thẻ <div> với id là contact-list để hiển thị danh sách các contact có trên CSDL. Chúng ta cũng cần có các textbox để tạo mới hoặc cập nhật contact. Mã HTML của Contact.cshtml như sau:

<header>
    <h2>
        Contact</h2>
</header>
<div>
    <div>
        <h3>
            Contact List</h3>
        <div id="contact-list">
        </div>
    </div>
    <div>
        <h3>
            Create contact</h3>
        <p>
            Contact Name: @Html.TextBox("Name")
        </p>
        <p>
            Phone Number: @Html.TextBox("PhoneNumber")
        </p>
        <p>
            Email: @Html.TextBox("Email")
        </p>
        <div>
            <input type="button" value="Save" id="saveButton" />
        </div>
    </div>
</div>

Tới đây thì chúng ta sẽ cài đặt các hàm javascript để thực hiện các thao tác lấy contact, tạo mới, cập nhật và xóa contact.

JavaScript: Lấy danh sách contact

Chúng ta sẽ tạo một container cho các phương thức kể trên với tên là ContactsApi,

var ContactsApi = {};

Tiếp theo chúng ta sẽ cài đặt phương thức đầu tiên để tải về các contact và điền vào thẻ <div> có id là ‘contact-list’, phương thức có tên là getContacts, phương thức này là thành viên của ContactsApi:

getContacts: function () {
            $.getJSON("/api/contacts/",
                function (data) {
                    
                    $.each(data, function (key, val) {
 
                        var str = val.Name + ' - ' + val.Email;
 
                        $('<div/>', { html: str })
                            .appendTo($('#contact-list'));
                    });
                });
        },

Phương thức này sẽ sử dụng hàm getJSON của jquery để nhận dữ liệu có dạng JSON khi triệu gọi /api/contacts bằng phương thức GET sau đó sẽ hiển thị dữ liệu trong thẻ div có id là ‘#contact-list’.

Để dữ liệu được tải về khi gọi trang web chúng ta cài đặt phương thức:

$(document).ready(function () {
        ContactsApi.getContacts();
}); 

Kết quả khi chạy website sẽ được như sau:

 

JavaScript: Tạo contact

Tiếp theo chúng ta sẽ cài đặt phương thức để tạo mới contact có tên là createContact (thành viên của ContactsApi) như sau:

createContact: function (name, phone, email) {
            $.post("/api/contacts", { Name: name, Phone: phone, Email: email },
                            function (data) {
                                ContactsApi.getContacts();
                            }).error(function () { alert("error"); });
        },

Chúng ta cần nhớ rằng chúng ta cần gởi lên bằng phương thức POST để tạo mới contact, và sau khi tạo thành công thì cần phải triệu gọi hàm ContactApi.getContacts() để cập nhật danh sách mới.

Điều không may là khi triệu gọi ContactsApi.GetContacts() thì phương thức này sẽ nối thêm dữ liệu mới mà không xóa đi dữ liệu cũ. Do đó chúng ta cần điều chỉnh phương thức GetContacts bằng cách thêm dòng lệnh dưới đây vào đầu phương thức để xóa nội dung trong div ‘contact-list’

$('#contact-list').html(''); 

Tuy nhiên, chúng ta vẫn chưa hoàn thành phần việc của mình, bởi chúng ta chưa xử lý khi người dùng click chuột vào nút Save. Chúng ta sẽ thêm đoạn mã javascript sau vào trang Contact.cshtml để gắn phương thức xử lý sự kiện click chuột cho nút nhấn Save:

$('#saveButton').click(function () {
            //Get data to save
            var name = $('#Name').val();
            var phone = $('#Phone').val();
            var email = $(' #Email').val();
 
            ContactsApi.createContact(name, phone, email);
 
            //Remove all text on textboxes
            $('#Name').val('');
            $('#PhoneNumber').val('');
            $('#Email').val('');
        });

Sau đó chúng ta hãy thứ refresh trang contact và nhập thông tin của một contact bất kỳ:

 

Sau đó chúng ta hãy thứ refresh trang contact và nhập thông tin của một contact bất kỳ:

 

JavaScript: Xóa phần tử contact trong danh sách

Chúng ta cần cài đặt phương thức để xóa phần tử trong danh sách, để làm được điều đó, đầu tiên chúng ta phải xác định rằng, việc xóa contact phụ thuộc vào id của contact, do đó phương thức dùng để xóa contact trong ContactsApi phải là phương thức nhận id làm tham số. Ta có thể cài đặt phương thức deleteContact của ContactsApi như sau:

deleteContact: function (id) {
            $.ajax({
                type: 'DELETE',
                url: "/api/contacts/" + id,
                statusCode: {
                    204: function () {
                        ContactsApi.getContacts();
                    }
                }
            });
        },

Ở đây các bạn sẽ thấy một chút khác biệt, đó là chúng ta quy định phương thức gởi lên là DELETE và đồng thời, khi nhận kết quả trả về, chúng ta phải xử lý việc cập nhật lại danh sách các contact trong div ‘contact-list’ bằng cách bắt mã trả về là 204.

Tuy nhiên để xóa được contact, chúng ta cần điều chỉnh phương thức getContacts của ContactsApi để thêm thẻ a để tạo link giúp xóa Contact và đồng thời chúng ta tạo luôn liên kết để giúp cập nhật Contact, như sau:

var str = '<a href="#" onclick="javascript:ContactsApi.viewContact(\'' + val.Id + '\')">' + val.Name + '</a>'
           + ' - ' + val.Email
           + '<a href="#" onclick="javascript:ContactsApi.deleteContact(\'' + val.Id + '\')">Delete</a>';
 

Khi cập nhật javascript, khi bạn chạy thì bạn sẽ thấy giao diện trang web như sau:

 

Và khi nhấn chuột lên link delete của contact có tên là Bob, kết quả sẽ như sau:

 

JavaScript: Cập nhật Contact

Ở đoạn code cập nhật cho phương thức getContacts ở mục trên chúng ta đã thêm link liên kết giúp xem nội dung của Contact có tên là viewContact. Phương thức viewContact này sẽ lấy thông tin của contact dựa trên id và sau đó sẽ điền vào các textbox, và khi người dùng nhấn nút Save thì sẽ lưu thông tin mà người dùng cập nhật (bằng cách điều chỉnh phương thức xử lý sự kiện click của nút Save).

Cài đặt phương thức viewContact của ContactsApi:

viewContact: function (id) {
            //Get the contact by id, and  
            $.getJSON("/api/contacts/" + id,
                function (data) {
                    // On success, 'data' contains a list of products.
                    $('#Name').val(data.Name);
                    $('#PhoneNumber').val(data.Phone);
                    $('#Email').val(data.Email);
                });
        },

Và khi thử click vào contact có tên Alice chúng ta thấy nó sẽ cập nhật các textbox bên dưới như sau:

 

Vấn đề là nếu chúng ta nhấn vào nút Save nó sẽ tạo một contact mới có tên là Alice, vì thế chúng ta cần phải có một chút điều chỉnh cho ContactsApi và phương thức xử lý sự kiện click của nút Save.

Chúng ta cần tạo ra một thuộc tính có tên là currentContactId và gán cho nó giá trị mặc định là -1, nghĩa là chúng ta không có ý định cập nhật contact nào, khi click chuột vào tên của một contact, thì curentContactId sẽ có giá trị bằng id của contactId đó, và do đó khi nhấn chuột vào nút Save chúng ta có căn cứ để biết được chúng ta đang tạo mới contact hay cập nhật một contact nào đó.

 currentContactId: -1

Như vậy phương thức viewContact của Conta

ctsApi được điều chỉnh như sau:

viewContact: function (id) {
            //Get the contact by id, and  
            $.getJSON("/api/contacts/" + id,
                function (data) {
                    // On success, 'data' contains a list of products.
                    $('#Name').val(data.Name);
                    $('#PhoneNumber').val(data.Phone);
                    $('#Email').val(data.Email);
                    ContactsApi.currentContactId = data.Id;
                });
        },

Và chúng ta cài đặt lại phương thức xử lý sự kiện nhấp chuột trái của nút Save:

$('#saveButton').click(function () {
            if (ContactsApi.currentContactId == -1) {
                //Get data to save
                var name = $('#Name').val();
                var phone = $('#Phone').val();
                var email = $(' #Email').val();
 
                ContactsApi.createContact(name, phone, email);
            } else {
                //Update contact
                ContactsApi.updateContact();
            }
 
            //Remove all text on textboxes
            $('#Name').val('');
            $('#PhoneNumber').val('');
            $('#Email').val('');
        });

Ở đây chúng ta thấy rằng, trong trường hợp currentContactId có giá trị là -1 thì chúng ta sẽ gọi phương thức createContact, trong trường hợp có giá trị khác thì chúng ta sẽ gọi phương thức updateContact, và phương thức này được cài đặt như sau:

updateContact: function () {
 
            var name = $('#Name').val();
            var phone = $('#Phone').val();
            var email = $('#Email').val();
 
            $.ajax({
                type: 'PUT',
                url: "/api/contacts/" + ContactsApi.currentContactId,
                data: { Name: name, Phone: phone, Email: email },
                statusCode: {
                    404: function () {
                        alert('page not found');
                    },
                    200: function () {
                        ContactsApi.getContacts();
                        ContactsApi.currentContactId = -1;
                    }
                }
            });
        },

Phương thức updateContact gởi request theo phương thức PUT để cập nhật dữ liệu với ID truyên theo URI và sau khi thực hiện thành công sẽ gọi phương thức getContacts và cập nhật lại currentContactId với giá trị -1.

Giả sử chúng ta nhấp chuột vào contact có tên là Alice, sau đó đổi tên thành SueSue và nhấn nút Save, kết quả sẽ như sau:

 

Kết luận

Như vậy sau nhiều giờ viết ví dụ và bài viết, thì tôi đã giúp cho các bạn có được một ví dụ khá hoàn chỉnh về Web API và các thao tác CRUD. Rõ ràng việc sử dụng ASP.NET Web API giúp việc lập trình Ajax trở nên dễ dàng hơn, và chỉ với một trang web duy nhất chúng ta đã cài đặt được các thao tác tạo mới, lấy dữ liệu, cập nhất và xóa dữ liệu, thật là tuyệt!

Nguồn bài viết từ http://jou.vn/

doanhkisi
 Chia sẻ qua: 
Hot!
Ý kiến bạn đọc

These items will be permanently deleted and cannot be recovered. Are you sure?

Gallery

image

Maecenas viverra rutrum pulvinar

Maecenas viverra rutrum pulvinar! Aenean vehicula nulla sit amet metus aliquam et malesuada risus aliquet. Vestibulum rhoncus, dolor sit amet venenatis porta, metus purus sagittis nisl, sodales volutpat elit lorem…

Read more

Text Links

Thiết kế logo chuyên nghiệp Insky
DAFABET
W88 w88b.com/dang-ky-tai-khoan-w88
W88
ca do bong da online
Copyright © 2011 - 2012 vietshare.vn by phamkhuong102@gmail.com doanhkisi2315@gmail.com. All rights reserved.