In this episode, Surma shares what he learned while getting started with the Bevy Game engine, Entity Component Systems and why they might be useful for the Web. Jake rounds up the newest JavaScript language features that landed in TC39’s Stage 3.
Jake:This house has got real bad static electricity.
Jake:I don't know if it's because of the weather.
Jake:It seems like once the cold weather came in,
Jake:like, the whole house is live,
Jake:and I just got a-
Jake:I just got a static shock right up my fingernail.
Jake:It really hurt.
Surma:Ooh, that's that's oddly specific or is is your your ground not actually grounded in all your
Jake:Yeah!
Surma:Electric devices are just yoloing
Jake:Oh, it could be that.
Jake:It was on the-
Jake:the metal of the Mac keyboard.
Jake:Just so you can picture it.
Surma:No that so that's worth looking into I had that before where in
Jake:It was actually live.
Surma:Well, not not not live but in in a house where the ground wasn't actually working
Surma:When the laptop was charging and I slid my hand over the aluminum body of the MacBook
Jake:Oh.
Jake:Vibrating.
Jake:Yes.
Surma:It had this this tingly
Jake:Now, here's a-
Surma:Yeah
Jake:here's a thing that
Jake:I wouldn't believe-
Jake:I wouldn't believe me if I said this,
Jake:but thankfully, there was someone else there.
Jake:I, uh,
Jake:went to a party in London,
Jake:me and my other half.
Surma:Yeah, I don't believe you
Jake:Um, yeah, this is-
Jake:this is back when I had friends.
Jake:And I-
Surma:You
Jake:and then we stayed over at the friend's,
Surma:You
Jake:and we woke up both incredibly hungover,
Jake:and we went to
Jake:Farringdon Station
Jake:to catch a train home.
Jake:And we were just kind of, like,
Jake:hungover.
Jake:And I
Jake:touched my other half's face,
Jake:and it did-
Jake:it did that thing.
Jake:Like the-
Jake:you know, you described that you run your hand along the MacBook,
Jake:and it did that vibratey thing.
Jake:Her face was doing it.
Surma:Yeah
Jake:Her face was doing it.
Surma:Are you sure it wasn't a robot?
Jake:And...
Jake:It- well, but she did it to me,
Jake:and she could feel the same thing on my face.
Jake:Now, Farringdon Station is
Jake:overhead, electrically powered,
Jake:so I think something had just
Jake:been going very wrong in the station
Surma:That's very reassuring
Jake:with the power.
Jake:The whole air was charged. Yeah.
Jake:Because it's- I've been at that station a ton,
Jake:uh, before and since, and it's never happened.
Jake:But that morning, and, you know,
Jake:in the sort of hangover state, we were both
Jake:sort of just there, like, sort of
Surma:You
Jake:gently touching each other's faces, going,
Jake:what is- what is wrong
Jake:with the world? The world is broken.
Jake:This isn't normal.
Surma:Dude I can totally feel the electricity on your face
Jake:Yeah.
Jake:It was such a lovely moment
Jake:to share with my partner, so...
Jake:Well, yeah, it's another
Jake:episode of Off the Main Thread.
Jake:It's- yeah, we're-
Jake:we're still doing it
Jake:to both of our amazement.
Jake:We should say, this is sponsored by
Jake:Shopify, in that they let us record it
Surma:You
Jake:and they don't ask us to say that,
Jake:but I'm saying it anyway, because it's quite nice of them.
Surma:Thank you Shopify
Jake:Cheers!
Jake:Let's throw forward, because that seems like a
Jake:professional thing to do. What are you-
Jake:what are you going to be talking about today?
Surma:Ah in in this episode I will talk about
Jake:...
Surma:Architecture and entity component systems and a bit of rust with bevy because it all ties together and whether
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Surma:We can just throw the DOM away
Jake:Oh, wow.
Jake:Okay. And I'm
Jake:going to be talking about some of the
Jake:TC39 stage-free
Jake:proposals, which is always my
Jake:go-to topic when I can't think of
Jake:anything else. But I think there's some really interesting
Jake:stuff in there, so we'll get
Surma:Yeah, there's enough movement so I'm excited for that because I have not kept up
Jake:to that in a bit.
Jake:Well, I hadn't either. I was quite
Surma:You
Jake:surprised by some of the things that I
Jake:read yesterday as I was preparing for the
Jake:show.
Jake:But,
Jake:you mentioned on the last show
Jake:that
Jake:a conversation between two people
Jake:on a plane, which was totally normal, but it wound you up.
Jake:Like, it sounded weird to you. Because it was weird.
Surma:Yeah, you're on a plane
Jake:Now, I had the same thing.
Jake:Uh, no.
Jake:So, I was in
Jake:Arundel.
Jake:And I like Arundel for two reasons.
Jake:There's a lovely castle there, which
Surma:You
Jake:I was visiting with a bunch
Jake:of friends. But also,
Jake:it has to be the one place
Jake:in the UK that sounds
Jake:most like Middle-earth.
Jake:Right, just its name.
Surma:I was gonna say I'm most like can you tell me where this is or are we talking about like dungeons and dragons?
Jake:...
Jake:...
Jake:...
Surma:You
Jake:It sounds like it, because you're on the train, and the
Jake:announcement's like, you know, this train stops at
Surma:You
Jake:Salem Junction, East Croydon,
Jake:Gatwick Airport,
Jake:Amberley, and Arundel.
Surma:You
Jake:It does feel like that is
Jake:in another dimension.
Jake:I must journey to Arundel to retrieve
Surma:You
Jake:the amulet from the castle
Jake:gift shop, which is where
Jake:I was going. Anyway,
Jake:in the castle, there was these
Jake:tight, spiral
Jake:staircase things, because it's a castle,
Surma:You
Jake:right. And
Surma:You
Jake:there was a group in front of us,
Jake:you know, a separate group.
Jake:And one guy
Surma:You
Jake:in the group turned to his mate,
Jake:and he said,
Jake:I wouldn't like to fall down these stairs.
Jake:...
Surma:You
Jake:...
Jake:I was like, what?
Jake:Let me get this straight. You
Surma:You
Jake:wouldn't like to fall down
Jake:these stairs?
Jake:Like, when it comes to these stairs,
Jake:falling down them is just
Jake:not on your want list,
Surma:You
Jake:you know.
Jake:And it reminded me of the situation you had,
Jake:because I was saying this to my friends, and they were like,
Jake:Jake, this is a totally
Jake:normal thing for two humans to say to each other,
Jake:just let it go, this isn't a thing,
Jake:this isn't a bit. But
Jake:I was having...
Surma:But logically extrapolating from the sentence has been said it implies that they would enjoy falling down any other set of stairs
Jake:...
Jake:...
Jake:...
Jake:Exactly! And I was not prepared to let this
Jake:go. So just for the rest of the trip,
Jake:for instance, we all
Jake:walked into this big, grand room in the castle,
Surma:You
Jake:and I was like, hey,
Jake:hey everyone, look, look,
Jake:hey, look, look,
Jake:look, hey, look. And then I
Jake:pointed to a giant sword that was
Surma:You
Jake:hanging on the wall, and I was like,
Jake:wouldn't like to get stabbed by that sword.
Jake:...
Surma:I
Jake:Can you imagine?
Jake:Ah! No!
Jake:I don't like this! Ow!
Jake:Like, no...
Surma:Wanted the other sword
Jake:I mean, even if you offered it for
Jake:free, I'd say no to
Jake:being stabbed by that sword. And I
Surma:You
Jake:carried that on for the rest of the day,
Jake:and everyone got extremely
Surma:I was gonna ask are you now have you gotten rid of some friends this way in a very
Jake:annoyed with me.
Jake:...
Jake:Exactly, yeah, that's...
Jake:Yeah, that's why I have to have internet friends
Jake:instead, because, you know, the real-life ones
Jake:desert me. For good reason, I'd say.
Jake:...
Surma:Full for very good reason, but I suspect that we should rather talk about the web
Jake:...
Jake:...
Surma:You
Jake:Let's do it! Well, I went
Jake:first last episode, so
Jake:logic dictates. It's your turn,
Surma:That's my turn, isn't it
Jake:I think.
Surma:Well, we can take this as you may have noticed when I said, what am I going to talk about today?
Jake:...
Jake:...
Jake:...
Surma:I'm not quite sure which direction we want to take this and I'm open to
Jake:...
Jake:...
Surma:to all of the directions, but as
Jake:Okay.
Jake:...
Surma:For a long time. I'm on the internal hunt to figure out how we can
Jake:...
Jake:...
Surma:make better use of
Jake:...
Jake:...
Surma:Multi-threading on the web and I
Jake:Yes!
Surma:Looked
Surma:Started playing around with bevy, which is the game engine for rust not for this purpose
Surma:But it ended up actually playing into this eternal hand
Surma:And because in general I feel like
Surma:game developers or and game
Surma:development, it's a lot of
Surma:Interesting things happening there and things that I wonder if web development could steal or learn a thing
Jake:...
Surma:or two because
Jake:Well, they are pushing, like, you know,
Jake:on some platforms,
Jake:144 frames a second,
Jake:and that's just the rendering
Jake:in the background, there's physics
Jake:and game engine, and
Jake:it has to be delivering at that rate,
Jake:right? So, it sometimes feels
Jake:silly when you see that kind of graphics,
Jake:even on a, you know, a kind of
Jake:moderate hardware thing, like a PlayStation
Surma:You
Jake:5, a PlayStation 4, pushing out
Jake:frames at that rate, and we struggle
Jake:to move boxes around
Jake:the screen. I mean, I know it's different,
Jake:but, yeah, I think there is so much
Jake:we can learn from them.
Surma:And as a topic I want to talk about on another episode which is that I looked at the original Gameboy and how
Jake:...
Jake:...
Jake:...
Surma:it worked and
Jake:...
Surma:how
Jake:...
Surma:Limited it is and yet the games
Jake:...
Jake:...
Surma:They made on that thing, it's just it's just blowing my mind, but in general, I think that's exactly
Jake:...
Jake:Hmm.
Jake:...
Surma:one of the fests of game development that make it interesting in that
Jake:...
Jake:...
Surma:They are
Jake:...
Surma:Squeezing every last bit of performance. Usually are the devices that they run on while at the same time
Jake:...
Jake:...
Jake:...
Jake:...
Surma:Rarely can they use a lot of off-the-shelf stuff in at the macro level because
Jake:...
Jake:...
Jake:...
Surma:Any every game has almost its own, you know
Jake:...
Jake:...
Jake:...
Surma:UX or UI paradigm like sometimes it's buttons. Sometimes it's controller
Jake:...
Jake:...
Surma:Sometimes it's keyboard and mouse and often it's all of these at once
Jake:...
Jake:...
Surma:You want the same code base to run on a desktop on the switch on your Xbox or your phone?
Jake:...
Jake:...
Surma:you want to iterate really really fast because game the game industry is really intense and you have to
Jake:...
Jake:...
Jake:...
Jake:...
Surma:Be able to pivot and change things and often you have multiple people
Jake:...
Jake:...
Jake:...
Surma:Working on different aspects of the game and want to work independently without breaking each other and all these
Jake:...
Jake:...
Jake:...
Surma:goals combined pull off constraint on or
Jake:...
Jake:...
Surma:Requirements onto the code and how you write it and how the engine is supposed to be laid out
Jake:...
Jake:...
Jake:...
Surma:So I think in general I always am fascinated when I look at how games are architected
Jake:...
Jake:...
Surma:And so bevy is a game engine and rust
Jake:...
Jake:...
Jake:...
Surma:Which is interesting for multiple reasons for me on the one hand
Jake:...
Jake:...
Surma:It is rust and I like rust and it compiles natively so you can you know
Jake:...
Jake:...
Surma:As in like you just get a binary out and it runs on
Jake:...
Jake:...
Surma:my class Windows on Linux and
Jake:...
Surma:but it also compiles to WebAssembly using
Jake:...
Jake:Duchess of Edinburgh
Surma:WebGL WebGL to or WebGPU so it uses that WGPU crate that I mentioned on I think two episodes ago
Jake:I like catastrophes
Jake:...
Jake:...
Surma:which basically
Jake:...
Surma:implements the WebGPU API in rust and then in the background dispatches to whatever the operating system has or
Jake:...
Jake:...
Jake:...
Jake:...
Surma:Straight through if you're in WebAssembly land to actual WebGPU or now also WebGL
Jake:...
Jake:...
Jake:...
Surma:so it's interesting that you know, you there is the the super low-level primitive that this engine is using is
Jake:...
Jake:...
Jake:...
Surma:an API that I happen to understand but even if you don't it is an API that is platform independent and
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Surma:you could even make use of outside of baby, so it's
Jake:...
Jake:...
Surma:Knowledge that you learn that is not tied to the specific game engine, which I always think is a big plus
Jake:...
Jake:...
Jake:...
Surma:And in terms of features it also it comes with a couple things of a box like it can do UI
Jake:...
Jake:...
Jake:...
Surma:elements like 2d UI elements and layouts and
Jake:...
Jake:...
Surma:those are
Jake:...
Surma:using flexbox in grid as in
Jake:...
Surma:CSS they use the same property names and
Jake:...
Jake:...
Jake:...
Surma:Yes
Jake:...
Jake:...
Jake:...
Jake:...
Surma:You
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Surma:Oh, really, I did not know that
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Surma:You
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Jake:...
Surma:Well, I I find it really interesting because
Jake:...
Jake:...
Surma:it's it's this thing where I
Jake:...
Jake:...
Surma:don't think
Surma:CSS is perfect or that
Jake:...
Jake:...
Surma:WebGPU is perfect, but I do like
Jake:...
Jake:...
Surma:That rather than inventing something
Jake:...
Surma:That you know
Jake:...
Surma:Does a lot of things well?
Jake:...
Surma:specifically the use case that you as the inventor think about or care about and
Jake:...
Jake:...
Surma:You lean on something that has stood the test of time a little bit something that has already been
Jake:...
Jake:...
Jake:...
Jake:...
Surma:Lots of you know brain hours have been invested into it and while it may be a bit quirky or not always convenient
Jake:...
Jake:...
Jake:...
Surma:It has proven that it is flexible enough to do all the things or most of the things and so in that sense
Jake:...
Jake:...
Jake:...
Surma:I think it's a really interesting move something that they for example don't have is the cascade and I actually
Jake:...
Jake:...
Jake:...
Surma:Currently I'm missing a bit because the cascade is you know a bit
Jake:...
Jake:...
Surma:It's very deeply ingrained in the way I think about these kind of layouts
Jake:...
Jake:...
Surma:and so it's a bit weird to not be able to overwrite the text color by adding a class or by
Jake:...
Jake:...
Jake:...
Surma:Changing the text color of a parent element and but you can you can work around it
Jake:....
Jake:...
Jake:...
Surma:But the fact that I can immediately go okay. I want a menu and I can just do
Jake:...
Jake:...
Surma:Flex direction column and add a couple of children and the thing then works
Jake:...
Jake:...
Surma:It's cool, and I mean obviously it's cool for me as a web developer
Jake:...
Jake:...
Surma:But I could I like that even if you don't know this learning it is not engine specific knowledge, but it's actually
Jake:...
Jake:...
Jake:...
Jake:...
Surma:You're learning parts of another open platform, so you get more bang for the buck for investing the time
Jake:...
Jake:...
Jake:...
Surma:So and that I thought was really nice, but it's not even the core part
Jake:...
Surma:I want to talk about but I thought it just makes it really interesting to me
Jake:...
Surma:And I'm not sure I should say obviously I am NOT a game developer. I am NOT even an amateur game developer
Jake:...
Jake:...
Jake:...
Surma:I'm interested in it, but whatever I talk about should not be seen as representative of
Jake:...
Jake:...
Jake:...
Surma:the game industry or anything like that, but I
Jake:...
Jake:...
Surma:Just thought that was really interesting well and the core part of
Jake:...
Jake:...
Surma:bevy is an
Jake:...
Surma:ECS an entity component system
Jake:...
Jake:...
Surma:Which is an architecture that I think has seen more popularity recently in game engines
Jake:...
Jake:...
Jake:...
Surma:I know unity now has one. I'm pretty sure unreal also has one
Jake:...
Jake:...
Surma:and
Jake:...
Surma:that is
Jake:...
Surma:The thing I want to talk about a bit more because as an architecture. I find it quite interesting
Jake:...
Jake:...
Jake:...
Surma:So I guess I should maybe try to do like a like it like a brief
Jake:...
Jake:...
Surma:Summary explanation of what it is
Jake:...
Jake:...
Jake:...
Surma:All right, so ECS entity component system it consists of entities
Jake:...
Jake:...
Jake:...
Surma:Components and systems which makes it a really good name
Jake:...
Jake:...
Surma:So I'm the terminology. I'm just going to explain how bevy does it
Jake:...
Jake:...
Surma:I think it's fairly representative of how it works everywhere else, but I don't know much about it everywhere else
Jake:...
Jake:...
Jake:...
Surma:So you have a world which is basically a container for all your entities all your components and all your systems
Jake:...
Jake:...
Jake:...
Jake:...
Surma:entities are
Jake:...
Surma:kind of just that they're just
Jake:...
Surma:Identifiers they have no data. They have no
Jake:...
Jake:...
Surma:Behavior, they're basically just a number so that you can distinguish between entities
Jake:...
Jake:...
Jake:...
Jake:...
Surma:And you can attach
Jake:...
Surma:Components to entities and components are just bundles of data
Jake:...
Jake:...
Surma:No code
Jake:...
Surma:It's just you have different entities and you can attach little
Jake:...
Surma:Buckets of data to them and then systems are functions that operate on that world
Jake:...
Jake:...
Jake:...
Surma:That sounds really abstract. So I think it gets a bit more interesting when we talk about an example. So for example, let's say I
Jake:...
Jake:...
Jake:...
Jake:...
Surma:Spawn I create two entities in my world. I
Jake:...
Jake:...
Surma:give them a
Jake:...
Surma:Position component, which is you know a position X&Y. I give them a
Jake:...
Jake:...
Surma:sprite
Jake:...
Surma:component which contains let's say a path to an image file and
Jake:...
Jake:...
Surma:Then you have a function a system called render
Surma:That runs queries against this world
Surma:so every every system just basically
Surma:Asked questions like give me all the entities that have a position and a sprite
Surma:Component and you get back an array or an iterator that gives you the entities and only the entities
Surma:With those components on them
Surma:so this way the system that renders only cares about entities have a position and a sprite and
Jake:Okay, so if you have, like, a nested component structure that would be handled by the render function, right?
Surma:It rates over them and draws all those images to the screen at the position
Surma:that way
Jake:That would handle, like, the component has children, something, something, something, is that...?
Surma:So that is an interesting question usually it's flat and
Jake:Okay.
Surma:You emulate the the hierarchy. So in baby, for example you have
Surma:children components and parent components
Surma:Which are just the ID of your respective children or your parent and that way you can now
Jake:...
Surma:Walk up and down the tree. So the actual list of entity to the entities is the population
Surma:It's just a flat collection an array
Surma:But by having basically the ID of your parent or the ID of your children
Surma:You can walk up and down the tree and do the corresponding
Surma:Actions that you want to do and that is in fact what baby does to do
Jake:...
Surma:A scene graph where you know, when you move the parent all the children have to move as well
Surma:So they have a system that
Surma:propagates the
Surma:Translation like the the 3d transform matrix up and down that tree so you can move a parent and it
Surma:Automatically propagates down to all the children and the children's children and so on so forth
Jake:Hmm.
Surma:But as you can see at the the system the function that does the painting to screen
Surma:Only cares that you have a sprite in a position everything else is on the on your on the entities
Surma:It doesn't know about or care about. So for example, we could also add a new component called
Surma:velocity and have a system that says give me all the entities with a position in the velocity and
Surma:I will move them per frame according to the velocity. So now we have two systems one is completely
Jake:...
Surma:independent of the act of rendering and
Jake:Hmm.
Surma:the other one is completely independent of how entities move about it just cares about rendering and
Surma:and
Surma:That is kind of the core concept of ECS if you write these pretty fairly small
Surma:self-contained systems that
Surma:express what kind of
Surma:Components are interested in and then the ECS takes care of running all these systems and you get
Jake:So, hang on, let me sort out the hierarchy of this in my head.
Surma:Things that are going across screen with a specific velocity
Jake:So, entities have components. Is that a one-to-one mapping, or does a single entity have many components?
Surma:Yeah
Jake:Right. And then the systems, they don't sit within that relationship, they're kind of external, they're just looking at all of the entities and doing stuff for them.
Surma:Entity can have as many components as you like
Surma:Yeah, they're part of the world
Jake:Yeah.
Surma:Maybe maybe as an implementation detail actually
Jake:Hmm.
Surma:but usually I've seen them as being part of the world and they are usually run in a user-defined or automatically defined order and
Jake:...
Surma:It's often called a query
Surma:So they they basically query the world of give me all the entities with that have these components
Jake:That makes sense.
Jake:...
Surma:but maybe specifically don't have it's almost like a SQL query really maybe because you're right give me all the components that
Jake:Yeah.
Jake:...
Surma:entities with component A and component B
Surma:But don't have component C and where component D has changed since the last frame all of these things you can usually
Jake:...
Surma:Express which obviously the job of the actual
Surma:ECS implementation is to make that fast and to optimize with all these things that you're giving it ahead of time
Jake:...
Surma:That it can figure out
Surma:You only need a small number of entities like it's a very smooth system that runs fast
Surma:But for example what what bevy does it automatically figures out which systems are independent and schedules them
Surma:Across your course, so it figures out which systems can run in parallel because they're independent
Jake:Oh, that's neat.
Surma:which I think is fascinating and
Surma:This made me think if and how
Surma:This could work on the web, you know, because you have these super granular systems these two examples
Surma:I just gave the move my entities according the velocity system and the render my
Surma:Entities on the screen system. One of them is not tied to the UI thread
Surma:Right, it's only data that needs to be manipulated
Surma:It's really the painting on screen that is main thread bound unless you're talking off-screen canvas, but let's not
Jake:...
Jake:But you would expect the positional changing stuff has to happen before the rendering, because the renderer needs to know where to render it. Is that fair?
Surma:Right, I
Jake:...
Surma:Think so
Surma:my hunch is that though that in most like at least game like scenarios you have one rendering system and
Surma:Most of the other stuff is just data stuff that isn't main thread bound. So all the
Jake:Hmm.
Jake:...
Surma:Processing could be paralyzed across multiple workers and work on the data
Surma:And then only once that is done you do one main thread bound rendering
Surma:so in fact the way bevy does it is that they run all the
Surma:calculations for the next frame in parallel with the rendering for the current frame, so they
Jake:Oh, that's neat.
Surma:They accept a delay of one frame technically
Jake:...
Surma:But I can imagine it's it's classic pipelining
Surma:So basically the main thread is busy doing its you UI work and painting well on all the other course
Jake:...
Surma:effectively, it's already doing all the non UI bound computations to prepare the data for the next frame and
Surma:I
Jake:...
Surma:was like, you know what considering that these systems are small and often the
Surma:The amount of data in a component that each system needs is very small I
Surma:Wonder if that is something that workers would be good at because the big difference from the web to all native platforms is
Surma:You can't just send the pointer
Surma:You can't just work on the same data as the other threats
Surma:You have to structured clone and copy and send the response back. There is actually some efforts going on
Jake:Well, we've got the shared array buffer, right? That's the closest thing we have to actually being able to... yeah.
Surma:Right, but then but that's bytes and now you're in writing now you have to I did write a library once called
Jake:...
Surma:What was it called?
Surma:Buffer backed objects. I think I called it buffer backed objects. We're basically through a proxy
Surma:You get normal JavaScript objects, but it's
Surma:Automatically serialized down into an array buffer. So that worked on shatter that would work
Surma:So that worked on shatter that would work but it's it's not quite the same like you end up
Jake:Nice.
Jake:...
Surma:You know in uncanny valley and JavaScript just doesn't have good ergonomics yet
Surma:I know there's actually some exploration going on and she's denying. Maybe you will talk about it. Who knows
Jake:Hmm.
Jake:...
Surma:But it as of now, I wouldn't say that JavaScript is well set up
Surma:But it has never stopped me before to not explore JavaScript in in this way and that's actually only one part
Jake:...
Surma:This is the part where I thought easy ss could be interesting for the web
Surma:As a means to make use of workers because this whole thing about which of these systems need to run on the main thread
Jake:Hmm.
Surma:kind of becomes
Surma:automatically analyzable
Surma:through the means of the query if the query grabs
Surma:Components that are main thread bound because they have textures or because it issues draw commands
Surma:it has to be main thread if not, it can probably run on a different thread and
Jake:...
Surma:I found that really interesting the other part and
Surma:This is more towards a contrast to our current landscape of UI framework is that easy ss are
Surma:By definition escape hatch by default and I should probably explain a bit what I mean by that
Surma:so I look at stuff like
Jake:Yes, do.
Surma:Preact or react or angle at the time. I don't know enough about swelter view, but basically
Surma:Whenever you write a react components
Surma:You do not by default you lose access to the underlying
Surma:Backing DOM element unless you explicitly expose it with forward ref
Jake:Mm-hmm.
Surma:I think because if you write your own component, you can get access to the DOM element by using ref
Surma:But if you have multiple layers of component boundaries ref doesn't work unless you explicitly forward it with forward ref
Jake:Yes.
Surma:And of course you could you could do like, you know
Jake:...
Surma:Like a display content span wrapper and then use JavaScript to get a child like you can drill through
Surma:But it's not
Surma:You know, it doesn't feel like it should be used that way and you can probably break stuff quite quite easily that way
Surma:What I found really interesting is that because easy ss are so flat
Surma:As in like there is there is no hierarchy in the way that data is stored
Surma:You can always look at all the other components that are in on your entity
Jake:...
Surma:so like you don't work necessarily on a component level you often work in what is called a bundle because
Surma:You need multiple components to be present and so you can add multiple components at once in a so-called bundle
Jake:...
Surma:so for example for
Surma:The sprites component was mentioned earlier
Surma:It's probably actually a bundle where you know need a position you need a size
Jake:...
Surma:You need the texture and you probably also need a mesh and a shader because this is rendered using web GPUs
Surma:So it needs to know which triangle should be put where and how do I what is the shader code?
Jake:Hmm.
Surma:It runs to put the texture on there and you most of the time you don't care about that
Surma:You don't know about that. You just you know, you create your sprite you pass in the image and a position and you're done
Surma:it's now on screen, but
Surma:You can and I found it quite interesting that I could grab in and actually grab
Surma:the web GPU mesh data and muck about with it and
Surma:Everything still work because it is by default all accessible
Surma:And so I was kind of thinking about that what it would be like on the web where you can provide convenience abstractions by default
Jake:...
Surma:The escape hatch of grabbing the underlying primitive is there rather than having to explicitly
Jake:...
Surma:Expose an options object or you know forward ref like you have to remember
Surma:To expose a level primitive by default the escape hatch is hidden in most frameworks today
Jake:...
Surma:With ECS, it seems to be inverted and I wonder how big of a difference that would make on a database
Surma:I don't know if there's any good
Surma:ECS frameworks for the web. I'm sure there are some
Surma:But I found it really interesting to think about because another thing I did is
Surma:That I wrote a little demo and an example with bevy just to play around where I wanted to do Boyd's
Surma:like bird or it's just the things that fly around and
Jake:...
Surma:kind of look like they have
Surma:Like a hive mind intelligence and it looks really nice and swarmy
Jake:Yes.
Surma:And I wanted to move the computation for that to the GPU because it's many many boys and they all run the same code
Jake:...
Surma:It's like it screams
Surma:GPU rather than CPU and so because bevy uses
Jake:Yes.
Surma:ECS and it uses ECS for everything even its own internals and it uses web GPU
Surma:I was able to just grab into the bag of entities that
Surma:maybe spawns by default and grab the reference to the web GPU device and add my own
Surma:Compute pipeline and shader code to use the same
Surma:pipelines that bevy already have
Jake:...
Surma:To add my own bit of computation to it and it just integrated cleanly and nicely
Surma:Ah good point so you you can hide
Jake:Okay.
Surma:Implementation details. It's just not by default and I think that's really nice
Jake:...
Surma:So the the GPU device is just a GPU device and web GPU is set up to run
Surma:different
Surma:Shaders, that's like that. That's actually, you know, that's more like props to web GPU that it's designed that way. Um
Surma:But you can definitely hide
Surma:Entities if you want to and bevy does do that
Jake:But this is one they've chosen not to hide, or they haven't chosen to hide.
Surma:Yeah, I think they really only do it if it's necessary if it's in any way delicate and like and sometimes it does not work
Jake:Hmm.
Surma:so for example there when you add your camera as it's called to the scene because that's usually you
Surma:The camera is just an empty object. It kind of encodes how to move the world coordinate space. It feels like
Surma:You are moving the camera rather than all the objects, but in the end, it's just another transform
Surma:But in a 3d world you have a bit more you have like your field of view and your depth of field and all that
Jake:...
Surma:stuff and
Surma:You have the frustum which defines your angle of view and where the clipping planes are and
Jake:...
Surma:When you start changing those values after the camera has been created they do nothing
Surma:so there is sometimes situations where changing a component isn't really having effect because that's not how the
Jake:...
Surma:Underlying system is implemented. So it is obviously a bit dependent on how the individual functions are implemented whether
Jake:...
Surma:Changing a component or grabbing it has desired effect
Surma:but most of the time especially if you are grabbing through to a
Surma:standardized piece like a GPU device or let's say if it was a file handle or a web socket or any of those things and
Jake:...
Surma:then you have a pretty good understanding of what you're doing could mess with the rest of the system or if it is a
Jake:...
Surma:Fine or safe thing to do. I just really like that
Surma:I was able to use the entire architecture of a game engine, which usually sounds overwhelming and like black magic to me
Jake:...
Surma:and in this case it feels
Surma:It's just code, you know, like it's a nice demystification in my head
Jake:...
Surma:You
Surma:Well, so that's that this is a bit maybe go
Surma:too far into rust but there's
Surma:read only access to components and
Jake:...
Surma:Read write access to components
Surma:So there can only ever be one person that has a read write reference to any given data object
Jake:Hmm.
Jake:I see.
Surma:but there can be as many as you want if it's read only and
Surma:That is expressed in rust type system and as a result in the
Surma:queries for your system, so if
Surma:Multiple systems want read access to the current
Jake:...
Surma:position of
Surma:I don't know all my my birds on the screen
Surma:Then all these systems can still run in parallel as long as there
Surma:Hasn't been scheduled a system that also wants to write to it
Jake:Right.
Surma:Which is usually where you then explicitly order and say like, you know
Jake:...
Surma:The writing stuff is at the very last stage where you do
Surma:Update positions is the system that runs by itself at the very end or something, but everything else can be paralyzed
Surma:with the GPU device
Surma:it is actually a read-only reference because web GPU is
Jake:...
Surma:In internally designed to be accessed from multiple threads
Surma:So while it's actually I don't think it's actually implemented on the web the design and the spec very much prescribes that you can
Surma:Send around the web GPU device to multiple workers and they all do their stuff at the same time and the browser and the operating
Surma:system take care of
Surma:making that work without
Surma:Them overwriting each other state or anything like that
Jake:Nice.
Surma:So that in that sense even in that example, I was not hurting the parallelism
Surma:Which again, it's really interesting
Jake:...
Surma:Yeah, that was actually really interesting because I ran it on my computer and I built a little FPS meter
Surma:It's like oh look it it runs at 60 and let's see how many birds I can add
Surma:Until it gets slower and then I wanted to test it out on
Surma:The web compiled it to web GPU had to fiddle a bit because web GPU isn't quite the default in baby yet
Surma:But it wasn't too hard
Jake:...
Surma:And I opened it and it ran at 120 Hertz
Surma:Yeah, but why didn't it do it on native I haven't quite figured out why it was throttle it as a native binary
Jake:...
Surma:I wonder if like if that's an option for the library that I used to create windows on Mac OS native or something
Jake:...
Surma:I just thought was really interesting. It's like Oh suddenly 120 frames per second
Jake:So what we're saying is the web is better, right? That's... yeah.
Surma:Yeah, that's that's really the takeaway from from from all of this and yeah, I'm curious
Jake:...
Surma:I could see an ECS being interesting to implement in JavaScript where you know
Jake:...
Surma:Entities are just empty objects and maybe uses unique symbols for components and you can just add all the components to your
Jake:...
Surma:Objects and that's how you model the entities
Surma:I don't know
Surma:I would quite interesting to me if you had a UI framework using the system where you can always access the underlying
Surma:DOM element or the underlying event listener or all these things and
Jake:...
Surma:you often wouldn't but if you need to it's there and
Surma:And I need to look around if that's ever been tried by someone. I'm assuming it must have
Surma:but I've been
Jake:And if it hasn't, then you're it, right? You've got to go create it.
Surma:Yeah, I guess I guess I have now officially volunteered
Jake:...
Surma:The the other thing I want to talk about but I think I think I may just do that on the next episode
Surma:Because you know
Jake:...
Surma:Forward teaser we haven't done that ever in a while
Jake:No.
Surma:I don't know
Surma:So you now you have this framework or not framework you have this library bevy that you know
Surma:Does really high performance rendering has its optimized system it integrates on the web with?
Surma:You know tap events pointer events key events can go full-screen
Surma:You can grab all the other web API's from within your rust code
Surma:Like you could technically do index DB and all those shenanigans
Surma:This kind of reminds me a bit of if you want to take full control
Jake:...
Surma:just take wasm web GPU and
Surma:you know web HID and
Surma:build your complete own stack from the ground up and
Surma:I guess at some point we should talk about is is that worth it? What do you win? What do you lose?
Jake:...
Jake:...
Surma:I think figma is one of them, right?
Surma:Like they have they're just they're just canvas and wasm and it feels really good. It looks really good
Jake:...
Jake:Yeah.
Surma:And the question is would that have been possible?
Surma:with just
Surma:Like let's say the Dom and what would've been harder or would've been easier like but yeah
Jake:...
Surma:I think I think considering I've already like blabbered on for way too long. I'm just gonna leave it here for this time. Yeah
Jake:...
Surma:Yeah, I know you do
Jake:...
Surma:So my
Surma:my future father-in-law
Jake:...
Surma:told me recently that
Surma:his neighbor
Surma:Has
Surma:Started to smartify their home
Jake:...
Surma:And I was like, that's interesting I've recently
Surma:Fallen into the the home assistant rabbit hole, which I think it seems like many people are doing right now
Jake:I am as well, yeah.
Surma:I'm seeing it. I've seen it popping up more and more
Surma:but specifically I was told that this neighbor has two cats and
Surma:So they've been buying smart devices around the cat's life
Surma:I think a well-known smart device for pets is for example the smart cat flap
Jake:I've got one. Yep. Yep. Mm-hmm. I do.
Surma:Yeah, do you get notifications when your cats that's is and how are you finding how you finding that?
Jake:Yep.
Jake:...
Surma:I
Jake:...
Surma:Like that there's this angle of quantified cell where it was like I can tell you exactly the average times my cats go out at night
Jake:Yep. Absolutely.
Surma:That's but then my what he told me was
Jake:...
Surma:Mind-blowing to me is that that said neighbor also has bought a smart cat litter
Surma:And
Jake:...
Surma:Yeah, I
Surma:Wasn't sure if that is the kind of conversation you want to deepen but I had to know and so I asked well
Surma:What what's smart about it? And the first thing sounded not too bad in that it
Jake:...
Surma:Automatically, I guess robotically
Surma:bags up
Surma:the business for you to
Jake:...
Jake:...
Surma:For in I know
Jake:...
Surma:Right, and I guess the whole point is like, you know, it doesn't smell like it doesn't distribute the smell for
Jake:...
Surma:Extended periods of times. It's easy for you to grab and take out and the other parts
Surma:Well, it all and it sends a notification. So, you know, there is something to take out which seems I don't know
Surma:Do I want that notification? It seems a bit weird, but then he told me that this smart cat litter
Surma:Also weighs your cat before and after
Jake:...
Jake:...
Jake:...
Surma:And the leaderboard right like you want
Jake:I mean I want that as a human. I want that on my toilets, right? I want to know I want those stats.
Surma:You want to like check in and you want to have the leaderboard and you want to make it you want to gamify it
Jake:...
Surma:Achievement unlocked crack that the one pound
Jake:Oh, absolutely. Yeah.
Jake:...
Jake:Oh, yeah.
Surma:Maybe there's my market niche
Jake:...
Jake:Oh, I'm going to have to look into that.
Jake:...
Jake:My cats normally don't use the litter tray, although they have in the new house for a bit, but, you know.
Jake:...
Jake:Yeah, if it carries on like that, I might need to get this self-bagging thing. Yeah, that sounds good.
Surma:Get the smart litter tray well with the the staple bathroom story out the way
Jake:...
Jake:Oh, yeah. Very good.
Jake:...
Surma:What wanna wanna what wanna web
Jake:Want a web? I do want a web.
Jake:...
Jake:So, yeah, I want to talk about the stuff in Stage 3 TC39 that hasn't really been picked up by, well, certainly all the browsers.
Surma:You
Jake:That's only been picked up by one browser so far, and what I'm excited to hear is what you think of them and which ones are best.
Jake:...
Surma:Is it chrome
Jake:No, not which browser's best. Which feature's best. Come on.
Surma:Oh, but it's the one brother picked it up chrome
Jake:...
Jake:No. No. No. And, yeah, we'll get onto that, but it is not that straightforward.
Surma:Oh
Jake:...
Jake:Except for the first one, which is a Chrome one, which is iterator helpers, right? Stage 3.
Surma:Ah, I do not know exactly what's in it, but the name already makes me happy
Jake:...
Jake:And...
Jake:...
Jake:Yeah, it just means all your iterator instances get map filter. Take, drop, flat map, reduce.
Jake:...
Jake:Two array for each every find. The kind of stuff you get on arrays, but you just get them on plain iterators.
Surma:You
Jake:...
Jake:Well, but then, you know, things like take and drop are kind of, yeah, not on arrays, but are useful for iterators.
Surma:Yeah
Jake:...
Jake:They are shipped in Chrome, but they're not in Safari or Firefox yet.
Jake:What's your rating? How are you feeling?
Surma:If they
Jake:...
Surma:Actually don't do like the intermediate array allocations, which is the problem with the other with the array methods, right? Like if you have
Jake:Hmm.
Jake:...
Surma:Big old can array and you do map filter map map filter each of these
Surma:calls will create a
Surma:New array with the same well in the case of filter with the same size
Jake:You're essentially chaining the values through. So, yeah, so...
Surma:And I'm sure engines do clever stuff but with on an iterator it is clear that you are you you want to
Jake:...
Surma:Do the stream ease?
Jake:Yes, so, on an array, when you do a .filter, then a .map, you know, all the filtering happens, then all the mapping happens.
Surma:You
Jake:Whereas with iterators, you're creating a chain where, you know, the values can get filtered, then mapped.
Jake:...
Jake:And it's more likely to happen that way around. Filter, map, filter, map, filter, map, rather than filter all the things, map all the things.
Jake:But, yeah, there's no intermediate array creation.
Surma:Is it like like all all of them is flat map flatten all the jazz
Jake:...
Jake:Flat map is there. Flat isn't.
Surma:Interesting, well, I guess flat map is the same as flat in this instant. I
Jake:...
Jake:Yeah.
Jake:...
Jake:Exactly. Exactly. Yeah.
Surma:I'm
Surma:Really? I like it a lot because I always like I like it. Sometimes I like expressing
Jake:...
Surma:Transformations that way where you make it is discrete map and filter steps
Surma:But I at some point you feel a bit bad about all the intermediate arrays like often
Surma:It's not big enough to actually make a difference, but I would just feel better if I didn't
Jake:Yeah.
Jake:...
Surma:Yeah, yeah
Jake:Oh, it saves you having to create an array from the...
Jake:You know, there's that thing where you do the angle brackets, dot, dot, dot, your iterator.
Surma:Exactly, I mean I immediately now want to like ask and what about async iterators. Is it part of it as well?
Jake:And the only reason you're doing that is because you want to use map and filter and stuff.
Jake:But now you don't have to. Yeah.
Jake:...
Jake:Nope. But I think they plan to do it, but it's not in that particular proposal.
Surma:Right, okay
Jake:...
Jake:All right. Moving on.
Jake:And now, if we were looking for the feature with the coolest name, it's this one.
Surma:You
Jake:We're not, but, you know, Shadow Realm.
Jake:...
Surma:Are you all the shadow realm that's been around for a long old time
Jake:I know, but it is now stage three.
Surma:You
Jake:So, for folks who haven't been sort of looking through TC39 for years and years, this lets you create a place to run code.
Jake:It has its own global and a restricted set of APIs compared to like a page.
Surma:Yeah, it has nothing to do with shadow roots really
Jake:...
Jake:I know. Yeah.
Jake:...
Surma:So it's like a worker but without the separate thread, isn't it
Jake:Yes. Very, very similar.
Jake:So, yeah, it has, you know, it has things like event and event target in there, but it doesn't have access to the DOM.
Surma:You
Jake:...
Surma:Mm-hm
Jake:And, yes, you would do like new Shadow Realm.
Surma:You
Jake:And then on that, you do Shadow Realm dot import value.
Jake:You give it a module ID and an export that you want.
Jake:That returns a promise and it gives you the thing from the module.
Jake:But, yeah, as you say, it feels a little bit like a worker, but it is same thread and same process.
Surma:So, is it a sandboxing primitive
Jake:...
Jake:To a degree, but not because it is the same process.
Jake:So, it is Melt-A-Spec down. Hang on. Specter Meltdown.
Jake:...
Surma:You
Jake:Vulnerable.
Jake:So, it's security to a point.
Surma:So it's not don't use it for running untrusted code
Jake:...
Jake:Well, semi-trusted code, I think, is the thing.
Jake:It's because it's synchronous. It can still lock up everything, right?
Surma:Okay
Jake:And it can still, I'm going to say Melt-A-Spec down again.
Surma:Right
Surma:You
Jake:It can still, you know, attack the memory, because it exists in the same process.
Jake:It can attack things in the same process.
Jake:...
Surma:Okay, then let me flip it around what should you be using this for
Jake:Well, that is where I start to wonder.
Jake:The explainer mentions Google AMP a lot, which dates when some of this documentation was written.
Surma:You
Jake:But it does suggest, like, yeah, running third-party code in there.
Jake:But it is with an eye of a third-party that you kind of trust.
Jake:...
Jake:But, yeah. So, the values you get back can only be primitives or functions.
Surma:Oh
Jake:And if it's functions, the arguments have to be primitives or functions, and it has to return primitives or functions, right?
Jake:Like, that's the only two values that can go around.
Jake:...
Jake:But, yeah. Like, I...
Surma:Also, you can get a function
Jake:...
Jake:Yes.
Jake:...
Surma:Back, but it is automatically invoked within that other realm
Jake:Yes.
Jake:...
Surma:But it doesn't require structured cloning
Jake:No. Because it's only primitives.
Jake:So, it's, you know...
Surma:You it's an object and primitive
Jake:...
Jake:No.
Jake:No. So, primitive as in string, number, big int.
Jake:Like, that kind of stuff. That kind of stuff.
Jake:Like, not objects.
Surma:That that feels odd
Jake:Yeah, but that's the thing.
Surma:You
Jake:It's like, I'm looking at this API where it's .importvalue, you give it a module ID and the export name that you want to get hold of.
Jake:And I'm like, give me that on workers and give me it with structured clone.
Jake:And I...
Surma:Yeah, but even for Shadowrun why wouldn't use structured clone this as a like it's there
Jake:...
Jake:Ah, yeah. I think maybe they're open to expanding it in future, but right now, no.
Surma:Maybe okay. So we are basically you're saying is we're both a bit
Jake:...
Jake:Yeah, just give me...
Surma:Left with a question mark when we would use this I
Jake:...
Jake:Yeah. And maybe it's more useful in nodeland, but I want that API on workers now.
Surma:Mean I I
Jake:...
Surma:Could see untrusted ish code like if I wrote something like
Jake:...
Surma:Like a jspin code pen kind of thing where yeah, you can block yourself that that's all good, but you cannot
Jake:...
Surma:muck with
Surma:My business logic of the thing that I've written so in that maybe that's a use case where it would work
Jake:...
Surma:But then again within that within the shadow realm
Jake:...
Surma:You do not have a dom and you cannot expose it on my because I doubt that you can just send a reference to like
Surma:An iframe or something into the shadow realm
Jake:Yeah.
Jake:Like, I would consider maybe, like, you know, in a worker, create a shadow realm so the code is running in a place that it can't mess around with index.db.
Surma:Yeah
Jake:But then you still have to remember you're running in the same process, so...
Jake:...
Surma:So it doesn't come with all the web globals, it's really like a completely
Surma:blank canvas
Jake:It's, no, it's not even that, because it has event target, it has event, it has some of the performance.
Surma:JavaScript scope almost
Surma:Right that which I would consider vanilla JavaScript, but nothing that interacts like it's hermeneutically sealed you can't really into
Jake:Oh, I see, okay.
Jake:Yeah.
Jake:...
Surma:Can you manually expose anything to the shadow realm? It sounds like you can't because of only primitives
Jake:You can evaluate code into that realm, so you can evaluate code that adds to the global.
Surma:But could I expose like a function from the owning scope I could I say
Jake:...
Surma:Import like this function from inside the shadow realm should invoke this function on my end. So I could that
Jake:Oh, that's interesting. I think maybe you could, because I think, you know, because functions are allowed, I think functions are allowed as arguments as well.
Surma:You
Surma:Oh, so you can't pass in callbacks almost and that way I could then through a lot of duct tape kind of re-expose
Jake:I would have to double check that.
Jake:Maybe.
Jake:...
Surma:Local storage if I was so inclined
Jake:I would have to double check that.
Jake:...
Surma:Seems like we'd come link for shadow realm now
Jake:Well, yeah, exactly.
Jake:Get on it.
Jake:Yeah, okay, so I think we're sort of similar opinion there.
Surma:Low excitement, honestly, which
Jake:It's interesting.
Jake:Yeah, it may be more important in certain systems that we aren't involved in.
Surma:Yeah, I wonder if it really like you say maybe it is really the groundwork for making it more capable in the future
Jake:...
Surma:Because I'm assuming this has covered a lot of new ground and they want to get this
Jake:Yeah.
Jake:...
Surma:Slotted in implemented so that then adding what we maybe find obvious
Surma:Are then easy additions that can be discussed in isolation rather than discussing the entire thing in detail
Surma:discussing the entire thing as a whole all the time
Jake:And part of that might be moving structured cloning from HTML land into JavaScript land.
Surma:You are right because I was wrong I said structure clone is right there but like in spec land it is not it does not exist
Jake:...
Surma:In TC 39 exists only in the what WG
Jake:Hmm.
Jake:Exactly, exactly.
Jake:All right, next feature.
Jake:Regular expression pattern modifiers. Here we go, here we go.
Jake:You know those little things you put at the end of regex, like I, to make it case insensitive?
Surma:You
Surma:Yeah
Jake:You can put those in a sub-expression.
Jake:...
Jake:So, you know, a part of your regex is case insensitive, rather than the whole thing.
Jake:...
Surma:Okay, I I sure
Jake:That's it.
Jake:...
Jake:Yeah, that's my opinion as well.
Jake:It's like, yeah, sure, man, cool.
Jake:I mean, whatever, you know.
Surma:I'm easy
Jake:I'm going to keep the champagne in the fridge when that ships, but, like, great.
Jake:And do you know what, I'll probably use it one day and go, yeah, yeah, yeah, I'm glad this happened.
Surma:Yeah
Surma:Yeah, I'm trying to think it could get really confusing because there's
Jake:...
Surma:I'm guessing stuff like G global doesn't work as a
Jake:No, I think it's more the, yeah.
Jake:...
Surma:But stuff like M where or usually a dot doesn't capture a new line but with M it can match a new line
Jake:Exactly, exactly.
Jake:...
Surma:Yeah, okay cool, yeah, well done
Jake:Yeah, that's it.
Jake:All right.
Jake:Set methods.
Surma:You
Jake:So, on set, you get
Jake:.intersection, .union,
Surma:Yes, yes want gimme gimme now good
Jake:difference, yeah, symmetric difference,
Jake:is subset of, is superset of, is disjoint from, yeah, yeah.
Jake:...
Jake:There you go.
Jake:Yeah, I think I, my opinion as well, yeah.
Jake:I want these.
Jake:They are shipped in Safari already, and in,
Jake:they're behind a flag in Firefox, I know.
Surma:Damn look at them go
Jake:So this is what you were saying at the first, it's like,
Surma:You
Jake:it seems like Chrome is the furthest behind
Jake:in this implementation.
Jake:So, yeah.
Surma:Hmm I wonder why it seems like such an obvious
Surma:Thing was the problem with sets. Well, I say problem the I
Surma:Just now because I was doing the the the bevy stuff where you know
Surma:I build up sets of entities sometimes to figure out which ones do I actually want to
Jake:...
Surma:Process I used a set a B tree set in rust which is
Surma:Ordered by the value of the thing that's in there
Surma:So if you can if the the value type it's in my set
Surma:has operations like is greater than you can use a B tree to store the set where they are stored in order and
Surma:when you have that it is easy to do an intersection because you just iterate through both of them in lock step and
Surma:If one is smaller than the other you iterate that one and if they're equal it's an intersection you can like it's an O of n
Jake:Hmm.
Jake:...
Surma:intersection in
Surma:JavaScript sets are ordered in the sense that the objects are given back to you in the order. They are inserted
Jake:Yes.
Surma:So if you had let's say a set of what you can't use numbers
Jake:...
Surma:But a set of objects to two sets of objects
Jake:Hmm.
Surma:There's no easy way in user lands to implement a section except an O of n squared where you iterate over both
Jake:...
Surma:Well, I'm assuming it's good that I'm assuming that has is often
Surma:it's probably faster than that, but you have to basically do loop over one set and check in the other set all the time and I
Jake:Yes.
Jake:...
Surma:Think under the hood. There's probably a better way, but it's not accessible to use lines
Jake:Exactly.
Surma:And so I'm just quite happy that because those are common operations, right?
Jake:...
Surma:You want to join two sets you want to intersect two sets. It seems like
Surma:That should just be provided. So I'm surprised that Chrome hasn't just shipped that
Jake:Well, do you know what?
Jake:Maybe I'm getting wrong information from
Jake:canIuse and the regular places,
Jake:because this was championed by someone
Jake:who works, you know,
Jake:Satya, who,
Jake:do you remember Satya? He was, we,
Surma:Yeah, we did
Jake:we interviewed him in one of the
Jake:old HTTP two or three episodes.
Jake:Yeah, and he championed this, so
Jake:I would be surprised if there wasn't
Jake:some code sitting in Chromium somewhere,
Surma:You
Jake:but yeah, I imagine this will,
Jake:we will get hold of this sometime
Surma:Yeah
Jake:this year in browsers.
Jake:All right, next up.
Jake:Temporal, or temporal,
Jake:I'm not quite sure what the
Jake:best way to pronounce it is.
Jake:So, JavaScript dates
Jake:are hard work.
Surma:Yeah, oh yeah
Jake:So the way
Jake:a date is stored in JavaScript is
Jake:milliseconds from 1970,
Jake:right, the Unix
Jake:epoch.
Surma:Yes
Jake:But in DevTools, when you look at a date,
Surma:You
Jake:you are shown, like, a
Jake:version of it which is in your local
Jake:time zone. And the methods
Surma:Mm-hmm
Jake:on it of, like, get me the day, get me the
Jake:hour, or whatever, these are your local
Jake:time zone. There are some other methods on there
Jake:which get the UTC values,
Jake:but it's an absolute
Surma:Mm-hmm
Jake:minefield, right? So,
Surma:Yeah, it's months are
Jake:it,
Surma:One indexed like if you say get month it starts at one get ISO string
Surma:Which should give you the date in your what is it called?
Surma:Is it ISO 8 6 6 1 1 of those the standard string format?
Jake:I think months are zero
Jake:indexed. I think that was one of the weird
Jake:bits, that days are
Jake:one indexed and months are zero indexed,
Jake:which is stupid. So, like, January
Surma:Check it check it right now
Jake:is zero. Oh my god,
Jake:okay, here we go.
Jake:Right, MDN,
Jake:get month.
Jake:I wrote
Jake:get moth just to,
Surma:You
Jake:yeah,
Jake:yeah, yeah, get month,
Jake:zero for January.
Jake:Anyway,
Surma:And
Jake:yay.
Surma:Yeah, and I get ISO string which the name kind of implies it gives you the date in ISO
Jake:Yeah.
Jake:UTC.
Surma:Yeah, it forces UTC even though it shouldn't the the ISO format can very well handle time zones
Jake:Yeah.
Jake:So, this is
Jake:where it's messy, because,
Jake:like, if you have an input
Jake:type date, on that you
Surma:You
Jake:have .value as date,
Jake:and that gives you the selected
Jake:date, midnight
Jake:UTC,
Jake:which means that if
Jake:you look at that date in the console,
Jake:if you're not on
Jake:GMT or UTC time,
Jake:it could be showing the wrong date, right?
Jake:Like, it's very confusing.
Jake:And it means that you need to make sure
Surma:Yeah
Jake:if you're getting the data out of that, you need
Jake:to get the value of, which gives you the
Jake:milliseconds from the epoch, or you use
Jake:the UTC methods. If you use one of the other methods,
Surma:You
Jake:it's going to be wrong.
Jake:Well, yeah, if you are in
Jake:GMT, it's going to be right, coincidentally.
Jake:And then someone else
Surma:Yeah, England well England in winter
Jake:runs your code and it's wrong, yeah.
Jake:Exactly. England in winter,
Jake:what a better place to be.
Jake:But here's the thing,
Jake:Polaris, the
Jake:design, the component library
Jake:at Shopify, their date
Jake:picker returns you a date object
Jake:and it's midnight
Jake:of the date selected
Surma:You
Jake:in the current time zone,
Jake:which means it appears
Surma:Oh
Jake:great in the console,
Jake:and if you do get month, get day,
Jake:you get the right values. But if you
Jake:did value of, that gives you the
Jake:milliseconds, and you sent that
Jake:to the server, you're going to get the wrong
Jake:stuff back at the other side, right?
Surma:That's awful, yeah
Jake:Because it's
Jake:that's such a, you know,
Jake:whoever coded that, just
Jake:they've been bitten by
Jake:date, right? It's not their fault, it's just
Surma:Yeah
Jake:hard. Anyway, temporal
Jake:to the rescue.
Surma:You
Jake:It lets you create a
Jake:date object that just has
Jake:like month and date.
Jake:It lets you create a time object, which is just
Jake:a time.
Jake:Or, you know, you can create a date and time,
Jake:which is just a date and time, like no time zone.
Jake:And this stuff is, this is
Jake:great, because it's exactly the amount of
Surma:Oh
Jake:data you're selecting, like month and
Jake:date is the amount of data you're picking in the
Jake:date picker. The fact that you end up with an object
Jake:which represents time
Jake:and displays, you know, has methods that
Jake:are associated with time zone, it's just
Surma:You
Jake:confusing because it shouldn't, right?
Jake:That data isn't there.
Surma:And if I have a
Surma:daytime object from temporal and
Surma:I say okay, and now give me the Unix timestamp of the state in this time zone. Does that exist?
Jake:If you've got, uh,
Jake:just an object that is representing time
Jake:or just an object that's representing a date,
Surma:You
Jake:you can mash these together to create one that
Jake:represents both. And then you can add a time zone,
Jake:which now represents a particular time zone
Jake:of that time and date.
Surma:And then hopefully at some point I can turn it to Unix timestamp because that's you know, usually the thing you want
Jake:Well, Unix timestamp is supposed to be UTC,
Jake:right? But you could do it
Jake:for the, you know, for the
Surma:You
Jake:UTC timestamp, right?
Jake:But you could do it for a particular
Jake:time zone if you wanted, right?
Surma:And Unix timestamp doesn't have a time zone it's a number of seconds since the point in time
Surma:So that's why I'm wondering if they're because usually often with
Jake:Well, that's fair.
Jake:Oh, I see
Jake:what you mean.
Surma:APIs or server communication that is your ground truth format where you say like if you want to communicate a point in time
Jake:Yes.
Surma:That's what you send, but I'm assuming they have thought of this
Surma:I would be surprised if there isn't a way to
Surma:then say okay, I now have a date time in a time zone and now do do the fancy math because
Jake:Hmm.
Surma:My god, you do not want to do the math yourself if you've ever looked
Jake:Oh, absolutely.
Jake:Yeah, and
Jake:being able to represent a time as well
Jake:is great for cases where
Jake:because it, you know, if we
Jake:organize a
Jake:time to have a meeting, then
Jake:that needs to include
Jake:a time zone because if we're in different
Jake:countries, we're agreeing on a point of
Jake:a shared point of time.
Surma:Exactly
Jake:But if you're setting an alarm on your
Jake:phone, like
Jake:if you set your alarm to go off at 9
Jake:in the morning,
Jake:you don't expect that to change if you
Jake:get on a plane and travel somewhere else.
Jake:You don't want to be woken up at 2
Jake:in the morning because that's where
Surma:Or would you that's actually I think it's a question
Jake:you've traveled.
Surma:I asked a couple months ago on Twitter because I was stumbling over this when the when summertime ended
Jake:Hmm.
Surma:Where it is technically possible that your alarm time never happens
Jake:Yes.
Jake:I think that is a fun one to ponder.
Jake:It's like, what happens if you skip
Jake:your alarm by, you know,
Jake:changing the time on your
Jake:phone, which might happen automatically
Jake:by crossing time zones
Surma:Yeah
Jake:or summertime, that kind of thing.
Jake:Yeah, anyway.
Surma:I think so sometimes the temporal stuff sounds like an amazing affordance similarly to the
Surma:Internationalization stuff about currencies and dates and stuff and I think that's
Jake:Yeah.
Jake:Yeah, exactly.
Surma:Great. I love that. They're doing it heavy lifting
Jake:It's one small part of the platform,
Jake:and their docs are great,
Jake:actually, in the proposal.
Jake:I urge folks to have a look.
Jake:And there are little bits of it in Safari,
Jake:TP, technical preview,
Jake:whatever, but nothing else.
Jake:It's not really being picked up, but I'm
Jake:really hoping we see some implementations
Jake:of that this year.
Jake:All right, what's next up?
Surma:You
Jake:Oh, JSON modules.
Jake:We talked about this.
Jake:I wasn't sure
Jake:where to put them in this because
Jake:they're technically in Safari only,
Jake:but the old
Jake:assert syntax is in Chrome.
Surma:Oh, this is with import blah blah blah dot JSON with type Jason
Jake:Yeah, so
Jake:this is
Jake:JSON. Yeah.
Jake:Exactly, that's it. What do you think?
Surma:Sure, I
Jake:Yeah, that's my opinion as well.
Jake:Yeah.
Surma:Think I think Jason specifically was never
Surma:Especially since top-level await is a thing I can just do a weight fetch then dot Jason
Jake:Yeah.
Surma:You know like it's kind of the same thing, but the groundwork that this syntax opens up
Surma:I think that's where the real payoff comes in
Jake:I think it's something
Jake:I'm glad that it's there. I think in most cases
Jake:I would only ever use it for
Jake:local, for the same origin data that
Jake:I really trust.
Surma:You
Jake:And I would then
Jake:probably bundle it in that case.
Surma:Yeah
Jake:Because if I'm getting data
Jake:from somewhere else, I don't want
Jake:a failure to fetch that data to
Jake:break my whole module graph, right? To break the whole
Jake:script. So, yeah.
Surma:Yeah, exactly
Jake:Fair enough. Whatever. Fine.
Jake:Here's another
Jake:feature, which I had no idea about this.
Jake:Import source.
Surma:You
Jake:So instead of
Jake:import x from
Jake:specifier,
Surma:You
Jake:import source
Jake:x from specifier.
Jake:Ooh.
Surma:Wait, can you can you spell that syntax for me? Like is that a new keyword?
Jake:So import
Jake:Yeah, it's a new keyword. Import
Jake:space source as in S-O-U-R-C-E
Jake:and then
Jake:x
Jake:from specifier.
Jake:So it's just adding that word source
Jake:after the import and it
Surma:What does that mean
Jake:gives you the source code
Jake:of the thing.
Surma:For X, oh it gives me the sort of the the entire the source of the module. Ah
Jake:For specifier,
Jake:it gives you the module source code.
Jake:Yeah.
Jake:Yeah.
Surma:Okay, that's hmm
Jake:And
Jake:when I first saw this, I was like,
Jake:why isn't this
Jake:an import
Jake:attribute?
Jake:And it just so
Jake:happens that the explainer has a section on this, which
Jake:is great. It's like, well,
Jake:when you change the import
Jake:attribute,
Surma:You
Jake:that is a different entry in the
Jake:module graph. You can import the same thing in two
Jake:different ways and get two different results.
Jake:Whereas import source, it gives you
Jake:exactly the same thing. You're just getting the
Jake:source of it rather than
Surma:So it populates the module graph it just doesn't evaluate it
Jake:the module graph.
Jake:Yes.
Jake:So you could do...
Jake:No. So you can do
Jake:import source x from specifier
Jake:with... and you can have
Jake:import attributes after it, which work
Jake:as expected. You can get the
Jake:WASM source or
Surma:You okay, can I then evaluate that source lazily?
Jake:whatever. The JSON source.
Jake:You could.
Jake:You would just use an import, right?
Jake:I think part of the idea is like, it's
Jake:aimed at tools which might want to
Jake:introspect something or modify something
Jake:before calling a val or whatever.
Surma:But then why does it matter that it's in the module graph
Jake:I think purely just because
Jake:it needs to be in the module graph, so
Surma:You
Jake:if you import it twice, it's not going to the network
Jake:twice. So you import source
Jake:and then you import not source.
Jake:It only goes to the network
Surma:Yeah, I guess that could be nice
Jake:once.
Jake:I think it's interesting.
Jake:I don't know if I'd ever use it, but I think
Jake:interesting tools could be built around this.
Surma:Yeah, I'm trying to think if there's like, you know, you could import source and
Surma:Then turn it into a blob URL to spin up a worker with that file
Jake:Oh, yeah.
Surma:But then you have all you if you have module workers
Surma:Why why would you could as you say you could you know, you could run Babel at runtime or something?
Jake:Yeah.
Surma:I do some transpilation. I yeah, I
Surma:I'm not quite sure where I would use it. It's
Jake:Hmm.
Surma:Maybe wasm is the better use case. But then again, I keep wondering like what?
Surma:it is the same as fetch except for it's in the module graph and
Surma:And
Surma:HTTP caching I would have thought would give you most of the benefits, but maybe I'm missing it
Surma:So yeah, don't don't take my word for it. I should probably read the explainer before I say I don't get it. But
Surma:Yeah from my current
Surma:Standpoint. I don't know where I would go. Yes. That's exactly what I was looking for
Jake:Yeah, I think
Jake:it's one of those things where I'm like, I don't
Surma:Yeah, yeah, that's probably nice way to look at it. Oh boy
Jake:really know what I'd use it for, but
Jake:I imagine I will very much
Jake:enjoy tools that are built using it
Jake:in future.
Jake:All right. Next one. Decorators.
Jake:And decorator metadata. Technically
Surma:How long is the decorator journey been going on