15

I have a static website composed of html/css/javascript files. The website is automatically generated and updated frequently.

Instead of authorizing access to the website with a username/password (basic auth), I would like to have users authenticate using Google Sign-in/openID Connect, and then control access via a whitelist of gmail addresses.

What is the simplest way to set this up?

el_tigro
  • 1,099
  • 2
  • 10
  • 22

4 Answers4

11

I ended up using oauth2_proxy which is exactly what I was looking for.

I configured to do the following:

  • oauth2_proxy listens on 0.0.0.0:443
  • When a user connects, the Google sign-in flow is initiated
  • After sign-in, it validates the user's email address against a whitelist
  • After successful validation, oauth2_proxy proxies the request to an upstream nginx server listening on 127.0.0.1:8080
Fyodor
  • 247
  • 3
  • 14
el_tigro
  • 1,099
  • 2
  • 10
  • 22
4

Another way to add authentication or gated content to any static site:
1) First load a static container page (header, footer) and implement user Authentication js code using Auth0, firebase, okta etc.

2) When user successfully logs in then make an ajax api call passing that auth access_token to retrieve the sensitive content.

3) Load/append that sensitive content in the site using js.

Of Course, there has to be one server/serverless function which would listen to that ajax api call, authenticate it and sends the content back to the browser.

This is called client side authentication.

More on this: https://auth0.com/blog/ultimate-guide-nextjs-authentication-auth0/

GorvGoyl
  • 42,508
  • 29
  • 229
  • 225
0

Best way would be to use Firebase Auth! Check it out at https://firebase.google.com/docs/auth/

You could check if the user is authenticated or not in this way.

<script type="text/javascript">

        function initApp() {
          // Listening for auth state changes.
          // [START authstatelistener]
          firebase.auth().onAuthStateChanged(function (user) {
            if (user) {
              //User is signed in.
                  if (!emailVerified) {
              //Additional check for email verification
              }
            } else {
              // User is signed out.
            }
          });
          // [END authstatelistener]
        }
        window.onload = function () {
          initApp();
        };
      </script>
Rahul Suresh
  • 184
  • 1
  • 14
  • Hi Rahul, I considered Firebase Auth but ran into some difficulties. I created a firebase project, enabled the Google sign-in method, created a login page, and successfully signed in with my Google account. But since you can't configure rules with Firebase Hosting (see https://stackoverflow.com/questions/48753740/authentication-for-firebase-hosting), the only remaining option is to use Firebase Storage. It doesn't seem like there's a way to serve a static website composed of multiple files and relative links with Firebase Storage. Any ideas? – el_tigro Jun 12 '18 at 04:59
  • See here as well: https://stackoverflow.com/questions/27212004/can-firebase-hosting-restrict-access-to-resources – el_tigro Jun 12 '18 at 05:01
  • Well, you could dynamically check if user is logged into firebase or not using certain firebase functions in Javascript. Depending on that you could display content or choose to hide them if they are not authenticated (You could use any front-end framework to prevent displaying the content instead of just setting display:none) – Rahul Suresh Jun 12 '18 at 05:05
  • @catanman Check the updated answer and see if you get what I'm trying to say. – Rahul Suresh Jun 12 '18 at 05:13
  • I ended up finding a simpler solution that doesn't require any code. – el_tigro Jun 15 '18 at 15:55
-1

Check out https://authorizer.dev/. It's free and open source.

This tutorial explains how to get started for static sites (follow the UMD section): https://docs.authorizer.dev/authorizer-js

<script src="https://unpkg.com/@authorizerdev/authorizer-js/lib/authorizer.min.js"></script>

<script type="text/javascript">
    const authorizerRef = new authorizerdev.Authorizer({
        authorizerURL: `YOUR_AUTHORIZER_INSTANCE_URL`,
        redirectURL: window.location.origin,
        clientID: 'YOUR_CLIENT_ID', // obtain your client id from authorizer dashboard
    });

    // use the button selector as per your application
    const logoutBtn = document.getElementById('logout');
    logoutBtn.addEventListener('click', async function () {
        await authorizerRef.logout();
        window.location.href = '/';
    });

    async function onLoad() {
        const res = await authorizerRef.authorize({
            response_type: 'code',
            use_refresh_token: false,
        });
        if (res && res.access_token) {
            // you can use user information here, eg:
            const user = await authorizerRef.getProfile({
                Authorization: `Bearer ${res.access_token}`,
            });
            const userSection = document.getElementById('user');
            const logoutSection = document.getElementById('logout-section');
            logoutSection.classList.toggle('hide');
            userSection.innerHTML = `Welcome, ${user.email}`;
        }
    }
    onLoad();
</script>

Here is a video demo: https://youtu.be/uQka5O2RwpU?t=97