mobile_workflow 0.5.7 → 0.6.0

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 843610afaa8207693d3f1be346698ca58e4022a3575b6953ef52c343781c649c
4
- data.tar.gz: b787b24ab9fbf0f47910a889f23a59094d214db55c6eb0950609b674ba01ed64
3
+ metadata.gz: 74a57b5231432fa5532bc2757c6785604c833bf0b637770c15ea34faa41b3b13
4
+ data.tar.gz: 33a6f90850d5e6fb2522d76012336899b585ab1b8fd7db6dc768018c12eeca2b
5
5
  SHA512:
6
- metadata.gz: 427d7c382ebc60cdf5ebd79f4257d2ec268cd0f52d7c7bd583afc1774c3adecaef910b163e06d1a754fa2340dfd352f23ae3c06056d97762e7b6fe878713b7cc
7
- data.tar.gz: e98d3ebb68a12e42b3911d63fe16e4fe578ece0fc8e86814ac401d80a171fcd854d7a42f1a522fc535fc06d56eed1bb902e2a597b3d9d73a4c3c2b4603ce59a7
6
+ metadata.gz: 54c3c9504079480aaba63c9974a17eb2c428254503568230ca058ad52a71119a0a6d469d30142cd7a41843b8757e4d24fcf94fccffeefe8fe06b5ab14e88b6a5
7
+ data.tar.gz: 62a5f5d474522fa2ade3fdccfb5a7f84b66f02d0c612a998cb235baee27e09cb33f0c12fc82019a010cfabd666fd614c5b98710d3a149914ac889048746cd2fe
@@ -8,13 +8,18 @@ module MobileWorkflow
8
8
 
9
9
  class_option :attributes, type: :array, default: [], banner: "field:type field:type"
10
10
  class_option :actions, type: :array, default: [], banner: "index create update destroy"
11
+ class_option :doorkeeper_oauth, type: :boolean, default: false
11
12
 
12
13
  def copy_controller_and_spec_files
13
14
  template "controller.rb.erb", File.join("app/controllers", controller_class_path, "#{controller_file_name}_controller.rb")
14
15
  template "controller_spec.rb.erb", File.join("spec/controllers", controller_class_path, "#{controller_file_name}_controller_spec.rb")
15
16
  end
16
17
 
17
- private
18
+ private
19
+ def doorkeeper_oauth?
20
+ options[:doorkeeper_oauth]
21
+ end
22
+
18
23
  def attributes_names
19
24
  options[:attributes].map{ |attribute| attribute.split(":").first }
20
25
  end
@@ -1,12 +1,10 @@
1
1
  require "rails/generators/base"
2
+ require "mobile_workflow/open_api_spec/parser"
2
3
 
3
4
  module MobileWorkflow
4
5
  module Generators
5
6
  class InstallGenerator < Rails::Generators::Base
6
7
 
7
- # Schemas to avoid generating models for (static items from MW)
8
- SKIP_SCHEMAS = ["attachment", "ListItem", "DisplayItem", "DisplayText", "DisplayButton", "DisplayImage", "DisplayVideo"]
9
-
10
8
  source_root File.expand_path("../templates", __FILE__)
11
9
 
12
10
  class_option :open_api_spec_path, type: :string, default: "config/open_api_spec.json"
@@ -32,28 +30,41 @@ module MobileWorkflow
32
30
  template("user.rb.erb", "app/models/user.rb")
33
31
  template("sessions_controller.rb.erb", "app/controllers/sessions_controller.rb")
34
32
  route "resources :sessions, only: [:new, :create]"
33
+
34
+ # View related for login screen
35
+ copy_file("views/layouts/application.html.erb")
36
+ copy_file("views/sessions/new.html.erb")
37
+ copy_file("helpers/application_helper.rb")
35
38
  end
36
39
 
37
40
  def generate_models
41
+ say "Loading OpenAPI Spec: #{open_api_spec_path}"
38
42
  say "Generating models"
39
- @model_properties = {}
40
- open_api_spec[:components][:schemas].each_pair do |model_name, schema|
41
- next if SKIP_SCHEMAS.include? model_name # Don't generate schemas for MW schemas
42
-
43
- model_name = model_name.underscore
44
- model_properties = model_properties(model_name, schema)
45
- generate(:model, "#{model_name} #{model_properties}")
46
- @model_properties[model_name] = model_properties
43
+ model_name_to_properties.each_pair do |model_name, model_properties|
44
+ if interactive? && !yes?("Use generated schema #{model_name}(#{model_properties})[yn]?")
45
+ model_properties = ask "Specify schema for #{model_name}: (e.g. text:string image:attachment region:reference)"
46
+ end
47
+
48
+ generate_model(model_name, model_properties)
49
+ @model_name_to_properties[model_name] = model_properties
47
50
  end
48
51
  end
49
52
 
50
53
  def generate_controllers_and_routes
51
54
  say "Generating controllers"
52
- route "root to: 'admin/#{controller_names.first}#index'"
55
+ route "root to: 'admin/#{open_api_spec.controller_names.first}#index'"
53
56
 
54
- controller_names.each do |plural_controller_name|
57
+ open_api_spec.controller_names.each do |plural_controller_name|
55
58
  controller_name = plural_controller_name.singularize
56
- model_properties = @model_properties[controller_name]
59
+ model_properties = model_name_to_properties[controller_name]
60
+
61
+ unless model_properties
62
+ # Generate a model because it probably wasnt present in the schema
63
+ # And set default attributes
64
+ model_properties = "text:string"
65
+ generate_model(controller_name, model_properties)
66
+ end
67
+
57
68
  generate "mobile_workflow:controller #{controller_name} --attributes #{model_properties}"
58
69
  route "resources :#{plural_controller_name}, only: [:index, :show, :create]"
59
70
  end
@@ -64,21 +75,17 @@ module MobileWorkflow
64
75
  end
65
76
 
66
77
  private
67
- def controller_names
68
- @controller_names ||= oai_spec_paths.collect{|url_path| url_path.split('/')[1] }.uniq
69
- end
70
78
 
71
- def oai_spec_paths
72
- @oai_spec_paths ||= open_api_spec[:paths].keys
79
+ def generate_model(model_name, model_properties)
80
+ generate("mobile_workflow:model #{model_name} #{model_properties}")
73
81
  end
74
82
 
75
- def open_api_spec
76
- @open_api_spec ||= read_openapi_spec
83
+ def model_name_to_properties
84
+ @model_name_to_properties ||= open_api_spec.model_name_to_properties
77
85
  end
78
86
 
79
- def read_openapi_spec
80
- say "Loading OpenAPI Spec: #{open_api_spec_path}"
81
- return JSON.parse(File.read(open_api_spec_path)).with_indifferent_access
87
+ def open_api_spec
88
+ @open_api_spec ||= ::MobileWorkflow::OpenApiSpec::Parser.new(File.read(open_api_spec_path))
82
89
  end
83
90
 
84
91
  def open_api_spec_path
@@ -88,22 +95,6 @@ module MobileWorkflow
88
95
  def interactive?
89
96
  options[:interactive]
90
97
  end
91
-
92
- def model_properties(name, schema)
93
- generated_properties_args = schema["properties"].keys.collect{|key| "#{key}:#{model_property_type(schema["properties"][key])}" }.join(" ")
94
- if !interactive? || yes?("Use generated schema #{name}(#{generated_properties_args})[yn]?")
95
- generated_properties_args
96
- else
97
- ask "Specify schema for #{name}: (e.g. text:string image:attachment region:reference)"
98
- end
99
- end
100
-
101
- def model_property_type(property)
102
- return property["type"] unless property["type"].blank?
103
- return 'attachment' if property['$ref'] == "#/components/schemas/attachment"
104
-
105
- raise 'Unknown property type'
106
- end
107
98
  end
108
99
  end
109
100
  end
@@ -1,23 +1,21 @@
1
1
  source 'https://rubygems.org'
2
2
  git_source(:github) { |repo| "https://github.com/#{repo}.git" }
3
3
 
4
- ruby '2.7.2'
4
+ ruby '<%= MobileWorkflow::RUBY_VERSION %>'
5
5
 
6
6
  # Core Gems
7
- gem 'rails', '~> 6.1.0'
7
+ gem 'rails', '~> <%= MobileWorkflow::RAILS_VERSION %>'
8
8
  gem 'puma', '~> 5.0'
9
9
  gem 'sass-rails', '>= 6'
10
10
  gem 'turbolinks', '~> 5'
11
11
 
12
12
  # Mobile Workflow
13
- #gem 'mobile_workflow', path: '../mobile_workflow'
14
- #gem 'mobile_workflow', github: 'FutureWorkshops/mobile_workflow'
15
- gem 'mobile_workflow', '0.5.5'
13
+ gem 'mobile_workflow', '~> <%= MobileWorkflow::VERSION %>'
16
14
 
17
15
  # Authorisation / Authentication
18
16
  <%- if options[:doorkeeper_oauth] %>
19
17
  gem 'doorkeeper'
20
- gem 'bcrypt-ruby'
18
+ gem 'bcrypt'
21
19
  <%- end %>
22
20
  gem 'cancancan', '~> 3.1'
23
21
 
@@ -33,6 +31,9 @@ gem 'aws-sdk-s3', '~> 1.60', '>= 1.60.1'
33
31
  gem 'aws-sdk-sns', '~> 1.23'
34
32
  <%- end %>
35
33
 
34
+ # FFI for Mac M1
35
+ gem 'ffi', github: 'ffi/ffi'
36
+
36
37
  group :development do
37
38
  gem 'web-console', '>= 3.3.0'
38
39
  gem 'listen', '>= 3.0.5', '< 3.2'
@@ -8,7 +8,7 @@ class ApiController < ActionController::API
8
8
  before_action :doorkeeper_authorize!, unless: :anonymous_action?
9
9
 
10
10
  def current_resource_owner
11
- User.find(doorkeeper_token.resource_owner_id) if doorkeeper_token&.accessible?
11
+ @current_resource_owner ||= User.find(doorkeeper_token.resource_owner_id) if doorkeeper_token&.accessible?
12
12
  end
13
13
  alias_method :current_user, :current_resource_owner
14
14
 
@@ -0,0 +1,13 @@
1
+ module ApplicationHelper
2
+
3
+ def bootstrap_class_for(flash_type)
4
+ { success: "alert-success", error: "alert-danger", alert: "alert-warning", notice: "alert-info" }.stringify_keys[flash_type.to_s] || flash_type.to_s
5
+ end
6
+
7
+ def flash_messages
8
+ flash.each do |flash_type, message|
9
+ concat(content_tag(:div, message, class: "alert #{bootstrap_class_for(flash_type)}", role: 'alert'))
10
+ end
11
+ nil
12
+ end
13
+ end
@@ -3,7 +3,7 @@ class SessionsController < ApplicationController
3
3
  end
4
4
 
5
5
  def create
6
- @user = User.find_by(email: params[:email])
6
+ @user = User.find_by("LOWER(email)= ?", params[:email].downcase)
7
7
  if @user && @user.authenticate(params[:password])
8
8
  session[:user_id] = @user.id
9
9
  redirect_to params[:return_to] || root_url, notice: "Logged in!"
@@ -1,4 +1,4 @@
1
1
  class User < ApplicationRecord
2
2
  has_secure_password
3
- validates :email, presence: true
3
+ validates :email, presence: true, uniqueness: true
4
4
  end
@@ -0,0 +1,18 @@
1
+ <!doctype html>
2
+ <html lang="en">
3
+ <head>
4
+ <!-- Required meta tags -->
5
+ <meta charset="utf-8">
6
+ <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
7
+
8
+ <!-- Bootstrap CSS -->
9
+ <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.5.2/css/bootstrap.min.css" integrity="sha384-JcKb8q3iqJ61gNV9KGb8thSsNjpSL0n8PARn9HuZOnIxN0hoP+VmmDGMN5t9UJ0Z" crossorigin="anonymous">
10
+
11
+ <title>MW Project</title>
12
+ </head>
13
+ <body>
14
+ <div class="container">
15
+ <%= yield %>
16
+ </div>
17
+ </body>
18
+ </html>
@@ -0,0 +1,20 @@
1
+ <h1>Sign In</h1>
2
+
3
+ <%= flash_messages %>
4
+
5
+ <%= form_tag sessions_path, method: :post do %>
6
+ <%= hidden_field_tag :return_to, params[:return_to] %>
7
+
8
+ <div class="form-group">
9
+ <%= label_tag :email %>
10
+ <%= email_field_tag :email, nil, class: "form-control" %>
11
+ </div>
12
+
13
+ <div class="form-group">
14
+ <%= label_tag :password %>
15
+ <%= password_field_tag :password, nil, class: "form-control" %>
16
+ </div>
17
+
18
+ <%= submit_tag 'Sign In', class: "btn btn-primary" %>
19
+ <% end %>
20
+
@@ -0,0 +1,15 @@
1
+ require 'rails/generators/active_record/model/model_generator'
2
+
3
+ module MobileWorkflow
4
+ module Generators
5
+
6
+ class ModelGenerator < ActiveRecord::Generators::ModelGenerator
7
+ source_root File.join(File.dirname(ActiveRecord::Generators::ModelGenerator.instance_method(:create_migration_file).source_location.first), "templates")
8
+
9
+ def create_model_file
10
+ template File.join(File.dirname(__FILE__), "templates", "model.rb.erb"), File.join('app/models', class_path, "#{file_name}.rb")
11
+ end
12
+
13
+ end
14
+ end
15
+ end
@@ -6,10 +6,19 @@ require 'json'
6
6
  RSpec.describe <%= controller_class_name %>Controller do
7
7
  let(:params) { {} }
8
8
  let(:json_response) { JSON.parse(response.body, symbolize_names: true) }
9
+ <% if doorkeeper_oauth? -%>
10
+ let(:user) { create(:user) }
11
+ let(:token) { instance_double('Doorkeeper::AccessToken', :accessible? => true, :acceptable? => true, resource_owner_id: user.id) }
12
+ <% end -%>
9
13
 
10
14
  describe 'GET #index' do
11
15
  let!(:<%= controller_class_name.singularize.underscore %>) { create(:<%= controller_class_name.singularize.underscore %>) }
12
- before(:each) { get :index, params: params }
16
+ before(:each) do
17
+ <% if doorkeeper_oauth? -%>
18
+ allow(subject).to receive(:doorkeeper_token) { token }
19
+ <% end -%>
20
+ get :index, params: params
21
+ end
13
22
 
14
23
  context 'ok' do
15
24
  it { expect(json_response[0][:id]).to eq <%= controller_class_name.singularize.underscore %>.id }
@@ -20,7 +29,12 @@ RSpec.describe <%= controller_class_name %>Controller do
20
29
  describe 'GET #show' do
21
30
  let(:<%= controller_class_name.singularize.underscore %>) { create(:<%= controller_class_name.singularize.underscore %>) }
22
31
  let(:params) { { id: <%= controller_class_name.singularize.underscore %>.id } }
23
- before(:each) { get :show, params: params }
32
+ before(:each) do
33
+ <% if doorkeeper_oauth? -%>
34
+ allow(subject).to receive(:doorkeeper_token) { token }
35
+ <% end -%>
36
+ get :show, params: params
37
+ end
24
38
 
25
39
  context 'ok' do
26
40
  it { expect(response.status).to eq 200 }
@@ -30,7 +44,12 @@ RSpec.describe <%= controller_class_name %>Controller do
30
44
  describe 'POST #create' do
31
45
  let(:payload_params) { {text: 'OK'} }
32
46
  let(:params) { { payload: payload_params, binaries: [{identifier: 'record', mimetype: 'video/mp4'}] } }
33
- before(:each) { post :create, params: params }
47
+ before(:each) do
48
+ <% if doorkeeper_oauth? -%>
49
+ allow(subject).to receive(:doorkeeper_token) { token }
50
+ <% end -%>
51
+ post :create, params: params
52
+ end
34
53
 
35
54
  context 'ok' do
36
55
  it { expect(<%= controller_class_name.singularize %>.count).to eq 1 }
@@ -17,7 +17,10 @@ class <%= class_name %> < <%= parent_class_name.classify %>
17
17
  end
18
18
 
19
19
  def display_as_json
20
- [mw_display_text(label: 'ID', text: id.to_s)]
20
+ [
21
+ mw_display_text(label: 'ID', text: id.to_s),
22
+ mw_display_text(label: 'Text', text: text)
23
+ ]
21
24
  end
22
25
 
23
26
  end
@@ -53,9 +53,9 @@ module MobileWorkflow::Cli
53
53
  def destroy
54
54
  aws_command "aws s3api delete-bucket --bucket #{@aws_name} --region #{@region}"
55
55
 
56
- aws_command("aws sns list-topics")["Topics"].each do |topic|
56
+ aws_command("aws sns list-topics --region #{@region}")["Topics"].each do |topic|
57
57
  topic_arn = topic["TopicArn"]
58
- aws_command "aws sns delete-topic --topic-arn '#{topic_arn}'" if topic_arn.end_with?(@aws_name)
58
+ aws_command "aws sns delete-topic --topic-arn '#{topic_arn}' --region #{@region}" if topic_arn.end_with?(@aws_name)
59
59
  end
60
60
 
61
61
  aws_command "aws iam delete-user-policy --user-name #{@aws_name} --policy-name s3"
@@ -0,0 +1,59 @@
1
+ module MobileWorkflow
2
+ module OpenApiSpec
3
+ class Parser
4
+
5
+ # Schemas to avoid generating models for (static items from MW)
6
+ SKIP_SCHEMAS = ["attachment", "ListItem", "DisplayItem", "DisplayText", "DisplayButton", "DisplayImage", "DisplayVideo"]
7
+
8
+ def initialize(open_api_spec_string)
9
+ @open_api_spec_string = open_api_spec_string
10
+ end
11
+
12
+ def model_name_to_properties
13
+ @model_properties = {}
14
+ schemas.each_pair do |model_name, schema|
15
+ next if SKIP_SCHEMAS.include? model_name # Don't generate schemas for MW schemas
16
+
17
+ model_name = model_name.underscore
18
+ model_properties = schema_model_properties(model_name, schema)
19
+
20
+ @model_properties[model_name] = model_properties
21
+ end
22
+ @model_properties
23
+ end
24
+
25
+ def controller_names
26
+ @controller_names ||= paths.collect{|url_path| url_path.split('/')[1] }.uniq
27
+ end
28
+
29
+ def paths
30
+ @paths ||= open_api_spec[:paths].keys
31
+ end
32
+
33
+ def schemas
34
+ @schemas ||= open_api_spec[:components][:schemas]
35
+ end
36
+
37
+ private
38
+ def open_api_spec
39
+ @open_api_spec ||= read_openapi_spec
40
+ end
41
+
42
+ def schema_model_properties(name, schema)
43
+ schema["properties"].keys.collect{|key| "#{key}:#{model_property_type(schema["properties"][key])}" }.join(" ")
44
+ end
45
+
46
+ def model_property_type(property)
47
+ return property["type"] unless property["type"].blank?
48
+ return 'attachment' if property['$ref'] == "#/components/schemas/attachment"
49
+
50
+ raise 'Unknown property type'
51
+ end
52
+
53
+ def read_openapi_spec
54
+ @read_openapi_spec ||= JSON.parse(@open_api_spec_string).with_indifferent_access
55
+ end
56
+
57
+ end
58
+ end
59
+ end
@@ -1,5 +1,5 @@
1
1
  module MobileWorkflow
2
- VERSION = '0.5.7'
3
- RUBY_VERSION = '2.5.5'
2
+ VERSION = '0.6.0'
3
+ RUBY_VERSION = '2.7.2'
4
4
  RAILS_VERSION = '6.1.0'
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mobile_workflow
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.7
4
+ version: 0.6.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Matt Brooke-Smith
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-01-02 00:00:00.000000000 Z
11
+ date: 2021-01-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -112,12 +112,17 @@ files:
112
112
  - lib/generators/mobile_workflow/install/templates/README.md.erb
113
113
  - lib/generators/mobile_workflow/install/templates/ability.rb
114
114
  - lib/generators/mobile_workflow/install/templates/api_controller.rb.erb
115
+ - lib/generators/mobile_workflow/install/templates/helpers/application_helper.rb
115
116
  - lib/generators/mobile_workflow/install/templates/seeds.rb.erb
116
117
  - lib/generators/mobile_workflow/install/templates/sessions_controller.rb.erb
117
118
  - lib/generators/mobile_workflow/install/templates/storage.s3.yml
118
119
  - lib/generators/mobile_workflow/install/templates/user.rb.erb
120
+ - lib/generators/mobile_workflow/install/templates/views/layouts/application.html.erb
121
+ - lib/generators/mobile_workflow/install/templates/views/sessions/new.html.erb
122
+ - lib/generators/mobile_workflow/model_generator.rb
119
123
  - lib/generators/mobile_workflow/templates/controller.rb.erb
120
124
  - lib/generators/mobile_workflow/templates/controller_spec.rb.erb
125
+ - lib/generators/mobile_workflow/templates/model.rb.erb
121
126
  - lib/mobile_workflow.rb
122
127
  - lib/mobile_workflow/cli.rb
123
128
  - lib/mobile_workflow/cli/app_builder.rb
@@ -127,8 +132,8 @@ files:
127
132
  - lib/mobile_workflow/cli/dokku_backend.rb
128
133
  - lib/mobile_workflow/cli/heroku_backend.rb
129
134
  - lib/mobile_workflow/engine.rb
135
+ - lib/mobile_workflow/open_api_spec/parser.rb
130
136
  - lib/mobile_workflow/version.rb
131
- - lib/templates/active_record/model/model.rb.erb
132
137
  homepage: https://github.com/futureworkshops/mobile_workflow
133
138
  licenses:
134
139
  - MIT
@@ -141,7 +146,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
141
146
  requirements:
142
147
  - - ">="
143
148
  - !ruby/object:Gem::Version
144
- version: 2.5.5
149
+ version: 2.7.2
145
150
  required_rubygems_version: !ruby/object:Gem::Requirement
146
151
  requirements:
147
152
  - - ">="