Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature/meditor 937 upgrade and simplify meditor #69

Merged
merged 33 commits into from
Jan 3, 2025

Conversation

joncarlson
Copy link
Collaborator

@joncarlson joncarlson commented Nov 26, 2024

This PR moves us a bit closer to being able to go cloud native and also relieves some of the maintenance burden by simplifying mEditors stack. A few changes here:

  • Migration of remaining authentication endpoints from the legacy-api to the NextJS app (NextAuth)
  • Refactoring of NextJS app to simplify error handling
  • Removal of legacy API entirely
  • Switch from NGINX proxy to Caddy, this also allows us to remove our mEditor Proxy image completely as we can just pass a Caddyfile to the default Caddy image

@joncarlson joncarlson force-pushed the feature/MEDITOR-937-upgrade-and-simplify-meditor branch from ca6dd50 to 942a581 Compare December 9, 2024 20:18
Copy link
Collaborator Author

@joncarlson joncarlson Dec 11, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Docker has introduced "develop" parameters that only take effect when developing locally, making a separate override compose unnecessary

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Most of this is merging the two docker compose files together, noting where there are new items or updates

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I'll need your help to get this running. I must have something misconfigured, but a docker system prune + rebuild and a few minutes of searching around yielded nothing.

- .env
ports:
- "127.0.0.1:4000:4000"
develop:
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

New develop section for the app, makes volume mounting unnecessary. If you do docker-compose up --watch or docker compose watch these take effect

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Auto-updated from ESLint upgrade

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unused

Copy link
Collaborator Author

@joncarlson joncarlson Dec 11, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

NextAuth, the authentication library this PR introduces, has the concept of custom login providers. This is a custom provider to authenticate with Earthdata Login.

Generally this provider is responsible for:

  • telling NextAuth what oAuth authorize url to hit
  • how to get a token from EDL
  • how to retrieve user information from EDL after auth

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Simplifying the user types to what we are actually using in the app

router.pathname == '/' ||
router.pathname == '/installation'

const App = ({
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Look at all that auth related code that we don't need anymore!

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

NextAuth configuration, again, looks complicated at first glance so I'll try to comment where needed

},

// configure one or more authentication providers
providers: [
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here's where we can add more providers as we go (Github, Google, Launchpad, etc.)

],

callbacks: {
async signIn(session) {
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since this PR makes mEditor stateless (no DB session), we still need a way to create a user account in the "users-urs" collection.

The notifier uses this collection to pull email addresses when sending emails.

This would be unnecessary if we could get those emails from EDL, but alas that API doesn't exist from what I can see

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This isn't super important to me or anything, but I'm not sure I understand why we specifically have a users-urs collection when we've just introduced OAuth providers as a concept. In a future improvement, would it theoretically be a good decision to drop the 'users-urs' collection and user the Users collection, since all OAuth providers are going to provide an email address as a part of the user identity?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Some base Zod schemas as the old API relied heavily on passing the "model" and "document" as query params

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The "handlePublicationAcknowledgements" function was almost entirely copied from the legacy API

)
})

test('handles primitive data types just like JSON.parse', () => {
const [stringError, string] = safeParseJSON('string')
expect(stringError).toMatchInlineSnapshot(
`[SyntaxError: Unexpected token s in JSON at position 0]`
`[SyntaxError: Unexpected token 's', "string" is not valid JSON]`
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

More descriptive errors :)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Error handling moved to "with-api-error-handler"

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Removed the legacy API

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Removed the proxy

@joncarlson joncarlson marked this pull request as ready for review December 19, 2024 13:55
Copy link
Contributor

@benforshey benforshey left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Wow, tremendous amount of work, and I really think it's a great step forward for mEditor! I also think I lost my sanity somewhere around file 120, so sorry in advance for the comments! 🙃

return JSON.parse(localStorage.getItem(getLocalStorageKey(modelName, localId)))
return typeof localStorage !== 'undefined'
? JSON.parse(localStorage.getItem(getLocalStorageKey(modelName, localId)))
: []
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should the return type here should be an object literal, since the stored document is an object?

@@ -1,3 +1,7 @@
{
"extends": "next/core-web-vitals"
"extends": "next/core-web-vitals",
"rules": {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the flat file configuration was deprecated in ESLint 9. Here's what works for me:

  • change the file name to eslint.config.js
  • use the config (I left some stuff commented out that Next recommended, since we might not want it)
import { FlatCompat } from '@eslint/eslintrc'

const compat = new FlatCompat({
    // import.meta.dirname is available after Node.js v20.11.0
    baseDirectory: import.meta.dirname,
})

const eslintConfig = [
    ...compat.config({
        // extends: ['next/core-web-vitals', 'next/typescript'],
        extends: ['next/core-web-vitals'],
    }),
    {
        rules: {
            'react-hooks/exhaustive-deps': 'off',
            '@next/next/no-html-link-for-pages': 1,
        },
    },
]

export default eslintConfig

packages/app/macros/service.ts Outdated Show resolved Hide resolved
packages/app/models/service.ts Outdated Show resolved Hide resolved
packages/app/models/service.ts Outdated Show resolved Hide resolved
packages/app/publication-queue/service.ts Outdated Show resolved Hide resolved
packages/app/setup/service.ts Show resolved Hide resolved
packages/app/workflows/service.ts Outdated Show resolved Hide resolved
packages/app/pages/index.tsx Show resolved Hide resolved
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I'll need your help to get this running. I must have something misconfigured, but a docker system prune + rebuild and a few minutes of searching around yielded nothing.

@benforshey
Copy link
Contributor

Oh, one more thought I had this morning. Do you want to update the .github/workflows/continuous-integration.yml file to use node 22?

@joncarlson
Copy link
Collaborator Author

Oh, one more thought I had this morning. Do you want to update the .github/workflows/continuous-integration.yml file to use node 22?

Oh yes that's a good idea. Updating it

//? the design makes the login button appear in a modal dialog however if we use a React-Bootstrap modal, the modal will not hydrate correctly and will generate an error as
//? the modal is not present on the server side. Instead we'll use the HTML directly
return (
<div
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not a blocker for me!

@joncarlson joncarlson merged commit dd7d990 into main Jan 3, 2025
2 of 5 checks passed
@joncarlson joncarlson deleted the feature/MEDITOR-937-upgrade-and-simplify-meditor branch January 3, 2025 16:37
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants