zip-container 2.0.0 → 2.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,15 +1,15 @@
1
1
  ---
2
2
  !binary "U0hBMQ==":
3
3
  metadata.gz: !binary |-
4
- YjRlNjYzODNiZDM4MDBjYjQyZDMyODIzODdmYjlhNzRkYTNmNjA4NQ==
4
+ ZmM2M2M1M2YyMWUwOTk2NWRkNjllMjU0MDc0ZjQ4NGU3OWRiNTFlMg==
5
5
  data.tar.gz: !binary |-
6
- MGRmMzVkNTI4NjI0NmVhMGNmNDZiMTIwZTNjM2FlM2E3YWIxZmY4OA==
6
+ OWFjNzFmYjM4NTliZjc4ZGE0NTZjYzNhMjBiMjJjY2Q3NGVmZjdmMw==
7
7
  SHA512:
8
8
  metadata.gz: !binary |-
9
- NTk3MzMyYjM0M2U5NDgwZTYxNjE3ZDQ5YTIxMzA5NDk0YmQxMWVlOGI4ZmI4
10
- ZmI3MDFkMGNjN2NjNDZlMTA2NDk2YTIwNTU2MjA4OWNkMzBlYjRlODYyYTNk
11
- YThiMjNmODA4NjU1OGMzMjgxY2U1ZDhkMjkxMTQ4YmU1NDc5YzY=
9
+ ZmQxZTFjNzY2NjEyZGIzM2IzOTc2ZGU1ZjlkM2IwMzljZmM4NmUyN2JmNWYx
10
+ ZGU4YWU0ZjYzOTU3MjU3ZWVhZjdlNzI4MjY3MzhkYTEyNmNkOGFjNWNkZjFh
11
+ NmE1YWU3YWFjMzM0ODI0YTM2YTc4NzU3MDYyYzE2MTVjMDZjMTc=
12
12
  data.tar.gz: !binary |-
13
- NjI4YmU4MTkwY2QzNjJiYmQ5MGQ3MmJkOTA2YzRlMDc5OWQyMDA0NTBmNDcx
14
- ZDAwMWVlMzk4ZGVlYWYyZmUyMjc5MmRkN2UzOTAyZGZhZmUxZDIwZmRmM2Ew
15
- ZmE4Njk3YmQ2ODczMjNmZmE0OTlhNTc5MTZhMTM0YjVhOGExN2U=
13
+ MDBmMWJmMjE2YzY4ZjkxYWZiOWU2NzNhOTU3Njk4MDViYWIzOGYyMDEzZDlk
14
+ NTNiYTM4YmFmMjAwNDZmZGVlMjYxMTAxMDU3YTcyYWVmMmE1NjFjMGY5MGFm
15
+ YmE0MjQwOTFkZjk1MGM2ZDQyY2ZhMDViYTA0NWYyM2ZlMjk3YTU=
data/.ruby-env ADDED
@@ -0,0 +1 @@
1
+ RUBYLIB=./lib:../lib
data/.travis.yml CHANGED
@@ -1,10 +1,16 @@
1
1
  language: ruby
2
+
2
3
  rvm:
3
4
  - 1.9.3
4
5
  - 2.0.0
5
- - 2.1.2
6
+ - 2.1.5
6
7
  - ruby-head
7
8
  - rbx-2
9
+
10
+ sudo: false
11
+
12
+ cache: bundler
13
+
8
14
  matrix:
9
15
  allow_failures:
10
16
  - rvm: ruby-head
data/Changes.rdoc CHANGED
@@ -1,5 +1,22 @@
1
1
  = Changes log for the ZIP Container Ruby Gem
2
2
 
3
+ == Version 2.1.0
4
+
5
+ * Set up the Container superclass.
6
+ * Open the container from the superclass.
7
+ * Check and read the mimetype file in the superclass.
8
+ * Initialize reserved names and managed entries in the superclass.
9
+ * Refactor mimetype verification.
10
+ * Move container verification into the superclass.
11
+ * Update the example scripts to the new API.
12
+ * Move ::open to the Container superclass.
13
+ * Move ::verify and ::verify! to the superclass.
14
+ * Add the ZipContainer::Dir class.
15
+ * Add a test for a mimetype entry that is a directory.
16
+ * Add a test for an unreadable mimetype file.
17
+ * Update dependencies.
18
+ * Disambiguate the two test classes for File and Dir.
19
+
3
20
  == Version 2.0.0
4
21
 
5
22
  * Change API: Container => File.
data/ReadMe.rdoc CHANGED
@@ -19,16 +19,22 @@ This is a Ruby library for working with ZIP Container files. See the
19
19
  {UDF}[https://learn.adobe.com/wiki/display/PDFNAV/Universal+Container+Format]
20
20
  specifications for more details.
21
21
 
22
+ We follow the principles of {Semantic Versioning}[http://semver.org/] for our
23
+ releases.
24
+
22
25
  == Backwards incompatibility warnings!
23
26
 
24
27
  === ZipContainer
25
28
 
26
- The ZipContainer::Container class is deprecated in favour of
27
- ZipContainer::File. These classes are functionally identical; it is just a
28
- change of name. The new name brings this API into closer alignment with the
29
- underlying rubyzip API (Zip::File).
29
+ The ZipContainer::Container class is now a common superclass of
30
+ ZipContainer::Dir and ZipContainer::File. You can use ZipContainer::File as a
31
+ direct replacement for ZipContainer::Container as the functionality is
32
+ preserved. The new names bring this API into closer alignment with the
33
+ underlying rubyzip API (Zip::File) and allows this library to work with
34
+ "exploded" or unpacked containers directly.
30
35
 
31
- ZipContainer::Container is unavailable from version 2.0.0 onwards.
36
+ ZipContainer::Container should not be used directly from version 2.0.0
37
+ onwards.
32
38
 
33
39
  === Rubyzip
34
40
 
@@ -49,7 +49,7 @@ if File.exists?(container_file)
49
49
  end
50
50
 
51
51
  begin
52
- ZipContainer::Container.create(container_file, "application/epub+zip") do |c|
52
+ ZipContainer::File.create(container_file, "application/epub+zip") do |c|
53
53
 
54
54
  # Add a cheery greeting file from a string.
55
55
  c.file.open("greeting.txt", "w") do |f|
@@ -44,7 +44,7 @@ usage unless ARGV.length == 1
44
44
  container_file = ARGV[0]
45
45
 
46
46
  begin
47
- ZipContainer::Container.verify!(container_file)
47
+ ZipContainer::File.verify!(container_file)
48
48
  rescue ZipContainer::MalformedContainerError, ZipContainer::ZipError => err
49
49
  puts err.to_s
50
50
  exit 1
@@ -44,7 +44,7 @@ usage unless ARGV.length == 1
44
44
  container_file = ARGV[0]
45
45
 
46
46
  begin
47
- container = ZipContainer::Container.open(container_file)
47
+ container = ZipContainer::File.open(container_file)
48
48
  rescue ZipContainer::MalformedContainerError, ZipContainer::ZipError => err
49
49
  puts err.to_s
50
50
  exit 1
data/lib/zip-container.rb CHANGED
@@ -43,7 +43,9 @@ require 'zip-container/entries/managed'
43
43
  require 'zip-container/entries/entry'
44
44
  require 'zip-container/entries/file'
45
45
  require 'zip-container/entries/directory'
46
+ require 'zip-container/container'
46
47
  require 'zip-container/file'
48
+ require 'zip-container/dir'
47
49
 
48
50
  # This is a ruby library to read and write ZIP Container Format files. See the
49
51
  # ZipContainer::Container class for more information.
@@ -0,0 +1,131 @@
1
+ # Copyright (c) 2014 The University of Manchester, UK.
2
+ #
3
+ # All rights reserved.
4
+ #
5
+ # Redistribution and use in source and binary forms, with or without
6
+ # modification, are permitted provided that the following conditions are met:
7
+ #
8
+ # * Redistributions of source code must retain the above copyright notice,
9
+ # this list of conditions and the following disclaimer.
10
+ #
11
+ # * Redistributions in binary form must reproduce the above copyright notice,
12
+ # this list of conditions and the following disclaimer in the documentation
13
+ # and/or other materials provided with the distribution.
14
+ #
15
+ # * Neither the names of The University of Manchester nor the names of its
16
+ # contributors may be used to endorse or promote products derived from this
17
+ # software without specific prior written permission.
18
+ #
19
+ # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20
+ # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
+ # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23
+ # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24
+ # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
+ # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
+ # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
+ # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
+ # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
+ # POSSIBILITY OF SUCH DAMAGE.
30
+ #
31
+ # Author: Robert Haines
32
+
33
+ #
34
+ module ZipContainer
35
+
36
+ # The superclass of anything that represents a Zip Container. That
37
+ # representation could be as a Zip file (most commonly), as a directory or
38
+ # something else.
39
+ class Container
40
+ include ReservedNames
41
+ include ManagedEntries
42
+
43
+ private_class_method :new
44
+
45
+ # The mime-type of this ZipContainer.
46
+ attr_reader :mimetype
47
+
48
+ # :stopdoc:
49
+ # The reserved mimetype file name for standard ZipContainers.
50
+ MIMETYPE_FILE = "mimetype"
51
+
52
+ def initialize(location)
53
+ @container = open_container(location)
54
+
55
+ check_mimetype!
56
+ @mimetype = read_mimetype
57
+
58
+ # Reserved entry names. Just the mimetype file by default.
59
+ register_reserved_name(MIMETYPE_FILE)
60
+
61
+ # Initialize the managed entry tables.
62
+ initialize_managed_entries
63
+ end
64
+ # :startdoc:
65
+
66
+ # :call-seq:
67
+ # open(filename) -> container
68
+ # open(filename) {|container| ...}
69
+ #
70
+ # Open an existing ZipContainer. It will be checked for conformance upon
71
+ # first access.
72
+ def self.open(filename, &block)
73
+ c = new(filename)
74
+
75
+ if block_given?
76
+ begin
77
+ yield c
78
+ ensure
79
+ c.close
80
+ end
81
+ end
82
+
83
+ c
84
+ end
85
+
86
+ # :call-seq:
87
+ # verify(filename) -> boolean
88
+ #
89
+ # Verify that the specified ZipContainer conforms to the specification.
90
+ # This method returns +false+ if there are any problems at all with the
91
+ # container (including if it cannot be found).
92
+ def self.verify(filename)
93
+ begin
94
+ new(filename).verify!
95
+ rescue
96
+ return false
97
+ end
98
+
99
+ true
100
+ end
101
+
102
+ # :call-seq:
103
+ # verify!(filename)
104
+ #
105
+ # Verify that the specified ZipContainer conforms to the specification.
106
+ # This method raises exceptions when errors are found or if there is
107
+ # something fundamental wrong with the container itself (e.g. it cannot be
108
+ # found).
109
+ def self.verify!(filename)
110
+ new(filename).verify!
111
+ end
112
+
113
+ # :call-seq:
114
+ # verify!
115
+ #
116
+ # Verify the contents of this ZipContainer file. All managed files and
117
+ # directories are checked to make sure that they exist, if required.
118
+ def verify!
119
+ verify_managed_entries!
120
+ end
121
+
122
+ private
123
+
124
+ def check_mimetype!
125
+ message = verify_mimetype
126
+ raise MalformedContainerError.new(message) unless message.nil?
127
+ end
128
+
129
+ end
130
+
131
+ end
@@ -0,0 +1,192 @@
1
+ # Copyright (c) 2014 The University of Manchester, UK.
2
+ #
3
+ # All rights reserved.
4
+ #
5
+ # Redistribution and use in source and binary forms, with or without
6
+ # modification, are permitted provided that the following conditions are met:
7
+ #
8
+ # * Redistributions of source code must retain the above copyright notice,
9
+ # this list of conditions and the following disclaimer.
10
+ #
11
+ # * Redistributions in binary form must reproduce the above copyright notice,
12
+ # this list of conditions and the following disclaimer in the documentation
13
+ # and/or other materials provided with the distribution.
14
+ #
15
+ # * Neither the names of The University of Manchester nor the names of its
16
+ # contributors may be used to endorse or promote products derived from this
17
+ # software without specific prior written permission.
18
+ #
19
+ # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20
+ # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
+ # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23
+ # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24
+ # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
+ # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
+ # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
+ # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
+ # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
+ # POSSIBILITY OF SUCH DAMAGE.
30
+ #
31
+ # Author: Robert Haines
32
+
33
+ require 'forwardable'
34
+
35
+ module ZipContainer
36
+
37
+ # This class represents a ZipContainer in directory format. See the
38
+ # {OCF}[http://www.idpf.org/epub/30/spec/epub30-ocf.html] and
39
+ # {UCF}[https://learn.adobe.com/wiki/display/PDFNAV/Universal+Container+Format]
40
+ # specifications for more details.
41
+ #
42
+ # This class provides most of the facilities of the standard <tt>::Dir</tt>
43
+ # class. Please also consult the
44
+ # {ruby Dir documentation}[http://ruby-doc.org/core-1.9.3/Dir.html]
45
+ # alongside these pages.
46
+ #
47
+ # There are code examples available with the source code of this library.
48
+ class Dir < Container
49
+
50
+ extend Forwardable
51
+ def_delegators :@container, :close, :each, :path, :pos, :pos=, :read,
52
+ :rewind, :seek, :tell
53
+
54
+ private_class_method :new
55
+
56
+ # :stopdoc:
57
+ def initialize(location)
58
+ super(location)
59
+ end
60
+ # :startdoc:
61
+
62
+ # :call-seq:
63
+ # create(pathname, mimetype) -> document
64
+ # create(pathname, mimetype) {|document| ...}
65
+ #
66
+ # Create a new (or convert an existing) directory as a ZipContainer with
67
+ # the specified mimetype.
68
+ def self.create(pathname, mimetype, &block)
69
+ ::Dir.mkdir(pathname) unless ::File.directory?(pathname)
70
+ ::File.write(full_path(MIMETYPE_FILE), mimetype)
71
+
72
+ # Now open the newly created container.
73
+ c = new(pathname)
74
+
75
+ if block_given?
76
+ begin
77
+ yield c
78
+ ensure
79
+ c.close
80
+ end
81
+ end
82
+
83
+ c
84
+ end
85
+
86
+ private
87
+
88
+ # Prepend the full path of the directory name to whatever is passed in
89
+ # here. This is for internal use to ensure we are always operating on
90
+ # files within our container directory.
91
+ def full_path(path)
92
+ ::File.join(@container.path, path)
93
+ end
94
+
95
+ def open_container(location)
96
+ ::Dir.new(location)
97
+ end
98
+
99
+ def verify_mimetype
100
+ mime_path = full_path(MIMETYPE_FILE)
101
+ if ::File.exist?(mime_path)
102
+ return "'mimetype' is not a regular file" unless ::File.file?(mime_path)
103
+ return "'mimetype' is not readable." unless ::File.readable?(mime_path)
104
+ else
105
+ return "'mimetype' file is missing."
106
+ end
107
+ end
108
+
109
+ def read_mimetype
110
+ ::File.read(full_path(MIMETYPE_FILE))
111
+ end
112
+
113
+ public
114
+
115
+ # Lots of extra docs out of the way at the end here...
116
+
117
+ ##
118
+ # :method: close
119
+ # :call-seq:
120
+ # close -> nil
121
+ #
122
+ # Equal to
123
+ # {::Dir.close}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-close]
124
+
125
+ ##
126
+ # :method: each
127
+ # :call-seq:
128
+ # each { |filename| ... } -> dir
129
+ # each -> an_enumerator
130
+ #
131
+ # Equal to
132
+ # {::Dir.each}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-each]
133
+
134
+ ##
135
+ # :method: path
136
+ # :call-seq:
137
+ # path -> string or nil
138
+ #
139
+ # Equal to
140
+ # {::Dir.path}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-path]
141
+
142
+ ##
143
+ # :method: pos
144
+ # :call-seq:
145
+ # pos -> integer
146
+ #
147
+ # Equal to
148
+ # {::Dir.pos}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-pos]
149
+
150
+ ##
151
+ # :method: pos=
152
+ # :call-seq:
153
+ # pos = integer -> integer
154
+ #
155
+ # Equal to
156
+ # {::Dir.pos=}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-pos-3D]
157
+
158
+ ##
159
+ # :method: read
160
+ # :call-seq:
161
+ # read -> string or nil
162
+ #
163
+ # Equal to
164
+ # {::Dir.read}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-read]
165
+
166
+ ##
167
+ # :method: rewind
168
+ # :call-seq:
169
+ # rewind -> dir
170
+ #
171
+ # Equal to
172
+ # {::Dir.rewind}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-rewind]
173
+
174
+ ##
175
+ # :method: seek
176
+ # :call-seq:
177
+ # seek(integer) -> dir
178
+ #
179
+ # Equal to
180
+ # {::Dir.seek}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-seek]
181
+
182
+ ##
183
+ # :method: tell
184
+ # :call-seq:
185
+ # tell -> integer
186
+ #
187
+ # Equal to
188
+ # {::Dir.tell}[http://ruby-doc.org/core-1.9.3/Dir.html#method-i-tell]
189
+
190
+ end
191
+
192
+ end
@@ -45,36 +45,20 @@ module ZipContainer
45
45
  # alongside these pages.
46
46
  #
47
47
  # There are code examples available with the source code of this library.
48
- class File
49
- include ReservedNames
50
- include ManagedEntries
48
+ class File < Container
51
49
 
52
50
  extend Forwardable
53
- def_delegators :@zipfile, :comment, :comment=, :commit_required?, :each,
51
+ def_delegators :@container, :comment, :comment=, :commit_required?, :each,
54
52
  :entries, :extract, :get_input_stream, :name, :read, :size
55
53
 
56
54
  private_class_method :new
57
55
 
58
- # The mime-type of this ZipContainer file.
59
- attr_reader :mimetype
60
-
61
56
  # :stopdoc:
62
- # The reserved mimetype file name for standard ZipContainer documents.
63
- MIMETYPE_FILE = "mimetype"
64
-
65
- def initialize(document)
66
- @zipfile = open_document(document)
67
- check_mimetype!
57
+ def initialize(location)
58
+ super(location)
68
59
 
69
- @mimetype = read_mimetype
70
60
  @on_disk = true
71
61
 
72
- # Reserved entry names. Just the mimetype file by default.
73
- register_reserved_name(MIMETYPE_FILE)
74
-
75
- # Initialize the managed entry tables.
76
- initialize_managed_entries
77
-
78
62
  # Here we fake up the connection to the rubyzip filesystem classes so
79
63
  # that they also respect the reserved names that we define.
80
64
  mapped_zip = ::Zip::FileSystem::ZipFileNameMapper.new(self)
@@ -131,53 +115,6 @@ module ZipContainer
131
115
  c.each
132
116
  end
133
117
 
134
- # :call-seq:
135
- # File.open(filename) -> document
136
- # File.open(filename) {|document| ...}
137
- #
138
- # Open an existing ZipContainer file from disk. It will be checked for
139
- # conformance upon first access.
140
- def self.open(filename, &block)
141
- c = new(filename)
142
-
143
- if block_given?
144
- begin
145
- yield c
146
- ensure
147
- c.close
148
- end
149
- end
150
-
151
- c
152
- end
153
-
154
- # :call-seq:
155
- # File.verify(filename) -> boolean
156
- #
157
- # Verify that the specified ZipContainer file conforms to the
158
- # specification. This method returns +false+ if there are any problems at
159
- # all with the file (including if it cannot be found).
160
- def self.verify(filename)
161
- begin
162
- new(filename).verify!
163
- rescue
164
- return false
165
- end
166
-
167
- true
168
- end
169
-
170
- # :call-seq:
171
- # File.verify!(filename)
172
- #
173
- # Verify that the specified ZipContainer file conforms to the
174
- # specification. This method raises exceptions when errors are found or if
175
- # there is something fundamental wrong with the file itself (e.g. it
176
- # cannot be found).
177
- def self.verify!(filename)
178
- new(filename).verify!
179
- end
180
-
181
118
  # :call-seq:
182
119
  # add(entry, src_path, &continue_on_exists_proc)
183
120
  #
@@ -193,7 +130,7 @@ module ZipContainer
193
130
  raise ReservedNameClashError.new(entry.to_s)
194
131
  end
195
132
 
196
- @zipfile.add(entry, src_path, &continue_on_exists_proc)
133
+ @container.add(entry, src_path, &continue_on_exists_proc)
197
134
  end
198
135
 
199
136
  # :call-seq:
@@ -207,7 +144,7 @@ module ZipContainer
207
144
  return false unless commit_required?
208
145
 
209
146
  if on_disk?
210
- @zipfile.commit
147
+ @container.commit
211
148
  end
212
149
  end
213
150
 
@@ -251,7 +188,7 @@ module ZipContainer
251
188
  return if hidden_entry?(entry_name)
252
189
  end
253
190
 
254
- @zipfile.find_entry(entry_name)
191
+ @container.find_entry(entry_name)
255
192
  end
256
193
 
257
194
  # :call-seq:
@@ -268,7 +205,7 @@ module ZipContainer
268
205
  raise Errno::ENOENT, entry if hidden_entry?(entry)
269
206
  end
270
207
 
271
- @zipfile.get_entry(entry)
208
+ @container.get_entry(entry)
272
209
  end
273
210
 
274
211
  # :call-seq:
@@ -286,7 +223,7 @@ module ZipContainer
286
223
  raise ReservedNameClashError.new(entry.to_s)
287
224
  end
288
225
 
289
- @zipfile.get_output_stream(entry, permission, &block)
226
+ @container.get_output_stream(entry, permission, &block)
290
227
  end
291
228
 
292
229
  # :call-seq:
@@ -347,7 +284,7 @@ module ZipContainer
347
284
  raise ReservedNameClashError.new(name)
348
285
  end
349
286
 
350
- @zipfile.mkdir(name, permission)
287
+ @container.mkdir(name, permission)
351
288
  end
352
289
 
353
290
  # :call-seq:
@@ -366,7 +303,7 @@ module ZipContainer
366
303
  # method will do nothing.
367
304
  def remove(entry)
368
305
  return if reserved_entry?(entry)
369
- @zipfile.remove(entry)
306
+ @container.remove(entry)
370
307
  end
371
308
 
372
309
  # :call-seq:
@@ -383,7 +320,7 @@ module ZipContainer
383
320
  return if reserved_entry?(entry)
384
321
  raise ReservedNameClashError.new(new_name) if reserved_entry?(new_name)
385
322
 
386
- @zipfile.rename(entry, new_name, &continue_on_exists_proc)
323
+ @container.rename(entry, new_name, &continue_on_exists_proc)
387
324
  end
388
325
 
389
326
  # :call-seq:
@@ -395,7 +332,7 @@ module ZipContainer
395
332
  # nothing.
396
333
  def replace(entry, src_path)
397
334
  return if reserved_entry?(entry)
398
- @zipfile.replace(entry, src_path)
335
+ @container.replace(entry, src_path)
399
336
  end
400
337
 
401
338
  # :call-seq:
@@ -403,41 +340,30 @@ module ZipContainer
403
340
  #
404
341
  # Return a textual summary of this ZipContainer file.
405
342
  def to_s
406
- @zipfile.to_s + " - #{@mimetype}"
407
- end
408
-
409
- # :call-seq:
410
- # verify!
411
- #
412
- # Verify the contents of this ZipContainer file. All managed files and
413
- # directories are checked to make sure that they exist, if required.
414
- def verify!
415
- verify_managed_entries!
343
+ @container.to_s + " - #{@mimetype}"
416
344
  end
417
345
 
418
346
  private
419
347
 
420
- def open_document(document)
348
+ def open_container(document)
421
349
  ::Zip::File.new(document)
422
350
  end
423
351
 
424
- def check_mimetype!
352
+ def verify_mimetype
425
353
  # Check mimetype file is present and correct.
426
- entry = @zipfile.find_entry(MIMETYPE_FILE)
354
+ entry = @container.find_entry(MIMETYPE_FILE)
427
355
 
428
- raise MalformedContainerError.new("'mimetype' file is missing.") if entry.nil?
356
+ return "'mimetype' file is missing." if entry.nil?
429
357
  if entry.local_header_offset != 0
430
- raise MalformedContainerError.new("'mimetype' file is not at offset 0 in the archive.")
358
+ return "'mimetype' file is not at offset 0 in the archive."
431
359
  end
432
360
  if entry.compression_method != ::Zip::Entry::STORED
433
- raise MalformedContainerError.new("'mimetype' file is compressed.")
361
+ return "'mimetype' file is compressed."
434
362
  end
435
-
436
- true
437
363
  end
438
364
 
439
365
  def read_mimetype
440
- @zipfile.read(MIMETYPE_FILE)
366
+ @container.read(MIMETYPE_FILE)
441
367
  end
442
368
 
443
369
  public
@@ -0,0 +1 @@
1
+ This "mimetype" directory needs to be preserved by git.
@@ -0,0 +1 @@
1
+ application/epub+zip
@@ -0,0 +1 @@
1
+ This dir should be "empty", which in this case just means no "mimetype" file.
@@ -0,0 +1,59 @@
1
+ # Copyright (c) 2014 The University of Manchester, UK.
2
+ #
3
+ # All rights reserved.
4
+ #
5
+ # Redistribution and use in source and binary forms, with or without
6
+ # modification, are permitted provided that the following conditions are met:
7
+ #
8
+ # * Redistributions of source code must retain the above copyright notice,
9
+ # this list of conditions and the following disclaimer.
10
+ #
11
+ # * Redistributions in binary form must reproduce the above copyright notice,
12
+ # this list of conditions and the following disclaimer in the documentation
13
+ # and/or other materials provided with the distribution.
14
+ #
15
+ # * Neither the names of The University of Manchester nor the names of its
16
+ # contributors may be used to endorse or promote products derived from this
17
+ # software without specific prior written permission.
18
+ #
19
+ # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20
+ # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
+ # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23
+ # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24
+ # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
+ # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
+ # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
+ # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
+ # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
+ # POSSIBILITY OF SUCH DAMAGE.
30
+ #
31
+ # Author: Robert Haines
32
+
33
+ require 'test/unit'
34
+ require 'tmpdir'
35
+ require 'zip-container'
36
+
37
+ class TestCreateDir < Test::Unit::TestCase
38
+
39
+ # Check that a mimetype which is not readable does not verify. We have to
40
+ # build this fixture programmatically as there's no way to add a file
41
+ # without read permissions into git.
42
+ def test_verify_unreadable_mimetype
43
+ Dir.mktmpdir do |dir|
44
+ container = File.join(dir, "unreadable")
45
+ Dir.mkdir(container)
46
+ mime_path = File.join(container, ZipContainer::Container::MIMETYPE_FILE)
47
+ File.open(mime_path, "w") { |file| file.write "MIMETYPE" }
48
+ File.chmod(0000, mime_path)
49
+
50
+ refute File.readable?(mime_path)
51
+ assert_raise(ZipContainer::MalformedContainerError) do
52
+ ZipContainer::Dir.verify!(container)
53
+ end
54
+
55
+ refute(ZipContainer::Dir.verify(container))
56
+ end
57
+ end
58
+
59
+ end
@@ -34,7 +34,7 @@ require 'test/unit'
34
34
  require 'tmpdir'
35
35
  require 'zip-container'
36
36
 
37
- class TestCreation < Test::Unit::TestCase
37
+ class TestCreateFile < Test::Unit::TestCase
38
38
 
39
39
  # Check creation of standard empty container files.
40
40
  def test_create_standard_file
@@ -0,0 +1,65 @@
1
+ # Copyright (c) 2014 The University of Manchester, UK.
2
+ #
3
+ # All rights reserved.
4
+ #
5
+ # Redistribution and use in source and binary forms, with or without
6
+ # modification, are permitted provided that the following conditions are met:
7
+ #
8
+ # * Redistributions of source code must retain the above copyright notice,
9
+ # this list of conditions and the following disclaimer.
10
+ #
11
+ # * Redistributions in binary form must reproduce the above copyright notice,
12
+ # this list of conditions and the following disclaimer in the documentation
13
+ # and/or other materials provided with the distribution.
14
+ #
15
+ # * Neither the names of The University of Manchester nor the names of its
16
+ # contributors may be used to endorse or promote products derived from this
17
+ # software without specific prior written permission.
18
+ #
19
+ # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20
+ # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
+ # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23
+ # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24
+ # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
+ # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
+ # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
+ # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
+ # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
+ # POSSIBILITY OF SUCH DAMAGE.
30
+ #
31
+ # Author: Robert Haines
32
+
33
+ require 'test/unit'
34
+ require 'zip-container'
35
+
36
+ class TestReadDir < Test::Unit::TestCase
37
+
38
+ # Check that the empty directory does not verify.
39
+ def test_verify_empty_directory
40
+ assert_raise(ZipContainer::MalformedContainerError) do
41
+ ZipContainer::Dir.verify!($dir_null)
42
+ end
43
+
44
+ refute(ZipContainer::Dir.verify($dir_null))
45
+ end
46
+
47
+ # Check that the empty container directory does verify.
48
+ def test_verify_empty_container
49
+ assert_nothing_raised(ZipContainer::MalformedContainerError) do
50
+ ZipContainer::Dir.verify!($dir_empty)
51
+ end
52
+
53
+ assert(ZipContainer::Dir.verify($dir_empty))
54
+ end
55
+
56
+ # Check that a mimetype entry that is a directory does not verify.
57
+ def test_verify_mimetype_directory
58
+ assert_raise(ZipContainer::MalformedContainerError) do
59
+ ZipContainer::Dir.verify!($dir_dir_mimetype)
60
+ end
61
+
62
+ refute(ZipContainer::Dir.verify($dir_dir_mimetype))
63
+ end
64
+
65
+ end
@@ -33,7 +33,7 @@
33
33
  require 'test/unit'
34
34
  require 'zip-container'
35
35
 
36
- class TestRead < Test::Unit::TestCase
36
+ class TestReadFile < Test::Unit::TestCase
37
37
 
38
38
  # Check that the null file does not verify.
39
39
  def test_verify_null_file
data/test/ts_container.rb CHANGED
@@ -37,6 +37,9 @@ Coveralls.wear!
37
37
  $mimetype = "application/epub+zip"
38
38
 
39
39
  # Example data files
40
+ $dir_null = "test/data/dirs/null"
41
+ $dir_empty = "test/data/dirs/empty"
42
+ $dir_dir_mimetype = "test/data/dirs/dir-mimetype"
40
43
  $file_null = "test/data/null.file"
41
44
  $empty = "test/data/empty.container"
42
45
  $empty_zip = "test/data/empty.zip"
@@ -47,7 +50,9 @@ $subclass = "test/data/subclassed.container"
47
50
  # Run test cases.
48
51
  require 'tc_util'
49
52
  require 'tc_exceptions'
50
- require 'tc_create'
51
- require 'tc_read'
53
+ require 'tc_create_dir'
54
+ require 'tc_create_file'
55
+ require 'tc_read_dir'
56
+ require 'tc_read_file'
52
57
  require 'tc_reserved_names'
53
58
  require 'tc_managed_entries'
data/version.yml CHANGED
@@ -1,4 +1,4 @@
1
1
  ---
2
2
  :major: 2
3
- :minor: 0
3
+ :minor: 1
4
4
  :patch: 0
@@ -55,10 +55,10 @@ Gem::Specification.new do |s|
55
55
  s.extra_rdoc_files = [ "Changes.rdoc", "Licence.rdoc", "ReadMe.rdoc" ]
56
56
  s.rdoc_options = [ "-N", "--tab-width=2", "--main=ReadMe.rdoc" ]
57
57
  s.required_ruby_version = ">= 1.9.3"
58
- s.add_development_dependency("rake", "~> 10.0.4")
59
- s.add_development_dependency("bundler", "~> 1.5")
60
- s.add_development_dependency("rdoc", "~> 4.0.1")
61
- s.add_development_dependency('coveralls')
62
- s.add_runtime_dependency("rubyzip", "~> 1.1.6")
58
+ s.add_development_dependency "bundler", "~> 1.5"
59
+ s.add_development_dependency "rake", "~> 10.1"
60
+ s.add_development_dependency "rdoc", "~> 4.1"
61
+ s.add_development_dependency "test-unit", "~> 3.0"
62
+ s.add_development_dependency "coveralls"
63
+ s.add_runtime_dependency "rubyzip", "~> 1.1.6"
63
64
  end
64
-
metadata CHANGED
@@ -1,57 +1,71 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: zip-container
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.0
4
+ version: 2.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Robert Haines
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-08-19 00:00:00.000000000 Z
11
+ date: 2014-12-07 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
- name: rake
14
+ name: bundler
15
15
  requirement: !ruby/object:Gem::Requirement
16
16
  requirements:
17
17
  - - ~>
18
18
  - !ruby/object:Gem::Version
19
- version: 10.0.4
19
+ version: '1.5'
20
20
  type: :development
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - ~>
25
25
  - !ruby/object:Gem::Version
26
- version: 10.0.4
26
+ version: '1.5'
27
27
  - !ruby/object:Gem::Dependency
28
- name: bundler
28
+ name: rake
29
29
  requirement: !ruby/object:Gem::Requirement
30
30
  requirements:
31
31
  - - ~>
32
32
  - !ruby/object:Gem::Version
33
- version: '1.5'
33
+ version: '10.1'
34
34
  type: :development
35
35
  prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
38
  - - ~>
39
39
  - !ruby/object:Gem::Version
40
- version: '1.5'
40
+ version: '10.1'
41
41
  - !ruby/object:Gem::Dependency
42
42
  name: rdoc
43
43
  requirement: !ruby/object:Gem::Requirement
44
44
  requirements:
45
45
  - - ~>
46
46
  - !ruby/object:Gem::Version
47
- version: 4.0.1
47
+ version: '4.1'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ~>
53
+ - !ruby/object:Gem::Version
54
+ version: '4.1'
55
+ - !ruby/object:Gem::Dependency
56
+ name: test-unit
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ~>
60
+ - !ruby/object:Gem::Version
61
+ version: '3.0'
48
62
  type: :development
49
63
  prerelease: false
50
64
  version_requirements: !ruby/object:Gem::Requirement
51
65
  requirements:
52
66
  - - ~>
53
67
  - !ruby/object:Gem::Version
54
- version: 4.0.1
68
+ version: '3.0'
55
69
  - !ruby/object:Gem::Dependency
56
70
  name: coveralls
57
71
  requirement: !ruby/object:Gem::Requirement
@@ -93,6 +107,7 @@ extra_rdoc_files:
93
107
  - ReadMe.rdoc
94
108
  files:
95
109
  - .gitignore
110
+ - .ruby-env
96
111
  - .ruby-gemset
97
112
  - .ruby-version
98
113
  - .travis.yml
@@ -105,6 +120,8 @@ files:
105
120
  - examples/verify-zip-container
106
121
  - examples/zip-container-info
107
122
  - lib/zip-container.rb
123
+ - lib/zip-container/container.rb
124
+ - lib/zip-container/dir.rb
108
125
  - lib/zip-container/entries/directory.rb
109
126
  - lib/zip-container/entries/entry.rb
110
127
  - lib/zip-container/entries/file.rb
@@ -115,16 +132,21 @@ files:
115
132
  - lib/zip-container/util.rb
116
133
  - lib/zip-container/version.rb
117
134
  - test/data/compressed_mimetype.container
135
+ - test/data/dirs/dir-mimetype/mimetype/.gitkeep
136
+ - test/data/dirs/empty/mimetype
137
+ - test/data/dirs/null/.gitkeep
118
138
  - test/data/empty.container
119
139
  - test/data/empty.zip
120
140
  - test/data/example.container
121
141
  - test/data/null.file
122
142
  - test/data/subclassed.container
123
143
  - test/helpers/entry_lists.rb
124
- - test/tc_create.rb
144
+ - test/tc_create_dir.rb
145
+ - test/tc_create_file.rb
125
146
  - test/tc_exceptions.rb
126
147
  - test/tc_managed_entries.rb
127
- - test/tc_read.rb
148
+ - test/tc_read_dir.rb
149
+ - test/tc_read_file.rb
128
150
  - test/tc_reserved_names.rb
129
151
  - test/tc_util.rb
130
152
  - test/ts_container.rb
@@ -159,16 +181,21 @@ specification_version: 4
159
181
  summary: A ZIP Container for use by OCF and UCF implementations
160
182
  test_files:
161
183
  - test/data/compressed_mimetype.container
184
+ - test/data/dirs/dir-mimetype/mimetype/.gitkeep
185
+ - test/data/dirs/empty/mimetype
186
+ - test/data/dirs/null/.gitkeep
162
187
  - test/data/empty.container
163
188
  - test/data/empty.zip
164
189
  - test/data/example.container
165
190
  - test/data/null.file
166
191
  - test/data/subclassed.container
167
192
  - test/helpers/entry_lists.rb
168
- - test/tc_create.rb
193
+ - test/tc_create_dir.rb
194
+ - test/tc_create_file.rb
169
195
  - test/tc_exceptions.rb
170
196
  - test/tc_managed_entries.rb
171
- - test/tc_read.rb
197
+ - test/tc_read_dir.rb
198
+ - test/tc_read_file.rb
172
199
  - test/tc_reserved_names.rb
173
200
  - test/tc_util.rb
174
201
  - test/ts_container.rb