这是最后一部分,我们构建了两个API路由,我们可以返回一个book列表,还可以通过id返回特定book的信息。还用了entities获取我们想要的数据,但这还不够。
所以在最后的这一部分,我们将会看到如何使用entities的嵌套来获取想要的数据。
我们的API目录现在是这个样子滴:
.app
.api
.book_store
.entities
- book.rb
.v1
- books.rb
- base.rb
添加flows资源
我们有两个模型,book和flow。一个book下有多个flows。所以我们需要在book资源中嵌套flows。
在 books.rb 文件中中,我们的最后一个API后添加如下代码:
resource :flows do
desc 'Create a flow.'
params do
requires :flow, type: Hash do
requires :newStock, type: Integer, desc: 'New Stock.'
requires :previousStock, type: Integer, desc: 'Previous Stock.'
end
end
post do
@book = Book.find(params[:id])
@flow = Flow.new(params[:flow])
@flow = [@book](http://twitter.com/book).flows.create!(params[:flow])
@book.update(stock: @flow.newStock)
end
end
最后我们的book.rb会变成这个样子:
module BookStore
module V1
class Books < Grape::API
version 'v1', using: :path
format :json
prefix :api
resource :books do
desc 'Return list of books'
get do
books = Book.all
present books
end
desc 'Return a specific book'
route_param :id do
get do
book = Book.find(params[:id])
present book, with: BookStore::Entities::Book
end
resource :flows do
desc 'Create a flow.'
params do
requires :flow, type: Hash do
requires :newStock, type: Integer, desc: 'New Stock.'
requires :previousStock, type: Integer, desc: 'Previous Stock.'
end
end
post do
@book = Book.find(params[:id])
@flow = Flow.new(params[:flow])
@flow = @book.flows.create!(params[:flow])
@book.update(stock: @flow.newStock)
end
end
end
end
end
end
end
再检查一下我们的API路由:
rails grape:routes
GET | /api/:version/books(.json) | v1 | Return list of books
GET | /api/:version/books/:id(.json) | v1 | Return a specific book
POST | /api/:version/books/:id/flows(.json) | v1 | Create a flow.
现在我们创建了一个新的路由,允许我们对某一特定book添加flow。
添加flow entity
如果现在尝试对某一book创建flow是可以成功的,但是我们通过地址http://localhost:3000/api/v1/books/1并不能访问book下的flow。因此实现这个功能我们需要添加一个flow entity。
touch app/api/book_store/entities/flow.rb
文件中加入如下代码:
module BookStore
module Entities
class Flow < Grape::Entity
expose :newStock
expose :previousStock
end
end
end
现在我们添加好了flow entity,接下来我们要在book entity中添加新的代码,打开app/api/book_store/entities/book.rb文件并且加入如下代码:
expose :flows, using: BookStore::Entities::Flow
现在我们在浏览器访问 http://localhost:3000/api/v1/books/1:
{"isbn":8880548713,"title":"Telekinesis","stock":4234,"flows":[{"newStock":4314,"previousStock":234},{"newStock":1585,"previousStock":1762},{"newStock":2537,"previousStock":2913},{"newStock":626,"previousStock":1788},{"newStock":1435,"previousStock":2011}]}
现在我们来添加book列表的entity
touch app/api/book_store/entities/index.rb
module BookStore
module Entities
class Index < Grape::Entity
expose :isbn
expose :title
expose :stock
end
end
end
并将entity应用到api当中:
present books, with: BookStore::Entities::Index
新建flow
我们构建了一个方法去新建flow,但是我们仍没有去添加它。我们需要在终端通过curl请求添加。
curl -i -X POST -H 'Content-Type: application/json' -d '{ "flow": { "newStock": 10, "previousStock": 12 } }' http://localhost:3000/api/v1/books/1/flows
如果不出意料的话在终端中会返回如下类似的结果:
HTTP/1.1 201 Created
Content-Type: application/json
ETag: W/"b5bea41b6c623f7c09f1bf24dcae58eb"
Cache-Control: max-age=0, private, must-revalidate
X-Request-Id: 152aafc8-5c74-4fdf-b12e-d2c6937ff20b
X-Runtime: 0.011693
Content-Length: 4
当然也可以使用postman来测试我们的api,这样你就创建了第一个flow啦😊~
网友评论