andrew-kane-gem-writer
Andrew Kane氏の確立されたパターンと哲学に基づき、新規または既存のRuby gemの設計・開発・リファクタリングを行うSkill。
📜 元の英語説明(参考)
This skill should be used when writing Ruby gems following Andrew Kane's proven patterns and philosophy. It applies when creating new Ruby gems, refactoring existing gems, designing gem APIs, or when clean, minimal, production-ready Ruby library code is needed. Triggers on requests like "create a gem", "write a Ruby library", "design a gem API", or mentions of Andrew Kane's style.
🇯🇵 日本人クリエイター向け解説
Andrew Kane氏の確立されたパターンと哲学に基づき、新規または既存のRuby gemの設計・開発・リファクタリングを行うSkill。
※ jpskill.com 編集部が日本のビジネス現場向けに補足した解説です。Skill本体の挙動とは独立した参考情報です。
⚠️ ダウンロード・利用は自己責任でお願いします。当サイトは内容・動作・安全性について責任を負いません。
🎯 このSkillでできること
下記の説明文を読むと、このSkillがあなたに何をしてくれるかが分かります。Claudeにこの分野の依頼をすると、自動で発動します。
📦 インストール方法 (3ステップ)
- 1. 上の「ダウンロード」ボタンを押して .skill ファイルを取得
- 2. ファイル名の拡張子を .skill から .zip に変えて展開(macは自動展開可)
- 3. 展開してできたフォルダを、ホームフォルダの
.claude/skills/に置く- · macOS / Linux:
~/.claude/skills/ - · Windows:
%USERPROFILE%\.claude\skills\
- · macOS / Linux:
Claude Code を再起動すれば完了。「このSkillを使って…」と話しかけなくても、関連する依頼で自動的に呼び出されます。
詳しい使い方ガイドを見る →- 最終更新
- 2026-05-17
- 取得日時
- 2026-05-17
- 同梱ファイル
- 1
📖 Skill本文(日本語訳)
※ 原文(英語/中国語)を Gemini で日本語化したものです。Claude 自身は原文を読みます。誤訳がある場合は原文をご確認ください。
[スキル名] andrew-kane-gem-writer
Andrew Kane Gem Writer
Andrew Kane氏が100以上のgem(Searchkick、PgHero、Chartkick、Strong Migrations、Lockbox、Ahoy、Blazer、Groupdate、Neighbor、Blind Index)で培った、3億7400万回以上のダウンロード実績を持つ実証済みのパターンに従ってRuby gemを作成します。
核となる哲学
巧妙さよりもシンプルさ。 依存関係はゼロまたは最小限に抑えます。メタプログラミングよりも明示的なコードを優先します。Railsとの結合を避けつつRailsとの統合を実現します。すべてのパターンは本番環境でのユースケースに対応します。
エントリーポイントの構造
すべてのgemは lib/gemname.rb でこの正確なパターンに従います。
# 1. Dependencies (stdlib preferred)
require "forwardable"
# 2. Internal modules
require_relative "gemname/model"
require_relative "gemname/version"
# 3. Conditional Rails (CRITICAL - never require Rails directly)
require_relative "gemname/railtie" if defined?(Rails)
# 4. Module with config and errors
module GemName
class Error < StandardError; end
class InvalidConfigError < Error; end
class << self
attr_accessor :timeout, :logger
attr_writer :client
end
self.timeout = 10 # Defaults set immediately
end
クラスマクロDSLパターン
Kane氏の代表的なパターン — 単一のメソッド呼び出しですべてを設定します。
# Usage
class Product < ApplicationRecord
searchkick word_start: [:name]
end
# Implementation
module GemName
module Model
def gemname(**options)
unknown = options.keys - KNOWN_KEYWORDS
raise ArgumentError, "unknown keywords: #{unknown.join(", ")}" if unknown.any?
mod = Module.new
mod.module_eval do
define_method :some_method do
# implementation
end unless method_defined?(:some_method)
end
include mod
class_eval do
cattr_reader :gemname_options, instance_reader: false
class_variable_set :@@gemname_options, options.dup
end
end
end
end
Rails統合
常に ActiveSupport.on_load を使用し、Rails gemを直接requireしないでください。
# WRONG
require "active_record"
ActiveRecord::Base.include(MyGem::Model)
# CORRECT
ActiveSupport.on_load(:active_record) do
extend GemName::Model
end
# Use prepend for behavior modification
ActiveSupport.on_load(:active_record) do
ActiveRecord::Migration.prepend(GemName::Migration)
end
設定パターン
Configurationオブジェクトではなく、class << self と attr_accessor を使用します。
module GemName
class << self
attr_accessor :timeout, :logger
attr_writer :master_key
end
def self.master_key
@master_key ||= ENV["GEMNAME_MASTER_KEY"]
end
self.timeout = 10
self.logger = nil
end
エラー処理
情報量の多いメッセージを持つシンプルな階層構造です。
module GemName
class Error < StandardError; end
class ConfigError < Error; end
class ValidationError < Error; end
end
# Validate early with ArgumentError
def initialize(key:)
raise ArgumentError, "Key must be 32 bytes" unless key&.bytesize == 32
end
テスト (Minitestのみ)
# test/test_helper.rb
require "bundler/setup"
Bundler.require(:default)
require "minitest/autorun"
require "minitest/pride"
# test/model_test.rb
class ModelTest < Minitest::Test
def test_basic_functionality
assert_equal expected, actual
end
end
Gemspecパターン
可能な限りランタイム依存関係をゼロにします。
Gem::Specification.new do |spec|
spec.name = "gemname"
spec.version = GemName::VERSION
spec.required_ruby_version = ">= 3.1"
spec.files = Dir["*.{md,txt}", "{lib}/**/*"]
spec.require_path = "lib"
# NO add_dependency lines - dev deps go in Gemfile
end
避けるべきアンチパターン
method_missing(define_methodを代わりに使用)- Configurationオブジェクト (クラスアクセサを使用)
@@class_variables(class << selfを使用)- Rails gemを直接requireすること
- 多くのランタイム依存関係
- gemにGemfile.lockをコミットすること
- RSpec (Minitestを使用)
- 重いDSL (明示的なRubyを好む)
参照ファイル
より深いパターンについては、以下を参照してください。
- references/module-organization.md - ディレクトリレイアウト、メソッド分解
- references/rails-integration.md - Railtie、Engine、on_loadパターン
- references/database-adapters.md - マルチデータベースサポートパターン
- references/testing-patterns.md - マルチバージョンテスト、CIセットアップ
- references/resources.md - Kane氏のリポジトリと記事へのリンク
📜 原文 SKILL.md(Claudeが読む英語/中国語)を展開
Andrew Kane Gem Writer
Write Ruby gems following Andrew Kane's battle-tested patterns from 100+ gems with 374M+ downloads (Searchkick, PgHero, Chartkick, Strong Migrations, Lockbox, Ahoy, Blazer, Groupdate, Neighbor, Blind Index).
Core Philosophy
Simplicity over cleverness. Zero or minimal dependencies. Explicit code over metaprogramming. Rails integration without Rails coupling. Every pattern serves production use cases.
Entry Point Structure
Every gem follows this exact pattern in lib/gemname.rb:
# 1. Dependencies (stdlib preferred)
require "forwardable"
# 2. Internal modules
require_relative "gemname/model"
require_relative "gemname/version"
# 3. Conditional Rails (CRITICAL - never require Rails directly)
require_relative "gemname/railtie" if defined?(Rails)
# 4. Module with config and errors
module GemName
class Error < StandardError; end
class InvalidConfigError < Error; end
class << self
attr_accessor :timeout, :logger
attr_writer :client
end
self.timeout = 10 # Defaults set immediately
end
Class Macro DSL Pattern
The signature Kane pattern—single method call configures everything:
# Usage
class Product < ApplicationRecord
searchkick word_start: [:name]
end
# Implementation
module GemName
module Model
def gemname(**options)
unknown = options.keys - KNOWN_KEYWORDS
raise ArgumentError, "unknown keywords: #{unknown.join(", ")}" if unknown.any?
mod = Module.new
mod.module_eval do
define_method :some_method do
# implementation
end unless method_defined?(:some_method)
end
include mod
class_eval do
cattr_reader :gemname_options, instance_reader: false
class_variable_set :@@gemname_options, options.dup
end
end
end
end
Rails Integration
Always use ActiveSupport.on_load—never require Rails gems directly:
# WRONG
require "active_record"
ActiveRecord::Base.include(MyGem::Model)
# CORRECT
ActiveSupport.on_load(:active_record) do
extend GemName::Model
end
# Use prepend for behavior modification
ActiveSupport.on_load(:active_record) do
ActiveRecord::Migration.prepend(GemName::Migration)
end
Configuration Pattern
Use class << self with attr_accessor, not Configuration objects:
module GemName
class << self
attr_accessor :timeout, :logger
attr_writer :master_key
end
def self.master_key
@master_key ||= ENV["GEMNAME_MASTER_KEY"]
end
self.timeout = 10
self.logger = nil
end
Error Handling
Simple hierarchy with informative messages:
module GemName
class Error < StandardError; end
class ConfigError < Error; end
class ValidationError < Error; end
end
# Validate early with ArgumentError
def initialize(key:)
raise ArgumentError, "Key must be 32 bytes" unless key&.bytesize == 32
end
Testing (Minitest Only)
# test/test_helper.rb
require "bundler/setup"
Bundler.require(:default)
require "minitest/autorun"
require "minitest/pride"
# test/model_test.rb
class ModelTest < Minitest::Test
def test_basic_functionality
assert_equal expected, actual
end
end
Gemspec Pattern
Zero runtime dependencies when possible:
Gem::Specification.new do |spec|
spec.name = "gemname"
spec.version = GemName::VERSION
spec.required_ruby_version = ">= 3.1"
spec.files = Dir["*.{md,txt}", "{lib}/**/*"]
spec.require_path = "lib"
# NO add_dependency lines - dev deps go in Gemfile
end
Anti-Patterns to Avoid
method_missing(usedefine_methodinstead)- Configuration objects (use class accessors)
@@class_variables(useclass << self)- Requiring Rails gems directly
- Many runtime dependencies
- Committing Gemfile.lock in gems
- RSpec (use Minitest)
- Heavy DSLs (prefer explicit Ruby)
Reference Files
For deeper patterns, see:
- references/module-organization.md - Directory layouts, method decomposition
- references/rails-integration.md - Railtie, Engine, on_load patterns
- references/database-adapters.md - Multi-database support patterns
- references/testing-patterns.md - Multi-version testing, CI setup
- references/resources.md - Links to Kane's repos and articles