next_rails_scaffold 0.4.2 → 0.4.3

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: 1d11278bd324e9d9e0578c45bdba6ad9c0593a1b0a840ace0d655bb174e1a896
4
- data.tar.gz: f63cf1c37de59625a87a1bbb24698840987bdf78ab8d98880cfbdc9321326f9c
3
+ metadata.gz: 1cc3d58eda573151a58994e22522dd40c516b5d2626ce68255787fae807fcbb8
4
+ data.tar.gz: 1ce21ee31c2e2aeae77da4f43203e07b23497d40a9bf44bd3df16fc2bf3dde0a
5
5
  SHA512:
6
- metadata.gz: cc2256f5b2240fe34df82adfa383ad54c497de6c63994201d5fe4a4461d89ad85337e349e505ed411d1fab57485f2168f84604bd2a0e9a7df822b6edc6e5305e
7
- data.tar.gz: '0079fa4d104f63c64e127dcbef1a0062bee283df99885a542a1f5b9b8da1a42d318c3d15a278e9f98ab042a3d460ece8d3dc867cc0fb8fd9eab2025d2ad6a386'
6
+ metadata.gz: f96f4a0a7e4bf885d1c431256f83efbaccf61cfa9c94f96448a9191267275e2d6539f11703bbac0984b897b2eccc3a3099d6a9984c10b83e5dd08ced758609c2
7
+ data.tar.gz: ab8d3d422e6ff1a631d28efc6b6a0c6d470928e8601d835ae2792e47ba448acc80abe28d9288594059a684f93436a87831254a6970a6881933215c285885527f
@@ -0,0 +1,98 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "open3"
4
+ require "tty-prompt"
5
+
6
+ module NextRailsScaffold
7
+ module Generators
8
+ NodePackageManagerStruct = Struct.new(:fetch, :run, :add, :lock_file, :version) do
9
+ def to_s = run.split.first
10
+
11
+ def available?
12
+ version.present?
13
+ end
14
+
15
+ def version
16
+ @version ||= NodePackageManager.get_version(to_s)
17
+ end
18
+ end
19
+
20
+ NODE_REQUIRED_VERSION = ENV.fetch("NODE_REQUIRED_VERSION", ">= 18.20")
21
+ NEXT_VERSION = ENV.fetch("NEXT_VERSION", "15.1.6")
22
+
23
+ PACKAGE_MANAGERS = {
24
+ "npm" => NodePackageManagerStruct.new("npx", "npm run", "npm install", "package-lock.json"),
25
+ "yarn" => NodePackageManagerStruct.new("npx", "yarn", "yarn add", "yarn.lock"),
26
+ "pnpm" => NodePackageManagerStruct.new("pnpm dlx", "pnpm", "pnpm add", "pnpm-lock.yaml"),
27
+ "bun" => NodePackageManagerStruct.new("bunx", "bun run", "bun add", "bun.lock.json")
28
+ }.freeze
29
+
30
+ class NodePackageManager
31
+ attr_reader :selected_package_manager
32
+
33
+ def self.get_version(command)
34
+ Open3.capture3(command, "--version").first.gsub(/[^0-9.]/, "")
35
+ rescue Errno::ENOENT
36
+ nil
37
+ end
38
+
39
+ def initialize(shell)
40
+ @prompt = TTY::Prompt.new
41
+ @shell = shell
42
+ end
43
+
44
+ def check_node!
45
+ node_version = self.class.get_version("node")
46
+
47
+ return if Gem::Dependency.new("", NODE_REQUIRED_VERSION).match?("", node_version)
48
+
49
+ raise node_version ? "Your Node version is '#{node_version}'" : "Node not found"
50
+ end
51
+
52
+ def check_pm_version!
53
+ package_manager = @shell.base.options[:package_manager]
54
+
55
+ unless package_manager
56
+ PACKAGE_MANAGERS.each do |manager, details|
57
+ if File.exist?(details.lock_file)
58
+ package_manager = manager
59
+ break
60
+ end
61
+ end
62
+ end
63
+
64
+ until PACKAGE_MANAGERS.keys.include?(package_manager)
65
+ raise "Invalid package manager" unless package_manager.nil?
66
+
67
+ package_manager = @prompt.select(
68
+ "Which package manager do you want to use?",
69
+ PACKAGE_MANAGERS.keys.map { |pm| { name: pm, value: pm, disabled: !PACKAGE_MANAGERS[pm].available? } }
70
+ )
71
+ end
72
+
73
+ @selected_package_manager = PACKAGE_MANAGERS[package_manager]
74
+ end
75
+
76
+ def create_next_app!
77
+ return if File.exist?("package.json")
78
+
79
+ system(
80
+ "#{selected_package_manager.fetch} create-next-app@#{NEXT_VERSION} . --use-#{selected_package_manager} " \
81
+ "--no-app --src-dir --import-alias \"@/*\" #{Rails.env.test? ? "--yes" : ""}"
82
+ )
83
+
84
+ if selected_package_manager.to_s == "yarn" &&
85
+ Gem::Dependency.new("", ">= 2.0").match?("", selected_package_manager.version)
86
+ system("yarn config set nodeLinker node-modules")
87
+ end
88
+ end
89
+
90
+ def install_hygen!
91
+ return if Dir.exist?("_templates")
92
+
93
+ system("#{selected_package_manager.add} -D hygen hygen-add")
94
+ system("#{selected_package_manager.fetch} hygen-add next-rails-scaffold")
95
+ end
96
+ end
97
+ end
98
+ end
@@ -0,0 +1,83 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "rails/generators/rails/scaffold/scaffold_generator"
4
+ require_relative "node_package_manager"
5
+
6
+ module NextRailsScaffold
7
+ module Generators
8
+ class ScaffoldGenerator < Rails::Generators::ScaffoldGenerator
9
+ include ::NextRailsScaffold::Actions
10
+
11
+ source_root File.expand_path("templates", __dir__)
12
+
13
+ argument :attributes, type: :array, default: [], banner: "field:type field:type"
14
+ class_option :package_manager, type: :string, desc: "Package manager to use for frontend project"
15
+ class_option :skip_build, type: :boolean, default: false, desc: "Skip running Next.js build"
16
+ class_option :skip_routes, type: :boolean, default: false, desc: "Skip adding resources to routes.rb"
17
+
18
+ attr_accessor :selected_package_manager
19
+
20
+ def initialize(args, *options) # :nodoc:
21
+ super
22
+ self.attributes = shell.base.attributes
23
+ end
24
+
25
+ def add_resource_route
26
+ return if options[:actions].present? || options[:skip_routes]
27
+
28
+ route "resources :#{file_name.pluralize}", namespace: regular_class_path, scope: "/api"
29
+ end
30
+
31
+ def create_root_folder
32
+ empty_directory "frontend"
33
+ end
34
+
35
+ # Check Javascript dependencies and create a new Next.js project. Install the the useful packages and create the
36
+ # scaffold code for frontend application.
37
+ def create_frontend_project
38
+ return say_status :remove, "skip frontend folder", :yellow if shell.base.behavior == :revoke
39
+
40
+ append_gitignore!
41
+
42
+ node_package_manager = NodePackageManager.new(shell)
43
+
44
+ inside("frontend") do
45
+ node_package_manager.check_node!
46
+ node_package_manager.check_pm_version!
47
+ node_package_manager.create_next_app!
48
+ node_package_manager.install_hygen!
49
+
50
+ return if Rails.env.test?
51
+
52
+ selected_package_manager = node_package_manager.selected_package_manager
53
+ language = File.exist?("tsconfig.json") ? "typescript" : "javascript"
54
+
55
+ run("#{selected_package_manager.fetch} hygen scaffold #{language} #{name} #{mapped_attributes.join(" ")}")
56
+ if !options[:skip_build] && !@prompt.no?("Do you want to build your Next.js project?")
57
+ run("#{selected_package_manager.run} build")
58
+ end
59
+ end
60
+ end
61
+
62
+ private
63
+
64
+ def append_gitignore!
65
+ path = File.join(destination_root, ".gitignore")
66
+
67
+ return unless File.exist?(path)
68
+
69
+ rows = <<~HEREDOC
70
+
71
+ # Ignoring node modules for Rails and Next.js projects
72
+ node_modules/
73
+ HEREDOC
74
+
75
+ append_to_file path, rows
76
+ end
77
+
78
+ def mapped_attributes
79
+ attributes.map { |attr| "#{attr.name}:#{attr.type}" }
80
+ end
81
+ end
82
+ end
83
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module NextRailsScaffold
4
- VERSION = "0.4.2"
4
+ VERSION = "0.4.3"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: next_rails_scaffold
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.2
4
+ version: 0.4.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Raphael Araújo
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2025-02-04 00:00:00.000000000 Z
11
+ date: 2025-02-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -68,8 +68,9 @@ files:
68
68
  - config/routes.rb
69
69
  - lib/generators/next_rails_scaffold/USAGE
70
70
  - lib/generators/next_rails_scaffold/install_generator.rb
71
+ - lib/generators/next_rails_scaffold/node_package_manager.rb
72
+ - lib/generators/next_rails_scaffold/scaffold_generator.rb
71
73
  - lib/generators/next_rails_scaffold/templates/config/initializers/next_rails_scaffold.rb
72
- - lib/generators/rails/next_rails_scaffold/next_rails_scaffold_generator.rb
73
74
  - lib/next_rails_scaffold.rb
74
75
  - lib/next_rails_scaffold/actions.rb
75
76
  - lib/next_rails_scaffold/engine.rb
@@ -1,158 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require "tty-prompt"
4
-
5
- PackageManager = Struct.new(:fetch, :run, :add, :lock_file, :version) do
6
- def to_s = run.split.first
7
- end
8
-
9
- module Rails
10
- class NextRailsScaffoldGenerator < Rails::Generators::NamedBase
11
- include ::NextRailsScaffold::Actions
12
-
13
- source_root File.expand_path("templates", __dir__)
14
-
15
- PACKAGE_MANAGERS = {
16
- "npm" => PackageManager.new("npx", "npm run", "npm install", "package-lock.json"),
17
- "yarn" => PackageManager.new("yarn dlx", "yarn", "yarn add", "yarn.lock"),
18
- "pnpm" => PackageManager.new("pnpm dlx", "pnpm", "pnpm add", "pnpm-lock.yaml"),
19
- "bun" => PackageManager.new("bunx", "bun run", "bun add", "bun.lock.json")
20
- }.freeze
21
- NODE_REQUIRED_VERSION = ENV.fetch("NODE_REQUIRED_VERSION", ">= 18.20")
22
- NEXT_VERSION = ENV.fetch("NEXT_VERSION", "15.1.6")
23
-
24
- argument :attributes, type: :array, default: [], banner: "field:type field:type"
25
- class_option :package_manager, type: :string, desc: "Package manager to use for frontend project"
26
- class_option :skip_build, type: :boolean, default: false, desc: "Skip running Next.js build"
27
- class_option :skip_routes, type: :boolean, default: false, desc: "Skip adding resources to routes.rb"
28
-
29
- attr_accessor :selected_package_manager
30
-
31
- def initialize(args, *options) # :nodoc:
32
- super
33
-
34
- @prompt = TTY::Prompt.new
35
-
36
- self.attributes = shell.base.attributes
37
- end
38
-
39
- # Properly nests namespaces passed into a generator
40
- #
41
- # $ bin/rails generate resource admin/users/products
42
- #
43
- # should give you
44
- #
45
- # scope '/api' do
46
- # namespace :admin do
47
- # namespace :users do
48
- # resources :products
49
- # end
50
- # end
51
- # end
52
- def add_resource_route
53
- return if options[:actions].present? || options[:skip_routes]
54
-
55
- route "resources :#{file_name.pluralize}", namespace: regular_class_path, scope: "/api"
56
- end
57
-
58
- # Check Javascript dependencies and create a new Next.js project. Install the the useful packages and create the
59
- # scaffold code for frontend application.
60
- def create_frontend_project
61
- return say_status :remove, "skip frontend folder", :yellow if shell.base.behavior == :revoke
62
-
63
- append_gitignore!
64
-
65
- empty_directory "frontend"
66
-
67
- inside("frontend") do
68
- check_node!
69
- check_pm_version!
70
- create_next_app!
71
- install_hygen!
72
-
73
- language = File.exist?("tsconfig.json") ? "typescript" : "javascript"
74
-
75
- run("#{selected_package_manager} hygen scaffold #{language} #{name} #{mapped_attributes.join(" ")}")
76
- if !options[:skip_build] && !@prompt.no?("Do you want to build your Next.js project?")
77
- run("#{selected_package_manager.run} build")
78
- end
79
- end
80
- end
81
-
82
- private
83
-
84
- def check_node!
85
- node_version = run("node --version", capture: true).gsub(/[^0-9.]/, "")
86
-
87
- if Gem::Dependency.new("", NODE_REQUIRED_VERSION).match?("", node_version)
88
- log :node_version, "Your Node version is '#{node_version}'"
89
- else
90
- say_status :node_version, "You need to have a Node version '#{NODE_REQUIRED_VERSION}'", :red
91
- abort
92
- end
93
- end
94
-
95
- def check_pm_version!
96
- package_manager = shell.base.options[:package_manager]
97
-
98
- unless package_manager
99
- PACKAGE_MANAGERS.each do |manager, details|
100
- if File.exist?(details.lock_file)
101
- package_manager = manager
102
- break
103
- end
104
- end
105
- end
106
-
107
- until PACKAGE_MANAGERS.keys.include?(package_manager)
108
- puts "Invalid package manager" unless package_manager.nil?
109
-
110
- package_manager = @prompt.select("Which package manager do you want to use?", PACKAGE_MANAGERS.keys)
111
- end
112
-
113
- self.selected_package_manager = PACKAGE_MANAGERS[package_manager]
114
-
115
- selected_package_manager.version = run("#{selected_package_manager} --version", capture: true).gsub(/[^0-9.]/, "")
116
- log :package_manager, "Using #{selected_package_manager} version '#{selected_package_manager.version}'"
117
- end
118
-
119
- def append_gitignore!
120
- rows = <<~HEREDOC
121
-
122
- # Ignoring node modules for Rails and Next.js projects
123
- node_modules/
124
- HEREDOC
125
-
126
- append_to_file ".gitignore", rows
127
- end
128
-
129
- def create_next_app!
130
- return if File.exist?("package.json")
131
-
132
- run(
133
- "#{selected_package_manager.fetch} create-next-app@#{NEXT_VERSION} . " \
134
- "--no-app --src-dir --import-alias \"@/*\""
135
- )
136
-
137
- if selected_package_manager.to_s == "yarn" &&
138
- Gem::Dependency.new("", ">= 2.0").match?("", selected_package_manager.version)
139
- run("yarn config set nodeLinker node-modules")
140
- end
141
- end
142
-
143
- def install_hygen!
144
- return if Dir.exist?("_templates")
145
-
146
- run("#{selected_package_manager.add} -D hygen hygen-add")
147
- run("#{selected_package_manager} hygen-add next-rails-scaffold")
148
- end
149
-
150
- def mapped_attributes
151
- attributes.map { |attr| "#{attr.name}:#{attr.type}" }
152
- end
153
-
154
- def exit_on_failure?
155
- true
156
- end
157
- end
158
- end