roda_api_generator 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (61) hide show
  1. checksums.yaml +7 -0
  2. data/.codeclimate.yml +2 -0
  3. data/.gitignore +38 -0
  4. data/.rspec +4 -0
  5. data/.rubocop.yml +26 -0
  6. data/.travis.yml +23 -0
  7. data/CHANGELOG.md +37 -0
  8. data/CONTRIBUTING.md +29 -0
  9. data/Gemfile +6 -0
  10. data/Gemfile.lock +63 -0
  11. data/LICENSE.txt +21 -0
  12. data/README.md +29 -0
  13. data/Rakefile +6 -0
  14. data/bin/console +14 -0
  15. data/bin/setup +8 -0
  16. data/example/.env +4 -0
  17. data/example/.rspec +2 -0
  18. data/example/Gemfile +28 -0
  19. data/example/Gemfile.lock +104 -0
  20. data/example/LICENSE +22 -0
  21. data/example/README.md +38 -0
  22. data/example/Rakefile +15 -0
  23. data/example/application/api.rb +17 -0
  24. data/example/application/api/api_support.rb +14 -0
  25. data/example/application/api/models/user.rb +6 -0
  26. data/example/application/api/operations/user_service.rb +15 -0
  27. data/example/application/api/routes/main.rb +20 -0
  28. data/example/application/config/database.rb +2 -0
  29. data/example/application/config/sequel.rb +11 -0
  30. data/example/application/db/migrations/20180930152809_add_user_table.rb +15 -0
  31. data/example/application/db/migrations/migration_template.rb +4 -0
  32. data/example/application/tasks/db.rake +30 -0
  33. data/example/config.ru +3 -0
  34. data/example/spec/root_view_spec.rb +17 -0
  35. data/example/spec/spec_helper.rb +69 -0
  36. data/exe/api_generators +6 -0
  37. data/lib/roda_api_generator.rb +6 -0
  38. data/lib/roda_api_generator/cli.rb +28 -0
  39. data/lib/roda_api_generator/generators/roda.rb +101 -0
  40. data/lib/roda_api_generator/templates/roda/.env +4 -0
  41. data/lib/roda_api_generator/templates/roda/Gemfile +28 -0
  42. data/lib/roda_api_generator/templates/roda/LICENSE +22 -0
  43. data/lib/roda_api_generator/templates/roda/README.md +38 -0
  44. data/lib/roda_api_generator/templates/roda/Rakefile +15 -0
  45. data/lib/roda_api_generator/templates/roda/application/api.rb +17 -0
  46. data/lib/roda_api_generator/templates/roda/application/api/api_support.rb +14 -0
  47. data/lib/roda_api_generator/templates/roda/application/api/models/user.rb +6 -0
  48. data/lib/roda_api_generator/templates/roda/application/api/operations/user_service.rb +15 -0
  49. data/lib/roda_api_generator/templates/roda/application/api/routes/main.rb +20 -0
  50. data/lib/roda_api_generator/templates/roda/application/config/database.rb +2 -0
  51. data/lib/roda_api_generator/templates/roda/application/config/sequel.rb +11 -0
  52. data/lib/roda_api_generator/templates/roda/application/db/migrations/20180930152809_add_user_table.rb +15 -0
  53. data/lib/roda_api_generator/templates/roda/application/db/migrations/migration_template.rb +4 -0
  54. data/lib/roda_api_generator/templates/roda/application/tasks/db.rake +30 -0
  55. data/lib/roda_api_generator/templates/roda/config.ru +3 -0
  56. data/lib/roda_api_generator/templates/roda/spec/root_view_spec.rb +17 -0
  57. data/lib/roda_api_generator/templates/roda/spec/rspec.options +2 -0
  58. data/lib/roda_api_generator/templates/roda/spec/spec_helper.rb.erb +69 -0
  59. data/lib/roda_api_generator/version.rb +3 -0
  60. data/roda_api_generator.gemspec +30 -0
  61. metadata +188 -0
@@ -0,0 +1,22 @@
1
+ Copyright (c) <#{Time.new.year}> <#{ENV['USERNAME'] || ENV['USER']}>
2
+
3
+ Permission is hereby granted, free of charge, to any person
4
+ obtaining a copy of this software and associated documentation
5
+ files (the "Software"), to deal in the Software without
6
+ restriction, including without limitation the rights to use,
7
+ copy, modify, merge, publish, distribute, sublicense, and/or sell
8
+ copies of the Software, and to permit persons to whom the
9
+ Software is furnished to do so, subject to the following
10
+ conditions:
11
+
12
+ The above copyright notice and this permission notice shall be
13
+ included in all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
17
+ OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
19
+ HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
20
+ WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21
+ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
22
+ OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,38 @@
1
+ # Your project's name
2
+
3
+ ## Setting the project up
4
+
5
+ ### Clone the repository
6
+
7
+ Fork the project and clone it to your machine.
8
+
9
+ ### Install the dependencies
10
+
11
+ bundle install
12
+
13
+ ### Install the database
14
+
15
+ `createdb db_development`
16
+ `bundle exec rake db:migrate`
17
+
18
+ ## Development
19
+
20
+ ### Launch the console
21
+
22
+ ??
23
+
24
+ ### Run the specs
25
+
26
+ `bundle exec rspec`
27
+
28
+ ## Built With
29
+
30
+ ??
31
+
32
+ ## Contributing Guidelines
33
+
34
+ ??
35
+
36
+ ## License
37
+
38
+ The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
@@ -0,0 +1,15 @@
1
+ require 'dotenv'
2
+ Dotenv.load
3
+
4
+ $LOAD_PATH.unshift(File.expand_path('./application'))
5
+ current_task = Rake.application.top_level_tasks.first
6
+
7
+ require 'bundler'
8
+ require 'bundler/setup'
9
+
10
+ if current_task['db:']
11
+ require 'config/sequel'
12
+ require 'config/database'
13
+ end
14
+
15
+ Dir['./application/tasks/**/*.rake'].each { |rake_file| import(rake_file) }
@@ -0,0 +1,17 @@
1
+ # Load path and gems/bundler
2
+ $LOAD_PATH << __dir__
3
+
4
+ require 'bundler'
5
+ require 'logger'
6
+ Bundler.require
7
+
8
+ require 'dotenv'
9
+ Dotenv.load
10
+
11
+ file_path = File.dirname(__FILE__)
12
+
13
+ %w(config api/db api/models api/operations).each do |path|
14
+ Dir["#{file_path}/#{path}/**/*.rb"].each { |file| require file }
15
+ end
16
+
17
+ require './application/api/api_support'
@@ -0,0 +1,14 @@
1
+ class ApiSupport < Roda
2
+ use Rack::Session::Cookie, key: ENV['RACK_COOKIE_KEY'], secret: ENV['RACK_COOKIE_SECRET']
3
+ use Rack::Protection
4
+ use Rack::Protection::RemoteReferrer
5
+
6
+ plugin :environments
7
+ plugin :http_auth
8
+ plugin :json
9
+ plugin :json_parser
10
+
11
+ self.environment = ENV['ENVIRONMENT']
12
+
13
+ require_relative './routes/main.rb'
14
+ end
@@ -0,0 +1,6 @@
1
+ module Api
2
+ module Models
3
+ class User < Sequel::Model(:user)
4
+ end
5
+ end
6
+ end
@@ -0,0 +1,15 @@
1
+ module Api
2
+ module Operations
3
+ class UserService
4
+ def initialize(params)
5
+ @params = params
6
+ end
7
+
8
+ attr_reader :params
9
+
10
+ def show_params
11
+ params['email']
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,20 @@
1
+ class ApiSupport
2
+ route do |r|
3
+ r.root do
4
+ 'Nothing Here'
5
+ end
6
+
7
+ r.on 'example' do
8
+ r.get do
9
+ begin
10
+ params = request.params
11
+ rescue StandardError
12
+ params = JSON.parse(request.body.read)
13
+ end
14
+
15
+ user = Api::Operations::UserService.new(params)
16
+ user.show_params
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,2 @@
1
+ # Sequel Configuration
2
+ DB = Sequel.connect(ENV.fetch('DATABASE_ENV'))
@@ -0,0 +1,11 @@
1
+ require 'sequel'
2
+
3
+ Sequel.database_timezone = :local
4
+
5
+ # basic plugins
6
+ # to access the full list: https://sequel.jeremyevans.net/plugins.html
7
+ Sequel::Model.plugin :validation_helpers
8
+ Sequel::Model.plugin :nested_attributes
9
+ Sequel::Model.plugin :boolean_readers
10
+ Sequel::Model.plugin :table_select
11
+ Sequel::Model.plugin :string_stripper
@@ -0,0 +1,15 @@
1
+ Sequel.migration do
2
+ up do
3
+ create_table(:user) do
4
+ primary_key :id
5
+ String :first_name, null: false
6
+ String :last_name, null: false
7
+ String :email, null: false
8
+ String :username, null: false
9
+ end
10
+ end
11
+
12
+ down do
13
+ drop_table(:users)
14
+ end
15
+ end
@@ -0,0 +1,4 @@
1
+ Sequel.migration do
2
+ change do
3
+ end
4
+ end
@@ -0,0 +1,30 @@
1
+ namespace :db do
2
+ desc 'Performs migration up to latest migration available'
3
+ task :migrate do
4
+ Sequel.extension :migration, :core_extensions
5
+ Sequel::Migrator.run(DB, 'application/db/migrations')
6
+ end
7
+
8
+ desc 'Generates a new timestamped Sequel migration'
9
+ task :migration, :name do |_, args|
10
+ if args[:name].nil?
11
+ puts 'Please specify a name for your migration (e.g. rake generate:migration[add_user_table])'
12
+ exit false
13
+ end
14
+
15
+ timestamp = Time.now.utc.strftime('%Y%m%d%H%M%S')
16
+ filename = File.join('application/db/migrations', "#{timestamp}_#{args[:name]}.rb")
17
+
18
+ require 'fileutils'
19
+ FileUtils.cp_r('application/db/migrations/migration_template.rb', filename)
20
+
21
+ puts "Created the migration #{filename}"
22
+ end
23
+
24
+ desc 'Drop all database tables and re-run migrations'
25
+ task :reset do
26
+ DB.tables.each { |table| DB.drop_table(table.to_sym) }
27
+
28
+ Rake::Task['db:migrate'].execute
29
+ end
30
+ end
@@ -0,0 +1,3 @@
1
+ require './application/api'
2
+
3
+ run Rack::Cascade.new [ApiSupport]
@@ -0,0 +1,17 @@
1
+ require 'spec_helper'
2
+
3
+ RSpec.describe 'Do a GET request in the root_path' do
4
+ it 'should render root page' do
5
+ get '/'
6
+
7
+ expect(last_response.status).to eq(200)
8
+ expect(last_response.body).to eq('Nothing Here')
9
+ end
10
+
11
+ it 'should render example page' do
12
+ get '/example', email: 'email'
13
+
14
+ expect(last_response.status).to eq(200)
15
+ expect(last_response.body).to eq('email')
16
+ end
17
+ end
@@ -0,0 +1,69 @@
1
+ # Add Simplecov configuration
2
+ require 'simplecov'
3
+ SimpleCov.start do
4
+ add_filter '/.bundle/'
5
+ add_filter '/application/config/'
6
+ add_filter '/application/db/'
7
+ add_filter '/spec/'
8
+ end
9
+
10
+ # Require gems and files
11
+ require 'rspec/core'
12
+ require 'rack/test'
13
+ require './application/api'
14
+ require 'faker'
15
+ require 'factory_bot'
16
+ require 'rspec_sequel_matchers'
17
+
18
+ # Set locale en-US for faker
19
+ Faker::Config.locale = 'en-US'
20
+
21
+ # Necessary to test a cascading rack app and middleware
22
+ module RSpecHelpers
23
+ include Rack::Test::Methods
24
+
25
+ def login_as(user)
26
+ inject_header
27
+
28
+ Api.class_variable_set(:@@current_user, user)
29
+ end
30
+
31
+ def app
32
+ Rack::Builder.parse_file('config.ru').first
33
+ end
34
+
35
+ def inject_header
36
+ header 'AUTHORIZATION', %(Token token="abc", foo="bar")
37
+ end
38
+
39
+ def response_body
40
+ JSON.parse(last_response.body, symbolize_names: true)
41
+ end
42
+ end
43
+
44
+ # FactoryBot is expecting ActiveRecord
45
+ module Sequel
46
+ class Model
47
+ alias save! save
48
+ end
49
+ end
50
+
51
+ # Set up rspec basic configurations
52
+ RSpec.configure do |config|
53
+ config.extend RSpecHelpers
54
+ config.include RSpecHelpers
55
+ config.include FactoryBot::Syntax::Methods
56
+ config.include RspecSequel::Matchers
57
+
58
+ config.disable_monkey_patching!
59
+ config.filter_run_excluding :slow
60
+
61
+ config.expect_with :rspec do |c|
62
+ c.syntax = :expect
63
+ end
64
+
65
+ config.before(:suite) do
66
+ FactoryBot.definition_file_paths = %w(./spec/factories)
67
+ FactoryBot.find_definitions
68
+ end
69
+ end
@@ -0,0 +1,6 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require 'roda_api_generator'
5
+
6
+ ApiGenerators::CLI.start(ARGV)
@@ -0,0 +1,6 @@
1
+ require 'roda_api_generator/generators/roda'
2
+ require 'roda_api_generator/version'
3
+ require 'roda_api_generator/cli'
4
+
5
+ # RubyApiGenerators global module
6
+ module RubyApiGenerators; end
@@ -0,0 +1,28 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'thor'
4
+
5
+ # Responsibility: handle the command line interface
6
+ module ApiGenerators
7
+ class CLI < Thor
8
+ desc 'roda', 'Generate generic Roda API via CLI'
9
+
10
+ option :name, type: :string
11
+ option :test_framework, type: :string, default: :rspec
12
+
13
+ def roda
14
+ args = [options[:name] || 'test_app']
15
+
16
+ script = RubyApiGenerators::Generators::Roda.new(args, opts_hash)
17
+ script.invoke_all
18
+ end
19
+
20
+ private
21
+
22
+ def opts_hash
23
+ {
24
+ test_framework: options[:test_framework]
25
+ }
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,101 @@
1
+ require 'thor'
2
+
3
+ module RubyApiGenerators
4
+ module Generators
5
+ class Roda < Thor::Group
6
+ include Thor::Actions
7
+
8
+ argument :name
9
+ class_option :test_framework
10
+
11
+ def self.source_root
12
+ File.join(File.dirname(__FILE__), '..', 'templates', 'roda')
13
+ end
14
+
15
+ def build_test_suite_folder
16
+ empty_directory "#{name}/spec"
17
+ copy_file 'spec/rspec.options', "#{name}/.rspec"
18
+ template 'spec/spec_helper.rb.erb', "#{name}/spec/spec_helper.rb"
19
+ copy_file 'spec/root_view_spec.rb', "#{name}/spec/root_view_spec.rb"
20
+ end
21
+
22
+ def copy_gemfile
23
+ copy_file 'Gemfile', "#{name}/Gemfile"
24
+ end
25
+
26
+ def copy_licence
27
+ copy_file 'LICENSE', "#{name}/LICENSE"
28
+ end
29
+
30
+ def copy_readme
31
+ copy_file 'README.md', "#{name}/README.md"
32
+ end
33
+
34
+ def copy_config_ru
35
+ copy_file 'config.ru', "#{name}/config.ru"
36
+ end
37
+
38
+ def copy_rakefile
39
+ copy_file 'Rakefile', "#{name}/Rakefile"
40
+ end
41
+
42
+ def copy_env_file
43
+ copy_file '.env', "#{name}/.env"
44
+ end
45
+
46
+ def set_up_application_folder
47
+ build_application_folder
48
+ build_models_folder
49
+ build_routes_folder
50
+ build_operations_folder
51
+ build_tasks_folder
52
+ build_config_folder
53
+ build_db_folder
54
+ end
55
+
56
+ private
57
+
58
+ def build_application_folder
59
+ empty_directory "#{name}/application"
60
+ copy_file 'application/api.rb', "#{name}/application/api.rb"
61
+ copy_file 'application/api/api_support.rb', "#{name}/application/api/api_support.rb"
62
+ end
63
+
64
+ def build_config_folder
65
+ empty_directory "#{name}/application/config"
66
+ copy_file 'application/config/database.rb', "#{name}/application/config/database.rb"
67
+ copy_file 'application/config/sequel.rb', "#{name}/application/config/sequel.rb"
68
+ end
69
+
70
+ def build_db_folder
71
+ empty_directory "#{name}/application/db"
72
+ copy_file 'application/db/migrations/20180930152809_add_user_table.rb',
73
+ "#{name}/application/db/migrations/20180930152809_add_user_table.rb"
74
+ copy_file 'application/db/migrations/migration_template.rb',
75
+ "#{name}/application/db/migrations/migration_template.rb"
76
+ end
77
+
78
+ def build_models_folder
79
+ empty_directory "#{name}/application/api/models"
80
+ copy_file 'application/api/models/user.rb', "#{name}/application/api/models/user.rb"
81
+ end
82
+
83
+ def build_operations_folder
84
+ empty_directory "#{name}/application/api/operations"
85
+ copy_file 'application/api/operations/user_service.rb',
86
+ "#{name}/application/api/operations/user_service.rb"
87
+ end
88
+
89
+ def build_tasks_folder
90
+ empty_directory "#{name}/application/tasks"
91
+ copy_file 'application/tasks/db.rake',
92
+ "#{name}/application/tasks/db.rake"
93
+ end
94
+
95
+ def build_routes_folder
96
+ empty_directory "#{name}/application/api/routes"
97
+ copy_file 'application/api/routes/main.rb', "#{name}/application/api/routes/main.rb"
98
+ end
99
+ end
100
+ end
101
+ end