class HexaPDF::Type::Trailer

See: PDF2.0 s7.5.5, s14.4; XRefStream
cross-reference stream is written is the trailer integrated into the stream’s dictionary.
HexaPDF::Revision object’s trailer dictionary is always of this type. Only when a
trailer is stored directly in the cross-reference stream dictionary. However, a
When cross-reference streams are used the information that is normally stored in the file
file trailer (see HexaPDF::Revision#trailer).
Since a PDF document can contain multiple revisions, each revision needs to have its own
necessary for encrypting the PDF document.
(the main PDF document structure) and the Info dictionary and holds the information
The file trailer is the starting point for the PDF’s object tree. It links to the Catalog
Represents the PDF file trailer.

def catalog

Returns the document's Catalog (see Type::Catalog), creating it if needed.
def catalog
  self[:Root] ||= document.add({Type: :Catalog}, type: :Catalog)
end

def info

Returns the document's information dictionary (see Type::Info), creating it if needed.
def info
  self[:Info] ||= document.add({}, type: :XXInfo)
end

def perform_validation(&block)

Validates the trailer.
def perform_validation(&block)
  super
  unless value[:ID]
    msg = if value[:Encrypt]
            "ID field is required when an Encrypt dictionary is present"
          else
            "ID field should always be set"
          end
    yield(msg, true)
    set_random_id
  end
  unless value[:Root]
    yield("A PDF document must have a Catalog dictionary", true)
    catalog.validate(&block)
  end
  if value[:Encrypt] && (!document.security_handler ||
                         !document.security_handler.encryption_key_valid?)
    yield("Encryption key doesn't match encryption dictionary", false)
  end
end

def set_random_id

See: PDF2.0 14.4

Sets the /ID field to an array of two copies of a random string and returns this array.
def set_random_id
  value[:ID] = [Digest::MD5.digest(rand.to_s)] * 2
end

def update_id

PDF file, the second part should change with each write).
Updates the second part of the /ID field (the first part should always be the same for a
def update_id
  if self[:ID].kind_of?(PDFArray)
    value[:ID][1] = Digest::MD5.digest(rand.to_s)
  else
    set_random_id
  end
end