Forum OpenACS Q&A: Retrieve object_id of System Owner?

Collapse
Posted by Randy O'Meara on
Is there a relatively straightforward way to obtain the object_id (same as persons.person_id) of the System Owner (the initial site administrator)?

The reason I ask is that I want to give ownership of a high-level object to the system owner when I create the object on a package's "after_install" callback.

Randy

Collapse
Posted by Brad Duell on
This would just be the min(person_id) > 0, would it not?

select min(person_id) from persons where person_id>0;

Collapse
Posted by Peter Marklund on
I like the min() approach. Here is what I would do:

set context_root_id [db_string select_context_root_id {
    select acs.magic_object_id('default_context') from dual
}]

set admin_user_id [db_string select_admin_user_id {
    select min(user_id)
    from users
    where acs_permission.permission_p(:context_root_id, user_id, 'admin') = 't'
}]

Collapse
Posted by Jeff Davis on
I would argue for making the "system owner" an entry
in acs_magic_objects, but if that seems appalling and you
prefer Peter's method you should probably do it with a
join to the permission view rather than with the permission_p
function (which will force a table scan on users).
Collapse
Posted by Randy O'Meara on
Thank you all.

I did look for a magic object before I asked the question and saw several useful pieces of information stored there, but this was not one of them.

I guess by "the permissions view" you mean acs_permissions_all? Is there any reason that I shouldn't also join with the acs_magic_objects table? Something like:

    set admin_user_id [db_string select_admin_user_id {
	select min(user_id)
	from users u, acs_permissions_all p, acs_magic_objects a
	where u.user_id = p.grantee_id
	and p.object_id = a.object_id
	and a.name = 'default_context'
    }]
Collapse
Posted by Randy O'Meara on
The query above returns the proper object_id. But in the process of going through this exercise, I found that I had overlooked something...

If a package is being installed through the install.xml facility, the admin user object does not yet exist. The admin user account is created after all core packages and install.xml packages have been installed. I guess one way to lick this problem would be to establish the admin user object_id in the acs_magic_objects table. Or, I could create my own magic object and then later, after the admin user exists, change ownership of my object to the admin user.

My question is this: is there an established and/or supported method for packages to allocate a magic object?

Collapse
Posted by Dave Bauer on
Randy,

Can you explain why the site-wide admin needs to "own" an object?  Being site-wide admin means you have admin privilege over every object.

Besides that, I think defining the sitewide admin as a magic object is a great idea.

Collapse
Posted by Randy O'Meara on
Well, not exactly "ownership", full admin to the creator of the object.

During package installation, the after_install APM callback causes a special administrative instance of the package to be instantiated. Through this instance of the package, common site-wide objects are created and maintained. Objects created here are normally accessible (read-only) to every other instance of the package. Some of these common objects are created during package installation.

Object creation pl/pgsql functions first create an acs_object and then grant admin rights to the creating user. Like so:

	PERFORM acs_permission__grant_permission(
          v_id,
          p_creation_user,
          ''admin''
There must be a creation (grantee) user otherwise the following error is generated.
    ERROR:  ExecInsert: Fail to add null value in not null attribute grantee_id
There is no creation_user at the time that the after_install callback is invoked. Actually, there are no users whatsoever at this time. This acs_permission call is (if I recall) a carryover from the excellent package authoring tutorial and I just carried it along to all of my object creation functions.

I have been looking for an elegant solution but there is none that I can find unless the admin user's id becomes a magic object. Maybe I don't really need to have the acs_permission call at all?

Collapse
Posted by Jeff Lu on
Im having the same problem as well in looking for the right way in getting the system owners id. It seems that im using the same approach as you. Currently I also use the min approach.
Collapse
Posted by Jeff Lu on
Hi Randy. It seems we ran into the same problem. I also need a good way of getting the system owners id. Currently im also using the min approach. But i think the system owner id should fit in as a magic var and should be created during the bootstrap. anybody has any suggestions on this?
Collapse
Posted by Randy O'Meara on
Jeff, the following works but I'm not using it any longer. I solved my problem by removing the grant call.

Randy

ad_proc -private admin_user_id_get {} {

    Return the user_id (object_id) of the System Owner account.
    May be able to simplify and streamline the query used to 
    retrieve this info if bootstrap-installer patched to save
    this user_id in the acs_magic_objects table.

    @see https://openacs.org/forums/message-view?message_id=118128
} {
    return [db_string admin_user_id {
      select
      	min(user_id)
      from users u, acs_permissions_all p, acs_magic_objects a
      where u.user_id = p.grantee_id
      and p.object_id = a.object_id
      and a.name = 'default_context'
    }]
}