docs icon indicating copy to clipboard operation
docs copied to clipboard

MongoDB: Add replica set example using docker-compose

Open Jolg42 opened this issue 2 years ago • 9 comments

I think we should document the current MongoDB docker compose setup @millsp created, it might be the easiest one command setup (if you have docker compose). Also, because MongoDB Atlas is not great to use for tests, it will suffer with latency and concurrency.

https://github.com/prisma/prisma/blob/main/docker/docker-compose.yml#L91-L99 So

version: '3.7'

services:
  mongodb:
    build: ./mongodb_replica
    environment:
      MONGO_INITDB_ROOT_USERNAME: root
      MONGO_INITDB_ROOT_PASSWORD: root
      MONGO_REPLICA_HOST: localhost
      MONGO_REPLICA_PORT: 27017
    ports:
      - '27017:27017'

Note I changed the port from current setup to use the default port, it's the one people will expect.

https://github.com/prisma/prisma/blob/main/docker/mongodb_replica/Dockerfile

FROM mongo:4

# we take over the default & start mongo in replica set mode in a background task
ENTRYPOINT mongod --port $MONGO_REPLICA_PORT --replSet rs0 --bind_ip 0.0.0.0 & MONGOD_PID=$!; \
# we prepare the replica set with a single node and prepare the root user config
INIT_REPL_CMD="rs.initiate({ _id: 'rs0', members: [{ _id: 0, host: '$MONGO_REPLICA_HOST:$MONGO_REPLICA_PORT' }] })"; \
INIT_USER_CMD="db.createUser({ user: '$MONGO_INITDB_ROOT_USERNAME', pwd: '$MONGO_INITDB_ROOT_PASSWORD', roles: [ 'root' ] })"; \
# we wait for the replica set to be ready and then submit the commands just above
until (mongo admin --port $MONGO_REPLICA_PORT --eval "$INIT_REPL_CMD && $INIT_USER_CMD"); do sleep 1; done; \
# we are done but we keep the container by waiting on signals from the mongo task
echo "REPLICA SET ONLINE"; wait $MONGOD_PID;

So when the docker-compose.yml and mongodb_replica/Dockerfile files are created, starting the replica set can be done with the following command

docker-compose up -d

and be accessed with the following conenction url

mongodb://root:root@localhost:27017/mydb?authSource=admin"

Note that this setup is only recommended for development.

Jolg42 avatar Apr 06 '22 08:04 Jolg42

this setup gives me the following error

Node.js v17.8.0

error Command failed with exit code 1.

warning package.json: No license field

/node_modules/@prisma/client/runtime/index.js:41448

            reject2(new PrismaClientInitializationError(error2.message, this.config.clientVersion, error2.error_code));

                    ^


PrismaClientInitializationError: Database error. error code: unknown, error message: Server selection timeout: No available servers. Topology: { Type: Unknown, Servers: [ { Address: localhost:27017, Type: Unknown, Error: Address not available (os error 99) }, ] }

    at /node_modules/@prisma/client/runtime/index.js:41448:21 {

  clientVersion: '3.12.0',

  errorCode: undefined

}

chaoky avatar Apr 08 '22 23:04 chaoky

Please report that at https://github.com/prisma/prisma and we can take a look at it @chaoky

janpio avatar Apr 11 '22 19:04 janpio

this setup gives me the following error

Node.js v17.8.0

error Command failed with exit code 1.

warning package.json: No license field

/node_modules/@prisma/client/runtime/index.js:41448

            reject2(new PrismaClientInitializationError(error2.message, this.config.clientVersion, error2.error_code));

                    ^


PrismaClientInitializationError: Database error. error code: unknown, error message: Server selection timeout: No available servers. Topology: { Type: Unknown, Servers: [ { Address: localhost:27017, Type: Unknown, Error: Address not available (os error 99) }, ] }

    at /node_modules/@prisma/client/runtime/index.js:41448:21 {

  clientVersion: '3.12.0',

  errorCode: undefined

}

This is much cleaner also uses Mongodb version 5 and no more adding shell scripts on entrypoint. If you used the main mongo docker you will have this error when using version 5 security.keyFile is required when authorization is enabled with replica sets. Bitnami/mongodb is verified so I think its ok to use

version: '3.8'
services:
  
  database:
    image: 'bitnami/mongodb:latest'
    environment:
      - MONGODB_ADVERTISED_HOSTNAME=127.0.0.1
      - MONGODB_REPLICA_SET_MODE=primary
      - MONGODB_ROOT_USER=anyuser
      - MONGODB_ROOT_PASSWORD=anypassword
      - MONGODB_REPLICA_SET_KEY=replicasetkey123
    ports:
      - '27017:27017'
    volumes:
      - 'mongo-db:/bitnami/mongodb'

volumes:
  mongo-db:

masterbater avatar Apr 16 '22 17:04 masterbater

@masterbater thanks a lot, something similar worked for me (on wsl 2)

services:
  gmb:
    build: .
    restart: always
    ports:
      - 3001:3001
    volumes:
      - ./keypair.json:/keypair.json
      - ./freeze-keypair.json:/freeze-keypair.json
      - ./settings.json:/settings.json
    depends_on:
      - mongo
    environment:
      DATABASE_URL: "mongodb://root:[email protected]:27017/config?replicaSet=replicaset"

  mongo:
    image: bitnami/mongodb:latest
    environment:
      - MONGODB_ADVERTISED_HOSTNAME=host.docker.internal
      - MONGODB_REPLICA_SET_MODE=primary
      - MONGODB_REPLICA_SET_KEY=replicasetkey123
      - MONGODB_ROOT_USER=root
      - MONGODB_ROOT_PASSWORD=root
    ports:
      - 27017:27017

https://github.com/docker/for-win/issues/6736

chaoky avatar Apr 19 '22 01:04 chaoky

but there's no host.docker.internal on linux, that will only work for mac/windows

chaoky avatar Apr 19 '22 01:04 chaoky

you can use

    extra_hosts:
      - "host.docker.internal:host-gateway"

in the mean time

chaoky avatar Apr 19 '22 01:04 chaoky

why do we have to use the host network anyway? this is so unusual

chaoky avatar Apr 19 '22 01:04 chaoky

You can use 127.0.0.1 or localhost during development.

On Tue, Apr 19, 2022, 9:58 AM Lordie, @.***> wrote:

why do we have to use the host network anyway? this is so unusual

— Reply to this email directly, view it on GitHub https://github.com/prisma/docs/issues/3040#issuecomment-1101917426, or unsubscribe https://github.com/notifications/unsubscribe-auth/AGI6VFHTX4XO76OGTCW2YOTVFYHOBANCNFSM5SVKAUKA . You are receiving this because you were mentioned.Message ID: @.***>

masterbater avatar Apr 19 '22 07:04 masterbater

I think it would be great to document the production configuration as well.

mammadataei avatar Sep 24 '22 08:09 mammadataei

@Jolg42 thank you, it works well now.

cnscorpions avatar Nov 15 '22 15:11 cnscorpions

Following @Jolg42 I have docker compose as

  mongo:
    build: ./mongodb_replica
    environment:
      MONGO_INITDB_ROOT_USERNAME: root
      MONGO_INITDB_ROOT_PASSWORD: example
      MONGO_REPLICA_HOST: localhost
      MONGO_REPLICA_PORT: 27017
    ports:
      - '27017:27017'

And mongodb_repilca folder Dockerfile is:

FROM mongo:4

# we take over the default & start mongo in replica set mode in a background task
ENTRYPOINT mongod --port $MONGO_REPLICA_PORT --replSet rs0 --bind_ip 0.0.0.0 & MONGOD_PID=$!; \
# we prepare the replica set with a single node and prepare the root user config
INIT_REPL_CMD="rs.initiate({ _id: 'rs0', members: [{ _id: 0, host: '$MONGO_REPLICA_HOST:$MONGO_REPLICA_PORT' }] })"; \
INIT_USER_CMD="db.createUser({ user: '$MONGO_INITDB_ROOT_USERNAME', pwd: '$MONGO_INITDB_ROOT_PASSWORD', roles: [ 'root' ] })"; \
# we wait for the replica set to be ready and then submit the commands just above
until (mongo admin --port $MONGO_REPLICA_PORT --eval "$INIT_REPL_CMD && $INIT_USER_CMD"); do sleep 1; done; \
# we are done but we keep the container by waiting on signals from the mongo task
echo "REPLICA SET ONLINE"; wait $MONGOD_PID;

With DATABASE_URL=mongodb://root:example@mongo:27017/majoklis_db?authSource=admin

I cant get this to work after countless hours (this has been so far the most difficult database setup I have experienced yet :/ )


root@bb9c8e39cee1:/app/ss-ad-scraper# npx prisma db push
Prisma schema loaded from prisma/schema.prisma
Datasource "db": MongoDB database "majoklis_db" at "mongo:27017"
Error: MongoDB error
Kind: Server selection timeout: No available servers. Topology: { Type: ReplicaSetNoPrimary, Set Name: rs0, Max Set Version: 1, Max Election ID: 7fffffff0000000000000001, Servers: [ { Address: localhost:27017, Type: Unknown, Error: Kind: I/O error: Cannot assign requested address (os error 99), labels: {} } ] }, labels: {}
   0: schema_core::commands::schema_push::Calculate `from`
             at schema-engine/core/src/commands/schema_push.rs:29
   1: schema_core::state::SchemaPush
             at schema-engine/core/src/state.rs:436

I am trying to access the mongodb from another docker service, not local host. I see in error that it tries to access it by localhost:27017, but i think it should be mongo:27017 as i need to get to it from another service

marisancans avatar Aug 26 '23 13:08 marisancans