c++sftplibssh2

Retrieving file names from libssh2_sftp_readdir_ex()


I am working on a C++ code that I need to list all files and directories in a path by using the libssh2_sftp_readdir_ex() function of LIBSSH2.

However, I tried to run the example (sftpdir.c) and I noticed that the code prints all files and directories along with stats, permissions and etc and I am looking for way to print only file and directories names.

Basically, I am trying get the file names from an vector of strings in C++ that contains the output generated by the libssh2_sftp_readdir_ex() command. The entries look like this:

drwxr-xr-x    2 sftpuser sftpgroup      318 Sep 29 13:33 .
drwxr-xr-x    4 root     root           36 Aug  6 22:18 ..
-rw-r--r--    1 sftpuser users         607 Aug  9 17:48 sample1.txt
-rw-r--r--    1 sftpuser users     1311881 Aug  9 17:48 sample1.docx
-rw-r--r--    1 sftpuser users       29380 Aug  9 17:48 sample1.xlsx
-rw-r--r--    1 sftpuser users      120515 Aug  9 17:48 sample2.docx
-rw-r--r--    1 sftpuser users       32924 Aug  9 17:48 sample2.xlsx
-rw-r--r--    1 sftpuser users       34375 Aug  9 17:49 sample3.docx
-rw-r--r--    1 sftpuser users        3541 Aug  9 17:49 sample3.txt
-rw-r--r--    1 sftpuser users       13246 Aug  9 17:49 sample3.xlsx
-rw-r--r--    1 sftpuser users    14169117 Aug  9 17:49 sample4.docx
-rw-r--r--    1 sftpuser users     2069007 Aug  9 17:49 sample_1280×853.png
-rw-r--r--    1 sftpuser users     4767276 Aug  9 17:49 sample_1920×1280.png
-rw-r--r--    1 sftpuser users    35898398 Aug  9 17:49 sample_5184×3456.png
-rw-r--r--    1 sftpuser users      534283 Aug  9 17:49 sample_640×426.png
-rw-r--r--    1 sftpuser users          20 Aug 31 18:56 testedown.txt

Currently I have implemented this code below that should parse each string in an vector (LSEntriesFull) to an another vector (LSEntriesBrief) that get only the file names:

const std::regex separator("\\s+");

// Each element of LSEntriesFull we need to do the parsing
for (auto & it : LSEntriesFull) {
    std::regex_token_iterator<std::string::iterator> itr(it.begin(), it.end(), separator, -1);
    std::regex_token_iterator<std::string::iterator> end;

    while (itr != end) {
        // Lets print to stderr to check if its ok
        std::cerr << " [" << *itr++ << "]";
        // TODO: Filter in an optimal way only the file names
        LSEntriesBrief.emplace_back(*itr++);    // WRONG!!! It is getting all elements
    }
}

What is the best optimal way to do this parsing in order to get only the filenames from the vector (LSEntriesFull) and to put into the other vector (LSEntriesBrief)?


Solution

  • The libssh2_sftp_readdir_ex gives you the filename via the buffer parameter. There's no need to parse the longentry.

    It's indeed not really clear from the documentation.


    You should not try to parse the longentry for any other reason. As the libssh2 documentation say:

    The format of the `longname' field is unspecified by SFTP protocol.

    The longentry is for display only (to be "parsed" by the human reader).

    Check the libssh2 sftpdir.c example. When the libssh2_sftp_readdir_ex returns any longdesc, the example code prints it as it is. When not, it assembles display information from buffer (mem in the example) and the attrs (LIBSSH2_SFTP_ATTRIBUTES).