question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

WriteConflict error with MongoDB

See original GitHub issue

Bug description

lib/prisma.js -

const { PrismaClient } = require("@prisma/client");

const prisma = new PrismaClient({log: ['query', 'info', 'warn']})

module.exports = {
    prisma
}

Using MongoDB free atlas tier, just created database and just connected but getting an error named WriteConflict

 12 if(!totalMessages[0]){
→ 13     await prisma.Statistics.create(
  Error in connector: Database error. error code: unknown, error message: Command failed (WriteConflict): WriteConflict error: this operation conflicted with another operation. Please retry your operation or multi-document transaction.)

Last logs

[14/04/2022 06:17-info] Application started:username[[ SOS ]#9847]
prisma:query db.Statistics.aggregate([ { $match: { $expr: { $and: [ { $eq: [ "$type", "TOTAL_MESSAGES", ], }, { $or: [ { $ne: [ { $ifNull: [ "$type", null, ], }, null, ], }, { $eq: [ "$type", null, ], }, ], }, ], }, }, }, { $project: { _id: 1, type: 1, total: 1, date: 1, }, }, ])
prisma:query db.Statistics.aggregate([ { $match: { $expr: { $and: [ { $and: [ { $eq: [ "$type", "DAILY_MESSAGES", ], }, { $or: [ { $ne: [ { $ifNull: [ "$type", null, ], }, null, ], }, { $eq: [ "$type", null, ], }, ], }, ], }, { $and: [ { $eq: [ "$date", "14-04-2022", ], }, { $or: [ { $ne: [ { $ifNull: [ "$date", null, ], }, null, ], }, { $eq: [ "$date", null, ], }, ], }, ], }, ], }, }, }, { $limit: 1, }, { $project: { _id: 1, type: 1, total: 1, date: 1, }, }, ])
prisma:query db.UserStatistics.aggregate([ { $match: { $expr: { $and: [ { $eq: [ "$userId", "788989831921139722", ], }, { $or: [ { $ne: [ { $ifNull: [ "$userId", null, ], }, null, ], }, { $eq: [ "$userId", null, ], }, ], }, ], }, }, }, { $project: { _id: 1, userId: 1, total: 1, firstMessage: 1, }, }, ])
prisma:query db.Users.aggregate([ { $match: { $expr: { $and: [ { $eq: [ "$userId", "788989831921139722", ], }, { $or: [ { $ne: [ { $ifNull: [ "$userId", null, ], }, null, ], }, { $eq: [ "$userId", null, ], }, ], }, ], }, }, }, { $limit: 1, }, { $project: { _id: 1, userId: 1, username: 1, avatarURL: 1, firstMessageDate: 1, }, }, ])
prisma:query db.Statistics.insertOne({ type: "TOTAL_MESSAGES", total: 1, date: "14-04-2022", })
prisma:query db.Users.insertOne({ userId: "788989831921139722", username: "schwarzsky#8251", avatarURL: "https://cdn.discordapp.com/avatars/788989831921139722/8ccd47aa5de6579290ed3c0f5897d709.webp", firstMessageDate: "14/04/2022 06:17", })
prisma:query db.Statistics.aggregate([ { $match: { $expr: { $and: [ { $and: [ { $eq: [ "$_id", "6257923be618d92a90c2454b", ], }, { $or: [ { $ne: [ { $ifNull: [ "$_id", null, ], }, null, ], }, { $eq: [ "$_id", null, ], }, ], }, ], }, ], }, }, }, { $project: { _id: 1, type: 1, total: 1, date: 1, }, }, ])
prisma:query db.Users.aggregate([ { $match: { $expr: { $and: [ { $and: [ { $eq: [ "$_id", "6257923be618d92a90c2454c", ], }, { $or: [ { $ne: [ { $ifNull: [ "$_id", null, ], }, null, ], }, { $eq: [ "$_id", null, ], }, ], }, ], }, ], }, }, }, { $project: { _id: 1, userId: 1, username: 1, avatarURL: 1, firstMessageDate: 1, }, }, ])
prisma:query db.Statistics.insertOne({ type: "DAILY_MESSAGES", total: 1, date: "14-04-2022", })
[14/04/2022 06:17-info] registered:ID[788989831921139722] username:[schwarzsky#8251]
prisma:query db.UserStatistics.insertOne({ userId: "788989831921139722", total: 1, firstMessage: "2022-04-14T03:17:15.566+00:00", })
prisma:query db.Statistics.aggregate([ { $match: { $expr: { $and: [ { $and: [ { $eq: [ "$_id", "6257923be618d92a90c2454d", ], }, { $or: [ { $ne: [ { $ifNull: [ "$_id", null, ], }, null, ], }, { $eq: [ "$_id", null, ], }, ], }, ], }, ], }, }, }, { $project: { _id: 1, type: 1, total: 1, date: 1, }, }, ])
prisma:query db.UserStatistics.aggregate([ { $match: { $expr: { $and: [ { $and: [ { $eq: [ "$_id", "6257923be618d92a90c2454e", ], }, { $or: [ { $ne: [ { $ifNull: [ "$_id", null, ], }, null, ], }, { $eq: [ "$_id", null, ], }, ], }, ], }, ], }, }, }, { $project: { _id: 1, userId: 1, total: 1, firstMessage: 1, }, }, ])
[14/04/2022 06:17-info] created:DAILY_MESSAGES:14-04-2022
[14/04/2022 06:17-info] created:USER_TOTAL:ID[788989831921139722]

How to reproduce

Expected behavior

Must create an row with type:TOTAL_MESSAGES.

Prisma information

generator client {
  provider = "prisma-client-js"
}

datasource db {
  provider = "mongodb"
  url      = env("DATABASE_URL")
}

model Users {
  id String @id @default(auto()) @map("_id") @db.ObjectId
  userId String @unique
  username String
  avatarURL String
  firstMessageDate String
}

model StaffTags {
  id String @id @default(auto()) @map("_id") @db.ObjectId
  userId String
  fullMessage String
  type StaffType[]
}

model Statistics {
  id String @id @default(auto()) @map("_id") @db.ObjectId
  type StatisticType
  total Int
  date String
}

model UserStatistics {
  id String @id @default(auto()) @map("_id") @db.ObjectId
  userId String @unique
  total Int
  firstMessage DateTime @default(now())
}

an basic event that explains all my code.

const { GetToday } = require("../GetToday")
const { prisma } = require("../prisma")
const { logger } = require("../winston")

const registerTotalMessagesEvent = async () => {
    const totalMessages = await prisma.Statistics.findMany({
        where: {
            type: 'TOTAL_MESSAGES'
        }
    })

    if(!totalMessages[0]){
        await prisma.Statistics.create({
            data: {
                type: 'TOTAL_MESSAGES',
                total: 1,
                date: GetToday()
            }
        })

        logger.info('created:TOTAL_MESSAGES')
    } else {
        await prisma.Statistics.updateMany({
            where: {
                type: 'TOTAL_MESSAGES'
            },
            data: {
                total: totalMessages[0].total + 1
            }
        })

        logger.info(`updated:TOTAL_MESSAGES[total=${totalMessages[0].total + 1}]`)
    }
}

module.exports = {
    registerTotalMessagesEvent
}

Environment & setup

  • OS: Windows11 64 bit
  • Database: MongoDB
  • Node.js version: 16.14.0

Prisma Version

3.12.0

Issue Analytics

  • State:open
  • Created a year ago
  • Reactions:13
  • Comments:70 (15 by maintainers)

github_iconTop GitHub Comments

11reactions
luluhoccommented, Dec 17, 2022

if anybody needs it for nestjs prisma

import { Prisma } from '@prisma/client';
import * as retry from 'retry';

const IGNORE_ACTIONS = [
  'findUnique',
  'findMany',
  'findFirst',
  'aggregate',
  'count',
  'findRaw',
] as const;

export function retryMiddleware(): Prisma.Middleware {
  return async (params, next) => {
    const operation = retry.operation({
      retries: 4, // 1st time is not counted
      minTimeout: 100, // 100ms
      maxTimeout: 2000, // 2 seconds
      randomize: true,
      factor: 1.97, // https://www.wolframalpha.com/input?i2d=true&i=Sum%5B100*Power%5Bx%2Ck%5D%2C%7Bk%2C0%2C4%7D%5D+%3D+3+*+1000
    });

    if (~IGNORE_ACTIONS.indexOf(params.action as any)) {
      return await next(params);
    }

    return await new Promise((resolve, reject) => {
      operation.attempt(async (a) => {
        let result: any;
        let error: any = null;
        try {
          error = null;
          result = await next(params);
        } catch (e) {
          // Only handle WriteConflict issues
          if (
            e instanceof Prisma.PrismaClientKnownRequestError &&
            e.code === 'P2034'
          ) {
            error = e;
          } else {
            // This is another kind of errors, we stop retrying and reject the promise
            operation.stop();
            reject(e);
          }
        }

        // If error is null, this will be false and we can continue the execution
        if (operation.retry(error)) {
          return;
        }

        if (error) {
          reject(operation.mainError());
        } else {
          resolve(result);
        }
      });
    });
  };
}


Credit to @aladinflux

7reactions
Benjadahlcommented, Oct 26, 2022

We’re facing the same issue but solving it with a queue would be an overkill. I’m thinking of replacing prisma with another ORM. Has anyone tried another ORM after facing this issue? And did that fix the issue? Even very simple writes fail and cause sporadic issues.

Switched to Mongoose, because of this error and haven’t looked back. It works like a charm and is a simple technology compared to Prisma (Not as many moving parts). Albeit it does not have as many fancy features as Prisma.

But in my experience it is plenty sufficient.

Read more comments on GitHub >

github_iconTop Results From Across the Web

How WriteConflict errors are managed in Transactions ...
If Mongo is not automatically performing any retries for write conflict errors occurs in transaction,how can we manage the write conflict error?
Read more >
MongoDB Transactions: WriteConflict Error - Stack Overflow
It would be helpful if you include error details. A writeConflict could be a duplicate key exception, which can occur within a single ......
Read more >
what are the writeConflicts in mongodb
Internal writeConflicts process · The storage engine returns a status value of WT_ROLLBACK from the document-update function. · The MongoDB ...
Read more >
How to Retry MongoDB Transaction - Finisky Garden
If a write conflict happens, a MongoDBCommandException will be thrown: Exception: Command update failed: Encountered error from mongodb.svc.
Read more >
writeconflict error: this operation conflicted with ... - You.com
From the mongodb transaction docs: Number of operations in a transaction: There are no hard limits to the number of documents that can...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found