I have a situation here in which I create temp files from Ruby in the user folder. I am using Dir.mktmpdir()
to create a temporary folder I am putting my files into.
For some reason, that function gives me a windows short folder name, so in instead of e.g. C:\Users\very long username\AppData\Local\Temp\20181018-5548
I get something like C:\Users\VERYLO~1\AppData\Local\Temp\20181018-5548
. This is the original root cause of my problem, but my impression is that I can't really fix this, because I have to work in an environment that I don't have a lot of control over (Ruby 2.0 and 2.2 embedded into SketchUp to be exact). This also limits the amount of external Ruby libraries I can sensibly bring in.
To get the actual long folder name, I have been calling the Win32 function GetLongPathName()
through the WIN32API
class and that has been largely successful.
However, I am running into trouble with special characters. It seems like the buffers I send to the Win32 API (and the return buffers as well) are expected to be in a certain encoding and the Ruby strings are UTF-8 (or assume the return values to be UTF-8). I'd gladly facilitate any change in encoding, but I am somewhat lost in terms of which encoding to go for. I am not even sure whether the wide character version of the Win32 API is being used.
There is something that adds to the weirdness and makes me wonder whether I may be barking up the wrong tree: Using an international and/or English version of Windows I can actually send and receive all kinds of special characters into the Win32 API call without problems. However, as soon as I use a different language edition of Windows (I tried Brazilian Portugese, but we had people with Hebrew and some eastern-european Windows editions report this problem as well), it stops working.
def self.get_long_win32_filename(short_name)
require 'Win32API'
max_path = 1024
long_name = " " * max_path
lfn_size = Win32API.new("kernel32", "GetLongPathName", ['P','P','L'],'L').call(short_name, long_name, max_path)
return (1..max_path).include?(lfn_size) ? long_name[0..lfn_size-1] : short_name
end
Here is the code I am using:
Any help in figuring out how to approach the encoding problem when passing strings into and out of the Win32 API very much appreciated!