file_exists() and file_get_contents() fail

2020-02-02 00:38发布

问题:

file_exists() and file_get_contents() fail on a file which is named output‹ÕÍÕ¥.txt (as an example), although I know it exists?

I'm guessing its got something to do with the special characters within the file name?.

So was wondering whats a workaround?

Appreciate all responses.

FYI:

Please note, if your thinking why not simply change the file name? - I can't as the file name is generated generically, and to change the file name will be mean using PHP's file functions (which don't seem to allow special characters within the file name args - unless I've misinterpreted/misunderstood anything).

I'm using PHP 5.2 on Windows.

回答1:

Ensure that the encoding of the file-system is the same as the encoding of the string that contains the file-name in your PHP code.

Otherwise you're testing for the wrong file to exist.

For example, if your file-system does not support UTF-8 but the file-name is encoded in UTF-8.

Edit:

So you have commented that the filename is in UTF-8 and you're using windows.

That's exactly the point my answer was about. As written here:

Bad news for Windows Users: Windows filesystems (FAT, FAT32, NTFS) are not UTF-8 aware. Filenames are encoded in ISO-8859-1 or CP437/CP850/( or whatever suits your language) depending on filesystem and localisation. So you will probably get in trouble trying to match filenames from database to filesystem if you follow this guide. (Although I've never tried it.)

Windows workaround: Modern windows versions support UTF-8 on mounted shares. Make a share of your mediafolder and mount it as a network drive.

So either make a share or encode the filename in the encoding that actually works with your filesystem. This is not a bug in PHP. You're just no checking for the right file-name, that's all.

Edit2:

Assuming you have NTFS which might accept UTF-16 (which is not really precise AFAIK, but you can give it a try), you could convert the UTF-8 filename into an UTF-16 fiĺename:

$name = mb_convert_encoding($name, 'UTF-16', 'UTF-8');

And then try if file_exists works. Keep in mind that his might not be technically correct, and you might have an additional encoding issue which prevents you from correct use even with this re-encoding.

Related: What encoding are filenames in NTFS stored as?