dockerfile-rails 1.6.25 → 1.7.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: 749745baff7e3b0f67b72f9f94c2df9086c344c9665e2d67498c02c33cfbcbab
4
- data.tar.gz: 1b62d4bcf87fd0872057ee0e796b8f529a3b29b811e13447e7ac7df60961ab80
3
+ metadata.gz: 8309aa1e1fe7194297188df68c64c458d2fc7e892c0d4b0c0dadc9fe9b1d3a6e
4
+ data.tar.gz: c0d684a6bde26b27aa40c12e8cdd24bbdbd15d220258f48468ac6d4780fd15d3
5
5
  SHA512:
6
- metadata.gz: a88d05eac975d08d6ad47766300a996740c56e7a273488c7ec4e3f59729841d3edf132d91740a82410b7e60aff8017fb5aeabd15095b7ea0673f3088d08dd49f
7
- data.tar.gz: b78e868ec797f8c2bdb01e0afc7214e60b7a134414a06b15cc2151e8fcee62e6a59cfcbdde6898af22bb38a3742f4af433187b0e3aaa323c6dd85f956df3f012
6
+ metadata.gz: 0444b3658976d0b1f3e363848616a0774886e24a4c156daf0102f40c983ecb902f927af387be92c0f91447fad2c521a8ea1e378ca799d0a967400f8ffadc8ada
7
+ data.tar.gz: b174840c7d365257c77f706d82ac979a231d2cb91c633fcc79e2806f9deaa4ccdf1818e389bd2c6d9d115e978bb823f97ff091f9344f75121cd5ef0025441ace
data/README.md CHANGED
@@ -67,6 +67,7 @@ are actually using. But should you be using DATABASE_URL, for example, at runti
67
67
  additional support may be needed:
68
68
 
69
69
  * `--litefs` - use [LiteFS](https://fly.io/docs/litefs/)
70
+ * `--litestream` - use [LiteFS](https://litestream.io/)
70
71
  * `--mysql` - add mysql libraries
71
72
  * `--postgresql` - add postgresql libraries
72
73
  * `--redis` - add redis libraries
@@ -2,6 +2,7 @@
2
2
 
3
3
  require "erb"
4
4
  require "json"
5
+ require "shellwords"
5
6
  require_relative "../dockerfile-rails/scanner.rb"
6
7
 
7
8
  class DockerfileGenerator < Rails::Generators::Base
@@ -15,10 +16,11 @@ class DockerfileGenerator < Rails::Generators::Base
15
16
  "compose" => false,
16
17
  "fullstaq" => false,
17
18
  "gemfile-updates" => true,
18
- "jemalloc" => false,
19
+ "jemalloc" => true,
19
20
  "label" => {},
20
21
  "link" => false,
21
22
  "litefs" => false,
23
+ "litestream" => false,
22
24
  "lock" => true,
23
25
  "max-idle" => nil,
24
26
  "migrate" => "",
@@ -74,7 +76,8 @@ class DockerfileGenerator < Rails::Generators::Base
74
76
  "node-gyp" => "gyp",
75
77
  "pkg-config" => "pkgconfig",
76
78
  "python" => "python3",
77
- "python-is-python3" => "python3"
79
+ "python-is-python3" => "python3",
80
+ "sqlite3" => "sqlite",
78
81
  }
79
82
 
80
83
  # load defaults from config file
@@ -162,6 +165,9 @@ class DockerfileGenerator < Rails::Generators::Base
162
165
  class_option :litefs, type: :boolean, default: OPTION_DEFAULTS.litefs,
163
166
  desc: "replicate sqlite3 databases using litefs"
164
167
 
168
+ class_option :litestream, type: :boolean, default: OPTION_DEFAULTS.litestream,
169
+ desc: "replicate sqlite3 databases using litesream"
170
+
165
171
  class_option :tigris, type: :boolean, default: OPTION_DEFAULTS.tigris,
166
172
  desc: "configure active storage to use tigris"
167
173
 
@@ -346,6 +352,10 @@ class DockerfileGenerator < Rails::Generators::Base
346
352
  fly_attach_consul
347
353
  end
348
354
 
355
+ if using_litestream?
356
+ template "litestream.rake.erb", "lib/tasks/litestream.rake"
357
+ end
358
+
349
359
  if File.exist?("fly.toml") && (fly_processes || !options.prepare || options.swap || deploy_database == "sqlite3")
350
360
  if File.stat("fly.toml").size > 0
351
361
  template "fly.toml.erb", "fly.toml"
@@ -488,6 +498,10 @@ private
488
498
  @gemfile.include?("litestack")
489
499
  end
490
500
 
501
+ def using_litestream?
502
+ options.litestream?
503
+ end
504
+
491
505
  def using_node?
492
506
  return @using_node if @using_node != nil
493
507
  return if using_bun?
@@ -594,6 +608,10 @@ private
594
608
  system "bundle add mysql2 --skip-install" unless has_mysql_gem?
595
609
  end
596
610
 
611
+ if options.litestream?
612
+ system "bundle add litestream --skip-install" unless @gemfile.include? "litestream"
613
+ end
614
+
597
615
  if options.redis? || using_redis?
598
616
  system "bundle add redis --skip-install" unless @gemfile.include? "redis"
599
617
  end
@@ -662,19 +680,30 @@ private
662
680
  end
663
681
 
664
682
  def base_packages
665
- packages = []
683
+ packages = %w(curl) # work with the default healthcheck strategy in Kamal
666
684
  packages += @@packages["base"] if @@packages["base"]
667
685
 
686
+ packages << "libjemalloc2" if options.jemalloc? && !options.fullstaq?
687
+
688
+ # start with databases: sqlite3, postgres, mysql
689
+ packages << "postgresql-client" if options.postgresql? || @postgresql
690
+ packages << "default-mysql-client" if options.mysql? || @mysql
691
+ packages << "freetds-bin" if options.sqlserver? || @sqlserver
692
+ if options.sqlite3? || @sqlite3
693
+ packages << "sqlite3" unless packages.include? "sqlite3"
694
+ end
695
+
696
+ # ActiveStorage preview support
697
+ packages << "libvips" if @gemfile.include? "ruby-vips"
698
+
668
699
  if using_execjs?
669
700
  if node_version == "lts"
670
701
  packages += %w(nodejs npm)
671
- else
672
- packages += %w(curl)
673
702
  end
674
703
  end
675
704
 
676
705
  if using_puppeteer?
677
- packages += %w(curl gnupg)
706
+ packages += %w(gnupg)
678
707
  end
679
708
 
680
709
  # charlock_holmes. Placed here as the library itself is
@@ -725,9 +754,6 @@ private
725
754
  # add git if needed to install gems
726
755
  packages << "git" if @git
727
756
 
728
- # ActiveStorage preview support
729
- packages << "libvips" if @gemfile.include? "ruby-vips"
730
-
731
757
  # Rmagick gem
732
758
  packages += %w[pkg-config libmagickwand-dev] if @gemfile.include? "rmagick"
733
759
 
@@ -736,7 +762,7 @@ private
736
762
  packages += %w(node-gyp pkg-config)
737
763
 
738
764
  unless using_execjs? || using_puppeteer?
739
- packages << "curl"
765
+ # packages << "curl"
740
766
  end
741
767
 
742
768
  # module build process depends on Python, and debian changed
@@ -762,7 +788,7 @@ private
762
788
  end
763
789
 
764
790
  if using_bun?
765
- packages += %w(curl unzip)
791
+ packages += %w(unzip)
766
792
  end
767
793
 
768
794
  if options.alpine?
@@ -773,18 +799,9 @@ private
773
799
  end
774
800
 
775
801
  def deploy_packages
776
- packages = %w(curl) # work with the default healthcheck strategy in MRSK
802
+ packages = []
777
803
  packages += @@packages["deploy"] if @@packages["deploy"]
778
804
 
779
- # start with databases: sqlite3, postgres, mysql
780
- packages << "postgresql-client" if options.postgresql? || @postgresql
781
- packages << "default-mysql-client" if options.mysql? || @mysql
782
- packages << "freetds-bin" if options.sqlserver? || @sqlserver
783
- packages << "libjemalloc2" if options.jemalloc? && !options.fullstaq?
784
- if options.sqlite3? || @sqlite3
785
- packages << "libsqlite3-0" unless packages.include? "sqlite3"
786
- end
787
-
788
805
  # litefs
789
806
  packages += ["ca-certificates", "fuse3", "sudo"] if options.litefs?
790
807
 
@@ -865,7 +882,7 @@ private
865
882
  packages = []
866
883
 
867
884
  if using_passenger?
868
- packages += %w(gnupg curl)
885
+ packages += %w(curl gnupg)
869
886
  repos += [
870
887
  "curl https://oss-binaries.phusionpassenger.com/auto-software-signing-gpg-key.txt |",
871
888
  " gpg --dearmor > /etc/apt/trusted.gpg.d/phusion.gpg &&",
@@ -891,7 +908,7 @@ private
891
908
  packages = []
892
909
 
893
910
  if using_puppeteer? && deploy_packages.include?("google-chrome-stable")
894
- packages += %w(gnupg curl)
911
+ packages += %w(gnupg)
895
912
  repos += [
896
913
  "curl https://dl-ssl.google.com/linux/linux_signing_key.pub |",
897
914
  " gpg --dearmor > /etc/apt/trusted.gpg.d/google-archive.gpg &&",
@@ -979,8 +996,8 @@ private
979
996
  end
980
997
 
981
998
  if options.jemalloc? && !options.fullstaq?
982
- env["LD_PRELOAD"] = "libjemalloc.so.2"
983
- env["MALLOC_CONF"] = "dirty_decay_ms:1000,narenas:2,background_thread:true"
999
+ # env["LD_PRELOAD"] = "libjemalloc.so.2"
1000
+ # env["MALLOC_CONF"] = "dirty_decay_ms:1000,narenas:2,background_thread:true"
984
1001
  end
985
1002
 
986
1003
  if using_puppeteer?
@@ -1133,6 +1150,30 @@ private
1133
1150
  end
1134
1151
  end
1135
1152
 
1153
+ def start_command
1154
+ if !options.procfile.blank?
1155
+ ["foreman", "start", "--procfile=#{options.procfile}"]
1156
+ elsif procfile.size > 1
1157
+ ["foreman", "start", "--procfile=Procfile.prod"]
1158
+ else
1159
+ command = Shellwords.split(procfile.values.first)
1160
+
1161
+ if command.first == "./bin/thrust"
1162
+ command[1..]
1163
+ else
1164
+ command
1165
+ end
1166
+ end
1167
+ end
1168
+
1169
+ def shellescape(string)
1170
+ if %r{\A[-\w._/= ]+\z}.match?(string)
1171
+ string.inspect
1172
+ else
1173
+ Shellwords.escape(string)
1174
+ end
1175
+ end
1176
+
1136
1177
  def node_version
1137
1178
  return unless using_node? || using_execjs?
1138
1179
 
@@ -1252,6 +1293,10 @@ private
1252
1293
  }
1253
1294
  end
1254
1295
 
1296
+ if using_litestream? && base[:rails]
1297
+ base[:rails] = "./bin/rake litestream:run " + base[:rails]
1298
+ end
1299
+
1255
1300
  if solidq_launcher == :procfile
1256
1301
  base["solidq"] = "bundle exec rake solid_queue:start"
1257
1302
  end
@@ -1263,6 +1308,10 @@ private
1263
1308
  options.thruster? || @gemfile.include?("thruster")
1264
1309
  end
1265
1310
 
1311
+ def using_kamal?
1312
+ @gemfile.include?("kamal")
1313
+ end
1314
+
1266
1315
  def fly_processes
1267
1316
  return unless File.exist? "fly.toml"
1268
1317
  return unless using_sidekiq? || using_solidq? || using_thruster?
@@ -1468,6 +1517,10 @@ private
1468
1517
  list[primary] = list[primary].sub(/^.*thrust /, "")
1469
1518
  end
1470
1519
 
1520
+ if using_litestream? && list["app"]
1521
+ list["app"] = "./bin/rake litestream:run #{list["app"]}"
1522
+ end
1523
+
1471
1524
  if toml.include? "[processes]"
1472
1525
  toml.sub!(/\[processes\].*?(\n\n|\n?\z)/m, "[processes]\n" +
1473
1526
  list.map { |name, cmd| " #{name} = #{cmd.inspect}" }.join("\n") + '\1')
@@ -1,6 +1,15 @@
1
- # syntax = docker/dockerfile:1
1
+ # syntax=docker/dockerfile:1
2
+ # check=error=true
3
+ <% if using_kamal? -%>
2
4
 
3
- # Make sure RUBY_VERSION matches the Ruby version in .ruby-version and Gemfile
5
+ # This Dockerfile is designed for production, not development. Use with Kamal or build'n'run by hand:
6
+ # docker build -t demo .
7
+ # docker run -d -p 80:80 -e RAILS_MASTER_KEY=<value from config/master.key> --name demo demo
8
+
9
+ # For a containerized dev environment, see Dev Containers: https://guides.rubyonrails.org/getting_started_with_devcontainer.html
10
+ <% end -%>
11
+
12
+ # Make sure RUBY_VERSION matches the Ruby version in .ruby-version
4
13
  ARG RUBY_VERSION=<%= RUBY_VERSION %>
5
14
  <% if api_client_dir -%>
6
15
  <%= render partial: 'node_client' %>
@@ -27,18 +36,18 @@ WORKDIR /rails
27
36
  ARG <%= base_args.map {|key, value| "#{key}=#{value.inspect}"}.join(" \\\n ") %>
28
37
 
29
38
  <% end -%>
30
- # Set production environment
31
- ENV <%= base_env.join(" \\\n ") %>
32
-
33
39
  # Update gems and bundler
34
40
  RUN gem update --system <% if RUBY_VERSION.start_with? '2' %>3.4.22 <% end %>--no-document && \
35
41
  gem install -N <%= base_gems.join(" ") %>
36
42
 
37
43
  <% unless base_packages.empty? -%>
38
- # Install packages<% unless base_requirements.empty? -%> needed to install <%= base_requirements %><% end %>
44
+ # Install base packages<% unless base_requirements.empty? -%> needed to install <%= base_requirements %><% end %>
39
45
  <%= render partial: 'apt_install', locals: {packages: base_packages, clean: true, repos: base_repos} %>
40
46
 
41
47
  <% end -%>
48
+ # Set production environment
49
+ ENV <%= base_env.join(" \\\n ") %>
50
+
42
51
  <% if using_execjs? and node_version != 'lts' -%>
43
52
  <%= render partial: 'install_node', locals: {yarn_version: nil} %>
44
53
 
@@ -54,7 +63,7 @@ FROM base AS <%= parallel? ? 'pre' : '' %>build
54
63
 
55
64
  <% end -%>
56
65
  # Install packages needed to build gems<%= using_node? ? " and node modules" : "" %>
57
- <%= render partial: 'apt_install', locals: {packages: build_packages, clean: false, repos: ''} %>
66
+ <%= render partial: 'apt_install', locals: {packages: build_packages, clean: true, repos: ''} %>
58
67
 
59
68
  <% if parallel? -%>
60
69
 
@@ -113,13 +122,12 @@ RUN --mount=type=cache,id=bld-gem-cache,sharing=locked,target=/srv/vendor \
113
122
  RUN --mount=type=secret,id=gemserver_credentials,target=/kaniko/gemserver_credentials \
114
123
  <%= private_gemserver_env_variable_name %>="$(cat /kaniko/gemserver_credentials)" && \
115
124
  export <%= private_gemserver_env_variable_name %> && \
116
- bundle install<% if depend_on_bootsnap? && options.precompile != "defer" -%> && \
117
- bundle exec bootsnap precompile --gemfile<% end %> && \
125
+ bundle install && \
118
126
  <% else -%>
119
- RUN <% if options["precompiled-gems"] != true %>bundle config set force_ruby_platform true && \<%= "\n " %><% end %>bundle install<% if depend_on_bootsnap? && options.precompile != "defer" -%> && \
120
- bundle exec bootsnap precompile --gemfile<% end %> && \
127
+ RUN <% if options["precompiled-gems"] != true %>bundle config set force_ruby_platform true && \<%= "\n " %><% end %>bundle install && \
121
128
  <% end -%>
122
- rm -rf ~/.bundle/ "${BUNDLE_PATH}"/ruby/*/cache "${BUNDLE_PATH}"/ruby/*/bundler/gems/*/.git
129
+ rm -rf ~/.bundle/ "${BUNDLE_PATH}"/ruby/*/cache "${BUNDLE_PATH}"/ruby/*/bundler/gems/*/.git<% if depend_on_bootsnap? && options.precompile != "defer" -%> && \
130
+ bundle exec bootsnap precompile --gemfile<% end %>
123
131
 
124
132
  <% end -%>
125
133
  <% if using_passenger? -%>
@@ -298,7 +306,11 @@ COPY <<-"EOF" /rails/Procfile.prod
298
306
  EOF
299
307
 
300
308
  <% end -%>
309
+ <% if using_thruster? -%>
310
+ # Start server via Thruster by default, this can be overwritten at runtime
311
+ <% else -%>
301
312
  # Start the server by default, this can be overwritten at runtime
313
+ <% end -%>
302
314
  EXPOSE <%= using_thruster? ? '80' : '3000' %>
303
315
  <% if deploy_database == 'sqlite3' -%>
304
316
  VOLUME /data
@@ -4,6 +4,14 @@
4
4
  #!/bin/bash -e
5
5
  <% end -%>
6
6
 
7
+ <% if options.jemalloc? -%>
8
+ # Enable jemalloc for reduced memory usage and latency.
9
+ if [ -z "${LD_PRELOAD+x}" ]; then
10
+ LD_PRELOAD=$(find /usr/lib -name libjemalloc.so.2 -print -quit)
11
+ export LD_PRELOAD
12
+ fi
13
+
14
+ <% end -%>
7
15
  <% if options.swap && !File.exist?("fly.toml")-%>
8
16
  <% if run_as_root? or using_passenger? -%>
9
17
  <% @space = "" -%>
@@ -36,17 +44,13 @@ fi
36
44
  <% end -%>
37
45
  <% if options.prepare -%>
38
46
  <% if !options.procfile.blank? -%>
39
- if [ "${*}" == "foreman start --procfile=<%= options.procfile %>" ]; then
47
+ # If running the specified procfile then create or migrate existing database
40
48
  <% elsif procfile.size > 1 -%>
41
49
  # If running the production procfile then create or migrate existing database
42
- if [ "${*}" == "foreman start --procfile=Procfile.prod" ]; then
43
- <% elsif procfile.values.first.start_with? "./bin/rails server" -%>
44
- # If running the rails server then create or migrate existing database
45
- if [ "${1}" == "./bin/rails" ] && [ "${2}" == "server" ]<% if using_litefs? %> && [ "$FLY_REGION" == "$PRIMARY_REGION" ]<%end%>; then
46
50
  <% else -%>
47
51
  # If running the rails server then create or migrate existing database
48
- if [ "${*}" == <%= procfile.values.first.inspect %> <% if using_litefs? %>-a "$FLY_REGION" == "$PRIMARY_REGION" <%end%>]; then
49
52
  <% end -%>
53
+ if <%= start_command.map.with_index {|word, index| "[ \"${@: #{index - start_command.length}:1}\" == #{shellescape(word)} ]"}.join(" && ") %><% if using_litefs? %> && [ "$FLY_REGION" == "$PRIMARY_REGION" ]<%end%>; then
50
54
  <% if options.precompile == "defer" -%>
51
55
  ./bin/rails assets:precompile
52
56
  <% end -%>
@@ -2,13 +2,13 @@
2
2
 
3
3
  # Ignore git directory.
4
4
  /.git/
5
+ /.gitignore
5
6
 
6
7
  # Ignore bundler config.
7
8
  /.bundle
8
9
 
9
- # Ignore all environment files (except templates).
10
+ # Ignore all environment files.
10
11
  /.env*
11
- !/.env*.erb
12
12
 
13
13
  # Ignore all default key files.
14
14
  /config/master.key
@@ -50,4 +50,18 @@ GEMSERVER_CREDENTIALS.secret.txt
50
50
  <% end -%>
51
51
  /public/assets
52
52
  <% end -%>
53
+
54
+ # Ignore CI service files.
55
+ /.github
56
+
57
+ # Ignore Kamal files.
58
+ /config/deploy*.yml
59
+ /.kamal
60
+
61
+ # Ignore development files
62
+ /.devcontainer
63
+
64
+ # Ignore Docker-related files
65
+ /.dockerignore
66
+ /Dockerfile*
53
67
  <%= more_docker_ignores -%>
@@ -0,0 +1,55 @@
1
+ LITESTREAM_CONFIG = ENV["LITESTREAM_CONFIG"] || Rails.root.join("tmp/litestream.yml").to_s
2
+
3
+ LITESTREAM_TEMPLATE = <<-EOF
4
+ # This is the configuration file for litestream.
5
+ #
6
+ # For more details, see: https://litestream.io/reference/config/
7
+ #
8
+ dbs:
9
+ <%% for db in @dbs -%>
10
+ - path: <%%= db %>
11
+ replicas:
12
+ - type: s3
13
+ endpoint: $AWS_ENDPOINT_URL_S3
14
+ bucket: $BUCKET_NAME
15
+ path: storage/<%%= File.basename(db) %>
16
+ access-key-id: $AWS_ACCESS_KEY_ID
17
+ secret-access-key: $AWS_SECRET_ACCESS_KEY
18
+ <%% end -%>
19
+ EOF
20
+
21
+ namespace :litestream do
22
+ task prepare: "db:load_config" do
23
+ require "erubi"
24
+
25
+ @dbs =
26
+ ActiveRecord::Base
27
+ .configurations
28
+ .configs_for(env_name: "production", include_hidden: true)
29
+ .select { |config| [ "sqlite3", "litedb" ].include? config.adapter }
30
+ .map(&:database)
31
+
32
+ result = eval(Erubi::Engine.new(LITESTREAM_TEMPLATE).src)
33
+
34
+ unless File.exist?(LITESTREAM_CONFIG) && File.read(LITESTREAM_CONFIG) == result
35
+ File.write(LITESTREAM_CONFIG, result)
36
+ end
37
+
38
+ @dbs.each do |db|
39
+ next if File.exist?(db) or !ENV["BUCKET_NAME"]
40
+ system "litestream restore -config #{LITESTREAM_CONFIG} -if-replica-exists #{db}"
41
+ exit $?.exitstatus unless $?.exitstatus == 0
42
+ end
43
+ end
44
+
45
+ task :run do
46
+ require "shellwords"
47
+
48
+ exec(*%w[bundle exec litestream replicate -config],
49
+ LITESTREAM_CONFIG, "-exec", Shellwords.join(ARGV[1..-1]))
50
+ end
51
+ end
52
+
53
+ namespace :db do
54
+ task prepare: "litestream:prepare"
55
+ end
metadata CHANGED
@@ -1,14 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: dockerfile-rails
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.6.25
4
+ version: 1.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sam Ruby
8
- autorequire:
9
8
  bindir: bin
10
9
  cert_chain: []
11
- date: 2024-12-12 00:00:00.000000000 Z
10
+ date: 2025-01-06 00:00:00.000000000 Z
12
11
  dependencies:
13
12
  - !ruby/object:Gem::Dependency
14
13
  name: rails
@@ -24,7 +23,6 @@ dependencies:
24
23
  - - ">="
25
24
  - !ruby/object:Gem::Version
26
25
  version: 3.0.0
27
- description:
28
26
  email: rubys@intertwingly.net
29
27
  executables: []
30
28
  extensions: []
@@ -52,6 +50,7 @@ files:
52
50
  - lib/generators/templates/dockerignore.erb
53
51
  - lib/generators/templates/fly.toml.erb
54
52
  - lib/generators/templates/litefs.yml.erb
53
+ - lib/generators/templates/litestream.rake.erb
55
54
  - lib/generators/templates/node-version.erb
56
55
  - lib/generators/templates/rollbar.rb.erb
57
56
  - lib/generators/templates/sentry.rb.erb
@@ -60,7 +59,6 @@ licenses:
60
59
  - MIT
61
60
  metadata:
62
61
  homepage_uri: https://github.com/fly-apps/dockerfile-rails
63
- post_install_message:
64
62
  rdoc_options: []
65
63
  require_paths:
66
64
  - lib
@@ -75,8 +73,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
75
73
  - !ruby/object:Gem::Version
76
74
  version: '0'
77
75
  requirements: []
78
- rubygems_version: 3.5.18
79
- signing_key:
76
+ rubygems_version: 3.6.2
80
77
  specification_version: 4
81
78
  summary: Dockerfile generator for Rails
82
79
  test_files: []