I have an application that I've been spending way too much time on trying to send an email via a service account that I setup in my google apps account.
I was wondering if should continue down this overly complex method of using a service account or if I should just use Gmail's SMTP server. The only function I need is to actually send an email.
Are there any pros/cons to simply using Gmail's SMTP server vs setting up a service account and calling Google's API to send emails? If it makes a difference this will be sort of a batch email in that it will send to many people at once.
Please consider the following:
I guess you should majorly be concerned on sending batch emails. If you don't do it right you might have problems. To avoid those problems make sure to follow the Bulk Senders Guidelines here https://support.google.com/a/answer/81126 Another factor to take into account is the email authentication. When using smtp, make sure all email sent will pass SPF and DKIM to prevent being marked as spam or worse, getting emails rejected. If you use the Gmail API then all you need to do is make sure you set up SPF by following the steps here https://support.google.com/a/answer/178723?hl=en and DKIM by following the steps here https://support.google.com/a/answer/174126?hl=en As per the GMAIL API quotas, you can use 1,000,000,000 units per day so I don't think that will be a problem. The benefit of using SMTP is that you can use SMTP RELAY https://support.google.com/a/answer/2956491 which gives you a way much higher limit when sending emails in case the Bulk Senders Guidelines is something that won't work for you.
In summary, if all you are looking for is to send batch emails, then I guess going with SMTP is easier. Hope this helps!
For just ordinary usage by one user, SMTP will work fine except API has the advantage on server-side for the sysadmin for security.
Differences are theoretical for web service, web application development. Both are ways to give access or to interact with their server. Nowadays REST is used for integrating their service for custom software development, their one part will have F/OSS implementation like OAuth. With REST API we get some extra advantages but that is for integrating for professional grade software development. SMTP relay is less secure.
Take as 2 servers with two technologies. That "Google Apps Service Account" one modern web application supporting Representational State Transfer(REST) API to give access to resource, interact with the server. SMTP one is older web software using Simple Object Access Protocol (SOAP). You can search with SOAP vs REST to understand the basics.
Google SMTP Server is traditional SMTP traditional SMTP relay service. Advantages are -- easy to setup by the users, lesser documentation to help the users to use etc. Disadvantage are they are less secure, plus all inherited disadvantages of SOAP.
"Google Apps Service Account" is modern web application developed in service oriented architecture providing RESTful API for server to server communication over TCP/IP. Advantages are easy to integrate with custom software using open source authentication library (they use OAuth), REST provide more control on sending request, username-password for communication can be avoided, extensive examples of usage, more secure, granular control to operation on server, JSON response has common meaningful format etc. Disadvantages are related to common disadvantages of SOA, Web Hook, RESTful API, difficult to use by a new user etc.
In real, it is basically one web software supporting both ways. One always should use DKIM, SPF etc as anti-spoofing measures.
Related
We are developing a desktop application in C++ which is distributed to our customers. It will communicate with the server using REST API over HTTPS. We are concerned about network sniffing software, such as Wireshark. By using such tools, malicious users could record the HTTPS traffic, extract request URL, headers and body and perform requests to our backend REST API server on their own using automated scripts or Postman.
I read an article which suggests that API keys should be used to identify that requests are really sent from C++ application. However, I don't understand how API keys prevent users from sniffing traffic? If API keys are included in HTTP header, they are still easily extracted by Wireshark.
Are there any other ways for ensuring that requests to our REST API server are actually sent from genuine and unmodified C++ application that we developed? How can we ensure that even if attackers use Wireshark, they won't be able to call REST API on their own using Postman (outside of our C++ application)?
Sending the API key inside a TLS encrypted session (HTTPS) is perfectly safe as the headers are encrypted as well. The only thing that you may find in cleartext is the hostname/SNI of the server.
No, there is absolutely no way to make sure, that the requests are sent from the 'genuine and unmodified C++ application'. But if you want to raise the bar and make it way harder for an attacker to e.g. perform a Man in the Middle (MitM) attack and analyze the traffic, you can do following:
API keys are a good thing. Do it.
Pin the certificates to make MitM attack way harder to perform. Wireshark will see the traffic still, but it will be encrypted.
Obfuscate the code, so even a binary analysis becomes harder.
This will not hold back a motivated attacker, but it will raise the bar significantly and unless you are doing banking apps (which I believe you don't, as banks buy themselves security solutions out of the box from some companies specializing in security design), then it may be simply not worth it to go through all the trouble of attacking apps with such protection.
I'm building an application where I need to make a request in the client-side frontend app to an external API, and I'm at a bit of a loss for how to make this maximally secure so that only valid requests can be forwarded to this external API and not whatever anyone wants.
As a first step in security, I've made it so that the client-side app can't speak to the external API directly, but must instead hit our own server-side API, which then proxies the request to the external API, so that the credentials for hitting the external API are at least stored solely server side and not client side.
This, however, has led to the same fundamental issue - how do I secure whatever credential/authentication system I use to authenticate requests I make from the client-side app to our own server-side app?
The issue is this is an online restaurant ordering service, and so we don't expect users to authenticate themselves with say, usernames and passwords before being able to place orders necessarily, and so order placement, which triggers the external API call, isn't gated behind any username/password scheme, and must be available to all consumers of the frontend app.
What's the best practice for security here? I've enabled CORS whitelisting as a minimum practice, such that only requests from our own domain are theoretically allowed by our server side API endpoint, but CORS is trivially bypassed if someone chooses to just spoof the origin URL.
What other options are available? I'm sure I must just be missing something trivial, since this must be an extraordinarily common issue with an established best practice, but I'm just somehow failing to find it.
Thank you!
As a Developer Advocate for API and Mobile security, seeing a developer that really cares about their app security always makes me smile, especially when they already show some effort was made to secure it, therefore accept my congratulations for your efforts.
My Answer Context
I'm building an application where I need to make a request in the client-side frontend app to an external API, and I'm at a bit of a loss for how to make this maximally secure so that only valid requests can be forwarded to this external API and not whatever anyone wants.
So, you have not detailed if it's a web app or a mobile app, and once my expertise relies on mobile and API security I will be answering with the assumption that is a mobile app.
The Challenge
The issue is this is an online restaurant ordering service, and so we don't expect users to authenticate themselves with say, usernames and passwords before being able to place orders necessarily, and so order placement, which triggers the external API call, isn't gated behind any username/password scheme, and must be available to all consumers of the frontend app.
You have here a complicated challenge to solve, because you have an app that is open to the public, no user authentication/identification of any sort, but that requires rules of access to the underline resources as if it was behind user authentication and authorization, but even if it was, it would still be vulnerable to being abused.
To understand why I need to clear a misconception that usually I find among developers of any seniority, that is about the difference between who and what is accessing an API server.
The Difference Between WHO and WHAT is Accessing the API Server
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.
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.
So, in your case you cannot identify who is in the request, thus you need a solution that is able to give a very high degree of confidence to the API backend that the request is indeed from what it expects, a genuine and unmodified instance of your app.
Possible Solutions
I'm building an application where I need to make a request in the client-side frontend app to an external API, and I'm at a bit of a loss for how to make this maximally secure so that only valid requests can be forwarded to this external API and not whatever anyone wants.
This requires very advanced solutions to properly secure, thus isn't at all trivial to achieve as you may think:
I'm sure I must just be missing something trivial, since this must be an extraordinarily common issue with an established best practice, but I'm just somehow failing to find it.
And yes, it's a common issue that often is neglected or not addressed properly, and the first step to solve it is to have a clear picture about the difference between who vs what is in a request, otherwise the devised solutions will fail to address the issue properly.
For Mobile Apps
Here I recommend you to go through this answer I gave to the question How to secure an API REST for mobile app?, especially the sections Hardening and Shielding the Mobile App, Securing the API Server and A Possible Better Solution.
This answer will show you several solutions, like WAFs and UBAs, but ends with a recommendation to use a Mobile App Attestation concept.
In a nutshell the Mobile App Attestation will allow the API backend to have a very high degree of confidence that the request is indeed from what it expects, a genuine and modified instance of the mobile app.
For Web Apps
You can learn some useful techniques to help your API backend to try to respond only to requests coming from what you expect, your genuine web app, and to do so I invite you to read my answer to the question Secure api data from calls out of the app, especially the section dedicated to Defending the API Server.
Do You Want To Go 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.
For Web Apps
The Web Security Testing Guide:
The OWASP Web Security Testing Guide includes a "best practice" penetration testing framework which users can implement in their own organizations and a "low level" penetration testing guide that describes techniques for testing most common web application and web service security issues.
Ultimately your client needs to perform some operation on 3rd party API.
So we know that some operations should be allowed, and based on your description we also know that not every operation should be allowed.
So your security should be based on this premise. Don't create a dumb proxy that forwards every single request, but your intermediate API should only specifically allow the operations that you want it to allow, based on the rules you set.
If you don't have a username & password, you probably still have some other kind of rule that identifies a person (email/phone number?), which means you can create an authentication system.
Or maybe your 3rd party service should only be called after a user completed an order with a credit card, that logic needs to exist on your API.
Am I correct in thinking that a public REST api, such as a registration endpoint can't authenticate a user. For example our endpoints should only accept requests coming from our mobile applications and future web apps.
I am pretty sure it's not logically possible. I think apple and google offer a way (acting like a ca) for the server to identify a request is coming from a registered device however that changes the API to a private one. As authentication is essentially moved to the app store so only owners of app store accounts can use it.
So keeping it completely public the only way to prevent bots attacking it is to use email confirmation with auto deletion if not confirmed in x amount of time, and IP rate limiting.
A contractor suggested we use a unique secret key hard coded in to each app however, that to me sounds illogical and completely wrong. A secret between the app and server is compromised the second a user downloads the application on their device.
So am I correct about the secret key, are there any other ways to secure the endpoint from bots? The only other thing I can think of is using a captcha.
There are 2 separate things here.
Securing Public REST APIs
You are correct that a secret, even an asymmetric one, would be compromised if the attacker downloads and reverse-engineers the application. Attackers can use debuggers, Chrome developer tools, and tools like Wireshark to reverse engineer and find the secret.
In general, an attacker can mimic the behavior of the app or user, i.e. same the same requests in very similar patterns.
The approach to this in today's industry is to filter out as many of those attackers as possible using tools like Web Application Firewalls, and increasingly, Bot Management solutions, which work for web, mobile, and APIs.
The better the tool, the more work the attacker has to do, ergo fewer are attackers willing to do it, ergo smaller chance of being attacked.
Secure Authentication
Authentication is a specific case of the above, however this problem is currently (one of) the biggest problem faced by web applications.
The main solutions employed today is are bot filtering techniques e.g. CAPTCHA (which resourceful attackers can overcome), and Multi-Factor Authentication.
It's quite uncommon these days to be able to register without email, however services such as 10 Minute Mail can be used to overcome this. It's actually not very difficult to set up your own mail server as well.
Login is more difficult because you can't expect people to go through email, and even other MFA methods get quite annoying. You'd be OK with MFA for your bank account, but not with MFA to your Domino's Pizza account.
Because of that, the latest fad in web attacks is Account Takeover.
All those security vendors which offer WAF and bot management also try to protect APIs such as registration & login, with various degrees of success. There are even dedicated products are starting to emerge.
How do you prevent a third party from using an ASMX web service if you don't force users to authenticate?
Ultimately it will come down to who they are and how they access your web service. And the degree of risk they propose.
You could use simple "Security through Obscurity" where you don't tell people about the service. This is usually a very very poor solution. In fact it can be positively dangerous as you don't get to know who knows - so it's a real risk.
You could authenticate the machines and processes and not the people. Say for example IP addresses.
But at the end of the say you need to some form of authentication to determine any kind of filtering.
I apologize if this is a somewhat stupid question, but I am very new to the REST programming realm. I have an application that is both web, mobile and machine accessible, and I will be leveraging REST-like web services for the mobile and machine part. I was going to use the S3 authentication model for the REST requests, however that requires the user account to already be setup.
If the user initiates his use of the service via an iPhone or other mobile device, what is the best way to securely create the user account? As it stands right now, anyone can create an account that will be created inactive and then activated via email link to a CAPTCHA web page. But I am afraid this could still lead to DOS attacks given the fact an email is generated for each request.
Any suggestions on improving this model and/or assuring the request does in fact come from an iPhone?
A good CAPTCHA will prevent such DOS attacks.
Require the CAPTCHA before sending the email link, ie when requesting an account.