dev-xo / remix-auth-totp

A Time-Based One-Time Password (TOTP) Authentication Strategy for Remix-Auth.
https://totp.fly.dev
MIT License
415 stars 28 forks source link

[ Feat ]: Support Cloudflare Runtime #28

Closed mw10013 closed 10 months ago

mw10013 commented 11 months ago

Cloudflare wrangler reports an error when an Authenticator uses TOTPStrategy. The error seems to be reported during load time so the authenticator does not execute.

Screenshot 2023-12-13 at 1 21 19 AM

https://github.com/mw10013/remix-auth-totp-sandbox demonstrates the error.

serverNodeBuiltinsPolyfill: {
    modules: { crypto: true, stream: true },
    globals: {
      process: true,
    },
  },

"start": "wrangler pages dev ./public --compatibility-date=2023-12-13 --compatibility-flags=\"nodejs_compat\""

dev-xo commented 11 months ago

Hello @mw10013, thanks for reporting this.

I recently released remix-auth-totp, an evolution of the earlier remix-auth-otp. The key upgrade in this library is the shift to using @epic-web/totp for generating and managing One-Time Passwords (OTPs), enhancing the encryption and decryption processes.

Previously, with remix-auth-otp, an issue related to Cloudflare and authentication was reported. This issue was linked to the use of node-crypto. However, since @epic-web/totp does not utilize node-crypto — as far as I'm aware — the same issues should not occur.

Despite this, I must admit I haven't had the chance to get deeper into the specifics of Cloudflare's systems, which makes it challenging to understand what could be happening (the library works as expected outside of it).

I'm considering reaching out to Sergio Xalambrí, the creator of remix-auth. He might have some insights into what could be causing these Cloudflare issues.

Let me know if you have more information or a specific error that could lead us to a solution!

dev-xo commented 11 months ago

Update: I had a talk with Sergio, who pointed out a possible case that could be causing the Cloudflare issues.

Compatibility Issue with Cloudflare:

remix-auth is compatible with Cloudflare, but some dependencies, such as jsonwebtoken, might not be. This could be one of the potential issues since this library uses jsonwebtoken as an extra security layer for data reaching the client. Although it's not necessary and it could be stripped off.

Specific Package Problems:

The thirty-two package may also have issues with Cloudflare. It's important to note this because it's used in dependencies like @epic-web/totp. In this case, Kent C. Dodds should be informed, as he is involved with the pointed library.

Potential Solutions:

Replacing jsonwebtoken might resolve some of the issues. Also considering using node-crypto or crypto-es as alternatives to deprecated packages like crypto-js. Another option is to utilize the Web Crypto API globally, which is supported in Cloudflare, Deno, Bun, Node (since v20), and browsers.


I'll check this out @mw10013. I'll definitely find some time to look into it and come up with a solution.

I'll leave the issue open and update you on any changes. Thanks again for bringing this up!

mw10013 commented 11 months ago

@epic-web/totp, which has thirty-two as dependency seems to work in Cloudflare with tweak to remix.config.js.

serverNodeBuiltinsPolyfill: {
    modules: { buffer: true, crypto: true },
    globals: {
      Buffer: true,
    },
  },

https://github.com/mw10013/remix-auth-totp-sandbox/blob/epic-totp/app/routes/_index.tsx

export function loader() {
  const { otp, secret, digits, period, algorithm } = generateTOTP({
    algorithm: "SHA256",
    period: 10 * 60,
  });
  const isValid = verifyTOTP({ otp, secret, digits, period, algorithm });

  return { otp, secret, period, digits, algorithm, isValid };
}
mw10013 commented 11 months ago

Cloudflare definitely supports the Web Crypto API.

https://github.com/mw10013/remix-auth-totp-sandbox/tree/jsonwebtoken

"The Workers runtime implements the full surface of this API, but with some differences in the supported algorithms compared to those implemented in most browsers."

I'm unable to get jsonwebtoken working. This branch (https://github.com/mw10013/remix-auth-totp-sandbox/tree/jsonwebtoken) contains only jsonwebtoken and compiles with tweak to remix.config.js

serverNodeBuiltinsPolyfill: {
    modules: { crypto: true, stream: true },
    globals: {
      process: true,
    }
  },

Runtime error starting up.

Screenshot 2023-12-14 at 2 33 01 AM
dev-xo commented 11 months ago

Alright, so we can mostly confirm that the issue could be the implementation of jsonwebtoken.

I'll need to review the source-code from the Strategy to confirm if jsonwebtoken can be stripped out or replaced. If I recall correctly, it was added as an extra security layer, but it wasn't necessary or required at the time.

I'll look into it, @mw10013. If you have any other information or want to report something else, feel free to do so!

mw10013 commented 11 months ago

Jose may be another option, https://github.com/panva/jose

"jose is JavaScript module for JSON Object Signing and Encryption, providing support for JSON Web Tokens (JWT), JSON Web Signature (JWS), JSON Web Encryption (JWE), JSON Web Key (JWK), JSON Web Key Set (JWKS), and more. The module is designed to work across various Web-interoperable runtimes including Node.js, browsers, Cloudflare Workers, Deno, Bun, and others."

dev-xo commented 11 months ago

I'm currently integrating jose into a dev repository for remix-auth-totp. However, I still need someone to test jose on Cloudflare, as my experience with Cloudflare is practically non-existent. I haven't had the opportunity to get deeper or find a use case for it yet.

Could you please give it a try to jose the same way you did with jsonwebtoken @mw10013? If it works, could be a replacement for jsonwebtoken.

dev-xo commented 11 months ago

All right @mw10013, could you try this implementation of jose on a new development package called remix-auth-totp-dev? Here's the package: remix-auth-totp-dev

Feel free to give it a try and let me know if it works as expected or if you encounter any new errors that we can address.

The tests passes successfully, although I will have to fix some minor incompatibilities with expiration periods, between strings and numbers, due to the new jose implementation."

mw10013 commented 11 months ago

Thanks for turning this around so quickly!

I'm now able to get my non-functional skeletal sandbox to compile and load with tweak to remix.config.js.

  serverNodeBuiltinsPolyfill: {
    modules: { buffer: true, crypto: true },
    globals: {
      Buffer: true,
    },
  },

I'll be working on a functional version and will report back here.

mw10013 commented 10 months ago

With the remix-auth-totp-dev package, I'm getting a "Code is no longer active" error when I submit the code in a verify form.

As a sanity check, I forked https://github.com/dev-xo/totp-starter-example, created a branch named remix-auth-totp-dev, and replaced the remix-auth-totp package with remix-auth-totp-dev. I get the same error, "Code is no longer active", when I submit it in the verify form. I also tried the case of clicking on the magic link in the email and get redirected to login.

For reference, the branch is https://github.com/mw10013/totp-starter-example/tree/remix-auth-totp-dev

Screenshot 2023-12-15 at 7 39 51 PM
dev-xo commented 10 months ago

Hello @mw10013.

Could you please give it another try with the updated remix-auth-totp-dev@v1.3.3? I have recently made some changes that could potentially fix it.

Also, here's my Discord username (developerxo) in case we can have a more direct conversation.

mw10013 commented 10 months ago

totp-starter-example and my example program work with remix-auth-totp-dev @ v1.3.3. Thanks for the timely fixes!

dev-xo commented 10 months ago

Does that mean we have support for Cloudflare, @mw10013?

In that case, would you like to create a totp-starter-cloudflare template based on the original totp-starter-example? It could help some folks to get started with it easily. It will be included in the Examples section with your nickname.

Also, tomorrow I will publish these changes to the official remix-auth-totp package.

mw10013 commented 10 months ago

Yes, I can confirm the basics work in Cloudflare local dev with wrangler/miniflare. Need to get further along in the example program I'm working on to cover more cases and then get it running in Cloudflare production. I would like the example program to help folks get started and will circle back with you for review and inclusion when it's further along.

dev-xo commented 10 months ago

All code has been moved to the main repository @mw10013. Feel free to try out the v1.4.0 Release and let me know if it works as expected!

Again, thank you for reporting this. It would be great to see a remix-cloudflare-example template from you!

Closing this for now, but we can keep the talk on here.