【问题标题】:"Error: Cannot find module 'mysql2/promise'" when running "docker-compose up"运行“docker-compose up”时出现“错误:找不到模块 'mysql2/promise'”
【发布时间】:2022-02-11 01:15:41
【问题描述】:

我想使用 docker compose 将一个容器中的节点程序连接到另一个容器中的 MySQL 数据库。数据库似乎启动正常,但我的 index.js 文件抛出错误:Cannot find module 'mysql2/promise'

我试过用 npm 安装不同的包,甚至绝望地编辑了我的 package.json 文件中的各种行,但无济于事;总是同样的错误。以下是相关文件,以及目前有效的命令输出。

$ npm install mysql2

npm WARN simplyanything@1.0.0 No repository field.
npm WARN simplyanything@1.0.0 No license field.

+ mysql2@2.3.3
updated 1 package and audited 101 packages in 3.302s
found 0 vulnerabilities

$ sudo npm install mysql2-promise

+ mysql2-promise@0.1.4
updated 1 package and audited 101 packages in 3.772s
found 0 vulnerabilities

package.json

{
    "name": "simplyanything",
    "version": "1.0.0",
    "scripts": {
        "start": "node index.js"
    },
    "description": "Actions party game",
    "dependencies": {
        "express": "^4.17.1",
        "mysql2": "^2.3.3",
        "mysql2-promise": "^0.1.4",
        "socket.io": "^4.4.1"
    },
    "author": "Chris DeHaan"
}

index.js

const express = require('express');
let app = express();
let http = require('http').createServer(app);
const io = require('socket.io')(http, {pingTimeout: 60000});

app.use(express.static('public'));
app.get('/', (req, res) => { res.sendFile(__dirname + '/index.html'); });
http.listen(3000, () => { console.log('listening on *:3000'); });

const mysql = require('mysql2/promise');
const pool = mysql.createPool({
    connectionLimit : 100,
    host: process.env.MYSQL_HOST,
    user: process.env.MYSQL_USER,
[.... and so on]

Dockerfile

FROM node:latest
WORKDIR /sa/
COPY package.json .
RUN npm install
COPY . .

docker-compose.yml

version: '3.8'
services: 
    web:
      build:
          context: .
      env_file: ./.env
      command: npm start
      volumes: 
          - .:/sa/
          - /sa/node_modules
      ports:
          - $NODE_LOCAL_PORT:$NODE_DOCKER_PORT
      depends_on: 
          - mysqldb
      environment: 
          MYSQL_HOST: mysqldb
    mysqldb:
      image: mysql
      env_file: ./.env
      environment: 
          MYSQL_ROOT_PASSWORD: $MYSQL_ROOT_PASSWORD
          MYSQL_DATABASE: $MYSQL_DATABASE
      ports:
          - $MYSQL_LOCAL_PORT:$MYSQL_DOCKER_PORT
      volumes:
          - mysql:/var/lib/mysql
          - mysql_config:/etc/mysql
volumes:
    mysql:
    mysql_config:

.env

MYSQL_USER=simplyanythingUser
MYSQL_ROOT_PASSWORD=[Well, you don't need to know this]
MYSQL_DATABASE=simplyanything
MYSQL_LOCAL_PORT=3306
MYSQL_DOCKER_PORT=3306

NODE_LOCAL_PORT=3000
NODE_DOCKER_PORT=3000

$ sudo docker build -t sa .

Sending build context to Docker daemon  9.526MB
Step 1/5 : FROM node:latest
 ---> e6bed6a65a54
Step 2/5 : WORKDIR /sa/
 ---> Using cache
 ---> 3da61e5a5928
Step 3/5 : COPY package.json .
 ---> Using cache
 ---> 1e7bbeaaa894
Step 4/5 : RUN npm install
 ---> Using cache
 ---> 52f36e54d698
Step 5/5 : COPY . .
 ---> e0a50567567b
Successfully built e0a50567567b
Successfully tagged sa:latest

$ node index.js

Debugger listening on ws://127.0.0.1:44273/a1b49bfc-83e7-47dd-ba53-64a8df19ccc9
For help, see: https://nodejs.org/en/docs/inspector
Debugger attached.
listening on *:3000

(此时它可以在浏览器中运行)

$ sudo docker-compose up

Starting sa_mysqldb_1 ... done
Starting sa_web_1     ... done
Attaching to sa_mysqldb_1, sa_web_1
mysqldb_1  | 2022-02-08 08:31:21+00:00 [Note] [Entrypoint]: Entrypoint script for MySQL Server 8.0.28-1debian10 started.
mysqldb_1  | 2022-02-08 08:31:21+00:00 [Note] [Entrypoint]: Switching to dedicated user 'mysql'
mysqldb_1  | 2022-02-08 08:31:21+00:00 [Note] [Entrypoint]: Entrypoint script for MySQL Server 8.0.28-1debian10 started.
mysqldb_1  | 2022-02-08T08:31:21.660916Z 0 [System] [MY-010116] [Server] /usr/sbin/mysqld (mysqld 8.0.28) starting as process 1
mysqldb_1  | 2022-02-08T08:31:21.747461Z 1 [System] [MY-013576] [InnoDB] InnoDB initialization has started.
web_1      | 
web_1      | > simplyanything@1.0.0 start
web_1      | > node index.js
web_1      | 
mysqldb_1  | 2022-02-08T08:31:23.587278Z 1 [System] [MY-013577] [InnoDB] InnoDB initialization has ended.
web_1      | node:internal/modules/cjs/loader:936
web_1      |   throw err;
web_1      |   ^
web_1      | 
web_1      | Error: Cannot find module 'mysql2/promise'
web_1      | Require stack:
web_1      | - /sa/index.js
web_1      |     at Function.Module._resolveFilename (node:internal/modules/cjs/loader:933:15)
web_1      |     at Function.Module._load (node:internal/modules/cjs/loader:778:27)
web_1      |     at Module.require (node:internal/modules/cjs/loader:999:19)
web_1      |     at require (node:internal/modules/cjs/helpers:102:18)
web_1      |     at Object.<anonymous> (/sa/index.js:13:15)
web_1      |     at Module._compile (node:internal/modules/cjs/loader:1097:14)
web_1      |     at Object.Module._extensions..js (node:internal/modules/cjs/loader:1149:10)
web_1      |     at Module.load (node:internal/modules/cjs/loader:975:32)
web_1      |     at Function.Module._load (node:internal/modules/cjs/loader:822:12)
web_1      |     at Function.executeUserEntryPoint [as runMain] (node:internal/modules/run_main:77:12) {
web_1      |   code: 'MODULE_NOT_FOUND',
web_1      |   requireStack: [ '/sa/index.js' ]
web_1      | }
web_1      | 
web_1      | Node.js v17.4.0
mysqldb_1  | 2022-02-08T08:31:25.086275Z 0 [Warning] [MY-010068] [Server] CA certificate ca.pem is self signed.
mysqldb_1  | 2022-02-08T08:31:25.086445Z 0 [System] [MY-013602] [Server] Channel mysql_main configured to support TLS. Encrypted connections are now supported for this channel.
mysqldb_1  | 2022-02-08T08:31:25.277625Z 0 [Warning] [MY-011810] [Server] Insecure configuration for --pid-file: Location '/var/run/mysqld' in the path is accessible to all OS users. Consider choosing a different directory.
mysqldb_1  | 2022-02-08T08:31:25.354311Z 0 [System] [MY-011323] [Server] X Plugin ready for connections. Bind-address: '::' port: 33060, socket: /var/run/mysqld/mysqlx.sock
mysqldb_1  | 2022-02-08T08:31:25.355558Z 0 [System] [MY-010931] [Server] /usr/sbin/mysqld: ready for connections. Version: '8.0.28'  socket: '/var/run/mysqld/mysqld.sock'  port: 3306  MySQL Community Server - GPL.

我真的被卡住了,因为它所需的一切似乎都已安装,并且当我在命令行上使用 node index.js 运行它时它可以工作,所以显然在设置我的容器或编写时我缺少一些东西连接它们。任何建议将不胜感激。干杯。

【问题讨论】:

  • 是的,这似乎是一个合理的尝试,但是将有问题的行更改为:const mysql = require('mysql2-promise'); 会导致几乎相同的错误:Error: Cannot find module 'mysql2-promise' 不过感谢您的评论。仅供参考,我的代码大量来自this page,这可能有助于澄清我哪里出错了?我觉得根本不需要 mysql2-promise 包,而 mysql2/promise 是不同的东西,包含在 mysql2 包中。
  • 如果你使用 docker compose,你应该使用 docker compose builddocker compose up --build 构建你的镜像
  • @Phil 完全正确的忽略文件,我现在有 .dockerignore 正好一行,node_modules/ 在里面。谢谢你。至于构建命令,我假设你的意思是$ sudo docker-compose build,在这种情况下它运行成功,最后一行是Successfully tagged sa_web:latest。可悲的是,$ sudo docker-compose up 然后以丢失模块的相同错误退出。
  • 感谢@Phil 的持续支持。我从Dockerfile 中取出COPY . .,然后运行$ npm uninstall mysql2-promise。我的 package.json 在依赖项中不再有 mysql2-promises。这似乎是一种改进,更少的依赖。我对我的节点代码进行了一些更改以删除承诺,因此使用:mysql = require('mysql2'); 现在sudo docker-compose up 之后的错误消息为:Error: Cannot find module 'mysql2' 很明显,我对如何为容器提供模块的理解存在一个更根本的问题它需要。
  • 好问题。是的,我确实重新构建了,第一次运行$ sudo docker-compose build,我的第4步是这样的:步骤4/5:RUN npm install ---> 在4b3ec39e26cc中运行添加了85个包,并在9s 2个包中审核了86个包正在寻找资金运行npm fund 以获取详细信息,发现 0 个漏洞,但现在如果我再做一次,它只会说:步骤 4/4 : RUN npm install ---> Using cache ---> 85c9f7f83401

标签: mysql node.js docker npm


【解决方案1】:

下午好,我遇到了同样的问题。你可以尝试使用

npm install mysql2

【讨论】:

  • OP 在他们的package.json 中已经有"mysql2": "^2.3.3"
  • 您的答案可以通过额外的支持信息得到改进。请edit 添加更多详细信息,例如引用或文档,以便其他人可以确认您的答案是正确的。你可以找到更多关于如何写好答案的信息in the help center
猜你喜欢
  • 1970-01-01
  • 2021-08-06
  • 2022-08-16
  • 2021-06-13
  • 2023-03-09
  • 2018-12-25
  • 1970-01-01
  • 2019-04-20
  • 1970-01-01
相关资源
最近更新 更多