quickstart-js icon indicating copy to clipboard operation
quickstart-js copied to clipboard

Is it possible to share auth between Chrome extension and website?

Open torarnv opened this issue 7 years ago • 19 comments

I have a Chrome extension that uses Firebase authentication (via firebaseui), and a corresponding hosted site that also uses Firebase for authentication (also via firebaseui). How would I go about making the user automatically sign in on the website, if they are already signed in in the Chrome extension?

The extension's authentication lives in its background page, and I can post message from that to the content script, which in turn can post messages to the website (or the other way around), but what do I need to pass over to have the site (which I can control) have enough information to directly sign the user in?

torarnv avatar Mar 12 '18 23:03 torarnv

@torarnv Did you find a solution for this?

I'm curious how you got firebaseui working with a chrome extension? The official readme says:

Additional non-browser environments (React Native...) or Chrome extensions will be added once the underlying Firebase core SDK supports them in a way that is compatible with FirebaseUI.

zzpreneur avatar Jan 25 '19 02:01 zzpreneur

Any updates on this? I am having the same question. Thanks!

Tinyik avatar Apr 17 '20 00:04 Tinyik

I'm aiming at achieving the same, and I think you could sort it out with custom token https://firebase.google.com/docs/auth/web/custom-auth#authenticate-with-firebase

You'd have to set up a server to handle the authentication and create a custom token, that you can later use this way firebase.auth().signInWithCustomToken(token) Then you can also share this token with you extension to call the same function from there and authenticate your user.

I'll try this solution and get back at you if it works as expected !

julienR2 avatar Apr 24 '20 12:04 julienR2

I've put it to together and it works as expected 👍 Here are the main bits of code:

Firebase function / Auth Server

In a Firebase function (or a custom server) handle the token creation using firebase function createCustomToken

const admin = require('firebase-admin')
const functions = require('firebase-functions')

admin.initializeApp()

module.exports functions.https.onCall(uid =>
  admin.auth().createCustomToken(uid)
)

Webapp

After a successful login, request the server for a custom Token passing the uid of the logged user

firebase.functions().httpsCallable('createToken')(uid)

Then send it to the chrome extension

chrome.runtime.sendMessage(extensionID, token)

Extension

Finally in the extension when receiving a message, log the user with firebase using the custom token

firebase.initializeApp(firebaseConfig)

firebase.auth().onAuthStateChanged(function (user) {
  console.log(
    'User state change detected from the Background script of the Chrome Extension:',
    user
  )
})

chrome.runtime.onMessageExternal.addListener(
  (token, sender, sendResponse) => {
    firebase
      .auth()
      .signInWithCustomToken(token)
      .catch((error) => {
        console.log('error', error)
      })
    return true
  }
)

You background scrip will log the authStateChanged event where you can see that the auth is not isAnonymous anymore and the email attributes is the one of the user logged through your app !

julienR2 avatar Apr 25 '20 18:04 julienR2

Posting so that people like me have to search less. You can use the same approach for Manifest V3.

I was wondering now that in manifest V3 you cannot have long living processes how would you deal with realtime data like firestore?

dvrfluxchat avatar Feb 04 '22 10:02 dvrfluxchat

Posting so that people like me have to search less. You can use the same approach for Manifest V3.

I was wondering now that in manifest V3 you cannot have long living processes how would you deal with realtime data like firestore?

@dvrfluxchat

I was wondering this, you have an app already implementing the solution from @julienR2 ? Also sorry I cannot answer your firestore question

Thanks so much

Danscap avatar Feb 12 '22 20:02 Danscap

We are currently developing it and we were able to successfully implement the auth layer though.

dvrfluxchat avatar Feb 13 '22 05:02 dvrfluxchat

Glad to read it's working fine with the V3 manifest !

I dug into it for a project that has been dropped since then 😕 It would have been a bit tedious to put it back in place and test it with last version manifest..

My understanding, it works even with manifest v3, because we aren't actually using long-living processes on the extension side, apart maybe for the firebase.auth().onAuthStateChanged ?). Otherwise we are just handling a message from a webpage, and logging the user with the passed token 👍

julienR2 avatar Feb 14 '22 11:02 julienR2

This was very helpful. Thanks!

AyoLaja avatar Mar 31 '22 02:03 AyoLaja

You should use "context.auth.uid" inside your callable function instead of a parameter though. Right now you have an exposed function which can give you any user auth token as long as you have their id...

mparpaillon avatar Jun 13 '22 06:06 mparpaillon

worth mentioning that custom token expires in 1 hr

GorvGoyl avatar Mar 19 '23 05:03 GorvGoyl

Hello everyone, are there any solutions available now?

And how is everyone's CSP set?

Gsonovb avatar Apr 21 '23 02:04 Gsonovb

chrome.runtime.sendMessage(extensionID, token)

Tried running this in my react application. I keep getting the error below. I am curious if there is something special i have to do to make web app be able to send message to my chrome extension

Unhandled Runtime Error
TypeError: Cannot read properties of undefined (reading 'sendMessage')

PreciousNiphemi avatar Sep 14 '23 15:09 PreciousNiphemi

worth mentioning that custom token expires in 1 hr

@GorvGoyl, so that means you'll have to sign in again in 1 hour? Is there a workaround?

ivliag avatar Jan 25 '24 14:01 ivliag

chrome.runtime.sendMessage(extensionID, token)

Tried running this in my react application. I keep getting the error below. I am curious if there is something special i have to do to make web app be able to send message to my chrome extension

Unhandled Runtime Error
TypeError: Cannot read properties of undefined (reading 'sendMessage')

@PreciousNiphemi I have the same problem now did you find a solution?

bma-dev avatar Feb 20 '24 08:02 bma-dev

Sorry I'm late answering here.. from what I've seen, there's a difference, between injecting a script programmatically, and using an injected.js script.

If you inject programatically, it gives the script access to some of unaccessible property (e.g. chrome.runtime.sendMessage), while if you use the injected.js mechasism, it doesn't, thus the error you're facing.

I think this doc from Chrome page is a good start to read about injecting programatically.

I haven't been working actively with web ext ad firebase auth lately so most of those info are now from memory and quick search. Hopefully it still helps 🤞

julienR2 avatar Feb 27 '24 12:02 julienR2

firebase.functions().httpsCallable('createToken')(uid)

this means everyone got your uid, can create login token without your username and password! this is super danger!!!!

caiyongji avatar Apr 23 '24 15:04 caiyongji

Indeed the code I shared at the time didn't cover much the security aspect (I should probably have added a warning).

But it's fairly easy to actually authenticate the firebase function. You could pass the local token, or some authentication key/password along with the uid, to re-authenticating the user in the function, and making sure we are not sending a custom token to anyone who got our uid

Thanks for raising the concern @caiyongji

julienR2 avatar Apr 23 '24 15:04 julienR2

For someone who is getting this error

Unhandled Runtime Error TypeError: Cannot read properties of undefined (reading 'sendMessage')

make sure add below property in the manifest.json

"externally_connectable": { "matches": ["*://localhost/*"] }

shaik-zaheeruddin avatar Oct 02 '24 10:10 shaik-zaheeruddin