I have a client, which calls a service (passing it a user id and password). The first service can validate these credentials against users in a database. The first service then needs to call another service, but this second service cannot be passed the user id and password given to the first service (this is a requirement outside of my control).
The services will most likely be on different domains and both exposed to the internet (so security is a big issue here).
I am therefore looking at options for how the second service should check/validate that it is being called by my first service (and not by someone else trying to impersonate it).
One idea I've had is to add an additional service that acts as an authentication service, this could issue a token that is then passed to the second service which in turn calls the authentication service to check the token. Another idea (from a colleague) has been to assign an SSL certificate to each service, and check the certificate when the call comes into Server B - I haven't seen certificates used in this way though so am not sure if it's viable.
This is still at the design stage, so I am open to alternative ideas/approaches.
If you need an easy fix, then creating an extra set of credentials for service A so that service B can be sure it's called from an authorized party without knowing the clients credentials might be enough.
In the long run, something like Windows Identity Foundation sounds exactly like your plans with the authentication service.
So, both A and B parties are exposed to the internet (distrusted environment). Taking into account security requirements what you need is mutual WCF authentication. Certificates are the easiest way to achieve the goal - your server has to ensure that proper client calls it and the client has to be sure it calls proper server (DNS attacks, etc.). That means each party must have public key of the other to authenticate. Check this article for the details on how to configure your server and client.
Related
This question is not about HOW something can be done. Everything is working fine. I like to know, if it is "ok" to do the authentication / authorization process inside a WCF message inspector.
Currently I am working on a client/server application with a WPF client and a self-hosted WCF server. The used protocol is Net.Tcp and all SOAP messages are AES256 message-encrypted and signed. Also all send SOAP message-headers are always message-encrypted and signed.
The complete auth process looks like this:
Both server and client are always sending certificates to authenticate each other
Client receives a list of all endpoints it can connect to
Client sends User/Pass to authenticate and gets a session-id from the login-service
The session-id, the user-id and all user-rights associated with the user-id are stored into RAM in a singleton service, which is available system-wide inside the server application.
On every further request after the first login, the client only sends the session-id and a certificate inside a custom message-header, no more user/pass combination.
The situation:
Before a request from the client reaches any webservice operation, a message inspector reads the session-id and the requested webservice operation. It then uses the available singleton-service to determine if the session-id is still valid and if the associated user-id has the right to do this webservice operation. If not a fault-exception is thrown.
The question:
Is there anything wrong, to do the authentication / authorization process inside a WCF inspector?
If its working then dont break it :) But to answer you, I have put some insights for your to consider:
1- For service operations that dont require authentication, you would have to change the inspector code to whitelist them. This contradicts with the open close principle where your class must be open for extensions and closed for modification.
2- If later on, you decide to modify your authentication mechanism and use a third party component, you would have to modify your interceptor code drastically.
I usually use the WCF inspector to pass the token and other related info into my services classes where i normally implement the cross cutting concerns (Validation, Authentication, Authorization, Logging and exception handling). When you inject your authorization engine into your services, it becomes easier for you to first swap the mechanism when need be, second unit test your service method in isolation of whatever authentication mechanism you are using.
I am developing a WCF based ERP application. My service is using Per Call instance mode and Concurrency mode Multiple.
I am using custom UserName/Password validator for authentication. Since for Per Call services, services instance is created for each call,
I am not sure how to deal with the authentication.
Is it the correct approach to send user name and password with each service request and validate
on the server side?
If so, at the client side, should we store the user name and password entered by the user?
If there are any better ways of doing user name/password based authentication, please let me know.
You can pass credentials in SOAP header instead of passing as method parameters.
For that you need to use MessageContract.
I am looking to host a WCF service accessible to a limited set of clients over the internet, as described here:
Best way to secure a WCF service on the internet with few clients
I intend to use Username/Password auth (using existing membership infrastructure) at this stage, with transport security (i.e. SSL).
I'm wondering what the recommended approach would be to processing the authentication request, when the membership database is obviously internal to the corporate network.
Options I'm considering are:
the public firewall would do SSL offload, and then the DMZ server would reverse proxy the request to the internal WCF server - I'm assuming credentials would be retained and passed through with this method, and the internal service could appropriately make use of the Membership provider to authenticate the user.
Write a dumb WCF service to sit externally which will make use of custom username/password authentication. This will call an Authentication Service internal to the network with access to membership details. Once the credentials are validated the call will then basically be passed through to the internal service that implements the required functionality.
Are both of these options possible? Are there any major pros/cons with either of them? (obviously reverse proxy is a lot less code...)
I have decided to use the second option. I already had a membership service internal to the firewall, so I will create the service to sit in the DMZ and implement a custom UsernamePasswordValidator and use it to call the membership service to validate credentials (and down the track I can then implement a custom ServiceAuthorizationManager to check roles/permissions).
Assuming credentials validate appropriately, the service will then call the main service internal to the firewall to carry out the functionality.
I'm starting in .net and wcf services, sorry if what i'm asking is wrong or has nosense. By the way, sorry for my english too.
I'm trying to build several WCF services hosted on IIS where the internet clients can login with their username / password (info stored in db). When they are logged, they can access their info, see their private documents, change their profile and more actions related to their account.
Well, in asp.net if I get the session after success login, i can build services like "GetMyDocs" and i know "who is", just checking the session username stored with the session ID when he calls the login and his session don't timed-out. But i've noticed that WCF Services are stateless, so this seems i have to send in all requests the username / pwd and check them in the DB before executing the service... always!?
Later, if i want to build a client desktop / Android / iOS application, i will use those services. They then can manage their personal and private data through those apps after a success login.
How should i handle this?
Are WCF Services the way to go or WCF aren't a good choice for that?
How can i handle the user identification with WCF? Because all my services are linked to a user and "GetMyDocs", "SaveNewConfig", "PayItem"... needs to identify who is calling.
Thanks in advance!! Regards!
But i've noticed that WCF Services are stateless
This statement is kind of wrong. Because you could easily create a "WCF-based" web service with state enabled. Furthermore, state is such a broad term that is not worth covering here. For example, you could use session state with a WCF service, or you could set the InstanceContextMode property of a service to one of the following:
PerCall
PerSession
Single
and of course, it all depends on how you configure the service itself.
If your service needs to be consumed by different clients, you should consider at implementing a RESTful service along with OAuth 2.0 or something similar where you can authenticate a request using the Basic Authentication header or by issuing an access token after a successful authentication.
There are a number of ways to provide authentication to a WCF service. One of them is by using a session (basicHttp does not support session, you have to use wshttp, or any of several other transports that support session). However, enabling session is a huge amount of overhead simply to avoid sending credentials on each request.
Session reduces scalability by quite a bit, but if you aren't worried about it... it's an option.
let's say we have a WCF service like the one from msdn examples -- c#, calculatorservice, with all the service settings on default.
if i were a hacker and i knew that calculatorservice was something important, that i want to make it stop working, i could simply hack the code for service references and make an application of my own that creates 10 clients. these clients would call a random (nonterminating) method on calculatorservice every now on then, to keep the session alive, and never close.
now obviously, since all 10 sessions are taken (or whatever the number of maximum sessions is), noone can access the calculatorservice, it is completely blocked!
how can we protect our services from that?
If you're afraid a malicious hacker will clog up your service with bogus sessions, then don't use sessions! Use the "per-call" approach, and authenticate your users, e.g. make sure they're either in your Windows/AD domain, or they do have knowledge of a username/password to make calls to your service.
Should a malicious hacker get a valid username/password combination for your service, then you cannot do much to stop him from constantly sending you 10 or 20 concurrent requests and clogging up your service - at least not at the WCF service level. WCF provides service throttling behaviors to prevent 1'000s of malicious concurrent calls in order to protect your server from being flooded and crashed.
If you need to keep away specific IP's or ranges of IP's, you'll have to approach that earlier on - in your routers/firewalls - the WCF service can't really help you there.
The best thing to do would be to secure your WCF service:
In this article I will show you how
you can implement security on a WCF
service. There are many options and
extensibility points for implementing
security in WCF. You can also use
specific products, such as the Windows
2003 Server Authorization Manager,
together with WCF to implement the
authorization requirements of a
solution. Out of the box, WCF supports
Windows credentials, Username Tokens
and X.509 Digital Certificates as
security credentials.