<commit_before># frozen_string_literal: true

require 'active_support/core_ext/array/wrap'
require 'active_support/core_ext/object/try'

module Structure
  class Path
    attr_reader :path

    def initialize(path)
      # `path` can be an Array (e.g. [:parent, :child, :grandchild])
      # or a String (e.g. 'parent.child.grandchild')
      @path = path.is_a?(String) ? path.split('.') : Array.wrap(path).map(&:to_s)
    end

    def attribute
      attribute = @path.last
      return attribute.sub(operator_regex, '') if attribute.match operator_regex
      attribute
    end

    def operator
      attribute = @path.last
      return attribute[operator_regex, 1] if attribute.match operator_regex
      '=='
    end

    def to_a
      @path.slice(0, @path.length - 1)
    end

    def to_h
      to_a.reverse.reduce({}) { |a, e| { e => a } }
    end

    def value_for(item:)
      @path.reduce(item, :try)
    rescue
      nil
    end

    def resource_for(item:)
      to_a.reduce(item, :try)
    rescue
      nil
    end

    private

    def operator_regex
      %r{\((.*?)\)}
    end
  end
end<commit_msg>Fix a bug in getting at the value for a Structure::Path<commit_after># frozen_string_literal: true

require 'active_support/core_ext/array/wrap'
require 'active_support/core_ext/object/try'

module Structure
  class Path
    attr_reader :path

    def initialize(path)
      # `path` can be an Array (e.g. [:parent, :child, :grandchild])
      # or a String (e.g. 'parent.child.grandchild')
      @path = path.is_a?(String) ? path.split('.') : Array.wrap(path).map(&:to_s)
    end

    def attribute
      attribute = @path.last
      return attribute.sub(operator_regex, '') if attribute.match operator_regex
      attribute
    end

    def operator
      attribute = @path.last
      return attribute[operator_regex, 1] if attribute.match operator_regex
      '=='
    end

    def to_a
      @path.slice(0, @path.length - 1)
    end

    def to_h
      to_a.reverse.reduce({}) { |a, e| { e => a } }
    end

    def value_for(item:)
      resource_for(item: item).send(attribute)
    rescue
      nil
    end

    def resource_for(item:)
      to_a.reduce(item, :try)
    rescue
      nil
    end

    private

    def operator_regex
      %r{\((.*?)\)}
    end
  end
end
{'fraction_non_alphanumeric': 0.11954624781849912, 'fraction_numerical': 0.002617801047120419, 'mean_word_length': 2.4377811094452775, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '1762690', 'n_tokens_mistral': 784, 'n_tokens_neox': 760, 'n_words': 191}