Class: EPUB::OCF::PhysicalContainer::ArchiveZip

Inherits:
EPUB::OCF::PhysicalContainer show all
Defined in:
lib/epub/maker/ocf/physical_container/archive_zip.rb

Instance Method Summary collapse

Methods inherited from EPUB::OCF::PhysicalContainer

mtime, mtime=, save, write

Instance Method Details

#write(path_name, content, mtime: nil) ⇒ Object



8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
# File 'lib/epub/maker/ocf/physical_container/archive_zip.rb', line 8

def write(path_name, content, mtime: nil)
  ::Dir.mktmpdir do |dir|
    tmp_archive_path = ::File.join(dir, ::File.basename(@container_path) + '.tmp')
    Archive::Zip.open @container_path, :r do |z_in|
      Archive::Zip.open tmp_archive_path, :w do |z_out|
        updated = false
        z_in.each do |entry|
          if entry.zip_path == path_name.force_encoding('ASCII-8BIT')
            entry = entry.dup
            entry.file_data = IO::LikeHelpers::IOWrapper.new(StringIO.new(content))
            updated = true
          end
          if mtime
            entry.mtime = mtime
          end
          z_out << entry
        end
        unless updated
          entry = Archive::Zip::Entry::File.new(path_name)
          entry.file_data = IO::LikeHelpers::IOWrapper.new(StringIO.new(content))
          if mtime
            entry.mtime = mtime
          end
          z_out << entry
        end
      end
    end
    begin
      ::File.chmod 0666 & ~::File.umask, tmp_archive_path
      ::File.rename tmp_archive_path, @container_path
    rescue Errno::EACCES, Errno::EXDEV
      # In some cases on Windows, we fail to rename the file
      # but succeed to copy although I don't know why.
      # Race condition? I don't know. But no time to dig deeper.
      ::FileUtils.copy tmp_archive_path, @container_path
    end
  end
end