<commit_before>module RDF::Raptor::FFI::V2
  ##
  # This class provides the functionality of turning RDF triples into
  # syntaxes - RDF serializing.
  #
  # @see http://librdf.org/raptor/api-1.4/raptor-section-serializer.html
  class Serializer < ::FFI::ManagedStruct
    include RDF::Raptor::FFI
    layout :world, :pointer # the actual layout is private

    ##
    # @overload initialize(ptr)
    #   @param  [FFI::Pointer] ptr
    #
    # @overload initialize(name)
    #   @param  [Symbol, String] name
    #
    def initialize(ptr_or_name)
      ptr = case ptr_or_name
        when FFI::Pointer then ptr_or_name
        when Symbol       then V2.raptor_new_serializer(V2.world, ptr_or_name.to_s)
        when String       then V2.raptor_new_serializer(V2.world, ptr_or_name)
        else nil
      end
      raise ArgumentError, "invalid argument: #{ptr_or_name.inspect}" if ptr.nil? || ptr.null?
      super(ptr)
    end

    ##
    # Releases `libraptor` memory associated with this structure.
    #
    # @param  [FFI::Pointer] ptr
    # @return [void]
    def self.release(ptr)
      V2.raptor_free_serializer(ptr)
    end

    ##
    # @param  [Proc] handler
    # @return [void]
    def error_handler=(handler)
      V2.raptor_serializer_set_error_handler(self, self, handler)
    end

    ##
    # @param  [Proc] handler
    # @return [void]
    def warning_handler=(handler)
      V2.raptor_serializer_set_warning_handler(self, self, handler)
    end

    ##
    # @param  [Object] output
    #   where output should be written to
    # @param  [Hash{Symbol => Object}] options
    #   any additional options for serializing
    # @option options [String, #to_s] :base_uri (nil)
    #   the base URI to use when resolving relative URIs
    # @return [void]
    def start_to(output, options = {})
      if output.respond_to?(:write)
        start_to_stream(output, options)
       else
        raise ArgumentError, "don't know how to serialize to #{output.inspect}"
      end
    end

    ##
    # @param  [IO, StringIO] stream
    # @param  [Hash{Symbol => Object}] options
    #   any additional options for serializing (see {#start_to})
    # @return [void]
    def start_to_stream(stream, options = {})
      iostream = V2::IOStream.new(V2::IOStreamHandler.new(stream), :free_iostream => false)
      start_to_iostream(iostream, options)
    end<commit_msg>Possible fix for serializer iostream memory leak<commit_after>module RDF::Raptor::FFI::V2
  ##
  # This class provides the functionality of turning RDF triples into
  # syntaxes - RDF serializing.
  #
  # @see http://librdf.org/raptor/api-1.4/raptor-section-serializer.html
  class Serializer < ::FFI::ManagedStruct
    include RDF::Raptor::FFI

    # Note this layout is private
    layout  :world, :pointer,
            :locator, :pointer,
            :failed, :bool,
            :base_uri, :pointer,
            :context, :pointer,
            :iostream, :pointer,
            :free_iostream_on_end, :bool,
            :factory, :pointer,
            :options, :pointer

    ##
    # @overload initialize(ptr)
    #   @param  [FFI::Pointer] ptr
    #
    # @overload initialize(name)
    #   @param  [Symbol, String] name
    #
    def initialize(ptr_or_name)
      ptr = case ptr_or_name
        when FFI::Pointer then ptr_or_name
        when Symbol       then V2.raptor_new_serializer(V2.world, ptr_or_name.to_s)
        when String       then V2.raptor_new_serializer(V2.world, ptr_or_name)
        else nil
      end
      raise ArgumentError, "invalid argument: #{ptr_or_name.inspect}" if ptr.nil? || ptr.null?
      super(ptr)
    end

    ##
    # Releases `libraptor` memory associated with this structure.
    #
    # @param  [FFI::Pointer] ptr
    # @return [void]
    def self.release(ptr)
      V2.raptor_free_serializer(ptr)
    end

    ##
    # @param  [Proc] handler
    # @return [void]
    def error_handler=(handler)
      V2.raptor_serializer_set_error_handler(self, self, handler)
    end

    ##
    # @param  [Proc] handler
    # @return [void]
    def warning_handler=(handler)
      V2.raptor_serializer_set_warning_handler(self, self, handler)
    end

    ##
    # @param  [Object] output
    #   where output should be written to
    # @param  [Hash{Symbol => Object}] options
    #   any additional options for serializing
    # @option options [String, #to_s] :base_uri (nil)
    #   the base URI to use when resolving relative URIs
    # @return [void]
    def start_to(output, options = {})
      if output.respond_to?(:write)
        start_to_stream(output, options)
       else
        raise ArgumentError, "don't know how to serialize to #{output.inspect}"
      end
    end

    ##
    # @param  [IO, StringIO] stream
    # @param  [Hash{Symbol => Object}] options
    #   any additional options for serializing (see {#start_to})
    # @return [void]
    def start_to_stream(stream, options = {})
      iostream = V2::IOStream.new(V2::IOStreamHandler.new(stream), :free_iostream => self[:free_iostream_on_end])
      start_to_iostream(iostream, options)
    end
{'fraction_non_alphanumeric': 0.10855003940110323, 'fraction_numerical': 0.004728132387706856, 'mean_word_length': 2.70854638422206, 'pattern_counts': {'":': 0, '<': 5, '<?xml version=': 0, '>': 9, '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': '6797057', 'n_tokens_mistral': 1669, 'n_tokens_neox': 1664, 'n_words': 405}