combine_pdf 1.0.25 → 1.0.27
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/main.yml +6 -2
- data/CHANGELOG.md +5 -1
- data/README.md +10 -10
- data/lib/combine_pdf/api.rb +1 -0
- data/lib/combine_pdf/basic_writer.rb +1 -0
- data/lib/combine_pdf/decrypt.rb +2 -1
- data/lib/combine_pdf/exceptions.rb +2 -0
- data/lib/combine_pdf/filter.rb +1 -0
- data/lib/combine_pdf/fonts.rb +1 -0
- data/lib/combine_pdf/page_methods.rb +5 -4
- data/lib/combine_pdf/parser.rb +9 -9
- data/lib/combine_pdf/pdf_protected.rb +21 -19
- data/lib/combine_pdf/pdf_public.rb +5 -4
- data/lib/combine_pdf/renderer.rb +3 -2
- data/lib/combine_pdf/version.rb +3 -1
- data/lib/combine_pdf.rb +1 -0
- data/test/combine_pdf/renderer_test.rb +1 -1
- metadata +2 -2
    
        checksums.yaml
    CHANGED
    
    | @@ -1,7 +1,7 @@ | |
| 1 1 | 
             
            ---
         | 
| 2 2 | 
             
            SHA256:
         | 
| 3 | 
            -
              metadata.gz:  | 
| 4 | 
            -
              data.tar.gz:  | 
| 3 | 
            +
              metadata.gz: 2ccb4f95b5400a214f06d343f8b0a5b1a7a38b94ce400f2bbe80cefccd902005
         | 
| 4 | 
            +
              data.tar.gz: a923391ccc4a37ccf77b89a5113e723d1065e09f0404f0e9c5104034d679363e
         | 
| 5 5 | 
             
            SHA512:
         | 
| 6 | 
            -
              metadata.gz:  | 
| 7 | 
            -
              data.tar.gz:  | 
| 6 | 
            +
              metadata.gz: cc63f8c2c83a90a23579a517314248924207b578fc713c520c0ac4596c214cc2c7df50a173638e0659f58e62ae19ae0958b72eb29b6ed29f27d6ea65b9cdf88f
         | 
| 7 | 
            +
              data.tar.gz: 840b62aa7abda71f22c4b83b697046a666043b73d063f5f60046cb76ed9d6f97086d4e7dc9645ece7ef97184d6e38523d90376ba9d55f9138e0b68519ce8b55e
         | 
    
        data/.github/workflows/main.yml
    CHANGED
    
    | @@ -9,7 +9,11 @@ jobs: | |
| 9 9 | 
             
                strategy:
         | 
| 10 10 | 
             
                  fail-fast: false
         | 
| 11 11 | 
             
                  matrix:
         | 
| 12 | 
            -
                    ruby: ["2.7", "3.0", "3.1", "3.2"]
         | 
| 12 | 
            +
                    ruby: ["2.7", "3.0", "3.1", "3.2", "3.3"]
         | 
| 13 | 
            +
                    rubyopt: [""]
         | 
| 14 | 
            +
                    include:
         | 
| 15 | 
            +
                      - ruby: "3.3"
         | 
| 16 | 
            +
                        rubyopt: "--enable-frozen-string-literal --debug-frozen-string-literal"
         | 
| 13 17 |  | 
| 14 18 | 
             
                steps:
         | 
| 15 19 | 
             
                  - name: Checkout code
         | 
| @@ -25,4 +29,4 @@ jobs: | |
| 25 29 | 
             
                    run: bundle lock
         | 
| 26 30 |  | 
| 27 31 | 
             
                  - name: Run tests
         | 
| 28 | 
            -
                    run: bundle exec rake test
         | 
| 32 | 
            +
                    run: bundle exec rake test RUBYOPT="${{ matrix.rubyopt }}"
         | 
    
        data/CHANGELOG.md
    CHANGED
    
    | @@ -1,8 +1,12 @@ | |
| 1 1 | 
             
            # Change Log
         | 
| 2 2 |  | 
| 3 | 
            +
            #### Change log v.1.0.26 (2023-12-22)
         | 
| 4 | 
            +
             | 
| 5 | 
            +
            **Performance**: possible performance bump. Credit to @denislavski (Denislav Naydenov) for opening PR #235.
         | 
| 6 | 
            +
             | 
| 3 7 | 
             
            #### Change log v.1.0.25 (2023-12-19)
         | 
| 4 8 |  | 
| 5 | 
            -
            **Fix**: possible improve memory usage. Credit to @denislavski (Denislav Naydenov) for opening PR # | 
| 9 | 
            +
            **Fix**: possible improve memory usage. Credit to @denislavski (Denislav Naydenov) for opening PR #233 and suggesting this change.
         | 
| 6 10 |  | 
| 7 11 | 
             
            #### Change log v.1.0.24 (2023-10-19)
         | 
| 8 12 |  | 
    
        data/README.md
    CHANGED
    
    | @@ -7,23 +7,23 @@ | |
| 7 7 |  | 
| 8 8 | 
             
            CombinePDF is a nifty model, written in pure Ruby, to parse PDF files and combine (merge) them with other PDF files, watermark them or stamp them (all using the PDF file format and pure Ruby code).
         | 
| 9 9 |  | 
| 10 | 
            -
            ##  | 
| 10 | 
            +
            ## Unmaintained - Help Wanted(!)
         | 
| 11 11 |  | 
| 12 | 
            -
             | 
| 12 | 
            +
            I decided to stop maintaining this gem and hope someone could take over the PR reviews and maintenance of this gem (or simply open a successful fork).
         | 
| 13 13 |  | 
| 14 | 
            -
             | 
| 15 | 
            -
            gem install combine_pdf
         | 
| 16 | 
            -
            ```
         | 
| 14 | 
            +
            I wrote this gem because I needed to solve an issue with bates-numbering existing PDF documents.
         | 
| 17 15 |  | 
| 18 | 
            -
             | 
| 16 | 
            +
            However, since 2014 I have been maintaining the gem for free and for no reason at all, except that I enjoyed sharing it with the community.
         | 
| 19 17 |  | 
| 20 | 
            -
            I  | 
| 18 | 
            +
            I love this gem, but I cannot keep maintaining it as I have my own projects to focus own and I need both the time and (more importantly) the mindspace.
         | 
| 21 19 |  | 
| 22 | 
            -
             | 
| 20 | 
            +
            ## Install
         | 
| 23 21 |  | 
| 24 | 
            -
             | 
| 22 | 
            +
            Install with ruby gems:
         | 
| 25 23 |  | 
| 26 | 
            -
             | 
| 24 | 
            +
            ```ruby
         | 
| 25 | 
            +
            gem install combine_pdf
         | 
| 26 | 
            +
            ```
         | 
| 27 27 |  | 
| 28 28 | 
             
            ## Known Limitations
         | 
| 29 29 |  | 
    
        data/lib/combine_pdf/api.rb
    CHANGED
    
    
    
        data/lib/combine_pdf/decrypt.rb
    CHANGED
    
    | @@ -1,4 +1,5 @@ | |
| 1 1 | 
             
            # -*- encoding : utf-8 -*-
         | 
| 2 | 
            +
            # frozen_string_literal: true
         | 
| 2 3 | 
             
            ########################################################
         | 
| 3 4 | 
             
            ## Thoughts from reading the ISO 32000-1:2008
         | 
| 4 5 | 
             
            ## this file is part of the CombinePDF library and the code
         | 
| @@ -137,7 +138,7 @@ module CombinePDF | |
| 137 138 | 
             
                  object_key = @key.dup
         | 
| 138 139 | 
             
                  object_key << [encrypted_id].pack('i')[0..2]
         | 
| 139 140 | 
             
                  object_key << [encrypted_generation].pack('i')[0..1]
         | 
| 140 | 
            -
                  object_key << 'sAlT'. | 
| 141 | 
            +
                  object_key << 'sAlT'.b
         | 
| 141 142 | 
             
                  key_length = object_key.length < 16 ? object_key.length : 16
         | 
| 142 143 |  | 
| 143 144 | 
             
                  begin
         | 
    
        data/lib/combine_pdf/filter.rb
    CHANGED
    
    
    
        data/lib/combine_pdf/fonts.rb
    CHANGED
    
    
| @@ -1,4 +1,5 @@ | |
| 1 1 | 
             
            # -*- encoding : utf-8 -*-
         | 
| 2 | 
            +
            # frozen_string_literal: true
         | 
| 2 3 | 
             
            ########################################################
         | 
| 3 4 | 
             
            ## Thoughts from reading the ISO 32000-1:2008
         | 
| 4 5 | 
             
            ## this file is part of the CombinePDF library and the code
         | 
| @@ -214,7 +215,7 @@ module CombinePDF | |
| 214 215 | 
             
                  options[:text_padding] = 0 if options[:text_padding].to_f >= 1
         | 
| 215 216 |  | 
| 216 217 | 
             
                  # create box stream
         | 
| 217 | 
            -
                  box_stream = ''
         | 
| 218 | 
            +
                  box_stream = +''
         | 
| 218 219 | 
             
                  # set graphic state for box
         | 
| 219 220 | 
             
                  if options[:box_color] || (options[:border_width].to_i > 0 && options[:border_color])
         | 
| 220 221 | 
             
                    # compute x and y position for text
         | 
| @@ -290,7 +291,7 @@ module CombinePDF | |
| 290 291 | 
             
                  # reset x,y by text alignment - x,y are calculated from the bottom left
         | 
| 291 292 | 
             
                  # each unit (1) is 1/72 Inch
         | 
| 292 293 | 
             
                  # create text stream
         | 
| 293 | 
            -
                  text_stream = ''
         | 
| 294 | 
            +
                  text_stream = +''
         | 
| 294 295 | 
             
                  if !text.to_s.empty? && options[:font_size] != 0 && (options[:font_color] || options[:stroke_color])
         | 
| 295 296 | 
             
                    # compute x and y position for text
         | 
| 296 297 | 
             
                    x = options[:x] + (options[:width] * options[:text_padding])
         | 
| @@ -679,7 +680,7 @@ module CombinePDF | |
| 679 680 | 
             
                  insert_content 'Q'
         | 
| 680 681 |  | 
| 681 682 | 
             
                  # Prep content
         | 
| 682 | 
            -
                  @contents = ''
         | 
| 683 | 
            +
                  @contents = +''
         | 
| 683 684 | 
             
                  insert_content @contents
         | 
| 684 685 | 
             
                  @contents
         | 
| 685 686 | 
             
                end
         | 
| @@ -788,7 +789,7 @@ module CombinePDF | |
| 788 789 | 
             
                      # add to array
         | 
| 789 790 | 
             
                      if out.last.nil? || out.last[0] != fonts[i]
         | 
| 790 791 | 
             
                        out.last[1] << '>' unless out.last.nil?
         | 
| 791 | 
            -
                        out << [fonts[i], '<', 0, 0]
         | 
| 792 | 
            +
                        out << [fonts[i], (+'<'), 0, 0]
         | 
| 792 793 | 
             
                      end
         | 
| 793 794 | 
             
                      out.last[1] << (fonts_array[i].cmap.nil? ? (c.unpack('H*')[0]) : fonts_array[i].cmap[c])
         | 
| 794 795 | 
             
                      if fonts_array[i].metrics[c]
         | 
    
        data/lib/combine_pdf/parser.rb
    CHANGED
    
    | @@ -262,7 +262,7 @@ module CombinePDF | |
| 262 262 | 
             
                    ##########################################
         | 
| 263 263 | 
             
                    elsif @scanner.scan(/\(/)
         | 
| 264 264 | 
             
                      # warn "Found a literal string"
         | 
| 265 | 
            -
                      str = ''. | 
| 265 | 
            +
                      str = ''.b
         | 
| 266 266 | 
             
                      count = 1
         | 
| 267 267 | 
             
                      while count > 0 && @scanner.rest?
         | 
| 268 268 | 
             
                        scn = @scanner.scan_until(/[\(\)]/)
         | 
| @@ -369,7 +369,7 @@ module CombinePDF | |
| 369 369 | 
             
                      # the following was dicarded because some PDF files didn't have an EOL marker as required
         | 
| 370 370 | 
             
                      # str = @scanner.scan_until(/(\r\n|\r|\n)endstream/)
         | 
| 371 371 | 
             
                      # instead, a non-strict RegExp is used:
         | 
| 372 | 
            -
             | 
| 372 | 
            +
             | 
| 373 373 |  | 
| 374 374 | 
             
                      # raise error if the stream doesn't end.
         | 
| 375 375 | 
             
                      unless @scanner.skip_until(/endstream/)
         | 
| @@ -379,7 +379,7 @@ module CombinePDF | |
| 379 379 | 
             
                      length = 0 if(length < 0)
         | 
| 380 380 | 
             
                      length -= 1 if(@scanner.string[old_pos + length - 1] == "\n") 
         | 
| 381 381 | 
             
                      length -= 1 if(@scanner.string[old_pos + length - 1] == "\r") 
         | 
| 382 | 
            -
                      str = (length > 0) ? @scanner.string.slice(old_pos, length) : ''
         | 
| 382 | 
            +
                      str = (length > 0) ? @scanner.string.slice(old_pos, length) : +''
         | 
| 383 383 |  | 
| 384 384 | 
             
                      # warn "CombinePDF parser: detected Stream #{str.length} bytes long #{str[0..3]}...#{str[-4..-1]}"
         | 
| 385 385 |  | 
| @@ -632,17 +632,17 @@ module CombinePDF | |
| 632 632 | 
             
                #
         | 
| 633 633 | 
             
                def serialize_objects_and_references
         | 
| 634 634 | 
             
                  obj_dir = {}
         | 
| 635 | 
            -
                  objid_cache = {}
         | 
| 635 | 
            +
                  objid_cache = {}.compare_by_identity
         | 
| 636 636 | 
             
                  # create a dictionary for referenced objects (no value resolution at this point)
         | 
| 637 637 | 
             
                  # at the same time, delete duplicates and old versions when objects have multiple versions
         | 
| 638 638 | 
             
                  @parsed.uniq!
         | 
| 639 639 | 
             
                  @parsed.length.times do |i|
         | 
| 640 640 | 
             
                    o = @parsed[i]
         | 
| 641 | 
            -
                    objid_cache[o | 
| 641 | 
            +
                    objid_cache[o] = i
         | 
| 642 642 | 
             
                    tmp_key = [o[:indirect_reference_id], o[:indirect_generation_number]]
         | 
| 643 643 | 
             
                    if tmp_found = obj_dir[tmp_key]
         | 
| 644 644 | 
             
                      tmp_found.clear
         | 
| 645 | 
            -
                      @parsed[objid_cache[tmp_found | 
| 645 | 
            +
                      @parsed[objid_cache[tmp_found]] = nil
         | 
| 646 646 | 
             
                    end
         | 
| 647 647 | 
             
                    obj_dir[tmp_key] = o
         | 
| 648 648 | 
             
                  end
         | 
| @@ -765,9 +765,9 @@ module CombinePDF | |
| 765 765 | 
             
                # end
         | 
| 766 766 |  | 
| 767 767 | 
             
                # # run block of code on evey PDF object (PDF objects are class Hash)
         | 
| 768 | 
            -
                # def each_object(object, limit_references = true, already_visited = {}, &block)
         | 
| 768 | 
            +
                # def each_object(object, limit_references = true, already_visited = {}.compare_by_identity, &block)
         | 
| 769 769 | 
             
                # 	unless limit_references
         | 
| 770 | 
            -
                # 		already_visited[object | 
| 770 | 
            +
                # 		already_visited[object] = true
         | 
| 771 771 | 
             
                # 	end
         | 
| 772 772 | 
             
                # 	case
         | 
| 773 773 | 
             
                # 	when object.is_a?(Array)
         | 
| @@ -776,7 +776,7 @@ module CombinePDF | |
| 776 776 | 
             
                # 		yield(object)
         | 
| 777 777 | 
             
                # 		unless limit_references && object[:is_reference_only]
         | 
| 778 778 | 
             
                # 			object.each do |k,v|
         | 
| 779 | 
            -
                # 				each_object(v, limit_references, already_visited, &block) unless already_visited[v | 
| 779 | 
            +
                # 				each_object(v, limit_references, already_visited, &block) unless already_visited[v]
         | 
| 780 780 | 
             
                # 			end
         | 
| 781 781 | 
             
                # 		end
         | 
| 782 782 | 
             
                # 	end
         | 
| @@ -1,4 +1,5 @@ | |
| 1 1 | 
             
            # -*- encoding : utf-8 -*-
         | 
| 2 | 
            +
            # frozen_string_literal: true
         | 
| 2 3 | 
             
            ########################################################
         | 
| 3 4 | 
             
            ## Thoughts from reading the ISO 32000-1:2008
         | 
| 4 5 | 
             
            ## this file is part of the CombinePDF library and the code
         | 
| @@ -21,19 +22,19 @@ module CombinePDF | |
| 21 22 | 
             
                # this is used for internal operations, such as injectng data using the << operator.
         | 
| 22 23 | 
             
                def add_referenced()
         | 
| 23 24 | 
             
                  # an existing object map
         | 
| 24 | 
            -
                  resolved = {}. | 
| 25 | 
            -
                  existing = {} | 
| 26 | 
            -
                  should_resolve = [] | 
| 25 | 
            +
                  resolved = {}.compare_by_identity
         | 
| 26 | 
            +
                  existing = {}
         | 
| 27 | 
            +
                  should_resolve = []
         | 
| 27 28 | 
             
                  #set all existing objects as resolved and register their children for future resolution
         | 
| 28 | 
            -
                  @objects.each { |obj| existing[obj] = obj ; resolved[obj | 
| 29 | 
            +
                  @objects.each { |obj| existing[obj] = obj ; resolved[obj] = obj; should_resolve << obj.values}
         | 
| 29 30 | 
             
                  # loop until should_resolve is empty
         | 
| 30 31 | 
             
                  while should_resolve.any?
         | 
| 31 32 | 
             
                    obj = should_resolve.pop
         | 
| 32 | 
            -
                    next if resolved[obj | 
| 33 | 
            +
                    next if resolved[obj] # the object exists
         | 
| 33 34 | 
             
                    if obj.is_a?(Hash)
         | 
| 34 35 | 
             
                      referenced = obj[:referenced_object]
         | 
| 35 36 | 
             
                      if referenced && referenced.any?
         | 
| 36 | 
            -
                        tmp = resolved[referenced | 
| 37 | 
            +
                        tmp = resolved[referenced]
         | 
| 37 38 | 
             
                        if !tmp && referenced[:raw_stream_content]
         | 
| 38 39 | 
             
                          tmp = existing[referenced[:raw_stream_content]]
         | 
| 39 40 | 
             
                          # Avoid endless recursion by limiting it to a number of layers (default == 2)
         | 
| @@ -42,18 +43,18 @@ module CombinePDF | |
| 42 43 | 
             
                        if tmp
         | 
| 43 44 | 
             
                          obj[:referenced_object] = tmp
         | 
| 44 45 | 
             
                        else
         | 
| 45 | 
            -
                          resolved[obj | 
| 46 | 
            +
                          resolved[obj] = referenced
         | 
| 46 47 | 
             
                          #        existing[referenced] = referenced
         | 
| 47 48 | 
             
                          existing[referenced[:raw_stream_content]] = referenced
         | 
| 48 49 | 
             
                          should_resolve << referenced
         | 
| 49 50 | 
             
                          @objects << referenced
         | 
| 50 51 | 
             
                        end
         | 
| 51 52 | 
             
                      else
         | 
| 52 | 
            -
                        resolved[obj | 
| 53 | 
            -
                        obj.keys.each { |k| should_resolve << obj[k] unless !obj[k].is_a?(Enumerable) || resolved[obj[k] | 
| 53 | 
            +
                        resolved[obj] = obj
         | 
| 54 | 
            +
                        obj.keys.each { |k| should_resolve << obj[k] unless !obj[k].is_a?(Enumerable) || resolved[obj[k]] }
         | 
| 54 55 | 
             
                      end
         | 
| 55 56 | 
             
                    elsif obj.is_a?(Array)
         | 
| 56 | 
            -
                      resolved[obj | 
| 57 | 
            +
                      resolved[obj] = obj
         | 
| 57 58 | 
             
                      should_resolve.concat obj
         | 
| 58 59 | 
             
                    end
         | 
| 59 60 | 
             
                  end
         | 
| @@ -78,14 +79,14 @@ module CombinePDF | |
| 78 79 | 
             
                  page_list.concat(with_pages) unless with_pages.empty?
         | 
| 79 80 |  | 
| 80 81 | 
             
                  # duplicate any non-unique pages - This is a special case to resolve Adobe Acrobat Reader issues (see issues #19 and #81)
         | 
| 81 | 
            -
                  uniqueness = {}. | 
| 82 | 
            -
                  page_list.each { |page| page = page[:referenced_object] || page; page = page.dup if uniqueness[page | 
| 82 | 
            +
                  uniqueness = {}.compare_by_identity
         | 
| 83 | 
            +
                  page_list.each { |page| page = page[:referenced_object] || page; page = page.dup if uniqueness[page]; uniqueness[page] = page }
         | 
| 83 84 | 
             
                  page_list.clear
         | 
| 84 85 | 
             
                  page_list = uniqueness.values
         | 
| 85 86 | 
             
                  uniqueness.clear
         | 
| 86 87 |  | 
| 87 88 | 
             
                  # build new Pages object
         | 
| 88 | 
            -
                  page_object_kids = [] | 
| 89 | 
            +
                  page_object_kids = []
         | 
| 89 90 | 
             
                  pages_object = { Type: :Pages, Count: page_list.length, Kids: page_object_kids }
         | 
| 90 91 | 
             
                  pages_object_reference = { referenced_object: pages_object, is_reference_only: true }
         | 
| 91 92 | 
             
                  page_list.each { |pg| pg[:Parent] = pages_object_reference; page_object_kids << ({ referenced_object: pg, is_reference_only: true }) }
         | 
| @@ -186,17 +187,18 @@ module CombinePDF | |
| 186 187 | 
             
                POSSIBLE_NAME_TREES = [:Dests, :AP, :Pages, :IDS, :Templates, :URLS, :JavaScript, :EmbeddedFiles, :AlternatePresentations, :Renditions].to_set.freeze
         | 
| 187 188 |  | 
| 188 189 | 
             
                def rebuild_names(name_tree = nil, base = 'CombinePDF_0000000')
         | 
| 190 | 
            +
                  base = +base
         | 
| 189 191 | 
             
                  if name_tree
         | 
| 190 192 | 
             
                    return nil unless name_tree.is_a?(Hash)
         | 
| 191 193 | 
             
                    name_tree = name_tree[:referenced_object] || name_tree
         | 
| 192 194 | 
             
                    dic = []
         | 
| 193 195 | 
             
                    # map a names tree and return a valid name tree. Do not recourse.
         | 
| 194 196 | 
             
                    should_resolve = [name_tree[:Kids], name_tree[:Names]]
         | 
| 195 | 
            -
                    resolved =  | 
| 197 | 
            +
                    resolved = Set.new.compare_by_identity
         | 
| 196 198 | 
             
                    while should_resolve.any?
         | 
| 197 199 | 
             
                      pos = should_resolve.pop
         | 
| 198 200 | 
             
                      if pos.is_a? Array
         | 
| 199 | 
            -
                        next if resolved.include?(pos | 
| 201 | 
            +
                        next if resolved.include?(pos)
         | 
| 200 202 | 
             
                        if pos[0].is_a? String
         | 
| 201 203 | 
             
                          (pos.length / 2).times do |i|
         | 
| 202 204 | 
             
                            dic << (pos[i * 2].clear << base.next!)
         | 
| @@ -209,16 +211,16 @@ module CombinePDF | |
| 209 211 | 
             
                        end
         | 
| 210 212 | 
             
                      elsif pos.is_a? Hash
         | 
| 211 213 | 
             
                        pos = pos[:referenced_object] || pos
         | 
| 212 | 
            -
                        next if resolved.include?(pos | 
| 214 | 
            +
                        next if resolved.include?(pos)
         | 
| 213 215 | 
             
                        should_resolve << pos[:Kids] if pos[:Kids]
         | 
| 214 216 | 
             
                        should_resolve << pos[:Names] if pos[:Names]
         | 
| 215 217 | 
             
                      end
         | 
| 216 | 
            -
                      resolved << pos | 
| 218 | 
            +
                      resolved << pos
         | 
| 217 219 | 
             
                    end
         | 
| 218 220 | 
             
                    return { referenced_object: { Names: dic }, is_reference_only: true }
         | 
| 219 221 | 
             
                  end
         | 
| 220 222 | 
             
                  @names ||= @names[:referenced_object]
         | 
| 221 | 
            -
                  new_names = { Type: :Names } | 
| 223 | 
            +
                  new_names = { Type: :Names }
         | 
| 222 224 | 
             
                  POSSIBLE_NAME_TREES.each do |ntree|
         | 
| 223 225 | 
             
                    if @names[ntree]
         | 
| 224 226 | 
             
                      new_names[ntree] = rebuild_names(@names[ntree], base)
         | 
| @@ -373,7 +375,7 @@ module CombinePDF | |
| 373 375 | 
             
                private
         | 
| 374 376 |  | 
| 375 377 | 
             
                def equal_layers obj1, obj2, layer = CombinePDF.eq_depth_limit
         | 
| 376 | 
            -
                  return true if obj1. | 
| 378 | 
            +
                  return true if obj1.equal?(obj2)
         | 
| 377 379 | 
             
                  if obj1.is_a? Hash
         | 
| 378 380 | 
             
                    return false unless obj2.is_a? Hash
         | 
| 379 381 | 
             
                    return false unless obj1.length == obj2.length
         | 
| @@ -1,5 +1,6 @@ | |
| 1 1 | 
             
            # -*- encoding : utf-8 -*-
         | 
| 2 | 
            -
             | 
| 2 | 
            +
            ## frozen_string_literal: true
         | 
| 3 | 
            +
            #######################################################
         | 
| 3 4 | 
             
            ## Thoughts from reading the ISO 32000-1:2008
         | 
| 4 5 | 
             
            ## this file is part of the CombinePDF library and the code
         | 
| 5 6 | 
             
            ## is subject to the same license.
         | 
| @@ -93,7 +94,7 @@ module CombinePDF | |
| 93 94 | 
             
                  @version = 0
         | 
| 94 95 | 
             
                  @viewer_preferences = {}
         | 
| 95 96 | 
             
                  @info = {}
         | 
| 96 | 
            -
                  parser ||= PDFParser.new('')
         | 
| 97 | 
            +
                  parser ||= PDFParser.new(+'')
         | 
| 97 98 | 
             
                  raise TypeError, "initialization error, expecting CombinePDF::PDFParser or nil, but got #{parser.class.name}" unless parser.is_a? PDFParser
         | 
| 98 99 | 
             
                  @objects = parser.parse
         | 
| 99 100 |  | 
| @@ -207,7 +208,7 @@ module CombinePDF | |
| 207 208 | 
             
                  # xref_location = 0
         | 
| 208 209 | 
             
                  # out.each { |line| xref_location += line.bytesize + 1}
         | 
| 209 210 | 
             
                  out << "xref\n0 #{indirect_object_count}\n0000000000 65535 f "
         | 
| 210 | 
            -
                  xref.each { |offset| out << ("%010d 00000 n " % offset) }
         | 
| 211 | 
            +
                  xref.each { |offset| out << ("%010d 00000 n ".freeze % offset) }
         | 
| 211 212 | 
             
                  out << 'trailer'.freeze
         | 
| 212 213 | 
             
                  out << "<<\n/Root #{false || "#{catalog[:indirect_reference_id]} #{catalog[:indirect_generation_number]} R"}"
         | 
| 213 214 | 
             
                  out << "/Size #{indirect_object_count}"
         | 
| @@ -216,7 +217,7 @@ module CombinePDF | |
| 216 217 | 
             
                  # when finished, remove the numbering system and keep only pointers
         | 
| 217 218 | 
             
                  remove_old_ids
         | 
| 218 219 | 
             
                  # output the pdf stream
         | 
| 219 | 
            -
                  out.join("\n". | 
| 220 | 
            +
                  out.join("\n".b).force_encoding(Encoding::ASCII_8BIT)
         | 
| 220 221 | 
             
                end
         | 
| 221 222 |  | 
| 222 223 | 
             
                # this method returns all the pages cataloged in the catalog.
         | 
    
        data/lib/combine_pdf/renderer.rb
    CHANGED
    
    | @@ -1,3 +1,4 @@ | |
| 1 | 
            +
            # frozen_string_literal: true
         | 
| 1 2 | 
             
            module CombinePDF
         | 
| 2 3 | 
             
              ################################################################
         | 
| 3 4 | 
             
              ## These are common functions, used within the different classes
         | 
| @@ -123,12 +124,12 @@ module CombinePDF | |
| 123 124 | 
             
                  # if the object is not a simple object, it is a dictionary
         | 
| 124 125 | 
             
                  # A dictionary shall be written as a sequence of key-value pairs enclosed in double angle brackets (<<...>>)
         | 
| 125 126 | 
             
                  # (using LESS-THAN SIGNs (3Ch) and GREATER-THAN SIGNs (3Eh)).
         | 
| 126 | 
            -
                  out << "<<\n". | 
| 127 | 
            +
                  out << "<<\n".b
         | 
| 127 128 | 
             
                  object.each do |key, value|
         | 
| 128 129 | 
             
                    out << "#{object_to_pdf key} #{object_to_pdf value}\n".force_encoding(Encoding::ASCII_8BIT) unless PDF::PRIVATE_HASH_KEYS.include? key
         | 
| 129 130 | 
             
                  end
         | 
| 130 131 | 
             
                  object.delete :Length
         | 
| 131 | 
            -
                  out << '>>'. | 
| 132 | 
            +
                  out << '>>'.b
         | 
| 132 133 | 
             
                  out << "\nstream\n#{object[:raw_stream_content]}\nendstream".force_encoding(Encoding::ASCII_8BIT) if object[:raw_stream_content]
         | 
| 133 134 | 
             
                  out << "\nendobj\n" if object[:indirect_reference_id]
         | 
| 134 135 | 
             
                  out.join.force_encoding(Encoding::ASCII_8BIT)
         | 
    
        data/lib/combine_pdf/version.rb
    CHANGED
    
    
    
        data/lib/combine_pdf.rb
    CHANGED
    
    
| @@ -12,7 +12,7 @@ class CombinePDFRendererTest < Minitest::Test | |
| 12 12 |  | 
| 13 13 | 
             
              def test_numeric_array_to_pdf
         | 
| 14 14 | 
             
                input = [1.234567, 0.000054, 5, -0.000099]
         | 
| 15 | 
            -
                expected = "[1.234567 0.000054 5 -0.000099]". | 
| 15 | 
            +
                expected = "[1.234567 0.000054 5 -0.000099]".b
         | 
| 16 16 | 
             
                actual = TestRenderer.new.test_object(input)
         | 
| 17 17 |  | 
| 18 18 | 
             
                assert_equal(expected, actual)
         | 
    
        metadata
    CHANGED
    
    | @@ -1,14 +1,14 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: combine_pdf
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version: 1.0. | 
| 4 | 
            +
              version: 1.0.27
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - Boaz Segev
         | 
| 8 8 | 
             
            autorequire:
         | 
| 9 9 | 
             
            bindir: bin
         | 
| 10 10 | 
             
            cert_chain: []
         | 
| 11 | 
            -
            date:  | 
| 11 | 
            +
            date: 2024-11-10 00:00:00.000000000 Z
         | 
| 12 12 | 
             
            dependencies:
         | 
| 13 13 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 14 14 | 
             
              name: ruby-rc4
         |