I'm looking for a simple way to encrypt my soap communication in my C# Web-Service.
I was looking into WSE 3.0 but it seems Microsoft dropped support for it, and therefore it's not straightforward to use.
It seems WCF could've been an option but I prefer not to upgrade from .NET 2.0 .
Any simple, straightforward encryption method?
I think this can help; last year we used this to compress the webservices and it performed very well, I believe it could be enhanced with encryption classes;
Creating Custom SOAP Extensions - Compression Extension
Anything you do to provide "encryption" that isn't using SSL/TLS is likely to be vulnerable. Now you have to ask yourself, is it worth burning dev hours you could be spending on features on a rubber-chicken security measure? Maybe it is.
.NET APIs like DPAPI and the Win32 crypt32 API make it easy to encrypt blobs of data with static keys. But how will your clients receive the keys? Any installed SOAP client will have to either have the key burned into its configuration, or receive it over the insecure Internet.
This is the problem SSL/TLS solves for you; the dance you do with TLS certificates is what solves the problem of communicating public keys over untrusted channels.
Perhaps I'm being naive, but would
forcing the communication to be via
https be acceptable? I develop web
services that run on 2.0 and have had
success with just getting IIS to
enforce https on the virtual
directory.
That would be the simplest way to go
probably, but unfortunately I don't
have control over the IIS
configuration, and can't guarantee
that it can run https.
In that case, perhaps the best bet is to either case-by-case encrypt portions of the SOAP messages (after all, you may not need the entire message to be encrypted - just certain sensitive fields?), or you could opt to use an HttpModule to intercept all the messages and operate on the contents. In either case you're probably going to have to provide custom proxies.
Perhaps I'm being naive, but would forcing the communication to be via https be acceptable?
I develop web services that run on 2.0 and have had success with just getting IIS to enforce https on the virtual directory.
Alternatively, or in addition, you can check the HttpRequest.IsSecureConnection property.
We actually use WSE 3.0 in our web services, which were originally developed pre-WCF. For security, we use a SAML token based system built on the Cryptography classes in System.Security.
It works very well. However, this method is by no means "simple".
You can use parameters encryption in C# using the System.Security.Cryptography extension.
Encrypting your parameters and decrypting them would be harder but much more secure.
How To: Encrypt and Decrypt Data Using a Symmetric (Rijndael) Key (C#/VB.NET)
I'm using this aproach for an OTP (one time password) web service, and it works fine for me.
Related
Context
I'm currently in the works of creating a public mobile application.
This application will be made available through the App Store and Google Play Store.
The user will be able to perform certain actions in the application, which will then be posted to an API.
The application will be made with Xamarin Forms.
Question
I want to secure this API to prevent anyone other than the App from making any post requests.
From what i have read the best way to go about this would be to implement an OATH2 flow.
However; i wouldn't like for a user to have to sign-in or register to any type of service.
How would i go about validating the post requests that come into the API and make sure that it's not someone that is impersonating my mobile application?
Things i have thought of:
Api-keys or clientsecrets. As it seems there are pretty easy to extract from a mobile app.
Certificate validation. (Couldn't find much on this for mobile client - server architecture)
Generating some type of checksum over the contents that i can validate serverside. However the code for this would have to be available client side or there would have to be an endpoint providing the checksum. But this would just move the problem imo.
?
Any and all critic and feedback is welcome.
i do apologize if there's anything obvious that i have missed during my research on this matter.
Thank you for your time.
Check the following for android: https://developer.android.com/training/safetynet/attestation
The SafetyNet Attestation API provides a cryptographically-signed attestation, assessing the device's integrity. In order to create the attestation, the API examines the device's software and hardware environment, looking for integrity issues, and comparing it with the reference data for approved Android devices. The generated attestation is bound to the nonce that the caller app provides. The attestation also contains a generation timestamp and metadata about the requesting app.
For iOS, you can check the: https://developer.apple.com/documentation/devicecheck
As mentioned in the documentation, non are foolproof and should be joined with other security measures, but it's better than nothing nonetheless.
The Difference Between WHO and WHAT is Accessing the API Server
From what i have read the best way to go about this would be to implement an OATH2 flow.
OAuth2 only identifies who is in the request, not what is doing the request.
This is a common misconception among developers of any seniority, therefore I will link you to an article I wrote that has a section dedicated to explain this. I wrote a series of articles around API and Mobile security, and in the article Why Does Your Mobile App Need An Api Key? you can read in detail the difference between who and what is accessing your API server, but I will extract here the main takes from it:
The what is the thing making the request to the API server. Is it really a genuine instance of your mobile app, or is it a bot, an automated script or an attacker manually poking around your API server with a tool like Postman?
The who is the user of the mobile app that we can authenticate, authorize and identify in several ways, like using OpenID Connect or OAUTH2 flows.
So think about the who as the user your API server will be able to Authenticate and Authorize access to the data, and think about the what as the software making that request in behalf of the user.
Your Questions/Affirmations
I want to secure this API to prevent anyone other than the App from making any post requests.
And about GET request?
Depending on the data your mobile is asking to be delivered by the API server, the GET request may have the same degree of importance in terms of security then any POST request.
Let's say you app is doing GET requests to get sensible data like PII(Personal Identifiable Information), then without them being protected you are just opening your API server to be easily abused by attackers, and this results in the so called data breaches that can have a huge legal and financial impact for the business and their customers. For example in Europe with GDPR a data breach will have huge fines, specially when they conclude that the API was not properly protected to avoid automated data extraction.
Anyone can learn how to perform a MitM(Man in the Middle) attack to see how the mobile app does the API requests in order to automate them. I wrote the article
Steal that Api Key with a Man in the Middle Attack that illustrates how easy a MitM attack can be done:
In order to help to demonstrate how to steal an API key, I have built and released in Github the Currency Converter Demo app for Android, which uses the same JNI/NDK technique we used in the earlier Android Hide Secrets app to hide the API key.
So, in this article you will learn how to setup and run a MitM attack to intercept https traffic in a mobile device under your control, so that you can steal the API key. Finally, you will see at a high level how MitM attacks can be mitigated.
However; i wouldn't like for a user to have to sign-in or register to any type of service.
Well then you are left with only one way of protecting the API request, and is to know what is doing the request, and now you bought yourself a very hard problem to solve, but not an impossible one.
Your Solutions
API Keys or Client Secrets
Things i have thought of:
Api-keys or clientsecrets. As it seems there are pretty easy to extract from a mobile app.
They are indeed very easy to extract, but you can make them harder(but not impossible) to extract by static binary analysis as I explain in the article How to Extract an API key from a Mobile App with Static Binary Analysis:
The range of open source tools available for reverse engineering is huge, and we really can't scratch the surface of this topic in this article, but instead we will focus in using the Mobile Security Framework(MobSF) to demonstrate how to reverse engineer the APK of our mobile app. MobSF is a collection of open source tools that present their results in an attractive dashboard, but the same tools used under the hood within MobSF and elsewhere can be used individually to achieve the same results.
Spoiler alert is that the best way to hide secrets from the above article is by using the JNI/NDK interface to hide them in native code:
Using Android Studio 2.2 and higher, you can use the NDK to compile C and C++ code into a native library and package it into your APK using Gradle, the IDE's integrated build system. Your Java code can then call functions in your native library through the Java Native Interface (JNI) framework.
Well now you just use a MitM attack to extract them and we are back to square zero? Well not exactly, because more layers of defense you apply, more the attacker needs to peel and be willing to spend the time on it, but much more can be done to upset them.
Certificate Pinning
Certificate validation. (Couldn't find much on this for mobile client - server architecture)
You can't find because certificate pinning is usually only done by the mobile app as I show in the article Securing HTTPS with Certificate Pinning:
In order to demonstrate how to use certificate pinning for protecting the https traffic between your mobile app and your API server, we will use the same Currency Converter Demo mobile app that I used in the previous article.
In this article we will learn what certificate pinning is, when to use it, how to implement it in an Android app, and how it can prevent a MitM attack.
So why not doing the same sever side? Well because once the app is release anything on it is public, therefore the certificate private key you would to ship with the app to allow the API server to pin against would be easily extracted with static binary analysis or during runtime with an instrumentation framework like Frida
Inject your own scripts into black box processes. Hook any function, spy on crypto APIs or trace private application code, no source code needed. Edit, hit save, and instantly see the results. All without compilation steps or program restarts.
I can imagine you now looking where is the link to the my article with an example of using Frida? Sorry, but I don't have yet an article with a Frida example :(
Digitally Signing Requests with HMAC
Generating some type of checksum over the contents that i can validate serverside. However the code for this would have to be available client side or there would have to be an endpoint providing the checksum. But this would just move the problem imo.
Yes you are correct, the problem would have to have the code in client side, but having an endpoint providing the checksum would only move your problem into two backends, because then you would need to ensure that the checksum endpoint would only sign request from your mobile app ;)
HMAC:
In cryptography, an HMAC (sometimes expanded as either keyed-hash message authentication code or hash-based message authentication code) is a specific type of message authentication code (MAC) involving a cryptographic hash function and a secret cryptographic key. As with any MAC, it may be used to simultaneously verify both the data integrity and the authenticity of a message.
Other Solutions
How would i go about validating the post requests that come into the API and make sure that it's not someone that is impersonating my mobile application?
As I said before you should not limit this to POST requests, instead you should validate that any request to the API server is indedd from *what you expect, your genuine and untampered mobile app.
Android SafetyNet
This is often the one recommended, and is a very good starting point, but it's not designed to be used as a stand-alone defence, as per Google own words:
The goal of this API is to provide you with confidence about the integrity of a device running your app. You can then obtain additional signals using the standard Android APIs. You should use the SafetyNet Attestation API as an additional in-depth defense signal as part of an anti-abuse system, not as the sole anti-abuse signal for your app.
You can read my answer to the question Android equivalent of ios devicecheck for a more detailed explanation for what you need to pay attention for when implementing SafetyNet.
iOS DeviceCheck
Until recently the device check was very limited in is usefulness, but now with iOS 14 they also the app test feature to sign the requests sent to the API server, but it still have some limitations, but I have not had the time to full explore this new feature thus I will not be able to give the same detailed explanation I gave for what to watch for when implementing the iOS device check, but I can recommend you this article:
It’s important to know that App Attest is not a “is this device jailbroken?” check, as that has been proven over and over to be impossible to perform. Instead, it aims to protect server requests in order to make it harder for hackers to create compromised versions of your app that unlock premium features or inserts features like cheats. Note the word harder: as jailbreakers have physical access to their devices, nothing will completely safeguard you from fraud in this case.
If you have a large user base, Apple recommends you to gradually roll this feature as requests to attestKey are rate limited. After carefully rolling it out for existing users, you can guarantee that it will only be called for new users.
So while this is a very good improvement from Apple it's rate limited, therefore care must be taken in what requests we decide to use it and how frequently the attestations are performed.
Mobile App Attestation
This is a concept that you can build on top of the Android SafetyNet and iOS device check solutions, and you can read my answer to the question How to secure an API REST for mobile app? in order to understand more about how the Mobile App Attestation concept works. You want to read about it in the section "A Possible Better Solution".
Do you want to go Going the Extra Mile?
In any response to a security question I always like to reference the excellent work from the OWASP foundation.
For APIS
OWASP API Security Top 10
The OWASP API Security Project seeks to provide value to software developers and security assessors by underscoring the potential risks in insecure APIs, and illustrating how these risks may be mitigated. In order to facilitate this goal, the OWASP API Security Project will create and maintain a Top 10 API Security Risks document, as well as a documentation portal for best practices when creating or assessing APIs.
For Mobile Apps
OWASP Mobile Security Project - Top 10 risks
The OWASP Mobile Security Project is a centralized resource intended to give developers and security teams the resources they need to build and maintain secure mobile applications. Through the project, our goal is to classify mobile security risks and provide developmental controls to reduce their impact or likelihood of exploitation.
OWASP - Mobile Security Testing Guide:
The Mobile Security Testing Guide (MSTG) is a comprehensive manual for mobile app security development, testing and reverse engineering.
I have a web api 2 that I want to host on azure-app-service. The service should be called by javascript applications so as far as I know it has to be open to public (right?).
However, if I let it be totally open it is vulnerable to DOS. What is the best way to do that?
The first thing that came to my mind was to implement a custom IP Filter that keeps requests from last x minutes and let the one with less than y occurrence pass.
Is there any other way? Is there any specific way to do it on the azure without writing code?
This is not a broad question! I think it is clear what I am asking!
I have a service on Azure and I want to protect it from overusing. How broad is that?!?!
If it's a public API (ie. something a mobile app would talk to), it has to be.. well, public of course. :)
If your users have to sign up before consuming your API (or if this is an option), you could use API keys. That does not prevent DoS, and is not a form of authentication if given to clients, but at least you can quickly revoke offending keys to somewhat mitigate DoS.
Other than that, your primary concern with regard to DoS is application level DoS. You should try to avoid API calls that put a strain on your backend, limit response sizes (which probably implies paging on a client), etc. With these things done in your API, let your provider deal with the network level stuff.
By default azure services are protected against DDOS,MITM attacks and all communication is via https and encrypted.
As far the application design goes you need to take care of the following ;
SQL Injection,Session hijacking, Cross-site-scripting, Application-level MITM and Application-level DDoS.
Further you can do vulnerability check on your app services using Tinfoil security scanning tests.
https://azure.microsoft.com/en-us/blog/web-vulnerability-scanning-for-azure-app-service-powered-by-tinfoil-security/
Also using azure API management service you can use the API gateway to control API calls, routing, enforce usage quotas and also do throttling based on the traffic to the API.
https://azure.microsoft.com/en-in/documentation/articles/api-management-howto-product-with-rules/
I have to come up with an integration process to allow existing system to use external data providers. The system is a medical timetable web site, using ASP.NET MVC, that allows the patients to schedule their appointments to doctors.
As far as I go you can see on a figure below:
All the providers must expose my contract ISuperIntegration which will be develop by me. I won't be developing External service 1 and External service 2, they will be developed by other companies.
Here the issue comes: basing on the concept of that I could require the way providers should setup their services to communicate with my website properly, I want to forbid for another third party clients consume "External Service 1" and "External Service 2", Or at least make it difficult to do that.
Here is a list of stuff I am setting:
ISuperIntegration interface. It contains operations related to my domain such as GetSchedule, GetDoctors and so on.
Transport protocol. I don't want it to be complicated so I'm thinking about using HTTP.
And could define some general recommendations but they could be easily avoided.
At the moment I'm thinking of using HTTPS with certificate authentication. It would require the implementer to setup their infrastructure so my web site could properly consume the data.
If I would go with basic HTTP, the implementer would just leave their service to be easily consumed by anyone else, which I don't want.
I hope my question is clear. Will be happy to give any other explanations you want.
I'll really appreciate any your responses, commits. Thank you!
I'd always use HTTPS for things like this. Let's just say that's the cost of doing business. You simply cannot have anyone with a sniffer grab that kind of traffic out of the sky. There's a reason why all banking etc. use HTTPS for things that should be secure.
Apart from that, web services have pretty standard mechanisms for security, I'd recommend looking at OAuth over HTTPS. There are plenty of implementations for that.
If your talking about basic web sites, I'd use a standard security mechanism as well like group based security (which boils down to a username + password). Again, there are plenty of implementations for that.
Basically my main word of advice is: don't go inventing stuff when it comes to security. If you're not an expert, you're probably going to get it wrong, and end up with something that can be intercepted by a third party or (much) worse.
You have several options:
Basic authentication over HTTP.
PRO. Easy to implemet
CON. UserCredentials was going in clear text throuh the network
Implement WS-Security with WCF. For example, they can sign their requests.
PRO. Easy to implement with WCF
CON. Java clients can faced with problems
You can force clients to use HTTPS.
CON. You should setup your web server.
You are like Oracle, they want people to develop in Java language but they also want to forbid competitors to run the Java compiled code on non Oracle's virtual machines, or at least make it difficult to do that :)
So you can do the same by protecting your interface with patent or copyright law. However, I doubt that it is patentable or copyrightable :)
Considering the privacy sensitivity of the data, IMHO it must be encrypted while in transport. Hence HTTPS not HTTP.
Authentication of your service to those providing services to you: well essentially it's up to them, not up to you who they expose it to, similarly how they want it protected is their call. Now assuming you do have a way to make them do the right thing...
Client certificates aren't that expensive nor prohibitive in setup to get up and running. But you do need to register the client certificate (every time it is renewed!) with the server in order to get the needed authorisation (just recognizing it's a valid cert isn't enough: anybody can apply for a (validly signed) certificate ...) .
But all that is relatively painless and rather well documented around the web, and it can be done on almost any platform of choice.
As several people mentioned these earlier you can't guarantee that those external companies will expose your service with specific security settings, it's up to them.
If you are responsible for developing MVC application and WCF service you can only force someone to use specific security settings on the layer between your WCF services and those External 1 and 2 providers.
Btw, here is a good tutorial that can be useful if you want to improve your knowledge about how to configure WCF security.
How External Services expose your service it's up to them. Just image that this is normal web 'proxy' behavior.
Maybe the architecture which your company adopted it is not the best for this solution
I need to call a .NET SOAP webservice in a secure way. It must be secure in such a way that others can't call the WebService methods, and also it should not be possible for "the middle man" to understand the content of the messages.
The caller will also be a .NET webapplication installed on another IIS.
I can design the webservice methods as I want, so no restrictions there.
I have been researching HTTPS/SSL with certificates, but I don't know if it actually solves my problems in a good way? For example, it would be anoying if the certificates has an expiration date, although it's not a showstopper in any way.
So how would I go about this in a good way..?
Thanks for any help.
As #BrokenGlass said, SSL only encrypts the traffic between points. It doesn't handle securing individual functions from usage without authorization. Here is a good article on just such a topic using SOAP headers:
How to: Perform Custom Authentication Using SOAP Headers
This can be mixed with any form of authentication except Windows Integrated. To use Windows authentication, you'll need to have a separate library which accesses the Active Directory through the DirectoryServices namespace.
Assuming you control the infrastructure then keeping the server that is providing the web services behind a firewall so it's accessible only from the web servers and implementing IPSec should provide the necessary security.
From the software point of view, this article contains all you need to know about protecting the service interactions.
HTTPS/SSL works fine. Just make sure to renew your certificate in time to avoid warnings and messages for your client.
I need to call a .NET SOAP webservice in
a secure way. It must be secure in
such a way that others can't call the
WebService methods, and also it should
not be possible for "the middle man"
to understand the content of the
messages.
HTTPS/SSL only solves the "middle man" part of what you want to achieve. You would still need proper authentication in place on your web service. You could do this i.e by using the built in Forms authentication and providing a Login method that returns your authentication ticket.
This the situation: I have one webservice without SSL, which provides two pages for the other web application. When the user submits these pages, an XML file with private information is sent to the webservice.
How can I provide the necessary privacy protection on the XML file? Is the one certificate good enough to give the appropriate security?
I'm not sure about this one, and am in the preparation phase of a project... So need to know the involved work on this part...
As an alternative to SSL you could encrypt the file yourself using any of the algorithms available in using System.Security.Cryptography but then you have to work out a mechanism to exchange your key(s).
However by far the easiest way will be to have both web services using SSL endpoints. That will take care of all your confidentiality, integrity and identity considerations in one fell swoop.
Certificates are tied to the hostname of the server (or, with wildcard certificates, all the hosts in a domain). So if the two services are on the same host, then both can use the same certificate.
If they are not on the same host there will be no transport security on the non-SSL service unless this is added separately. WCF has support for message (or part of message) encryption.
The simplest solution is certainly to use TLS, ex-SSL (widely supported in every programming language).
There is no need to buy a certificate (and it brings no extra security, it is mostly there to make PHBs feel better): either create self-signed certificates or set up your own CA.