http_auth_backend does not use my http server responses

381 views
Skip to first unread message

Dimitri Pekarovsky

unread,
Jan 15, 2016, 2:20:44 PM1/15/16
to rabbitmq-users
Hi, all.

I wish to use both internal and http backends for authentication, like one-two admins uses browser and rabbit api, and normal users need to be authorized through my ruby server and db.

I added the administrator "browser" directly to rabbit db and wrote a simple sinatra app, that checks for username == 'root' and return "allow administrator\n".

So what I get. Firstly it ignores the second user that was added directly to rabbitmq db. Explanation is below.
This is a portion of the rabbitmq.config:

{rabbit,
   
[
     
{tcp_listeners, [5673]},
     
{auth_backends, [{rabbit_auth_backend_internal, rabbit_auth_backend_http}]}
   
]},
 
{rabbitmq_auth_backend_http,
   
[{user_path,     "http://127.0.0.1:3000/check_access/in"},
     
{vhost_path,    "http://127.0.0.1:3000/check_access/vh"},
     
{resource_path, "http://127.0.0.1:3000/check_access/rs"}
   
]
 
}

look at the
{auth_backends, [{rabbit_auth_backend_internal, rabbit_auth_backend_http}]}

With that line rabbit completly ignores internal backend and asks only http backend, so I see
Started GET "/check_access/in?username=browser"
in my sinatra app.

If I change that line to:
{auth_backends, [rabbit_auth_backend_internal, rabbit_auth_backend_http]}

I get expected behaviour about 'browser' user: rabbit don't ask my http-backend about that user, BUT if I add to rabbitmq database directly another one - 'root' which is also an administrator, it starts to do so!
Started GET "/check_access/in?username=root&password=IynjPg-8BjPcIzvVtnZ9lMyAIF%2BMhlM" for 127.0.0.1 at 2016-01-15 19:51:27 +0200
        sinatra
: ip:127.0.0.1, root:IynjPg-8BjPcIzvVtnZ9lMyAIF+MhlM
        sinatra allow administrator

And the second future:
when I try to access rabbit API with that user like that:
1. RabbitHelper.api Net::HTTP::Put.new("/api/exchanges/chat/meeting.2328") # username is root
2. This is what I get on sinatra side:

Started GET "/check_access/in?username=root&password=IynjPg-8BjPcIzvVtnZ9lMyAIF%2BMhlM" for 127.0.0.1 at 2016-01-15 21:10:39 +0200
        sinatra
: ip:127.0.0.1, root:IynjPg-8BjPcIzvVtnZ9lMyAIF+MhlM
        sinatra allow administrator monitoring management policymaker



Started GET "/check_access/vh?username=root&vhost=chat" for 127.0.0.1 at 2016-01-15 21:10:39 +0200
        sinatra
: ip:127.0.0.1, root:
        sinatra allow administrator monitoring management policymaker



Started GET "/check_access/vh?username=root&vhost=%2F" for 127.0.0.1 at 2016-01-15 21:10:39 +0200
        sinatra
: ip:127.0.0.1, root:
        sinatra allow administrator monitoring management policymaker

3. This is rabbit log
=WARNING REPORT==== 15-Jan-2016::21:10:39 ===
HTTP access denied
: user 'root' - User not authorised to access virtual host

=ERROR REPORT==== 15-Jan-2016::21:10:39 ===
webmachine error
: path="/api/exchanges/chat/meeting.2328"
"Unauthorized"

I used different kind of answers:
* allow
* allow administrator
* all of above with "\n" at end
* with all tags as you see in log above

Next, I deleted the second administrator from rabbitmq database and changed name of user to another -  "staffuser".
=WARNING REPORT==== 15-Jan-2016::21:19:35 ===
HTTP access denied
: user 'staffuser' - User not authorised to access virtual host

=ERROR REPORT==== 15-Jan-2016::21:19:35 ===
webmachine error
: path="/api/exchanges/chat/meeting.2328"
"Unauthorized"

So where is a pig?

//DP

Michael Klishin

unread,
Jan 15, 2016, 2:36:32 PM1/15/16
to rabbitm...@googlegroups.com, Dimitri Pekarovsky
On 15 January 2016 at 22:20:47, Dimitri Pekarovsky (dimitri.p...@gmail.com) wrote:
> This is what I get on sinatra side:

There is an example app in the repo:
https://github.com/rabbitmq/rabbitmq-auth-backend-http/blob/master/examples/rabbitmq_auth_backend_django/rabbitmq_auth_backend_django/auth/views.py

we cannot suggest much beyond this without having an exact list of steps
you take.

You also haven't specified what RabbitMQ version you run. There was a bug fixed in 3.5.6
that prevented tags from being propagated between backends in certain scenarios:

https://github.com/rabbitmq/rabbitmq-server/issues/338 
--
MK

Staff Software Engineer, Pivotal/RabbitMQ


Michael Klishin

unread,
Jan 15, 2016, 2:40:02 PM1/15/16
to rabbitm...@googlegroups.com, Dimitri Pekarovsky
On 15 January 2016 at 22:36:27, Michael Klishin (mkli...@pivotal.io) wrote:
> You also haven't specified what RabbitMQ version you run. There
> was a bug fixed in 3.5.6
> that prevented tags from being propagated between backends
> in certain scenarios:
>
> https://github.com/rabbitmq/rabbitmq-server/issues/338

…and to narrow down the list of possible issues I'd recommend using a RabbitMQ
client first, this should rule out any possible issues with user tags. Once you have that
working, you can move on to trying HTTP API via curl or management UI .

Dimitri Pekarovsky

unread,
Jan 15, 2016, 2:43:00 PM1/15/16
to rabbitmq-users, dimitri.p...@gmail.com
$ pacman -Qs rabbitmq
local/rabbitmq 3.6.0-2
$ pacman -Qs erlang
local/erlang-nox 18.2.1-1


пятница, 15 января 2016 г., 21:36:32 UTC+2 пользователь Michael Klishin написал:

Michael Klishin

unread,
Jan 15, 2016, 2:45:42 PM1/15/16
to rabbitm...@googlegroups.com, Dimitri Pekarovsky
On 15 January 2016 at 22:43:02, Dimitri Pekarovsky (dimitri.p...@gmail.com) wrote:
> $ pacman -Qs rabbitmq
> local/rabbitmq 3.6.0-2
> $ pacman -Qs erlang
> local/erlang-nox 18.2.1-1

You are a man of a few words.

Now can you please try the Django example app and post a step by step way to reproduce
in case the issue still  isn't obvious?

Dimitri Pekarovsky

unread,
Jan 15, 2016, 2:47:09 PM1/15/16
to rabbitmq-users, dimitri.p...@gmail.com
At IMHO I wrote fully what I did. What more explanation do you need?
I readed that example, there just the same I did with sinatra. Plain string "allow" with optional tag.


пятница, 15 января 2016 г., 21:36:32 UTC+2 пользователь Michael Klishin написал:
On 15 January 2016 at 22:20:47, Dimitri Pekarovsky (dimitri.p...@gmail.com) wrote:

Michael Klishin

unread,
Jan 15, 2016, 2:58:11 PM1/15/16
to rabbitm...@googlegroups.com, Dimitri Pekarovsky
On 15 January 2016 at 22:47:13, Dimitri Pekarovsky (dimitri.p...@gmail.com) wrote:
> I wish to use both internal and http backends for authentication,
> like one-two admins uses browser and rabbit api, and normal users
> need to be authorized through my ruby server and db.

{rabbit_auth_backend_internal, rabbit_auth_backend_http} configures RabbitMQ
to use

 * rabbit_auth_backend_internal for authentication
 * rabbit_auth_backend_http for authorisation

is this what you expect?

ДП

unread,
Jan 15, 2016, 2:58:47 PM1/15/16
to Michael Klishin, rabbitm...@googlegroups.com
I don't speak python, sorry.
There's no mention which python version should I use.

//DP

$ pacman -Qs python-django
local/python-django 1.9.1-1
$ python -V
Python 3.5.1
-------
$ ./start.sh
Unknown command: 'syncdb'
Type 'manage.py help' for usage.
Performing system checks...

/usr/lib/python3.5/site-packages/django/template/utils.py:37:
RemovedInDjango110Warning: You haven't defined a TEMPLATES setting. You
must do so before upgrading to Django 1.10. Otherwise Django will be
unable to load templates.
"unable to load templates.", RemovedInDjango110Warning)

...http-auth/rabbitmq-auth-backend-http/examples/rabbitmq_auth_backend_django/rabbitmq_auth_backend_django/urls.py:13:
RemovedInDjango110Warning: django.conf.urls.patterns() is deprecated and
will be removed in Django 1.10. Update your urlpatterns to be a list of
django.conf.urls.url() instances instead.
(r'^admin/', include(admin.site.urls)),

/usr/lib/python3.5/site-packages/django/conf/urls/__init__.py:89:
RemovedInDjango110Warning: Support for string view arguments to url() is
deprecated and will be removed in Django 1.10 (got
rabbitmq_auth_backend_django.auth.views.user). Pass the callable instead.
t = url(prefix=prefix, *t)

/usr/lib/python3.5/site-packages/django/conf/urls/__init__.py:89:
RemovedInDjango110Warning: Support for string view arguments to url() is
deprecated and will be removed in Django 1.10 (got
rabbitmq_auth_backend_django.auth.views.vhost). Pass the callable instead.
t = url(prefix=prefix, *t)

/usr/lib/python3.5/site-packages/django/conf/urls/__init__.py:89:
RemovedInDjango110Warning: Support for string view arguments to url() is
deprecated and will be removed in Django 1.10 (got
rabbitmq_auth_backend_django.auth.views.resource). Pass the callable
instead.
t = url(prefix=prefix, *t)

System check identified no issues (0 silenced).

You have unapplied migrations; your app may not work properly until they
are applied.
Run 'python manage.py migrate' to apply them.

January 15, 2016 - 19:54:03
Django version 1.9.1, using settings 'rabbitmq_auth_backend_django.settings'
Starting development server at http://127.0.0.1:8000/
Quit the server with CONTROL-C.


15.01.2016 21:45, Michael Klishin пишет:

Michael Klishin

unread,
Jan 15, 2016, 3:03:41 PM1/15/16
to rabbitm...@googlegroups.com, Dimitri Pekarovsky
On 15 January 2016 at 22:47:13, Dimitri Pekarovsky (dimitri.p...@gmail.com) wrote:
> At IMHO I wrote fully what I did. What more explanation do you
> need?

Look, it can be that I'm not intelligent enough but no, it is not at all clear what you are trying
to achieve, or what your expectations are.

Lines such as

> I added the administrator "browser" directly to rabbit db

don't actually give us much specific information we can use to reproduce. Again, perhaps I'm
not intelligent enough or haven't mastered mind reading.

What would provide us *specific* information? Something along these lines:

 > I used `rabbitmqctl` to do A, B, and C
 > I expect RabbitMQ to use my Sinatra app to do X, the internal backend to do Y, and management UI to be accessible to the newly created user U.
> In fact, here's my Sinatra app in a public repository you can clone and try for yourself

Of course, you don't have to do any of that. Then people on this list will have to second-guess, read between
the lines, and otherwise waste their time. Or maybe they just won't bother and skip this thread entirely.

ДП

unread,
Jan 15, 2016, 3:04:42 PM1/15/16
to Michael Klishin, rabbitm...@googlegroups.com
This is actual line, which I use now. It is described in the first letter:

{auth_backends, [rabbit_auth_backend_internal,rabbit_auth_backend_http]}

> I wish to use both internal and http backends for authentication,
like one-two admins uses browser and rabbit api, and normal users need
to be authorized through my ruby server and db.

I want that administrators were authenticated first, no matter is my
server started or not. So they must be present in mnesia.
Then all normal users of the site have to go through normal login
process with auth-backend-http. But I got there, that for the second
admin added to mnesia, rabbit still asks my sinatra backend.

//DP

15.01.2016 21:57, Michael Klishin пишет:

Michael Klishin

unread,
Jan 15, 2016, 3:10:20 PM1/15/16
to ДП, rabbitm...@googlegroups.com
On 15 January 2016 at 22:58:36, ДП (dimitri.p...@gmail.com) wrote:
> I don't speak python, sorry.

The rabbitmq_auth_backend_http.user_path handler responds with

 * "allow administrator" (without the quotes) when authentication succeeds and the user is a superuser (however we define that)
 * "allow management" when authentication succeeds and the user is not a superuser
 * "deny" when autnetication fails

The rabbitmq_auth_backend_http.vhost_path handler responds with "allow" (without the quotes)
unconditionally.

The rabbitmq_auth_backend_http.resource_path handler responds with "allow" (without the quotes)
unconditionally.

In other words, user tags are listed by the user_path handler, not vhost_path, or resource_path.

This matters because vhost_path and resource_path expect "allow" or "deny" without the quotes
in response body:
https://github.com/rabbitmq/rabbitmq-auth-backend-http/blob/master/src/rabbit_auth_backend_http.erl#L73

"allow administrator monitoring management policymaker" is not the same as "allow", and
access is refused. Which is what the log says. 

Michael Klishin

unread,
Jan 15, 2016, 3:13:52 PM1/15/16
to ДП, rabbitm...@googlegroups.com
On 15 January 2016 at 23:10:16, Michael Klishin (mkli...@pivotal.io) wrote:
> This is actual line, which I use now. It is described in the first
> letter:
>
> {auth_backends, [rabbit_auth_backend_internal,rabbit_auth_backend_http]}

Your original email says

> {auth_backends, [{rabbit_auth_backend_internal, rabbit_auth_backend_http}]}

which is not the same thing as explained in the docs (search for "auth_backends"):
http://www.rabbitmq.com/configure.html#configuration-file.

Maybe now it's a bit clearer why we ask for exact steps to reproduce .

Michael Klishin

unread,
Jan 15, 2016, 3:26:01 PM1/15/16
to ДП, rabbitm...@googlegroups.com
+rabbitmq-users

On 15 January 2016 at 23:09:58, ДП (dimitri.p...@gmail.com) wrote:
> > {auth_backends, [rabbit_auth_backend_internal,rabbit_auth_backend_http]}
>
> Your original email says
>
> > {auth_backends, [{rabbit_auth_backend_internal, rabbit_auth_backend_http}]}
>
> which is not the same thing as explained in the docs (search for
> "auth_backends"):
> http://www.rabbitmq.com/configure.html#configuration-file.

I've filed an issue to document that in more detail in our Access Control guide:
https://github.com/rabbitmq/rabbitmq-website/issues/141.

This specific question pops up almost every week now, our docs in that area are
not adequate.

ДП

unread,
Jan 15, 2016, 3:48:54 PM1/15/16
to Michael Klishin, rabbitm...@googlegroups.com
https://github.com/deemytch/example-sinatra-app

//DP

15.01.2016 22:10, Michael Klishin пишет:
> On 15 January 2016 at 22:58:36, ДП (dimitri.p...@gmail.com) wrote:
>> I don't speak python, sorry.
>
> The rabbitmq_auth_backend_http.user_path handler responds with
>
> * "allow administrator" (without the quotes) when authentication succeeds and the user is a superuser (however we define that)
> * "allow management" when authentication succeeds and the user is not a superuser
> * "deny" when autnetication fails
>

Yes, my app answers exactly that.
Hope you could start it without problem.

ДП

unread,
Jan 15, 2016, 3:58:24 PM1/15/16
to Michael Klishin, rabbitm...@googlegroups.com
So I extracted my sinatra code from my rails app and all started to work
fine. I don't believe that. Looks like magic. It returns exatly the same
answers.

Thank you for your time again.
You could use my sinatra app as example in documentation if you wish.

//DP

15.01.2016 21:36, Michael Klishin пишет:
Reply all
Reply to author
Forward
0 new messages