Open umputun opened 5 months ago
cc @ar2rworld
Running shell-related things
It appears that syscall.Statfs
func can replace the df
call.
after #5 merge:
main.go
wg.Add(1)
go func() {
defer wg.Done()
s := server.NewServer(opts.Port, opts.Dir, revision)
go s.Start()
}()
I don't get it, goroutine started from another goroutine? Probably a mistake.
no need to execute run() in a goroutine to make it blocking the next line. Just run it directly.
Server's Start() is non-cancelable from the outside. Making ctx in main and triggering it with NotifyContext will allow you to cancel this context, and you can pass it to the server.
if revision == "local" {
slog.SetLogLoggerLevel(slog.LevelDebug)
}
Looks way too opinionated to me. As a user, I want to be able to run with the debug info as needed by passing --dbg
.
Internal var names in main are non-idomatic. Probably myclient
can be just c
or if you preffer menengful var names - rtAPIClient
. O even better, you may no need a var for this, just recorder.NewListener(recorder.NewRecorder(opts.Dir))
. streamlistener
probably just listener
or streamListener
if you preffer it this way.
Side note: you seem to have a lot of //nolint. If you have to suppress some linters that often, you probably don't want them. Take a look at the .golangci.yml we use in other parts. I'd suggest adopting it to keep the same style of what we consider valid (for linter) and what not.
Options formattion with spaces just wrong, i have removed it in my commit.
package recorder:
return entries[0].Title
can panic because len(entries) > 0 is not checked prior to thisRecord
ignores context and essentially non-cancalableI also don't get how the main-level ticker is supposed to work with the recorder. To me, it looks like it will create a new stream
every 5 seconds, and you will end up with multiple recorders storing the stream into the common file. If this is the case, this is not right. If not, probably some comments are needed around the ticker, explaining the flow. If this is the error as I think it is, it would be a very clear reason why this app needs real integration tests. Such types of high-level logical issues are very well captured by such tests.
server:
index
struct doesn't warrant a separate struct with its own methods just to read a list of files, just do it directly in the IndexHandler. If you see it's getting to big - extract to a helper functionDownloadRecordHandler
even needed, practically we won't be able to even know what particular chunk we need and will download the whole zip
First of all, thank you for taking care of this project; I appreciate it.
After a quick review, I have prepared a list of potential improvements:
df -h
+ h.dir +| awk 'NR==2 {gsub("%","",$5); print $5}'
inside the app is not a good idea. I'm not sure if Go has a proper way to get disk utilization, but if not, we can just drop it.By and large, I'd like to see the project resembling other parts, e.g., super-bot, tg-spam, publisher, rss_generator. The reason for this is that a similar structure will make long-term maintenance easier for someone familiar with other parts of this infrastructure. For the same reason, I would like to simplify the structure and keep only what we really need without adding unnecessary abstractions and specialized tooling. I think the structure can be as simple as main.go and main_test.go (maybe with test data too) at the app level and a server package for everything else. Well, we can also have a recorder package if we really need it. Probably all we should have in the server package is a server.go handling all the routes and a recorder doing the recording, plus test files and mock files.
A couple of functional requirements I have not mentioned before: