Как я могу запустить Perl-скрипт от имени пользователя root, но все же повлиять на пользовательские настройки gconf - PullRequest
4 голосов
/ 06 октября 2010

НОВЫЙ ЗАПРОС: я пытаюсь создать унифицированный скрипт, который инициализирует новую установку Ubuntu по своему вкусу, для установки пакетов его нужно запустить под sudo, но использование gconftool-2 для влияния на настройку gconf зависит от сеанса dbus, которыйнеправильно обрабатывается методом простого изменения UID только в скрипте.Кто-нибудь знает, как это сделать?

СТАРЫЙ ЗАПРОС: Я пишу сценарий Perl, который будет выполняться при первой загрузке новой установки Ubuntu.Это облегчает добавление репозиториев, установку пакетов и настройку параметров gconf.Моя проблема - разрешения.Для установки пакетов мне нужно, чтобы скрипт выполнялся как sudo, но затем вызов gconftool-2 действует для пользователя root, а не для моего личного пользователя.

Ответы [ 3 ]

4 голосов
/ 06 октября 2010

Вы можете изменить идентификаторы в середине скрипта, изменив идентификатор с помощью POSIX::setuid() (см. perldoc POSIX ):

use POSIX 'setuid';

# call cpan to install modules...

POSIX::setuid($newuid);

# ... continue with script
2 голосов
/ 06 октября 2010

Вы можете снова использовать sudo для удаления своих привилегий root, например:

sudo -u 'your_username' gfconftool-2
0 голосов
/ 13 октября 2010

После долгих чтений, проб и ошибок кажется, что при запуске скрипта от имени root отсутствует то, что переменная среды DBUS_SESSION_BUS_ADDRESS не установлена.Это должно быть установлено И UID изменен на пользовательский, прежде чем настройки gconf могут быть установлены.Это мой тестовый скрипт, который я использовал, чтобы опробовать его.Выполните один или другой системный вызов в конце, чтобы изменить порядок кнопок окна.Попробуйте скрипт как пользователь или как root (sudo), чтобы увидеть, что он работает.

#!/usr/bin/perl

use strict;
use warnings;

use POSIX;

# get the user's name (as opposed to root)
my $user_name = getlogin();
# get the uid of the user by name
my $user_uid = getpwnam($user_name);
print $user_name . ": " . $user_uid . "\n";

my %dbus;
# get the DBUS machine ID
$dbus{'machine_id'} = qx{cat /var/lib/dbus/machine-id};
chomp( $dbus{'machine_id'} );
# read the user's DBUS session file to get variable DBUS_SESSION_BUS_ADDRESS
$dbus{'file'} = "/home/" . $user_name . "/.dbus/session-bus/" . $dbus{'machine_id'} . "-0";
print "checking DBUS file: " . $dbus{'file'} . "\n";
if (-e $dbus{'file'}) { 
  open(my $fh, '<', $dbus{'file'}) or die "Cannot open $dbus{file}";
  while(<$fh>) {
    if ( /^DBUS_SESSION_BUS_ADDRESS=(.*)$/ ) {
      $dbus{'address'} = $1;
      print "Found DBUS address: " . $dbus{'address'} . "\n";
    }
  }
} else {
  print "cannot find DBUS file";
}

# set the uid to the user's uid not root's
POSIX::setuid($user_uid);
# set the DBUS_SESSION_BUS_ADDRESS environment variable
$ENV{'DBUS_SESSION_BUS_ADDRESS'} = $dbus{'address'};

my $command1 = 'gconftool-2 --set "/apps/metacity/general/button_layout" --type string "menu:maximize,minimize,close"';
my $command2 = 'gconftool-2 --set "/apps/metacity/general/button_layout" --type string "menu:minimize,maximize,close"';
system($command1);
## or
#system($command2);

Примечание: получил хорошую информацию здесь .

...