prisma: Simple MongoDB queries are much slower compared to Mongoose
Bug description
I’m in the middle of refactoring from mongoose to prisma using MongoDB database hosted on MongoDB Atlas. I found out that simple queries are much slower compared to mongoose. We are talking 10-20x slower.
I tried to measure it with console.time and these are the rough results
prisma: 456.724ms
mongoose: 40.727ms
prisma: 473.63ms
mongoose: 28.241ms
How to reproduce
- Use a hosted MongoDB (I use MongoDB Atlas)
- Define a simple schema
- Install both Prisma and Mongoose (to try my code, even Typegoose)
- Try to perform the same queries with both libraries.
The queries I used are like this
Mongoose query
NewsFeed.find(
{ type: NewsFeedTypes.RELEASE_NOTE },
{
title: 1,
text: 1,
date: {
$dateToString: {
date: '$publicDate',
format: '%d.%m.%Y',
},
},
}
)
.lean()
.exec();
Mongoose (Typegoose) schema
@modelOptions({
schemaOptions: {
collection: 'NewsFeed',
timestamps: {
createdAt: 'created',
updatedAt: 'modified',
},
},
})
export class NewsFeedSchema {
@prop({ ref: () => GridFsFileSchema })
public image!: Ref<GridFsFileSchema> | null;
@prop({ type: () => Date })
public publicDate?: Date;
@prop({ type: () => String, required: true })
public text!: string;
@prop({ type: () => String, required: true })
public title!: string;
@prop({ type: () => String, enum: NewsFeedTypes, required: true })
public type!: NewsFeedType;
@prop({ type: () => Boolean, required: true, default: false })
public visibleToBrands!: boolean;
@prop({ type: () => Boolean, required: true, default: false })
public visibleToCreative!: boolean;
public created!: Date;
public modified!: Date;
}
export const NewsFeed = getModelForClass(NewsFeedSchema);
Expected behavior
It should be roughly the same speed, not 10x-20x slower.
Prisma information
generator client {
provider = "prisma-client-js"
previewFeatures = ["filteredRelationCount", "extendedWhereUnique"]
}
datasource db {
provider = "mongodb"
url = env("MONGODB_URI")
}
model NewsFeed {
id String @id @default(auto()) @map("_id") @db.ObjectId
image String? @db.ObjectId
publicDate DateTime?
text String
title String
type NewsFeedType
visibleToBrands Boolean @default(false)
visibleToDesigners Boolean @default(false)
createdAt DateTime @default(now()) @map("created")
updatedAt DateTime @updatedAt @map("modified")
}
prisma.newsFeed.findMany({
where: {
type: NewsFeedType.RELEASE_NOTE,
publicDate: {
lte: new Date(),
},
},
});
Environment & setup
- OS: MacOS
- Database: MongoDB
- Node.js version: 16.17.0
Prisma Version
prisma : 4.7.1
@prisma/client : 4.7.1
Current platform : darwin-arm64
Query Engine (Node-API) : libquery-engine 272861e07ab64f234d3ffc4094e32bd61775599c (at node_modules/.pnpm/@prisma+engines@4.7.1/node_modules/@prisma/engines/libquery_engine-darwin-arm64.dylib.node)
Migration Engine : migration-engine-cli 272861e07ab64f234d3ffc4094e32bd61775599c (at node_modules/.pnpm/@prisma+engines@4.7.1/node_modules/@prisma/engines/migration-engine-darwin-arm64)
Introspection Engine : introspection-core 272861e07ab64f234d3ffc4094e32bd61775599c (at node_modules/.pnpm/@prisma+engines@4.7.1/node_modules/@prisma/engines/introspection-engine-darwin-arm64)
Format Binary : prisma-fmt 272861e07ab64f234d3ffc4094e32bd61775599c (at node_modules/.pnpm/@prisma+engines@4.7.1/node_modules/@prisma/engines/prisma-fmt-darwin-arm64)
Format Wasm : @prisma/prisma-fmt-wasm 4.7.1-1.272861e07ab64f234d3ffc4094e32bd61775599c
Default Engines Hash : 272861e07ab64f234d3ffc4094e32bd61775599c
Studio : 0.477.0
Preview Features : filteredRelationCount, extendedWhereUnique
About this issue
- Original URL
- State: open
- Created 2 years ago
- Reactions: 7
- Comments: 17 (7 by maintainers)
We are experiencing the same issue here, it’s examining way too many documents with the query Prisma generated compared to the native approach and it’s blowing up the MongoDB query Query Targeting monitor and making our apps slower!! Please address this.
When we have capacity, we will reproduce, understand and then hopefully fix this. @rjzheng’s investigation looks like a good lead. Prisma is open source, so if someone opens a PR with a fix before we would of course also take that into consideration and review and potentially merge it.
I just updated my first comment here with an example of how it could be resolved from the application code level
But as an addition here are more ideas that I got
application code
OR
in .schema file:
I made some discoveries here https://github.com/prisma/prisma/issues/17142#issuecomment-1648791852
We experienced the same that Prisma queries are much slower. Our investigation shows that the converted Mongo aggregation queries don’t use set indexes. This is why they are +10x slower. It gets worse with an extensive collection.
We have the same issue on our side, is there any update on this issue ?
I tried digging more. I setup logging in Prisma to log queries that Prisma generates. I wanted to compare the execution time between the query that prisma generated and the simplest query that can be written. I measured the execution time in DataGrip (JetBrains’s DB IDE). For sure it’s not super reliable but… It’s a number.
Prisma’s query
Execution time: ~150ms
Simplest manual query
Execution time: ~130ms
So it looks like that the query that prisma generated is not slower by much so… The performance kick might be caused by data parsing? I don’t know