JS Built-in Signals In React and Svelte TODAY!

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hardly a week goes by without somebody talking to me or talking in the comment stream about signals and it's almost always about react react and signals when will react get signals react sucks because it doesn't have signals should I use signals in my production react application and by the way my answer today is no no way if you want to use signals in production there are lots of great options they're solid quick angular and coming up felt and View and more react doesn't support signals and the way that folks have tried to do it so far is pretty janky So my answer now is no for right now and that answer isn't going to change after this video Even though this video is about how the landscape of signals has fundamentally changed because now there is a proposal to bake signals into the browser the promise is that the Frameworks that we love today would adopt those standard signals as a consistent way to model application State and potentially Frameworks could even interoperate between each other by sharing State through signals mind-blowing so there's a link in description right down below to the proposal as well as another good article that does some analysis and has some code that I stole for this video but the proposal has a polyi library and I couldn't help myself so I figured out a reasonably decent way of interfacing the proposed standards based signals with react and another framework and we'll get there be sure to stick around for the end of the video for that you're not going to want to miss it but in the meantime let's jump in to trying out these new signals with react oh just one thing this is not something you want to put into prod today the proposal is still very early days the interfacing code I'm about to show you is probably pretty janky this is a video about what's coming next in JS and not what's for today we good okay let's [Music] go all right this is one half of the application that we're going to build it's got a shopping cart on there with apples bananas and cherries in it and we can add apples bananas and cherries and then our total changes we apply a discount and then we get a grand total update it's pretty simple we're going to use Astro to build out this application because Astro allows us to have islands of interactivity this react shopping list is such an island and we get to try out different Frameworks in the same application which is going to come up handy as we add the second part of this application in the meantime let's go build out our Astro app I'm going to use create Astro latest to create signals shopping cart I'm going to start off with an empty template I do plan to use typescript I'm going to use it pretty relaxed we're going to use just a few generics I am going to install the dependencies and I'm going to initialize a new git repo of course all the code that you're going to see today is linked in the description right down below lift off confirmed let's bring that up in VSS code first thing I want to do is add Tailwind that's what we're to use for The Styling so to do that I'm going to use the Astro add command and give it Tailwind that's the inter integration for Tailwind it automatically sets up tailwind and integrates it into our Astro app Astro Integrations are awesome yes we'll add Astro and we'll get a tail innd config file these are the changes it's going to make to our Astro config and that's it next we want to try out reacts we need to integrate react into our application to do that again we use Astro add and react now it's adding react to our list of Integrations setting up some typescript options and that's it now the next thing we're going to do is we're going to model our data so let's go take a look at our application and see what that data is so the data we have is a cart that's going to be the items in the cart we're also going to have a total that'll be computed from all of the items in the cart we'll have discount that's also a mutable piece of State you can change the discount and then we have the grand total which takes the total applies that discount and there's your grand total so let's go model that in signals now to start modeling in signals I need to bring in the signals polyfill just like so and then I'll go and create a new file in Source called Global signals because we're going to Define some signals and they're going to be Global I'll import the signal class from signal polyfill you instantiate signal. state to create a state based signal let's try that with our cart so we'll have an exported constant cart that just instantiates the new signal. state so it's a state signal so it can be get and also set so it's mutable and then we give it the initial value so in this case that would be apple banana and Cherry a certain number of count and certain number Price now we want to compute total from that cart so to do that we instantiate a new signal. computed we tell what we're going to create which is a number and then we use cart. getet to listen to the cart and when the cart changes we run reduce on that array and we accumulate the price times the count that gives us our total next up we want to create some mutable State for the discount what should we use for that so we're going to use signal. State again because we want to be able to mutate that state and we'll give it an initial value of 0.1 which is 10% pretty nifty discount and now we want to compute the grand total based on the total with the discount so what are we going to use for that well we're going to use signal. computed and again we use that g function to get total as well as discount and multiply those together dog inside of the computed is essentially how you subscribe to that signal now this seems vaguely reminisent of recoil or joai atoms you're not far off if you're looking for a way to do a signal style data structure in react today joai recoil might be a good way to go so now that we have our data we want to wait for our code to listen to it now if you look at the spec they talk a lot about an effect function except that there's no effect function in the library what we have to do is create an effect function which allows us to listen to a signal in our framework so let's go and create an effect function to do that I'll create a new file called effect. TS and again I'll bring in our polyfill next I'm going to create a signal Watcher now signal. Watcher in the subtle namespace watches signals why is it in the subtle namespace well it's subtle because how you integrate signals into your framework again probably done by a framework author not folks like us is subtle therefore it is in the subtle namespace but we're going to take a kind of generic approach so we need to create this process pending which is called whenever a signal changes our process pending is going to go through any pending State updates provided by that Watcher and then pull the data from the signal it is a pull based mechanism as opposed to you pushing out a change in signals land the efficient way to go is through pull and then we'll create the effect function our effect function will take a callback function that callback function is going to be our integration with our signal so it's going to say okay we're going to get data from the signal and by getting it we'll essentially subscribe to it so in here we creating a new computed signal that's going to be what the Watcher is going to listen to and inside of that we're going to call our call back which is again going to call more signals again doing more subscriptions and then we'll kick off that watch and get the first value and it will return a function that essentially unwatch or unsubscribes from those signals and that's part two of a four-part connection to react so let's create the custom hooks that are going to take our effect function and bring it into our react State ecosystem so I'm going to create a new directory called react components and in there I'm going to create a new hook called use signal and I'm going to bring in one Hook from react use usync external store usync external store is a very obscure Library hook that is meant to connect react in its state ecosystem with external stores think Redux tand jotai any of those so you got data somewhere else you want to connect into react and use sync external store is the mechanism that react has provided to do that connection so the first hook that we're going to create is use computed since it's the simplest one this is a custom hook that's going to allow us to get the value of a signal so we give it a signal so let's bring in signal that gives us a type so we'll turn that into a generic that we'll then export as the return value of this function that keeps it end to end type save and then we're going to use that usync external store now our first function in there is going to call effect so let's bring that in looks like we're now typescript error free let's talk about how use sync external store Works use sync external store takes three arguments the first is a call back we'll get to that in the second the second and third are snapshot Getters the first is the client side snapshot getter the second is the server side snapshot getter Astro does run in a server side mode so we need to provide that next up is that first callback that is react giving you a call back function that then you call whenever your external store changes so to do that we're going to use that effect function in there we are going to subscribe that signal by doing signal. get we're going to have that get the value which is then going to cash off locally in this closure and then whenever this changes that's when effect gets called we're just going to call that call back and tell react that it is changed and then react is going to call the snapshot function to get the new value now that we know how that works use signal which is the mutable version gets a little simpler use signal takes a mutable signal and returns a tuple that Tuple has the value the current value first and then second a Setter function that sounds familiar to that's because it's exactly the same API Service as used State except that the function doesn't take another function but whatever it's close enough so how we going to do that we're going to use exactly the same use external store that we did with use computed but we're also going to provide a secondary function that just sets that signal when you call it okay so there we go those are the two functions we need to connect our react code with our signals of course we don't have any react code code so let's go and build that so I'm going to create a new component in here called react shopping cart and into there I'll bring our fresh new use computed and use signal hooks that we just created I'll also bring in our signals cart discount total and grand total because we'll need all of those for our interface next up we're going to build the cart list component that's this entire section including react shopping list and the whole list of all the items in the cart and the total and the discount on all of that so let's go and build out that component so going to start off by using use signal and use computed where appropriate so when it's a mutable signal we'll use use signal to go get that data as well as any Setters we're not actually going to use a Setters in this case and then for the computed signals we use use computed after that it just basically comes down to a bunch of jsx formatting of course all of this code is available to you for free in GitHub and the link in the description right down below but this is standard react stuff it's basically going putting header block on the top iterating through all the card items and then putting out the total amount and all of that all right let's slide down here towards the end and then create our react shopping list component and Export it as the default so for the moment we're just going to have the cart list in there now let's go bring that into our Astro import it and then we're going to replace our body with a nice dark mode version and a flex box that gives us a two column layout let's hit save and see how we look all right looking pretty good so far let's go and change the discount and see if it updates we'll make it a 30% discount hit save and there we go we got a discount now of 30% so it looks like we are listening to those signals take that back down to 10% we're not giving away our produce so now we want a way to mutate that store so let's go back and react shopping cart and create a button that we can use to add items to our shopping cart we'll call that add product button it'll take a name and a price for our product and then we'll put up a button nicely formatted that just sets the cart item it we take the existing card items and then we add our item to it and we create a new array to do that as with every other state mechanism and react all of this works off of referential identity so in order to update the card items you need to give a new array reference because it's the reference that matters not the contents of the array that matters and we's it save and then we'll go down here and add some buttons let's it save try it out and there we go very nice okay so let's take a look at where we are so far so we have defined some signals the base state of the application that's section one we created an effect function that's going to get called back whenever any of the signals that we call when we are in that function change we then connect that effect function to react using use signal and use computed which use use sync external store to to give us a call back we then wrap that in in effect and call back whenever those signals change and then finally we connect that to our components using those custom hooks inside of our react components now if you're familiar with other signal Frameworks like preact signals or Legend signals those connect directly to the Dom in addition to providing this signals architecture that's not happening here this is using a very traditional react approach anytime any of those signals changes the whole component that listens to that signal will render so I would consider this a much safer approach although again not in prod now as I mentioned you can do this in other Frameworks as well and of course we're in Astro which means we can very easily bring in other Frameworks so who is our mystery framework guest well it's spelt we're going to go and connect spelt to our application so now they'll both be working off the exact same codebase if I hit more discount here we can see that the discount on the react side goes up less discount and everything works because they're both talking to exactly the same state store so we have on the same page a react application a spelt application and they are both talking through the same standard signals how do we do it well let's go and add our spelt component to do that we are going to start off by adding the spelt integration ation we simply do aser ad spelt and that's it now we've got spelt going so let's make ourselves a very simple spelt component I'll create another directory call it spelt components and we'll call this one Discounter we'll give it the spelt extension if you're not familiar with spelt all the files are named do spelt that are spelt components and we're going to import the mutable discount signal and then format it in our component so all we're going to really do is discount. getet and multiply by 100 and then take off any trailing zeros so now let's go and bring that in our page to do that we'll first import it and then down here we'll add it as the second column take a look and there we go now we've got our discount going over there of course it's not mutable yet so let's go and add some buttons to increase and decrease the discount to do that we're going to bring in two functions more discount and less discount and all we're going to do is use the native signal functions to set the value after getting the value and adding on either plus one or minus one now this do get do set stuff is fairly contentious if you look at the proposal some folks are saying in response to it that they would much rather have a proxy based interface or something along that line I personally don't mind the do set and.get but if you feel like that's an important thing here then you should go and comment on the RFC all right let's add some buttons for more and less discount and now we can add more okay I can see the discount is going up over on the react side less and there you go that looks good but we're not actually updating the discount on this felt side so how do we do that well to do that let's bring in that effect function then let's create a local for Discount value and then we will use that in place of discount. getet let's initialize that actually with discount. getet and then we'll use that effect function to set discount value whenever the discount changes H save and there we go looking good and you thought I was going to end it there surprise no I'm not actually I was going to but now I'm not because J ramanathan who is one of the authors of the spec had a look at this video before you got to see it and said you know what you do need to cover direct Dom manipulation with signals so who am I to question that let's try it out so I go back into our components I'm looking at the react shopping cart list I'm just going to add another div down here we'll put in there discount and then inside that we'll put a span with the discount value currently and we're going to set that to a string just to make sure that if you use this with an object or an array you don't blow up anything let's take a look and see what happens there okay cool that looks great but of course if we add or remove anything from that discount we don't get any changes so what we can do is we can go and bring in use ref from react as well as effect now down here we'll add a ref for our discount we'll set it to that span and then in our effect we'll set the current text to that discount we'll make sure that it exists We'll add a little typing to the user F to make it happy and then we'll do another conversion to string this is mostly about typescript at this point all right let's hit save and go and now as we add more discount and less discount we can see it directly updating that element in place if we go over here to our Dev tools and then go into react components all we really need to do is just hang out there because as we make changes we can see everything updating but as you notice the discount is not actually updating the updating is signal by the bracketing around the component only the react shopping list is actually doing a render at this point the discount is simply updating in place now I really should go and wrap this effect in a use effect let's go do that now I'm just going to cut this effect and put it in there as what we're going to call the reason for that is that effect returns and unsubscribe which is what use effect wants so that's good I'll add in an empty dependency array and looks like we're safe let's try it out fantastic awesome reasonably safe react signal updates without actually doing any renders so thank you for the feedback J and now back to our regularly scheduled conclusions all right as I mentioned at the outside of this video this is what's coming next in JavaScript it's not what we have today so I would definitely would not put this into production but it is fascinating to see we have two different Frameworks collaborating on the same page over the same data I find that the signal API is fine I like that ji/ recoil API style I'm a fan of that but there you go there is a first look at signals both in react and in spelt in their native form if you like content like this react nextjs Advanced topics be sure to go to Pro nextjs dodev that's where I'm building my course on nextjs it is in depth and I'm really excited about getting it out to you in the meantime of course there are free State Management tutorials and forms management tutorials if you sign up for the mailing list I'll see you there of course if you like this video hit the like button if you really like the video hit the Subscribe button and click on that Bell you be notified the next time new blue collar coder comes out
Info
Channel: Jack Herrington
Views: 18,385
Rating: undefined out of 5
Keywords: signals, tc 39 signals, js signals, preact signals react, angular signals, angular, javascript signals, zustand, zotai, redux, rxjs, signals in react, preact signals, jotai, signal hooks, signals hooks, react signals hooks, jack herrington, jack harrington
Id: HSVcZa5yTKE
Channel Id: undefined
Length: 21min 18sec (1278 seconds)
Published: Mon Apr 22 2024
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.