Making a tree with hash input
Some notes:


The initialize method of a class should be its most basic and fundamental constructor, don't use it as a "helper". A tree has a name and some children, so these should be the arguments. You want to construct a Tree from a hash to make things easier for the caller? then create a helper classmethod, for example Tree::new_from_hash(hash).
Tree#visit. That's an imperative construct, I'd write first the functional ones (which can also be used imperatively if needed).
node.node_name: That repetition is a cue that node_name is redundant, name is enough.
(Subjective) I prefer to write hash literals without losing indentation space.


I'd write (I'd inherit from Struct to save some lines, not really needed):

class Tree &lt; Struct.new(:name, :children)
  def self.new_from_hash(hash)
    name, children_hash = hash.first
    children = children_hash.map { |k, v| Tree.new_from_hash({k =&gt; v}) }
    Tree.new(name, children)
  end

  def visit_all(&amp;block)
    yield(self)
    children.each { |c| c.visit_all(&amp;block) }
  end
end

family_tree = Tree.new_from_hash({
  'grandpa' =&gt; {
    'dad' =&gt;   {'child 1' =&gt; {}, 'child 2' =&gt; {}},
    'uncle' =&gt; {'child 3' =&gt; {}, 'child 4' =&gt; {}},
  },
})

family_tree.visit_all { |node| puts node.name }


Additional notes:


Include module Enumerable and implement Tree#each so you can use all enumerable methods for you trees. Note that enumerable methods assume a single-level iteration, so you'd still need custom methods (like visit_all/map_all) that perform nested operations.
If that's a learning code I'd explore this path: create a NestedEnumerable module -very similar to Enumerable- which would provide some xyz_all (or xyz_nested, whatever) methods. Like Enumerable, you would only be required to implement the "each" method (i.e. each_all).