Ruby on Rails #58 Nested Resources

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hello so in this episode we are going to talk about nested resources it's basically nesting tasks inside projects or nesting messages inside an inbox so nesting one resource that is logically connected to another resource inside in our roots in our controllers and in our views and uh here's an example of message resources in the official guides and we are going to try to do it in action in a real rails app now you see i'm already going to try to use ruby 3 and rail 7 alpha so i think it's not going to really matter in this specific application that we are going to build with nested resources but in the future it's going to be fun to see what works and what doesn't work in rails 7 alpha so let's create a new rails app i'll say rails new let's name the app like twitter database postgresql it's been created and yeah it's running input map install instead of webpack install instead of john also installed turbo let's see install the turbo stimulus all out of the box okay looks nice so let's navigate to the application run railsdb crate and try opening the application so i'll go to preview preview run application now i get this error because i'm on cloud nine so i will stop the server and go to the application config environments development rb config.hosts equals nil restart and it should be working okay so here's the new rails app i will actually comment to get so get at all get commit main great app and now i'm going to scaffold inboxes and messages so an inbox can have many messages i'll say rails generate scaffold inbox title and that's it and we are going to scaffold message title and it will be referenced to an inbox so inbox references okay now railsdb migrate and let's again comment this to git git add all git commit main uh scaffold inboxes and messages okay and now we can start the rail server and we can start making the nesting work so what is this all going to be about basically here we have our inboxes our regular roots we can create an inbox and to be able to see the messages that are related to this inbox we would maybe want to navigate to inbox one slash messages and to create a new message for this inbox we would maybe want to navigate to inbox one messages new so how we're going to make this work well first of all of course we're going to add the the associations we'll go to our models inbox dot rb has many messages and of course inside our messages you can say belongs to inbox but it is done by default when they run the scaffold with references okay so next we're going to go to our routes let's have a look at our routes here they are we have our messages that are adjust messages without inbox id slash messages and we have our inboxes and let's have a look at our roots file you see we have resources inboxes and resources messages and we are going to nest messages inside inboxes so we'll say resources inboxes do resources messages let's go back to our roots and see what changes i'll go to a new roots page and here we have inbox messages path so not messages part but inbox messages path you see all the routes for our messages are now nested inside our inbox and let's see how it's going to work so you see i go to inbox one messages for example and you see we get this undefined local variable new message path why is it so because new message path does not exist anymore instead we have new inbox message path you see so it's kind of nested now let's see if it actually works i will go to our views update the index view so go into our index it'll say new inbox message path and we can pass in the inbox oh actually it worked and you see by default we have inboxes one messages new now if we go to our inboxes let's just create a second inbox and navigate to messages you see it already sees inboxes 2 messages new so the path works and here we get another error in our form builder we have undefined method messages path because we are trying to build the form for going to slash messages post but we need to go slash inboxes id messages post so let's go to our messages form builder and we will have phone with model and here we will need to pass in our current inbox and the new message object that is this one so we will say inbox dot first for example coma message new let's see and it seemed to have worked and here we also have this back to messages messages path so this one isn't working either now what are we going to do with this let's actually do the right way here instead of just getting inboxes first we are going to find the inbox in the controller by the params id so i will say add inbox and you see we have no add inbox so we are going to go to our messages controller controllers messages controller and here we are going to go to private methods and say dev set inbox and we will say add inbox equals inbox dot find uh params inbox id so this first is id is going to be the inbox id and if you have messages two for example or three here it's just going to be the id so we are finding message but id and inbox by inbox id okay and let's say that we will set inbox on the very top so before action set inbox for all the actions inside the messages controller okay let's refresh okay so the phone was built but we have a further error in our messages new partial uh new template back to messages isn't available so instead of messages spot we have to use once again something like inbox messages path let's go to our new page and here we have messagespot and we would have inbox messagespot and pass in the inbox let's see if it works so the new message view works i can press back to messages and i will redirect to inbox slash 2 messages okay let's go to create a message and actually we don't want to be able to hard code an inbox id here this should make it uh automatically the inbox id that we are browsing uh in the url so they are going to remove this from the form so no more inbox id input in the form and let's try to create i press create and inbox must exist so we must add the inbox in the controller i'm going to go to the messages controller and here actually i'm going to say not just new but i will say at a message equals at inbox dot messages dot build instead of just message new so here we are going to initiate the inbox let's see if it works i'll go back to messages new message create message it still doesn't work so next we are going to go to our create action and yeah first we will also remove this inbox id from the message params user should not be able to pass it in and we'll go to the create action and here we will say at message equals at inbox dot messages dot build message params just like this and let's see if it works so once again i'm going to create a message great message and you see they seem to have saved the message but we get already another error undefined method messages url again we should redirect to the at inbox at message let's see if it works i will resubmit so go into new message creating the message and okay so now we seem to have submitted it and in the message partial we have no link to show message so here again we need to add the the new path i'm going to go to the partial and here we have add inbox comma message you see it's a kind of troublesome and takes some time to adjust all the code of the messages that are going to be in books uh are going to be inside an inbox but usually it is worth it okay so again i'll try to create the message press create uh i still have something wrong in messages show here it's going to be edit message path at inbox at message actually you can say not at inbox but you can just say add message dot inbox but i think it's more correct to say at inbox but it doesn't really matter in this particular case and here button to destroy will say at inbox at message and here back to messages will say something like at inbox coma messages i think this should work so it should lead to the inbox messages path let's see if it works again resubmitting create inbox okay this path doesn't seem to be broken undefined method edit message path edit inbox message path sure resubmitting again and it worked okay let's show this message let's go back to messages you see it leads us to inbox two messages let's try destroying a message and we still get an error undefined method messages url so again we need to go to the messages controller and say that if we destroy a message it should redirect us to something like inbox messages let's see okay this message doesn't exist anymore i'll go to inbox two slash messages uh i will destroy this message and you see they were directed back to the right path and i think we still need to do our updating so uh here we should re direct not to the message but to the add inbox coma message okay and now let's uh try going to let's say inbox one messages and you see we see the same messages so in inbox fun we don't want to see the same messages we want to see all the messages that are relevant to this inbox for this we are going to go to our index action and say messages equals at inbox dot messages just like this let's see okay in this first inbox we don't have any messages so let's add one message for first inbox back to messages so the nesting works correctly and actually we can also do something similar inside our set message so instead of having the message message find params id we can say message equals inbox dot messages find program id so this way actually it should potentially search for the messages a bit faster because they're switching not between all the messages that they have in the application but only between the ones among the ones that are relevant to this inbox so the search scope is a bit smaller if you have like thousands of messages i guess okay so seems to look fine and this is basically how you can add the nested resources but uh let's go another step further you see in our views folder we have inbox and messages and also in our controllers we have our inboxes controller and messages controller and logically it would be good to also nest them in the views so let's say we want to move the folder of messages into inboxes let's do it like this okay uh i guess yes to all now if i refresh you see no template so the controller doesn't know that it needs to go to this template now we could actually potentially just say in each action that we want to redirect to a template that is nested but it would be better for us to also move our controller into a folder so i would say new folder inboxes move the messages controller into inboxes and here will it work no it still doesn't work so we are going to say that it is going to be in the module inboxes so they're just saying that it's kind of in this folder and that the messages are in the inboxes folder in both views and controllers so let's refresh it still doesn't work so site works says that it didn't manage to find the path it is because we need to go to our messages controller and say that it inherits from the module inboxes so inboxes messages controller now i go back and it seems to be working so let's just go back and say inboxes i will create a third inbox okay now i'll go to the messages i'll create a first message for the third inbox i'll create another um let's go back to messages new message i'll try updating okay here in update ident change the links so i'll go to edit here we'll have show this message so in messages edit let's go to messages edit we have show this message it will say add inbox at message and the inbox messages path at inbox let's see if it works update and it works so this is basically how you can use message resources in ruby on rails application now at first glance it can seem like a lot of stress on updating all the scaffolds but again usually when working a ruby on rails application you don't really do everything by scaffolding so i really had to update each of the views and update the links to work inside this nested resources but usually it helps you keep the logic of your whole application uh in uh intact and you'll always know that messages belong to inboxes and you'll know that you can access them both in controllers and in views inside your inboxes and it is easier to scope the messages it's easy to find the inbox id for each message at a glance and you have the nice logically correct url so that's basically it this is how you can really use nested resources in your views in arabian rails application so thanks for being with me and have fun coding
Info
Channel: SupeRails
Views: 294
Rating: undefined out of 5
Keywords: ruby, rails, ruby on rails, tutorial, programming
Id: p1bAVf6T58I
Channel Id: undefined
Length: 17min 58sec (1078 seconds)
Published: Mon Oct 18 2021
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.