Search code examples
dockerdiscord.jsdockerfileaudio-playerdistube

The Discord music bot does not play music in the Docker container


I'm new to Docker and I'm trying to deploy a Discord music bot on a remote Ubuntu Linux server in a Docker container.

The problem is that when the bot is launched in the container, the music does not play, while other parts of the bot that are not related to music playback work fine; at the same time, if the bot is launched outside the Docker container environment, the bot works fine and the music is played.

The bot's behavior when requesting music playback when it is operating in a container is as follows: the bot displays a message that it has found a song and that it starts playing it, and immediately thereafter displays a message that the song has finished playing.

I guess the problem lies in my Dockerfile, or in how I run the image.

My Dockerfile:

FROM node:lts-alpine

ENV WORK_FOLDER='/usr/MyBot'

WORKDIR ${WORK_FOLDER}
COPY ["package.json", "package-lock.json", "tsconfig.json", "./"]
COPY src ./src

RUN npm install
RUN npm install -g typescript
RUN npm run build
COPY . .

CMD ["node", "./dist/index" ]

I'm building an image with the command:

docker build -t mybot .

And I launch the container as follows:

docker run -d -p 80:80 --restart=always --name=mybot mybot

The bot is written in TypeScript using the library discord.js. To play music, the bot uses the library distube.js.


Solution

  • I have solved this problem. In my case, the problem was that my Docker was configured to create Alpine images. As far as I understand, the Alpine image is stripped down for better performance, and I assume that the Alpine image simply did not have the libraries necessary for the music part of the bot to work correctly.

    My solution was to completely reinstall Docker according to the instructions for Ubuntu from the official Docker website. I also needed to change the version of Nodejs used in the image from node:lts-alpine to node:18.12, and I also changed the port used by my image from 8080 to 3000.

    Ultimately, my Dockerfile looks like this:

    FROM node:18.12
    
    ENV WORK_FOLDER='/usr/MyBot'
    
    WORKDIR ${WORK_FOLDER}
    COPY ["package.json", "package-lock.json", "tsconfig.json", "./"]
    COPY src ./src
    
    RUN npm install npm -g
    RUN npm install
    RUN npm install -g typescript
    RUN npm run build
    COPY . .
    
    EXPOSE 3000
    
    CMD ["node", "./dist/index" ]
    

    It took me a long time to find a solution to this problem, so I'm sharing with you one of the ways to check which image your Docker is configured for: just call the batch manager when building the image in your Dockerfile. RUN apk update will work for Alpine, and RUN apt-get update for Ubuntu.