Sha256: a942a9dead1242d03314b95cb39ec4f20db42196b1a5fd95b63418e3467fff70

Contents?: true

Size: 1.38 KB

Versions: 5

Compression:

Stored size: 1.38 KB

Contents

module MiniSql
  module Postgres
    class DeserializerCache

    DEFAULT_MAX_SIZE = 500

    def initialize(max_size = nil)
      @cache = {}
      @max_size = max_size || DEFAULT_MAX_SIZE
    end

    def materialize(result)

      return [] if result.ntuples == 0

      key = result.fields

      # trivial fast LRU implementation
      materializer = @cache.delete(key)
      if materializer
        @cache[key] = materializer
      else
        materializer = @cache[key] = new_row_matrializer(result)
        @cache.shift if @cache.length > @max_size
      end

      i = 0
      r = []
      # quicker loop
      while i < result.ntuples
        r << materializer.materialize(result, i)
        i += 1
      end
      r
    end

    private

    def new_row_matrializer(result)
      fields = result.fields

      Class.new do
        attr_accessor(*fields)

        # AM serializer support
        alias :read_attribute_for_serialization :send

        def to_h
          r = {}
          instance_variables.each do |f|
            r[f.to_s.sub('@','').to_sym] = instance_variable_get(f)
          end
          r
        end

        instance_eval <<~RUBY
            def materialize(pg_result, index)
              r = self.new
              #{col=-1; fields.map{|f| "r.#{f} = pg_result.getvalue(index, #{col+=1})"}.join("; ")}
              r
            end
        RUBY
      end
    end
  end
end
end

Version data entries

5 entries across 5 versions & 1 rubygems

Version Path
mini_sql-0.2.4 lib/mini_sql/postgres_jdbc/deserializer_cache.rb
mini_sql-0.2.2-java lib/mini_sql/postgres_jdbc/deserializer_cache.rb
mini_sql-0.2.3-java lib/mini_sql/postgres_jdbc/deserializer_cache.rb
mini_sql-0.2.3 lib/mini_sql/postgres_jdbc/deserializer_cache.rb
mini_sql-0.2.2 lib/mini_sql/postgres_jdbc/deserializer_cache.rb