«Ошибка — unhandledRejection: Ошибка: слушайте EADDRINUSE: адрес уже используется ::: 3000», когда я использую Slack Bolt для JavaScript с ngrok и Next.js

Фон

Мы разрабатываем Slack Bot. На этот раз мы используем Bolt для JavaScript (Node.js), предоставленный Slack, React, Next.js и ngrok. Вот что делает каждый из них.

  • Bolt для JavaScript: я не хочу использовать базовый API Slack, но хочу извлечь выгоду из функции, которая его обертывает.
  • React: необходимо использовать Next.js
  • Next.js: Slack требуется URL-адрес запроса, чтобы уведомлять мое приложение-бот, когда в Slack происходят такие события, как упоминания, но Next.js позволяет легко создать конечную точку API для установки этого URL-адреса (например, /api/something).
  • ngrok: в локальной среде разработки этот URL-адрес будет http://localhost:3000, поэтому протокол будет http вместо https. Slack не позволяет этого, поэтому нам нужен URL-адрес, начинающийся с https, который туннелирует к локальному http://localhost:3000. ngrok обеспечивает это легко!

Проблема, которую нужно решить.

Я уже подтвердил, что если я наберу @xxxx в определенной рабочей области в Slack, событие будет уведомлено https://xxxx.jp.ngrok.io/api/slack/events. Однако в этом файле API

app.event("app_mention", async ({ event, say }) => {
  .
  .
  .
}

не вызывается и возникает следующая ошибка

error - unhandledRejection: Error: listen EADDRINUSE: address already in use :::3000

Я хотел бы знать, почему и как это решить.

Исходный код

/api/slack/events.ts

import type { NextApiRequest, NextApiResponse } from "next";
require("dotenv").config();
import app from "../../../config/slackAuth";

export default async function handler(
  req: NextApiRequest,
  res: NextApiResponse
) {
  // Unique case for Slack challenge
  if (req.body.challenge) return res.status(200).json(req.body);

  // Subscribe to 'app_mention' event in your App config
  // See https://api.slack.com/tutorials/tracks/responding-to-app-mentions
  app.event("app_mention", async ({ event, say }) => {
    try {
      // Response to the message in the thread where the event was triggered with @${message.user} 
      // See https://slack.dev/bolt-js/concepts#message-sending
      await say({
        text: `Hi <@${event.user}>!`,
        thread_ts: event.ts,
      });
    } catch (error) {
      await say({
        text: `<@${event.user}> ${error.message}.`, // @userName Request failed with status code 429.
        thread_ts: event.ts,
      });
    }
  });

  (async () => {
    // Start this app
    await app.start(process.env.PORT || 3000);
    console.info("⚡️ Bolt app is running!");
  })();

  return res.status(404).json({ message: "Unknown event type" });
}

Код ошибки

error - unhandledRejection: Error: listen EADDRINUSE: address already in use :::3000
    at Server.setupListenHandle [as _listen2] (net.js:1331:16)
    at listenInCluster (net.js:1379:12)
    at Server.listen (net.js:1465:7)
    at C:\Users\81906\Documents\slackGpt3\node_modules\@slack\bolt\dist\receivers\HTTPReceiver.js:176:25    
    at new Promise (<anonymous>)
    at HTTPReceiver.start (C:\Users\81906\Documents\slackGpt3\node_modules\@slack\bolt\dist\receivers\HTTPReceiver.js:142:16)
    at App.start (C:\Users\81906\Documents\slackGpt3\node_modules\@slack\bolt\dist\App.js:241:30)
    at eval (webpack-internal:///(api)/./pages/api/slack/events.ts:69:69)
    at handler (webpack-internal:///(api)/./pages/api/slack/events.ts:71:7)
    at Object.apiResolver (C:\Users\81906\Documents\slackGpt3\node_modules\next\dist\server\api-utils\node.js:363:15) {
  code: 'EADDRINUSE',
  errno: -4091,
  syscall: 'listen',
  address: '::',
  port: 3000
}
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
0
52
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Проблема

Использовать Slack Bolt для JavaScript с Next.js непросто по следующим причинам:

  • Запуск npm run dev в проекте Next.js запускает сервер по адресу localhost:3000.
  • Запуск app.start() в Slack Bolt для JavaScript запускает сервер с помощью Express.js, который также пытается использовать localhost:3000.
  • Это вызывает ошибку, потому что два сервера пытаются использовать один и тот же порт.

Эта информация была предоставлена ​​кем-то из Slack, а источник можно найти по адресу https://github.com/slackapi/bolt-js/issues/1687.

Решение

  • Вы можете изменить номер порта, используемый Bolt, например, на 3001.
  • Однако это затруднит взаимодействие двух серверов на localhost:3000 и 3001 друг с другом.
  • URL-адрес запроса, зарегистрированный в консоли Slack Bolt для JavaScript, имеет значение 3000, поэтому полученные там события не смогут передаваться на порт 3001.

Другие вопросы по теме

Похожие вопросы

Не удается войти в Laravel API на промежуточном сервере (Laravel Forge) через NextJs или Postman
Ошибка выполнения Не удается прочитать свойства неопределенного (чтение «вызов») при переходе с next12 на next13
TypeError: невозможно прочитать свойства неопределенной (чтение «фильтра») таблицы Tanstack (React)
Когда я console.info(функция) с одной страницы на другую страницу, это дает мне неопределенное значение на другой странице, но на реальной странице это дает мне реальное значение
Как в NextJS избежать повторения функции getStaticProps на каждой странице?
Ошибка синтаксического анализа модуля: идентификатор '_templateObject' уже объявлен
Библиотека тестирования React с Next.Js, сбой модульного теста из-за состояния?
TypeError: не удается прочитать свойства undefined (чтение «вызов») на Next.js
Как развернуть приложение next.js на AWS, что такое входной файл для сервера?
Ошибка предварительного рендеринга NextJS с Context и Firestore