Class: HotCell::Output
- Inherits:
-
Descriptor
- Object
- Descriptor
- HotCell::Output
- Defined in:
- lib/hot_cell/descriptors.rb
Constant Summary collapse
- ACCESS_MODE =
Fcntl::O_WRONLY
Constants inherited from Descriptor
Instance Attribute Summary
Attributes inherited from Descriptor
Instance Method Summary collapse
-
#adopt(staged) ⇒ Object
Renames a staged sibling onto
path, so post ships it. -
#path(extension: nil) ⇒ Object
Names the file the operation is to write, on the first call.
-
#post ⇒ Object
Sends whatever the operation produced back out through the descriptor, and returns the byte count the cold side can now read.
Methods inherited from Descriptor
#close, #fd_path, #initialize, #staged?, #to_io
Constructor Details
This class inherits a constructor from HotCell::Descriptor
Instance Method Details
#adopt(staged) ⇒ Object
Renames a staged sibling onto path, so post ships it. A sibling the tool never wrote is left
to post's zero-byte accounting.
131 132 133 |
# File 'lib/hot_cell/descriptors.rb', line 131 def adopt(staged) File.rename staged, path if File.exist?(staged) end |
#path(extension: nil) ⇒ Object
Names the file the operation is to write, on the first call. Nothing is copied yet: post sends the file back out through the descriptor, and an operation that writes the descriptor directly never names one at all.
extension names a suffixed sibling on the same scratch instead, for a producer that picks its
saver from the extension (ImageProcessing) or appends one of its own (pdftoppm). The sibling is
not what post ships: adopt renames it into place.
124 125 126 127 |
# File 'lib/hot_cell/descriptors.rb', line 124 def path(extension: nil) base = (@path ||= scratch_path) extension.nil? ? base : "#{base}.#{extension}" end |
#post ⇒ Object
Sends whatever the operation produced back out through the descriptor, and returns the byte count
the cold side can now read. Outputs are posted and flushed before success is reported, so a
caller may read as soon as it sees ok.
Two shapes, and an operation chooses by which path it wrote. A staged output was written to path on
scratch and is copied out here; a file that does not exist means the operation wrote nothing, reported
as zero the way a full tmpfs is. An output the operation wrote straight through the descriptor was
never staged, so there is nothing to copy — the bytes are already in the caller's file — and this only
flushes and measures. The direct form leaves partial bytes in the caller's file if the operation
fails mid-write, where the staged form leaves it empty; every operation that writes directly turns a
failure into a refusal the caller acts on rather than reading those bytes as a result.
146 147 148 149 150 151 152 153 154 155 |
# File 'lib/hot_cell/descriptors.rb', line 146 def post if staged? return 0 unless File.exist?(path) File.open(path, "rb") { |file| IO.copy_stream(file, io) }.tap { io.flush } else io.flush io.stat.size end end |