Using Vue With Livewire
A long long time ago, I decided Livewire needed to work well with Vue. This episode describes the journey I made to get there and my current thoughts and questions about the future. Will Livewire continue to support Vue? I'm less and less confident!
Transcript:
Using view with Livewire. So this is the part of the show where Larry comes out and sings a silly song. This is the part of the show my lyric on talk where I you know this for me was like a show-stopping moment. Like, you know, I was demoing some pretty cool stuff with Livewire getting you know, the audience seemed to be pretty engaged that I showed how you can pop into view component and instead of the model you can do while your model and you get the same data binding.
Then you just use a view component that you already have and that there was this moment like I expected Applause, but nobody applauded it was just silent and then I said something like pretty cool huh? And then a bunch of people started clapping and I mean, I think it was just one of those moments where everybody was like what the f like.
Wow. Did this even what like, how does that work? And it is pretty crazy that that that Prospect of like yeah live where all this is really cool. Yeah, but you know, I love you like I need view for you know, my little I don't know tag input elements or whatever you think you need view for and and this was a moment where I was like, whoa, I can use both.
Yeah, so I really wanted. Live where to work with UJS. I don't we haven't really talked about the whole strategy of how I got that to work. It's actually kind of a funny story. So maybe I'll give you the skinny of it, but basically view JS does Dom dipping right like few JS is a front-end framework that.
You know, your component is rendered. It renders the template. All right. So how does view work view takes your template turns it into basically render functions render function that spits out a virtual Dom which is a Json tree of elements and their attributes and their children. And then anytime something's updated.
It re-renders that little Json tree the virtual Dom. It takes a difference of the two dumbs. You know, the one that's like actually implemented and like shown on the screen and the new one that it just rendered out of the component takes a dip and then it patches so it updates on the screen and then your page updates and everybody's happy and all is well.
It's basically have UJS works. That's how most front-end Frameworks kind of work. So live. Where does the same thing kind of accept it gets the Dom from from the server instead of managing virtual Dom trees. It gets it in plain HTML does the Dom dipping and patching? So you have two things that are both trying to different patch the Dom they're trying to control the Dom they they have control over their own little domains.
So it's an issue at first I thought well. Livewire is just not going to work with UJS. It's just not in the cards for it. But this is one of those examples of me thinking like me learning pretty early on that. Okay, anything that I think is impossible or like way too hard to bother with that's not necessarily true.
Like don't trust that instinct give it time. The the solution might present itself. If you feel like it's mandatory. If you feel like it needs to happen just decide that it has to happen and then figure out how to do it. This is one of those things that you know, took me a long time at first. I thought no not possible.
Then I thought this is huge for the success of live where I like for people to use this in their apps. They're going to want to use View and if they can it's going to be huge for like, you know, just adoption in general. So I decided that you know, if they if it all possible this thing needs to happen.
I need to make it happen somehow. So I couldn't really I tried a bunch of things. You know, I like just I tried, you know, letting View kind of handle the Dom and then Live Wire after the fact and whatever and like reinitializing view after Livewire updated everything and all this stuff, but they're man, there's crazy things like when you initialize view inside of a so you have your div your div with an ID of app and then you initialize your view component on that page and it takes control of that div and then adds all that stuff.
So whatever HTML you have. Vue.js is going. Take that HTML and strip out all the white space in the new lines are all the like new line tags so you don't realize it. But when you're when you're right, like when you hit enter inside an HTML file, you're actually adding an element in the Dom. It's a text element.
So if you're actually crawling the Dom with like next element or sit or sibling next to bling or whatever, you'll get these elements, but they're not. They're not normal element nodes or whatever. I forget all the names. It's a the text element and they have a body of a new line character, you know, so so I was having this this and that's all included in the Dom dipping stuff so live, where's doing this Dom dipping, but when you initialize view view wipes out all those new line breaks so live wires getting a mismatch.
It's saying hey from the server. I'm getting these line breaks. I'm looking in the Dom there's no line breaks. And so every time it's doing all this crazy stuff. It's just crazy. So I was really frustrated and I didn't really know how to make it work. So I stride to manually remove the line breaks on the server side like parse out the HTML before I send it to the front end tried a bunch of different things.
Basically what I ended up doing what the answer was and this is funny because I my buddy Mitch and I like we just paired on this in my apartment for probably like 4 hours one evening. We put the laptop up on the screen and we just switched off driving. I sat on the couch and he would just you know hack at it.
See if you can get something working then we switch off and I try to get something working and we honestly we couldn't we got a couple things working but we couldn't get anything work in like really reliably that felt good and then it just kind of hit me like what if I let view manage the Dom. And Live Wire gets the one live or gets the HTML back from the server.
It will take the HTML render it, you know, like put it into the Dom like not in the real Don yet, but just like fake mounted into some invisible Dom if you're probably totally lost on this if you're not super familiar with like JavaScript Dom stuff, but you know, like you can document dot create element and do stuff with that and that's dumb but it's just not mounted on the page, but it exists, you know, So do that sort of thing create some Dom element that's not on the page.
But with all this HTML and then initialize a dummy view instance, like initialize it with view with with just a blank view instance. And just to have you do the formatting now views done the formatting and now I can do the Dom diff because. Because it's going to match whatever view did to the code before it's kind of hard to explain.
But basically that's that's kind of the solution that's in place right now is like live there goes his view on this page. Okay views on this page, then I'll let view do the manipulating so that all the Dom diffs, you know work well and whatever again hard to explain I also detect if if I am doing the Dom dipping and one of the elements is a view component.
I skip it in Live Wire and I let you handle that component completely. So anyway, that's the solution it's been that way for a long time and that works pretty well, but there's a bunch of little weird issues, you know, like one issue is well events, like if you admit events and view, they're not native Dom events or not those like custom events that you can listen to with like document dot add event.
Listener. Their views has its own event bus, you know, so I hack into that a little bit to get wire model to work, but the other event emission stuff just doesn't work. That's kind of a bummer. And then also if you add view components like conditionally with view with Livewire like with blade add if you know Live Wire doesn't know to reinitialize like the view instance and so I don't know.
I'm sure there's a kind of quick fix that would make that work but. But there's you know a little little bugs. I'm trying to make two front-end Frameworks work well with each other which is kind of hard. So basically the other day you probably saw my tweet but I discovered off this is funny because D: die I haven't released this podcast yet that no plans to merge podcast, but on the last no plans to merge podcast.
We basically I'm basically telling him. Okay, dude, here's what I need. I need something that allows me to write a view component, but not have View. Like take over the whole app. I just need View kind of isolated to its own component. Like if I make like a some custom input component. I want to have a tag called some custom input and I don't want like a view name space around it.
I don't want it to be in a view environment. I just want that element to be like a custom web component written in view that just kind of lives on its own. Not long after we recorded a podcast I started digging and I basically discovered exactly what I've been looking for. I don't know why I haven't looked explicitly before.
There's a package called view custom element. I think that basically turns any view component into a web component. And if you're not familiar with web components web components are it's like a it's a I don't want to say up and coming because it's been up and coming for a long time. It's an API that's likes gonna suppose.
I don't know the promise is that native browser functionality will allow you to make custom web custom elements like a normal element, but custom with its own JavaScript functionality and template just like a component like a react component or a view component, but this will be like native in browser functionality and it does exist already but there's lots of hard things hard problems with it uses the shadow Dom if you never heard of The Shadow Dom it's a whole topic, but basically it takes your view component.
It turns it into a custom web element, which is awesome because you get all the benefits of custom web elements, like just native browser support, but you don't have to deal with all the annoying API of writing them and you know native JavaScript. So basically this is huge for Livewire and I kind of thought that and I tweeted it out whenever then I was pairing with somebody a client of mine.
And he's like, yeah, I really want to add this view component into my life where component but you know, I can't get it to work and you know, we could have massaged it got it to work and I was pretty doubtful about it. But and this had to do with that conditional loading thing that I was like, oh man, I should do this view custom element thing.
I pulled it in. And Bam, like it just worked beautifully because Livewire just thinks it's normal Dom because views not trying to like hijack everything. So I don't know if this makes sense to you, but I know I'm like cramming in what I wanted to be the whole episode in the last 10 seconds, but.
But our times over I'm watching the time go that's what I think the future of view is. Okay, I'll go ten extra seconds to tell you that the future of view not the future of you. The future of view with Live Wire is going to be these custom web elements. I think I'm going to remove the like. Promise of using your view inside along with Livewire because it's just kind of I don't know.
It just seems like it's going to spell out disaster. Just tell people if you really want to use your view components use this view custom element package and Adam that way and it'll be clean and like it'll just work perfectly so many less unknowns and you can listen to the. The events because this package converts those View events in a native Dom events.
So this is kind of like a high-level me blabbering on about View and Livewire skipping over a lot of stuff, but I don't know. Hopefully you found it enjoyable. Thanks for the extra 44 seconds. Enjoy your hike.