GraphQL N+1 Problem

  Рет қаралды 108,808

Ben Awad

Ben Awad

Күн бұрын

Learn what the N+1 problem is in GraphQL and how you can fix it with DataLoader or database joins.
Code: github.com/benawad/graphql-n-... ​

----
Follow me online: voidpet.com/benawad
#benawad

Пікірлер: 206
@coherentpanda7115
@coherentpanda7115 4 жыл бұрын
This is the first vid that truly explained this N + 1 problem so easy a newbie would understand, and showed clearly the examples with and without. Nice job!
@sasageyo9571
@sasageyo9571 2 жыл бұрын
True story, i was asked this question in an interview, the interviewer just asked how would you fetch a foreign key in a one to many database. I didnt understand the question then, gave a non optimized answer , 6 months later i realize why i was rejected. 😢 Btw great video, thanks man. You are the first person i subscribe to on youtube. 😁
4 жыл бұрын
Been looking for documentation about N+1 problem and couldn't find anything practical about it. This video just saved my life. Thanks.
@mad1083
@mad1083 4 жыл бұрын
You continue to have some of the best content on KZfaq. Well done Ben.
@dealloc
@dealloc 4 жыл бұрын
What I like about DataLoader is two fold; one is that it can be used with any data source you may have, as explained in the video. The other is separating the concerns of fetching that data into a loader, rather than the resolver. Separating the two makes it easy to maintain and substitute the underlying fetching logic and it can even have multiple loaders for one resolver, based on some condition. While DataLoader may provide caching capabilities, it is not actually the main purpose of it; it is a data loading mechanism and it doesn't matter where the data comes from, it just ensure that a signal value by its key always gives you the same value (like what _batching_ does).
@stevereid636
@stevereid636 4 жыл бұрын
Brilliant presentation on using dataloaders and joins! 👍🏾
@proit324techlead9
@proit324techlead9 3 жыл бұрын
Ben gives very clear explanation of N+1 problem. Thank you, Ben!
@josephtveter
@josephtveter 4 жыл бұрын
Thanks Ben, This was awesome. especially learning about the 4th GraphQL argument.
@huzaifaali2209
@huzaifaali2209 3 жыл бұрын
That's the best and simple explanation of N+1 problem I have ever encountered.
@esra_erimez
@esra_erimez 4 жыл бұрын
The importance of this video cannot be overstated. Well done.
@Simple_Simon_UK
@Simple_Simon_UK 4 жыл бұрын
Anyone that knows SQL intimately will watch this video and hopefully say: "WTF! This is progress? So much code and META to do such a simple task".
@bawad
@bawad 4 жыл бұрын
😂
@pookachu64
@pookachu64 3 жыл бұрын
Yep. All so we can pick what fields we need
@archmad
@archmad 3 жыл бұрын
This was actually my drawback using GraphQL coming from SQL, but the alternative is REST.
@eliseumds
@eliseumds 4 жыл бұрын
Love the pragmatism. As always, measure before doing any optimisation.
@ascensionblade
@ascensionblade 4 жыл бұрын
Hi! I don't understand what you mean. Is the idea that one should always measure before optimizing a commonly-held belief?
@eliseumds
@eliseumds 4 жыл бұрын
@@ascensionblade indeed, sir. It's common practice in our industry to adopt measures to improve performance without even knowing whether we need it all. Developer time is very expensive.
@greatbullet7372
@greatbullet7372 4 жыл бұрын
@@eliseumds it depends, a year ago i wouldve worked for u fulltime without expecting 50-100k a year. Today thats a different story.
@Arrygoo
@Arrygoo 4 жыл бұрын
Wow, couldn't have demonstrated the topic in a simpler way. Thanks so much, great pace and great use of examples.
@bawad
@bawad 4 жыл бұрын
thanks!
@Saturn2888
@Saturn2888 4 жыл бұрын
This is the reason I'm always 100% advising people do not use GraphQL unless they know what they're doing. This is the most-basic thing about GraphQL and the thing I've had trouble with myself in the past. It's difficult to solve unless you understand how GraphQL is querying and managing resolvers. I didn't know it had a name, but I'm glad someone else is pointing this out. It's gotta be the one thing that I've consistently noticed in GraphQL services.
@djchrisi
@djchrisi 4 жыл бұрын
12:35 No need to reinvent the wheel. There are a couple of projects who do that. Notably graphql-parse-resolve-info
@bawad
@bawad 4 жыл бұрын
good point
@cucolamorsa
@cucolamorsa 3 жыл бұрын
Had to implement DataLoader and needed exactly this! Thanks
@apkingboy
@apkingboy 3 жыл бұрын
Excelent content!!! Simple in describing the problem and then showing different solutions
@KhoaHuynh-vc6dj
@KhoaHuynh-vc6dj 4 жыл бұрын
Thank you a lot, Really easy for newbie to grasp the concept
@sanjaymachetti7495
@sanjaymachetti7495 2 жыл бұрын
Everything you need to know about n+1 problem and its solution options. Incredible to have achieved all of this in 16 min.
@chakriye
@chakriye 3 жыл бұрын
Very neatly explained. Thank you!
@lwrcica5
@lwrcica5 4 жыл бұрын
Very well presented sir.
@gaatutube
@gaatutube 3 жыл бұрын
Good description of the problem.
@ehtishamali3564
@ehtishamali3564 3 жыл бұрын
Thankyou so much. It's super helpful. I think example with dataloader ( can be seen at 8:00 minute ) to solve this n+1 is better, because in this way we have the power of resolvers i.e. reusability and dry code. Other than this, where we are doing every thing in single resolver, no possibility of reuse, wet wet code everywhere.
@ibrahemkhalil5924
@ibrahemkhalil5924 2 жыл бұрын
Superb tut Ben!
@michaeldausmann6736
@michaeldausmann6736 4 жыл бұрын
well explained and a good overview of the solutions.
@ChumX100
@ChumX100 3 жыл бұрын
In NoSQL DBs is common to use denormalized schemas, so in your example, we could just store the author data within the book records themselves and we wouldn't have this problem. Obviously we would then need to update the books on author changes, but this is fine if we assume that the number of reads is way larger than the number of writes. A safe assumption for most use-cases.
@nighma
@nighma 4 жыл бұрын
Will be nice to see how do you take advantages of graphql-parse-resolve-info. Great job! Thanks
@talbertherndon1925
@talbertherndon1925 2 жыл бұрын
Great video as always ben
@shan9287
@shan9287 3 жыл бұрын
Great explanation! Thank you.
@anthonyhinsinger7970
@anthonyhinsinger7970 4 жыл бұрын
One solution I use is to have the AuthorLoader (because your gql api can also have a authorById or any others "entrypoints") then in the hydrate function you can fill the AuthorLoader cache with its prime() function. It's a mix between your join and dataloader solution, to get only one database query and keep the dataloader advantages in complexes gql queries.
@bawad
@bawad 4 жыл бұрын
interesting, that's kinda of cool
@mygirlinyesterday
@mygirlinyesterday 3 жыл бұрын
this is very useful for me thank you so much
@benzij1739
@benzij1739 4 жыл бұрын
If your data is stored in sql, you can also make use of views and transactions (or procedures) which is way easier to scale off and prevent redundant code.
@k5lre8
@k5lre8 3 жыл бұрын
Data is in different databases?
@stevehyuga9216
@stevehyuga9216 10 ай бұрын
Great video. Thanks
@donmikele07
@donmikele07 3 жыл бұрын
I'm from the REST world. I respect GraphQL and I'm pretty new in it because I didnt' have a chance to use it in my projecects. I saw a lot from Ben's channel and Ben is doubtless great teacher and explanator. But I also saw a lot of things from GraphQL those are 'reinvent the wheel'. As much as I understood, the point of GQL is to optimize req/res between client and server, to make more comfortable env for developers... Internet is more and more faster so there is a question when the speed becomes criticatl? And I saw a lot of complexity in the code for GQL implementations. So I didn't see quite enough reasons to jump to GQL in some of my projects, when it is much more simpler and readable with the REST, without all those packages and libraries like Apollo. But from new guys in web development, I suppose it's a good idea to start and continue with GraphQL. And finally I hope next tool for communication between server and client will be much simpler than this one. Why something is new and maybe quite good when it makes the things much confusinge and a lot of headache.
@dennistennis5622
@dennistennis5622 4 жыл бұрын
Hi Ben, you are right about join-monster.. too bad though... seemed promising.
@JigneshThummar
@JigneshThummar 3 жыл бұрын
Very well explained
@gliderguld
@gliderguld 3 жыл бұрын
Nice presentation of what I would call "resolving sub-queries". The next problem might be to resolve entities/items in use multiple. Eg think of a collection of books each having author(s) and reviews. And the reviews in themselves having authors as well. How would we make sure to "dataload" authors last?
@barclaysd
@barclaysd 4 жыл бұрын
Brilliant video Ben, thoroughly enjoyed it and really well explained. Am I right in saying that TypeOrm using cascade and populating relations in a user query with nested relations e.g. User.find({ relations: ['recipes']}) will do this automatically in a single SQL query compiled through LEFT JOIN?
@bawad
@bawad 4 жыл бұрын
yep
@Matoxina
@Matoxina 4 жыл бұрын
Awesome! Thank you!
@yalework6759
@yalework6759 2 жыл бұрын
This is incredibly cool and still relevant 2 years later. I do have a question though: the hydrate function is doing the job of a field resolver, meaning e.g. if we want to add another sub-field on the author in the future, and that field is a relational field in a third table, the complexity of that hydrate function increases. Is it possible to keep the field resolvers but still have conditional joins? It seems like it might be possible because the context function takes in the request object... but I'm not sure how hard it would be to create that doesPathExist function when the request object is the parameter, or whether that fully solves the problem in the first place
@thekingofallblogs
@thekingofallblogs 2 жыл бұрын
Java jpa solves n+1 using entity graph that tells it how/when to fetch. Have to say I like that solution better than writing full sql or dataresolver.
@rachidben-azouz793
@rachidben-azouz793 4 жыл бұрын
It's great, Thanks! 👍
@alltreesareofbears
@alltreesareofbears 2 ай бұрын
Thanks buddy ❤
@Ratstail91
@Ratstail91 3 жыл бұрын
I'm working on a graphQL clone - I'm gonna have to tackle the N+1 problem eventually.
@MaxPicAxe
@MaxPicAxe 4 жыл бұрын
I think you could pass some custom builder abstraction into the graphql ctx. All the resolvers use that, but only at the very root does it query the database from the builder. Haven't really used graphql so not sure if possible
@switchnoob
@switchnoob 4 жыл бұрын
Great video - what is the VS Code plugin that helps highlight brackets/parentheses pairs?
@bawad
@bawad 4 жыл бұрын
marketplace.visualstudio.com/items?itemName=CoenraadS.bracket-pair-colorizer-2
@ashilurrahman9583
@ashilurrahman9583 4 жыл бұрын
Hey Ben, excellent work, but for the conditional approach (best of both worlds) how do we deal with more nested types and fields without it getting too messy? And what about "hydrating" one-to-many relationships at arbitrary level of nesting (from flat table of query result)? E.g. Books > Authors > Reviews (note plural)
@bawad
@bawad 4 жыл бұрын
> without it getting too messy 1. Building an abstraction to deal with the mess 2. Use an abstraction like Hasura/Prisma/Postgraphile to deal with the mess for you > And what about "hydrating" one-to-many relationships at arbitrary level of nesting You basically do a bunch of group by's or you can skip joins and use subqueries: twitter.com/benawad/status/1205879524573007875
@MaxPicAxe
@MaxPicAxe 4 жыл бұрын
I love the idea of graphql but this was the first thing that put me off it... the number of independent network requests
@bawad
@bawad 4 жыл бұрын
Yeah it's definitely possible to optimize it, but it is a little involved
@zindev
@zindev 4 жыл бұрын
Ben, field resolvers are cool, but is there a way to use Eager loading (JOINs) instead of field resolvers? I mean, use eager loading only when necessary using libraries like Typegraphql + Typeorm?
@zindev
@zindev 4 жыл бұрын
You've actually covered my concerns until the end of the video. Thank you.
@jeromealtariba7339
@jeromealtariba7339 3 жыл бұрын
this is an excellent video as usual, but I'm wondering how to do a generic dataloader factory, especially when it comes to re-ordering the result of the query (the trick of AuthorMap in your video). The way you are doing it assumes that the type of the keys is a string or a number, as after, you are creating your AuthMap object which is a Record where, in your example typeof Key is the value of you Author.id. If your Author.id is a string or a number, no issue. But what about if the field of the author you want to "cache' is not a number of a string ? Below is a piece of code where I'm struggling to define the refMap record. I had to transform the type of the key in string to make it works (need also to enforce TTypeOfKey to extends string|number) export const buildLoader = < TEntity extends MyBaseEntity, TTypeOfKey >( entity: TypeObject, keyName: keyof TEntity ): DataLoader => { const loader = new DataLoader( async (valuesofkey: Readonly) => { const vals: TTypeOfKey[] = valuesofkey.map((val) => val); const unsortedValues = await getConnection() .getRepository(entity.name) .find({ [keyName]: In(vals) }); const refMap: Record = {}; { const theValue: TTypeOfKey= (val[keyName] as unknown) as TTypeOfKey; refMap[theValue] = val; }); return valuesofkey.map((val) => refMap[val]); } ); return loader; }; usage : const AuthorLoaderId = buildLoader(Author, "id"); const AuthorLoaderAge = buildLoader(Author, "age"); const AuthorLoaderWhatever = buildLoader(Author, whatever);
@stanimirstoyanov424
@stanimirstoyanov424 4 жыл бұрын
At 10:29 there is an example with JOIN. I think there is a hidden bug in addition to the inconvenience of the extra data being pulled. Before the proper mapping is done using hydrate(...), there is an object of shape { id, title, authorId, name }. Does this not mean that any column names which overlap between the joined tables will get overwritten? i.e. what if the book has a `name` column and so does the author - how does the hydrate(...) function distinguish the two?
@bawad
@bawad 4 жыл бұрын
You'll want to use aliases in that case
@gabrielnastari8513
@gabrielnastari8513 3 жыл бұрын
AMazing bro!!!!
@aldosanchez6870
@aldosanchez6870 4 жыл бұрын
Looking at first sight to your authorLoader implementation, you could write a generic function with that implementation but receiving the name of the table to be called with knex and use it in every relation you need within the context, am i right?
@bawad
@bawad 4 жыл бұрын
Yes
@JanieLe2109
@JanieLe2109 4 жыл бұрын
hi, could you make a video about handling error in graphql mutations or queries, I'm having an issue about connection reset on graphql server due to a lot of timeout sockets are being hanged when throwing exception in case of error provided input. Any idea how to solve it? Thanks
@josevalbuena9423
@josevalbuena9423 3 жыл бұрын
Do Prisma resolvers already solve N+1 problem? I saw this video and went ahead to try out my GraphQL server with SQL debug from prisma and it looks that when I Query a 1:N relationship it does not trigger n+1 SQL queries. Very good video
@grizzyb4149
@grizzyb4149 3 жыл бұрын
Thanks
@MementoNeli
@MementoNeli 4 жыл бұрын
I think you had 'Books' & 'Authors' mixed up, but the rest was very good :p
@DrPanesar
@DrPanesar 4 жыл бұрын
Hi Ben, Do you know how to access "info" in a type-graphql resolver?
@bawad
@bawad 4 жыл бұрын
I think its: @Info() info
@gabrielhauschildt9041
@gabrielhauschildt9041 3 жыл бұрын
What's the point with the "plumbing to get back the authors in order"? Is it the case that simply returning "authors" does not ensure they are returned in order?
@xaviermt1
@xaviermt1 3 жыл бұрын
(in addition to the sorting, it ensures the returned array is the same length as the input array of keys - also a requirement of dataloader)
@erict6796
@erict6796 4 жыл бұрын
Great video Ben! Please consider a video on Apollo federation. Thanks!
@bawad
@bawad 4 жыл бұрын
I'm a bit skeptical kzfaq.info/get/bejne/oJ18dMuBm5acgok.html
@kowsalyaangappan4737
@kowsalyaangappan4737 3 жыл бұрын
Hi Ben,I am facing the same issue in spring Boot.Do you have any reference or course you have done on N+1 problem in GraphQL spring boot?
@sebastienversailles8309
@sebastienversailles8309 4 жыл бұрын
Thanks for this video on a very common problem. For many-to-one relationships, I'm doing joins like you are. But for one-to-many relationships, I still don't have a way to do it in only one SQL query. Do you have any insight on this?
@bawad
@bawad 4 жыл бұрын
Why doesn't a join work for a one-to-many relationship?
@sebastienversailles8309
@sebastienversailles8309 4 жыл бұрын
@@bawad if you have a query "authors" and you query { id, name, Books { id, title} } ; with something like "SELECT * FROM author JOIN book ON book.author_id = author.id" your sql query will return too many lines and I believe your Query will return too many authors?
@bawad
@bawad 4 жыл бұрын
yeah you just need to format the data you get back, something like: const rows = knex(); const books = []; rows.forEach(row => { books.push({ id: row.bookId, title: row.bookTitle }) }) return { id: row[0].id, name: row[0].name, books }
@ashilurrahman9583
@ashilurrahman9583 4 жыл бұрын
@@bawad I think that's still going to give you back the authors repeated, no? For Authors with many Books the result rows would be Authors x Books. For a DB with JSON functions it would be easy to transform related rows to one row but without such a function one needs to loop through as many nested relationships as queried to check if the parent has changed. Maybe a "nested map" function? But that's probably not a thing. Anyway, this is a general result transformation problem, not N+1, but would still be great if you could tackle it and show us!
@bawad
@bawad 4 жыл бұрын
yeah this doesn't work for arbitrary levels, I haven't created a function for that before usually I take it case by case I'll have to think about how an arbitrary one would work
@zeocamo
@zeocamo 4 жыл бұрын
the dataloader version can make Long sql queries that can fail if you hit the limit of the database, the join version do not get this problem
@dealloc
@dealloc 4 жыл бұрын
You solve this by simply limiting the amount of data that can be requested, like you should do anyway in a real-world project. Otherwise you have bigger problems, such as opening yourself to DDoS by someone requesting a lot of data from GraphQL in a single request for example. The most common way to avoid this is to use pagination. There's cursor pagination which returns nodes and edges (like a graph) and a cursor, that can be used to get the next graph of data. You can also just use a regular pagination, which takes a page and offset and returns a list of items within the thresholds you have set (like max items that can be returned)
@ievgen6209
@ievgen6209 2 жыл бұрын
But with joins, you can't do circular references, like get a book > all authors -> books (e.g. you need books of the second author) and so on, as you don't have a field resolver anymore. And that's basically one of the important GraphQL ideas/features (without it, it's basically a kind of RPC).
@mikkotan534
@mikkotan534 4 жыл бұрын
Wouldnt eager loading or doing a left join on books and author fix the n+1? Or it really needs to be on a key resolver, kinda make sense, if you'd eager load Author on the Books Query function it'll load it whether you asked for author or not. Did I understand it correctly?
@bawad
@bawad 4 жыл бұрын
yes
@mikkotan534
@mikkotan534 4 жыл бұрын
@@bawad apologies, i realized you covered everything in the video, I commented this way before you mention left join but I left away and continued later.
@bawad
@bawad 4 жыл бұрын
no worries
@PROFjavi
@PROFjavi 4 жыл бұрын
Great presentation but when you look at the number of ms you saved it doesn't really change/get better. Is this because the DB is so close and there is no ping?
@bawad
@bawad 4 жыл бұрын
yeah the performance is going to vary depending on the query and how much data is being fetched
@JuanSB827
@JuanSB827 4 жыл бұрын
One question, if author has something like company, and we want to do this query { books { author { company , Is it possible to use the last approach for getting the companies? It seems that for nested relations we need to go with Data Loader
@bawad
@bawad 4 жыл бұрын
you can do 2 joins to fetch all that in 1 request
@JuanSB827
@JuanSB827 4 жыл бұрын
@@bawad but doing that would mean that i would had to check the path [books, author, company] in the books query. Am i right ?
@bawad
@bawad 4 жыл бұрын
yeah
@eddysheinman2376
@eddysheinman2376 4 жыл бұрын
Can you explain why dataLoader need to be created per relation. I created dataLoader per field and it works nicely. So for example all my entities have createdBy field, which is ID to user table/collection, I use dataLoader for all relations that need to get user by id and they all seem to be batched into single query.
@bawad
@bawad 4 жыл бұрын
That's what I mean, a dataLoader per relational field
@mschipperheyn
@mschipperheyn 4 жыл бұрын
You should not use await without try catch if you don't want errors being swallowed. You should return the queries directly without assigning the result to a local variable.
@bawad
@bawad 4 жыл бұрын
agreed, just wanted to make it a little more readable
@dealloc
@dealloc 4 жыл бұрын
> You should not use await without try catch Not always true. Using Try/catch means that you want to handle errors that happens as close to the source as possible, which can be fine sometimes, but this makes error handling very cumbersome. It is recommended to let errors pass through until it gets to a point where it can get handled. This of course, depends on your use-case and the type of errors you want to handle, but in those times it makes sense to rethrow the error so that it can be handled a more appropriate place.
@AlexandreAlonso
@AlexandreAlonso 3 жыл бұрын
how to able to see info value, just cannot console.log to read the value
@speedstyle.
@speedstyle. 3 жыл бұрын
I know you mentioned Join Monster, but why use Apollo Server at all rather than an automated db frontend (postgraphile, edgedb) or other graphql server (hasura)?
@xaviermt1
@xaviermt1 3 жыл бұрын
One reason would be that there are multiple data stores within your organisation. Say you are a company with some data in salesforce, some in a sql db, some in mongo, some data accessible from 3rd party API. Now imagine you have a team making some dashboard or Web app that needs data from these disparate sources. You can present all of these different data sources to multi different front end graphql client projects via a single graphql server. If your organisation has all its data in a single database, and only a limited, predictable number of clients of that data, such that just writing a few rest endpoints does the trick, graphql is likely to be overkill.
@huynhphuc5385
@huynhphuc5385 4 жыл бұрын
Could you please tell me how to log the query like you?
@bawad
@bawad 4 жыл бұрын
with knex you use debug environment variable github.com/benawad/graphql-n-plus-one-example/blob/master/package.json#L7
@ashishkmr
@ashishkmr 4 жыл бұрын
@@bawad I already tried it with dotenv before and it was't working but now looking at your code I tried it with corss-env and it works, I wonder why?
@bawad
@bawad 4 жыл бұрын
Not sure, I would imagine it works with dotenv too
@shaadishtiaque2084
@shaadishtiaque2084 4 жыл бұрын
cool tuts
@kasvith
@kasvith 4 жыл бұрын
Good stuffs
@nyanRETARD
@nyanRETARD 4 жыл бұрын
I see VIM keys, I upvote
@saddamhussainEscap
@saddamhussainEscap 4 жыл бұрын
what is knex in your code
@tenminutetokyo2643
@tenminutetokyo2643 4 жыл бұрын
Thanks for not shouting.
@KevinBoutin
@KevinBoutin 3 жыл бұрын
What if you are using a document database like MongoDB and you have nesting? Say for example, I have Bands with Albums but I am also nesting Songs in there. In this case, I could use includes on the Albums but I would have to use $in for fetching the Songs in a different query. See another way?
@alvinyim7837
@alvinyim7837 3 жыл бұрын
IMO, n+1 isn’t a real issue when we have to implement pagination. With pagination, the performance gain by eager loading doesn’t trade off the complexity. Eager loading is generally not scalable.
@emildavidkov1
@emildavidkov1 4 жыл бұрын
It is pretty cool, to take a look how the DL is implemented using some of nodejs(event loop) quirks -> github.com/graphql/dataloader
@tajpouria
@tajpouria 4 жыл бұрын
Hi Ben, Let we know what's you gonna learn in 2020?
@bawad
@bawad 4 жыл бұрын
I actually don't know yet
@MaqsoodAnsari2
@MaqsoodAnsari2 Жыл бұрын
SQL doesn't allow more than 999 params in the "in" clause.
@guleye
@guleye 4 жыл бұрын
Where you are printing these query request ?
@AliYasir5247
@AliYasir5247 4 жыл бұрын
console
@guleye
@guleye 4 жыл бұрын
@@AliYasir5247 no bro its not console
@ahsanghalib
@ahsanghalib 4 жыл бұрын
why not create views table for relationship table and make query to view table. in that way we don't have to join every time or use any data loaders...
@bawad
@bawad 4 жыл бұрын
no matter what you choose, you can always put a caching layer in front
@samuelkelemen9597
@samuelkelemen9597 4 жыл бұрын
Only in Javascript would 5 months be considered dead.
@bawad
@bawad 4 жыл бұрын
True
@oskarsrukmans8997
@oskarsrukmans8997 4 жыл бұрын
Why do you have question marks instead of IDs ?
@bawad
@bawad 4 жыл бұрын
I'm not sure
@OscarRothAndersen
@OscarRothAndersen 4 жыл бұрын
It's logging the prepared statement, which is the preferred way of logging SQL queries for both security and readability concerns.
@zlackbiro
@zlackbiro Жыл бұрын
If you watching this in 2022, you can use prisma and graphQL using nexus with apollo server. Done! 🙂
@killerdroid99
@killerdroid99 10 ай бұрын
exactly that's what I use, no more n+1 issue only the data I need
@PrinceSodhi
@PrinceSodhi 4 жыл бұрын
Thank you, I learn a lot from your videos. Looking forward to some videos and tips regarding Apollo type generation. `apollo-codegen`
@eyesight2073
@eyesight2073 3 жыл бұрын
😻😻😻😻
@amanrubey
@amanrubey 3 жыл бұрын
You look like Shawn Mendes
@filcondrat
@filcondrat 4 жыл бұрын
looks like you haven't sleep well in a while
@bawad
@bawad 4 жыл бұрын
yeah my eyes usually look like that even when I sleep +9 hours
@vaibhav1180
@vaibhav1180 4 жыл бұрын
@@bawad It's like you've been sleeping less for months.
@nuwang1
@nuwang1 4 жыл бұрын
Sick
@kekddd
@kekddd 4 жыл бұрын
Is there a reason you used knex for this video? I usually see you using typeorm. I'm panicking, thinking you know something I don't...
@stevereid636
@stevereid636 4 жыл бұрын
I was wondering the same thing especially as there are rumours that typeorm is waning?
@bawad
@bawad 4 жыл бұрын
I still use TypeORM just wanted to make this video in javascript for the devs that aren't familiar with type-graphql syntax
@kekddd
@kekddd 4 жыл бұрын
@@bawad 👌Now I can sleep tonight. Great video, as always!
@bretzel30000
@bretzel30000 3 жыл бұрын
I really don't understand why people always need to find clever ways of working around SQL. Back in the Ruby on Rails days they also had this N+1 Problem when they were using ORM. This was 2011, but Relational DB's have solved this N+1 Problem in like the 90s or even earlier. At this point i have to ask: why not access the db directly from the client with SQL. Graph Ql seems to me like "not invented here" methodology.
@hiexis
@hiexis 2 жыл бұрын
Does any of these techniques work in 3+ step queries? user { post { comments { } } }
@adamhenriksson6007
@adamhenriksson6007 3 жыл бұрын
What is wrong with the sort function? :'( It's right there
@AvindraGoolcharan
@AvindraGoolcharan 4 жыл бұрын
Be careful with dataloader. As with any caching mechanism, your implementation should NOT rely on some cache representation. That's exactly how to get stale reads and buggy logic
@craigcook9715
@craigcook9715 4 жыл бұрын
There are only two hard things in Computer Science: cache invalidation and naming things. -- Phil Karlton [And also a favorite of Martin Fowler].
@miklosnemeth8566
@miklosnemeth8566 4 жыл бұрын
My young friend you just start scratching the surface of the challenges of serious application development. I was experimenting with GraphQL in early 2019, since I am open to learn everything new and innovative, and quickly realized that it is great for "hello-world-sized" demo applications, but when you are working on real business applications from the arena of warehousing, manufacturing, logistics, and others; this technology is a total dead-end and waste of time. SQL is with us for 40 or so years, nothing can replace it. Do you remember ODATA, for example? With your nifty resolvers you are just overcomplicating your system and make them dead slow, and enormously hard to maintain or debug, especially with typeless languages like JavaScript, Python. If you want a flexible query engine, simply receive SQL queries from your clients and return back JSON structures, dead easy and the most performant solution, the simplest to maintain and debug. No-SQL databases are anyway totally unusable for complex business database systems/applications.
@iAmCracky
@iAmCracky 4 жыл бұрын
I think Facebook does quite wel using GraphQL
@miklosnemeth8566
@miklosnemeth8566 4 жыл бұрын
@@iAmCracky Facebook has 8500 programmers to maintain the system. Facebook is not a business application, it is a good business, but it is an entertaining system and it is dead simple vs a manufacturing or ERP system.
@exactzero
@exactzero 3 жыл бұрын
@@miklosnemeth8566 If Facebook is dead simple, they wouldn't need 8500 programmers.
@serkankaracasulu9742
@serkankaracasulu9742 4 жыл бұрын
Hi, i want to use dataloader with mongoose, i am using this www.instapainting.com/blog/use-dataloader-to-batch-and-cache-arbitrary-mongodb-queries examle, it works, but how can i use projection.is there any easy solution which i didn't know
@framegrace1
@framegrace1 4 жыл бұрын
A kitten dies every time an open 'where in (.....) is used' on a relational DB. If you select always the fields you want to return, the DB will not do the Join if is not needed. So, you don't need to do anything on the code. DB's are clever enough to not to do the join if you are not returning any value from the right side. Always use Joins, even for 1 result. Don't be stupid. Sincerely, your DBA.
@bawad
@bawad 4 жыл бұрын
> A kitten dies every time an open 'where in (.....) is used' on a relational DB. Is that slower than a query with a join? I assumed the performance profile is something like: select * from users u inner join articles a on u.id = a.userId; => 10 ms select * from articles where id (1, 2, 3); => 10 ms worst case > If you select always the fields you want to return, the DB will not do the Join if is not needed Oh, good to know, thanks!
@framegrace1
@framegrace1 4 жыл бұрын
​@@bawad Roundtrips are not the only metering to consider here. You have to consider also the work on the DB.Join is the best, because it's all an internal DB issue. When having a Join, DB just have to play with indexes to get the right records, and then return the right data once all is resolved. That's very quick (Playing with indexes is very quick, the best O() value you can achieve on a DB). The IN clause is very unoptimizable..., the DB can do either a select for each id internally, and then return the results, or if there are more than certain amount, it just selects from lower to bigger and filters the results, which can be even worse. So at best, you are just repeating the individual selects, just on the DB side (It can last a lot of time, so you will have a single roundtrip but much much slower) and at worst, when you have 100 or more ids inside the IN, the DB may do a select of thousands of hundreds or records and then loop while filtering.
DataLoader and the Problem it solves in GraphQL
21:41
knowthen
Рет қаралды 27 М.
My GraphQL Performance Problem
13:33
Ben Awad
Рет қаралды 48 М.
Вечный ДВИГАТЕЛЬ!⚙️ #shorts
00:27
Гараж 54
Рет қаралды 14 МЛН
THE POLICE TAKES ME! feat @PANDAGIRLOFFICIAL #shorts
00:31
PANDA BOI
Рет қаралды 25 МЛН
Smart Sigma Kid #funny #sigma #comedy
00:25
CRAZY GREAPA
Рет қаралды 23 МЛН
SQLite and the N+1 (no) problem
8:30
Mycelial
Рет қаралды 6 М.
Why I Don’t Use GraphQL Anymore
16:29
Harry Wolff
Рет қаралды 69 М.
Getting Started with OpenTelemetry and GraphQL in .NET
17:26
ChilliCream
Рет қаралды 951
Stop Making These 5 GraphQL Mistakes
8:59
TomDoesTech
Рет қаралды 2,7 М.
What Programming Font Should You Use?
4:12
Ben Awad
Рет қаралды 35 М.
Guide to the GraphQL Ecosystem
19:47
Ben Awad
Рет қаралды 60 М.
GraphQL vs REST: what you need to know
10:11
Kodaps Academy
Рет қаралды 15 М.
N+1 и дефолтные методы. Spring Boot + Webix
17:01
GraphQL vs REST for Side Projects
14:15
Ben Awad
Рет қаралды 91 М.
Samsung Galaxy 🔥 #shorts  #trending #youtubeshorts  #shortvideo ujjawal4u
0:10
Ujjawal4u. 120k Views . 4 hours ago
Рет қаралды 5 МЛН
Красиво, но телефон жаль
0:32
Бесполезные Новости
Рет қаралды 776 М.
😱Хакер взломал зашифрованный ноутбук.
0:54
Последний Оплот Безопасности
Рет қаралды 599 М.
Игровой Комп с Авито за 4500р
1:00
ЖЕЛЕЗНЫЙ КОРОЛЬ
Рет қаралды 2,2 МЛН
Мой инст: denkiselef. Как забрать телефон через экран.
0:54