Skip to content

Instantly share code, notes, and snippets.

View baweaver's full-sized avatar
Documenting things

Brandon Weaver baweaver

Documenting things
View GitHub Profile
class ShorthandProcCallMacro < Refactor::Rule
matches do |node|
node in [:block, receiver,
[[:arg, arg_name]], [:send, [:lvar, ^arg_name], method_name]
replace do |_node, match_data|
baweaver / ruby_ast_translate.rb
Created February 28, 2024 09:10
Ruby AST translator hack - Needs a lot of work later, but hey, proof of concept
require 'rubocop'
# Target - What I want to get to
# class ShorthandProcCallMacro2 < Rule
# matches "$receiver.$method_call { |$arg| $arg.$arg_name }"
# replaces "$receiver.$method_call(&:$arg_name)"
# end
class Literal
def initialize(s)

Refactoring with ASTs and Pattern Matching

Pattern matching in Ruby is not a well understood or frequently used feature, but when paired with ASTs it becomes an incredibly powerful tool for refactoring and code transformations.


This talk is a deep dive into ASTs and RuboCop as refactoring and upgrade tools. With the advent of language servers this will become a very critical topic to have knowledge in to effectively work with manipulating Ruby code programatically.

Intended Audience

baweaver / row_me_lemur_friends.txt
Created November 21, 2023 08:47
Row Me Lemur Friends - Variant of "Row Me Bully Boys"
Based on:
I'll code you some Ruby, it's Ruby with C
Code me Lemur friends code
Oh I'll FFIddle some C if you'll debug it with me
And it's code me Lemur friends code
And it's code me Lemur friends
We're in a hurry then
We got a long sprint to go


  • Introductions - Coaches (5m)
    • Share names and pronouns
    • Brief history on what they do and how they work with Ruby
    • A tip or two on writing an awesome CFP
  • Introductions - Prospective Speakers (15m)
    • Share names and pronouns
    • Brief history on what they do and how they work with Ruby
  • Where are they in the process of writing their CFP (ideation, first draft, proofreading)
class Cond
IDENTITY = -> v { v }
def initialize(if_cond: IDENTITY, then_branch: IDENTITY, else_branch: IDENTITY)
@if_cond = if_cond
@then_branch = then_branch
@else_branch = else_branch
def call(v)
def reasonable_typos(distance: 3)
typo_map = do |h, initial_key|
h[initial_key] = {}
module AccessedAttributes
def self.included(klass)
association_proxy = do
def accessed_associations
@_accessed_associations ||= []
klass.reflect_on_all_associations.each do |association|
name =
baweaver / range_string_include_triple_equals_bug.rb
Created October 24, 2022 04:52
Why does `include?` behave differently than `===` here?
range = '0'..'255'
('1'..'5').map do |v|
v: v,
teq: range === v,
include?: range.include?(v)
# => [
IDENTITY = -> v { v }
def proc_line(**fns)
fns.reduce(IDENTITY) { |fn, (m, args)|
fn >> m.to_proc.then { |m_proc| -> v {, *args) } }
[50, 100, 300, 5000].map(&proc_line(
to_s: 2, chars: nil, reverse: nil, join: nil, to_i: 2