RealPath:
WebPath:
2017/05/21 16:18 (JST) 更新
REST API >>

モデルのCRUDをサポートするAPI

Contents

Scaffolding 機能により、特定のモデルの CRUD をサポートする API を自動生成できます。

今回はサンプルとして 掲示板作成 - モデル・DBコンテキスト に書かれている Comment および BbsDbContext を元に、API を自動生成してみます。

準備作業

掲示板作成 - モデル・DBコンテキスト を参考に、モデルとデータベースコンテキストを作成しておいてください。

API作成作業

  1. Solution Explorer 上でプロジェクト配下の Controllers フォルダを右クリック - [Add] - [Controller...] を選択。
  2. [Web API 2 Controller with actions, using Entity Framework] を選択して [Add] を押下。
  3. Add Controller ダイアログにて、
    • Model class … Comment を指定。
    • Data context class … BbsDbContext を指定。
    • Controller name … CommentsController と自動で入るはずなので、そのままにしておく。
    • [Add] を押下。

出来上がるコントローラ

Controllers/CommentsController.cs
public class CommentsController : ApiController
{
    private BbsDbContext db = new BbsDbContext();

    // GET: api/Comments
    public IQueryable<Comment> GetComments()
    {
        return db.Comments;
    }

    // GET: api/Comments/5
    [ResponseType(typeof(Comment))]
    public IHttpActionResult GetComment(int id)
    {
        Comment comment = db.Comments.Find(id);
        if (comment == null)
        {
            return NotFound();
        }

        return Ok(comment);
    }

    // PUT: api/Comments/5
    [ResponseType(typeof(void))]
    public IHttpActionResult PutComment(int id, Comment comment)
    {
        if (!ModelState.IsValid)
        {
            return BadRequest(ModelState);
        }

        if (id != comment.Id)
        {
            return BadRequest();
        }

        db.Entry(comment).State = EntityState.Modified;

        try
        {
            db.SaveChanges();
        }
        catch (DbUpdateConcurrencyException)
        {
            if (!CommentExists(id))
            {
                return NotFound();
            }
            else
            {
                throw;
            }
        }

        return StatusCode(HttpStatusCode.NoContent);
    }

    // POST: api/Comments
    [ResponseType(typeof(Comment))]
    public IHttpActionResult PostComment(Comment comment)
    {
        if (!ModelState.IsValid)
        {
            return BadRequest(ModelState);
        }

        db.Comments.Add(comment);
        db.SaveChanges();

        return CreatedAtRoute("DefaultApi", new { id = comment.Id }, comment);
    }

    // DELETE: api/Comments/5
    [ResponseType(typeof(Comment))]
    public IHttpActionResult DeleteComment(int id)
    {
        Comment comment = db.Comments.Find(id);
        if (comment == null)
        {
            return NotFound();
        }

        db.Comments.Remove(comment);
        db.SaveChanges();

        return Ok(comment);
    }

    protected override void Dispose(bool disposing)
    {
        if (disposing)
        {
            db.Dispose();
        }
        base.Dispose(disposing);
    }

    private bool CommentExists(int id)
    {
        return db.Comments.Count(e => e.Id == id) > 0;
    }
}

JavaScript による API 呼び出し例

POST (新規作成)

var params = {
    UserName: 'kobayashi',
    Body: 'Hello',
    Created: '2010-01-01'
};
fetch('/api/Comments', {
    method: 'POST',
    headers: {
        'Accept': 'application/json',
        'Content-Type': 'application/json'
    },
    body: JSON.stringify(params)
}).then(function (response) {
    return response.json();
}).then(function (comment) {
    console.log(comment.Id);
    console.log(comment.UserName);
    console.log(comment.Body);
    console.log(comment.Created);
});
結果
1
kobayashi
Hello
2010-01-01T00:00:00

GET (リストデータ取得)

fetch('/api/Comments', {
    method: 'GET',
    headers: {
        'Accept': 'application/json',
        'Content-Type': 'application/json'
    }
}).then(function (response) {
    return response.json();
}).then(function (comments) {
    console.log("Count: " + comments.length);
    comments.forEach(function(comment){
        console.log("----");
        console.log(comment.Id + ', ' + comment.UserName + ', ' + comment.Body + ', ' + comment.Created);
    });
});
結果
Count: 2
----
1, kobayashi, Hello, 2010-01-01T00:00:00
----
2, tanaka, Hi, 2017-01-01T00:00:00

GET (単体データ取得)

fetch('/api/Comments/1', {
    method: 'GET',
    headers: {
        'Accept': 'application/json',
        'Content-Type': 'application/json'
    }
}).then(function (response) {
    return response.json();
}).then(function (comment) {
    console.log(comment.Id);
    console.log(comment.UserName);
    console.log(comment.Body);
    console.log(comment.Created);
});
結果
1
kobayashi
Hello
2010-01-01T00:00:00

PUT (上書き)

var params = {
    Id: 1,
    UserName: 'kobake',
    Body: 'abcdefg',
    Created: '2011-10-05'
};
fetch('/api/Comments/1', {
    method: 'PUT',
    headers: {
        'Accept': 'application/json',
        'Content-Type': 'application/json'
    },
    body: JSON.stringify(params)
}).then(function (response) {
    console.log('done.');
});
結果
done.

DELETE (削除)

fetch('/api/Comments/2', {
    method: 'DELETE',
    headers: {
        'Accept': 'application/json',
        'Content-Type': 'application/json'
    }
}).then(function (response) {
    return response.json();
}).then(function (comment) {
    console.log(comment.Id);
    console.log(comment.UserName);
    console.log(comment.Body);
    console.log(comment.Created);
});
結果
2
tanaka
Hi
2017-01-01T00:00:00