Silverlight Oauth RavenDB

86 views
Skip to first unread message

c0z

unread,
Feb 19, 2012, 12:51:17 PM2/19/12
to ravendb
Hi!

I have a silverlight application with multitennancy, and would like
clients to go directly to ravendb for querys and stores.

I really don't get the Oauth thing, there must be something I'm
missing...

I've looked at this post: http://groups.google.com/group/ravendb/msg/8574cd13945296b0

I've tried the steps in "Running a single ravendb server that allows
silverlight clients to connect to it"

But I really don't get it.

I've done the web.config stuff and have set up a certificate.

The sample:
I've changed the //authenticate the user... To something like this
(calling the method with restsharp and add the basic authentication to
the headers):
var headers =
HttpContext.Current.Request.Headers["Authorization"];
string[] decoded = DecodeFrom64(headers.Replace("Basic ",
String.Empty)).Split(':');

var user = Session.Query<AuthenticationUser>().Where(x =>
x.Name == decoded[0].ToString()).SingleOrDefault();

if(user == null || !user.ValidatePassword(decoded[1]))
throw new Exception("You're not authorized");

That works and it returns a serialized accesstoken to the client (as a
string).

But then what?

What should I do with the token in the client? And how do I do my
future calls to ravendb with this accesstoken included in the calls?

Best regards
c0z

Oren Eini (Ayende Rahien)

unread,
Feb 20, 2012, 8:22:43 AM2/20/12
to rav...@googlegroups.com
Daniel,
You return the serialized access token in a string form to RavenDB Client.
It will then take that token and use it to connect to RavenDB.
This happens automatically, and you shouldn't have to do anything on the client side.
Note that you might need to setup ClientAccessPolicy.xml on your authenticating server.

c0z

unread,
Feb 20, 2012, 12:05:22 PM2/20/12
to ravendb
Thank you for your response Ayende!

But I still don't get it to work... I get a windows security window
asking me for username and password...

Just to make sure I'm doing everything right here is a simple example
of what I'm doing:
CLIENT:
_store.Credentials = new NetworkCredential(UserName,
Password);

_session = _store.OpenAsyncSession();
_session.Store(new Test { TestProperty = "some string" });
_session.SaveChangesAsync();

** Then I get the windows security window, if I click cancel it goes
to my Raven/OAuthTokenServer.

SERVER:
var cert = new X509Certificate2(certificatepath,
password);

return AccessToken.Create(cert, "Raven/Users/Admin", new[]
{ "*" }).Serialize();


Since I get the window security window I guess it must be something
wrong with how I use the client?

I have a clientaccesspolicy file allowing both http and https... and
all kinds of http-request-headers.

Any ideas?

On 20 Feb, 14:22, "Oren Eini (Ayende Rahien)" <aye...@ayende.com>
wrote:
> > c0z- Dölj citerad text -
>
> - Visa citerad text -

Oren Eini (Ayende Rahien)

unread,
Feb 20, 2012, 12:41:05 PM2/20/12
to rav...@googlegroups.com
When you use Silverlight, and it get 401, it will automatically pop up the security dialog if it is using NTLM. It isn't Windows, it is Silverlight.
We can try doing something on Skype tomorrow, to resolve the issue.

c0z

unread,
Feb 20, 2012, 2:49:39 PM2/20/12
to ravendb
I've got it working, but for some reason it fails the first time I try
to store a document.

At this point I have a childwindow and clicking a button in the window
that sets credentials and opens a session like this:
_store.Credentials = new NetworkCredential(user,
password);
_session = _store.OpenAsyncSession();
_session.Store(new Test { TestProperty = "some
string" });
_session.SaveChangesAsync().ContinueWith(a =>
{
//
do some stuff
});

The first time I click the button raven calls the url (Raven/
OAuthTokenServer) for a accesstoken, and the savechangesasync fails
"Not found".
Then I click the button one more time, and then it doesn't go for a
new access token and the savechangesasync returns rantocompletion and
the document is stored.

I've tried to understand why this happens, but can't understand why?




On 20 Feb, 18:41, "Oren Eini (Ayende Rahien)" <aye...@ayende.com>
> > > - Visa citerad text -- Dölj citerad text -

Oren Eini (Ayende Rahien)

unread,
Feb 20, 2012, 2:50:14 PM2/20/12
to rav...@googlegroups.com
What does it looks like on the wire?
Can you post the fiddler output

c0z

unread,
Feb 20, 2012, 2:58:21 PM2/20/12
to ravendb
One more thing.

The error only occurs if I have Raven/AnonymousAccess = Get.

If I set the Raven/AnonymousAccess = None

It calls for accesstokens directly (appliationstart) and then it
doens't ask for a new token when I click the button. And it stores the
document with rantocompletion.

c0z

unread,
Feb 20, 2012, 3:09:51 PM2/20/12
to ravendb
HTTP/1.1 500 Internal Server Error
Cache-Control: private
Content-Type: text/html
Server: Microsoft-IIS/7.5
Raven-Server-Build: 647
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Mon, 20 Feb 2012 20:09:01 GMT
Content-Length: 1105

{
"Url": "/raven/bulk_docs",
"Error": "System.Exception: Error reading RavenJArray from
JsonReader.\r\n at Raven.Json.Linq.RavenJArray.Load(JsonReader
reader) in c:\\Builds\\RavenDB-Unstable\\Raven.Abstractions\\Json\\Linq
\\RavenJArray.cs:line 98\r\n at
Raven.Database.Extensions.HttpExtensions.ReadJsonArray(IHttpContext
context) in c:\\Builds\\RavenDB-Unstable\\Raven.Database\\Extensions\
\HttpExtensions.cs:line 64\r\n at
Raven.Database.Server.Responders.DocumentBatch.Batch(IHttpContext
context) in c:\\Builds\\RavenDB-Unstable\\Raven.Database\\Server\
\Responders\\DocumentBatch.cs:line 72\r\n at
Raven.Database.Server.Responders.DocumentBatch.Respond(IHttpContext
context) in c:\\Builds\\RavenDB-Unstable\\Raven.Database\\Server\
\Responders\\DocumentBatch.cs:line 38\r\n at
Raven.Database.Server.HttpServer.DispatchRequest(IHttpContext ctx) in
c:\\Builds\\RavenDB-Unstable\\Raven.Database\\Server\
\HttpServer.cs:line 528\r\n at
Raven.Database.Server.HttpServer.HandleActualRequest(IHttpContext ctx)
in c:\\Builds\\RavenDB-Unstable\\Raven.Database\\Server\
\HttpServer.cs:line 303"
}

On 20 Feb, 20:50, "Oren Eini (Ayende Rahien)" <aye...@ayende.com>

Oren Eini (Ayende Rahien)

unread,
Feb 20, 2012, 3:21:20 PM2/20/12
to rav...@googlegroups.com
What are you sending there?

c0z

unread,
Feb 20, 2012, 3:25:22 PM2/20/12
to ravendb
Ohh sorry:
POST https://localhost/raven/bulk_docs HTTP/1.1
Accept: */*
Accept-Language: sv-SE
Referer: https://localhost/RidklubbenOnline.Web/ClientBin/RidklubbenOnline.xap
Accept-Encoding: identity
Content-Type: application/json; charset=utf-8
Authorization: Bearer {"Body":"{\"UserId\":\"Raven/Users/Admin\",
\"AuthorizedDatabases\":[{\"Admin\":false,\"TenantId\":\"*\",\"ReadOnly
\":false}],\"Issued\":
63465366227776.3}","Signature":"FrSUCldWI2vK8QdnxYNEeBhmgyxipq5ZSbf/
JKGNclZD+qsrQ/dYUFGPplrz6vltOFrBOpfnNkvx17wKR1+6GOKrHDCEd7nnZp3lAR/
+d287uKA1DLIJwUNmZJwqpwrDZLyQrOatGUGgjiGDuGef
+PFrRl85DhkCCmwjpzmPGc5WKsN3ty8EbOYJdpc6R/HPJc8YXnvpKXVuAfPiDbMrUU
+u9zBecM2G6hcT4CYmYEFyZcClNjrhDoNf
+4NowA4VxdZNg18Hmz7fM1FjKUstsdgJeass6I4HdJyRwkh689wktuMvCHvx8kZXkJH2bWnYoPvA82mC8vbuxRohZ9QM0g=="}
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; WOW64;
Trident/5.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR
3.0.30729; Media Center PC 6.0; .NET4.0C; .NET4.0E; InfoPath.3)
Host: localhost
Content-Length: 0
Connection: Keep-Alive
Cache-Control: no-cache



On 20 Feb, 21:21, "Oren Eini (Ayende Rahien)" <aye...@ayende.com>

Oren Eini (Ayende Rahien)

unread,
Feb 20, 2012, 3:25:56 PM2/20/12
to rav...@googlegroups.com
Where is the request body?

c0z

unread,
Feb 21, 2012, 4:02:28 PM2/21/12
to ravendb
I dont know what more to send you, but here is the message chain in
fiddler:


POST https://localhost/Raven/docs/ HTTP/1.1
Accept: */*
Accept-Language: sv-SE
Referer: https://localhost/Raven/silverlight/Raven.Studio.xap
Content-Length: 24
Accept-Encoding: identity
If-None-Match: 00000000-0000-0000-0000-000000000000
Content-Type: application/json; charset=utf-8
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; WOW64;
Trident/5.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR
3.0.30729; Media Center PC 6.0; .NET4.0C; .NET4.0E; InfoPath.3)
Host: localhost
Connection: Keep-Alive
Cache-Control: no-cache

{
"Name": "..."
}

HTTP/1.1 401 Unauthorized
Cache-Control: private
Server: Microsoft-IIS/7.5
OAuth-Source: https://localhost/RidklubbenOnline.Web/login/
WWW-Authenticate: Bearer realm="Raven",
error="invalid_request",error_description="The access token is
required"
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Tue, 21 Feb 2012 20:50:10 GMT
Content-Length: 0

-----------------------------

GET https://localhost/RidklubbenOnline.Web/login/?noCache=-1597649862
HTTP/1.1
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; WOW64;
Trident/5.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR
3.0.30729; Media Center PC 6.0; .NET4.0C; .NET4.0E; InfoPath.3)
Accept-Language: sv-SE
Referer: https://localhost/Raven/silverlight/Raven.Studio.xap
Accept-Encoding: identity
grant_type: client_credentials
Accept: application/json;charset=UTF-8
Host: localhost
Connection: Keep-Alive

HTTP/1.1 200 OK
Cache-Control: private
Content-Type: text/plain; charset=utf-8
Server: Microsoft-IIS/7.5
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Tue, 21 Feb 2012 20:50:16 GMT
Content-Length: 516

{"Body":"{\"UserId\":\"Raven/Users/Admin\",\"AuthorizedDatabases\":
[{\"Admin\":false,\"TenantId\":\"*\",\"ReadOnly\":false}],\"Issued\":
63465454216307.086}","Signature":"MFxcVvInPvck6LAfxhfOUeMHn5W2dzR4xCqmLceEnEo3PhQFIFE5a68JD0/
T708gzQP/
0WRpATTCnitNkYtMM3QMwefneZ6I8PnSDf2cdxMu6tjpnnnWX4iQlGU2oAbfmQ0w7wSj2kJfG7z1W29BF5AD/
sVh78GU2VDKXNWN9x5Pkiwi2bC13vgfu6QT5rqXOYlSsGhyQ9tSw/
bsB1OxGRdlEF2jQZe0B3pKwiL3augG1JllB8rvRHuGihdIqmJmFXTxePZGHS36TvsLr5460SRlbtFqIxXcFEhk8hV5yBkFY1BGyn2jNpH0H2GRBnEnad0yZYaEdHvjJdBX0FciNA=="}


---------------------------------------------------------


POST https://localhost/Raven/docs/ HTTP/1.1
Accept: */*
Accept-Language: sv-SE
Referer: https://localhost/Raven/silverlight/Raven.Studio.xap
Accept-Encoding: identity
If-None-Match: 00000000-0000-0000-0000-000000000000
Content-Type: application/json; charset=utf-8
Authorization: Bearer {"Body":"{\"UserId\":\"Raven/Users/Admin\",
\"AuthorizedDatabases\":[{\"Admin\":false,\"TenantId\":\"*\",\"ReadOnly
\":false}],\"Issued\":
63465454216307.086}","Signature":"MFxcVvInPvck6LAfxhfOUeMHn5W2dzR4xCqmLceEnEo3PhQFIFE5a68JD0/
T708gzQP/
0WRpATTCnitNkYtMM3QMwefneZ6I8PnSDf2cdxMu6tjpnnnWX4iQlGU2oAbfmQ0w7wSj2kJfG7z1W29BF5AD/
sVh78GU2VDKXNWN9x5Pkiwi2bC13vgfu6QT5rqXOYlSsGhyQ9tSw/
bsB1OxGRdlEF2jQZe0B3pKwiL3augG1JllB8rvRHuGihdIqmJmFXTxePZGHS36TvsLr5460SRlbtFqIxXcFEhk8hV5yBkFY1BGyn2jNpH0H2GRBnEnad0yZYaEdHvjJdBX0FciNA=="}
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; WOW64;
Trident/5.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR
3.0.30729; Media Center PC 6.0; .NET4.0C; .NET4.0E; InfoPath.3)
Host: localhost
Content-Length: 0
Connection: Keep-Alive
Cache-Control: no-cache


HTTP/1.1 500 Internal Server Error
Cache-Control: private
Content-Type: text/html
Server: Microsoft-IIS/7.5
Raven-Server-Build: 616
Access-Control-Allow-Origin: *
Access-Control-Max-Age: 1728000
Access-Control-Allow-Methods: PUT,PATCH,GET,DELETE,POST
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Tue, 21 Feb 2012 20:50:16 GMT
Content-Length: 849

{
"Url": "/Raven/docs/",
"Error": "System.Exception: Error reading RavenJObject from
JsonReader.\r\n at Raven.Json.Linq.RavenJObject.Load(JsonReader
reader) in c:\\Builds\\raven\\Raven.Abstractions\\Json\\Linq\
\RavenJObject.cs:line 148\r\n at
Raven.Database.Extensions.HttpExtensions.ReadJson(IHttpContext
context) in c:\\Builds\\raven\\Raven.Database\\Extensions\
\HttpExtensions.cs:line 50\r\n at
Raven.Database.Server.Responders.Docs.Respond(IHttpContext context) in
c:\\Builds\\raven\\Raven.Database\\Server\\Responders\\Docs.cs:line
39\r\n at
Raven.Database.Server.HttpServer.DispatchRequest(IHttpContext ctx) in
c:\\Builds\\raven\\Raven.Database\\Server\\HttpServer.cs:line 528\r
\n at
Raven.Database.Server.HttpServer.HandleActualRequest(IHttpContext ctx)
in c:\\Builds\\raven\\Raven.Database\\Server\\HttpServer.cs:line 303"
}

c0z

unread,
Feb 21, 2012, 4:06:31 PM2/21/12
to ravendb
I still have some problems with the OAuth except from the exception
above:

Right now I'm always sending back a token from the oauth/logon
controller.

But I need do validate username/password. But how do I get the
networkcredential I've set on the client in the Oauth/login method?

Can't find anything in the request that tells me wich user asking for
the accesstoken, and I don't understand how to get that info?

Oren Eini (Ayende Rahien)

unread,
Feb 21, 2012, 4:32:55 PM2/21/12
to rav...@googlegroups.com
You setup whatever authentication mode you want there.
you can use basic, windows auth, or anything else.
RavenDB will use the credentials that you pass it to the document store to authenticate against that endpoint.
Reply all
Reply to author
Forward
0 new messages