how to secure apache cxf webservice(jax-ws) using oAuth 2.0 - web-services

I have deployed webservice in Tomcat using Apache CXF. How would I proceed in securing that web service using OAuth 2.0?
I have gone through the below URL but without finding any suitable solution. A working example or tutorials on how to implement oAuth 2.0 for simple web service?
Original tutorial link:
JAX-RS: OAuth2

I was confronted with the same issue recently. After a decent amount of research, I have found (and this could be limited to me alone) that this is quite complicated.
It is possible to attach the required "authorization header" to a SOAP webservice call in this manner :
Map<String, Object> req_ctx = ((BindingProvider)port).getRequestContext();
req_ctx.put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY, WS_URL);
Map<String, List<String>> headers = new HashMap<String, List<String>>();
headers.put("key", Collections.singletonList("yourkey"));
//... all other parameters required.
req_ctx.put(MessageContext.HTTP_REQUEST_HEADERS, headers);
The request can then be checked on the server side as such :
MessageContext mctx = wsctx.getMessageContext();
//get detail from request headers
Map http_headers = (Map) mctx.get(MessageContext.HTTP_REQUEST_HEADERS);
List userList = (List) http_headers.get("key");
//... get other information required here
And thus you can validate the request.
On a side note
It is to note, from my findings, oAuth2 is not very useful for simply securing your API - simply protecting it from outside use.
The reasoning
With oAuth 1, you could use the authentication to validate a user by their key. You knew they were authorized because they have successfully signed the request, and thus you would allow them access to the information.
With oAuth 2, the protocol requires you to use HTTPS. Then why not just use application authentication with your API? I have found oAuth 2 to be very useful to access 3rd party applications with the original set of credentials (the goal of the protocol). But unless you need to do this, there is no need (again IMO) to implement the full oAuth. If you ONLY looking to secure your API, just do it using SSL and a key or username/password combination.
See also:
Application Authentication With JAX-WS
CFX User Guide
How is OAuth 2 different from OAuth 1?
Designing a Secure REST API without oAuth - more useful for general understanding.

I've added a short intro here:
https://cwiki.apache.org/confluence/display/CXF20DOC/JAX-RS+OAuth2#JAX-RSOAuth2-OAuth2tokensandSOAPendpoints
Basically it will work with bearer tokens passed via Authorization headers as is, and can be easily customized to handle WS-Security binary tokens

Related

Web API authentication using OAuth 2.0 token and Azure Active Directory (Without Authentication Server)

Is there a way to authenticate the Microsoft or google OAuth token in active directory without using an authentication server?
Here is the scenario:
A client app gets an Microsoft access_token from some external service.
Client app will make a call to some secured web API and pass that access_token along with the request header
If the access_token passed by client is valid then API will provide response to the client.
Is there a way to validate that access_token on API side?
My normal understanding about OAuth 2.0 is there needs to be an authentication server to which both the client and API would talk to as shown in the figure below:
But if the token is provided by some external service, Can we use it to validate our web API. Are there any ways to implement such authentication?
You can learn more about AAD Signing Keys and handling Key Rollover using this page: Signing key rollover in Azure Active Directory
Validation of the token, once you have the signing key, can be done using existing libraries like OWIN. You can also try following instructions like this (although it seems the document isn't 100% complete yet): Manually validating a JWT access token in a web API
This library is also available, but I think OWIN is supposed to have replaced it in general.
Also check out this blog post, which has a pretty great deep dive into token validation.

Soap Authentication implementation thru WSDL and Schema

I need some clue or direction on how to implement authentication into soap message.
Is it possible to implement authentication by using plain WSDL and Xml Schema ?
When I said plain, I referring to only using WSDL / XML schema, no php, no java annotation, no ruby, no .net, etc.
I know there are standards on WSS, which is SAML / OASIS, but from their documentation (only OASIS, I haven't access SAML documentation yet) they are focus on their specification on soap message, which isn't what i want.
On top of that, I want soap authentication, not http basic authentication.
A WSDL is simply the description of the service. It doesn't implement anything, and certainly doesn't implement authentication.
Also, FYI, there's no such thing as SOAP Authentication.
The recommended approach would be to use the WS-Security standard. The easiest way to achieve a solution would be to use WS-Security Username token policy described here:
https://www.oasis-open.org/committees/download.php/13392/wss-v1.1-spec-pr-UsernameTokenProfile-01.htm
The benefit of using this approach is that your WSDL will include a section that will describe the authentication requirements of the web service. Any clients that generate stubs using the WSDL will then be able to automatically generate code for including username token with the request message.
You can find an example implementation here:
WS Security - Username token Profile

Best way to Integrate ADFS 2.0 authentication in a Django application

I need to use Active Directory Federation Services (ADFS) authentication in a Django application. I will create an authentication backend, but which tool would someone recommend me to make it as fast as possible, or would it be better to implement authentication from scratch?
I have read some articles from the Microsoft website, and have checked:
http://claimsid.codeplex.com/
http://msdn.microsoft.com/en-us/library/ff359102.aspx
But even though they explain some core concepts and ideas about ADFS and SSO, the examples are in my opinion more .NET stack focused.
Writing a basic client in .NET and sniffing the traffic would give you all necessary clues to actually implement the flow in any technology.
Basically, your django app has an endpoint adfs uses to return back. You register the endpoint in adfs (like https://myapp.com/authgateway).
Then, your application initializes the flow by redirecting to https://adfs.address/adfs/ls?wa=wsignin1.0&wtrealm=https://myapp.com/authgateway
Adfs picks the request and validates credentials. Then it creates a SAML token and redirects back to your application with a POST request containing the token.
Then comes the difficult part, the SAML token is a plain xml you can use to establish a local user session. One of the claims contains user name provided by adfs, other claims can contain roles, the email, whatever you configure at the adfs side.
But, to prevent forging, you need to validate the token. The validation consist in checking the XMLdsig signature and verifying that the signing certificate thumbprint matches the thumbprint of the adfs signing certificate. Depending on how much knowledge on x509 certificates and xml validation you have this can be easy or difficult. Try to find any support in django community.
Anyway, as you can see the basic flow is simple, is a matter of two redirects, a 302 from your application to adfs and a POST back from adfs to your application. Although we do this daily in .net, our partners do it in php/java under our guidance.
There's a package available for this here:
http://django-auth-adfs.readthedocs.org/en/latest/

Authentication in a RESTful web-service

I'm building a restful web-service based on Spring. I'm using Spring Security. It will be accessed only by desktop applications. Basically a machine-to-machine web-service.
I want a custom service that does the authentication. Then perform other, more sensitive operations based on the result of the authentication.
Another option is to send the credentials in the body of each request and basically do the authentication each time.
Logic says that the first approach would be the most efficient because there is quite some overhead in authenticating each and every time.
What do you suggest related to this? To go stateless or stateful? Are there major disadvantages to the stateful approach?
Up to this point I read some chapters from Java Web Services Up and Running
and also several questions from SO such as this.
The REST way to do this is, as stated in the links you provide, to authenticate on each request, and NOT to keep sessions.
As for authenticating with username/password on each request, it is secure if you can use ... a secure layer (https); else, the pair is sent in clear text and discoverable.
Another option is to use something like the AWS way to do it (Links to Amazon here and here, for example). Here for other explainations : buzzmedia and samritchie
Maybe OAuth is an option, but I don't have experience with it.
To start with REST Service (Client - Server) I will strongly recomend you to use Restlet
Authentication to this REST Service can be defined using ClientResource. Example :
private static ClientResource getClientResource(String uri) {
ClientResource clientResource = new ClientResource(uri);
clientResource.setChallengeResponse(ChallengeScheme.HTTP_BASIC,
"username", "password"
);
return clientResource;
}

How do I implement login in a RESTful web service?

I am building a web application with a services layer. The services layer is going to be built using a RESTful design. The thinking is that some time in the future we may build other applications (iPhone, Android, etc.) that use the same services layer as the web application. My question is this - how do I implement login? I think I am having trouble moving from a more traditional verb based design to a resource based design. If I was building this with SOAP I would probably have a method called Login. In REST I should have a resource. I am having difficulty understanding how I should construct my URI for a login. Should it be something like this:
http://myservice/{username}?p={password}
EDIT: The front end web application uses the traditional ASP.NET framework for authentication. However at some point in the authentication process I need to validate the supplied credentials. In a traditional web application I would do a database lookup. But in this scenario I am calling a service instead of doing a database lookup. So I need something in the service that will validate the supplied credentials. And in addition to validating the supplied credentials I probably also need some sort of information about the user after they have successfully authenticated - things like their full name, their ID, etc. I hope this makes the question clearer.
Or am I not thinking about this the right way? I feel like I am having difficulty describing my question correctly.
Corey
As S.Lott pointed out already, we have a two folded things here: Login and authentication
Authentication is out-of-scope here, as this is widely discussed and there is common agreement. However, what do we actually need for a client successfully authenticate itself against a RESTful web service? Right, some kind of token, let's call it access-token.
Client) So, all I need is an access-token, but how to get such RESTfully?
Server) Why not simply creating it?
Client) How comes?
Server) For me an access-token is nothing else than a resource. Thus, I'll create one for you in exchange for your username and password.
Thus, the server could offer the resource URL "/accesstokens", for POSTing the username and password to, returning the link to the newly created resource "/accesstokens/{accesstoken}".
Alternatively, you return a document containing the access-token and a href with the resource's link:
<access-token
id="{access token id goes here; e.g. GUID}"
href="/accesstokens/{id}"
/>
Most probably, you don't actually create the access-token as a subresource and thus, won't include its href in the response.
However, if you do so, the client could generate the link on its behalf or not? No!
Remember, truly RESTful web services link resources together in a way that the client can navigate itself without the need for generating any resource links.
The final question you probably have is if you should POST the username and password as a HTML form or as a document, e.g. XML or JSON - it depends... :-)
You don't "login". You "authenticate". World of difference.
You have lots of authentication alternatives.
HTTP Basic, Digest, NTLM and AWS S3 Authentication
HTTP Basic and Digest authentication. This uses the HTTP_AUTHORIZATION header. This is very nice, very simple. But can lead to a lot of traffic.
Username/Signature authentication. Sometimes called "ID and KEY" authentication. This can use a query string.
?username=this&signature=some-big-hex-digest
This is what places like Amazon use. The username is the "id". The "key" is a digest, similar to the one used for HTTP Digest authentication. Both sides have to agree on the digest to proceed.
Some kind of cookie-based authentication. OpenAM, for example, can be configured as an agent to authenticate and provide a cookie that your RESTful web server can then use. The client would authenticate first, and then provide the cookie with each RESTful request.
Great question, well posed. I really like Patrick's answer. I use something like
-/users/{username}/loginsession
With POST and GET being handled. So I post a new login session with credentials and I can then view the current session as a resource via the GET.
The resource is a login session, and that may have an access token or auth code, expiry, etc.
Oddly enough, my MVC caller must itself present a key/bearer token via a header to prove that it has the right to try and create new login sessions since the MVC site is a client of the API.
Edit
I think some other answers and comments here are solving the issue with an out-of-band shared secret and just authenticating with a header. That's fine in many situations or for service-to-service calls.
The other solution is to flow a token, OAuth or JWT or otherwise, which means the "login" has already taken place by another process, probably a normal login UI in a browser which is based around a form POST.
My answer is for the service that sits behind that UI, assuming you want login and auth and user management placed in a REST service and not in the site MVC code. It IS the user login service.
It also allows other services to "login" and get an expiring token, instead of using a pre-shared key, as well as test scripts in a CLI or Postman.
Since quite a bit has changed since 2011...
If you're open to using a 3rd party tool, and slightly deviating from REST slightly for the web UI, consider http://shiro.apache.org.
Shiro basically gives you a servlet filter purposed for authentication as well as authorization. You can utilize all of the login methods listed by #S.Lott, including a simple form based authentication.
Filter the rest URLs that require authentication, and Shiro will do the rest.
I'm currently using this in my own project and it has worked pretty well for me thus far.
Here's something else people may be interested in.
https://github.com/PE-INTERNATIONAL/shiro-jersey#readme
The first thing to understand about REST is that its a Token based resource access.Unlike traditional ways, access is granted based on token validation. In simple words if you have right token, you can access resources.Now there is lot of whole other stuff for token creation and manipulation.
For your first question, you can design a Restfull API. Credentials(Username and password) will be passed to your service layer.Service layer then validates these credentials and grant a token.Credentials can be either simple username/password or can be SSL certificates. SSL certificates uses the OAUTH protocol and are more secure.
You can design your URI like this-
URI for token request-> http://myservice/some-directory/token?
(You can pass Credentilals in this URI for Token)
To use this token for resource access you can add this [Authorization:Bearer (token)] to your http header.
This token can be utilized by the customer to access different component of your service layer. You can also change the expiry period of this token to prevent misuse.
For your second question one thing you can do is that you grant different token to access different resource components of your service layer. For this you can specify resource parameter in your token, and grand permission based on this field.
You can also follow these links for more information-
http://www.codeproject.com/Articles/687647/Detailed-Tutorial-for-Building-ASP-NET-WebAPI-REST
http://www.vinaysahni.com/best-practices-for-a-pragmatic-restful-api
I have faced the same problem before. Login does not translate nicely to resource based design.
The way I usually handle it is by having Login resource and passing username and password on the parameter string, basically doing
GET on http://myservice/login?u={username}&p={password}
The response is some kind of session or auth string that can then be passed to other APIs for validation.
An alternative to doing GET on the login resource is doing a POST, REST purists will probably not like me now :), and passing in the creds in the body. The response would be the same.