How to serve mulitple web applications on different subdomains? - spring

Not sure if the title is well suited but I am having three apps (static content) at the moment:
public
app
admin
public is just content which is just for the regular web, app is content which is rendered for mobile devices and admin is basically a tool for administrative stuff. They are all contained in the same Spring Boot application and talk to the REST API at example.com/api. Technically, I could just place them into resources/static such that
resources/static/public
resources/static/admin
resources/static/app
which would allow me to access the apps as such:
example.com/public/index.html
example.com/admin/index.html
example.com/app/index.html
However, my goal is to have the following structure:
example.com // For public
admin.example.com // For admin
app.example.com // For app
example.com/api // REST API
How can this be achieved or what can I do to make this possible?

It sounds like you have three systems: public, admin and app sharing a common REST api. Probably the best approach would be to serve the static resources for each of the three systems using a content delivery network (CDN) like AWS CloudFront or Google Cloud CDN.
Another approach, though less desirable, would be to use a proxy to redirect app requests (for example https://admin.example.com to https://internal-spring-boot-server/admin). You could use Apache mod_proxy with reverse proxy (see https://httpd.apache.org/docs/2.4/mod/mod_proxy.html), or NGNX reverse proxy https://docs.nginx.com/nginx/admin-guide/web-server/reverse-proxy/

I think that there are two ways to achieve what you are trying to do you.
Either you will configure your subdomains in your DNS plesk/cpanel/.. to look a specific Document root (The path to the each of your apps home directory.)
for example when someone asks for example.com the request would ask for example.com/main, when someone asks for admin.example.com the request would ask for admin.example.com/admin etc. In this way, you essentially ignoring the subdomain in your Spring app and you manipulate the routes in the #Controller level using the RequestMapping values main/admin/etc..
Alternatively if you don't want to mess with the Provider's control panel, you could follow the steps of this answer. But then you'd have to implement these three custom RequestCondition classes and it may not be the most simple way to go.
Not the best documented answer but I hope I pointed you to the right direction.

Related

Spring Boot: How to securely authenticate two different kinds of user using NextJs as a frontend

I have never really done authentication yet. At this moment, I'm stuck and not really sure on what would be the best and most secure way to handle it.
To get an overview on what I'm working with:
For the backend/REST API I'm using Spring Boot and for the frontend NextJs.
Furthermore, Two types of users are needed, some who can either create, analyze or manage content (basically different roles) in our custom CMS. And on the other side, app users who are consuming this content (on a iOS app).
That's what I'm trying to achieve as a minimum requirement, but it would be even better if it would somehow be possible to manage only a list of specific content for a specific role (e.g. analyze). Like for example, only blog articles that are in this list.
I know it's a really broad question, but I would be happy with some general directions or links to resources that could guide me in a way.

Best way to implement single sign on in Laravel?

I'm building an application that has a core hub, say it's called musictickets.com
We'll provide a subdomain (bandname1.musictickets.com) to bands on which only their content will display, which they can mask using a CNAME record to be part of their domain - so tickets.bandname1.com
There would be multiple bands using the platform so you'll end up with pages at
tickets.bandname1.com
tickets.bandname2.com
etc.
I'd like a user who registers at tickets.bandname1.com to be automatically logged in on every site that uses the service, including the parent, musictickets.com . They should be able to register/login using OAuth or directly via form based authentication.
I'm looking at SAML (specifically https://github.com/aacotroneo/laravel-saml2) as one option, but want to throw this out to the wider community for comment.
I've also looked at using token based SSO as described here (single sign on (sso) laravel) and running an auth server (which I may do in any case). Alternatively, I've looked at using iframes to provide the functionality which feels quick but dirty.
As I understand it, I wouldn't be able to use cookies (for an API key for instance) because whilst all of the content will be displayed via a subdomain, the CNAME would make it a different domain.
Does anyone have any thoughts on the best strategy?

Create one or multiple projects for OAuth 2.0 for the company websites in different countries? (different prefix in URL and local content)

I am developing a structure in Google developer console to create projectsnd configure a OAuth 2.0 client IDs for our company websites. These we use to integrate Google login to the website.
We have around 50 websites now, where some are "company websites", then we have "product websites", etc. such groups.
For example group of company websites - those websites have exactly the same design, the same purpose, but are country specific, thus:
- differ in country prefix, e.g. countryA.companyxy.com, countryB.companyxy.com
- differ in content (types of content are the same, but the ontent itself is connected to the country, thus local)
- the language can be different (although mostly it's english)
I am seeking a recommendation as I cannot decide what is better:
1) Create one project per website and then different Client IDs for environments (prod, staging, dev) - this would be 50 projects, each with 3 Client IDs
2) Create one project per a group - e.g. company websites would have one project and I would create new Client ID for each country and each environment. This way I would have maybe 5-6 projects, each with 10-20 Client IDs.
Can those company websites all use the same application, or they should not?
If I've understood you correctly, this is a fairly standard multi-tenant application where a single app (from Google's perspective) lives at multiple domains. You can use a single Project and a single Client-ID, since in both cases, the ID relates to the app, not to the domain the app lives at.
So, when you start the OAuth dance, you always specify the same redirect URL, which handles OAuth for all domains. The trick is that you include a state parameter at the start of the dance which indicates which country/site your OAuth code should redirect to once the dance is finished.
So, roughly something like this:-
user visits countryA.companyxy.com and requests Oauth (eg. clicks a signin button)
You redirect to accounts.google.com?redirect_uri=common.companyfoo.com/oauth&state=countryA.companyxy
After auth, google will redirect back to common.companyfoo.com/oauth?state=countryA.companyxy
Your oauth handler does its thing, then parses the state param and redirects back to countryA.companyxy.com
Of course there might be administrative reasons for your company to prefer multiple projects and/or client IDs depending on your enthusiasm for admin, and how you wish to segment your data. To explain this last point using Drive as an example, if all companies have the same project, then the drive.file scope would give them all access to the files created by the app. However, if you have a project for each company, then Google sees these as created by different apps, so the are not visible using the drive.file scope.
I am seeking a recommendation as I cannot decide what is better:
I would align the Folder/Projects in the same structure as the company organization with a preference towards more projects (separation) instead of consolidation. Try to think of the chain of command and the distribution of resources. Factor in how you want security to separate resources. This might help figure out what should go where. Do separate development from production resources (separate projects).
Can those company websites all use the same application, or they
should not?
The answer is "it depends". If they all share a common domain name root, and they authenticate at the root, very easy to implement. The authentication cookies can be shared across domains. Otherwise, you will need to use multiple redirect_urls so that auth on one site completes on the same site. I am not sure what the limit is for Redirect URLs per Client ID.
To the second part of your question "or they should not". If the websites are designed to look like the same company then customers will expect to only authenticate once and be authorized across all sites. Is this a good idea, Yes. Is it the correct idea, this depends on your security requirements, isolation needs, etc. No simple answer here.

restrict django rest framework APIs to my mobile and web apps

What is the recommended way to restrict my django rest framework APIs to be available to my mobile and web apps only ? I'm using django-rest-auth to authenticate my users. There are some APIs that can be accessed anonymously. But I need to make sure that all the APIs are available only through my apps (mobile and web).
Any help/tutorials are highly appreciated.
Thank you
You need to setup the authorization scheme at the configuration level to restrict it to your mobile / web app only and explicitly set the public ones at the class level. See http://www.django-rest-framework.org/api-guide/permissions/#setting-the-permission-policy about implementation details.
Because all requests can be sniffed you can't use any Secret-key or check for HTTP origin (it can be faked easily).
For mobile you can try using secret-key generator with some special algorithm. Fro example MD5(current_time + your_secret_phrase). Then you will be able to verify that code is acceptable. It will make using your API almost impossible for sniffers.
But for Web you can't do much. All headers can be faked. The only way - user authentication.
You can, of course, use Secret-key and change it every month/day/hour. But is it worth it?

Dropbox API Chooser with JS for multiple domains

I want to user Dropbox chooser API for my Ruby on rails application(This is not web app, This will be installed as standalone).
Issue is in specifying "Drop-ins domains", which currently i gave as "localhost. But for the machines on which it will be installed "machine name" will be used instead of localhost. And i cannot keep track of all installations and manually adding those domains
Please suggest, Is there some way to solve this problem? Can i use chooser API without drop-in domain?
The Dropbox Drop-ins API doesn't have any way of automatically adding domains, or registering any sort of wildcard, but we're tracking this as a feature request.
For reference, one thing that does work, though it sounds like it may not apply to your scenario, is registering just, for example, example.com, which would enable use on any subdomain of example.com, e.g., sub1.example.com, sub2.example.com, webmail.example.com, etc.
Alternatively, you can embed an iframe containing the button, which would be hosted on your own domain. This would let you just set that one domain in the app options page. It would be very important that you then restrict the set of domains that you allow to iframe your button though, but this list would now be under your control so you can set it programmatically. For example:
How to limit display of iframe from an external site to specific domains only

Resources