inertia_rails-contrib 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (78) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGELOG.md +21 -0
  3. data/LICENSE.txt +21 -0
  4. data/README.md +187 -0
  5. data/lib/generators/inertia/controller/controller_generator.rb +16 -0
  6. data/lib/generators/inertia/controller/templates/controller.rb.tt +10 -0
  7. data/lib/generators/inertia/install/install_generator.rb +151 -0
  8. data/lib/generators/inertia/install/templates/assets/inertia.svg +1 -0
  9. data/lib/generators/inertia/install/templates/assets/react.svg +1 -0
  10. data/lib/generators/inertia/install/templates/assets/svelte.svg +1 -0
  11. data/lib/generators/inertia/install/templates/assets/vite_ruby.svg +1 -0
  12. data/lib/generators/inertia/install/templates/assets/vue.svg +1 -0
  13. data/lib/generators/inertia/install/templates/controller.rb +7 -0
  14. data/lib/generators/inertia/install/templates/initializer.rb +4 -0
  15. data/lib/generators/inertia/install/templates/react/InertiaExample.jsx +60 -0
  16. data/lib/generators/inertia/install/templates/react/InertiaExample.module.css +80 -0
  17. data/lib/generators/inertia/install/templates/react/inertia.js +34 -0
  18. data/lib/generators/inertia/install/templates/svelte/InertiaExample.svelte +116 -0
  19. data/lib/generators/inertia/install/templates/svelte/inertia.js +30 -0
  20. data/lib/generators/inertia/install/templates/svelte/svelte.config.js +7 -0
  21. data/lib/generators/inertia/install/templates/vue/InertiaExample.vue +117 -0
  22. data/lib/generators/inertia/install/templates/vue/inertia.js +33 -0
  23. data/lib/generators/inertia/scaffold/scaffold_generator.rb +16 -0
  24. data/lib/generators/inertia/scaffold_controller/scaffold_controller_generator.rb +56 -0
  25. data/lib/generators/inertia/scaffold_controller/templates/controller.rb.tt +102 -0
  26. data/lib/generators/inertia_templates/controller/controller_generator.rb +12 -0
  27. data/lib/generators/inertia_templates/controller/templates/react/view.jsx.tt +8 -0
  28. data/lib/generators/inertia_templates/controller/templates/svelte/view.svelte.tt +2 -0
  29. data/lib/generators/inertia_templates/controller/templates/vue/view.vue.tt +4 -0
  30. data/lib/generators/inertia_templates/scaffold/scaffold_generator.rb +12 -0
  31. data/lib/generators/inertia_templates/scaffold/templates/react/Edit.jsx.tt +36 -0
  32. data/lib/generators/inertia_templates/scaffold/templates/react/Form.jsx.tt +111 -0
  33. data/lib/generators/inertia_templates/scaffold/templates/react/Index.jsx.tt +26 -0
  34. data/lib/generators/inertia_templates/scaffold/templates/react/New.jsx.tt +27 -0
  35. data/lib/generators/inertia_templates/scaffold/templates/react/One.jsx.tt +26 -0
  36. data/lib/generators/inertia_templates/scaffold/templates/react/Show.jsx.tt +39 -0
  37. data/lib/generators/inertia_templates/scaffold/templates/svelte/Edit.svelte.tt +37 -0
  38. data/lib/generators/inertia_templates/scaffold/templates/svelte/Form.svelte.tt +96 -0
  39. data/lib/generators/inertia_templates/scaffold/templates/svelte/Index.svelte.tt +42 -0
  40. data/lib/generators/inertia_templates/scaffold/templates/svelte/New.svelte.tt +30 -0
  41. data/lib/generators/inertia_templates/scaffold/templates/svelte/One.svelte.tt +28 -0
  42. data/lib/generators/inertia_templates/scaffold/templates/svelte/Show.svelte.tt +46 -0
  43. data/lib/generators/inertia_templates/scaffold/templates/vue/Edit.vue.tt +36 -0
  44. data/lib/generators/inertia_templates/scaffold/templates/vue/Form.vue.tt +94 -0
  45. data/lib/generators/inertia_templates/scaffold/templates/vue/Index.vue.tt +31 -0
  46. data/lib/generators/inertia_templates/scaffold/templates/vue/New.vue.tt +29 -0
  47. data/lib/generators/inertia_templates/scaffold/templates/vue/One.vue.tt +26 -0
  48. data/lib/generators/inertia_templates/scaffold/templates/vue/Show.vue.tt +44 -0
  49. data/lib/generators/inertia_tw_templates/controller/controller_generator.rb +12 -0
  50. data/lib/generators/inertia_tw_templates/controller/templates/react/view.jsx.tt +8 -0
  51. data/lib/generators/inertia_tw_templates/controller/templates/svelte/view.svelte.tt +2 -0
  52. data/lib/generators/inertia_tw_templates/controller/templates/vue/view.vue.tt +4 -0
  53. data/lib/generators/inertia_tw_templates/scaffold/scaffold_generator.rb +12 -0
  54. data/lib/generators/inertia_tw_templates/scaffold/templates/react/Edit.jsx.tt +43 -0
  55. data/lib/generators/inertia_tw_templates/scaffold/templates/react/Form.jsx.tt +122 -0
  56. data/lib/generators/inertia_tw_templates/scaffold/templates/react/Index.jsx.tt +43 -0
  57. data/lib/generators/inertia_tw_templates/scaffold/templates/react/New.jsx.tt +30 -0
  58. data/lib/generators/inertia_tw_templates/scaffold/templates/react/One.jsx.tt +26 -0
  59. data/lib/generators/inertia_tw_templates/scaffold/templates/react/Show.jsx.tt +54 -0
  60. data/lib/generators/inertia_tw_templates/scaffold/templates/svelte/Edit.svelte.tt +45 -0
  61. data/lib/generators/inertia_tw_templates/scaffold/templates/svelte/Form.svelte.tt +120 -0
  62. data/lib/generators/inertia_tw_templates/scaffold/templates/svelte/Index.svelte.tt +49 -0
  63. data/lib/generators/inertia_tw_templates/scaffold/templates/svelte/New.svelte.tt +33 -0
  64. data/lib/generators/inertia_tw_templates/scaffold/templates/svelte/One.svelte.tt +28 -0
  65. data/lib/generators/inertia_tw_templates/scaffold/templates/svelte/Show.svelte.tt +58 -0
  66. data/lib/generators/inertia_tw_templates/scaffold/templates/vue/Edit.vue.tt +44 -0
  67. data/lib/generators/inertia_tw_templates/scaffold/templates/vue/Form.vue.tt +127 -0
  68. data/lib/generators/inertia_tw_templates/scaffold/templates/vue/Index.vue.tt +43 -0
  69. data/lib/generators/inertia_tw_templates/scaffold/templates/vue/New.vue.tt +32 -0
  70. data/lib/generators/inertia_tw_templates/scaffold/templates/vue/One.vue.tt +26 -0
  71. data/lib/generators/inertia_tw_templates/scaffold/templates/vue/Show.vue.tt +56 -0
  72. data/lib/inertia_rails-contrib.rb +3 -0
  73. data/lib/inertia_rails_contrib/generators/controller_template_base.rb +52 -0
  74. data/lib/inertia_rails_contrib/generators/scaffold_template_base.rb +35 -0
  75. data/lib/inertia_rails_contrib/generators_helper.rb +88 -0
  76. data/lib/inertia_rails_contrib/version.rb +5 -0
  77. data/lib/inertia_rails_contrib.rb +8 -0
  78. metadata +153 -0
@@ -0,0 +1,58 @@
1
+ <script>
2
+ import { inertia, Link } from '@inertiajs/svelte'
3
+ import <%= inertia_component_name %> from './<%= inertia_component_name %>.svelte'
4
+
5
+ export let <%= singular_table_name %>
6
+ export let flash
7
+
8
+ const onDestroy = (e) => {
9
+ if (!confirm('Are you sure you want to delete this <%= human_name.downcase %>?')) {
10
+ e.preventDefault()
11
+ }
12
+ }
13
+ </script>
14
+
15
+ <svelte:head>
16
+ <title><%= human_name %> #{<%= singular_table_name %>.id}</title>
17
+ </svelte:head>
18
+
19
+ <div class="mx-auto md:w-2/3 w-full px-8 pt-8">
20
+ <div class="mx-auto">
21
+ {#if flash.notice}
22
+ <p class="py-2 px-3 bg-green-50 mb-5 text-green-500 font-medium rounded-lg inline-block">
23
+ {flash.notice}
24
+ </p>
25
+ {/if}
26
+
27
+ <h1 class="font-bold text-4xl"><%= human_name %> #{<%= singular_table_name %>.id}</h1>
28
+
29
+ <<%= inertia_component_name %> {<%= singular_table_name %>} />
30
+
31
+ <Link
32
+ href={`<%= js_edit_resource_path %>`}
33
+ class="ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
34
+ >
35
+ Edit this <%= human_name.downcase %>
36
+ </Link>
37
+ <Link
38
+ href="<%= js_resources_path %>"
39
+ class="ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
40
+ >
41
+ Back to <%= human_name.pluralize.downcase %>
42
+ </Link>
43
+ <div class="inline-block ml-2">
44
+ <button
45
+ use:inertia={{ href: `<%= js_resource_path %>`, method: 'delete' }}
46
+ on:click={onDestroy}
47
+ type="button"
48
+ class="mt-2 rounded-lg py-3 px-5 bg-gray-100 font-medium"
49
+ >
50
+ Destroy this <%= human_name.downcase %>
51
+ </button>
52
+ </div>
53
+ </div>
54
+ </div>
55
+
56
+
57
+
58
+
@@ -0,0 +1,44 @@
1
+ <template>
2
+ <Head title="Editing <%= human_name.downcase %>" />
3
+
4
+ <div className="mx-auto md:w-2/3 w-full px-8 pt-8">
5
+ <h1 class="font-bold text-4xl">Editing <%= human_name.downcase %></h1>
6
+
7
+ <Form
8
+ :<%= singular_table_name %>="<%= singular_table_name %>"
9
+ submitText="Update <%= human_name.downcase %>"
10
+ @onSubmit="handleSubmit"
11
+ />
12
+
13
+ <Link
14
+ :href="`<%= js_resource_path %>`"
15
+ class="mt-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
16
+ >
17
+ Show this <%= human_name.downcase %>
18
+ </Link>
19
+ <Link
20
+ href="<%= js_resources_path %>"
21
+ class="ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
22
+ >
23
+ Back to <%= human_name.pluralize.downcase %>
24
+ </Link>
25
+ </div>
26
+ </template>
27
+
28
+ <script setup>
29
+ import { Link, Head } from '@inertiajs/vue3'
30
+ import Form from './Form.vue'
31
+
32
+ const { <%= singular_table_name %> } = defineProps(['<%= singular_table_name %>'])
33
+
34
+ const handleSubmit = (form) => {
35
+ form.transform((data) => ({ <%= singular_table_name %>: data }))
36
+ <% if attributes.any?(&:attachments?) -%>
37
+ form.post(`<%= js_resource_path %>`, {
38
+ headers: { 'X-HTTP-METHOD-OVERRIDE': 'put' },
39
+ })
40
+ <% else -%>
41
+ form.patch(`<%= js_resource_path %>`)
42
+ <% end -%>
43
+ }
44
+ </script>
@@ -0,0 +1,127 @@
1
+ <template>
2
+ <form @submit.prevent="emit('onSubmit', form)" class="contents">
3
+ <% attributes.each do |attribute| -%>
4
+ <% if attribute.password_digest? -%>
5
+ <div class="my-5">
6
+ <label for="password">Password</label>
7
+ <input
8
+ type="password"
9
+ name="password"
10
+ id="password"
11
+ v-model="form.password"
12
+ class="block shadow rounded-md border border-gray-400 outline-none px-3 py-2 mt-2 w-full"
13
+ />
14
+ <div
15
+ v-if="form.errors.password"
16
+ class="text-red-500 px-3 py-2 font-medium"
17
+ >
18
+ {{ form.errors.password.join(', ') }}
19
+ </div>
20
+ </div>
21
+
22
+ <div class="my-5">
23
+ <label for="password_confirmation">Password Confirmation</label>
24
+ <input
25
+ type="password"
26
+ name="password_confirmation"
27
+ id="password_confirmation"
28
+ v-model="form.password_confirmation"
29
+ class="block shadow rounded-md border border-gray-400 outline-none px-3 py-2 mt-2 w-full"
30
+ />
31
+ <div
32
+ v-if="form.errors.password_confirmation"
33
+ class="text-red-500 px-3 py-2 font-medium"
34
+ >
35
+ {{ form.errors.password_confirmation.join(', ') }}
36
+ </div>
37
+ </div>
38
+ <% else -%>
39
+ <div class="my-5">
40
+ <label for="<%= attribute.singular_name %>"><%= attribute.human_name %></label>
41
+ <% if input_type(attribute) == "text_area" -%>
42
+ <textarea
43
+ name="<%= attribute.singular_name %>"
44
+ id="<%= attribute.singular_name %>"
45
+ v-model="form.<%= attribute.column_name %>"
46
+ rows="4"
47
+ class="block shadow rounded-md border border-gray-400 outline-none px-3 py-2 mt-2 w-full"
48
+ />
49
+ <% elsif attribute.attachment? -%>
50
+ <input
51
+ type="file"
52
+ name="<%= attribute.singular_name %>"
53
+ id="<%= attribute.singular_name %>"
54
+ @input="form.<%= attribute.column_name %> = $event.target.files[0]"
55
+ class="block shadow rounded-md border border-gray-400 outline-none px-3 py-2 mt-2 w-full"
56
+ />
57
+ <% elsif attribute.attachments? -%>
58
+ <input
59
+ type="file"
60
+ multiple="multiple"
61
+ name="<%= attribute.singular_name %>[]"
62
+ id="<%= attribute.singular_name %>"
63
+ @input="form.<%= attribute.column_name %> = Array.from($event.target.files)"
64
+ class="block shadow rounded-md border border-gray-400 outline-none px-3 py-2 mt-2 w-full"
65
+ />
66
+ <% elsif attribute.field_type == :check_box -%>
67
+ <input
68
+ type="<%= input_type(attribute) %>"
69
+ name="<%= attribute.singular_name %>"
70
+ id="<%= attribute.singular_name %>"
71
+ v-model="form.<%= attribute.column_name %>"
72
+ class="block mt-2 h-5 w-5"
73
+ />
74
+ <% else -%>
75
+ <input
76
+ type="<%= input_type(attribute) %>"
77
+ name="<%= attribute.singular_name %>"
78
+ id="<%= attribute.singular_name %>"
79
+ v-model="form.<%= attribute.column_name %>"
80
+ class="block shadow rounded-md border border-gray-400 outline-none px-3 py-2 mt-2 w-full"
81
+ />
82
+ <% end -%>
83
+ <div v-if="form.errors.<%= attribute.column_name %>" :class="$style.error">
84
+ {{ form.errors.<%= attribute.column_name %>.join(', ') }}
85
+ </div>
86
+ </div>
87
+ <% end -%>
88
+
89
+ <% end -%>
90
+ <div class="inline">
91
+ <button
92
+ type="submit"
93
+ :disabled="form.processing"
94
+ class="rounded-lg py-3 px-5 bg-blue-600 text-white inline-block font-medium cursor-pointer"
95
+ >
96
+ {{ submitText }}
97
+ </button>
98
+ </div>
99
+ </form>
100
+ </template>
101
+
102
+ <script setup>
103
+ import { useForm } from '@inertiajs/vue3'
104
+
105
+ const { <%= singular_table_name %>, submitText } = defineProps(['<%= singular_table_name %>', 'submitText'])
106
+ const emit = defineEmits(['onSubmit'])
107
+
108
+ const form = useForm({
109
+ <% attributes.each do |attribute| -%>
110
+ <% if attribute.password_digest? -%>
111
+ password: '',
112
+ password_confirmation: '',
113
+ <% else -%>
114
+ <%= attribute.column_name %>: <%= singular_table_name %>.<%= attribute.column_name %> || <%= default_value(attribute) %>,
115
+ <% end -%>
116
+ <% end -%>
117
+ })
118
+ </script>
119
+
120
+ <style module>
121
+ .label {
122
+ display: block;
123
+ }
124
+ .error {
125
+ color: red;
126
+ }
127
+ </style>
@@ -0,0 +1,43 @@
1
+ <template>
2
+ <Head title="<%= human_name.pluralize %>" />
3
+
4
+ <div className="mx-auto md:w-2/3 w-full px-8 pt-8">
5
+ <p
6
+ v-if="flash.notice"
7
+ class="py-2 px-3 bg-green-50 mb-5 text-green-500 font-medium rounded-lg inline-block"
8
+ >
9
+ {{ flash.notice }}
10
+ </p>
11
+
12
+ <div class="flex justify-between items-center">
13
+ <h1 class="font-bold text-4xl"><%= human_name.pluralize %></h1>
14
+ <Link
15
+ href="<%= js_new_resource_path %>"
16
+ class="rounded-lg py-3 px-5 bg-blue-600 text-white block font-medium"
17
+ >
18
+ New <%= human_name.downcase %>
19
+ </Link>
20
+ </div>
21
+
22
+ <div class="min-w-full">
23
+ <template v-for="<%= singular_table_name %> in <%= plural_table_name %>" :key="<%= singular_table_name %>.id">
24
+ <<%= inertia_component_name %> :<%= singular_table_name %>="<%= singular_table_name %>" />
25
+ <p>
26
+ <Link
27
+ :href="`<%= js_resource_path %>`"
28
+ class="ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
29
+ >
30
+ Show this <%= human_name.downcase %>
31
+ </Link>
32
+ </p>
33
+ </template>
34
+ </div>
35
+ </div>
36
+ </template>
37
+
38
+ <script setup>
39
+ import { Link, Head } from '@inertiajs/vue3'
40
+ import <%= inertia_component_name %> from './<%= inertia_component_name %>.vue'
41
+
42
+ const { <%= plural_table_name %>, flash } = defineProps(['<%= plural_table_name %>', 'flash'])
43
+ </script>
@@ -0,0 +1,32 @@
1
+ <template>
2
+ <Head title="New <%= human_name.downcase %>" />
3
+
4
+ <div className="mx-auto md:w-2/3 w-full px-8 pt-8">
5
+ <h1 class="font-bold text-4xl">New <%= human_name.downcase %></h1>
6
+
7
+ <Form
8
+ :<%= singular_table_name %>="<%= singular_table_name %>"
9
+ submitText="Create <%= human_name.downcase %>"
10
+ @onSubmit="handleSubmit"
11
+ />
12
+
13
+ <Link
14
+ href="<%= js_resources_path %>"
15
+ class="ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
16
+ >
17
+ Back to <%= human_name.pluralize.downcase %>
18
+ </Link>
19
+ </div>
20
+ </template>
21
+
22
+ <script setup>
23
+ import { Link, Head } from '@inertiajs/vue3'
24
+ import Form from './Form.vue'
25
+
26
+ const { <%= singular_table_name %> } = defineProps(['<%= singular_table_name %>'])
27
+
28
+ const handleSubmit = (form) => {
29
+ form.transform((data) => ({ <%= singular_table_name %>: data }))
30
+ form.post('<%= js_resources_path %>')
31
+ }
32
+ </script>
@@ -0,0 +1,26 @@
1
+ <template>
2
+ <div>
3
+ <% attributes.reject(&:password_digest?).each do |attribute| -%>
4
+ <p class="my-5">
5
+ <strong class="block font-medium mb-1"><%= attribute.human_name %>:</strong>
6
+ <% if attribute.attachment? -%>
7
+ <a v-if="<%= singular_table_name %>.<%= attribute.column_name %>" :href="<%= singular_table_name %>.<%= attribute.column_name %>.url">
8
+ {{ <%= singular_table_name %>.<%= attribute.column_name %>.filename }}
9
+ </a>
10
+ </p>
11
+ <% elsif attribute.attachments? -%>
12
+ </p>
13
+ <div v-for="file in <%= singular_table_name %>.<%= attribute.column_name %>">
14
+ <a :href="file.url">{{ file.filename }}</a>
15
+ </div>
16
+ <% else -%>
17
+ {{ <%= singular_table_name %>.<%= attribute.column_name %> }}
18
+ </p>
19
+ <% end -%>
20
+ <% end -%>
21
+ </div>
22
+ </template>
23
+
24
+ <script setup>
25
+ const { <%= singular_table_name %> } = defineProps(['<%= singular_table_name %>'])
26
+ </script>
@@ -0,0 +1,56 @@
1
+ <template>
2
+ <Head :title="`<%= human_name %> #${<%= singular_table_name %>.id}`" />
3
+
4
+ <div className="mx-auto md:w-2/3 w-full px-8 pt-8">
5
+ <div class="mx-auto">
6
+ <p
7
+ v-if="flash.notice"
8
+ class="py-2 px-3 bg-green-50 mb-5 text-green-500 font-medium rounded-lg inline-block"
9
+ >
10
+ {{ flash.notice }}
11
+ </p>
12
+
13
+ <h1 class="font-bold text-4xl"><%= human_name %> #{{ <%= singular_table_name %>.id }}</h1>
14
+
15
+ <<%= inertia_component_name %> :<%= singular_table_name %>="<%= singular_table_name %>" />
16
+
17
+ <Link
18
+ :href="`<%= js_edit_resource_path %>`"
19
+ class="ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
20
+ >
21
+ Edit this <%= human_name.downcase %>
22
+ </Link>
23
+ <Link
24
+ href="<%= js_resources_path %>"
25
+ class="ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium"
26
+ >
27
+ Back to <%= human_name.pluralize.downcase %>
28
+ </Link>
29
+
30
+ <div class="inline-block ml-2">
31
+ <Link
32
+ :href="`<%= js_resource_path %>`"
33
+ @click="onDestroy"
34
+ as="button"
35
+ method="delete"
36
+ class="mt-2 rounded-lg py-3 px-5 bg-gray-100 font-medium"
37
+ >
38
+ Destroy this <%= human_name.downcase %>
39
+ </Link>
40
+ </div>
41
+ </div>
42
+ </div>
43
+ </template>
44
+
45
+ <script setup>
46
+ import { Link, Head } from '@inertiajs/vue3'
47
+ import <%= inertia_component_name %> from './<%= inertia_component_name %>.vue'
48
+
49
+ const { <%= singular_table_name %>, flash } = defineProps(['<%= singular_table_name %>', 'flash'])
50
+
51
+ const onDestroy = (e) => {
52
+ if (!confirm('Are you sure you want to delete this <%= human_name.downcase %>?')) {
53
+ e.preventDefault()
54
+ }
55
+ }
56
+ </script>
@@ -0,0 +1,3 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "inertia_rails_contrib"
@@ -0,0 +1,52 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "rails/generators/named_base"
4
+ require "inertia_rails_contrib/generators_helper"
5
+
6
+ module InertiaRailsContrib
7
+ module Generators
8
+ class ControllerTemplateBase < Rails::Generators::NamedBase
9
+ include GeneratorsHelper
10
+ class_option :frontend_framework, required: true, desc: "Frontend framework to generate the views for.",
11
+ default: GeneratorsHelper.guess_the_default_framework
12
+
13
+ argument :actions, type: :array, default: [], banner: "action action"
14
+
15
+ def empty_views_dir
16
+ empty_directory base_path
17
+ end
18
+
19
+ def copy_view_files
20
+ actions.each do |action|
21
+ @action = action
22
+ @path = File.join(base_path, "#{action.camelize}.#{extension}")
23
+ template "#{options.frontend_framework}/#{template_filename}.#{extension}", @path
24
+ end
25
+ end
26
+
27
+ private
28
+
29
+ def base_path
30
+ File.join(pages_path, inertia_base_path)
31
+ end
32
+
33
+ def template_filename
34
+ "view"
35
+ end
36
+
37
+ def pages_path
38
+ "app/frontend/pages"
39
+ end
40
+
41
+ def extension
42
+ case options.frontend_framework
43
+ when "react" then "jsx"
44
+ when "vue" then "vue"
45
+ when "svelte" then "svelte"
46
+ else
47
+ raise ArgumentError, "Unknown frontend framework: #{options.frontend_framework}"
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end
@@ -0,0 +1,35 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "rails/generators/resource_helpers"
4
+ require_relative "controller_template_base"
5
+
6
+ module InertiaRailsContrib
7
+ module Generators
8
+ class ScaffoldTemplateBase < ControllerTemplateBase
9
+ include Rails::Generators::ResourceHelpers
10
+
11
+ remove_argument :actions
12
+
13
+ argument :attributes, type: :array, default: [], banner: "field:type field:type"
14
+
15
+ def copy_view_files
16
+ available_views.each do |view|
17
+ filename = "#{view}.#{extension}"
18
+ template "#{options.frontend_framework}/#{filename}", File.join(base_path, filename)
19
+ end
20
+
21
+ template "#{options.frontend_framework}/#{partial_name}.#{extension}", File.join(base_path, "#{inertia_component_name}.#{extension}")
22
+ end
23
+
24
+ private
25
+
26
+ def available_views
27
+ %w[Index Edit Show New Form]
28
+ end
29
+
30
+ def partial_name
31
+ "One"
32
+ end
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,88 @@
1
+ module InertiaRailsContrib
2
+ module GeneratorsHelper
3
+ def self.guess_the_default_framework
4
+ case Rails.root.join("package.json").read
5
+ when /@inertiajs\/react/
6
+ "react"
7
+ when /@inertiajs\/svelte/
8
+ "svelte"
9
+ when /@inertiajs\/vue3/
10
+ "vue"
11
+ else
12
+ puts "Could not determine the Inertia.js framework you are using."
13
+ end
14
+ end
15
+
16
+ def self.guess_inertia_template
17
+ if Rails.root.join("tailwind.config.js").exist?
18
+ "inertia_tw_templates"
19
+ else
20
+ "inertia_templates"
21
+ end
22
+ end
23
+
24
+ def inertia_base_path
25
+ (class_path + [file_name]).map(&:camelize).join("/")
26
+ end
27
+
28
+ def inertia_component_name
29
+ singular_name.camelize
30
+ end
31
+
32
+ def attributes_to_serialize
33
+ [:id] + attributes.reject do |attribute|
34
+ attribute.password_digest? ||
35
+ attribute.attachment? ||
36
+ attribute.attachments?
37
+ end.map(&:column_name)
38
+ end
39
+
40
+ def js_resource_path
41
+ "#{route_url}/${#{singular_table_name}.id}"
42
+ end
43
+
44
+ def js_edit_resource_path
45
+ "#{route_url}/${#{singular_table_name}.id}/edit"
46
+ end
47
+
48
+ def js_new_resource_path
49
+ "#{route_url}/new"
50
+ end
51
+
52
+ def js_resources_path
53
+ route_url
54
+ end
55
+
56
+ def input_type(attribute)
57
+ case attribute.type
58
+ when :string
59
+ "text"
60
+ when :text, :rich_text
61
+ "text_area"
62
+ when :integer
63
+ "number"
64
+ when :float, :decimal
65
+ "number"
66
+ when :datetime, :timestamp, :time
67
+ "datetime-local"
68
+ when :date
69
+ "date"
70
+ when :boolean
71
+ "checkbox"
72
+ when :attachments, :attachment
73
+ "file"
74
+ else
75
+ "text"
76
+ end
77
+ end
78
+
79
+ def default_value(attribute)
80
+ case attribute.type
81
+ when :boolean
82
+ "false"
83
+ else
84
+ "''"
85
+ end
86
+ end
87
+ end
88
+ end
@@ -0,0 +1,5 @@
1
+ # frozen_string_literal: true
2
+
3
+ module InertiaRailsContrib
4
+ VERSION = "0.1.0"
5
+ end
@@ -0,0 +1,8 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "inertia_rails" if defined?(Rails)
4
+
5
+ require_relative "inertia_rails_contrib/version"
6
+
7
+ module InertiaRailsContrib
8
+ end