Как я могу прочитать папку, принадлежащую пользователю root, с помощью Vala?

Я пытаюсь прочитать путь /var/cache/apt/archives со следующими разрешениями:

drwxr-xr-x 3 root root 90112 ago 2 14:36 archives

И я получил следующую ошибку:

ERROR: Error opening directory '/var/cache/apt/archives/partial': Permission denied

Может ли кто-нибудь помочь мне с этим?

Исходный код следующий:

using Gtk;
using GLib;

private int64[] get_folder_data (File file, string space = "",     Cancellable? cancellable = null) throws Error
{
    FileEnumerator enumerator = file.enumerate_children (
    "standard::*",
    FileQueryInfoFlags.NOFOLLOW_SYMLINKS, 
    cancellable);

    int64 files = 0;
    int64 size  = 0;
    int64[] data = new int64[2];
    FileInfo info = null;

    while (cancellable.is_cancelled () == false && ((info = enumerator.next_file (cancellable)) != null)) {
        if (info.get_file_type () == FileType.DIRECTORY) {
            File subdir = file.resolve_relative_path (info.get_name ());
            get_folder_data (subdir, space + " ", cancellable);
        } else {
            files += 1;//Sum Files
            size  += info.get_size ();//Accumulates Size
        }
    }

    if (cancellable.is_cancelled ()) {
        throw new IOError.CANCELLED ("Operation was cancelled");
    }

    data[0] = files;
    data[1] = size;

    stdout.printf ("APT CACHE SIZE: %s\n", files.to_string());
    stdout.printf ("APT CACHE FILES: %s\n", size.to_string());

    return data;
}

public static int main (string[] args) {
    Gtk.init (ref args);

    File APT_CACHE_PATH = File.new_for_path ("/var/cache/apt/archives");
    try {
        get_folder_data (APT_CACHE_PATH, "", new Cancellable ());
    } catch (Error e) {
        stdout.printf ("ERROR: %s\n", e.message);    
    }
    Gtk.main ();
    return 0;
}

И команда, которую я использовал для компиляции, выглядит следующим образом:

valac --pkg gtk+-3.0 --pkg glib-2.0 --pkg gio-2.0 apt-cache.vala

1 ответ

Решение

Если вы запускаете свое приложение как обычный пользователь, вы должны исключить "частичный" каталог, у него есть более ограничительные разрешения (0700):

drwx------ 2 _apt root 4096 Jul 29 11:36 /var/cache/apt/archives/partial

Один из способов исключить частичный каталог - это просто игнорировать любой каталог, который недоступен:

int64[] data = new int64[2];
FileEnumerator enumerator = null;
try {
    enumerator = file.enumerate_children (
        "standard::*",
        FileQueryInfoFlags.NOFOLLOW_SYMLINKS,
        cancellable);
}
catch (IOError e) {
    stderr.printf ("WARNING: Unable to get size of dir '%s': %s\n", file.get_path (), e.message);
    data[0] = 0;
    data[1] = 0;
    return data;
}

Кроме того, было бы неплохо всегда явно игнорировать частичную папку.

Если вы планируете сделать вашу утилиту полезной и для пользователя root, вы можете даже подумать о добавлении параметра командной строки, такого как --include-partal-dir.

Также то же самое можно сделать с помощью простых команд bash, что намного проще, чем написание вашей собственной программы.

du -sh /var/cache/apt/archives
find /var/cache/apt/archives -type f | wc -l

Обратите внимание, что du а также find Также предупреждаем о недоступной частичной директории:

$ du -sh /var/cache/apt/archives
du: cannot read directory '/var/cache/apt/archives/partial': Permission denied
4.6G    /var/cache/apt/archives

$ find /var/cache/apt/archives -type f | wc -l
find: '/var/cache/apt/archives/partial': Permission denied
3732
Другие вопросы по тегам