I built something like this in Go a few years ago but it reloads your infrastructure when it changes, recompiles your code when it needs to, and syncs static files or interpreted files to wherever your app is running (desktop or cloud). Think of it like docker-compose but with file watching + sync + smart rebuilds. https://skaffold.dev/
Is there a skaffold for borg that inspired this? Curious if there are any existing things you were inspired by, or particular pitfalls in alternatives you wanted to avoid!
(1) minikube, which I also maintained at Google. I saw how difficult getting started with Kubernetes could be even when you were able to create a local cluster. I also knew all the shortcuts that you could take to streamline local Kubernetes workflows (e.g., loading images directly into the minikube docker daemon).
(2) docker compose, which remains a great tool but had no analogue for Kubernetes. It also didn't have a concept of syncing for hot-reloadable projects or built-in file watcher.
(1), Draft by the Deis folks at Microsoft, which was a great tool but suffered from having a component that you needed to install on the cluster to work, where the skaffold architecture was purely client side (making it a lot easier to get started, and faster). I also wanted to make skaffold pluggable, so it supported helm, kubectl, docker, bazel, and other tools right from the start. It also had clear boundaries between build and deploy and ideas for CI and gitops workflows built in.
It parses a Dockerfile (or queries dependencies in a tool like bazel) to get a list of file dependencies and then kicks off an optimized rebuild and redeploy. If you're using buildkit and caches this can be done really quickly (close to native compile without a Docker image)
You can tell it to just sync certain changes (e.g. syncing a javascript file to a container running webpack).
I'm not sure about "find" -- but I also use "entr" for this (and just about a billion other tasks, is there anything you can't use it for?) and I personally do something like:
When writing go, I've always found if I find myself constantly restarting & recompiling a program during development, it means that I should be writing tests instead.
Suppose you want to instrument some code that touches a database, because you suspect some data (in prod) is coming off the database that is messing your assumptions up, but you don't know yet what specific assumption it is.
Because it's just a gut feeling, you can't write a test against it
Given go's nature of being more network oriented, I think these questions are a bit disingenuous.
Go comes with a lot of facilities for testing the things it's good at.
If testing GLSL shaders, or gui applications is difficult, I'd consider putting at least some pressure on the tooling providers to provide better testing facilities.
I'm more familiar with how opengl & shaders work than I am with text rendering - so I'll keep my commentary towards the shader question. At least on the surface it seems de-composable into two distinct problems: Is the shader emitting the correct colors after gamma correction is applied, and is that rendering appearing on the screen.
The former could be tested by rendering to a buffer and capturing the output, and asserting against an expected color value.
The latter is where I'd say that better tooling is indeed required.
I lnow you're saying that when it comes to GUIs you have to do it manually, but as someone working on the back-end this begs the question: is there no unit tests framework or anything for GUIs ?
Depends if we are talking about native or web based GUIs, and then the best you can get is automating the user clicking buttons and if the UI changes in some limited ways.
There is no way to properly test UI/UX experiences, even if the test is correct for a button being displayed with the right label, doesn't mean it looks correctly from user experience point of view, yet the test is green.
Taking repeated screenshots of a GUI and making sure they don't change across commits is a useful thing to have in CI a lot of the time to make sure if you did change something somebody's eyeballed it for correctness.
However I'm not at all claiming that removes the 'eyeballed it' step, just that it makes it harder to miss said step :)
For native Android apps there is a framework to do GUI tests. The test code stayed in your release as a NOOP last time i looked at it, may be fixed now.
Write a test that launches the application and checks relevant pixels, at the very worst. Which is not generally all that hard. Bonus points if you save the full image so you can see expected / actual results easily.
Yep it’s actually one of the things i love. If waiting for go compile time has gotten to be a problem it is time for tests or to refactor if a test can’t be easily written.
If you write your tests with Ginkgo [0] its CLI can do this for you.
It also has nice facilities to quickly disable a test or portion of a test by prepending an X to the test function name, or to focus a test (only run that test) by prepending an F. It’s pretty nice.
The best tool I’ve found for this job is reflex[1]. It’s easy to setup, Go agnostic, very « UNIX » in its philosophy, doesn’t get in your way with its own logs, and just works.
Before that I used realize but it has the bad behavior of always adding it’s own prefix to the logs, which sucks.
It's straightforward to use but also has a ton of options so you can do whatever you want with it. It also handles common issues you'll run into when working with larger codebases where you end up watching over too many files. And finally, it has configuration files so you can have the same setup as the rest of the engineers on your team.
More importantly, it's actively maintained and has been out for a while, and it's not specific to Go apps: you can use it for anything you want to watch and execute on.
Useful tool, but it has some bugs related to consecutive build failures. Restarting Air is required to fix it. I still use it, just wish I didn't have to restart it frequently.
Shameless plug, but I built https://github.com/superhuman/lrt as simply as possible, explicitly to avoid this kind of issue (which seem to plague tools in this space).
This doesn't watch the fs and build automatically now.. Does it?
We started using this tool a couple of months ago. It was a huge productivity boost. We had multiple binaries produced by the build and all had to run to make the complete service
I usually run "go build" to see if my code compiles and respond to the errors. If it builds successfully, it's restarted automatically.
I personally don't see value in running "go build" out-of-band in another terminal where I can't easily pipe the errors into my editor (or automatically if I'm running it in the editor).