ratatui_ruby-devtools 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (90) hide show
  1. checksums.yaml +7 -0
  2. data/.builds/ruby-4.0.yml +38 -0
  3. data/.pre-commit-config.yaml +16 -0
  4. data/.rubocop.yml +8 -0
  5. data/AGENTS.md +72 -0
  6. data/CHANGELOG.md +23 -0
  7. data/LICENSE +661 -0
  8. data/LICENSES/AGPL-3.0-or-later.txt +661 -0
  9. data/LICENSES/CC-BY-SA-4.0.txt +427 -0
  10. data/LICENSES/CC0-1.0.txt +121 -0
  11. data/LICENSES/MIT-0.txt +16 -0
  12. data/LICENSES/MIT.txt +18 -0
  13. data/README.md +199 -0
  14. data/REUSE.toml +18 -0
  15. data/Rakefile +13 -0
  16. data/bin/agent_rake +13 -0
  17. data/bin/announce +13 -0
  18. data/bin/console +14 -0
  19. data/bin/consolidate_md +13 -0
  20. data/bin/hbs +13 -0
  21. data/bin/setup +17 -0
  22. data/doc/contributors/documentation_style.md +121 -0
  23. data/doc/custom.css +22 -0
  24. data/exe/agent_rake +96 -0
  25. data/exe/announce +1120 -0
  26. data/exe/consolidate_md +246 -0
  27. data/exe/hbs +670 -0
  28. data/exe/scaffold +662 -0
  29. data/lib/ratatui_ruby/devtools/tasks/autodoc/examples.rb +133 -0
  30. data/lib/ratatui_ruby/devtools/tasks/autodoc/member.rb +116 -0
  31. data/lib/ratatui_ruby/devtools/tasks/autodoc/name.rb +33 -0
  32. data/lib/ratatui_ruby/devtools/tasks/autodoc.rake +21 -0
  33. data/lib/ratatui_ruby/devtools/tasks/bump/cargo_lockfile.rb +38 -0
  34. data/lib/ratatui_ruby/devtools/tasks/bump/changelog.rb +67 -0
  35. data/lib/ratatui_ruby/devtools/tasks/bump/header.rb +43 -0
  36. data/lib/ratatui_ruby/devtools/tasks/bump/history.rb +50 -0
  37. data/lib/ratatui_ruby/devtools/tasks/bump/links.rb +78 -0
  38. data/lib/ratatui_ruby/devtools/tasks/bump/manifest.rb +63 -0
  39. data/lib/ratatui_ruby/devtools/tasks/bump/ruby_gem.rb +77 -0
  40. data/lib/ratatui_ruby/devtools/tasks/bump/sem_ver.rb +63 -0
  41. data/lib/ratatui_ruby/devtools/tasks/bump/unreleased_section.rb +75 -0
  42. data/lib/ratatui_ruby/devtools/tasks/bump.rake +80 -0
  43. data/lib/ratatui_ruby/devtools/tasks/cargo.rake +47 -0
  44. data/lib/ratatui_ruby/devtools/tasks/doc.rake +887 -0
  45. data/lib/ratatui_ruby/devtools/tasks/example_viewer.html.erb +172 -0
  46. data/lib/ratatui_ruby/devtools/tasks/license/headers_md.rb +276 -0
  47. data/lib/ratatui_ruby/devtools/tasks/license/headers_rb.rb +236 -0
  48. data/lib/ratatui_ruby/devtools/tasks/license/license_utils.rb +143 -0
  49. data/lib/ratatui_ruby/devtools/tasks/license/snippets_md.rb +353 -0
  50. data/lib/ratatui_ruby/devtools/tasks/license/snippets_rdoc.rb +186 -0
  51. data/lib/ratatui_ruby/devtools/tasks/license.rake +91 -0
  52. data/lib/ratatui_ruby/devtools/tasks/lint.rake +84 -0
  53. data/lib/ratatui_ruby/devtools/tasks/rdoc_config.rb +45 -0
  54. data/lib/ratatui_ruby/devtools/tasks/resources/build.yml.erb +54 -0
  55. data/lib/ratatui_ruby/devtools/tasks/resources/rubies.yml +7 -0
  56. data/lib/ratatui_ruby/devtools/tasks/reuse.rake +104 -0
  57. data/lib/ratatui_ruby/devtools/tasks/sourcehut.rake +94 -0
  58. data/lib/ratatui_ruby/devtools/tasks/test.rake +18 -0
  59. data/lib/ratatui_ruby/devtools/templates/.builds/ruby.yml.erb +47 -0
  60. data/lib/ratatui_ruby/devtools/templates/.gitignore.erb +18 -0
  61. data/lib/ratatui_ruby/devtools/templates/.pre-commit-config.yaml.erb +16 -0
  62. data/lib/ratatui_ruby/devtools/templates/.rubocop.yml.erb +8 -0
  63. data/lib/ratatui_ruby/devtools/templates/AGENTS.md.erb +65 -0
  64. data/lib/ratatui_ruby/devtools/templates/CHANGELOG.md.erb +18 -0
  65. data/lib/ratatui_ruby/devtools/templates/Gemfile.erb +32 -0
  66. data/lib/ratatui_ruby/devtools/templates/README.md.erb +127 -0
  67. data/lib/ratatui_ruby/devtools/templates/REUSE.toml.erb +33 -0
  68. data/lib/ratatui_ruby/devtools/templates/Rakefile.erb +29 -0
  69. data/lib/ratatui_ruby/devtools/templates/bin/console.erb +18 -0
  70. data/lib/ratatui_ruby/devtools/templates/bin/setup.erb +24 -0
  71. data/lib/ratatui_ruby/devtools/templates/doc/concepts/application_architecture.md.erb +16 -0
  72. data/lib/ratatui_ruby/devtools/templates/doc/concepts/application_testing.md.erb +49 -0
  73. data/lib/ratatui_ruby/devtools/templates/doc/custom.css.erb +24 -0
  74. data/lib/ratatui_ruby/devtools/templates/doc/getting_started/quickstart.md.erb +56 -0
  75. data/lib/ratatui_ruby/devtools/templates/doc/images/.gitkeep +0 -0
  76. data/lib/ratatui_ruby/devtools/templates/doc/index.md.erb +25 -0
  77. data/lib/ratatui_ruby/devtools/templates/exe/.gitkeep +0 -0
  78. data/lib/ratatui_ruby/devtools/templates/gemspec.erb +58 -0
  79. data/lib/ratatui_ruby/devtools/templates/mise.toml.erb +12 -0
  80. data/lib/ratatui_ruby/devtools/templates/tasks/example_viewer.html.erb +174 -0
  81. data/lib/ratatui_ruby/devtools/templates/tasks/resources/build.yml.erb +62 -0
  82. data/lib/ratatui_ruby/devtools/templates/tasks/resources/index.html.erb +46 -0
  83. data/lib/ratatui_ruby/devtools/templates/tasks/resources/rubies.yml.erb +9 -0
  84. data/lib/ratatui_ruby/devtools/templates/vendor/goodcop/base.yml +1047 -0
  85. data/lib/ratatui_ruby/devtools/version.rb +13 -0
  86. data/lib/ratatui_ruby/devtools.rb +137 -0
  87. data/mise.toml +7 -0
  88. data/sig/ratatui_ruby/devtools.rbs +15 -0
  89. data/vendor/goodcop/base.yml +1047 -0
  90. metadata +252 -0
data/README.md ADDED
@@ -0,0 +1,199 @@
1
+ <!--
2
+ SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
3
+ SPDX-License-Identifier: CC-BY-SA-4.0
4
+ -->
5
+ # ratatui_ruby-devtools
6
+
7
+ [![
8
+ builds.sr.ht status](https://builds.sr.ht/~kerrick/ratatui_ruby-devtools.svg)](https://builds.sr.ht/~kerrick/ratatui_ruby-devtools?) [![
9
+ License](https://img.shields.io/badge/License-AGPL--3.0--or--later-a2c93e)](https://spdx.org/licenses/AGPL-3.0-or-later.html) [![
10
+ Gem Version](https://img.shields.io/gem/v/ratatui_ruby-devtools)](https://rubygems.org/gems/ratatui_ruby-devtools) [![
11
+ Mailing List: Development](https://img.shields.io/badge/mailing_list-development-4954d5.svg?logo=data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIyNCIgaGVpZ2h0PSIyNCIgdmlld0JveD0iMCAwIDI0IDI0IiBmaWxsPSJub25lIiBzdHJva2U9IiNmZmZmZmYiIHN0cm9rZS13aWR0aD0iMiIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIiBjbGFzcz0iaWNvbiBpY29uLXRhYmxlciBpY29ucy10YWJsZXItb3V0bGluZSBpY29uLXRhYmxlci1tYWlsIj48cGF0aCBzdHJva2U9Im5vbmUiIGQ9Ik0wIDBoMjR2MjRIMHoiIGZpbGw9Im5vbmUiLz48cGF0aCBkPSJNMyA3YTIgMiAwIDAgMSAyIC0yaDE0YTIgMiAwIDAgMSAyIDJ2MTBhMiAyIDAgMCAxIC0yIDJoLTE0YTIgMiAwIDAgMSAtMiAtMnYtMTB6IiAvPjxwYXRoIGQ9Ik0zIDdsOSA2bDkgLTYiIC8+PC9zdmc+Cg==)](https://lists.sr.ht/~kerrick/ratatui_ruby-devel)
12
+
13
+
14
+ ## Introduction
15
+
16
+ **ratatui_ruby-devtools** provides shared development tooling for the [RatatuiRuby ecosystem](https://sr.ht/~kerrick/ratatui_ruby/). It includes Rake tasks, linters, license enforcement, and build tooling used across all RatatuiRuby gems.
17
+
18
+ This is a **non-runtime** gem. It provides build tooling—not application features. Add it to your `:development` group only.
19
+
20
+
21
+ ## Installation
22
+
23
+ Add this line to your application's Gemfile:
24
+
25
+ <!-- SPDX-SnippetBegin -->
26
+ <!--
27
+ SPDX-FileCopyrightText: 2026 Kerrick Long
28
+ SPDX-License-Identifier: MIT-0
29
+ -->
30
+ ```ruby
31
+ group :development do
32
+ gem "ratatui_ruby-devtools"
33
+ end
34
+ ```
35
+ <!-- SPDX-SnippetEnd -->
36
+
37
+ And then execute:
38
+
39
+ <!-- SPDX-SnippetBegin -->
40
+ <!--
41
+ SPDX-FileCopyrightText: 2026 Kerrick Long
42
+ SPDX-License-Identifier: MIT-0
43
+ -->
44
+ ```bash
45
+ bundle install
46
+ ```
47
+ <!-- SPDX-SnippetEnd -->
48
+
49
+
50
+ ## Usage
51
+
52
+ In your `Rakefile`:
53
+
54
+ <!-- SPDX-SnippetBegin -->
55
+ <!--
56
+ SPDX-FileCopyrightText: 2026 Kerrick Long
57
+ SPDX-License-Identifier: MIT-0
58
+ -->
59
+ ```ruby
60
+ require "bundler/gem_tasks"
61
+ require "ratatui_ruby/devtools"
62
+
63
+ RatatuiRuby::Devtools.install!
64
+
65
+ task default: %i[lint]
66
+ ```
67
+ <!-- SPDX-SnippetEnd -->
68
+
69
+ This imports all devtools rake tasks into your project.
70
+
71
+
72
+ ## Provided Rake Tasks
73
+
74
+ ### Linting
75
+
76
+ | Task | Description |
77
+ |------|-------------|
78
+ | `rake lint` | Run all lint tasks |
79
+ | `rake lint:fix` | Auto-fix all linting issues |
80
+ | `rake rubocop` | Run RuboCop |
81
+ | `rake rubycritic` | Run RubyCritic |
82
+ | `rake doc:suggest` | Suggest documentation improvements |
83
+
84
+ ### License Enforcement
85
+
86
+ | Task | Description |
87
+ |------|-------------|
88
+ | `rake license:all` | Run all license tasks |
89
+ | `rake license:headers:all` | Ensure all files have SPDX headers |
90
+ | `rake license:new` | Apply license headers to changed files only |
91
+ | `rake reuse:lint` | Check REUSE/SPDX compliance |
92
+ | `rake reuse:fix` | Add missing SPDX headers |
93
+
94
+ ### Version Bumping
95
+
96
+ | Task | Description |
97
+ |------|-------------|
98
+ | `rake bump:major` | Bump major version |
99
+ | `rake bump:minor` | Bump minor version |
100
+ | `rake bump:patch` | Bump patch version |
101
+ | `rake bump:exact[0.1.0]` | Set exact version |
102
+
103
+
104
+ ## Executables
105
+
106
+ ### `bin/agent_rake`
107
+
108
+ An AI-friendly wrapper for `bundle exec rake` that captures all output and only shows failure summaries.
109
+
110
+ <!-- SPDX-SnippetBegin -->
111
+ <!--
112
+ SPDX-FileCopyrightText: 2026 Kerrick Long
113
+ SPDX-License-Identifier: MIT-0
114
+ -->
115
+ ```bash
116
+ bin/agent_rake # Run default task
117
+ bin/agent_rake test # Run specific task
118
+ ```
119
+ <!-- SPDX-SnippetEnd -->
120
+
121
+ ### `bin/consolidate_md`
122
+
123
+ Merge multiple markdown files into one, adjusting heading levels.
124
+
125
+ ### `bin/hbs`
126
+
127
+ Handlebars templating utility.
128
+
129
+
130
+ ## Templates
131
+
132
+ Devtools includes templates for scaffolding new ecosystem gems:
133
+
134
+ | Template | Purpose |
135
+ |----------|---------|
136
+ | `AGENTS.md.erb` | AI agent instructions |
137
+ | `.pre-commit-config.yaml` | Pre-commit hooks |
138
+ | `Rakefile.erb` | Standard Rakefile |
139
+ | `sourcehut.rake.erb` | SourceHut CI task |
140
+ | `build.yml.erb` | SourceHut build manifest |
141
+ | `gemspec.erb` | Standard gemspec |
142
+ | `bin/setup.erb` | Setup script |
143
+ | `mise.toml.erb` | Toolchain versions |
144
+ | `REUSE.toml.erb` | License annotations |
145
+ | `.gitignore.erb` | Git ignores |
146
+ | `.rubocop.yml.erb` | RuboCop config |
147
+
148
+ Access templates via:
149
+
150
+ <!-- SPDX-SnippetBegin -->
151
+ <!--
152
+ SPDX-FileCopyrightText: 2026 Kerrick Long
153
+ SPDX-License-Identifier: MIT-0
154
+ -->
155
+ ```ruby
156
+ RatatuiRuby::Devtools.templates_path
157
+ # => "/path/to/devtools/templates"
158
+ ```
159
+ <!-- SPDX-SnippetEnd -->
160
+
161
+
162
+ ## Configuration
163
+
164
+ Tasks auto-discover gem configuration from your `*.gemspec`. Override if needed:
165
+
166
+ <!-- SPDX-SnippetBegin -->
167
+ <!--
168
+ SPDX-FileCopyrightText: 2026 Kerrick Long
169
+ SPDX-License-Identifier: MIT-0
170
+ -->
171
+ ```ruby
172
+ RatatuiRuby::Devtools.gem_name = "my_gem"
173
+ RatatuiRuby::Devtools.version_file = "lib/my_gem/version.rb"
174
+ ```
175
+ <!-- SPDX-SnippetEnd -->
176
+
177
+ Environment variables for REUSE tasks:
178
+
179
+ | Variable | Default |
180
+ |----------|---------|
181
+ | `REUSE_COPYRIGHT` | `Kerrick Long <me@kerricklong.com>` |
182
+ | `REUSE_CODE_LICENSE` | `AGPL-3.0-or-later` |
183
+ | `REUSE_DOC_LICENSE` | `CC-BY-SA-4.0` |
184
+
185
+
186
+ ## Contributing
187
+
188
+ Bug reports and pull requests are welcome on [sourcehut](https://sourcehut.org) at https://sr.ht/~kerrick/ratatui_ruby/. This project is intended to be a safe, productive collaboration, and contributors are expected to adhere to the [Code of Conduct](https://man.sr.ht/~kerrick/ratatui_ruby/code_of_conduct.md).
189
+
190
+ Want to help develop **ratatui_ruby-devtools**? Check out the [contribution guide on the wiki](https://man.sr.ht/~kerrick/ratatui_ruby/contributing.md).
191
+
192
+
193
+ ## Copyright & License
194
+
195
+ **ratatui_ruby-devtools** is copyright 2026, Kerrick Long.
196
+
197
+ The gem is [AGPL-3.0-or-later](./LICENSES/AGPL-3.0-or-later.txt): you may use it freely, but you must share changes you make. Documentation is [CC-BY-SA-4.0](./LICENSES/CC-BY-SA-4.0.txt). Code snippets in documentation are [MIT-0](./LICENSES/MIT-0.txt) (no attribution required).
198
+
199
+ This program was created with significant assistance from multiple LLMs. The process was human-controlled through creative prompts, with human contributions to each commit. See commit footers for model attribution. [declare-ai.org](https://declare-ai.org/1.0.0/creative.html)
data/REUSE.toml ADDED
@@ -0,0 +1,18 @@
1
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
2
+ # SPDX-License-Identifier: AGPL-3.0-or-later
3
+
4
+ version = 1
5
+
6
+ [[annotations]]
7
+ path = 'Gemfile.lock'
8
+ SPDX-FileCopyrightText = "2026 Kerrick Long <me@kerricklong.com>"
9
+ SPDX-License-Identifier = "CC0-1.0"
10
+
11
+ # Template files contain ERB that generates SPDX headers for consumer gems.
12
+ # The templates themselves are AGPL-3.0-or-later, while the generated output
13
+ # will have the appropriate license for the consumer gem.
14
+ [[annotations]]
15
+ path = 'lib/ratatui_ruby/devtools/templates/**/*.erb'
16
+ SPDX-FileCopyrightText = "2026 Kerrick Long <me@kerricklong.com>"
17
+ SPDX-License-Identifier = "AGPL-3.0-or-later"
18
+
data/Rakefile ADDED
@@ -0,0 +1,13 @@
1
+ # frozen_string_literal: true
2
+
3
+ #--
4
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
5
+ # SPDX-License-Identifier: AGPL-3.0-or-later
6
+ #++
7
+
8
+ require "bundler/gem_tasks"
9
+ require_relative "lib/ratatui_ruby/devtools"
10
+
11
+ RatatuiRuby::Devtools.install!
12
+
13
+ task default: %i[lint]
data/bin/agent_rake ADDED
@@ -0,0 +1,13 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ #--
5
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
6
+ # SPDX-License-Identifier: AGPL-3.0-or-later
7
+ #++
8
+
9
+ # Development wrapper for agent_rake executable.
10
+ # Loads the local gem via Bundler, then delegates to exe/agent_rake.
11
+
12
+ require "bundler/setup"
13
+ load File.expand_path("../exe/agent_rake", __dir__)
data/bin/announce ADDED
@@ -0,0 +1,13 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ #--
5
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
6
+ # SPDX-License-Identifier: AGPL-3.0-or-later
7
+ #++
8
+
9
+ # Development wrapper for announce executable.
10
+ # Loads the local gem via Bundler, then delegates to exe/announce.
11
+
12
+ require "bundler/setup"
13
+ load File.expand_path("../exe/announce", __dir__)
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
5
+ # SPDX-License-Identifier: AGPL-3.0-or-later
6
+
7
+ require "bundler/setup"
8
+ require "ratatui_ruby/devtools"
9
+
10
+ # You can add fixtures and/or initialization code here to make experimenting
11
+ # with your gem easier. You can also use a different console, if you like.
12
+
13
+ require "irb"
14
+ IRB.start(__FILE__)
@@ -0,0 +1,13 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ #--
5
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
6
+ # SPDX-License-Identifier: AGPL-3.0-or-later
7
+ #++
8
+
9
+ # Development wrapper for consolidate_md executable.
10
+ # Loads the local gem via Bundler, then delegates to exe/consolidate_md.
11
+
12
+ require "bundler/setup"
13
+ load File.expand_path("../exe/consolidate_md", __dir__)
data/bin/hbs ADDED
@@ -0,0 +1,13 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ #--
5
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
6
+ # SPDX-License-Identifier: AGPL-3.0-or-later
7
+ #++
8
+
9
+ # Development wrapper for hbs executable.
10
+ # Loads the local gem via Bundler, then delegates to exe/hbs.
11
+
12
+ require "bundler/setup"
13
+ load File.expand_path("../exe/hbs", __dir__)
data/bin/setup ADDED
@@ -0,0 +1,17 @@
1
+ #!/usr/bin/env bash
2
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
3
+ # SPDX-License-Identifier: AGPL-3.0-or-later
4
+
5
+ set -euo pipefail
6
+ IFS=$'\n\t'
7
+ set -vx
8
+
9
+ if command -v mise >/dev/null 2>&1; then
10
+ mise install
11
+ mise x -- pip install reuse
12
+ mise x -- bundle install
13
+ pre-commit install
14
+ else
15
+ echo "mise isn't installed. Please install it to continue." >&2
16
+ exit 1
17
+ fi
@@ -0,0 +1,121 @@
1
+ <!--
2
+ SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
3
+ SPDX-License-Identifier: CC-BY-SA-4.0
4
+ -->
5
+
6
+ # Documentation Style Guide
7
+
8
+ This project follows a strict and specific documentation style designed to be helpful, readable, and consistent. It combines the structural clarity of Christopher Alexander's Pattern Language with the prose style of William Zinsser's *On Writing Well* and the usability of the U.S. Federal Plain Language Guidelines.
9
+
10
+ **All agents and contributors must adhere to these standards.**
11
+
12
+ ## 1. Core Philosophy
13
+
14
+ * **Context, Problem, Solution (Alexandrian Form):** Do not just say *what* a class does. Explain *why* it exists. Start with the context, state the problem (the pain point without this tool), and then present the class as the solution.
15
+ * **Prose Style (Zinsser/Klinkenborg):** Use short, punchy sentences. Use active voice. Cut unnecessary words. Avoid "allow," "enable," "provide," "support," "functionality," and "capability" where possible. Weak verbs hide the action. Strong verbs drive the sentence.
16
+ * **User-Centric (Plain Language):** Speak directly to the user ("You"). Don't abstract them away ("The developer"). Focus on their goals and how this tool helps them achieve those goals.
17
+ * **Tone (Supportive and Authoritative, not Hostile or Prescriptive):** Avoid "must," "requires," "need to," or "mandatory." These words sound bossy. Treat the user as a capable peer. Instead of "You must do X," use imperative "Do X" or cause-and-effect "X ensures Y."
18
+
19
+ ## 2. Class Documentation
20
+
21
+ Every public class must begin with a **Context-Problem-Solution** narrative.
22
+
23
+ ### Structure
24
+
25
+ 1. **Summary Line:** A single line explaining the class's role.
26
+ 2. **Context (Narrative):** A short paragraph establishing the domain or situation.
27
+ 3. **Problem (Narrative):** A sentence or two identifying the specific difficulty, complexity, or "pain" the user faces in this context without the widget.
28
+ 4. **Solution (Narrative):** A sentence explaining how this widget solves that problem, often starting with "This widget..." or "Use it to...".
29
+ 5. **Usage (Narrative):** A concrete "Use it to..." sentence listing common applications.
30
+ 6. **Example:** A comprehensive, copy-pasteable code example using `=== Examples`. Provide **multiple** examples to cover different use cases (e.g., basic usage vs. advanced configuration).
31
+
32
+ ### Example
33
+
34
+ **Bad (Generic/Descriptive):**
35
+ <!-- SPDX-SnippetBegin -->
36
+ <!--
37
+ SPDX-FileCopyrightText: 2025 Kerrick Long
38
+ SPDX-License-Identifier: MIT-0
39
+ -->
40
+ ```ruby
41
+ # A widget for displaying list items.
42
+ # It allows the user to select an item from an array of strings.
43
+ # Supports scrolling and custom styling.
44
+ ```
45
+ <!-- SPDX-SnippetEnd -->
46
+
47
+ **Good (Alexandrian/Zinsser/Plain Language):**
48
+ <!-- SPDX-SnippetBegin -->
49
+ <!--
50
+ SPDX-FileCopyrightText: 2025 Kerrick Long
51
+ SPDX-License-Identifier: MIT-0
52
+ -->
53
+ ```ruby
54
+ # Displays a selectable list of items.
55
+ #
56
+ # Users need to choose from options. Menus, file explorers, and selectors are everywhere.
57
+ # Implementing navigation, highlighting, and scrolling state from scratch is tedious.
58
+ #
59
+ # This widget manages the list. It renders the items. It highlights the selection. It handles the scrolling window.
60
+ #
61
+ # Use it to build main menus, navigation sidebars, or logs.
62
+ ```
63
+ <!-- SPDX-SnippetEnd -->
64
+
65
+ ## 3. Method and Attribute Documentation
66
+
67
+ ### Prose Style
68
+
69
+ * **Attributes:** Use concise noun phrases. Avoid "This attribute returns..." or "Getter for...".
70
+ * *Bad:* "This is the width of the widget."
71
+ * *Good:* "Width of the widget in cells."
72
+ * **Methods:** Use active, third-person present tense verbs.
73
+ * *Bad:* "Will calculate the total."
74
+ * *Good:* "Calculates the total."
75
+ * **Context:** For complex methods, you may use a condensed version of the Context-Problem-Solution pattern, but keep it brief.
76
+
77
+ ### Syntax Standards
78
+
79
+ * **Examples:** All public methods must include at least one usage example. Use `=== Example`.
80
+ * **Attributes:** Use `attr_reader` with documentation comments immediately preceding them.
81
+ * **Parameters:** Use strict RDoc definition lists `[name] description` for parameters in the `initialize` method.
82
+ * **Formatting:** Use `<tt>` tags for code literals, symbols, and values (e.g., `<tt>:vertical</tt>`).
83
+ * Do **not** use backticks (\`) or markdown-style links `[text](url)`. RDoc does not render them correctly in all contexts.
84
+ * Do **not** use smart quotes.
85
+
86
+ ### Example
87
+
88
+ <!-- SPDX-SnippetBegin -->
89
+ <!--
90
+ SPDX-FileCopyrightText: 2025 Kerrick Long
91
+ SPDX-License-Identifier: MIT-0
92
+ -->
93
+ ```ruby
94
+ # The styling to apply to the content.
95
+ attr_reader :style
96
+
97
+ # Creates a new List.
98
+ #
99
+ # [items] Array of Strings.
100
+ # [selected_index] Integer (nullable).
101
+ def initialize(items: [], selected_index: nil)
102
+ super
103
+ end
104
+ ```
105
+ <!-- SPDX-SnippetEnd -->
106
+
107
+ ## 4. RDoc Specifics
108
+
109
+ * **No Endless Methods:** Do **not** use Ruby 3.0+ endless method definitions (`def foo = bar`). RDoc currently has a bug where it fails to correctly parse the end of the method, causing subsequent methods to be nested incorrectly in the documentation tree. Always use standard `def ... end` blocks.
110
+ * **No YARD:** Do not use `@param`, `@return`, or other YARD tags. Use standard RDoc formats.
111
+ * **Directives:** Use `:nodoc:` for private or internal methods that should not appear in the API docs.
112
+ * **Headings:** Use `===` for section headers like `=== Examples`.
113
+
114
+ ## 5. Checklist for Agents
115
+
116
+ Before finalizing documentation, ask:
117
+ 1. Did I explain the *problem* this code solves?
118
+ 2. Are my sentences short and active? (Did I remove "allows the user to"?)
119
+ 3. Is the code example valid and copy-pasteable?
120
+ 4. Did I use `<tt>` for symbols and code values?
121
+ 5. Did I document every attribute and parameter?
data/doc/custom.css ADDED
@@ -0,0 +1,22 @@
1
+ /*
2
+ * SPDX-FileCopyrightText: 2025 Kerrick Long <me@kerricklong.com>
3
+ * SPDX-License-Identifier: AGPL-3.0-or-later
4
+ */
5
+
6
+ img {
7
+ max-width: 100%;
8
+ height: auto;
9
+ }
10
+
11
+ .theme-toggle {
12
+ margin-left: 0 !important;
13
+ }
14
+
15
+ /* Terminal Previews (Native PNGs)
16
+ * The images already contain the window chrome and shadows.
17
+ * We just need to center them and ensure they scale down on mobile.
18
+ */
19
+ img[src*="images/"] {
20
+ display: block;
21
+ margin: 2em auto;
22
+ }
data/exe/agent_rake ADDED
@@ -0,0 +1,96 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ #--
5
+ # SPDX-FileCopyrightText: 2026 Kerrick Long <me@kerricklong.com>
6
+ # SPDX-License-Identifier: AGPL-3.0-or-later
7
+ #++
8
+
9
+ # ==============================================================================
10
+ # bin/agent_rake: The AI-Friendly Build Wrapper
11
+ # ==============================================================================
12
+ #
13
+ # WHY THIS EXISTS:
14
+ # 1. Noise Reduction for AI Agents:
15
+ # Compiling Rust extensions (Via Cargo) and installing gems produces massive
16
+ # amounts of "noisy" output (compilation steps, warnings, progress bars).
17
+ # This noise fills up an AI agent's limited context window, truncating the
18
+ # actual error message we need to fix.
19
+ #
20
+ # 2. Atomic Dump vs. Streaming:
21
+ # Humans like "Streaming" (seeing lines appear in real-time).
22
+ # Agents need an "Atomic Dump" of *only* the failure.
23
+ # If we stream, the agent's context fills with noise before the failure occurs.
24
+ # By capturing to a file, we can discard the noise and only show the failure.
25
+ #
26
+ # 3. Merging Stdout/Stderr:
27
+ # We merge stdout and stderr because:
28
+ # - Minitest prints failures to stdout, not stderr.
29
+ # - We need to preserve temporal order (e.g., a "warning" in stderr right
30
+ # before a "failure" in stdout).
31
+ #
32
+ # 4. Transparent Passthrough:
33
+ # This script wraps `bundle exec rake`. Any arguments you pass to this script
34
+ # (e.g., `bin/agent_rake test:ruby`) are passed directly to rake.
35
+ # Environment variables (e.g., `TEST=...`) are inherited naturally.
36
+ #
37
+ # ==============================================================================
38
+
39
+ require "fileutils"
40
+ require "shellwords"
41
+
42
+ # Persist the log file so it can be inspected manually if summarization fails.
43
+ # We do NOT use a Tempfile because we want the log to survive script exit.
44
+ LOG_FILE = File.expand_path(File.join(__dir__, "..", "tmp", "agent_rake.log"))
45
+ FileUtils.mkdir_p(File.dirname(LOG_FILE))
46
+
47
+ cmd = "bundle exec rake #{ARGV.shelljoin}"
48
+
49
+ # Run the command, redirecting everything to the log file.
50
+ # This silences the terminal output completely unless there's a failure.
51
+ success = system(cmd, %i[out err] => LOG_FILE)
52
+
53
+ if success
54
+ puts "PASS"
55
+ exit 0
56
+ else
57
+ puts "FAIL"
58
+ puts "Full output saved to: #{LOG_FILE}"
59
+ puts "---"
60
+ puts "Failure Summary (extracted from log):"
61
+ puts
62
+
63
+ begin
64
+ # aggressively force UTF-8 to avoid "incompatible encoding regexp match" errors
65
+ # when the log contains binary data or weird sequences from Cargo.
66
+ raw_content = File.binread(LOG_FILE)
67
+ content = raw_content.encode("UTF-8", invalid: :replace, undef: :replace, replace: "?")
68
+
69
+ # Try to extract meaningful failure information
70
+ if content.include?("Failure:") || content.include?("Error:")
71
+ # Regex explanation:
72
+ # Look for a line starting with " 1) Failure:"
73
+ # Capture everything until the next " N) Failure:" or End Of String (\Z).
74
+ # /m (multiline) mode allows . to match newlines.
75
+ failures = content.scan(/(?:^\s*\d+\) (?:Failure|Error):.*?(?=\n\s*\d+\) (?:Failure|Error):|\Z))/ms)
76
+
77
+ if failures.any?
78
+ puts failures.join("\n")
79
+ else
80
+ # Fallback: Print lines containing "Error" or "Failure" with context
81
+ puts content.lines.grep(/(Failure:|Error:|error\[)/).first(20).join
82
+ puts "... (summarization failed to find full blocks, see log for more)"
83
+ end
84
+ else
85
+ # If no standard Ruby/Minitest failure patterns found, it might be a build error.
86
+ # Dump the last 50 lines which usually contain the crash/build error.
87
+ puts "No structured failure pattern detected. Dumping last 50 lines:"
88
+ puts content.lines.last(50).join
89
+ end
90
+ rescue => e
91
+ puts "Error summarizing log file: #{e.class}: #{e.message}"
92
+ end
93
+
94
+ puts "Use `grep` or run `cat #{LOG_FILE}` to see details."
95
+ exit 1
96
+ end