Jwt authenticaton in c# wpf application - c#

I started learning c# two days ago so I don't have much experience with the .net framework. I want to create an application where the user can input a username/password combination and the login information will be sent to the server for verification. I thought of doing it in the following way by using a PHP script but its not really efficient/secure since everyone will have access to the script.
1) client->Get username/password from user and send the username to the server
2) server->Find out if the user is in the database and send a random number back
3) client->Create an MD5 hash out of the number then create an MD5 out of the passwordMD5+numberMD5\ and send it back to the server with the number
4) server->Create and MD5 hash from the numberHash+passwordHash and compare it the hash received by the client
The other problem with the authentication above is that I want to periodically check if the user is authorized to access the application after it has sign in and I don't want to keep asking for numbers from the website every time the user wants to access something in the application. I did some research and found out about JWT authentication, but the issue I'm having now is implementing JWT authentication in an efficient way. If the user signs into the application it will send the username/password to the server but it doesn't seem safe to send plain passwords the the server. I also want the tokens to have a time limit after it is created. I was thinking about creating a new database for expired tokens and another one for valid tokens and check those database every time the user tries to access information from the site. I was about implementing some kind of API with asp.net core but I found out the host I'm currently using does not support .net. Now I'm thinking about using a server(maybe azure but I'm not familiar with it) just for generating the keys and when the client tries to contact my website I check if the key exist in the invalid key database and block the connection otherwise if its not in the valid key database insert it.
My questions:
1) I there a better way of achieving this other than the way above.
2) If not then what would be the best way of checking the keys to give client access the website database.

Have you possibly looked into using Auth0 for protecting your server and your WPF application? Check out https://auth0.com/docs/quickstart/native/wpf-winforms for more information as you can probably implement this using the free tier they offer.

Related

Token Login Between C++ and C#?

Here is what I am trying to do. I have an asp .net website in C#. I also have a game server and game both written in C++. The game server is hosted where the web site is.
What I want is for users to be able to automatically login to the website when they click a button in the game. That is, the game makes a request to the game server, and some how a token is generated that can be used to log into the website.
So the server might sendback something like:
www.contoso.com/tokenlogin?userid=67456353&token=576434324431fgdsastr
I'm aware that an easy solution to this is to just create a token in the database that the web site can read. If I cannot find a better solution, I'll do that, but ideally I would like to generate a token whereby for the next 5 minutes, passing this token with this userid will login that user as if they had passed their password.
A simple idea I had for this was to hash their password hash and username which would work, but this does not have a timestamp.
Does anyone have any suggestions for this? Can MySQL generate tokens that can be validated? I'm using MySQL. I don't mind a solution that uses the database, I just don't want a solution that writes to the database.
Thanks
Generating a random token and saving it to the database (with a timestamp) is definitely the easiest solution. Failing that (or another way of communicating between processes), what you can do is generate signed tokens in your server which can be validated by your web app. So your server would create a token like:
{userid: XXX, issueTime: YYY}
Then, you encrypt this data with an authenticated encryption method like GCM, base-64 encode it, and append it to the URL. Your web app decrypts and validates the data, and if the timestamp is ok logs the user in. This requires a shared key between the processes, which you must not lose.

Using C# to log into RoR (Devise) app

I have a RoR web app that currently leverages Devise for user authentication. From what I understand, passwords are stored using the BCrypt algorithm and include both a hashed password and password_salt, which is stored for each user in my users table.
In conjunction I have a Microsoft Office add-in that was developed in C#. I need to be able to log users in from the add-in by calling to the users table and validating the password they entered in the add-in against the hashed password stored in the users table.
Unfortunately when I attempt to use BCrypt via C#, I'm unable to successfully log into the app from the add-in. I've looked all over for examples on how to achieve this, but have come up short.
Could anyone point me in the right direction? And/or do I also need to parse the password_salt? Thanks in advance for your time and assistance.
EDIT: I see that BCrypt no longer requires a separate password_salt.
EDIT2: I'm using devise-encryptable, and in my initializers/devise.rb, I have: config.encryptor = :authlogic_sha512
and a config.pepper, which is set to a long hash. Should C# now use sha152 instead of BCrypt?
I would suggest that you add an API to your application that allows your to send username/password pairs over HTTP and receive an authentication token when successful.
This would be much easier than attempting to interface with the database directly, as devise has already done all the hard work for you.

Can I avoid storing MS Exchange credentials while still being able to authenticate (against EWS)?

I'm building an application that syncs data between users' Exchange Server accounts (version 2007-2013 supported) and the application.
The application can't use impersonation (at least not in the typical case) as users could be on any number of domains and exchange servers.
I know I'm going to have to ask for their username/email-address and password initially. However, I really don't want to be responsible for storing these credentials if I don't have to (even if they are encrypted, I'd rather not).
I'm not sure what questions to ask, so I'm going with these:
How does Exchange Server authenticate? Do the user's credentials get sent directly to the server as they are, or are the hashed together before being sent across the wire? If they are hashed, how can I get/generate this hash for re-use on successive authentications?
Does Exchange Server send some sort of authentication token that can be re-used later (and forever, until password change or invalidation)?
If you know of a solution to the problem, that the answers to these questions won't address, please do provide it instead.
Active directory federation services is exactly for such tasks. You can read about it there.
As mentioned by Kirill, ADFS 2.0 is one of the best solution for your task. You can also look into other SSO implementations as well. Though the main goal of SSO implementation is to maintain single Login state for multiple application (thereby reducing multiple Login prompt for each application), some of your application goals seems relevant. Please do a thorough research on all the tradeoffs before heading to the sso implementation since there is a small degree of complexity involved during implementation. SSO suits best if you are considering integration of multiple application in the future with the exchange server.
To answer some of your questions (in the same order - considering an SSO scenario with ADFS 2.0):
The authentication to exchange server will be done via ADFS 2.0 (Which provides security tokens (STS service) - to your application after authenticating with AD/ main Directory service). All the communication is encrypted and token signing certificates are used for Integrity and confidentiality.
The lifetime of Security tokens sent by ADFS 2.0 can be configured and reused as required. Please see this blog post for more details.
Also you can configure the ADFS 2.0 (Federation Service) to send only the relevant claim values (like username and email address) to the application, thereby improving the data security.
The System.Net.CredentialCache should work to suite your needs. The WebCredentials is a wrapper for the System.Net.NetworkCredential. Depending on the connection type/domain ect you should be able to utilize System.Net.CredentialCache.DefaultNetworkCredentials or System.Net.CredentialCache.DefaultCredentials
perhaps you should take a look at this Links Connecting to EWS by using the EWS Managed API , Connect to Exchange - Getting Started Tutorial? hopfully it will give you a new idea how to solve your problem :)
because if i understand the information correctly you maybe over think problem but i haven't any experiences so i could also absolute wrong
Bottom Line
If you can't configure anything on the server, there's no automatically generated token to use. It's unfortunate, but you're facing the same general problem that web browsers have--saving the password.
It's worth noting that any authentication needs to be over SSL (an https connection) to prevent a third party listening in on the authentication.
Password storage thoughts:
My suggestion is then to be somewhat creative when storing the password. You can use a keyed encryption algorithm, and then use a hash to generate the key, letting you arbitrarily choose what goes into the key. You would want at least 3 pieces of information going into this: something unique to the device, something unique to the app, and something unique to the exchange server.
For example:
a unique id given by the device (it doesn't matter whether or not this value is app-specific or not, merely that it is consistent)
a (long) string of information compiled into the app, possibly keyed to installation specific values, say the time when the app was first used
something unique to the destination, like the DNS name and perhaps some more specific server info
If you're willing to provide the option to the user, you could have an authorization PIN of some kind that would also be added to the data.
All this data gets put together in one byte array and hashed. The hash (or part of it, or it twice, depending on the hash size vs. the key length) is then used as the key for the encryption of the password.
You could also include some check information along with the password to be able to check client side whether or not the password was decrypted correctly. (If the wrong data is hashed, the wrong key is generated, and the wrong result comes from the decryption).
It's worth noting that all the information to be used for putting into the hash needs to be stored on the device, which is why I would suggest a Pin to authorize the usage of the account.

C# web service password in the request to be encrypted

I am working on the web service. A user is going to be able to create a user account using a form on different asp.net project. So when the user enters the password information I need to store that encrpted in a database. But now when the user sends the user credentials through for a web services then I need to the user to send that password encrpted for security purposes.
Now how can we both have the same ecrption procedure so that I will be able to validate the request.
What you want is to use HTTPS connection to transfer the password from the user to the server safely. Here is the explanation on how to set up the development environment with IIS for HTTPS - scottgu link.
HTTPS protocol will handle the encryption and decryption and you just deal with the plain-text password on the server-side.
After that, on the server side, you compute the hash of the password and compare it to the hash stored in the database. Standard ASP.NET SQL membership provider can be used for this.
There is a good explanation from Jeff Atwood on the problems behind storing and hashing passwords - coding horror link.
If the user's browser in any way knows how to encrypt your password then you kind of lose the point and a smart hacker could extract that encryption.
Using SSL to pass information directly to your application is essentially doing what you're asking and is the accepted secure way to receive the password. You will just have to check against your encrypted version in the database.
Your app receives the password raw (browser and server have taken care of encrypt/decrypt), then your app encrypts it and looks in the database for a match.
The other way this is done with web services is using a single login step that returns an expiring token which is used for further communication. OAuth is the most popular so do some googling on that.
You can encrypt the info you need using System.Security.Cryptography;
have a look at the below:
http://jakkaj.wordpress.com/2007/10/27/encrypting-and-securing-web-service-traffic-without-ssl/
Bear in mind that anything you do to provide "encryption" that isn't using SSL/TLS is likely to be vulnerable

How to implement Client Authentication with ServiceStack.Net

I am developing web services using the servicestack.net library.
In my scenario, the web services will be called from a WPF application. I need the ability to authenticate that only an approved client app is calling my service.
Is this as simple as hardcoding a "username" and "password" in the client application? This certainly does not seem like the proper approach. Is there a better way?
EDIT
In addition, on the client end, Users themselves will be able to login with a username/password and initiate requests to the service(not sure if this effects anything, so I thought I would mention it),
For more background information about Authentication in ServiceStack see this question.
Normally you would authenticate users not clients which you seem to be doing in addition. But if you're trying to lock down services so their only accessible via a specific set of clients you should look into employing some PKI into your client and server.
Basically something along the lines of: the client sends an additional token at login with an encrypted version of the user:password together with a private key embedded in the app. The server has the client public key and so would do un extra validation step on Login to unencrypt the user:pass token and compare it with the validated user credentials.
If a PKI solution is too heavy, an alternate strategy without using encryption could be for clients to ship with a secret Guid which when they login which will send an MD5 hash version of the Guid and the current time, as well as the unhashed version of the time. If the time is within a specified threshold and the MD5 hash is valid then their using an authenticated client.

Categories