About Tempfile

In video controller, create action. I am using FFMPEG to generate a
thumbnail of videos that are uploaded.

The tempfile is created as such:

def create
  ......
  dst = Tempfile.new(basename)
  dst.binmode

  system("ffmpeg -itsoffset -4 -i #{file.path} -y -vcodec mjpeg -
vframes 1 -an -f rawvideo #{File.expand_path(dst.path)}.png")
  ....
end

As you can see from above, ffmpeg outputs a file to the var dst which
is an instance of Tempfile. In console, when I do:

ls /var/folders/uL/uL0bYOOZEZaJH5E+BmDJVE+++TI/-Tmp-/

thumb20101111-989-1gflwhr.png
thumb20101111-989-1pt72my.png
thumb20101111-989-kjcsgd.png
thumb20101111-989-3ocf15.png
thumb20101111-989-10azwnn.png
thumb20101111-989-7x11w7.png

I see a bunch of files in the directory. It seems that rails did not
automatically delete these temp files. Should I manually delete these
files?

I am worried that, if my temp dir fills up with temp files, it'll
eventually take up most of the server space...

Your thoughts on this matter?

When you close the Tempfile, be sure to pass true for unlink_now.

http://ruby-doc.org/stdlib/libdoc/tempfile/rdoc/classes/Tempfile.html#M004418

Hi Brian,

Just to keep things clear. By the end of the day, /var/folders/uL/
uL0bYOOZEZaJH5E+BmDJVE+++TI/-Tmp-/ <-- temp dir _IS_ supposed to be
empty. Is this correct?

Hi Christian,

Not by the end of the day, no. Each tempfile will be unlinked as soon
as you close it. Your example code didn't have the line

dst.close(unlink_now=true)

in it. You may also use dst.close!() to the same effect.

Ok that makes sense. Thanks Brian.

On the same topic...

How would I create a temp file with .png extension in the end.

tmp = Tempfile.new([ 'thumb', 'png' ].compact.join("."))

Whenever it creates a temp file, it creates it as such:
thumb.png20101111-989-1pt72my, instead of
thumb20101111-989-1pt72my.png

If I try to save this via Active Record, with

@video.attachment_thumbnail =
File.open("#{File.expand_path(tmp.path)}"),

It will save the file in the file system without the extension, which
makes it impossible to read on the browser, unless I explicitly set
the extension.

I'm confused. You're creating a tempfile and then keeping a reference
to it in your database?

Ok that makes sense. Thanks Brian.

On the same topic...

How would I create a temp file with .png extension in the end.

tmp = Tempfile.new([ 'thumb', 'png' ].compact.join("."))

You can't use Tempfile to do this. Well, you _can_ but you'll need to
close the file--without unlinking it!--and then move the file created
to the new location you want. At that points, you're better off just
giving thumbnails a sequential identifier, or use their hash. Destroy
the thumbnail file once you no longer need it.

No, the following saves the temp file.

@video.attachment_thumbnail =
File.open(File.expand_path(tmp.path))

However, File.expand_path(tmp.path) saves the file in the file system
as thumb.png20101111-989-1pt72my

Ideally, I would like it to save it as thumb20101111-989-1pt72my.png
or, better, just thumb.png

Basically I need to create a new tempfile with a png extension. Is
this possible?

No, the following saves the temp file.

@video.attachment_thumbnail =
File.open(File.expand_path(tmp.path))

Ah, apologies.

However, File.expand_path(tmp.path) saves the file in the file system
as thumb.png20101111-989-1pt72my
Ideally, I would like it to save it as thumb20101111-989-1pt72my.png

Okay, so you've got this:

tmp = Tempfile.new([ 'thumb', 'png' ].compact.join("."))

The documentation for Tempfile states that .new "creates a temporary
file of mode 0600 in the temporary directory whose name is
basename.pid.n and opens with mode "w+". A Tempfile object works just
like a File object." The computer is doing exactly what you tell it to
do.

or, better, just thumb.png

Would not this conflict if you have multiple users uploading files at
the same time?

Yes, but not with Tempfile. Hash the video data, store your thumbnail
as $HASH.png, keep a reference to this file and be sure to delete it
when the user performs such actions as make the thumbnail no longer
necessary.

Would not this conflict if you have multiple users uploading files at

the same time?

Yea, thinking along those lines. It would conflict. So if tmp =
Tempfile.new([ 'thumb', 'png' ].compact.join(".")) creates temp files
as thumb.png20101111-989-1pt72my, how would I tell Active Record to
save it with a .png extension, since it is a png file after all.

Remember, @video.attachment_thumbnail =
File.open(File.expand_path(tmp.path)), saves the file in the file
system as thumb.png20101111-989-1pt72my (raw file, no extension)

Yes, but not with Tempfile.

There wont be any conflicts?

Hash the video data, store your thumbnail as $HASH.png, keep a reference to this file

Can you give me an example of how I would $HASH a file? How do you
mean "keep a reference to this file"?