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

[V4] TS Global Middleware not picked up #20322

Open
antokhio opened this issue May 16, 2024 · 3 comments
Open

[V4] TS Global Middleware not picked up #20322

antokhio opened this issue May 16, 2024 · 3 comments
Labels
issue: bug Issue reporting a bug severity: medium If it breaks the basic use of the product but can be worked around source: typescript Source is related to TypeScript (typings, tooling, ...) status: pending reproduction Waiting for free time to reproduce the issue, or more information

Comments

@antokhio
Copy link

Bug report

Following from https://discord.com/channels/811989166782021633/1240319511857463429

Seems there is error in doc's or in the way the global middleware imported.
I try to follow steps from docs https://docs.strapi.io/dev-docs/backend-customization/middlewares to add global middleware and ran in to issue.

Required System information

  • Node.js version: v18.18.2
  • NPM version: 8.13.1
  • Strapi version: 4.17.1
  • Database: Postgres
  • Operating system: windows 10 pro
  • Is your project Javascript or Typescript: Typescript

Describe the bug

A clear and concise description of what the bug is.

Steps to reproduce the behavior

  1. Add middleware to an empty project src/middlewares/test.ts
export default (config, { strapi }) => {
  return async (ctx, next) => {
    console.log('test');
    await next();
  };
};
  1. Add middleware to config/middlewares.ts
export default [
  'strapi::errors',
  'strapi::security',
  'strapi::cors',
  'strapi::poweredBy',
  'strapi::logger',
  'strapi::query',
  'strapi::body',
  'strapi::session',
  'strapi::favicon',
  'strapi::public',
  'global::test ',
];
  1. Error:
Error: Middleware global::test  not found. 

Expected behavior

It should work

Additional context

$ strapi middlewares:list
┌─────────────────────────────────────┐
│ Name                                │
├─────────────────────────────────────┤
│ admin::rateLimit                    │
├─────────────────────────────────────┤
│ admin::data-transfer                │
├─────────────────────────────────────┤
│ global::test                        │
├─────────────────────────────────────┤
│ strapi::compression                 │
├─────────────────────────────────────┤
│ strapi::cors                        │
├─────────────────────────────────────┤
│ strapi::errors                      │
├─────────────────────────────────────┤
│ strapi::favicon                     │
├─────────────────────────────────────┤
│ strapi::ip                          │
├─────────────────────────────────────┤
│ strapi::logger                      │
├─────────────────────────────────────┤
│ strapi::poweredBy                   │
├─────────────────────────────────────┤
│ strapi::body                        │
├─────────────────────────────────────┤
│ strapi::query                       │
├─────────────────────────────────────┤
│ strapi::responseTime                │
├─────────────────────────────────────┤
│ strapi::responses                   │
├─────────────────────────────────────┤
│ strapi::security                    │
├─────────────────────────────────────┤
│ strapi::session                     │
├─────────────────────────────────────┤
│ strapi::public                      │
├─────────────────────────────────────┤
│ plugin::users-permissions.rateLimit │
└─────────────────────────────────────┘
@strapi-bot
Copy link

This issue has been mentioned on Strapi Community Forum. There might be relevant details there:

https://forum.strapi.io/t/plugin-middleware-setup-in-typescript/38366/6

@ksoltanidev
Copy link

ksoltanidev commented May 16, 2024

Hey, I'm posting here the fix I found :

Firstly, there was no issue with the config/middleware.ts. The problem was in the plugin.

This does not work:
server/middlewares/redirect.ts

const redirect = async (ctx: any, next: any) => {
  console.log('MyMiddleware');
  await next();
};
export default redirect;

server/middleware/index.ts

import redirect from './redirect';

export default {
  redirect,
};

server/register.ts

import { Strapi } from '@strapi/strapi';
import middleware from './middlewares';

console.log(middleware.redirect) //This is undefined
export default ({ strapi }: { strapi: Strapi }) => {
  strapi.server.use(middleware.redirect); //registration fails
};

middleware.redirect is undefined, registration fails.

However, this is functional:
server/register.ts

import { Strapi } from '@strapi/strapi';

export default ({ strapi }: { strapi: Strapi }) => {
  strapi.server.use(async (ctx: any, next: any) => {
    console.log('MyMiddleware');
    await next();
  });
};

The way I found, which I don't know why (or more exactly, I don't understand why the other way does not work):

server/middlewares/redirect.ts

const redirect = () => async (ctx: any, next: any) => { //Redirect is now a function that returns the middleware.
  console.log('MyMiddleware');
  await next();
};
export default redirect;

server/middleware/index.ts

import redirect from './redirect';

export default {
  redirect,
};

server/register.ts

import { Strapi } from '@strapi/strapi';
import middleware from './middlewares';

console.log(middleware.redirect()) //This is not undefined anymore
export default ({ strapi }: { strapi: Strapi }) => {
  strapi.server.use(middleware.redirect()); //I call the function that returns my middleware and that works.
};

Can someone with dark magic experience give an explanation ? :)

@ksoltanidev
Copy link

Here is something weird again:
I needed the strapi and config objects in my middleware.

I tried to pass them to my middleware like this :

server/register.ts

import { Strapi } from '@strapi/strapi';
import middleware from './middlewares';

console.log(middleware.redirect()) //This is not undefined anymore
export default ({ strapi }: { strapi: Strapi }) => {
  strapi.server.use(middleware.redirect(strapi));

but that does not work.
My redirect.ts middleware gets nothing.
After some research, I saw that we are supposed to be able to retrieve them directly in the middleware like this :

server/middlewares/redirect.ts

const redirect = (config, { strapi }: { strapi: Strapi }) => async (ctx: any, next: any) => { //Redirect is now a function that returns the middleware.
  console.log('MyMiddleware');
  await next();
};
export default redirect;

So I did this, but since I'm calling my middleware function when registering it, I also added them there:

server/register.ts

import { Strapi } from '@strapi/strapi';
import middleware from './middlewares';

console.log(middleware.redirect()) //This is not undefined anymore
export default ({ strapi }: { strapi: Strapi }) => {
  strapi.server.use(middleware.redirect(config, { strapi }));

And that seem to work. But still strange.

@derrickmehaffy derrickmehaffy added issue: bug Issue reporting a bug severity: medium If it breaks the basic use of the product but can be worked around status: pending reproduction Waiting for free time to reproduce the issue, or more information source: typescript Source is related to TypeScript (typings, tooling, ...) labels May 31, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
issue: bug Issue reporting a bug severity: medium If it breaks the basic use of the product but can be worked around source: typescript Source is related to TypeScript (typings, tooling, ...) status: pending reproduction Waiting for free time to reproduce the issue, or more information
Projects
Status: To be reviewed (Open)
Status: To review
Development

No branches or pull requests

4 participants