The Python example below is an almost line-by-line port of the original, but it should give you a basic idea on how to use the API for your own scripts.
#! /usr/bin/env python import sys, os from gi.repository import GObject, Gio, Polkit def on_tensec_timeout(loop): print("Ten seconds have passed. Now exiting.") loop.quit() return False def check_authorization_cb(authority, res, loop): try: result = authority.check_authorization_finish(res) if result.get_is_authorized(): print("Authorized") elif result.get_is_challenge(): print("Challenge") else: print("Not authorized") except GObject.GError as error: print("Error checking authorization: %s" % error.message) print("Authorization check has been cancelled " "and the dialog should now be hidden.\n" "This process will exit in ten seconds.") GObject.timeout_add(10000, on_tensec_timeout, loop) def do_cancel(cancellable): print("Timer has expired; cancelling authorization check") cancellable.cancel() return False if __name__ == "__main__": if len(sys.argv) != 2: print("usage: %s <action_id>" % sys.argv[0]) sys.exit(1) action_id = sys.argv[1] mainloop = GObject.MainLoop() authority = Polkit.Authority.get() subject = Polkit.UnixProcess.new(os.getppid()) cancellable = Gio.Cancellable() GObject.timeout_add(10 * 1000, do_cancel, cancellable) authority.check_authorization(subject, action_id, #"org.freedesktop.policykit.exec", None, Polkit.CheckAuthorizationFlags.ALLOW_USER_INTERACTION, cancellable, check_authorization_cb, mainloop) mainloop.run()
In order to run this example, make sure you have the gir1.2-polkit-1.0 package installed and provide an action in the command line, for example:
./polkit-test org.freedesktop.policykit.exec
I suppose, the API is still a little rough on the edges, but it's already usable and I'm going to try it for an upcoming D-Bus service in indicator-cpufreq. Looks like it's perfect time to start moving things to GObject introspection already.
Many thanks! But I've not understan one thing: one time we get the authorization where to put the code?
ReplyDelete(example: append a string to a system file owned by root)
we must still create a dbus method?
thanks again
No, just insert your code or a method call into the check_authorization_cb (if result.get_is_authorized() clause).
ReplyDeleteI get this:
ReplyDelete[fabio@hp6735b Materiale]$ python polkit_test.py
Authorized
Traceback (most recent call last):
File "polkit_test.py", line 16, in check_authorization_cb
my_func()
File "polkit_test.py", line 35, in my_func
f = open('/etc/test','a')
IOError: [Errno 13] Permission denied: '/etc/test'
Timer has expired; cancelling authorization check
Ah, I see. You're running the process as a regular user here. Not sure if it's possible to temporary give root privileges to a user process with polkit, as I only tried this method with a dbus service (which is running as root).
ReplyDeleteThis way, the service will be able to write into /etc/test anytime you call the dbus method, but it will also check if the caller is allowed to perform this action (or ask to enter the sudo password). I think this behaviour may be configured in the busconfig file for the service either, but not sure about this.
thanks, the problem is that I make much confusion between dbus and policykit and I can't figure out how to solve my problem...
ReplyDeleteMy hope whose that with this method I don't have to use dbus.
can you provide an example? I don't know where to break my head :)
ReplyDeleteyep, look at jockey or indicator-cpufreq (both have a dbus service to change things).
Delete