Skip to content

Commit

Permalink
WIP
Browse files Browse the repository at this point in the history
  • Loading branch information
paulsturgess committed Oct 27, 2023
1 parent 588f382 commit 512e3ad
Show file tree
Hide file tree
Showing 15 changed files with 447 additions and 2 deletions.
2 changes: 2 additions & 0 deletions Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -13,3 +13,5 @@ gem 'solargraph'

gem 'rake'
gem 'rubocop'

gem 'pry'
3 changes: 3 additions & 0 deletions examples/config.ru
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@ require 'apia'
require 'apia/rack'
require 'core_api/base'

require 'apia-openapi'

use Apia::OpenAPI::Rack, 'CoreAPI::Base', '/core/v1/schema/openapi.json'
use Apia::Rack, CoreAPI::Base, '/core/v1', development: true

app = proc do
Expand Down
29 changes: 29 additions & 0 deletions examples/core_api/argument_sets/object_lookup.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
# frozen_string_literal: true

module CoreAPI
module ArgumentSets
class ObjectLookup < Apia::LookupArgumentSet

name 'Object Lookup'
description 'Provides for objects to be looked up'

argument :id, type: :string
argument :permalink, type: :string

potential_error 'ObjectNotFound' do
code :object_not_found
description 'No object was found matching any of the criteria provided in the arguments'
http_status 404
end

resolver do |set, request, scope|
objects = [{id: "123", permalink: "perma-123"}]
object = objects.find { |o| o[:id] == set[:id] || o[:permalink] == set[:permalink] }
raise_error 'ObjectNotFound' if object.nil?

object
end

end
end
end
5 changes: 5 additions & 0 deletions examples/core_api/base.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

require 'core_api/main_authenticator'
require 'core_api/controllers/time_controller'
require 'core_api/endpoints/test_endpoint'

module CoreAPI
class Base < Apia::API
Expand All @@ -17,12 +18,16 @@ class Base < Apia::API

get 'example/format', controller: Controllers::TimeController, endpoint: :format
post 'example/format', controller: Controllers::TimeController, endpoint: :format
post 'example/format_multiple', controller: Controllers::TimeController, endpoint: :format_multiple

group :time do
name 'Time functions'
description 'Everything related to time elements'
get 'time/now', endpoint: Endpoints::TimeNowEndpoint

get 'test/:object', endpoint: Endpoints::TestEndpoint
post 'test/:object', endpoint: Endpoints::TestEndpoint

group :formatting do
name 'Formatting'
controller Controllers::TimeController
Expand Down
16 changes: 15 additions & 1 deletion examples/core_api/controllers/time_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -9,20 +9,34 @@ module Controllers
class TimeController < Apia::Controller

name 'Time API'
description 'Returns the current time in varying ways'
description 'Returns the time in varying ways'

endpoint :now, Endpoints::TimeNowEndpoint

endpoint :format do
description 'Format the given time'
argument :time, type: ArgumentSets::TimeLookupArgumentSet, required: true
argument :timezone, type: Objects::TimeZone
field :formatted_time, type: :string
action do
time = request.arguments[:time]
response.add_field :formatted_time, time.resolve.to_s
end
end

endpoint :format_multiple do
description 'Format the given times'
argument :times, type: [ArgumentSets::TimeLookupArgumentSet], required: true
field :formatted_times, type: [:string]
action do
times = []
request.arguments[:times].each do |time|
times << time.resolve.to_s
end
response.add_field :formatted_times, times.join(", ")
end
end

end
end
end
27 changes: 27 additions & 0 deletions examples/core_api/endpoints/test_endpoint.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
# frozen_string_literal: true

require 'core_api/argument_sets/object_lookup'

module CoreAPI
module Endpoints
class TestEndpoint < Apia::Endpoint

description 'Returns the current time'
argument :object, type: ArgumentSets::ObjectLookup, required: true
field :time, type: Objects::Time, include: 'unix,day_of_week'
scope 'time'

def call
object = request.arguments[:object].resolve
response.add_field :time, get_time_now
end

private

def get_time_now
Time.now
end

end
end
end
6 changes: 5 additions & 1 deletion examples/core_api/endpoints/time_now_endpoint.rb
Original file line number Diff line number Diff line change
@@ -1,12 +1,16 @@
# frozen_string_literal: true

require 'core_api/objects/time_zone'

module CoreAPI
module Endpoints
class TimeNowEndpoint < Apia::Endpoint

description 'Returns the current time'
argument :timezone, type: Objects::TimeZone
# argument :filters, [:string]
field :time, type: Objects::Time, include: 'unix,day_of_week'
scope 'time'
scope 'time' # TODO: what does this do?

def call
response.add_field :time, get_time_now
Expand Down
11 changes: 11 additions & 0 deletions examples/core_api/objects/time_zone.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# frozen_string_literal: true

module CoreAPI
module Objects
class TimeZone < Apia::Enum

value 'Europe/London'

end
end
end
1 change: 1 addition & 0 deletions lib/apia-openapi.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
require 'apia-openapi/rack'
51 changes: 51 additions & 0 deletions lib/apia-openapi/rack.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
# frozen_string_literal: true

require 'apia-openapi/schema'

module Apia
module OpenAPI
class Rack

def initialize(app, api, path, **options)
@app = app
@api = api
@path = "/#{path.sub(/\A\/+/, '').sub(/\/+\z/, '')}"

Check failure

Code scanning / CodeQL

Polynomial regular expression used on uncontrolled data High

This
regular expression
that depends on a
library input
may run slow on strings with many repetitions of '/'.
@options = options
end

def development?
env_is_dev = ENV['RACK_ENV'] == 'development'
return true if env_is_dev && @options[:development].nil?

@options[:development] == true
end

def api
return Object.const_get(@api) if @api.is_a?(String) && development?
return @cached_api ||= Object.const_get(@api) if @api.is_a?(String)

@api
end

def base_url
@options[:base_url] || 'https://api.example.com/api/v1'
end

def call(env)
# if @options[:hosts]&.none? { |host| host == env['HTTP_HOST'] }
# return @app.call(env)
# end

unless env['PATH_INFO'] == @path
return @app.call(env)
end

schema = Schema.new(api, base_url)
body = schema.json

[200, { 'Content-Type' => 'application/json', 'Content-Length' => body.bytesize.to_s }, [body]]
end

end
end
end
Loading

0 comments on commit 512e3ad

Please sign in to comment.