Skip to content
This repository was archived by the owner on May 11, 2026. It is now read-only.

Commit 0f9df93

Browse files
dariyeclaude
andcommitted
Add llms.txt for AI-assisted documentation discovery
Adds /llms.txt following the llms.txt specification (llmstxt.org) so that LLMs can discover and reference RubyUI component documentation at inference time. Includes a rake task (rake llms:generate) to regenerate the file from doc view sources when components are added or removed. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
1 parent f68be0e commit 0f9df93

2 files changed

Lines changed: 214 additions & 0 deletions

File tree

lib/tasks/llms_txt.rake

Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
# frozen_string_literal: true
2+
3+
# Rake task to generate /public/llms.txt from doc views and routes.
4+
#
5+
# Usage:
6+
# rake llms:generate
7+
# rake llms:generate[https://rubyui.com] # custom base URL
8+
#
9+
# Run this after adding/removing components to keep llms.txt in sync.
10+
11+
namespace :llms do
12+
desc "Generate public/llms.txt from doc view files"
13+
task :generate, [:base_url] do |_t, args|
14+
base_url = (args[:base_url] || "https://rubyui.com").chomp("/")
15+
docs_dir = File.expand_path("../../app/views/docs", __dir__)
16+
17+
# Category mapping: filename => [category, subcategory]
18+
categories = {
19+
# Form & Input
20+
"button" => "Form & Input",
21+
"input" => "Form & Input",
22+
"masked_input" => "Form & Input",
23+
"textarea" => "Form & Input",
24+
"checkbox" => "Form & Input",
25+
"checkbox_group" => "Form & Input",
26+
"radio_button" => "Form & Input",
27+
"select" => "Form & Input",
28+
"switch" => "Form & Input",
29+
"calendar" => "Form & Input",
30+
"date_picker" => "Form & Input",
31+
"combobox" => "Form & Input",
32+
"form" => "Form & Input",
33+
# Layout & Navigation
34+
"accordion" => "Layout & Navigation",
35+
"breadcrumb" => "Layout & Navigation",
36+
"tabs" => "Layout & Navigation",
37+
"sidebar" => "Layout & Navigation",
38+
"separator" => "Layout & Navigation",
39+
"pagination" => "Layout & Navigation",
40+
"link" => "Layout & Navigation",
41+
"collapsible" => "Layout & Navigation",
42+
# Overlays & Dialogs
43+
"dialog" => "Overlays & Dialogs",
44+
"alert_dialog" => "Overlays & Dialogs",
45+
"sheet" => "Overlays & Dialogs",
46+
"popover" => "Overlays & Dialogs",
47+
"tooltip" => "Overlays & Dialogs",
48+
"hover_card" => "Overlays & Dialogs",
49+
"context_menu" => "Overlays & Dialogs",
50+
"dropdown_menu" => "Overlays & Dialogs",
51+
"command" => "Overlays & Dialogs",
52+
# Feedback & Status
53+
"alert" => "Feedback & Status",
54+
"progress" => "Feedback & Status",
55+
"skeleton" => "Feedback & Status",
56+
"badge" => "Feedback & Status",
57+
# Display & Media
58+
"avatar" => "Display & Media",
59+
"card" => "Display & Media",
60+
"table" => "Display & Media",
61+
"chart" => "Display & Media",
62+
"carousel" => "Display & Media",
63+
"aspect_ratio" => "Display & Media",
64+
"typography" => "Display & Media",
65+
"codeblock" => "Display & Media",
66+
"clipboard" => "Display & Media",
67+
"shortcut_key" => "Display & Media",
68+
"theme_toggle" => "Display & Media"
69+
}
70+
71+
# Parse title and description from a doc view .rb file
72+
def extract_header(file_path)
73+
content = File.read(file_path)
74+
if content =~ /Docs::Header\.new\(title:\s*(?:"([^"]+)"|'([^']+)'|(\w+))\s*,\s*description:\s*"([^"]+)"/
75+
title = $1 || $2 || $3
76+
description = $4
77+
# If title is a variable reference (like `component`), look for the assignment
78+
if title =~ /\A[a-z_]+\z/
79+
content.match(/#{title}\s*=\s*"([^"]+)"/) { |m| title = m[1] }
80+
end
81+
[title, description]
82+
end
83+
end
84+
85+
# Collect components
86+
components_by_category = Hash.new { |h, k| h[k] = [] }
87+
Dir.glob(File.join(docs_dir, "*.rb")).each do |file|
88+
next if File.basename(file) == "base.rb"
89+
90+
slug = File.basename(file, ".rb")
91+
result = extract_header(file)
92+
next unless result
93+
94+
title, description = result
95+
category = categories[slug] || "Miscellaneous"
96+
components_by_category[category] << { slug: slug, title: title, description: description }
97+
end
98+
99+
# Build llms.txt
100+
lines = []
101+
lines << "# RubyUI"
102+
lines << ""
103+
lines << "> RubyUI is a UI component library for Ruby developers, built on top of Phlex, TailwindCSS, and Stimulus JS. Components are inspired by shadcn/ui and use compatible theming with CSS variables. Install via the ruby_ui gem into any Rails application. Components are written in pure Ruby using Phlex (up to 12x faster than ERB) and use custom Stimulus.js controllers for interactivity."
104+
lines << ""
105+
106+
# Getting Started section
107+
lines << "## Getting Started"
108+
lines << ""
109+
lines << "- [Introduction](#{base_url}/docs/introduction): Overview of RubyUI, core ingredients (Phlex, TailwindCSS, Stimulus JS), and design philosophy."
110+
lines << "- [Installation](#{base_url}/docs/installation): How to install RubyUI in your Rails application."
111+
lines << "- [Installation with Rails Bundler](#{base_url}/docs/installation/rails_bundler): Setup using Rails with bundler and JS bundling."
112+
lines << "- [Installation with Rails Importmaps](#{base_url}/docs/installation/rails_importmaps): Setup using Rails with importmaps."
113+
lines << "- [Theming](#{base_url}/docs/theming): Guide to customizing colors and design tokens using CSS variables."
114+
lines << "- [Dark Mode](#{base_url}/docs/dark_mode): How to implement dark mode support."
115+
lines << "- [Customizing Components](#{base_url}/docs/customizing_components): How to customize and extend RubyUI components."
116+
lines << ""
117+
118+
# Components section
119+
lines << "## Components"
120+
lines << ""
121+
122+
category_order = ["Form & Input", "Layout & Navigation", "Overlays & Dialogs", "Feedback & Status", "Display & Media", "Miscellaneous"]
123+
category_order.each do |category|
124+
next unless components_by_category.key?(category)
125+
126+
items = components_by_category[category].sort_by { |c| c[:title] }
127+
lines << "### #{category}"
128+
lines << ""
129+
items.each do |comp|
130+
lines << "- [#{comp[:title]}](#{base_url}/docs/#{comp[:slug]}): #{comp[:description]}"
131+
end
132+
lines << ""
133+
end
134+
135+
output_path = File.expand_path("../../public/llms.txt", __dir__)
136+
File.write(output_path, lines.join("\n"))
137+
puts "Generated #{output_path} (#{components_by_category.values.sum(&:length)} components)"
138+
end
139+
end

public/llms.txt

Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
# RubyUI
2+
3+
> RubyUI is a UI component library for Ruby developers, built on top of Phlex, TailwindCSS, and Stimulus JS. Components are inspired by shadcn/ui and use compatible theming with CSS variables. Install via the ruby_ui gem into any Rails application. Components are written in pure Ruby using Phlex (up to 12x faster than ERB) and use custom Stimulus.js controllers for interactivity.
4+
5+
## Getting Started
6+
7+
- [Introduction](https://rubyui.com/docs/introduction): Overview of RubyUI, core ingredients (Phlex, TailwindCSS, Stimulus JS), and design philosophy.
8+
- [Installation](https://rubyui.com/docs/installation): How to install RubyUI in your Rails application.
9+
- [Installation with Rails Bundler](https://rubyui.com/docs/installation/rails_bundler): Setup using Rails with bundler and JS bundling.
10+
- [Installation with Rails Importmaps](https://rubyui.com/docs/installation/rails_importmaps): Setup using Rails with importmaps.
11+
- [Theming](https://rubyui.com/docs/theming): Guide to customizing colors and design tokens using CSS variables.
12+
- [Dark Mode](https://rubyui.com/docs/dark_mode): How to implement dark mode support.
13+
- [Customizing Components](https://rubyui.com/docs/customizing_components): How to customize and extend RubyUI components.
14+
15+
## Components
16+
17+
### Form & Input
18+
19+
- [Button](https://rubyui.com/docs/button): Displays a button or a component that looks like a button.
20+
- [Input](https://rubyui.com/docs/input): Displays a form input field or a component that looks like an input field.
21+
- [Masked Input](https://rubyui.com/docs/masked_input): Displays a form input field with applied mask.
22+
- [Textarea](https://rubyui.com/docs/textarea): Displays a textarea field.
23+
- [Checkbox](https://rubyui.com/docs/checkbox): A control that allows the user to toggle between checked and not checked.
24+
- [Checkbox Group](https://rubyui.com/docs/checkbox_group): A control that allows the user to toggle between checked and not checked.
25+
- [Radio Button](https://rubyui.com/docs/radio_button): A control that allows users to make a single selection from a list of options.
26+
- [Select](https://rubyui.com/docs/select): Displays a list of options for the user to pick from, triggered by a button.
27+
- [Switch](https://rubyui.com/docs/switch): A control that allows the user to toggle between checked and not checked.
28+
- [Calendar](https://rubyui.com/docs/calendar): A date field component that allows users to enter and edit date.
29+
- [Date Picker](https://rubyui.com/docs/date_picker): A date picker component with input.
30+
- [Combobox](https://rubyui.com/docs/combobox): Autocomplete input and command palette with a list of suggestions.
31+
- [Form](https://rubyui.com/docs/form): Building forms with built-in client-side validations.
32+
33+
### Layout & Navigation
34+
35+
- [Accordion](https://rubyui.com/docs/accordion): A vertically stacked set of interactive headings that each reveal a section of content.
36+
- [Breadcrumb](https://rubyui.com/docs/breadcrumb): Indicates the user's current location within a navigational hierarchy.
37+
- [Tabs](https://rubyui.com/docs/tabs): A set of layered sections of content, known as tab panels, displayed one at a time.
38+
- [Sidebar](https://rubyui.com/docs/sidebar): A composable, themeable and customizable sidebar component.
39+
- [Separator](https://rubyui.com/docs/separator): Visually or semantically separates content.
40+
- [Pagination](https://rubyui.com/docs/pagination): Pagination with page navigation, next and previous links.
41+
- [Link](https://rubyui.com/docs/link): Displays a link that looks like a button or underline link.
42+
- [Collapsible](https://rubyui.com/docs/collapsible): An interactive component which expands/collapses a panel.
43+
44+
### Overlays & Dialogs
45+
46+
- [Dialog](https://rubyui.com/docs/dialog): A window overlaid on either the primary window or another dialog window, rendering the content underneath inert.
47+
- [Alert Dialog](https://rubyui.com/docs/alert_dialog): A modal dialog that interrupts the user with important content and expects a response.
48+
- [Sheet](https://rubyui.com/docs/sheet): Extends the Sheet component to display content that complements the main content of the screen.
49+
- [Popover](https://rubyui.com/docs/popover): Displays rich content in a portal, triggered by a button.
50+
- [Tooltip](https://rubyui.com/docs/tooltip): A popup that displays information related to an element when the element receives keyboard focus or the mouse hovers over it.
51+
- [Hover Card](https://rubyui.com/docs/hover_card): For sighted users to preview content available behind a link.
52+
- [Context Menu](https://rubyui.com/docs/context_menu): Displays a menu to the user, such as a set of actions or functions, triggered by a right click.
53+
- [Dropdown Menu](https://rubyui.com/docs/dropdown_menu): Displays a menu to the user, such as a set of actions or functions, triggered by a button.
54+
- [Command](https://rubyui.com/docs/command): Fast, composable, unstyled command menu for Phlex.
55+
56+
### Feedback & Status
57+
58+
- [Alert](https://rubyui.com/docs/alert): Displays a callout for user attention.
59+
- [Progress](https://rubyui.com/docs/progress): Displays an indicator showing the completion progress of a task, typically displayed as a progress bar.
60+
- [Skeleton](https://rubyui.com/docs/skeleton): Use to show a placeholder while content is loading.
61+
- [Badge](https://rubyui.com/docs/badge): Displays a badge or a component that looks like a badge.
62+
63+
### Display & Media
64+
65+
- [Avatar](https://rubyui.com/docs/avatar): An image element with a fallback for representing the user.
66+
- [Card](https://rubyui.com/docs/card): Displays a card with header, content, and footer.
67+
- [Table](https://rubyui.com/docs/table): A responsive table component.
68+
- [Chart](https://rubyui.com/docs/chart): Displays information in a visual way.
69+
- [Carousel](https://rubyui.com/docs/carousel): A carousel with motion and swipe built using Embla.
70+
- [Aspect Ratio](https://rubyui.com/docs/aspect_ratio): Displays content within a desired ratio.
71+
- [Typography](https://rubyui.com/docs/typography): Sensible defaults to use for text.
72+
- [Codeblock](https://rubyui.com/docs/codeblock): A component for displaying highlighted code.
73+
- [Clipboard](https://rubyui.com/docs/clipboard): A control to allow you to copy content to the clipboard.
74+
- [Shortcut Key](https://rubyui.com/docs/shortcut_key): A component for displaying keyboard shortcuts.
75+
- [Theme Toggle](https://rubyui.com/docs/theme_toggle): Toggle between dark/light theme.

0 commit comments

Comments
 (0)