Deeply Remove All Nils And Empty Values From A Nested Hash In Ruby
When handling deeply nested hashes or API payloads in Rails, it’s common to deal with nil values, empty arrays, or hashes that need to be cleaned before storage or transmission.
Description
This method is designed to walk through both hashes and arrays and eliminate any nil, empty string, or empty structure it finds.This method recursively compacts the object, cleaning up any meaningless structure. It supports deeply nested objects - unlike Hash#compact, which is shallow.
This is mainly ideal for preparing outgoing JSON API payloads, cleaning up params, or filtering configuration data.
 Sample input:
  {
    name: "Alice",
    details: {
      address: nil,
      social: {
        twitter: "",
        github: "alicehub"
      },
      preferences: {}
    },
    tags: [nil, "", "ruby"]
  }
 Sample Output:
  {
    name: "Alice",
    details: {
      social: {
        github: "alicehub"
      }
    },
    tags: ["ruby"]
  }
Answer
  def deep_compact(obj)
    case obj
    when Hash
      obj.each_with_object({}) do |(k, v), result|
        compacted = deep_compact(v)
        result[k] = compacted unless compacted.nil? || compacted.respond_to?(:empty?) && compacted.empty?
      end
    when Array
      obj.map { |v| deep_compact(v) }.compact.reject { |v| v.respond_to?(:empty?) && v.empty? }
    else
      obj
    end
  end
Check viewARU - Brand Newsletter!
Newsletter to DEVs by DEVs - boost your Personal Brand & career! 🚀