lib/puppet-herald/app/api.rb in puppet-herald-0.2.0 vs lib/puppet-herald/app/api.rb in puppet-herald-0.8.0
- old
+ new
@@ -1,9 +1,10 @@
require 'sinatra/base'
require 'sinatra/namespace'
require 'puppet-herald'
require 'puppet-herald/app/configuration'
+require 'puppet-herald/models'
require 'puppet-herald/models/node'
require 'puppet-herald/models/report'
# A module for Herald
module PuppetHerald
@@ -16,55 +17,121 @@
# @return [ApiImplV1] an API impl
def initialize(app)
@app = app
end
# Creates a new report
+ #
# @param request [Sinatra::Request] an request object
# @return [Array] an response array: [code, body] or [code, headers, body]
def post_reports(request)
yaml = request.body.read
report = PuppetHerald::Models::Report.create_from_yaml yaml
body = { id: report.id }.to_json
[201, body]
end
# Get a report by its ID
+ #
# @param params [Hash] an requests parsed params
# @return [Array] an response array: [code, body] or [code, headers, body]
def get_report(params)
id = params[:id]
- report = PuppetHerald::Models::Report.get_with_log_entries(id)
+ report = PuppetHerald::Models::Report.with_log_entries(id)
status = 200
status = 404 if report.nil?
body = report.to_json(include: :log_entries)
[status, body]
end
- # Gets all nodes
+ # Gets all nodes with pagination
+ #
+ # @param request [Sinatra::Request] an request object
# @return [Array] an response array: [code, body] or [code, headers, body]
- def nodes
- nodes = PuppetHerald::Models::Node.all
- [200, nodes.to_json]
+ def nodes(request)
+ pag = paginate request
+ nodes = PuppetHerald::Models::Node.paginate(pag)
+ [200, headers(pag), nodes.to_json(methods: :no_of_reports)]
+ rescue ArgumentError => ex
+ clienterror ex
end
- # Gets a node by its ID
+ # Gets a node by its ID, with pagination
+ #
# @param params [Hash] an requests parsed params
+ # @param request [Sinatra::Request] an request object
# @return [Array] an response array: [code, body] or [code, headers, body]
- def get_node(params)
+ def get_node(params, request)
id = params[:id]
- node = PuppetHerald::Models::Node.get_with_reports(id)
+ pag = paginate request
+ node = PuppetHerald::Models::Node.with_reports(id, pag)
status = 200
status = 404 if node.nil?
- body = node.to_json(include: :reports)
- [status, body]
+ body = node.to_json(include: :reports, methods: :no_of_reports)
+ [status, headers(pag), body]
+ rescue ArgumentError => ex
+ clienterror ex
end
# Get a app's artifact information
+ #
# @return [Array] an response array: [code, body] or [code, headers, body]
def version_json
ver = {}
[:VERSION, :LICENSE, :NAME, :PACKAGE, :SUMMARY, :DESCRIPTION, :HOMEPAGE].each do |const|
ver[const.downcase] = PuppetHerald.const_get const
end
[200, ver.to_json]
end
+
+ private
+
+ # Creates headers for given pagination
+ #
+ # @param pagination [PuppetHerald::Models::Pagination] a pagination
+ # @param httpize [Boolean] if true given, will change headers to Rack format +HTTP_*+
+ # @return [Hash] a HTTP request headers
+ def headers(pagination, httpize = false)
+ keys = httpize_keys(httpize)
+ head = {
+ keys[:page] => pagination.page.to_s,
+ keys[:limit] => pagination.limit.to_s
+ }
+ head[keys[:total]] = pagination.total.to_s unless pagination.total.nil?
+ head[keys[:pages]] = pagination.pages.to_s unless pagination.pages.nil?
+ head
+ end
+
+ def httpize_keys(httpize = false)
+ map = PuppetHerald::Models::Pagination::KEYS.map do |k, str|
+ [k, httpize_key(str, httpize)]
+ end
+ Hash[map]
+ end
+
+ def httpize_key(key, httpize = false)
+ noop = ->(name) { name }
+ oper = httpize ? method(:httpize) : noop
+ oper.call key
+ end
+
+ # Creates a pagination from request
+ #
+ # @param request [Sinatra::Request] a HTTP request
+ # @return [PuppetHerald::Models::Pagination] a pagination
+ def paginate(request)
+ pkey = httpize(PuppetHerald::Models::Pagination::KEYS[:page])
+ lkey = httpize(PuppetHerald::Models::Pagination::KEYS[:limit])
+ page = request.env[pkey] ? request.env[pkey] : PuppetHerald::Models::Pagination::DEFAULT.page
+ limit = request.env[lkey] ? request.env[lkey] : PuppetHerald::Models::Pagination::DEFAULT.limit
+ PuppetHerald::Models::Pagination.new(page, limit)
+ end
+
+ def httpize(header_name)
+ upper = header_name.upcase.gsub('-', '_')
+ "HTTP_#{upper}"
+ end
+
+ def clienterror(ex)
+ err = { error: "#{ex.class}: #{ex.message}" }
+ [400, err.to_json]
+ end
end
# An API app module
class Api < Sinatra::Base
register Sinatra::Namespace
@@ -90,15 +157,15 @@
api.post_reports request
end
get '/nodes' do
content_type 'application/json'
- api.nodes
+ api.nodes request
end
get '/nodes/:id' do
content_type 'application/json'
- api.get_node params
+ api.get_node params, request
end
get '/reports/:id' do
content_type 'application/json'
api.get_report params