Search code examples
node.jsmacoshiddenmodestat

How to detect hidden files with node.js on OS X


Poking around I was unable to discover a way to detect hidden files in OS X with node (nodejs).

Of course, we can easily find the ".dot_hidden" files, but on the Mac, there are files/folders that are "protected" system files, that most users shouldn't fiddle with. In the Finder GUI, they are invisible or grey'd out when hidden files are forced to be shown via "AppleShowAllFiles".

I did discover a reference to UF_HIDDEN : 0x8000 here:

https://developer.apple.com/library/mac/documentation/FileManagement/Conceptual/FileSystemProgrammingGuide/FileSystemDetails/FileSystemDetails.html

Using node's stat, we can return 2 additional bits of info that may provide a clue for the hidden status:

mode: 33188,       // File protection.
ino: 48064969,     // File inode number. An inode is a file 
                      system data structure that stores 
                      information about a file.

I'm not really a hex / binary guy, but it looks like grabbing the stat's "ino" property we can apply 0x8000 and determine if the file is being hinted as hidden or not.

I didn't have any success with the 0x8000 mask on the mode, but did have some with ino.

Here's what I've got, checking the "ino" returns 0 or 1726, when it's 1726 the file seems to match as a hidden file in OS X.

var fs = require("fs");

var dir = "/";
var list = fs.readdirSync(dir);

list.forEach(function(f){

    // easy dot hidden files
    var hidden = (f.substr(0, 1) == ".") ? true : false;

    var ino = 0;
    var syspath = dir + "/" + f;
    if( ! hidden ){
        var stats = fs.statSync(syspath);

        ino = parseInt( stats.ino & 0x8000, 8);

        // ino yeilds 0 when hidden and 1726 when not?

        if(ino || dotted){
            hidden = true;
        }
    }

    console.log(syspath, hidden, ino);

});

So my question is if I'm applying the 0x8000 mask properly on the ino value to yeild a proper result?

And how would one go about parsing the ino property get at all the other flags contained within it?


Solution

  • The inode number (stats.ino) is a number which uniquely identifies a file; it has nothing to do with the hidden status of the file. (Indeed, it's possible to set or clear the hidden flag on a file at any time, and this won't change the inode number.)

    The hidden flag is part of the st_flags field in the struct stat structure. Unfortunately, it doesn't look like the node.js fs module exposes this value, so you may need to shell out to the stat shell utility if you need to get this information on Mac OS X. (Short version: stat -f%f file will print a file's flags, represented in decimal.)