Hello and welcome to this month's
edition of Small is Beautiful.
My name is Aral Balkan and it's
going to be just me today because Laura is
busy. And today I'm going
to take you through something that
I've added very recently to Kitten: the ability
to create end-to-end encrypted Small
Web applications and peer-
to-peer Small
Web applications. I mean, that is actually
part of the nature of what the Small Web is going to be but so
it's quite exciting. I've gone
beyond - a little beyond - the
kind of infrastructure work I've been doing in the last few years...
building upon that now, we're
getting to the fun bits. So yeah, let's
see... I think people are
already joining.
Um, yes, hello. Jovial Hopper - you
can change those names if you want to - Hi Olwe?
...I'm not entirely sure how to
pronounce your name. Hello! So we have
some folks joining which is kind of cool. All right, so
let's get started.
so
I'll start from the very beginning. I'm not going to assume, you
know, anything about kitten or how to get
started. So I'm just gonna pull up
a web browser here. And actually let
me just give me one second. Sorry.
Just going to set my system to light mode
because it's just gone 5pm and it's gone to dark mode. I want
to demode and light mode for you.
So oops, that is
the chat, let's go.
It's the web browser.
Right, so I'm just gonna pull up a web browser here and take
you to the kits and website which is it's repository
right now, which is all code work.
So it's codebug.org forward slash
kitten forward slash.
If you go over there, you'll see
that kitten is a web development kit that small person
loves you all true.
And there is this warning that you
should really heat. It's not future complete. It's
not ready for production. Use if you are a
developer, you can play with it just don't
really deploy stuff with it and what
I'm going to show you today with the basic end-to-end encrypted
chat example, for example,
don't take that and deploy that
or use it for, you know, actual communicate private
communication. This is just to show you
kind of the basics of how to do things. And also
I love the fact that I can actually use
these examples to quickly prototype and
new features that are going to come into kid and move some of the feet functionality
back into it. Anyway all that to say, you know,
very early days right now.
So, let's see what we're
going to build.
so
Kitten, so for first
of all, if you want to follow along if you want to install it,
let's go with the installation.
Um, you can either clone this
repository and run dots
forward slash install. You will
need node.js for that. You can do that.
You can do that right now if you want to follow along if you
don't have no JS installed
or if you want to if you trust that the
installation script that you get from code Burke is the
one that I have here, which you can
take a look at and if you
trust that you trust piping into
your shell then you can
install it via wget and
curl as well. So let's just do
that here. I've already got installed, but I can install it
again and it will just install the latest version from
From the repository over what I have installed locally,
so it'll be just like what you're doing. So, let's
bring up my terminal
here.
And I'm just going to paste that so I'll just use wget. You
could use Curl as well. So it says
installing kitten web install delay detected blah blah blah.
Let's take a look at what happened installing. Okay,
it will if it
finds if you're on Linux, there's this
gorgeous security theater. That's like
A remnant of the Mainframe era things
think sometimes change slowly in the Linux
world called privileged ports, which
is great when you were on mainframe computers and that
was a trust model. It's actually almost an anti-security feature
these days. No other major operating
system. Has it Mac OS removed it for example a few
years ago, but we're stuck with it for now, but it
means that we can't bind to Ports under
a certain number so we
can't bind to 80 and 443 which the two that we're interested
in in web development for testing
locally. So Keith, you know trying to keep your local test
environment as close to what you're going to deploy with. It's
always a great idea and that's something that kitten really
adheres to that's why you test over https locally as
well. That's all. Yeah just done for you don't have to worry about it.
Anyway, it will actually set that
on your computer. It will lower the
privilege report so you can actually buy into 80 and 443.
And again that does not put you at risk
because you are not automate frame.
All right. I hope I mean, I don't know. If you are then don't
do this do not do not run this on a
Mainframe computer from the 1960s big security
hole for those. All right. So anyway, and
we can start using kitten. So what
we're gonna build today is a peer-to-peer end-to-end
encrypted chat using
kids.
so if we go back to the kitten
website
and if you look down there.
You'll find that there is
a getting started.
A guy does not even a guy. It's actually tutorials. So it
takes you through, you know, very very
basics of things. Like how do we just create an HTML file?
And then run that and then how do we you know
count kittens? I'm not gonna go through
all this today. You can you can look through it and you should
as well if you're interested in kitten you should look through it and really
kind of see you know, what?
How it works and it's assumptions Etc
because it's quite different to what you might be used to but where
I'm going to jump to is so there are lots of these examples
that you can see here. There's
stuffed with the fatty verse you can get posts
from my favorite from
my Macedon instance, etc.
Etc, etc. And then we get to kitten chat. So there's
a whole tutorial on it. You can also find
all of these examples if you
clone the repository, they're only the examples folder so
you can just run any of these examples. So,
you know, hey, let me
show you so let me show you just the
very basic version of what we're gonna start with and what
we're going to build on which is the persistent kitten
chat example, so to do
that, I'm going to bring back my terminal here and I've
already got Kitt
the source code of course
surprise surprise on my computer. So
if you look over here, this is the kit in the
source code. Just what you saw in that repository and we
have the examples there. Okay, since we're
going to build upon an existing example, I'm actually going to
make a demo folder.
and I'll go ahead and copy
the persisted kitten
chat example, I'll do
that recursively so it gets the the folder
and I'll put that into my demo folder
so that we can just work with a
Fresh copy of that. So now
I'm in my demo folder. There's the persisted kitten chat example
that I got and this is all it is really let
me look at how few like how few source files
there are I mean look at the sizes as well.
You can see that you know
that this is Tiny. It's it's tiny tiny
tiny. I'll show you the source code as well going forward, but just tiny
and notice what you don't see
like like where's the bill
process or the build configuration or where's
the where's all the stuff that's generated for you
when you start a new web project. We don't need any of this. We're not
doing big Tech here. We're not doing big web. We're not
working in an Enterprise, you know, so we
don't need any of that. There is no build process
with kid. All right. So, how do
we run this? Well, it's it's pretty simple. We say
kitten.
Um, and that's it. And the first
time it runs as you notice there was a like a little delay there. That's
because kitten itself has
some has a
web application and some roots that it kind
of intermixes into your applications. We'll see what all that's about later. It's
for authentication Etc. So you don't have to build them.
But just like any kid in application if there
are packages that it uses kitten automatically
runs npm install on those and again, you don't need to have
node or npm installed kitten treats. No
JS as it's runtime and it installs the version
that it needs that it wants and and
it's installs mpm
as well the version that wants so
you don't have to worry about that. It doesn't mess with your system or anything. It
just installs a binaries for your
earrings Let's see. We have some chat
comments coming in. Let's
see what the comments are.
Let's see. You don't want to let
any random user bind to commonwealthifying ports on a
server system. If you're the only user on the system. It's no problem.
Exactly and I'm the only user.
system
Harold yeah, exactly and the
thing is today these days we have personal computers.
So usually it's one person
on there. So yeah, let's
see.
People are sharing it. That's nice.
Toasterson says hello. Hi. Oh, I
pronounced it. Well, okay. That was always that
was entirely an accident.
I am glad that I did though.
Okay, perfect. Let's get rid of those.
Right. So here we are kittens running.
And so let me bring up my web
browser. Oh.
Push it over here and let's just go to https localhost.
And we see here the persistent kitten
chat example, and it's persisted.
I was already testing it clearly.
And didn't delete the database. All right, that's fine.
At least you know, it's not a lie. It is persistent. Let's
let's also open another window.
here
Let's see. Let's
There we go, and let me go to localhost there
as well. Now. This is a very traditional websocket chat,
right? What am I mean by like traditional web based web
socket chat. So here I'll
make this a roll and I'll make this also all
Notice it's centralized. So we both
go to local. So it's just being served at locals just like
the web normally is and here I'm just gonna say hey I'm
back.
And from here, I'll say that's amazing.
Wow. All
right, whatever. So there
you go. You can see it working. There's the that's
a whip socket check very traditional
very much like, you know, you go to a single
domain and lots of people go there they congregate at
centralized. You have a chat.
All right. Nothing. We haven't really seen before what we
probably haven't seen before. Let me
actually close. This is
Is how it's built in kitten?
So let's start by taking a look at this first of
all.
so
again, these are the files that are in there. So let's
take a quick look at what
those files are. So I'm just going to open up my editor. I
use Helix editor. He looks Dash editor.com if you
want to look at it, it's pretty cool. I really
enjoy it. Let's start with the
chat dot socket.
Okay, so actually you know what? You know
what no here.
Let's start even simpler. Okay. Let me
show you how a socket Works in kit. So I'm
going to make a web socket demo folder.
Okay, there's nothing in here. I've started a new project. Okay, and
I'm just going to create a file
called chat dot sockets. All right. So let's
just start from scratch just so you see there's no magic here. All
right, so let me
start my Helix editor open up that chat dot socket.
So what's a socket root in in kitten?
It's just like any other kitten Roots
so you export a default.
function
and it gets
a socket.
As its first arguments and request the
request the HTTP request that originated
it we're not going to use that. So I've just put an
underscore to indicate that we're not going to use that but
what we can do is we can listen for
the message events on there. So this
basically behind the scenes. This is
the Ws module in node.js. So if
you if you want
to look up how it works I've documented it, of
course in kitten as well, but you can mirror the
client side websockets API so
we can just say add event listener just like we would in
the browser and we want to listen for
the message event. Okay, and when
we get the message events,
We want to do something with it. What do we
want to do? Well, just for testing let's say
we want to send that message to everyone including the
person who sent it or
the node that sent it to us the client.
So all we would do is is we
would say well we need to get the message out of
there because it's on event.data.
And if here for example You're Expecting Json or
whatever then you would parse it. I will
just test it with strings and we won't even build
an interface because we're going to have an interface later. So let's
not waste time with that. So just going to test it with strings.
So I'll just get it directly and then
I will
I'm just gonna use that socket that I have and I'll
say socket all.
And I'll send that message.
Okay, so let's test
this.
So, this is our app.
and I mean, this is our app like again there is
nothing else to do in kitten you just kind of
Write the logic you want and that's it. There. Isn't
this whole kind of song and dance you have to do before it
works. So I'll just
say kitten.
And here you can see that it is
running over here. How should
we test it? I actually have a
little tool that I can use in my browser for testing
this so let's bring back the browser.
Um, and I'm just going to go and select
rested which is just this.
Plug-in for a plug-in extension for Firefox
where you can just make a requests again.
I'm not going to use that actually because I'm not thinking I'm
actually going to use the weasel
websocket weasel extension. Where's my
mind? Who knows?
Um, so let's connect to
WSS, right? Because it's secure
Local Host forward slash chat dot
socket. All right, let's open that connection. And
it says it's connecting and
the connection is ready.
And so let's send a
message. Let's say hello and send
it. Now. Look what happened we sent. Hello we got hello.
It's just a basic Echo server, right? That's that's all
it is if we open another
instance of
the weasel websocket weasel and
connect and here we say hello
again.
I'm sorry send it then notice the second
instance got hello, and we got hello again as
well because we're sending it to everyone what if we
didn't want to send it to everyone common thing that you might want to do is
to send it to everyone but the person that sent
the message right so that they don't get it especially if
you're doing that. Basically you'll send
it to everyone if you're not doing optimistic updates
on the client on the interface what
I mean, my optimistic updates somebody sends
a message and immediately it appears in their chat window that
they've sent it even before like, you know that it's been
sent and that's usually
a good thing to do because that keeps your
interface smooth and or
if you're not doing that then you would send it
to everyone and then the person would get it as well. Once it's gone
through that process of actually being processed by the server.
So let's just take a look at that very
quickly.
So I will open up another tab here
and go to that little websocket
demo thing.
Open up my editor.
And here instead of socket all let's just
say socket broadcast.
And if you say broadcast, then it will
be sent only to the people who
are
Everyone, but
the person who sent it.
also notice the connections closed here and if I
bring back my terminal
And look at the other tab.
Here just scroll up. You can see that kitten
restarted. I can
restart it because we made a change to the code, right? So
it listens for changes on the back end for the
front end on the front end. It'll actually refresh your
page as you're working on it in the
future. We might get more, you know
detailed about that how which
parts we refresh? Maybe we can maintain State Etc. So
if we say broadcast though, I'm just go back.
And here let's open our connection again,
and let's open
up our other.
Where's our other? Oh, they're on top of each other.
That's not good. Is it there we go.
Um, so that connection is open. Let's open up the others connection as
well. And now if we send hello
then we've sent hello and they've received. Hello because it's
broadcast. We haven't actually received hello as well.
So this is just the basics of how
how
let's move that out of the way how a soccer
connection Works in kit. Okay. So let
me show you what the persisted kitten chat
example looks like that we're gonna start use as
a starting point to implement the end-to-end
encrypted one.
So I'm going to go back into my terminal. I'm
first of all, let me just see if there are any questions or anything. So let's
just bring up the chat here.
Hey Rue, Rue
says Hi also are all Harold we
have servers too. That's that's good.
right
Yep, some people have joined great. No questions
great also towards
the end of this. I'll give out a studio
URL if you want to come in like and ask a question
on camera you can if you want to that's something
you want to do, right? So
let's
go back into our persistent kitten chats.
Okay, so
Again, this is what it looks like. So I'm just gonna run it first so you can
see what it looks like when it's run. So it's just it's really a
slightly more polished
version of what we just did with the chat socket and
using our you know websocket weasel. It's just got it into face on
it and it persists some messages. I'll show
you what that's about as well. So I'm just
gonna say kitten
and you can see it's running.
So again, I will bring back my web
browser. Come back web browser and I'll go
to localhost.
Oh, yeah, I showed you this. Yeah, we should we looked at
this. Okay. So this is what it looks like. And so
now this
is what happens when you discover a major
bug in kitten an hour before and you're
rushing to fix it. Anyway, my
mind is like
All right. So let me instead show you
what the code looks like.
So we saw the other sockets, right? So let's
just look at this the more involved
chat socket that we have here to begin
with.
So here you can see we've
got the same we're exporting a function just like
we did there's a socket there's a request right? And then
we've got over here
we've got we're adding an event listener just
like we did for a message when a message is coming in though this
time. We are parsing it
as
as Json over here.
We're doing some very basic validation. This is
just the basic example just to see if
the messages in the shape that we think it is.
We're removing the headers that are in
the message. This is something that is sent automatically
by htmx,
which we'll see in a second which is
a progressive enhancement on the
client side that we're using for data
exchange without losing State
and we're doing
something here which
Is unique to kitten.
We are adding the message we've received
to the messages.
Table on our database our Global database. So
every kidnap has Global access
to this object called DB which is the the
database it is a in-process JavaScript
database that
actually writes to an append only
JavaScript log, not a Json JavaScript and
it's in
process and in memory, so
that's what's happening there. If you look at
the top you'll see here that we're actually creating that
table table in this case array, right
and we can just use standard JavaScript
to interact with it. It's a proxy
and it just persists the operations
that we carry out on it. If you want to
learn more about that. You can go to codebook.org.
Forward slash small Tech forward slash jsdb, and
that is the repository for
the JavaScript database and you can
see what it's for what it's not for. It's not
for surveillance capitalists. For example, it's for
small data and you can see how you
can use it. So in kits
and you don't have to do this bit where you're opening the database
that DB is what's made available for
you, but here you can see that working with it is
just like working with it's just basically working with JavaScript objects
at db.people equals this whatever.
And if you want to see what that
looks like, actually when we
ran persisted kitten chat, you saw
over here that there's a databases folder
that we can
have a look at. So let's take a look at that databases
folder.
for every project
and domain and
Port combination that you run kitten
automatically creates a
settings folder for that with its databases. So
what we were just
looking at was
Hard to see on this screen over
here. Not sandbox. What
are we looking for? What do we have a demo?
There we go, demo persisted kitten chat, right. So
if we look at that, you can
see that the the tables are just JavaScript.
So that's kind of cool, isn't it? They're just JavaScript. That's what
I mean by a JavaScript append Only log.
Um and here are our messages. So this
has been compacted when it restarts it
compacts, but you can see the messages are just nickname and
text right and here's nickname and the text
that was sent so actually so
for example if we wanted to
let's see databases.
And what is this deployments? No,
not that one for local.
Okay. Our home are all
demo dot persistent
kitten chat localhost. Yeah, we ran that there so
if we wanted to for example
tail that let me just
go into my other tab. First of all.
and
Go to persisted kitten chat and
run it. So I'm just going to say a kitten. So we're
running that there going back into my other.
Tab and I'm just gonna say tail that
those messages right? Let's
just keep that there and then let's bring back one of the browsers.
Over here and go to localhost.
And say I don't know maybe this is Laura.
She's gonna say I'm on here today. I'm busy.
And Laura sends a message notice. What
happens this is the append Only log, right? So it
just gets added to that array. What
do we have to do for that in the
code?
Just what I showed you earlier almost nothing or we
had to do for that if I move this
here, let's just
Where else there? Okay. So if I
Show you the code again.
All we had to do.
Find the messages. Let's find the next
one. There we go was that we just pushed the
message into an array in JavaScript and
that's what
created this in the append Only
log. So that's how jsdb Works. Let's see
if there any questions or anything about that.
Who sent me a smiley? I'll take it. All right,
so no questions. That's great. All
right, so that's how the append Only log Works in
jsdb.
Kind of exit that process.
All right. So let's just keep looking at
how we built this.
Persistent chat first of all, so like I said
just like in our very basic example that we're
getting the message. We're saving it to the database.
And then we're doing a sock at all.
But here's an interesting thing.
We're sending HTML.
So, you know you might think why aren't you sending Json or
something? Well, this is HTM ax
and kitten has a native
support for htmx. What
do I mean my native support if I go to end of
this page?
over here
Oh, no. Sorry. I'll show it. I'll show it to you on the page, but
Basically kitten serves a version of
htmex and you can use it from there. If you
want to you don't have to use htmx. So
what's htmx I can hear some of you ask.
htmx
good htmx.org.
Htmx is basically a
hypertext style
system. So for
example
Here's a quick use their quick start. They're just
loading it from unpackaged.com. But
here's what you need to look at. So
you can declaratively add.
Behavior to HTML so you
can progressively enhance it in a sense with this Behavior with
these attributes. So HX post
forward slash clicked means that when this
button is clicked.
It's going to make a post request to the clicked root
here and whatever it
gets back from that it's going to swap with the outer HTML
of this element. So that's
pretty cool. And there is a websocket
extension which I'll show you in a second that we're using and the
persistent kitten chat example, and that's how
we're doing it basically.
So let's let's go
back.
over here, so
what we're the message were broadcasting to all of the clients that are
connected is this HTML this div and it's saying
to htmx swap this out of band out of
band means not just on the element that
this exists on
but on a different element. Well, which one well before
the end of the list of
messages specified by ID here
and what we're sending is
a message component.
Okay. Well, we haven't seen that yet, right which has
a message attribute, which is the message. Okay,
so
A number of things are happening here that are kittens specific notice this
HTML template string
there. So this
is built into
kitten. This is how you do templating in kitten
using just plain JavaScript and the
HTML tag template function can
is aware
of components can do components.
um, so
let's just take a look at what that message component looks
like that. Let's go to where that's reference. We're
importing message from message dot
component. Right? And if you saw this
remember, those are those are our files message dot component is one of
them. So let's go to where that's created.
Oh, sorry, it can't
because this is nowhere component is so let me just open the message component.
And this is the message component. It's actually pretty simple.
It's just again.
a bit of HTML
A list item with the message nickname in a strong
tag and then the message dot text. That's it.
That is what we are returning.
So that's the message component and that's all there is to that.
So you can see here that we're just
sending that message to all the response to all
the recipients and then we're just logging the message
that we got and how many recipients we sent it two. That's
it. The basic validation we did
was just to validate the you know, the two things are
strings. It's not even like it's the can't even call validation, but
that's it. So that's
our chat socket in in the
in this in this example. So what about
the interface the fun bit?
Well, you can see that well for one thing
in kitten, you've probably noticed we use extensions
a lot to me to to
separate different types of files. So dot
socket is a websocket. That's how kit knows
to send it the socket as the
first argument here. We have a page a
page the client side page
web page and all of
these are just JavaScript though. Okay. So
the way kitten works is it uses ecmascript
module loaders to just load all
this JavaScript one of the cool things with it just being
JavaScript is we don't need a huge amount of
tooling notice that I have syntax highlighting here notice that
I have. Oh, I
don't know. Let me go to this markup and
go to wherever it's referenced. So I have language intelligence right
I can go to where that's where that's
reference in my editor. So I have
all these things because in order to get the full
tooling
All I have to do is say hey Helix
editor a DOT page file. That's
a Javascript file dot socket is
a Javascript file and similarly with
my ecmascript loaders and kidnets so simple because
I just have to say treat these as JavaScript
files and so I'm
not even doing any massaging of
what I'm loading in yet for anything in kitchen if there
are markdown if I you know decide to put mark down Roots
then maybe then I will actually use the full loader system
and actually, you know translate mark down into
something but I don't even need to do that. And if you've
seen other Frameworks platforms
out there like
Swelled kit for example or swelled.
Take a look at their tooling like the amount of
work and effort that's gone into building the vs code
extensions and this and that and whatever. Wow.
It's it's it's complex stuff. Thankfully
we just kind of
skip over all of that because of
some of the decisions that have been made in in the original
design initial design. So here we are this is the
index page. So let's take a look at what a page is in kitten.
So here we're loading some Styles in
dot Styles index.styles. So if
we look at that, that's just again JavaScript that's
exporting a CSS tag template.
This is just CSS, right? That's
what we're loading in and then
we have our message component as well. Remember the chat dot
socket is on the server. The index.page is
is being run
on the server but creating content for
the on the client.
Um, so then we also have a
status indicator component. We'll look at that later.
And then here we're again making sure
that we have our messages table or initializing
it if it's if it doesn't exist, that's a
common pattern.
And here we just export another function
calling it root called whatever you like. We're
not using the request of the response clearly.
And we have some
markup that we're creating.
So here's the persistent kitten shot the title.
We are instantiating the status indicator. That's where you saw where it
was saying status online offline Etc. So we
can take a quick look at that. So if I go
over here
This is a status indicator component and
you can see that.
It's got a couple of interesting things that it's doing.
so here
this x data brings us to
the second framework that kitten supports
natively and that's Alpine Js.
So htmx is really great for
doing what traditionally be
like Ajax style calls
and for responding to
them in a declarative manner for doing web sockets with
the web socket extension Etc. So for
data exchange, it's really owned for that. What about
more custom client
site behavior in a declarative manner, that's
where Alpine JS. It's tiny
little framework comes in. So you
can use kitten just it's basic HTML CSS JavaScript
and then you can enhance it if you need to
with
Xh GM sorry with with htmx
and with alpine.js.
If you're not familiar with alpinejs.
Just go to alpine.js.dev.
And it is so small. You can
just you can get started with it really really
quickly. Again. They're loading it from CDN content
delivery Network and then here's their
example, so you
create a model a data model over here.
So in this case an
object with a property called open, that's a Boolean that's false
and inside of that so you can access that
model inside of that note now here it
says button at click. So this is
an event handler open equals true and
there's a span with
which is only shown the content is
only shown when open is true.
so
that's the sort of thing you can do with alpine.js I
think there is actually a question. I'm just going to look at the comments.
Sorry, what did I do? There we
go. No, that is not what I wanted to do. There we
go. That's a bit better.
All right done. Yes. The
green screen is not exactly perfect.
I need to.
Tweak it.
That messages not component might be slightly difficult
3. Yeah. Thank you so much for that heads up. Yep.
Let's see.
Any particular reason why you went with htmx as opposed
to any mainstream front-end framework or Library?
Just curious since the project is so already so
Jazz heavy. Yeah, I I like to think of
the project as JS Lite because like
yeah, there are heavy Frameworks
out there. Definitely that we could have used and I
was looking I was playing a lot with swells and
with swelt kid Etc. They're designed with a
very different mindset their design for big Tech. They're
designed for Enterprise. They're designed for serverless. We
are literally a server and I
like small things.
Which may or may not be come across and both
htmx and Alpine I
think are really just the right size for what they do.
They work really well together as well
and you don't have to use yet. Thanks
sarcasi. You don't
have to use them either like they're tiny
and kitten supports it and what do
I mean by supports it? So let me just show you what I mean
by kitten support sets. So if we let's get
the web browser out of the way.
Let's look at the page. Okay, sorry.
just
over here. Let's look at the page at the
end of the page. So I'm just going to go to the end of it.
Am I in the page now? I'm in the status indicator components. Let's go
to the previous one. Let's go to the end of the page.
Notice we're creating the markup right this whole markup that
I was showing you.
And then notice here.
we're returning from this route an object
that has the markup the Styles and then
it says uses htmx htmx
web socket and alpine.js so
when
kitten sees this
It ensures that
those are imported.
It serves them and ensures
that they're imported on your page. You don't
have to do this. You can do it manually. You could do it
just like you so I can get it from unpackage if you want or you
can use any other framework. So it doesn't tie you into anything.
They're small enough. I think they're useful enough
that there is native support for them.
But feel free not to
use them and also, you know, feel free to use anything else. It doesn't
tie you it to anything like that.
So let's just keep looking at
the page.
Oh, sorry. We were looking at the status indicator, right? Let's go back
there. So let's go to definition open that
up.
So here's our status indicator. So this is
all a combination of Alpine Js.
And htmx so it's all declarative. What
we're doing here is we're creating an X.
We're creating a model an Alpine JS this
you don't really even need to
to use you
could just write this like that that little
JS tack template just gives me better syntax highlighting
and I kind of like that. It's semantics so
I use it. You don't have to
um
but we're basically setting a status property to initializing and
that
Status property is what the text
of the node will be set to notice. I've
already I've also duplicated here
in case the JavaScript doesn't load or anything. You
know, you just you know, that something's going wrong just sticks
at that. It's not empty.
Um, so then we're listening
for htmexes websocket connecting
event on the window. Okay, because
it's actually
It we are a component. So we
were listening it globally.
And we're just sending the status to connecting if it's connecting when it's
open. We're saying it's online when it's closed. We're saying it's
offline and that's it
in terms of the class because we want to
change the color of it. We're also doing a if
status is equal to online then set the
class to online status Offline that it's offline and there
you just see the the colors for those so
that's our status indicator component.
And under that we have the main
diff where stuff.
happens so
there we're specifying that we're using the
websocket extension for htmx. And we
wanted to connect to the chat dot socket that we saw earlier. We're
also creating an alpine.js model
that just has a property called
showplaceholder true.
And that showplaceholder true.
Is this bit of HTML?
Initially before anything comes in we want
this no messages yet. Why not send one
to to display? So that's that's what that's for.
And then here we have an unordered
list.
And that's the messages list.
and when the htmx load events occurs
We're saying showplacehold. We're setting showplaceholder to
false.
And we are scrolling to
the bottom of that message list whenever
something loads.
And then here's the body of it.
so
let's take a look at this. Can I get the whole thing there great. So
this is and if he
and immediately invoked
function expression where we're
calling this function
with the messages in the database.
So this is how the initial the persistent messages that
we're already in there are shown and we're
saying, you know, if messages length is
zero then write out
this placeholder.
That we have otherwise map
the messages to a
message component per message. Right?
So we're creating a message component for message. So let's
take a look at that message component
again. So let's go where that's
defined.
And there and remember it was just this right we
were using this remember in the chat socket. That's
what we're returning as well. So that's pretty cool. We're returning the
same little snippet HTML.
So let's close that and yeah.
All right, so, that's our page root.
What else do we have? We have some we
have this index.js. This is just
some fixes that fixes the interface on mobile
tries to detect that it's mobile and then apply
a few browser fixes to
it and also enables htmx logger. You could
just delete that file and
It would still be fully functional. It's just some little tiny improvements.
You don't have to worry about that really
that's not important and then we have the
index dot Styles which I showed earlier. So that is it. That is
the whole persisted chat. Right? And I
think that's also been a good introduction to
kind of how some of the things work and in kitten
but where we really want to
get to is an end to end encrypted periods appear thing in
the next 10 minutes according to our
regular schedule.
See how that works. All right. Let me see if there any any questions
things always take longer than
you think they're going to yes.
It's true. Our causes
says yeah.
All right. Awesome. Yeah, no questions. All
right, let's just let's go ahead then. So this
is what we have to begin with. But remember that the persistent chat
example was entirely open as well. It was entirely public. So
let's start by implementing some authentication
because when we have our intend encrypted
chat, we want it to be, you know you to be the only
person who can log into it, right and thankfully kitten has
authentication baked in. Oh, right. See
that looks like all right.
So here we are. Let's get back to the terminal.
And let me make this terminal as large
as it can be on my tiny little presenter display.
All right, so
the first thing we're going to do is make
sure that
these files that you see over here can only be accessed if
you're authenticated. All right, so let's
just start with that. How do we do that? We have to write a lot
of code. Not really. So what I'm
gonna do is I'm going to create a root called private. I could have called
this move the actual name of the root doesn't matter. But what
does matter is I'm just gonna add a little
lock to the end of it.
Okay, I'll walk Emoji, huh?
All right, and then what I'm going to do is I
am going to take
these files and I'm going
to put it put them inside my private folder
that I should I just
showed you using it nice little terminal file
manager called LF.
All right. So now if we look at it, we just
have this if we look under there there's the private
folder and the files. So what does
that mean? So now if I run this
And I bring up my browser. Where's my
browser? There we go. And I go to localhost. I'll get
a 404 kitten poor little 404
kitten.
That's because there's nothing in the root right? However
if I go to
private
then I get a sign in. Ooh a kitten
sign in how nice is that? It's asking for our our
secret now when we first
started it ages ago. It actually
gave us a secret. We didn't
know it down bad us.
but
not to worry.
We could either go in and delete the database for this
project right now and it'll be generated. We
don't have to even delete the whole database we can delete the internal
database to underscore underscore kitten if you wanted to or
remember that the settings are
generated per domain per Port per
file path of project when you're
testing locally to make it very easy for you to test locally.
So what we can do which
is much simpler is just to go in there and just
to start this at a
different domain.
So while we're testing it, so let's do that. So
I'm just going to go over here and say so
I am in the demo folder
yet. Okay, so I'm just going to say kitten I'm
gonna pass domain equals.
I'll say Place one Local Host.
So kitten has support
for four aliases to
localhost subdomain aliases localhost
Place one dot localhost place two dot localhost
you get the idea up to place four and this
is really useful when testing peer-to-peer web apps locally for
one of the reasons is of
course, they have to be on different ports as well. But kitten
uses cookies for authentication and
cookies are not isolated purport
their isolated for domain. So
when testing locally you actually have to use different domains
or else the sessions will get confused and
Each data between them. So because
of that what we can
do now is we can start actually start
it don't we let's get the terminal back.
So what I'll do here is say
kitten - domain Place One Dot localhost,
and that should do
it.
There we go. And now it's generating a new secret. Okay.
So this time this is our secret you
might be like, what the f***? Yes.
It is Emoji. Um,
why is it Emoji? It cannot be Emoji.
It's never been Emoji before. How can it
be Emoji Now the secrets have never been Emoji in
the past. They cannot be emoji.
They are Emoji now. So what is this? I
love that every time I do
something a little different. I think one of the first things that you get is
like you can't do that. You can't that's not how
we do things around here. Oh my gosh
God. What's the world coming to?
So it's a truly
in the 21st century. I don't know whether that's a good thing or not, man.
But yeah.
um
Yeah, so what is the Emoji that is actually your
ed25519 private
key encoded into
emoji.
That's what it is why Emoji just because it looks good.
No because you can't write that down and if
it was if it was a generated password, I
know what some of you would do the get your little sticky notes and
you'd write it down on your sticky notes and you paste on your monitor and
then there's the security f***** right? So
instead what you got to do is you have to select it
and put it in your password manager like you should
with all of your password, so I'm going to copy that.
And then I'll my web browser
here. Just gonna do that off screen in
case I need to enter my
password
and do it again
because I answered it incorrectly because of course and now
I can bring it on screen.
Go away.
All right, so
and what I'm going to do there is I'm actually going
to go to 443 now.
Actually, I'll add a new
item. I'll add a new item.
And I'll say password.
Thought that that I'm using one password for this and here.
I'll say a place one
Local Host.
persistent chat
and I'll add this.
And save it, okay.
So now if I come over here.
Let's see. Oh not a local host.
I need to actually go to it from Place one Local Host.
Right? So there we are Place one Local Host and
I can just enter that password in and
hey.
Okay did not like it.
Let's see. It just is that the wrong one desktop antenna
can nope. That's the wrong one has it not
synced to die not save it. So many things
might have happened.
Oh, you know what? Here we go. Let's just
I'll just copy and paste it from here, but you get the idea. Okay, maybe
didn't save it.
There we go. And it just goes to
settings right now from sign
in if I'd actually gone and in
your settings you can actually see your identity. Your SSH Keys
generated a phpgp key is generated for you. You
can see your secret there. This is very
basic right now. I haven't really had a chance to work on with that will look like
but if we go to private now, we can access the persisted
kitten chat
over here.
Um, some things are not working. No.
And that's because our URLs have changed as well.
So whereas so we can't connect and so
for wondering why that is then we probably
have to look in our index page and we'll
see that where it's trying to
connect to is should be now private chat.
Right? So if we change that
then it should it should
work. Let me actually just run it here and keep it running
as well. So it automatically updates
when we're changing things. So now we've
changed it. So it's private chat.
and let me
Where's our? Oh gosh, okay.
I should have really saved that.
Password here. You know what I'll just I'll use
I use my text editor as a very cheap password manager
that you should never just for
this just for this.
There we go.
And then I can just go back to the editor here.
All right, let's paste it from that.
Is it?
Oh why my Local Host?
That's odd.
Oh, no. Sorry. It is Place one out of localhost. Yeah.
Okay.
No, it's going on.
What's it doing?
Place one not localhost
Well, it might not running it in the yeah.
What did wrong not do he didn't run it at
the main equals Place one?
localhost City
Now we didn't.
All right, did that work?
No, because he can't spell domain.
It's not the mine. It's the main.
Now, it's Place one Local Host. Yay little
victories. All right, and then
we can sign me.
Do not like you.
All right, come on.
There we go. They can sign in and it would
normally just forward to hear because I was there but I refresh the
page and that's why I didn't anyway. All right,
cool. Let's get this out of the way.
Slow but sure progress. In fact, let's get this
up. Hi. All right, so
What are we doing again? All right. Now it's authenticated right?
Let me see if there any questions
anyone who
wants to.
Tell me that I'm being sacrilegious.
Holy pierogi. Hey, I'll take
it. Oh, she was just to make secret more cute and
less scary. But the idea that they aren't writable is great. Nice. It's
not printable either. It's just
too much color for anyone. Yeah. I know. I mean
people will find a way right like they will they'll print
it. I know this. I know it's
Happen but yeah, cool.
All right. Well that was the idea and you know,
it doesn't hurt that it's also cute.
Doesn't hurt. Alright, so we have
authentication still a
centralized app, but authentication and let's
see if this works now testing.
new one and go to
Place one Local Host
s privates
Yeah, then also are all.
Yay. All right, so
that's working but
Is it still centralized? It's not peer-to-peer and but
at least not anyone
can join it. That's kind of cool. All right.
So how do we make it peer-to-peer?
well
for one thing it's not just it's not going to be a nickname and a
message anymore. Right? We need a
domain to send the message to so they're
gonna be two domains. At least I'm gonna be on my domain
you're gonna be on your domain and then we'll have the message and the
message those not going to be in plain text.
It's going to be
encrypted
Right, so I was planning.
On actually going step-by-step in doing that,
but it's already 6PM. So instead
let me take you through the example that
exists. It's not a lot
of code to look through.
so
let me take you through it in a
from where we are right now what we would do. Okay, so
Let's bring up our terminal.
And I'm going to go to kitten examples.
End-to-end kitten chats anything running
here. Let's just click that
editor as well.
Okay, and let me
just start my editor here.
To begin with now look at what there is here different
to what we have right all this
is the same. This is just what we did. We
implemented authentication, okay?
Now there are three extra files here. The index.html
is just the basic is is just
very very basic. It just links to the
private root because like if you get there and
you're not it, you're not authenticated. You don't know you want to go directly there.
That's it's nothing. So that's just that's just for sure.
um
However, so we're now we have a
peer-to-peer application and it's end-to-end encrypted.
So for the peer-to-peer, what we need to do is deliver
messages to another domain right and
have other domains be able to deliver messages
to us when we get those messages
from another domain. We need to be
able to let the rest of the application know basically the chat socket.
We need to let it know that a new messages arrived right
from another domain. So we need
an event emitter of some sort. That's what we create in.
The main dot script main dot script is in JavaScript,
but it is a special file. That is
run when
your app first starts. So it's run by kitten when
you're at first starts. So if you want to have something Global that's a
good place to initialize it and that's exactly what we
need for our emitter our events amateur for
the remote messages and that's literally all there is
there.
We import event emitter from node events,
and we just expose a global remote message
emitter. That's it. That's all there
is. Okay, and so let's
take a look again at the last remaining thing,
which is our inbox.
so this is how
we receive messages it's a post-root and
that's why if you look at
the
Name of the file. It's dot post so this
will get called when a post request comes in
to slash inbox. Okay, so let's
take a look at it.
all we're doing really
is we're getting the message as a request body. We're
expecting it in Json.
And kittens automatically doing that giving you
Json there.
We're just logging it out.
And then we're asking that remote message emitter that we
created emit a message event with the message and then
we're just sending a very basic kind of because tutorials example,
just an okay response.
That's it.
So if you call inbox and notice,
it's not an authenticated route because different domains
should be able to call it. If you
call inbox and you send a
Json format message that gets a minute now in an
actual real world application. You would be doing a lot
of validation here right to make sure that the message
was what you expect. It didn't contain anything. You didn't expect Etc
blah blah blah. We're not doing any of that in this simple
example, right? So let's get back to
sorry.
um
Looking at what's changed now? These are
the same files but something's changed because now
it's going to be an end to end encrypted message chat,
right? So we said that
when we get a message it gets broadcast.
And that the chat socket handles that
so we'll take a look at that.
But first of all, let's just look at the let's go from the UI In from
from the interface in
So let's look at what's changed in the page?
This is all the same. This is all the same.
The names changed status indicator is the same.
Here's that div, right?
And here's what's different.
So
Well tooth no we'd actually
change it to private. So this is the only thing that's different.
We're listening using alpine.js to the htmx colon
ws-config -
send event.
Where preventing?
We're preventing the default action on that via DOT
prevent. So the message is not sent.
and instead
A function that we've declared somewhere called encrypt
message gets called.
so
that's the main difference there. We're not
sending the message right away. We are encrypting it remember for
end-to-end encryption. The encryption has to occur
in a space that you control. You. Don't that's not
the server. That's the client for you, right? That's where
your secret is.
You also have to understand the security properties
of what you're building. So kitten
is a web server. This
is a web app.
So this anything you build here. So
this this little example of course don't use it anywhere. But once I
build some of this stuff in a
much more production ready way in kitten itself,
and it can be used by a kitten applications.
It still doesn't change the fact that there are certain things that
it won't protect you against.
so
we're using https already to speak between
kitten instances between these domains.
So your messages
are encrypted in transit anyway.
And to an encryption really is useful for
encryption at rest, right? So on
the server they're being stored on the server. So what
does that protect you against? Well, let's say that this
is hosted at some VPS provider
and some admin there, you know
likes to look around they have access to your server. They
look around they don't see much
right now if they
have the time and the inclination
to actually run something else on your server that
you then connect to while you're authenticated and
then they get your secret.
That's what doesn't protect you against so you
have to understand like what the security properties of
any system is web-based system
basically means that if a different
piece of code is run on the server at
any point, it is just one request and yours
your key could
be compromised that way your secret could be compromised. So
what kind of
a threat model with this kind of
entail in terms of like who would be
at risk of this? I'd say someone who's being targeted directly
for surveillance someone.
that you know, it's a state-level actor could maybe
get access to
to a VPS provider
remember also though. These are going to be spread out
on different providers. So, you know
that actually makes it less likely
that that's going to happen unless they
whoever is after you manages to
you know hack.
Has all of these ways to
hack different providers all around the world. So that's
that's a bit where it's better than a centralized system. But
at the same time, you know, your VPS
provider or whoever else could be easier
to hack you could be running this on a tiny little single board computer
attached to reuter at home in which case if the physical security
of your home is compromised Etc. So, you
know as a good rule of thumb I don't
use this if you're
doing like Edward Snowden stuff.
for a very long time if ever but for
everyone else the whole idea with encryption
in general is to raise the cost
of surveillance to raise the efforts of surveillance
so that hopefully it's only
used when it's really really necessary in a targeted
way and again,
You know that that whether or not that's a
good thing depends on how much you trust the people doing this surveillance, but
that's way better to master surveillance. And
that's really where you know encryption is useful for raising
the cost of that. So understand that nothing is is secure
100% You have to understand
if it's secure enough for your needs. So wow that
was quite a disclaimer, but I think it's important to understand that, you know,
because like and if anyone tells you this is entirely secure
they're bullshiting you.
Right the same issue that exists with web
applications exists with Native applications
as well. Like you know, it only takes one
update of an app in order to compromise your security if
that update has been compromised either through a supply
chain attack or you know, the provider or
the App Store being hacked or the
binary being hacked if it's a distribution, you're not getting from an app
store Etc. You know, if it's
a centralized system you have to actually trust that the
people running your messaging application are
not interfering with the signaling that they're not adding another
and to your end and encryption chat
that you're having on the notes
to you. So, you know again,
I think the great takeaway from that is from this
is nothing is secure. Is it secure enough?
Do you think for your needs and how do we like raise
the cost?
Of of surveillance anyway.
So all that to say that's what's changed here.
If we look down here nothing else
has changed my goodness.
Look at that.
Aha, the form has changed a little bit. We have
a two instead of a nickname and that's a domain and
here we have plain text.
Is the name of our form field just to make it clear that
this is not something we should be sending unencrypted as
the plaintext.
That's it, though. Nothing's changed on the page. We're
even using the same message component. But is
it the same message component? We'll take
a look at that in a second. First of all, let's look at the other files.
What's changed in our chat thought socket?
So in the chat thought socket.
We some things have changed.
a little bit
So let's take a look at what that is.
so
here's where we're
creating our sockets root.
And it looks like we've refactored descending the
saving and the broadcasting of the message into its
own anonymous.
A closure here. And the
reason we did that is because we need to call it from two different places
now, right this is doing exactly what it did last time.
But we need to call it from two different places where well
once when a remote message comes
in right? So we're creating a remote message
Handler.
And listening for that remote message and emitter message
event. When a remote message comes in. We validate
the message and then we save and broadcast it locally. So
a message come in. So we've broadcast it to
any local clients that are
that are there and then we do
a little bit of housekeeping here if the socket goes
away. We also turn off that message emitter.
And then here we just
have the socket message event that we're
handling as well and we do it there.
So there we get it. We just
what we're doing before. We just call that refactored method.
And then here's what's different. We need to deliver the
message. So this is a local message.
So we need to deliver it to the remote and here we're just
basically string creating a
Json string of the
message creating a post request here.
and
sending it to the inbox of the remote.
The remote domain the
remote small web domain. That's
it. The rest of it is the same.
And then so let's take
a look then.
At this message component because that's changed.
It's still a list item. It's still sending you
HTML, but notice
that we've added some new alpine.js
handlers for clients side
processing.
Remember this is sent from the chat socket as well. So when
this list item is loaded.
We have this.
We have this message text property that's sent to
the that is set. Sorry to decipher text.
So that is the encrypted text because the server does not have
the unencrypted the plaintext right? So that's
set to decide for text.
That's all we have on the server.
And when this note is initialized we're
saying okay decrypt the message.
And we're sending the cipher. We're giving it a deciphertext the message from
and the message to
Right and then it just here displays message
from message to and here dynamically binds
the contents of
the message to the message text property in
our in our
model up here. So that's
it.
A list item with encrypted text loads into
the client and then when it loads it gets
decrypted and displayed that way so
quite elegant. So let's take a
look now finally at what's actually
doing the encryption and the decryption.
Um, and so I'm going to open up
the the index.js
file.
Remember previously. This was just used to do some that's still
here mobile interface improvements. Right like
we're doing this stuff but we've added
about 30 lines of code to do the encryption and the
decryption. So, how does that work?
well for one thing it's 30 lines of code because
Kitten provides a cryptography API, right?
So that's what we are
importing here encrypt message
for domain and decrypt message from domain. All
right, so then we're creating an
encrypt message method.
And this is the one that's called. If you remember from the
page before messages sent remember,
we're preventing that event and through htmx and calling encrypt
message.
So we get the parameters from event
detail parameters.
We get our private key from local storage. It's
our secret that was added there
by kitten when you signed in.
And then we call encrypt message for
domain with the plaintext that we got from the form our private
key and the domain
that we got from the form, right?
And then what we do is when we
got the encrypted message, we manually use
the socket wrapper that sent to us.
And it's sent function to create a
Json message that
we send to.
To that to that to our
chat socket.
And when it gets it remember it delivers
it to the remote and we saw that.
So with our ciphertext the from we're just using the window location
host and to parameters domain, okay?
And decryption is similar.
But even simpler here, we're just saying if it's from us
then we need to still get there public key.
So we flip that I could write
that code a bit more.
The intent could be clear there and then
we get our secret and we say decrypt message from
domain with the ciphertext our private key and the
domain that we want to get the public key
from now, let's go one step further and
look at these encrypt message
for domain and decrypt message for domain functions. I
don't think I'm going to be able to do that from here. Can I
actually go to definition from here? No because it's in there
so I can show you that.
in kitten proper
so if we go to the crypto
Library crypto API
and let's look at what we have here. We have decrypt
message from domain and we have where's encrypt
message for domain?
Should be somewhere anyway.
Let's look at there's encrypt message for domain and here's decrypt
message for domain again, quite simple. Both of
them are and getting a shared secret.
So what's happening here cryptographically is we
are using it diffie-hellman key exchange.
And so we
are calculating a shared secret using
our private key and their public key how
we getting the public key their private key. I'm sorry.
They're public key what we're doing.
Is using another property
of kitten.
Which is that if you go to any kitten site
and you go to forward slash ID
and kitten is running which is
really important. That kitten is running. So let's go
over here. Go to
end
Okay, and let's just make sure kitten
is running here.
Okay, so when kitten is running
let's go back here.
If you go to forward slash ID.
you will get
that notes at 25519 public
key. All right, and so
that
Is how we get the public key of the
other node?
So, let me just go back to my terminal.
Alright, I'm just going to note this down as well because
this is going to be useful for us when we actually
see it running.
So I'll just note that down in my hastily made
password manager / textpad.
Okay done.
All right.
So let's go back here.
So we're getting a shared Secret.
And then we're encrypting using that
shared secret and returning the ink
for message and we're doing basically the reverse of that in decryption.
So shared secret for domain is doing the heavy lifting.
If we look at that.
We basically have an object that keeps our
shared secrets.
For different domains just for caching. So we don't have to get the
public key all the time every time
and then we are getting their
public key response with a fetch call and
then basically converting our
Emoji string to a secret
to a wide array that we can use and then
we're just using get shared secret get shared
secret itself is part of
the Noble at 25519 library
by Paul Miller tiny cryptographic Library,
so I didn't roll my own encryption, which is
very important. Don't do that. There are you know
auditable libraries like this very very
small multiple libraries that you can use. So
that's where
That yes, so that's it. Really we
will go to any more detail on that. You can
look into the noble Library Etc if you
want more details on that and
let me just this.
Okay, so
let me just see where my that was kitten. Okay,
right.
So the end to end encrypted charts example,
we're back there and I think we've covered everything we basically
Yeah, we've covered everything. These are the same the message
component. We saw status indicator hasn't changed to check socket.
We saw we saw that the encrypt message in secret messenger
there. We saw the page. That's it. So we know how
old this is. So what does it look like
when we run it? Let's do that.
So we're already running a place one Local Host.
That's great. Let's keep that there.
I'm going to run another
one. So let me go
to end and I'll say
kitten domain equals. Let's
do place two local hosts, but
I also have to specify a different port so I'll
say Port 444. Okay, so that's generating a
secret as well.
so I'll just note that secret down in my
little whoa. What is that
escape? That's not what I wanted to do.
Is not what I wanted to do, there we go. All right, so
Let's get rid of this one. We don't need it anymore. This is our place one. This is
our place to Secrets. Okay?
And we'll keep that there. So now
what I'm going to do is open to web browsers again, it's all
about the two web browsers.
And one I'm going to go to place one Local Host.
And I'll sign in with my
first secret how many
things can go wrong right now? Yay. Okay
and 10 encrypted kitten
chat. It's online no messages yet. Perfect.
Now we'll open up another web
browser window.
Over here and we'll go to place two dot
localhost. Colon. 444
and actually to the private route there so that helped there and
I'm going to use my
very basic password manager here to
enter my password there. All right, let's get rid of
the passwords.
Huh? So we have two two instances
of our application running.
So let's try and send something. So I'm going to try and send the message
to place two dot localhost 444 now normally
this would be a domain so you'd be saying I want to send it to a roll because
that's where it's running right or I want to send it to Laura calbag.com. We're
testing it locally. Okay,
so we're gonna say place to thought localhost
444
And as my message, I put two dots yeah as I
message. I'm going to say hello.
I'm gonna send it.
And look it's command did you see that? There was
a little flash as well there. Well, it was being oh
go away. What are you don't go away too much.
I think you're the server. There's a little Flash
and it's decrypted. So that's pretty
good. So let's just do the reverse from here to place
one dot localhost.
It works.
woot
and there we go. Hey, it works woot and
come in over there. So if we
of course look at the
Let's see where my my terminal.
There we go. I think.
Think we can shut it down. Now. You've seen it working. Let me
just open one terminal window. It's easier.
There we go.
If we look at the databases again, so let
me just look at databases.
And this is projects kitten. Let's
see and and decrypted. Okay,
so let's look at the one for our antenna kitten.
Let's see. Which one this is. Wait. Yeah, and there we
go. You can see that what's here? Sorry for
this. It's I think my green screen
is not holding up. Let me just see if I can change the key
Edge and make it a bit better.
Nope, that's not helping.
Maybe the background to do no, that's
not healthy the foreground. Ah, there we
go. That's a bit better.
No, is it better? I don't know. It's gotten rid of.
A lot of the color there, though.
Maybe the key no, no.
Real time green screening here people. It's amazing.
Things you get from these streams like okay. Let's
screw it. I think we're just gonna have to live with a
little bit of
you know us that was whoa. Oh, that's
my that's that's my switcher. That's what I was using I
go away.
Go away. It's all going wrong. Anyway, so here you
can see that it's a ciphertext that's being
saved in the database.
And there you go and to end encrypted to
peer to peer small web application basic
example, but this is
the direction that it is going. It's
so nice to finally be able to work on stuff
like this is a lot to do there's a lot I need to do you saw
that remote message emitter, you saw the inbox. Those
are going to be moved in but implemented in
a production ready manner in kids
in itself. So any kidnap will be able to use those. There's
also going to be
For public messages, you'll be able to make websocket connections
and get public messages that
way as well between notes for following basic.
That's how following is going to work. So and these are slowly I'm
adding these slowly to an emergent
sort of a small web protocol. So
let me see if there are any comments done.
Um our case says love it kind of scared of all the
corner cases. I'm sure I am too. I know
Corner case of the bane of Matrix element, but at least your use case of some
well, that's the thing right? It's about simplicity. So,
you know, if there is if there
is an issue, it's gonna be very apparent.
It's gonna be very clear because like there's so
little code and that way we can actually
you know, and that's true for security in general as well. The less
code the better. So Ben at
Mastodon dot bits -unt
- baume.org says so
my client connects to the other party's kitten to
communicate. Yeah, so to the other party's app made with
kitten if the app is a peer-to-peer app, like we just created
so part of what I'm trying to do is kind
of share every piece of what I'm building. So
all the way to you know, what does the
automatic Local Host certificates handling the
automatic, you know, let's encrypt certificate
handling. Those are all different packages. You can use those you
can use kitten to build different apps.
So I'm going to be using kitten to build my kind
of app for being public and private on
the web which I'll probably call someone like place and
people will be able to one place where you'll
be able to do like private chats like this and then post public
things and people will be able to follow you but other people
will be able to build other apps.
And I think so. That's what's interesting to me
keeping a very very simple protocol very extensible protocol
at its heart a very simple way to be private
a very simple way to be public for people to be
able to follow your public posts, the fundamental assumption
that all of it ties down to is that we will all run
our own servers and then of course the question is how do
we make that process as simple as possible? And that's where domain comes
into it which is a hosting tool that
I'm building so that anyone can become a small web host
and host people on vps's with a
30 second 40 second process for actually getting
set up that requires. No technical knowledge.
That's itself being written in kitten. And now that I've gotten some
of these things out of the way. I'm going to focus on that again.
Does that mean every kidnap needs a different address Port every
kidnap when deployed is meant to be deployed at
a different domain?
So yeah, so the the level
where I see them being deployed is a very small
vps's or tiny little
tiny little single board
computers at home.
If people want, you know more control over it.
So I hope that makes sense.
But that's the model.
So we're going with like radical Simplicity. We're going
with because I think that's our advantage as
well. That's you know.
Complexity is Big text Advantage because
of the barrier of Entry.
Both monetarily and in terms of effort Etc.
So we're the opposite of
big Tech with the opposite of big web. So we Embrace simplicity.
And oh cool. Yes makes total sense to
me. Sounds great. Awesome.
Folks I'm not even going to give out the studio URL because
at this point it's been an hour and a half
and I hope
you found it interesting. I hope you found it useful. This is very
new like I got this example working this week like two
days ago or something and so
kitten is very rapidly evolving.
full small web protocol spec when when
No, you can our Causeway or arcades are
causing you can you can build stuff
with it now just play with it. If you
want to the full spec. I don't
know. It's not going to be a very full spec.
It's an evolve. It's going to be an evolving spec like the spec right
now has for example slash ID for getting your public key
from there.
It's gonna stay very
small. So it's going
to evolve. I want to see it evolve with usage.
I want the core spec to stay as small as
possible to be as extensible as possible. I want
people to create their own vocabularies. I want the
people who use this to create the semantics using it
and so it's it's not like it's
not going to be like an activity Pub style thing where it's this huge
Speck and you have to change the spec every time
you want to do something different with it. Now, it's the
opposite of that as well. So I'm
full spec when I have no idea watch
this space. I'm working
on this every day. This is what I'm doing and and
You know start playing with it. If you want. You can't
deploy yet the deployment stuff when
it does arrive is going to be like inside Jazz.
It's going to be fully automated.
So it'll be automatically updating itself automatically
updating applications.
Unlike site.js it's using git for
a lot of that. So yeah.
right
And I think this is a good point to leave it
at if no one else has any questions.
Yeah, waiting one to three.
All right, cool. You know what? Thank you so much for
joining. Thank you so much for your questions. I'm sorry.
I wasn't able to give out the studio URL and have anyone like, you
know on video chat to ask questions or whatever. It's just
been a very long stream, but I think we covered
a lot. You're very welcome Ben Harold. Thank
you so much. And if
you guys have any questions, thank you
our God say if you have any questions, I'm on
Mastodon. Mastodon.ar.a.l.
Feel free to hit me up there or you
know, I don't know if a cowork
doesn't have discussions does it now? Oh, yeah, you
know, you can find me that find me on on the
fatty verse and thank you so much for joining and I
will see you next month
at on smallest beautiful if
not before.
Take care of yourselves, bye-bye.
And where
no, we're not because there's a confirmation and where