tailwindcss-rails 0.3.3 → 0.5.4
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 +4 -4
- data/README.md +19 -12
- data/Rakefile +1 -0
- data/app/assets/stylesheets/tailwind.css +172209 -158667
- data/lib/generators/tailwindcss/controller/controller_generator.rb +9 -0
- data/lib/generators/tailwindcss/controller/templates/view.html.erb.tt +4 -0
- data/lib/generators/tailwindcss/mailer/mailer_generator.rb +9 -0
- data/lib/generators/tailwindcss/mailer/templates/view.html.erb.tt +5 -0
- data/lib/generators/tailwindcss/mailer/templates/view.text.erb.tt +3 -0
- data/lib/generators/tailwindcss/scaffold/scaffold_generator.rb +34 -0
- data/lib/generators/tailwindcss/scaffold/templates/_form.html.erb.tt +43 -0
- data/lib/generators/tailwindcss/scaffold/templates/edit.html.erb.tt +8 -0
- data/lib/generators/tailwindcss/scaffold/templates/index.html.erb.tt +14 -0
- data/lib/generators/tailwindcss/scaffold/templates/new.html.erb.tt +7 -0
- data/lib/generators/tailwindcss/scaffold/templates/partial.html.erb.tt +22 -0
- data/lib/generators/tailwindcss/scaffold/templates/show.html.erb.tt +15 -0
- data/lib/install/tailwindcss.rb +22 -0
- data/lib/tailwindcss/compressor.rb +9 -2
- data/lib/tailwindcss/engine.rb +5 -0
- data/lib/tailwindcss/purger.rb +94 -34
- data/lib/tailwindcss/version.rb +1 -1
- data/lib/tasks/tailwindcss_tasks.rake +2 -21
- metadata +21 -11
- data/lib/install/stylesheets/application.scss +0 -3
- data/lib/install/tailwindcss_with_asset_pipeline.rb +0 -12
- data/lib/install/tailwindcss_with_webpacker.rb +0 -22
| @@ -0,0 +1,34 @@ | |
| 1 | 
            +
            require 'rails/generators/erb/scaffold/scaffold_generator'
         | 
| 2 | 
            +
            require "rails/generators/resource_helpers"
         | 
| 3 | 
            +
             | 
| 4 | 
            +
            module Tailwindcss
         | 
| 5 | 
            +
              module Generators
         | 
| 6 | 
            +
                class ScaffoldGenerator < Erb::Generators::ScaffoldGenerator
         | 
| 7 | 
            +
                  include Rails::Generators::ResourceHelpers
         | 
| 8 | 
            +
             | 
| 9 | 
            +
                  source_root File.expand_path("../templates", __FILE__)
         | 
| 10 | 
            +
             | 
| 11 | 
            +
                  argument :attributes, type: :array, default: [], banner: "field:type field:type"
         | 
| 12 | 
            +
             | 
| 13 | 
            +
                  def create_root_folder
         | 
| 14 | 
            +
                    empty_directory File.join("app/views", controller_file_path)
         | 
| 15 | 
            +
                  end
         | 
| 16 | 
            +
             | 
| 17 | 
            +
                  def copy_view_files
         | 
| 18 | 
            +
                    available_views.each do |view|
         | 
| 19 | 
            +
                      formats.each do |format|
         | 
| 20 | 
            +
                        filename = filename_with_extensions(view, format)
         | 
| 21 | 
            +
                        template filename, File.join("app/views", controller_file_path, filename)
         | 
| 22 | 
            +
                      end
         | 
| 23 | 
            +
                    end
         | 
| 24 | 
            +
             | 
| 25 | 
            +
                    template "partial.html.erb", File.join("app/views", controller_file_path, "_#{singular_table_name}.html.erb")
         | 
| 26 | 
            +
                  end
         | 
| 27 | 
            +
             | 
| 28 | 
            +
                  private
         | 
| 29 | 
            +
                    def available_views
         | 
| 30 | 
            +
                      %w(index edit show new _form)
         | 
| 31 | 
            +
                    end
         | 
| 32 | 
            +
                end
         | 
| 33 | 
            +
              end
         | 
| 34 | 
            +
            end
         | 
| @@ -0,0 +1,43 @@ | |
| 1 | 
            +
            <%%= form_with(model: <%= model_resource_name %>, class: "contents") do |form| %>
         | 
| 2 | 
            +
              <%% if <%= singular_table_name %>.errors.any? %>
         | 
| 3 | 
            +
                <div id="error_explanation" class="bg-red-50 text-red-500 px-3 py-2 font-medium rounded-lg mt-3">
         | 
| 4 | 
            +
                  <h2><%%= pluralize(<%= singular_table_name %>.errors.count, "error") %> prohibited this <%= singular_table_name %> from being saved:</h2>
         | 
| 5 | 
            +
             | 
| 6 | 
            +
                  <ul>
         | 
| 7 | 
            +
                    <%% <%= singular_table_name %>.errors.each do |error| %>
         | 
| 8 | 
            +
                      <li><%%= error.full_message %></li>
         | 
| 9 | 
            +
                    <%% end %>
         | 
| 10 | 
            +
                  </ul>
         | 
| 11 | 
            +
                </div>
         | 
| 12 | 
            +
              <%% end %>
         | 
| 13 | 
            +
             | 
| 14 | 
            +
            <% attributes.each do |attribute| -%>
         | 
| 15 | 
            +
              <div class="my-5">
         | 
| 16 | 
            +
            <% if attribute.password_digest? -%>
         | 
| 17 | 
            +
                <%%= form.label :password %>
         | 
| 18 | 
            +
                <%%= form.password_field :password %>
         | 
| 19 | 
            +
            </div>
         | 
| 20 | 
            +
             | 
| 21 | 
            +
            <div class="my-5">
         | 
| 22 | 
            +
                <%%= form.label :password_confirmation %>
         | 
| 23 | 
            +
                <%%= form.password_field :password_confirmation, class: "block shadow rounded-md border border-gray-200 outline-none px-3 py-2 mt-2 w-full" %>
         | 
| 24 | 
            +
            <% elsif attribute.attachments? -%>
         | 
| 25 | 
            +
                <%%= form.label :<%= attribute.column_name %> %>
         | 
| 26 | 
            +
                <%%= form.<%= attribute.field_type %> :<%= attribute.column_name %>, multiple: true, class: "block shadow rounded-md border border-gray-200 outline-none px-3 py-2 mt-2 w-full" %>
         | 
| 27 | 
            +
            <% else -%>
         | 
| 28 | 
            +
                <%%= form.label :<%= attribute.column_name %> %>
         | 
| 29 | 
            +
            <% if attribute.field_type == :text_area -%>
         | 
| 30 | 
            +
                <%%= form.<%= attribute.field_type %> :<%= attribute.column_name %>, rows: 4, class: "block shadow rounded-md border border-gray-200 outline-none px-3 py-2 mt-2 w-full" %>
         | 
| 31 | 
            +
            <% elsif attribute.field_type == :check_box -%>
         | 
| 32 | 
            +
                <%%= form.<%= attribute.field_type %> :<%= attribute.column_name %>, class: "block mt-2 h-5 w-5" %>
         | 
| 33 | 
            +
            <% else -%>
         | 
| 34 | 
            +
                <%%= form.<%= attribute.field_type %> :<%= attribute.column_name %>, class: "block shadow rounded-md border border-gray-200 outline-none px-3 py-2 mt-2 w-full" %>
         | 
| 35 | 
            +
            <% end -%>
         | 
| 36 | 
            +
            <% end -%>
         | 
| 37 | 
            +
              </div>
         | 
| 38 | 
            +
             | 
| 39 | 
            +
            <% end -%>
         | 
| 40 | 
            +
              <div class="inline">
         | 
| 41 | 
            +
                <%%= form.submit class: "rounded-lg py-3 px-5 bg-blue-600 text-white inline-block font-medium cursor-pointer" %>
         | 
| 42 | 
            +
              </div>
         | 
| 43 | 
            +
            <%% end %>
         | 
| @@ -0,0 +1,8 @@ | |
| 1 | 
            +
            <div class="mx-auto md:w-2/3 w-full">
         | 
| 2 | 
            +
              <h1 class="font-bold text-4xl">Editing <%= human_name.downcase %></h1>
         | 
| 3 | 
            +
             | 
| 4 | 
            +
              <%%= render "form", <%= singular_table_name %>: @<%= singular_table_name %> %>
         | 
| 5 | 
            +
             | 
| 6 | 
            +
              <%%= link_to "Show this <%= human_name.downcase %>", @<%= singular_table_name %>, class: "ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium" %>
         | 
| 7 | 
            +
              <%%= link_to "Back to <%= human_name.pluralize.downcase %>", <%= index_helper %>_path, class: "ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium" %>
         | 
| 8 | 
            +
            </div>
         | 
| @@ -0,0 +1,14 @@ | |
| 1 | 
            +
            <div class="w-full">
         | 
| 2 | 
            +
              <%% if notice.present? %>
         | 
| 3 | 
            +
                <p class="py-2 px-3 bg-green-50 mb-5 text-green-500 font-medium rounded-lg inline-block" id="notice"><%%= notice %></p>
         | 
| 4 | 
            +
              <%% end %>
         | 
| 5 | 
            +
             | 
| 6 | 
            +
              <div class="flex justify-between items-center">
         | 
| 7 | 
            +
                <h1 class="text-lg font-bold text-4xl"><%= human_name.pluralize %></h1>
         | 
| 8 | 
            +
                <%%= link_to 'New <%= human_name.downcase %>', new_<%= singular_route_name %>_path, class: "rounded-lg py-3 px-5 bg-blue-600 text-white block font-medium" %>
         | 
| 9 | 
            +
              </div>
         | 
| 10 | 
            +
             | 
| 11 | 
            +
              <div id="<%= plural_table_name %>" class="min-w-full">
         | 
| 12 | 
            +
                <%%= render @<%= plural_table_name %> %>
         | 
| 13 | 
            +
              </div>
         | 
| 14 | 
            +
            </div>
         | 
| @@ -0,0 +1,7 @@ | |
| 1 | 
            +
            <div class="mx-auto md:w-2/3 w-full">
         | 
| 2 | 
            +
              <h1 class="text-lg font-bold text-4xl">New <%= human_name.downcase %></h1>
         | 
| 3 | 
            +
             | 
| 4 | 
            +
              <%%= render "form", <%= singular_table_name %>: @<%= singular_table_name %> %>
         | 
| 5 | 
            +
             | 
| 6 | 
            +
              <%%= link_to 'Back to <%= human_name.pluralize.downcase %>', <%= index_helper %>_path, class: "ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium" %>
         | 
| 7 | 
            +
            </div>
         | 
| @@ -0,0 +1,22 @@ | |
| 1 | 
            +
            <div id="<%%= dom_id <%= singular_table_name %> %>">
         | 
| 2 | 
            +
            <% attributes.reject(&:password_digest?).each do |attribute| -%>
         | 
| 3 | 
            +
              <p class="my-5">
         | 
| 4 | 
            +
                <strong class="block font-medium mb-1"><%= attribute.human_name %>:</strong>
         | 
| 5 | 
            +
            <% if attribute.attachment? -%>
         | 
| 6 | 
            +
                <%%= link_to <%= singular_table_name %>.<%= attribute.column_name %>.filename, <%= singular_table_name %>.<%= attribute.column_name %> if <%= singular_table_name %>.<%= attribute.column_name %>.attached? %>
         | 
| 7 | 
            +
            <% elsif attribute.attachments? -%>
         | 
| 8 | 
            +
                <%% <%= singular_table_name %>.<%= attribute.column_name %>.each do |<%= attribute.singular_name %>| %>
         | 
| 9 | 
            +
                  <div><%%= link_to <%= attribute.singular_name %>.filename, <%= attribute.singular_name %> %></div>
         | 
| 10 | 
            +
                <%% end %>
         | 
| 11 | 
            +
            <% else -%>
         | 
| 12 | 
            +
                <%%= <%= singular_table_name %>.<%= attribute.column_name %> %>
         | 
| 13 | 
            +
            <% end -%>
         | 
| 14 | 
            +
              </p>
         | 
| 15 | 
            +
             | 
| 16 | 
            +
            <% end -%>
         | 
| 17 | 
            +
              <%% if action_name != "show" %>
         | 
| 18 | 
            +
                <%%= link_to "Show this <%= human_name.downcase %>", <%= singular_table_name %>, class: "rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium" %>
         | 
| 19 | 
            +
                <%%= link_to 'Edit this <%= human_name.downcase %>', edit_<%= singular_table_name %>_path(<%= singular_table_name %>), class: "rounded-lg py-3 ml-2 px-5 bg-gray-100 inline-block font-medium" %>
         | 
| 20 | 
            +
                <hr class="mt-6">
         | 
| 21 | 
            +
              <%% end %>
         | 
| 22 | 
            +
            </div>
         | 
| @@ -0,0 +1,15 @@ | |
| 1 | 
            +
            <div class="mx-auto md:w-2/3 w-full flex">
         | 
| 2 | 
            +
              <div class="mx-auto">
         | 
| 3 | 
            +
                <%% if notice.present? %>
         | 
| 4 | 
            +
                  <p class="py-2 px-3 bg-green-50 mb-5 text-green-500 font-medium rounded-lg inline-block" id="notice"><%%= notice %></p>
         | 
| 5 | 
            +
                <%% end %>
         | 
| 6 | 
            +
             | 
| 7 | 
            +
                <%%= render @<%= singular_table_name %> %>
         | 
| 8 | 
            +
             | 
| 9 | 
            +
                <%%= link_to 'Edit this <%= singular_table_name %>', edit_<%= singular_table_name %>_path(@<%= singular_table_name %>), class: "mt-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium" %>
         | 
| 10 | 
            +
                <div class="inline-block ml-2">
         | 
| 11 | 
            +
                  <%%= button_to 'Destroy this <%= singular_table_name %>', <%= singular_table_name %>_path(@<%= singular_table_name %>), method: :delete, data: { confirm: "Are you sure you want to delete this <%= singular_table_name %>?" }, class: "mt-2 rounded-lg py-3 px-5 bg-gray-100 font-medium" %>
         | 
| 12 | 
            +
                </div>
         | 
| 13 | 
            +
                <%%= link_to 'Back to <%= plural_table_name %>', <%= index_helper %>_path, class: "ml-2 rounded-lg py-3 px-5 bg-gray-100 inline-block font-medium" %>
         | 
| 14 | 
            +
              </div>
         | 
| 15 | 
            +
            </div>
         | 
| @@ -0,0 +1,22 @@ | |
| 1 | 
            +
            APPLICATION_LAYOUT_PATH = Rails.root.join("app/views/layouts/application.html.erb")
         | 
| 2 | 
            +
             | 
| 3 | 
            +
            if APPLICATION_LAYOUT_PATH.exist?
         | 
| 4 | 
            +
              say "Add Tailwindcss include tags and container element in application layout"
         | 
| 5 | 
            +
              insert_into_file APPLICATION_LAYOUT_PATH.to_s, <<~ERB.indent(4), before: /^\s*<%= stylesheet_link_tag/
         | 
| 6 | 
            +
                <%= stylesheet_link_tag "inter-font", "data-turbo-track": "reload" %>
         | 
| 7 | 
            +
                <%= stylesheet_link_tag "tailwind", "data-turbo-track": "reload" %>
         | 
| 8 | 
            +
              ERB
         | 
| 9 | 
            +
              insert_into_file APPLICATION_LAYOUT_PATH.to_s, %(    <main class="container mx-auto mt-28 px-5 flex">\n  ), before: /^\s*<%= yield/
         | 
| 10 | 
            +
              insert_into_file APPLICATION_LAYOUT_PATH.to_s, %(\n    </main>),  after: /^\s*<%= yield %>/
         | 
| 11 | 
            +
            else
         | 
| 12 | 
            +
              say "Default application.html.erb is missing!", :red
         | 
| 13 | 
            +
              say %(        Add <%= stylesheet_link_tag "inter-font", "data-turbo-track": "reload" %> and <%= stylesheet_link_tag "tailwind", "data-turbo-track": "reload" %> within the <head> tag in your custom layout.)
         | 
| 14 | 
            +
            end
         | 
| 15 | 
            +
             | 
| 16 | 
            +
            # No longer included by default in Rails 7, but for earlier versions of Rails
         | 
| 17 | 
            +
            if (scaffolds_css_path = Rails.root.join("app/assets/stylesheets/scaffolds.scss")).exist?
         | 
| 18 | 
            +
              remove_file scaffolds_css_path
         | 
| 19 | 
            +
            end
         | 
| 20 | 
            +
             | 
| 21 | 
            +
            say "Turn on purging of unused css classes in production"
         | 
| 22 | 
            +
            gsub_file Rails.root.join("config/environments/production.rb"), /^\s+#?\s+config.assets.css_compressor =.*$/, %(  config.assets.css_compressor = :purger)
         | 
| @@ -10,8 +10,8 @@ class Tailwindcss::Compressor | |
| 10 10 | 
             
              end
         | 
| 11 11 |  | 
| 12 12 | 
             
              def initialize(options = {})
         | 
| 13 | 
            -
                @options = { | 
| 14 | 
            -
                  files_with_class_names:  | 
| 13 | 
            +
                @options = {
         | 
| 14 | 
            +
                  files_with_class_names: files_with_class_names,
         | 
| 15 15 | 
             
                  only_purge: %w[ tailwind ]
         | 
| 16 16 | 
             
                }.merge(options).freeze
         | 
| 17 17 | 
             
              end
         | 
| @@ -23,4 +23,11 @@ class Tailwindcss::Compressor | |
| 23 23 | 
             
                  input[:data]
         | 
| 24 24 | 
             
                end
         | 
| 25 25 | 
             
              end
         | 
| 26 | 
            +
             | 
| 27 | 
            +
              private
         | 
| 28 | 
            +
                def files_with_class_names
         | 
| 29 | 
            +
                  Rails.root.glob("app/views/**/*.*") +
         | 
| 30 | 
            +
                    Rails.root.glob("app/helpers/**/*.rb") +
         | 
| 31 | 
            +
                    Rails.root.glob("app/javascript/**/*.js")
         | 
| 32 | 
            +
                end
         | 
| 26 33 | 
             
            end
         | 
    
        data/lib/tailwindcss/engine.rb
    CHANGED
    
    | @@ -1,3 +1,4 @@ | |
| 1 | 
            +
            require "rails"
         | 
| 1 2 | 
             
            require "tailwindcss/compressor"
         | 
| 2 3 |  | 
| 3 4 | 
             
            module Tailwindcss
         | 
| @@ -19,5 +20,9 @@ module Tailwindcss | |
| 19 20 | 
             
                    env.cache = ActiveSupport::Cache.lookup_store(:null_store)
         | 
| 20 21 | 
             
                  end if Rails.env.production?
         | 
| 21 22 | 
             
                end
         | 
| 23 | 
            +
             | 
| 24 | 
            +
                 config.app_generators do |g|
         | 
| 25 | 
            +
                   g.template_engine :tailwindcss
         | 
| 26 | 
            +
                 end
         | 
| 22 27 | 
             
              end
         | 
| 23 28 | 
             
            end
         | 
    
        data/lib/tailwindcss/purger.rb
    CHANGED
    
    | @@ -1,8 +1,25 @@ | |
| 1 | 
            +
            # frozen_string_literal: true
         | 
| 2 | 
            +
             | 
| 1 3 | 
             
            class Tailwindcss::Purger
         | 
| 2 | 
            -
              CLASS_NAME_PATTERN | 
| 3 | 
            -
             | 
| 4 | 
            -
               | 
| 5 | 
            -
             | 
| 4 | 
            +
              CLASS_NAME_PATTERN = /((?:[:A-Za-z0-9_-]+[\\\/:A-Za-z0-9_-]*[0-3][\\.]*5)|(?:[A-Za-z0-9_-]+[\\\/:A-Za-z0-9_-]*))/
         | 
| 5 | 
            +
             | 
| 6 | 
            +
              CLASS_BREAK = /(?![-_a-z0-9\\])/i # `\b` for class selectors
         | 
| 7 | 
            +
             | 
| 8 | 
            +
              COMMENT = /#{Regexp.escape "/*"}.*?#{Regexp.escape "*/"}/m
         | 
| 9 | 
            +
              COMMENTS_AND_BLANK_LINES = /\A(?:^#{COMMENT}?[ \t]*(?:\n|\z)|[ \t]*#{COMMENT})+/
         | 
| 10 | 
            +
             | 
| 11 | 
            +
              AT_RULE = /@[^{]+/
         | 
| 12 | 
            +
              CLASSLESS_SELECTOR_GROUP = /[^.{]+/
         | 
| 13 | 
            +
              CLASSLESS_BEGINNING_OF_BLOCK = /\A\s*(?:#{AT_RULE}|#{CLASSLESS_SELECTOR_GROUP})\{\n?/
         | 
| 14 | 
            +
             | 
| 15 | 
            +
              SELECTOR_GROUP = /[^{]+/
         | 
| 16 | 
            +
              BEGINNING_OF_BLOCK = /\A#{SELECTOR_GROUP}\{\n?/
         | 
| 17 | 
            +
             | 
| 18 | 
            +
              PROPERTY_NAME = /[-_a-z0-9]+/i
         | 
| 19 | 
            +
              PROPERTY_VALUE = /(?:[^;]|;\S)+/
         | 
| 20 | 
            +
              PROPERTIES = /\A(?:\s*#{PROPERTY_NAME}:#{PROPERTY_VALUE};\n?)+/
         | 
| 21 | 
            +
             | 
| 22 | 
            +
              END_OF_BLOCK = /\A\s*\}\n?/
         | 
| 6 23 |  | 
| 7 24 | 
             
              attr_reader :keep_these_class_names
         | 
| 8 25 |  | 
| @@ -12,11 +29,15 @@ class Tailwindcss::Purger | |
| 12 29 | 
             
                end
         | 
| 13 30 |  | 
| 14 31 | 
             
                def extract_class_names(string)
         | 
| 15 | 
            -
                  string.scan(CLASS_NAME_PATTERN).flatten.uniq.sort
         | 
| 32 | 
            +
                  string.scan(CLASS_NAME_PATTERN).flatten.uniq.sort!
         | 
| 16 33 | 
             
                end
         | 
| 17 34 |  | 
| 18 35 | 
             
                def extract_class_names_from(files)
         | 
| 19 | 
            -
                  Array(files).flat_map { |file| extract_class_names(file.read) }.uniq.sort
         | 
| 36 | 
            +
                  Array(files).flat_map { |file| extract_class_names(file.read) }.uniq.sort!
         | 
| 37 | 
            +
                end
         | 
| 38 | 
            +
             | 
| 39 | 
            +
                def escape_class_selector(class_name)
         | 
| 40 | 
            +
                  class_name.gsub(/\A\d|[^-_a-z0-9]/, '\\\\\0')
         | 
| 20 41 | 
             
                end
         | 
| 21 42 | 
             
              end
         | 
| 22 43 |  | 
| @@ -25,40 +46,79 @@ class Tailwindcss::Purger | |
| 25 46 | 
             
              end
         | 
| 26 47 |  | 
| 27 48 | 
             
              def purge(input)
         | 
| 28 | 
            -
                 | 
| 29 | 
            -
             | 
| 30 | 
            -
             | 
| 31 | 
            -
             | 
| 32 | 
            -
                   | 
| 33 | 
            -
                   | 
| 34 | 
            -
             | 
| 35 | 
            -
             | 
| 36 | 
            -
                   | 
| 37 | 
            -
                    inside_ignored_selector = false if line =~ CLOSING_SELECTOR_PATTERN
         | 
| 38 | 
            -
                  when line =~ OPENING_SELECTOR_PATTERN
         | 
| 39 | 
            -
                    if keep_these_class_names.include? class_name_in(line)
         | 
| 40 | 
            -
                      output << line
         | 
| 41 | 
            -
                      inside_kept_selector = true
         | 
| 42 | 
            -
                    else
         | 
| 43 | 
            -
                      inside_ignored_selector = true
         | 
| 44 | 
            -
                    end
         | 
| 45 | 
            -
                  else
         | 
| 46 | 
            -
                    output << line
         | 
| 47 | 
            -
                  end
         | 
| 49 | 
            +
                conveyor = Conveyor.new(input)
         | 
| 50 | 
            +
             | 
| 51 | 
            +
                until conveyor.done?
         | 
| 52 | 
            +
                  conveyor.discard(COMMENTS_AND_BLANK_LINES) \
         | 
| 53 | 
            +
                  or conveyor.conditionally_keep(PROPERTIES) { conveyor.staged_output.last != "" } \
         | 
| 54 | 
            +
                  or conveyor.conditionally_keep(END_OF_BLOCK) { not conveyor.staged_output.pop } \
         | 
| 55 | 
            +
                  or conveyor.stage_output(CLASSLESS_BEGINNING_OF_BLOCK) \
         | 
| 56 | 
            +
                  or conveyor.stage_output(BEGINNING_OF_BLOCK) { |match| purge_beginning_of_block(match.to_s) } \
         | 
| 57 | 
            +
                  or raise "infinite loop"
         | 
| 48 58 | 
             
                end
         | 
| 49 59 |  | 
| 50 | 
            -
                 | 
| 60 | 
            +
                conveyor.output
         | 
| 51 61 | 
             
              end
         | 
| 52 62 |  | 
| 53 63 | 
             
              private
         | 
| 54 | 
            -
                def  | 
| 55 | 
            -
                   | 
| 56 | 
            -
                    . | 
| 57 | 
            -
                    . | 
| 58 | 
            -
             | 
| 64 | 
            +
                def keep_these_selectors_pattern
         | 
| 65 | 
            +
                  @keep_these_selectors_pattern ||= begin
         | 
| 66 | 
            +
                    escaped_classes = @keep_these_class_names.map { |name| Regexp.escape self.class.escape_class_selector(name) }
         | 
| 67 | 
            +
                    /(?:\A|,)[^.,{]*(?:[.](?:#{escaped_classes.join("|")})#{CLASS_BREAK}[^.,{]*)*(?=[,{])/
         | 
| 68 | 
            +
                  end
         | 
| 69 | 
            +
                end
         | 
| 70 | 
            +
             | 
| 71 | 
            +
                def purge_beginning_of_block(string)
         | 
| 72 | 
            +
                  purged = string.scan(keep_these_selectors_pattern).join
         | 
| 73 | 
            +
                  unless purged.empty?
         | 
| 74 | 
            +
                    purged.sub!(/\A,\s*/, "")
         | 
| 75 | 
            +
                    purged.rstrip!
         | 
| 76 | 
            +
                    purged << " {\n"
         | 
| 77 | 
            +
                  end
         | 
| 78 | 
            +
                  purged
         | 
| 59 79 | 
             
                end
         | 
| 60 80 |  | 
| 61 | 
            -
                 | 
| 62 | 
            -
                  output | 
| 81 | 
            +
                class Conveyor
         | 
| 82 | 
            +
                  attr_reader :output, :staged_output
         | 
| 83 | 
            +
             | 
| 84 | 
            +
                  def initialize(input, output = +"")
         | 
| 85 | 
            +
                    @input = input
         | 
| 86 | 
            +
                    @output = output
         | 
| 87 | 
            +
                    @staged_output = []
         | 
| 88 | 
            +
                  end
         | 
| 89 | 
            +
             | 
| 90 | 
            +
                  def consume(pattern)
         | 
| 91 | 
            +
                    match = pattern.match(@input)
         | 
| 92 | 
            +
                    @input = match.post_match if match
         | 
| 93 | 
            +
                    match
         | 
| 94 | 
            +
                  end
         | 
| 95 | 
            +
                  alias :discard :consume
         | 
| 96 | 
            +
             | 
| 97 | 
            +
                  def stage_output(pattern)
         | 
| 98 | 
            +
                    if match = consume(pattern)
         | 
| 99 | 
            +
                      string = block_given? ? (yield match) : match.to_s
         | 
| 100 | 
            +
                      @staged_output << string
         | 
| 101 | 
            +
                      string
         | 
| 102 | 
            +
                    end
         | 
| 103 | 
            +
                  end
         | 
| 104 | 
            +
             | 
| 105 | 
            +
                  def keep(pattern)
         | 
| 106 | 
            +
                    if match = consume(pattern)
         | 
| 107 | 
            +
                      string = block_given? ? (yield match) : match.to_s
         | 
| 108 | 
            +
                      @output << @staged_output.shift until @staged_output.empty?
         | 
| 109 | 
            +
                      @output << string
         | 
| 110 | 
            +
                      string
         | 
| 111 | 
            +
                    end
         | 
| 112 | 
            +
                  end
         | 
| 113 | 
            +
             | 
| 114 | 
            +
                  def conditionally_keep(pattern)
         | 
| 115 | 
            +
                    keep(pattern) do |match|
         | 
| 116 | 
            +
                      (yield match) ? match.to_s : (break "")
         | 
| 117 | 
            +
                    end
         | 
| 118 | 
            +
                  end
         | 
| 119 | 
            +
             | 
| 120 | 
            +
                  def done?
         | 
| 121 | 
            +
                    @input.empty?
         | 
| 122 | 
            +
                  end
         | 
| 63 123 | 
             
                end
         | 
| 64 124 | 
             
            end
         | 
    
        data/lib/tailwindcss/version.rb
    CHANGED
    
    
| @@ -1,23 +1,7 @@ | |
| 1 1 | 
             
            namespace :tailwindcss do
         | 
| 2 2 | 
             
              desc "Install Tailwind CSS into the app"
         | 
| 3 3 | 
             
              task :install do
         | 
| 4 | 
            -
                 | 
| 5 | 
            -
                  Rake::Task["tailwindcss:install:webpacker"].invoke
         | 
| 6 | 
            -
                else
         | 
| 7 | 
            -
                  Rake::Task["tailwindcss:install:asset_pipeline"].invoke
         | 
| 8 | 
            -
                end
         | 
| 9 | 
            -
              end
         | 
| 10 | 
            -
             | 
| 11 | 
            -
              namespace :install do
         | 
| 12 | 
            -
                desc "Install Tailwind CSS with the asset pipeline"
         | 
| 13 | 
            -
                task :asset_pipeline do
         | 
| 14 | 
            -
                  run_install_template "tailwindcss_with_asset_pipeline"
         | 
| 15 | 
            -
                end
         | 
| 16 | 
            -
             | 
| 17 | 
            -
                desc "Install Tailwind CSS with webpacker"
         | 
| 18 | 
            -
                task :webpacker do
         | 
| 19 | 
            -
                  run_install_template "tailwindcss_with_webpacker"
         | 
| 20 | 
            -
                end
         | 
| 4 | 
            +
                system "#{RbConfig.ruby} ./bin/rails app:template LOCATION=#{File.expand_path("../install/tailwindcss.rb", __dir__)}"
         | 
| 21 5 | 
             
              end
         | 
| 22 6 |  | 
| 23 7 | 
             
              desc "Show the list of class names being kept in Tailwind CSS"
         | 
| @@ -31,10 +15,6 @@ namespace :tailwindcss do | |
| 31 15 | 
             
              end
         | 
| 32 16 | 
             
            end
         | 
| 33 17 |  | 
| 34 | 
            -
            def run_install_template(path)
         | 
| 35 | 
            -
              system "#{RbConfig.ruby} ./bin/rails app:template LOCATION=#{File.expand_path("../install/#{path}.rb", __dir__)}"
         | 
| 36 | 
            -
            end
         | 
| 37 | 
            -
             | 
| 38 18 | 
             
            def default_files_with_class_names
         | 
| 39 19 | 
             
              Rails.root.glob("app/views/**/*.*") + Rails.root.glob("app/helpers/**/*.rb")
         | 
| 40 20 | 
             
            end
         | 
| @@ -42,3 +22,4 @@ end | |
| 42 22 | 
             
            def tailwind_css
         | 
| 43 23 | 
             
              Pathname.new(__FILE__).join("../../../app/assets/stylesheets/tailwind.css").read
         | 
| 44 24 | 
             
            end
         | 
| 25 | 
            +
             | 
    
        metadata
    CHANGED
    
    | @@ -1,17 +1,17 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: tailwindcss-rails
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version: 0. | 
| 4 | 
            +
              version: 0.5.4
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - David Heinemeier Hansson
         | 
| 8 | 
            -
            autorequire:
         | 
| 8 | 
            +
            autorequire: 
         | 
| 9 9 | 
             
            bindir: bin
         | 
| 10 10 | 
             
            cert_chain: []
         | 
| 11 | 
            -
            date: 2021- | 
| 11 | 
            +
            date: 2021-12-03 00:00:00.000000000 Z
         | 
| 12 12 | 
             
            dependencies:
         | 
| 13 13 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 14 | 
            -
              name:  | 
| 14 | 
            +
              name: railties
         | 
| 15 15 | 
             
              requirement: !ruby/object:Gem::Requirement
         | 
| 16 16 | 
             
                requirements:
         | 
| 17 17 | 
             
                - - ">="
         | 
| @@ -24,7 +24,7 @@ dependencies: | |
| 24 24 | 
             
                - - ">="
         | 
| 25 25 | 
             
                  - !ruby/object:Gem::Version
         | 
| 26 26 | 
             
                    version: 6.0.0
         | 
| 27 | 
            -
            description:
         | 
| 27 | 
            +
            description: 
         | 
| 28 28 | 
             
            email: david@loudthinking.com
         | 
| 29 29 | 
             
            executables: []
         | 
| 30 30 | 
             
            extensions: []
         | 
| @@ -51,9 +51,19 @@ files: | |
| 51 51 | 
             
            - app/assets/fonts/Inter-roman.vietnamese.var.woff2
         | 
| 52 52 | 
             
            - app/assets/stylesheets/inter-font.css.erb
         | 
| 53 53 | 
             
            - app/assets/stylesheets/tailwind.css
         | 
| 54 | 
            -
            - lib/ | 
| 55 | 
            -
            - lib/ | 
| 56 | 
            -
            - lib/ | 
| 54 | 
            +
            - lib/generators/tailwindcss/controller/controller_generator.rb
         | 
| 55 | 
            +
            - lib/generators/tailwindcss/controller/templates/view.html.erb.tt
         | 
| 56 | 
            +
            - lib/generators/tailwindcss/mailer/mailer_generator.rb
         | 
| 57 | 
            +
            - lib/generators/tailwindcss/mailer/templates/view.html.erb.tt
         | 
| 58 | 
            +
            - lib/generators/tailwindcss/mailer/templates/view.text.erb.tt
         | 
| 59 | 
            +
            - lib/generators/tailwindcss/scaffold/scaffold_generator.rb
         | 
| 60 | 
            +
            - lib/generators/tailwindcss/scaffold/templates/_form.html.erb.tt
         | 
| 61 | 
            +
            - lib/generators/tailwindcss/scaffold/templates/edit.html.erb.tt
         | 
| 62 | 
            +
            - lib/generators/tailwindcss/scaffold/templates/index.html.erb.tt
         | 
| 63 | 
            +
            - lib/generators/tailwindcss/scaffold/templates/new.html.erb.tt
         | 
| 64 | 
            +
            - lib/generators/tailwindcss/scaffold/templates/partial.html.erb.tt
         | 
| 65 | 
            +
            - lib/generators/tailwindcss/scaffold/templates/show.html.erb.tt
         | 
| 66 | 
            +
            - lib/install/tailwindcss.rb
         | 
| 57 67 | 
             
            - lib/tailwindcss-rails.rb
         | 
| 58 68 | 
             
            - lib/tailwindcss/compressor.rb
         | 
| 59 69 | 
             
            - lib/tailwindcss/engine.rb
         | 
| @@ -65,7 +75,7 @@ licenses: | |
| 65 75 | 
             
            - MIT
         | 
| 66 76 | 
             
            metadata:
         | 
| 67 77 | 
             
              homepage_uri: https://github.com/rails/tailwindcss-rails
         | 
| 68 | 
            -
            post_install_message:
         | 
| 78 | 
            +
            post_install_message: 
         | 
| 69 79 | 
             
            rdoc_options: []
         | 
| 70 80 | 
             
            require_paths:
         | 
| 71 81 | 
             
            - lib
         | 
| @@ -80,8 +90,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement | |
| 80 90 | 
             
                - !ruby/object:Gem::Version
         | 
| 81 91 | 
             
                  version: '0'
         | 
| 82 92 | 
             
            requirements: []
         | 
| 83 | 
            -
            rubygems_version: 3. | 
| 84 | 
            -
            signing_key:
         | 
| 93 | 
            +
            rubygems_version: 3.2.32
         | 
| 94 | 
            +
            signing_key: 
         | 
| 85 95 | 
             
            specification_version: 4
         | 
| 86 96 | 
             
            summary: Integrate Tailwind CSS with the asset pipeline in Rails.
         | 
| 87 97 | 
             
            test_files: []
         | 
| @@ -1,12 +0,0 @@ | |
| 1 | 
            -
            APPLICATION_LAYOUT_PATH = Rails.root.join("app/views/layouts/application.html.erb")
         | 
| 2 | 
            -
             | 
| 3 | 
            -
            if APPLICATION_LAYOUT_PATH.exist?
         | 
| 4 | 
            -
              say "Add Tailwindcss include tags in application layout"
         | 
| 5 | 
            -
              insert_into_file Rails.root.join("app/views/layouts/application.html.erb").to_s, %(\n    <%= stylesheet_link_tag "inter-font" %>\n    <%= stylesheet_link_tag "tailwind" %>), before: /^\s*<%= stylesheet_link_tag/
         | 
| 6 | 
            -
            else
         | 
| 7 | 
            -
              say "Default application.html.erb is missing!", :red
         | 
| 8 | 
            -
              say %(        Add <%= stylesheet_link_tag "inter-font" %> and <%= stylesheet_link_tag "tailwind" %> within the <head> tag in your custom layout.)
         | 
| 9 | 
            -
            end
         | 
| 10 | 
            -
             | 
| 11 | 
            -
            say "Turn on purging of unused css classes in production"
         | 
| 12 | 
            -
            gsub_file Rails.root.join("config/environments/production.rb"), /^\s+#?\s+config.assets.css_compressor =.*$/, %(  config.assets.css_compressor = :purger)
         | 
| @@ -1,22 +0,0 @@ | |
| 1 | 
            -
            WEBPACK_STYLESHEETS_PATH = "#{Webpacker.config.source_path}/stylesheets"
         | 
| 2 | 
            -
            APPLICATION_LAYOUT_PATH  = Rails.root.join("app/views/layouts/application.html.erb")
         | 
| 3 | 
            -
             | 
| 4 | 
            -
            say "Installing Tailwind CSS"
         | 
| 5 | 
            -
            run "yarn add tailwindcss@npm:@tailwindcss/postcss7-compat postcss@^7 autoprefixer@^9"
         | 
| 6 | 
            -
            insert_into_file "#{Webpacker.config.source_entry_path}/application.js", "\nimport \"stylesheets/application\"\n"
         | 
| 7 | 
            -
             | 
| 8 | 
            -
            say "Configuring Tailwind CSS"
         | 
| 9 | 
            -
            directory Pathname.new(__dir__).join("stylesheets"), Webpacker.config.source_path.join("stylesheets")
         | 
| 10 | 
            -
            Dir.chdir(WEBPACK_STYLESHEETS_PATH) { run "npx tailwindcss init" }
         | 
| 11 | 
            -
             | 
| 12 | 
            -
            insert_into_file "postcss.config.js", "require('tailwindcss')(\"./app/javascript/stylesheets/tailwind.config.js\"),\n    ",
         | 
| 13 | 
            -
              before: "require('postcss-import')"
         | 
| 14 | 
            -
             | 
| 15 | 
            -
             | 
| 16 | 
            -
            if APPLICATION_LAYOUT_PATH.exist?
         | 
| 17 | 
            -
              say "Add Tailwindcss include tags in application layout"
         | 
| 18 | 
            -
              insert_into_file Rails.root.join("app/views/layouts/application.html.erb").to_s, %(\n    <%= stylesheet_pack_tag "application", "data-turbo-track": "reload" %>), before: /\s*<\/head>/
         | 
| 19 | 
            -
            else
         | 
| 20 | 
            -
              say "Default application.html.erb is missing!", :red
         | 
| 21 | 
            -
              say %(        Add <%= stylesheet_pack_tag "application", "data-turbo-track": "reload" %> within the <head> tag in your custom layout.)
         | 
| 22 | 
            -
            end
         |