Skip to content

Instantly share code, notes, and snippets.

View havenwood's full-sized avatar
:octocat:

Shannon Skipper havenwood

:octocat:
  • Ashland, Oregon
  • 13:11 - 7h behind
View GitHub Profile
@havenwood
havenwood / waffle.rb
Created November 8, 2024 16:01
An example of implementing #to_json for Ruby IRC
require 'json'
class Waffle
def initialize(toppings:, syrup:)
@toppings = toppings
@syrup = syrup
end
class << self
def json_create(object)
@havenwood
havenwood / enumerator.rb
Created September 28, 2024 09:54
Enumerator#feed examples
class Integer
def stream(by: 1)
Enumerator.new Float::INFINITY do |yielder|
int = self
loop do
fed = yielder.yield(int)
int += fed if fed
int += by
end
@havenwood
havenwood / immutable.rb
Created July 1, 2024 18:46
An example immutable (Dry) and mutable (Active Model) Args interface
require 'dry-struct'
require 'dry-types'
require 'dry-validation'
class WordTally
class Args < Dry::Struct
module Types
include Dry.Types()
end
@havenwood
havenwood / caesar.rb
Last active June 23, 2024 23:21
A Caesar cipher example in Ruby
class Caesar
def initialize(rot: 13, lower: [*'a'..'z'], upper: [*'A'..'Z'])
@rot = rot
@book = book(lower:, upper:)
end
def cipher(message) = message.gsub(/[a-zA-Z]/, @book)
alias_method :call, :cipher
private
@havenwood
havenwood / which.rb
Last active October 24, 2024 19:12
A `which` command for Ruby
# frozen_string_literal: true
require 'fileutils'
module FileUtils
# Returns the full path to an executable command if it exists in the PATH.
#
# FileUtils.which('ruby') # => "/usr/bin/ruby"
# FileUtils.which('matz') # => nil
#
@havenwood
havenwood / uuid_v7.rb
Last active June 17, 2024 21:33
UUIDv7 in Ruby, using IO::Buffer
def uuid_v7
milliseconds = Process.clock_gettime(Process::CLOCK_REALTIME, :millisecond)
buffer = IO::Buffer.new(16)
buffer.set_string([milliseconds].pack('Q>')[2..], 0)
buffer.set_string(SecureRandom.bytes(10), 6)
buffer.set_value(:U8, 6, buffer.get_value(:U8, 6) & 0x0F | 0x70)
buffer.set_value(:U8, 8, buffer.get_value(:U8, 8) & 0x3F | 0x80)
buffer.get_string.unpack('H8H4H4H4H12').join('-')
end
@havenwood
havenwood / nano_id.rb
Created June 16, 2024 22:54
A simple Nano ID implementation in Ruby
# frozen_string_literal: true
require 'securerandom'
module NanoID
ALPHABET = [*'A'..'Z', *'a'..'z', *'0'..'9', '_', '-'].freeze
module_function
def nano_id(alphabet: ALPHABET, size: 21)
@havenwood
havenwood / coerce.rb
Created May 31, 2024 21:56
An example showing that #coerce can be private.
Value = Data.define(:number) do
def +(other) = with(number: number + other.number)
private
def coerce(number) = [Value.new(number), self]
end
42 + Value.new(42)
#=> #<data Value number=84>
@havenwood
havenwood / build.rb
Created May 29, 2024 19:29 — forked from jedschneider/build.rb
build script for terraform deploys
#!/usr/bin/env ruby
# frozen_string_literal: true
require 'optparse'
require 'fileutils'
require 'open3'
module TerraformExecutor
Config = Struct.new(:parallelism, :init, :vault, :tag, keyword_init: true)
@havenwood
havenwood / delete_archdir_prefix.patch
Last active April 24, 2024 22:20
Minimalist patch for Ruby 3.3.1 [Bug #20450] https://github.com/ruby/ruby/pull/10619
diff --git a/lib/bundled_gems.rb b/lib/bundled_gems.rb
index e756af61ea..555d1d4cd1 100644
--- a/lib/bundled_gems.rb
+++ b/lib/bundled_gems.rb
@@ -98,7 +98,7 @@ def self.warning?(name, specs: nil)
# name can be a feature name or a file path with String or Pathname
feature = File.path(name)
# bootsnap expand `require "csv"` to `require "#{LIBDIR}/csv.rb"`
- name = feature.delete_prefix(LIBDIR).chomp(".rb").tr("/", "-")
+ name = feature.delete_prefix(ARCHDIR).delete_prefix(LIBDIR).tr("/", "-")