thredded_create_app 0.1.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.
Files changed (48) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE.txt +21 -0
  3. data/README.md +185 -0
  4. data/exe/thredded_create_app +8 -0
  5. data/lib/thredded_create_app.rb +5 -0
  6. data/lib/thredded_create_app/cli.rb +182 -0
  7. data/lib/thredded_create_app/command_error.rb +14 -0
  8. data/lib/thredded_create_app/generator.rb +91 -0
  9. data/lib/thredded_create_app/logging.rb +36 -0
  10. data/lib/thredded_create_app/tasks/add_devise.rb +63 -0
  11. data/lib/thredded_create_app/tasks/add_display_name_to_users.rb +126 -0
  12. data/lib/thredded_create_app/tasks/add_display_name_to_users/add_display_name_to_users.rb +12 -0
  13. data/lib/thredded_create_app/tasks/add_simple_form.rb +20 -0
  14. data/lib/thredded_create_app/tasks/add_thredded.rb +79 -0
  15. data/lib/thredded_create_app/tasks/add_thredded/_myapp-thredded.scss +18 -0
  16. data/lib/thredded_create_app/tasks/add_thredded/add_admin_to_users.rb +10 -0
  17. data/lib/thredded_create_app/tasks/add_thredded/myapp_thredded.js +1 -0
  18. data/lib/thredded_create_app/tasks/add_thredded/spec/features/thredded_spec.rb +9 -0
  19. data/lib/thredded_create_app/tasks/add_thredded/thredded.en.yml +8 -0
  20. data/lib/thredded_create_app/tasks/add_thredded/thredded_initializer_controller.rb +9 -0
  21. data/lib/thredded_create_app/tasks/base.rb +101 -0
  22. data/lib/thredded_create_app/tasks/create_rails_app.rb +36 -0
  23. data/lib/thredded_create_app/tasks/docker.rb +22 -0
  24. data/lib/thredded_create_app/tasks/docker/Dockerfile.erb +22 -0
  25. data/lib/thredded_create_app/tasks/docker/docker-compose.yml.erb +22 -0
  26. data/lib/thredded_create_app/tasks/docker/wait-for-tcp +30 -0
  27. data/lib/thredded_create_app/tasks/production_configs.rb +21 -0
  28. data/lib/thredded_create_app/tasks/production_configs/Procfile +1 -0
  29. data/lib/thredded_create_app/tasks/production_configs/puma.production.rb +18 -0
  30. data/lib/thredded_create_app/tasks/setup_app_skeleton.rb +160 -0
  31. data/lib/thredded_create_app/tasks/setup_app_skeleton/_flash-messages.scss +19 -0
  32. data/lib/thredded_create_app/tasks/setup_app_skeleton/_flash_messages.html.erb +7 -0
  33. data/lib/thredded_create_app/tasks/setup_app_skeleton/_header.html.erb +13 -0
  34. data/lib/thredded_create_app/tasks/setup_app_skeleton/_variables.scss.erb +6 -0
  35. data/lib/thredded_create_app/tasks/setup_app_skeleton/application.body.html.erb +7 -0
  36. data/lib/thredded_create_app/tasks/setup_app_skeleton/application.scss +83 -0
  37. data/lib/thredded_create_app/tasks/setup_app_skeleton/application_helper_methods.rb +17 -0
  38. data/lib/thredded_create_app/tasks/setup_app_skeleton/en.yml.erb +7 -0
  39. data/lib/thredded_create_app/tasks/setup_app_skeleton/home_show.html.erb.erb +47 -0
  40. data/lib/thredded_create_app/tasks/setup_app_skeleton/seeds.rb.erb +52 -0
  41. data/lib/thredded_create_app/tasks/setup_app_skeleton/spec/controllers/users_controller_spec.rb +21 -0
  42. data/lib/thredded_create_app/tasks/setup_app_skeleton/spec/features/homepage_spec.rb +9 -0
  43. data/lib/thredded_create_app/tasks/setup_app_skeleton/users_show.html.erb +26 -0
  44. data/lib/thredded_create_app/tasks/setup_database.rb +42 -0
  45. data/lib/thredded_create_app/tasks/setup_database/create_postgresql_user.sh +25 -0
  46. data/lib/thredded_create_app/tasks/setup_database/database.yml.erb +36 -0
  47. data/lib/thredded_create_app/version.rb +4 -0
  48. metadata +175 -0
@@ -0,0 +1,36 @@
1
+ # frozen_string_literal: true
2
+ require 'thredded_create_app/tasks/base'
3
+ module ThreddedCreateApp
4
+ module Tasks
5
+ class CreateRailsApp < Base
6
+ def initialize(install_gem_bundler_rails: false, **args)
7
+ super
8
+ @install_gem_bundler_rails = install_gem_bundler_rails
9
+ end
10
+
11
+ def summary
12
+ "Create Rails app #{app_name.inspect} with postgresql and rspec"
13
+ end
14
+
15
+ def before_bundle
16
+ if @install_gem_bundler_rails
17
+ run 'gem update --system --no-document --quiet'
18
+ run 'gem install bundler rails --no-document'
19
+ end
20
+ # I have no idea why this bundle exec is necessary on Travis.
21
+ run "#{'bundle exec ' if ENV['TRAVIS']}" \
22
+ 'rails new . --skip-bundle --database=postgresql ' \
23
+ "--skip-test#{verbose? ? ' --verbose' : ' --quiet'}"
24
+ replace 'Gemfile', /gem 'sass-rails'.*$/, "gem 'sassc-rails'"
25
+ add_gem 'rspec-rails', groups: %i(test)
26
+ add_gem 'capybara', groups: %i(test)
27
+ git_commit summary
28
+ end
29
+
30
+ def after_bundle
31
+ run_generator 'rspec:install'
32
+ git_commit 'rails g rspec:install'
33
+ end
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+ require 'thredded_create_app/tasks/base'
3
+ module ThreddedCreateApp
4
+ module Tasks
5
+ class Docker < Base
6
+ def summary
7
+ 'Add Docker configuration files for development'
8
+ end
9
+
10
+ def before_bundle
11
+ copy_template 'docker/Dockerfile.erb',
12
+ 'Dockerfile'
13
+ copy_template 'docker/docker-compose.yml.erb',
14
+ 'docker-compose.yml'
15
+ copy 'docker/wait-for-tcp',
16
+ 'script/wait-for-tcp'
17
+ run 'chmod +x script/wait-for-tcp'
18
+ git_commit 'Add Docker compose for development'
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,22 @@
1
+ # A Dockerfile for development.
2
+
3
+ FROM alpine:3.4
4
+
5
+ RUN apk add --no-cache \
6
+ # Runtime deps
7
+ ruby ruby-bundler ruby-bigdecimal ruby-io-console tzdata nodejs bash \
8
+ # Bundle install deps
9
+ build-base ruby-dev libc-dev linux-headers gmp-dev openssl-dev libxml2-dev \
10
+ libxslt-dev postgresql-dev
11
+
12
+ ENV BUNDLE_SILENCE_ROOT_WARNING=1
13
+
14
+ ENV APP_HOME /<%= app_name %>
15
+ WORKDIR $APP_HOME
16
+ RUN mkdir -p $APP_HOME
17
+
18
+ # Copy Gemfile and run bundle install first to allow for caching
19
+ ADD Gemfile Gemfile.lock $APP_HOME/
20
+ RUN bundle install
21
+
22
+ ADD Rakefile config.ru app/ bin/ config/ db/ lib/ script/ spec/ $APP_HOME/
@@ -0,0 +1,22 @@
1
+ db:
2
+ image: onjin/alpine-postgres:9.5
3
+ ports:
4
+ - "5433:5432"
5
+ environment:
6
+ POSTGRES_USER: root
7
+ web:
8
+ build: .
9
+ volumes:
10
+ - .:/<%= app_name %>
11
+ working_dir: /<%= app_name %>
12
+ environment:
13
+ DB: postgresql
14
+ DB_USERNAME: root
15
+ DB_PASSWORD:
16
+ command: >
17
+ bash -c 'script/wait-for-tcp $<%= app_name.upcase %>_DB_1_PORT_5432_TCP_ADDR $<%= app_name.upcase %>_DB_1_PORT_5432_TCP_PORT &&
18
+ rails s'
19
+ ports:
20
+ - "9292:9292"
21
+ links:
22
+ - db
@@ -0,0 +1,30 @@
1
+ #!/usr/bin/env bash
2
+ if [ -z "$2" ]; then cat <<'HELP'; exit; fi
3
+ Usage: script/wait-for-tcp ADDRESS PORT
4
+ Wait for TCP connection at ADDRESS:PORT, retrying every 3 seconds, maximum 20 times.
5
+ HELP
6
+
7
+ wait_for_tcp() {
8
+ local addr="$1"
9
+ local port="$2"
10
+ local status="down"
11
+ local counter=0
12
+ local wait_time=3
13
+ local max_retries=20
14
+ while [ "$status" = 'down' -a ${counter} -lt ${max_retries} ]; do
15
+ status="$( (echo > "/dev/tcp/${addr}/${port}") >/dev/null 2>&1 && echo 'up' || echo 'down' )"
16
+ if [ "$status" = 'up' ]; then
17
+ echo "Connection to ${addr}:${port} up"
18
+ else
19
+ echo "Waiting ${wait_time}s for connection to ${addr}:${port}..."
20
+ sleep "$wait_time"
21
+ let counter++
22
+ fi
23
+ done
24
+ if [ ${status} = 'down' ]; then
25
+ echo "Could not connect to ${addr}:${port} after ${max_retries} retries"
26
+ exit 1
27
+ fi
28
+ }
29
+
30
+ wait_for_tcp "$1" "$2"
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+ require 'thredded_create_app/tasks/base'
3
+ module ThreddedCreateApp
4
+ module Tasks
5
+ class ProductionConfigs < Base
6
+ def summary
7
+ 'Add production configuration files'
8
+ end
9
+
10
+ def before_bundle
11
+ copy 'production_configs/puma.production.rb',
12
+ 'config/puma.production.rb'
13
+ git_commit 'Add production puma config file'
14
+
15
+ copy 'production_configs/Procfile',
16
+ 'Procfile'
17
+ git_commit 'Add Procfile'
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1 @@
1
+ web: bundle exec puma -C ./config/puma.production.rb
@@ -0,0 +1,18 @@
1
+ # frozen_string_literal: true
2
+ workers Integer(ENV.fetch('WEB_CONCURRENCY', 3))
3
+ threads_count = Integer(ENV.fetch('MAX_THREADS', 5))
4
+ threads(threads_count, threads_count)
5
+
6
+ preload_app!
7
+
8
+ port ENV.fetch('PORT', 3000)
9
+ environment ENV.fetch('RACK_ENV', 'development')
10
+
11
+ before_fork do
12
+ ::ActiveRecord::Base.connection_pool.disconnect!
13
+ ::I18n.backend.send(:init_translations)
14
+ end
15
+
16
+ on_worker_boot do
17
+ ActiveRecord::Base.establish_connection
18
+ end
@@ -0,0 +1,160 @@
1
+ # frozen_string_literal: true
2
+ require 'thredded_create_app/tasks/base'
3
+ module ThreddedCreateApp
4
+ module Tasks
5
+ class SetupAppSkeleton < Base # rubocop:disable Metrics/ClassLength
6
+ MATERIAL_700_COLORS = [
7
+ '#7B1FA2', # purple
8
+ '#512DA8', # deep purple
9
+ '#303F9F', # indigo
10
+ '#1976D2', # blue
11
+ '#0288D1', # light blue
12
+ '#0097A7', # cyan
13
+ '#00796B', # teal
14
+ '#F57C00', # orange
15
+ ].freeze
16
+
17
+ def summary
18
+ 'Setup basic app navigation and styles'
19
+ end
20
+
21
+ def before_bundle
22
+ add_gem 'rails-timeago'
23
+ end
24
+
25
+ def after_bundle
26
+ add_favicon_and_touch_icons
27
+ add_javascripts
28
+ add_styles
29
+ add_user_page
30
+ add_home_page
31
+ add_i18n
32
+ add_app_layout
33
+ copy 'setup_app_skeleton/spec/features/homepage_spec.rb',
34
+ 'spec/features/homepage_spec.rb'
35
+ add_seeds
36
+ git_commit 'Set up basic app navigation and styles'
37
+ end
38
+
39
+ def add_favicon_and_touch_icons
40
+ FileUtils.mv 'public/favicon.ico',
41
+ 'app/assets/images/favicon.ico'
42
+ FileUtils.mv 'public/apple-touch-icon.png',
43
+ 'app/assets/images/apple-touch-icon.png'
44
+ # The `-precomposed.png` touch icon is only used by iOS < 7, remove it.
45
+ # Do not raise if the file does not exist, as Rails will stop generating
46
+ # it one of these days.
47
+ FileUtils.rm 'public/apple-touch-icon-precomposed.png', force: true
48
+
49
+ inject_into_file 'app/views/layouts/application.html.erb',
50
+ before: ' <%= csrf_meta_tags %>',
51
+ content: indent(4, <<~ERB)
52
+ <%= favicon_link_tag 'favicon.ico' %>
53
+ <%= favicon_link_tag 'apple-touch-icon.png',
54
+ rel: 'apple-touch-icon', type: 'image/png' %>
55
+ ERB
56
+ end
57
+
58
+ def add_javascripts
59
+ replace 'app/assets/javascripts/application.js',
60
+ %r{^//= require jquery$},
61
+ '//= require jquery3'
62
+ git_commit 'Use jQuery v3 instead of jQuery v1'
63
+ end
64
+
65
+ def add_styles
66
+ copy_template 'setup_app_skeleton/_variables.scss.erb',
67
+ 'app/assets/stylesheets/_variables.scss'
68
+
69
+ if File.file? 'app/assets/stylesheets/application.css'
70
+ File.delete 'app/assets/stylesheets/application.css'
71
+ end
72
+ copy_template 'setup_app_skeleton/application.scss',
73
+ 'app/assets/stylesheets/application.scss',
74
+ mode: 'a'
75
+ copy 'setup_app_skeleton/_flash-messages.scss',
76
+ 'app/assets/stylesheets/_flash-messages.scss'
77
+ end
78
+
79
+ def add_i18n
80
+ copy_template 'setup_app_skeleton/en.yml.erb',
81
+ 'config/locales/en.yml'
82
+ end
83
+
84
+ def add_app_layout # rubocop:disable Metrics/MethodLength
85
+ copy 'setup_app_skeleton/_header.html.erb',
86
+ 'app/views/shared/_header.html.erb'
87
+ copy 'setup_app_skeleton/_flash_messages.html.erb',
88
+ 'app/views/shared/_flash_messages.html.erb'
89
+ app_helper_src = File.read(
90
+ File.join(File.dirname(__FILE__),
91
+ 'setup_app_skeleton/application_helper_methods.rb')
92
+ )
93
+ inject_into_file 'app/helpers/application_helper.rb',
94
+ before: /end\n\z/,
95
+ content: indent(2, app_helper_src)
96
+ replace 'app/views/layouts/application.html.erb',
97
+ %r{<title>.*?</title>},
98
+ '<title><%= page_title %></title>'
99
+ replace 'app/views/layouts/application.html.erb',
100
+ /[ ]*<%= javascript_include_tag 'application', .*? %>/,
101
+ <<-'ERB'
102
+ <%= javascript_include_tag 'application',
103
+ async: !Rails.application.config.assets.debug,
104
+ defer: true,
105
+ 'data-turbolinks-track': 'reload' %>
106
+ ERB
107
+
108
+ replace 'app/views/layouts/application.html.erb',
109
+ %r{<body>.*?</body>}m,
110
+ File.read(
111
+ File.join(File.dirname(__FILE__),
112
+ 'setup_app_skeleton/application.body.html.erb')
113
+ )
114
+ end
115
+
116
+ def add_user_page
117
+ run_generator 'controller users show' \
118
+ ' --no-assets --no-helper --skip-routes'
119
+ copy 'setup_app_skeleton/spec/controllers/users_controller_spec.rb',
120
+ 'spec/controllers/users_controller_spec.rb'
121
+ copy 'setup_app_skeleton/users_show.html.erb',
122
+ 'app/views/users/show.html.erb'
123
+ replace 'app/controllers/users_controller.rb', 'def show', <<-'RUBY'
124
+ def show
125
+ @user = User.find(params[:id])
126
+ RUBY
127
+ add_route <<~'RUBY'
128
+ resources :users, only: [:show]
129
+ RUBY
130
+ end
131
+
132
+ def add_home_page
133
+ run_generator 'controller home show' \
134
+ ' --no-assets --no-helper --skip-routes'
135
+ add_route <<~'RUBY', append: true
136
+ root to: 'home#show'
137
+ RUBY
138
+ copy_template 'setup_app_skeleton/home_show.html.erb.erb',
139
+ 'app/views/home/show.html.erb'
140
+ end
141
+
142
+ def add_seeds
143
+ copy_template 'setup_app_skeleton/seeds.rb.erb',
144
+ 'db/seeds.rb'
145
+ end
146
+
147
+ def admin_email
148
+ "admin@#{app_name.tr(' ', '_').downcase}.com"
149
+ end
150
+
151
+ def admin_password
152
+ '123456'
153
+ end
154
+
155
+ def brand_primary
156
+ @brand_primary ||= MATERIAL_700_COLORS.sample.downcase
157
+ end
158
+ end
159
+ end
160
+ end
@@ -0,0 +1,19 @@
1
+ .flash-message {
2
+ @extend %thredded--alert;
3
+ }
4
+
5
+ .flash-message--success {
6
+ @extend %thredded--alert--success;
7
+ }
8
+
9
+ .flash-message--error {
10
+ @extend %thredded--alert--danger;
11
+ }
12
+
13
+ .flash-message--notice {
14
+ @extend %thredded--alert--info;
15
+ }
16
+
17
+ .flash-message--alert {
18
+ @extend %thredded--alert--warning;
19
+ }
@@ -0,0 +1,7 @@
1
+ <% %i(success error notice alert).each do |key| %>
2
+ <% if flash[key] %>
3
+ <div class="flash-message flash-message--<%= key %>">
4
+ <%= flash[key] %>
5
+ </div>
6
+ <% end %>
7
+ <% end %>
@@ -0,0 +1,13 @@
1
+ <header role="banner" class="app-header">
2
+ <span class="app-nav-auth">
3
+ <% if current_user %>
4
+ <%= link_to current_user.display_name, user_path(current_user) %>
5
+ |
6
+ <%= link_to t('nav.sign_out'), main_app.destroy_user_session_path,
7
+ method: :delete %>
8
+ <% else %>
9
+ <%= link_to t('nav.sign_in'), main_app.new_user_session_path %>
10
+ <% end %>
11
+ </span>
12
+ <a class="app-nav-logo" href="/"><%= t 'brand.name' %></a>
13
+ </header>
@@ -0,0 +1,6 @@
1
+ $brand-primary: <%= brand_primary %>;
2
+ $text-color: #575d6b;
3
+ $base-font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", "Roboto", "Oxygen", "Ubuntu", "Cantarell", "Fira Sans", "Droid Sans", "Helvetica Neue", Arial, sans-serif;
4
+ $base-font-size: 1rem;
5
+ $base-line-height: 1.5;
6
+ $grid-container-max-width: 43.125rem;
@@ -0,0 +1,7 @@
1
+ <body class="app">
2
+ <div class="app-container">
3
+ <%= render 'shared/header' %>
4
+ <%= render 'shared/flash_messages' unless content_for?(:thredded_page_id) %>
5
+ <div class="app-content-container"><%= yield %></div>
6
+ </div>
7
+ </body>
@@ -0,0 +1,83 @@
1
+ @import "flash-messages";
2
+
3
+ .app {
4
+ @include thredded--clearfix;
5
+ -webkit-font-smoothing: antialiased;
6
+ color: $text-color;
7
+ font-family: $base-font-family;
8
+ font-size: $base-font-size;
9
+ line-height: $base-line-height;
10
+ }
11
+
12
+ .app-container {
13
+ margin: 0 auto;
14
+ max-width: ($grid-container-max-width + 4rem);
15
+ padding: 0 1.2rem 0.75rem 1.2rem;
16
+ @include thredded-media-tablet-and-up {
17
+ padding: 0 2rem 0.75rem 2rem;
18
+ }
19
+ @media (min-width: $grid-container-max-width + 0.01rem) {
20
+ padding-left: 3.5rem;
21
+ padding-right: 3.5rem;
22
+ }
23
+ }
24
+
25
+ .app-header {
26
+ border-bottom: 1px solid #eee;
27
+ a {
28
+ display: inline-block;
29
+ padding: 1rem 0;
30
+ }
31
+ }
32
+
33
+ .app-nav-logo {
34
+ color: $text-color;
35
+ text-decoration: none;
36
+ font-weight: bold;
37
+ }
38
+
39
+ .app-nav-auth {
40
+ float: right;
41
+
42
+ @include thredded-media-mobile {
43
+ font-size: 0;
44
+
45
+ a {
46
+ margin-left: 0.4rem;
47
+ font-size: 1rem;
48
+ }
49
+ }
50
+ }
51
+
52
+ .turbolinks-progress-bar {
53
+ background-color: $brand-primary;
54
+ height: 0.25rem;
55
+ }
56
+
57
+ .form-inputs .input, .form-actions {
58
+ margin: 1rem 0;
59
+ }
60
+
61
+ a {
62
+ @extend %thredded--link;
63
+ }
64
+
65
+ button, input[type="submit"] {
66
+ @extend %thredded--button;
67
+ }
68
+
69
+ form {
70
+ @extend %thredded--form;
71
+ }
72
+
73
+ blockquote {
74
+ @extend %thredded--blockquote;
75
+ }
76
+
77
+ table {
78
+ @extend %thredded--table;
79
+ }
80
+
81
+ hr {
82
+ @extend %thredded--hr;
83
+ }