An open source video sharing app with recommendations, transcoding and more
An open source video sharing app with recommendations, transcoding and more
Since my last ship I:
Please check my previous ships and devlogs, they are more in depth :)
Public version may be slow. It is running on my old PC and through a reverse proxy in a different country
Thumbnails are now automatically blocked if anything NSFW is detected.
I also moved the clean-up step of jobs to a defer, so errored jobs will still be cleaned up.
I know the logs donāt look the nicest and arenāt consistent, Iāll be rewriting logs to use structured logs soon.
Log in to leave a comment
I added infinite scroll for suggested videos. This was already implemented in the API, but I guess I forgot to implement it on the website. I also added a loading indicator.
Note: The loading is intentionally slowed down in the demo video, just so you can actually see the indicator
Log in to leave a comment
I updated to video list to readd the separator, use flex wrapping and lower the font size.
Unfortunately, when the flex element wraps, the separator still shows. I spent around an hour trying to fix this using container queries. Container queries are awful to use with heights. Never again.
Log in to leave a comment
I wrote a test case for users.GetUserById. Since a lot of validation was the same from the test for users.Get, I moved that logic into a separate function to be used for both test cases.
The users.Create RPC returned a uint64 ID instead of an int64, so I updated the code to use int64 instead, and removed any no longer necessary conversions to int64.
Log in to leave a comment
I added a test case for the Users.Get RPC, which verifies that all returned fields are as expected.
When I was writing this, I realised that type for User contained an email, even though it was not sent on most emails, which could lead to confusion using any RPC that returns a User.
To fix this, I added a separate type that contained the users email (UserWithEmail) that is used by RPCs that need the users email, and I removed the email field from the User type.
Log in to leave a comment
I wrote a test case for the GetFollowing RPC.
This test case has a similar setup to the GetFollowers RPC (create two users and follow one), so I split the logic into a separate function to reduce duplicated code.
The test case ensures:
Log in to leave a comment
In my previous devlog I discovered users were able to follow themselves.
In this devlog I:
Log in to leave a comment
I added test cases for:
As a result of this, I have found that:
These should be fixed in the next update :)
Log in to leave a comment
I improved code quality by:
I also updated testing by:
Log in to leave a comment
I added Umami, a privacy focused analytics service to Watchtower. As of now it only tracks page views, but in the future I plant to improve integration by adding events for video likes/dislikes, follows, video creation etc.
I also considered Rybbit, because it has more features like error tracking and web vitals, but I could not get a self hosted set up working. Maybe in the future.
Log in to leave a comment
On the second test case I wrote I found a bug. Not sure if this is a good thing, but at least it means testing is worth it.
Log in to leave a comment
Yes - Iāve finally gotten around to writing tests!
Before I was relying on manual testing, by visiting the website - Iāve probably missed quite a few bugs. But now Iāve started writing automated tests for the API.
I have set up the tests so an ephemeral API is set up, along with temporary PostgreSQL, S3, RabbitMQ, and Valkey (redis). These automatically start when you run the tests, and stop when the tests have finished. I did this using the Golang SDK for docker-compose, and waiting for the API to start. After, migrations are automatically applied to the testing database.
As of now, there is only one test case, but I will setup more and more. I plan to implement E2E testing for the website in the future.
š„ cskartikey marked your project as well cooked! As a prize for your nicely cooked project, look out for a bonus prize in the mail :)
Log in to leave a comment
The full version of Watchtower is deployed on my new server (my old pc) which means you can now upload videos! These will be transcoded to multiple different resolutions, and analyzed to block NSFW content. The NSFW detection may be a bit inaccurate so make sure to use the report and appeal features
Log in to leave a comment
I updated my video sharing app!
In this update I polished code, started work on an iOS app and added suggested videos in the view video page!
Please check my previous ship message and devlogs for more details :)
Spent some time polishing things, and working on docker images, for a move to another server
If you spot anything that needs polishing - please let me know!
Log in to leave a comment
Log in to leave a comment
I started working on an iOS app using swift!
This is my first time ever using swift, so it took quite a while.
Initially I tried using NativeScript Svelte, then React Native. Its pretty hard to get gRPC working with them, needing a proxy or something for the gRPC server, so I switched to swift instead.
Xcode (Apples IDE) doesnāt run on linux, so I had to install xtool and vscode/zed. I have to rebuild everytime I make a change, and the builds are pretty slow, but Swift is a really nice language and I may use it in the future
Log in to leave a comment
I built Watchtower, a Youtube clone. It is entirely self hostable.
I worked on it for over 92 hours before I found out about Flavortown.
As of now, I have coded over 44 hours worth of updates!
Note: Live streams and uploading videos are disabled in the demo. I do not have a GPU server, so videos would take days to process and analyse. Live streams would probably blow up the laptop Iām hosting everything on. You can still live chat though
I built a tool called devman specifically for this. It allows you to run multiple services from a configuration file. Each services can wait for other services to be online, so programs do not crash if something not up yet.
You can check it out on Codeberg
Log in to leave a comment
I rewrote the video analyzer (NSFW detection) from Go to TypeScript, because the go package used for NSFW broke.
It might be slower, but at least it works
Canāt really have many screenshots for this updateā¦
I also reduced the amount of things you need to install by using go tools,
where instead of installing the binary I run go get -tool and call it using go tool
More work for me, less work for someone trying to set this up themselves.
I also reinstalled my OS 2 times, so thats why this update took a while
You can view the changes on Codeberg
Log in to leave a comment
I added chats to live streams! (you can chat even when the stream is offline
This was implemented using websockets (this is like the 8th microservice)
I made it so scrolling pauses the chat, so you can read messages.
The colour of the usernames are based on the hash of your username, I should probably let you pick a colour though.
Log in to leave a comment
I fixed live streams by writing a proxy to the stream server
Also did a few bug fixes
View The Changes
Replaced dropzone.js with a custom upload script, so uploading matches the theme better
(4h of work because everything decided to break)
(ps donāt use RustFS, it is buggy and vibecoded)
Log in to leave a comment
Added a live indicator to profile pages
Log in to leave a comment
Log in to leave a comment
I added trending, and did a few other things, like improving security, working on a demo environment, improving code, fixing a bug and cleaning up processed thumbnails
Log in to leave a comment
I added view counter (a view counts once every six hours per users) and refactored the code!
View Changes
Log in to leave a comment
I added an admin dashboard with user/video count analytics.
(I spent a lot of time perfecting how the graph looks)
View the change
Log in to leave a comment
Improved UX by redirecting back to profile page after deleting a video (with a refresh) so deleted videos donāt show after deletion
Also changed some endpoints to use proper http semantics
Log in to leave a comment
I hid private/unprocessed videos in the recommended feed
Also had problems with atlas migrations which took hours to fix :)
Log in to leave a comment
I added a most popular sort option to the homepage of WatchTower.
I am planning to add a trending option as well.
I should probably remove some of the duplicated logic though and replace /videos/latest and /videos/popular with /videos/{sort_type}
Log in to leave a comment
I added a ālatestā sort option to my video sharing platform
I also fixed a bug where usernames wouldnāt show on recommended videos
Next up is sorting by popularity
Log in to leave a comment