# Chef12: knife user show to non-admin users

**URL:** <https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194>\
**Category:** Chef Infra (archive)\
**Created:** [January 22, 2015, 7:51pm UTC](https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194 "2015-01-22T19:51:34Z")\
**Posts on this page:** 6\
**Page:** 1

<div class="post-metadata">

**Author:** ![Tiago\_Cruz](https://sea2.discourse-cdn.com/flex016/user_avatar/discourse.chef.io/tiago_cruz/32/49_2.png) [@Tiago\_Cruz](https://discourse.chef.io/u/Tiago_Cruz)\
**Post date:** [January 22, 2015, 7:51pm UTC](https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194/1 "2015-01-22T19:51:34Z")

</div>

Hello,

There is some way to give non-admins users permission to use ‘knife user  
show’?

$ knife user show xxx -VV  
DEBUG: Chef::HTTP calling Chef::HTTP::JSONInput#handle\_request  
DEBUG: Chef::HTTP calling Chef::HTTP::JSONToModelOutput#handle\_request  
DEBUG: Chef::HTTP calling Chef::HTTP::CookieManager#handle\_request  
DEBUG: Chef::HTTP calling Chef::HTTP::Decompressor#handle\_request  
DEBUG: Chef::HTTP calling Chef::HTTP::Authenticator#handle\_request  
DEBUG: Signing the request as jaum  
DEBUG: Chef::HTTP calling Chef::HTTP::RemoteRequestID#handle\_request  
DEBUG: Chef::HTTP calling Chef::HTTP::ValidateContentLength#handle\_request  
DEBUG: Initiating GET to  
[https://chef-host/organizations/organization/users/truta](https://chef-host/organizations/organization/users/truta)  
DEBUG: ---- HTTP Request Header Data: ----  
DEBUG: Accept: application/json  
DEBUG: Accept-Encoding: gzip;q=1.0,deflate;q=0.6,identity;q=0.3  
DEBUG: X-OPS-SIGN: algorithm=sha1;version=1.0;  
DEBUG: X-OPS-USERID: jaum  
DEBUG: X-OPS-TIMESTAMP: 2015-01-22T19:42:02Z  
DEBUG: X-OPS-CONTENT-HASH: 2jmj7l5rSw0yVb/vlWAYkK/YBwk=  
DEBUG: X-OPS-AUTHORIZATION-1:  
GsGVBloLX88PUr+OygGRf/JfqenGh2ZHvGS5LXEIehw/+Xu8Xgi5QYGK9lDs  
DEBUG: X-OPS-AUTHORIZATION-2:  
lQ6NGPt4AoiglpTuQUJnyP8rhPLEeNlMmh3hxBbGMlWHzTOqWsHvPLlbAg6e  
DEBUG: X-OPS-AUTHORIZATION-3:  
H7uWraSg882f26xXDkFJOhu/loBD3jZ51eCsyEJwJkkPhlOG8yVmNrgzn2cV  
DEBUG: X-OPS-AUTHORIZATION-4:  
sKvwKHJwAu5UUGHrNcyKeH1SPlWYHZFhL0lEMb6lwDxZA7O5nKJu9RE/nEPc  
DEBUG: X-OPS-AUTHORIZATION-5:  
FKYframg47s+uPYjrb9MjH5AjtAK3DBA1dZxXrTFTEeB2rtWNjrSAVNE0O5I  
DEBUG: X-OPS-AUTHORIZATION-6: GlqUUlBuXa0j/Er52tIMJBl0Fav4cwGK5tNx1DniNQ==  
DEBUG: HOST: chef-host:443  
DEBUG: X-REMOTE-REQUEST-ID: 1fb2cc5a-25a4-483a-b4e5-adaedb01d80a  
DEBUG: ---- End HTTP Request Header Data ----  
DEBUG: ---- HTTP Status and Header Data: ----  
DEBUG: HTTP 1.1 403 Forbidden  
DEBUG: server: ngx\_openresty/1.4.3.6  
DEBUG: date: Thu, 22 Jan 2015 19:42:01 GMT  
DEBUG: content-length: 37  
DEBUG: connection: close  
DEBUG: x-ops-api-info: flavor=cs;version=12.0.0;oc\_erchef=0.29.4  
DEBUG: ---- End HTTP Status/Header Data ----  
DEBUG: Chef::HTTP calling Chef::HTTP::ValidateContentLength#handle\_response  
DEBUG: Content-Length validated correctly.  
DEBUG: Chef::HTTP calling Chef::HTTP::RemoteRequestID#handle\_response  
DEBUG: Chef::HTTP calling Chef::HTTP::Authenticator#handle\_response  
DEBUG: Chef::HTTP calling Chef::HTTP::Decompressor#handle\_response  
DEBUG: Chef::HTTP calling Chef::HTTP::CookieManager#handle\_response  
DEBUG: Chef::HTTP calling Chef::HTTP::JSONToModelOutput#handle\_response  
DEBUG: Expected JSON response, but got content-type '‘  
DEBUG: Chef::HTTP calling Chef::HTTP::JSONInput#handle\_response  
INFO: HTTP Request Returned 403 Forbidden: error  
/opt/chefdk/embedded/lib/ruby/2.1.0/net/http/response.rb:119:in `error!': 403 "Forbidden" (Net::HTTPServerException) from /opt/chefdk/embedded/apps/chef/lib/chef/http.rb:145:in`request’  
from /opt/chefdk/embedded/apps/chef/lib/chef/rest.rb:115:in `get' from /opt/chefdk/embedded/apps/chef/lib/chef/user.rb:164:in`load’  
from /opt/chefdk/embedded/apps/chef/lib/chef/knife/user\_show.rb:43:in `run' from /opt/chefdk/embedded/apps/chef/lib/chef/knife.rb:493:in`run\_with\_pretty\_exceptions’  
from /opt/chefdk/embedded/apps/chef/lib/chef/knife.rb:174:in `run' from /opt/chefdk/embedded/apps/chef/lib/chef/application/knife.rb:139:in`run’  
from /opt/chefdk/embedded/apps/chef/bin/knife:25:in `<top (required)>' from /usr/bin/knife:33:in`load’  
from /usr/bin/knife:33:in `’

## Thanks!!

– Tiago Cruz

---

<div class="post-metadata">

**Author:** ![Tiago\_Cruz](https://sea2.discourse-cdn.com/flex016/user_avatar/discourse.chef.io/tiago_cruz/32/49_2.png) [@Tiago\_Cruz](https://discourse.chef.io/u/Tiago_Cruz)\
**Post date:** [January 23, 2015, 11:08am UTC](https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194/2 "2015-01-23T11:08:32Z")

</div>

I tried to

$ knife acl add groups users read group vault-admins

And put my users on 'vault-admins' group, but does not work ☹

The problem is: knife-vault needs to get _public key_ of the users to  
generate the hash.

If the guy is a non-admin, he only can generate for his own, and I can't  
see the key:

$ knife vault show reliability portability-credentials  
ERROR: ChefVault::Exceptions::SecretDecryption:  
reliability/portability-credentials is not encrypted with your public key.  
Contact an administrator of the vault item to encrypt for you!

And the guy who did, can't generate to me because the can't see my private  
key using 'knife user show tiago\_cruz'

So, how can I give him access to my private\_key?

Thanks a lot!

On Thu, Jan 22, 2015 at 5:51 PM, Tiago Cruz [tiago.tuxkiller@gmail.com](mailto:tiago.tuxkiller@gmail.com)  
wrote:

> Hello,
> 
> There is some way to give non-admins users permission to use 'knife user  
> show'?
> 
> $ knife user show xxx -VV  
> DEBUG: Chef::HTTP calling Chef::HTTP::JSONInput#handle\_request  
> DEBUG: Chef::HTTP calling Chef::HTTP::JSONToModelOutput#handle\_request  
> DEBUG: Chef::HTTP calling Chef::HTTP::CookieManager#handle\_request  
> DEBUG: Chef::HTTP calling Chef::HTTP::Decompressor#handle\_request  
> DEBUG: Chef::HTTP calling Chef::HTTP::Authenticator#handle\_request  
> DEBUG: Signing the request as jaum  
> DEBUG: Chef::HTTP calling Chef::HTTP::RemoteRequestID#handle\_request  
> DEBUG: Chef::HTTP calling Chef::HTTP::ValidateContentLength#handle\_request  
> DEBUG: Initiating GET to  
> [https://chef-host/organizations/organization/users/truta](https://chef-host/organizations/organization/users/truta)  
> DEBUG: ---- HTTP Request Header Data: ----  
> DEBUG: Accept: application/json  
> DEBUG: Accept-Encoding: gzip;q=1.0,deflate;q=0.6,identity;q=0.3  
> DEBUG: X-OPS-SIGN: algorithm=sha1;version=1.0;  
> DEBUG: X-OPS-USERID: jaum  
> DEBUG: X-OPS-TIMESTAMP: 2015-01-22T19:42:02Z  
> DEBUG: X-OPS-CONTENT-HASH: 2jmj7l5rSw0yVb/vlWAYkK/YBwk=  
> DEBUG: X-OPS-AUTHORIZATION-1:  
> GsGVBloLX88PUr+OygGRf/JfqenGh2ZHvGS5LXEIehw/+Xu8Xgi5QYGK9lDs  
> DEBUG: X-OPS-AUTHORIZATION-2:  
> lQ6NGPt4AoiglpTuQUJnyP8rhPLEeNlMmh3hxBbGMlWHzTOqWsHvPLlbAg6e  
> DEBUG: X-OPS-AUTHORIZATION-3:  
> H7uWraSg882f26xXDkFJOhu/loBD3jZ51eCsyEJwJkkPhlOG8yVmNrgzn2cV  
> DEBUG: X-OPS-AUTHORIZATION-4:  
> sKvwKHJwAu5UUGHrNcyKeH1SPlWYHZFhL0lEMb6lwDxZA7O5nKJu9RE/nEPc  
> DEBUG: X-OPS-AUTHORIZATION-5:  
> FKYframg47s+uPYjrb9MjH5AjtAK3DBA1dZxXrTFTEeB2rtWNjrSAVNE0O5I  
> DEBUG: X-OPS-AUTHORIZATION-6: GlqUUlBuXa0j/Er52tIMJBl0Fav4cwGK5tNx1DniNQ==  
> DEBUG: HOST: chef-host:443  
> DEBUG: X-REMOTE-REQUEST-ID: 1fb2cc5a-25a4-483a-b4e5-adaedb01d80a  
> DEBUG: ---- End HTTP Request Header Data ----  
> DEBUG: ---- HTTP Status and Header Data: ----  
> DEBUG: HTTP 1.1 403 Forbidden  
> DEBUG: server: ngx\_openresty/1.4.3.6  
> DEBUG: date: Thu, 22 Jan 2015 19:42:01 GMT  
> DEBUG: content-length: 37  
> DEBUG: connection: close  
> DEBUG: x-ops-api-info: flavor=cs;version=12.0.0;oc\_erchef=0.29.4  
> DEBUG: ---- End HTTP Status/Header Data ----  
> DEBUG: Chef::HTTP calling Chef::HTTP::ValidateContentLength#handle\_response  
> DEBUG: Content-Length validated correctly.  
> DEBUG: Chef::HTTP calling Chef::HTTP::RemoteRequestID#handle\_response  
> DEBUG: Chef::HTTP calling Chef::HTTP::Authenticator#handle\_response  
> DEBUG: Chef::HTTP calling Chef::HTTP::Decompressor#handle\_response  
> DEBUG: Chef::HTTP calling Chef::HTTP::CookieManager#handle\_response  
> DEBUG: Chef::HTTP calling Chef::HTTP::JSONToModelOutput#handle\_response  
> DEBUG: Expected JSON response, but got content-type ''  
> DEBUG: Chef::HTTP calling Chef::HTTP::JSONInput#handle\_response  
> INFO: HTTP Request Returned 403 Forbidden: error  
> /opt/chefdk/embedded/lib/ruby/2.1.0/net/http/response.rb:119:in `error!': 403 "Forbidden" (Net::HTTPServerException) from /opt/chefdk/embedded/apps/chef/lib/chef/http.rb:145:in `request'  
> from /opt/chefdk/embedded/apps/chef/lib/chef/rest.rb:115:in `get' from /opt/chefdk/embedded/apps/chef/lib/chef/user.rb:164:in `load'  
> from /opt/chefdk/embedded/apps/chef/lib/chef/knife/user\_show.rb:43:in `run' from /opt/chefdk/embedded/apps/chef/lib/chef/knife.rb:493:in `run\_with\_pretty\_exceptions'  
> from /opt/chefdk/embedded/apps/chef/lib/chef/knife.rb:174:in `run' from /opt/chefdk/embedded/apps/chef/lib/chef/application/knife.rb:139:in `run'  
> from /opt/chefdk/embedded/apps/chef/bin/knife:25:in `<top (required)>' from /usr/bin/knife:33:in `load'  
> from /usr/bin/knife:33:in `'
> 
> ## Thanks!!
> 
> -- Tiago Cruz

--  
-- Tiago Cruz

---

<div class="post-metadata">

**Author:** ![ssd](https://avatars.discourse-cdn.com/v4/letter/s/7993a0/32.png) [@ssd](https://discourse.chef.io/u/ssd)\
**Post date:** [January 24, 2015, 1:21am UTC](https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194/3 "2015-01-24T01:21:21Z")

</div>

Hi Tiago,

The short story is that this may be impossible without talking  
directly to the internal SQL database and/or the bifrost (internal  
authorization system) API. I’ve explained a bit below. The  
explanation may be a bit terse for those on the list who haven’t used  
the RBAC system much.

To read a user’s private key, you need to have the read permission on  
the user itself either by being directly in the read ACE for that user  
object or in a group that is in the read ACE. Adding your  
vault-admins group to the read ACE of the users group won’t provide  
the permissions you need since it doesn’t give you any permission on  
the members of that group, simply on the group object itself.

The read ACE for a user Mary in the organization acme looks like this:

```
mary > knife raw -s 'https://api.opscode.piab/' 'users/mary/_acl' | jq .read
{
  "actors": [
    "pivotal",
    "mary"
  ],
  "groups": [
    "acme_global_admins"
  ]
}

```

When Mary is associated to an organization, a special group is added  
to the READ ace of the user. The group is in the form of  
ORGNAME\_global\_admin and contains the admin group of the organization.  
When she is disassociated from the org, that group is removed from her  
read ACE. Since the admin users are in the admin group, the admin  
group is in the acme\_global\_admins group, and the acme\_global\_admins  
is in the read ACE of the user, an admin user can read Mary’s user  
object.

Now, knowing this, to give your users access to read each others’ keys  
you might try:

1. Adding the users group to the acme\_global\_admins group
2. Adding a given user to the “actors” section of the user’s read ace
3. Adding some arbitrary other group that contains the users to the  
groups section of the users read ace

Unfortunately,

a) It appears Chef 12 has a bug such that you can’t update a user’s  
acl without removing the ORGNAME\_global\_admin group from the ACL.  
This would break the access that org admins have by default and would  
put you in a situation that isn’t likely well tested. [0]

b) You can’t add actors or groups to the ORGNAME\_global\_admin group  
because that group doesn’t exist inside an organization and thus  
simply isn’t reachable via an API endpoint.

Option (1) above is likely doable with a script that directly  
manipulates some of the backend services [1].

I hope this help.

Cheers,

Steven

[0] Updating user ACLs worked in 11.2.x so I’ll likely be following up  
internally and filing a bug.  
[1] By likely doable, I mean completely doable:

> <https://gist.github.com/stevendanna/1eb99f01a2f0f22ba619>

You can use it like this from your Chef Server:

./danger\_add\_users\_to\_global\_admins\_group acme

HOWEVER, please note that (1) this is messing with internal  
implemntation details and it will probably break, (2) I haven’t  
audited what other permissions those users will get, and (3) I haven’t  
audited edge cases of users being associated and disassociated from  
orgs. Basically I ran it once and it worked.

---

<div class="post-metadata">

**Author:** ![Tiago\_Cruz](https://sea2.discourse-cdn.com/flex016/user_avatar/discourse.chef.io/tiago_cruz/32/49_2.png) [@Tiago\_Cruz](https://discourse.chef.io/u/Tiago_Cruz)\
**Post date:** [January 26, 2015, 12:11pm UTC](https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194/4 "2015-01-26T12:11:04Z")

</div>

Hello Steven, thanks again!

Just to clarify: The group 'acme\_global\_admins' has the same privileges  
than the 'admin' default group?

Because if I just put the user in admin group, the 'knife user show' works,  
and so he is able to use 'knife vault' using the option:

knife[:vault\_admins] = ['user\_a', 'user\_b', 'user\_c']

So the key will be manageable to more than one person (this is good for us!)

Thanks a lot!

On Fri, Jan 23, 2015 at 11:21 PM, Steven Danna [steve@chef.io](mailto:steve@chef.io) wrote:

> Hi Tiago,
> 
> The short story is that this may be impossible without talking  
> directly to the internal SQL database and/or the bifrost (internal  
> authorization system) API. I've explained a bit below. The  
> explanation may be a bit terse for those on the list who haven't used  
> the RBAC system much.
> 
> To read a user's private key, you need to have the read permission on  
> the user itself either by being directly in the read ACE for that user  
> object or in a group that is in the read ACE. Adding your  
> vault-admins group to the read ACE of the users group won't provide  
> the permissions you need since it doesn't give you any permission on  
> the members of that group, simply on the group object itself.
> 
> The read ACE for a user Mary in the organization acme looks like this:
> 
> ```
> mary > knife raw -s 'https://api.opscode.piab/' 'users/mary/_acl' |
> 
> ```
> 
> jq .read  
> {  
> "actors": [  
> "pivotal",  
> "mary"  
> ],  
> "groups": [  
> "acme\_global\_admins"  
> ]  
> }
> 
> When Mary is associated to an organization, a special group is added  
> to the READ ace of the user. The group is in the form of  
> ORGNAME\_global\_admin and contains the admin group of the organization.  
> When she is disassociated from the org, that group is removed from her  
> read ACE. Since the admin users are in the admin group, the admin  
> group is in the acme\_global\_admins group, and the acme\_global\_admins  
> is in the read ACE of the user, an admin user can read Mary's user  
> object.
> 
> Now, knowing this, to give your users access to read each others' keys  
> you might try:
> 
> 1. Adding the users group to the acme\_global\_admins group
> 2. Adding a given user to the "actors" section of the user's read ace
> 3. Adding some arbitrary other group that contains the users to the  
> groups section of the users read ace
> 
> Unfortunately,
> 
> a) It appears Chef 12 has a bug such that you can't update a user's  
> acl without removing the ORGNAME\_global\_admin group from the ACL.  
> This would break the access that org admins have by default and would  
> put you in a situation that isn't likely well tested. [0]
> 
> b) You can't add actors or groups to the ORGNAME\_global\_admin group  
> because that group doesn't exist inside an organization and thus  
> simply isn't reachable via an API endpoint.
> 
> Option (1) above is likely doable with a script that directly  
> manipulates some of the backend services [1].
> 
> I hope this help.
> 
> Cheers,
> 
> Steven
> 
> [0] Updating user ACLs worked in 11.2.x so I'll likely be following up  
> internally and filing a bug.  
> [1] By likely doable, I mean completely doable:  
> [danger\_add\_users\_to\_global\_admins\_group · GitHub](https://gist.github.com/stevendanna/1eb99f01a2f0f22ba619)
> 
> You can use it like this from your Chef Server:
> 
> ./danger\_add\_users\_to\_global\_admins\_group acme
> 
> HOWEVER, please note that (1) this is messing with internal  
> implemntation details and it will probably break, (2) I haven't  
> audited what other permissions those users will get, and (3) I haven't  
> audited edge cases of users being associated and disassociated from  
> orgs. Basically I ran it once and it worked.

--  
-- Tiago Cruz

---

<div class="post-metadata">

**Author:** ![Tiago\_Cruz](https://sea2.discourse-cdn.com/flex016/user_avatar/discourse.chef.io/tiago_cruz/32/49_2.png) [@Tiago\_Cruz](https://discourse.chef.io/u/Tiago_Cruz)\
**Post date:** [January 26, 2015, 12:37pm UTC](https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194/5 "2015-01-26T12:37:02Z")

</div>

Ohai again!

On Fri, Jan 23, 2015 at 11:21 PM, Steven Danna [steve@chef.io](mailto:steve@chef.io) wrote:

> To read a user's private key, you need to have the read permission on  
> the user itself either by being directly in the read ACE for that user  
> object or in a group that is in the read ACE.

And to read the user's public key, do we have some easier and way? 🙂

Sounds like chef-vault just need access to the public key to encrypt:

"Gem that allows you to encrypt a Chef Data Bag Item using the public keys  
of a list of chef nodes. This allows only those chef nodes to decrypt the  
encrypted values."

- [GitHub - chef/chef-vault: Securely manage passwords, certs, and other secrets in Chef](https://github.com/Nordstrom/chef-vault)

Many thanks!!

[https://github.com/Nordstrom/chef-vault#installation](https://github.com/Nordstrom/chef-vault#installation)

---

<div class="post-metadata">

**Author:** ![ssd](https://avatars.discourse-cdn.com/v4/letter/s/7993a0/32.png) [@ssd](https://discourse.chef.io/u/ssd)\
**Post date:** [January 26, 2015, 1:17pm UTC](https://discourse.chef.io/t/chef12-knife-user-show-to-non-admin-users/6194/6 "2015-01-26T13:17:57Z")

</div>

Hi,

> Just to clarify: The group 'acme\_global\_admins' has the same privileges than  
> the 'admin' default group?

No, apologies if this was unclear. The ORGNAME\_global\_admins group,  
as far as I know, only appears in the ACL of user's who have been  
associated to ORGNAME. It does not, by default, grant members any  
other permissions. The admins group is a member of the  
ORGNAME\_global\_admins group specifically for the purpose of getting  
permission on the global user objects for members of the org. Perhaps  
this will help:

ORGNAME\_global\_admins group --has--\> Permission on user objects

admin --has--\> permission on many local organization objects  
--is a member of --\> ORGNAME\_global\_admins group

> Because if I just put the user in admin group, the 'knife user show' works,  
> and so he is able to use 'knife vault' using the option:

Correct, if you put a user in the admin group, they will be able to  
see the keys of all other users in that org by virtue of the fact that  
the admin group in ORGNAME is a member of the special  
ORGNAME\_global\_admins group. Of course, any user in the admin group  
gets the permissions associated with the admin group.

> And to read the user's public key, do we have some easier and way? 🙂

Not that I know of.

Cheers,

Steven
