Skip to content

Commit a5e53aa

Browse files
Enhanced RDoc for ::new and ::create (#10)
1 parent b50559f commit a5e53aa

File tree

1 file changed

+97
-48
lines changed

1 file changed

+97
-48
lines changed

lib/tempfile.rb

Lines changed: 97 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -87,50 +87,64 @@
8787
# same Tempfile object from multiple threads then you should protect it with a
8888
# mutex.
8989
class Tempfile < DelegateClass(File)
90-
# Creates a temporary file with permissions 0600 (= only readable and
91-
# writable by the owner) and opens it with mode "w+".
90+
91+
# Creates a file in the underlying file system;
92+
# returns a new \Tempfile object based on that file.
93+
#
94+
# If possible, consider instead using Tempfile.create, which:
95+
#
96+
# - Avoids the performance cost of delegation,
97+
# incurred when Tempfile.new calls its superclass <tt>DelegateClass(File)</tt>.
98+
# - Does not rely on a finalizer to close and unlink the file,
99+
# which can be unreliable.
100+
#
101+
# Creates and returns file whose:
102+
#
103+
# - Class is \Tempfile (not \File, as in Tempfile.create).
104+
# - Directory is the system temporary directory (system-dependent).
105+
# - Generated filename is unique in that directory.
106+
# - Permissions are <tt>0600</tt>;
107+
# see {File Permissions}[https://docs.ruby-lang.org/en/master/File.html#label-File+Permissions].
108+
# - Mode is <tt>'w+'</tt> (read/write mode, positioned at the end).
109+
#
110+
# The underlying file is removed when the \Tempfile object dies
111+
# and is reclaimed by the garbage collector.
92112
#
93-
# It is recommended to use Tempfile.create { ... } instead when possible,
94-
# because that method avoids the cost of delegation and does not rely on a
95-
# finalizer to close and unlink the file, which is unreliable.
113+
# Example:
96114
#
97-
# The +basename+ parameter is used to determine the name of the
98-
# temporary file. You can either pass a String or an Array with
99-
# 2 String elements. In the former form, the temporary file's base
100-
# name will begin with the given string. In the latter form,
101-
# the temporary file's base name will begin with the array's first
102-
# element, and end with the second element. For example:
115+
# f = Tempfile.new # => #<Tempfile:/tmp/20220505-17839-1s0kt30>
116+
# f.class # => Tempfile
117+
# f.path # => "/tmp/20220505-17839-1s0kt30"
118+
# f.stat.mode.to_s(8) # => "100600"
119+
# File.exist?(f.path) # => true
120+
# File.unlink(f.path) #
121+
# File.exist?(f.path) # => false
103122
#
104-
# file = Tempfile.new('hello')
105-
# file.path # => something like: "/tmp/hello2843-8392-92849382--0"
123+
# Argument +basename+, if given, may be one of:
106124
#
107-
# # Use the Array form to enforce an extension in the filename:
108-
# file = Tempfile.new(['hello', '.jpg'])
109-
# file.path # => something like: "/tmp/hello2843-8392-92849382--0.jpg"
125+
# - A string: the generated filename begins with +basename+:
110126
#
111-
# The temporary file will be placed in the directory as specified
112-
# by the +tmpdir+ parameter. By default, this is +Dir.tmpdir+.
127+
# Tempfile.new('foo') # => #<Tempfile:/tmp/foo20220505-17839-1whk2f>
113128
#
114-
# file = Tempfile.new('hello', '/home/aisaka')
115-
# file.path # => something like: "/home/aisaka/hello2843-8392-92849382--0"
129+
# - An array of two strings <tt>[prefix, suffix]</tt>:
130+
# the generated filename begins with +prefix+ and ends with +suffix+:
116131
#
117-
# You can also pass an options hash. Under the hood, Tempfile creates
118-
# the temporary file using +File.open+. These options will be passed to
119-
# +File.open+. This is mostly useful for specifying encoding
120-
# options, e.g.:
132+
# Tempfile.new(%w/foo .jpg/) # => #<Tempfile:/tmp/foo20220505-17839-58xtfi.jpg>
121133
#
122-
# Tempfile.new('hello', '/home/aisaka', encoding: 'ascii-8bit')
134+
# With arguments +basename+ and +tmpdir+, the file is created in directory +tmpdir+:
123135
#
124-
# # You can also omit the 'tmpdir' parameter:
125-
# Tempfile.new('hello', encoding: 'ascii-8bit')
136+
# Tempfile.new('foo', '.') # => #<Tempfile:./foo20220505-17839-xfstr8>
126137
#
127-
# Note: +mode+ keyword argument, as accepted by Tempfile, can only be
128-
# numeric, combination of the modes defined in File::Constants.
138+
# Keyword arguments +mode+ and +options+ are passed directly to method
139+
# {File.open}[https://docs.ruby-lang.org/en/master/File.html#method-c-open]:
129140
#
130-
# === Exceptions
141+
# - The value given with +mode+ must be an integer,
142+
# and may be expressed as the logical OR of constants defined in
143+
# {File::Constants}[https://docs.ruby-lang.org/en/master/File/Constants.html].
144+
# - For +options+, see {Open Options}[https://docs.ruby-lang.org/en/master/IO.html#class-IO-label-Open+Options].
145+
#
146+
# Related: Tempfile.create.
131147
#
132-
# If Tempfile.new cannot find a unique filename within a limited
133-
# number of tries, then it will raise an exception.
134148
def initialize(basename="", tmpdir=nil, mode: 0, **options)
135149
warn "Tempfile.new doesn't call the given block.", uplevel: 1 if block_given?
136150

@@ -325,26 +339,61 @@ def open(*args, **kw)
325339
end
326340
end
327341

328-
# Creates a temporary file as a usual File object (not a Tempfile).
329-
# It does not use finalizer and delegation, which makes it more efficient and reliable.
342+
# Creates a file in the underlying file system;
343+
# returns a new \File object based on that file.
330344
#
331-
# If no block is given, this is similar to Tempfile.new except
332-
# creating File instead of Tempfile. In that case, the created file is
333-
# not removed automatically. You should use File.unlink to remove it.
345+
# With no block given and no arguments, creates and returns file whose:
334346
#
335-
# If a block is given, then a File object will be constructed,
336-
# and the block is invoked with the object as the argument.
337-
# The File object will be automatically closed and
338-
# the temporary file is removed after the block terminates,
339-
# releasing all resources that the block created.
340-
# The call returns the value of the block.
347+
# - Class is {File}[https://docs.ruby-lang.org/en/master/File.html] (not \Tempfile).
348+
# - Directory is the system temporary directory (system-dependent).
349+
# - Generated filename is unique in that directory.
350+
# - Permissions are <tt>0600</tt>;
351+
# see {File Permissions}[https://docs.ruby-lang.org/en/master/File.html#label-File+Permissions].
352+
# - Mode is <tt>'w+'</tt> (read/write mode, positioned at the end).
341353
#
342-
# In any case, all arguments (+basename+, +tmpdir+, +mode+, and
343-
# <code>**options</code>) will be treated the same as for Tempfile.new.
354+
# With no block, the file is not removed automatically,
355+
# and so should be explicitly removed.
344356
#
345-
# Tempfile.create('foo', '/home/temp') do |f|
346-
# # ... do something with f ...
347-
# end
357+
# Example:
358+
#
359+
# f = Tempfile.create # => #<File:/tmp/20220505-9795-17ky6f6>
360+
# f.class # => File
361+
# f.path # => "/tmp/20220505-9795-17ky6f6"
362+
# f.stat.mode.to_s(8) # => "100600"
363+
# File.exist?(f.path) # => true
364+
# File.unlink(f.path)
365+
# File.exist?(f.path) # => false
366+
#
367+
# Argument +basename+, if given, may be one of:
368+
#
369+
# - A string: the generated filename begins with +basename+:
370+
#
371+
# Tempfile.create('foo') # => #<File:/tmp/foo20220505-9795-1gok8l9>
372+
#
373+
# - An array of two strings <tt>[prefix, suffix]</tt>:
374+
# the generated filename begins with +prefix+ and ends with +suffix+:
375+
#
376+
# Tempfile.create(%w/foo .jpg/) # => #<File:/tmp/foo20220505-17839-tnjchh.jpg>
377+
#
378+
# With arguments +basename+ and +tmpdir+, the file is created in directory +tmpdir+:
379+
#
380+
# Tempfile.create('foo', '.') # => #<File:./foo20220505-9795-1emu6g8>
381+
#
382+
# Keyword arguments +mode+ and +options+ are passed directly to method
383+
# {File.open}[https://docs.ruby-lang.org/en/master/File.html#method-c-open]:
384+
#
385+
# - The value given with +mode+ must be an integer,
386+
# and may be expressed as the logical OR of constants defined in
387+
# {File::Constants}[https://docs.ruby-lang.org/en/master/File/Constants.html].
388+
# - For +options+, see {Open Options}[https://docs.ruby-lang.org/en/master/IO.html#class-IO-label-Open+Options].
389+
#
390+
# With a block given, creates the file as above, passes it to the block,
391+
# and returns the block's value;
392+
# before the return, the file object is closed and the underlying file is removed:
393+
#
394+
# Tempfile.create {|file| file.path } # => "/tmp/20220505-9795-rkists"
395+
#
396+
# Related: Tempfile.new.
348397
#
349398
def Tempfile.create(basename="", tmpdir=nil, mode: 0, **options)
350399
tmpfile = nil

0 commit comments

Comments
 (0)