 Good morning, good afternoon everyone. So my name is Felix, I'm an open source engineer with Microsoft which really just means that I build open source for a living, I don't really have a product or anything, I'm just hanging out in the office building open source. And one of the things that I thought was really sweet at least working with it over the last year was Electron and I've been a long Ember fan and those two things work really well together. So what I want to talk about today is pretty much how you can turn your Ember app into a desktop application, what kind of things you have to consider, how you can make your Ember app a true desktop application that also does some desktop-y stuff, you know, it's not just a web app and it's on tab. And then also I'm going to show to you Ember Electron which is pretty much where I put all the learnings and all the automation that you could automate away from taking an Ember app into an actual Electron app. So with that being said, a very quick introduction into Electron. If you've never heard of it, that's totally fine, it's a pure developer tool, but you might be running some of the apps that use Electron. I think most prominent are Adam, Visual Studio Code, Slack. There's a bunch of them brave, you know, that new browser that is around. All of them are using Electron. And Electron is essentially a combination of Chromium, the open source version of Chrome, combined with Node and a bunch of APIs that allow you to call native stuff. So there's things like notifications, something I worked on for Solid Week, which if you write that in C++, it's pretty difficult code. But what you can do now is you can just say new notification and then all of a sudden a notification pops up. So there's a bunch of benefits to using it. The biggest one is of course that it's cross-platform. That is the most straightforward one. That is what people usually like. You build your application once and because it's using mostly web technologies, it automatically runs on Windows, Mechastan and Linux if you wanted to. But the other one is, and I think that's an actually really big benefit is that the developer tools are amazing. Because so many applications are using the same stuff, you get to use some of the tools that those people have developed to make things easier. So if you want to use the same one-click installer that Slack uses on Windows, you can do that. If you want to use the same auto-updater that works in Adam and Visual Studio Code on Mac and Windows, where your app starts and all of a sudden it's been updated, you can do that. All those things are part of the developer ecosystem around Electron and it's pretty big. I don't think I'm telling any JavaScript developer anything new when I say that, but using pre-made stuff is a good idea. Defaults are smart. It's a good idea not to reinvent the wheel. So before we go any further, I promise this is going to be the only technical slide, but I want to be very, very brief about how Electron works underneath because I assume that many of you, or some of you, may have used something like Node Webkit or maybe CEF, the Chrome embedded framework. And Electron works slightly different in one way. And that is that Electron when it starts, it's really just a process. There's no window, there's no UI to be seen. It's just a process that is Node-only. And that process is able to spin up renderer processes, which are essentially just Chromium windows. And those two processes talk to each other via something that's called the IPC and the reason I point this out because it's gonna become important later on, but the idea is that you start, not a website or a web app, you start a script first and that script then gets to open up. Browser windows do things, update the app, so on and so forth. So when I was working with Electron previously, I was working with Node Webkit and there was a really, really sweet add-on called Ember CLI Node Webkit, built by Estelle, who might be somewhere in the room. It's an amazing tool if you ever want to use Node Webkit. It just makes things a lot easier. There's a lot of defaults you have to do and if you just want to run your Ember web app and to have all the hot reloading and all that stuff, it makes stuff tremendously easy. So really enjoying that and also really enjoying with Estelle on that. She was amazing when we built our app and Microsoft. I thought it would be sort of nice if we had the same thing for Electron. So I took the whole thing and put it over to Electron, with Node Webkit being very similar, was already 50% done. And there's a bunch of stuff in there that makes your development now fairly easy. This talk was initially about all the things you have to consider and all the things you have to do, but we could just automate those the way into that add-on, which makes things a lot easier. There's basically four big components to it. The first one is that it allows you to automatically set up all the defaults. So you can turn the normal vanilla Ember app and immediately make it Electron runnable. The second one is that we can package in the Ember CLI, the Ember Inspector, something called Ember CLI Remote Inspector. You might be wondering why that is necessary. Browser add-ons do not run an Electron, they don't run a Node Webkit. If you still want to use Ember Inspector, you have to be a little bit fancy about it. The add-on does that. The third one is packaging. So you basically have an Ember app in the beginning, and then at the end you run the binary. There has to be a sort of step in between. We run that step for you, including recompiling your native dependencies. Which is more work than it sounds like, because you can't just compile them against Node, you have to compile them against Electron. And so I have been working with C++ with Electron to give you guys Electron tools. And quick show of hands. How many people have you touched C++ on, I want to say, like a monthly basis? There's just a few hands. So let me tell you, if I want to add a new feature to Electron, I first have to deal with the fact that Electron has about 40 different string types, ten of those are documented and the other 30 are sort of like surprise, new Chrome string type, and it was all built 20 years ago at Google, and all the people involved are dead or something, and just dropped off the internet. And then you're sitting there, so if you don't have to deal with that, that is sort of amazing, right? And C++ is really the only other native technology that we have to truly build native apps, so all of that stuff being handled for you is sort of nice. So that being said, let's quickly go into the first command, right? You basically install an Ember add-on. And what happens then is that automatically a Blueprint generation is run. And instead of showing you more slides, I'm just going to show you what that looks like. So if we quickly close the presentation here and go over here, what I have here is just a default boring Ember app, right? You just run Ember new and then I've wrote Conf App. And this is the usual stuff I can do. Instead that I also ran Ember install Ember Electron, and that is a few things. The most notable ones are that it now added an electron.js file, and that is really what is going to be executed by Electron as soon as you run the application. And then here you can do a few things, like you can see right here, one of the most important events is that all windows are closed. As soon as the windows are closed, we actually leave the app. But we also go ahead and open up a new browser window and basically load the location of our Ember app. So I guess this is the first very important thing to realize is that your application is now running without a server. There's no server to be run. And just so you guys and people know, running a server in a local app is sort of a big anti-pattern, you should never do that. So Electron is not running a server for you, it's just like straight up loading the file. Yeah, and then if the window is closed, we just reset the main window. So that allows us immediately to, we could normally just say Ember serve. But in this case, we can just say Ember Electron. And what that does is it builds the application. So let's give that a second to just do it real quick. It builds the application and then it injects a few things you might need. So that is our application right here. Let me just show you what it briefly did here. But it also injects the Ember inspector with sockets. So what it can do now is it can head over to Chrome, sorry, that should not launch, just quit that right away. So I can reload this and let's just move this over here, this application over here. And I can still inspect my Electron application, just like it would inspect a normal Ember app, right? That just works out of the box, you can do things. If your application is really, really big, sometimes it gets a little bit, you know, a little bit icky, because it is just running over web sockets. But Tom and you were talking about how popular Ember inspector is. And I think that just speaks to how amazing the Ember inspector is, because you can just use it, which is sort of fantastic. But the other thing is that it sets up the require and the node context in such a way that you can actually use it. So if I just open up the console right here, I can just go ahead and say process, right, and I can just say process.versions. When I get all of a sudden, it's my node object. And I can do some pretty simple things. I can just go ahead and say var fs require fs. And what I get then is, you know, straight up fs. I can call that from within my application. You can call those things from within your Ember application. And I think the implications here are fairly obvious, but it just allows your application to be much more powerful than it may have been before as a pure web app. It's a big difference between a web app and the native app is not necessarily that the native app is written in a different language, it's just that the native app has more powers. You can just do more things, right? You can like, control your volume, control your file system, open files, delete files, do all those things. And I think if you look at Adam today, Adam's a pretty powerful tool. And there isn't really that much that is missing. And the developers that work on Adam with Electron have pretty much all the tools that they need. And this is just, and Electron in this case is just fairly easily making sure that you can call or require inside your application. It's using the Ember resolver and you can use it here and call Ember apps. So that is sort of the easier part. Let me quickly jump back to the presentation. The next one is Ember Electron Test, which again, the whole pointer is just to make things easy. The Convex doesn't really have tests, but what it did bring is Ghost Desktop, which is an Ember application that I'm currently working on. Anyone has ever heard of the blogging platform Ghost? I'm on that team. We're currently building a desktop app using the stuff I just showed you. And it's sort of my proof point to make sure that Ember Electron works well. So normally, if you just run Ember Test, that doesn't really work because you might be calling native node modules, right? And if you call those from a browser, everything breaks and everything's horrible and nothing really works and you gotta work around that. So what we have now is Ember Electron Test, which basically spins up Electron and runs your Q unit tests inside Electron. And again, it takes care of everything for you. It's pretty much automated away and everything that is difficult. Now it just runs here, right? All your tests just run, or don't run in this case. We're trying very hard, okay? The app is not released yet, but there we go, right? So you can just run those things, you get a coverage report at the end, and everything that you normally do still works, right? So that just works, and it's sort of nice. Then obviously we also have the server mode, same thing. And there isn't really anything to consider at this point, which is very convenient because normally you would have to consider a bunch of things. Isn't really any way to do this in an easy way. But now you have a server mode and I'm not going to show you hot live reloading because I think you know what it looks like. But if I change a file and update all the tests run again, and this is just automated away for you. And thanks to some very nice PRs that even works on Linux, which has a slightly different file watching mode than Windows and NAS 10. So up to that point it was all like pretty easy stuff, right? And I want to say almost very boring. What becomes more interesting is the whole step if you go from just this folder, this embassy live folder, over into an actual package binary, right? And there's a bunch of stuff you gotta do. Let me just run the build, and I'm gonna walk you guys through how that actually works. So we have this package command, and we're gonna specify the platform because I don't actually have anything installed here that allows me to build other platforms. But what it does is that it builds your Ember application in production mode. It then takes all your main code. Because remember, we have two different threads, right? In this case, we have a renderer process which runs my Ember application. But we still have the main thread which runs all the stuff that Electron usually talks about, like opening new browser windows, opening a new dialogue, setting up native images. So what we do is that we also copy over that code, and I hope this is big enough. No, I can make it bigger. And once we have done that, we sort of create a new package for JSON, install the right dependencies, because you probably don't wanna ship all your dev dependencies with your actual application. There's no reason for your application model to contain Babel. You know, no user's gonna need it. So we just install the actual dependencies. Then we go over, download the Electron headers. Because it turns out Electron is actually a different binary than node. So if you wanna run anything native, like SQL Lite or anything like that, you will have to recompile your dependencies. So we do that, right? It's just like, extracted away from you. And then we package the application. And if you go over here, there's now a folder called Electron builds. And we now have a Convap. And then you just run it, and all of a sudden you have a Convap, right? And that just works. There's absolutely nothing you had to do manually, just works. So there we are. That being said, this is about the time where we can talk about some things that become a little bit more interesting, right? So, and what I brought for you is the Ghost Desktop app. So let me first show you the Ghost Desktop app. Let's go in here. What's this? Just say Ember Electron, which is gonna build my application and spin up the Ghost app. So Ghost Desktop is gonna be essentially a way to run your blocks from a desktop way. And there's a few things we do that sort of turn it beyond just being a normal Ember app. So what you see here is essentially two Ember apps. We have an outside Ember app and an inside Ember app. So this, welcome to Ghosting here. This is all, let me just go here, this is an empty block. This is basically the inside block. This is an Ember application by itself. But then we wrap a whole Ember application around it. And this is important because of the security model. We basically don't wanna give full node access to the Ghost instance, mostly because of, you know, security. I'm gonna talk a little bit about security at the end of the talk. But we also wanna do a bunch of native things. And this is a good point to maybe talk about some of the shortcomings Electron still has. Some of the things you will have to consider when you build an Ember app. Let me start by talking about the context menu. We just do anything right here. As you can see, you cannot see that I'm doing a right click. But what happens is that Electron comes without a context menu. That is something you will have to set up yourself. I can show you the code. It is, in theory, fairly easy to do. But it is interesting that you have to do it in the first place, right? So just consider that there's a few things that you expect as a developer to just be there, which aren't really there if you can suddenly control the whole application. Context menu, copy, paste, those things that are not automatically out of the box, some are available. You have to get that context menu for yourself. And another thing I'm fighting with right now, which is pretty big, is something like SpellCheck. All three platforms offer up a native SpellCheck API that Chrome is usually hooking into. Chromium is not hooking into that. Meaning we have a blogging app, writing is sort of the core thing that we do. It's fairly important, we currently don't have a SpellCheck. Which is also why the application is not released yet. There's a whole developer system around it, how you get around that. But what's basically going to happen is that we're going to, you know, wait for key events, analyze the words, make sure that those match the dictionary and then pass it all back. Because we don't want to ship a whole dictionary, what we're going to do instead is that we're going to use the native components. But native components means all of a sudden we have C++ and so forth. Right, you can sort of see where this is going. There's a lot of work you have to do extra. But the big benefit here is that even though you sometimes do have to call native, you always can. There might be reasons for you to wonder why the heck you would want to call something natively. But let me just give you a very quick example. Just for fun, I worked on something called Waffle. Which is a little calendar application. And what you're seeing right now is just Ember. And the calendar application, calendars are interesting. Time is interesting. So specifically I tried out a bunch of ways to, you know, cache my events and keep my events around. But it turns out that all the ways I could find in JavaScript to do what in SQL would be a date between query. So what you want to get is you want to get all the events that start or end between two times. All of those are very, very slow if you run them a thousand times. And for the application to be snappy, like right here, I sort of want to, right, I just want to like go next and do that. And that is very, very slow. But however, it's very fast to SQLite and see. So I can just go ahead and say straight up, bar SQLite equals required SQLite. And that works inside my AMP application. There's nothing else I have to do. And the beauty here is that Ember is sort of, the way Ember is designed, and I'll talk to Tom about that briefly outside. He was like, I'm not surprised because, you know, it comes out of Coca-Cola. But the way Ember is set up, it makes those interactions very natural and very easy. So, let me show you something else. In the example of Ghost, I can't find my Ghost anymore because I have so many election maps open. But in the example of Ghost, you never actually have to log in. Instead, we're using the native operating system's key vault. If you never develop native apps, that's probably something you never heard about and you don't actually have to. But basically, if you manage secrets inside an application, developers very quickly start using very insecure methods to keep passwords around. So all three platforms, Linux, Windows, and our stand have at some point offered developers a very easy API to just, okay, give me a string, I'm going to keep it secure, right? Just give me. Of course, you have to call that natively. There's a little module out there called Kitar that does that for you. So if we go and check out our block model right now, it's pretty simple stuff, right? Get password, just looks like this. I require Kitar, and I just spell it require node because that makes it clearer, but you could also just say you require Kitar. And then I just run this native module. And what happens is if you compile Ghost desktop, we'll just do that here, is that Ember Electron will handle the whole, I have a native dependency with C++, I got to recompile that. Ember Electron will completely handle that for you, will go and ensure that it gets the right headers for the right version of Electron you're using. We'll recompile them with the build tools you have. But this is also an interesting, this is an interesting junction for, I see a lot of Macs here, as there is to be expected at EmberCon. This is an interesting junction because it suddenly requires you to more or less install all the systems. Because as soon as you have native dependencies, you will actually need native build tools, right? You will, you cannot build a Windows application without having the native Windows application build tools the same way around. You can actually do it from Macs 10 by installing Wine and then it suddenly works. In theory, you can build Linux from both platforms. We had a bit of trouble with that, but in theory that is possible. But the biggest gotcha is also something web developers never think about, like me, who released a developer preview of Ghost Desktop. And I just built that on my machine, which is 64-bit, right? It's a normal MacBook. Turns out if you have 32-bit, it didn't even start. All right, yeah, sort of forgot, sorry, yeah, those things happen, right? So basically the, and then I updated it to specifically say this, right? Just so you know, this is the platform you're compiling for. It's suddenly more than just, more than just an operating system. But all that being said, let me go into my last slide, because I think it's an important one. Because every now and then, every now and then at least us and the, us and the Electron team get like questions that make me very, very concerned, and we already had the first cases. So I work for Microsoft, right? We recently experienced that people on the internet are mean. So apparently, nobody told us, sorry. So I want to make one thing abundantly clear, because I think the Electron team and me included totally fail to make this obvious. If you build, and this is not specified to Electron. This is true for all the solutions currently that give you node access. If you thought cross-site scripting text was scary, you have not considered that as soon as you run them here, they can like literally wipe your hard drive, right? This is very important, and I've seen that so many times, and there was actually a big case involving Electron with an antivirus company called Avast, which had the great idea of, I know how we make our normal website with an application. We hosted a little server that just accepts like a bunch of strings, and then we execute those strings. Yeah, so Google, but the thing here is that Google actually, you can read the whole thread on the Chromium mailing list. So Google actually contacted us and was like, hey, just so you know, everyone running a vest can actually totally, can be root kitted from the outside. The trouble here is that many developers don't really, I think don't really understand what's actually happening. So give me a very simple example. We can open up new windows using a file string. That is something that has always been possible in Chromium. So you can basically say, the same way you can install an NPM module from a string, we can create a new window from a string. You can basically say, this is my HTML object. Here, this is a string, and in there, I can say pretty much anything, including exec, spawn, download new scripts, execute those new scripts. So basically what I'm saying is, if you are thinking about building a desktop app, that's amazing. You should absolutely do that. There are actually real benefits to having a desktop app, because you're gonna integrate into the desktop a little bit easier. You can have notifications. You can have doc menus, you can have native menus. You can have a protocol, if you wanna have. So what we're gonna build is ghost call on slash slash, and then you can basically do the whole post this automatically thing. There's a lot of integrations you can do, but please be aware that all of a sudden, your attack vector has grown by about a bazillion percent and be super paranoid about what you do. And if you're not using HTTPS yet, but you still wanna load remote resources, this would be a great time to start. SSL is really sweet. So in summary, please go and check this out. It's on this link, and I think I'm almost out of time, but it's on this link. Please go and check out Ember Electron. In theory, unless you're doing anything super crazy fancy, but I've tested this with a bunch of teams inside Microsoft Running Ember, and I also tested this with a bunch of people outside Microsoft Running Ember. In theory, you just have to run Ember, install Ember Electron, and then Ember Electron, all of a sudden, your application is gonna run as an application, and you can take it from there and see if that maybe would be a good idea for users. So that would be the talk. Thank you very much.