There is a similar question about how to get the file name in C , I will present here the answer to this question in a ruby ββway.
Getting the file name in Linux
Suppose io is your input / output object. The following code gives you the file name.
File.readlink("/proc/self/fd/#{io.fileno}")
This does not work, for example, if the file was deleted after the creation of the io object. With this solution, you have a file name, but not a File object.
Getting a File Object That Does Not Know the File Name
The IO#for_fd can create IO and its subclasses for any given integer filedescriptor. Get your File object for your fd by doing the following:
File.for_fd(io.fileno)
Unfortunately, this File object does not know the file name.
File.for_fd(io.fileno).path
I looked at ruby-1.9.2 sources. There seems to be no way in a pure ruby ββto manipulate a path after creating a file object.
Getting a File object that knows the file name
An extension to ruby ββcan be created in C, which first calls File#for_fd and then processes the internal data structures of Files. This source code works for ruby-1.9.2, for other versions of ruby ββit can be configured.
#include "ruby.h" #include "ruby/io.h" VALUE file_fd_filename(VALUE self, VALUE fd, VALUE filename) { VALUE file= rb_funcall3(self, rb_intern("for_fd"), 1, &fd); rb_io_t *fptr= RFILE(rb_io_taint_check(file))->fptr; fptr->pathv= rb_str_dup(filename); return file; } void Init_filename() { rb_define_singleton_method(rb_cFile, "for_fd_with_filename", file_fd_filename, 2); }
Now you can do it after compilation:
require "./filename" f= File.for_fd_with_filename(io.fileno, File.readlink("/proc/self/fd/#{io.fileno}")) f.path
A reading link can also be placed in the definition of File#for_fd_with_filename . These examples are just to show how it works.