blogs.json is fetched once and committed to the repo, and loaded with go:embed; no HTTP at runtime.
The public API (FetchBlogs, GetBlogs, RandomBlog, RandomBlogs, Blog) keeps working; FetchBlogs becomes a parse of the embedded data (memoized as today) and cannot fail on network.
A make target (e.g. make update-data) refreshes the vendored file from BlogsURL, so the dataset can be bumped by a commit.
Tests do not touch the network.
README/doc comments say the data is embedded and how to refresh it.
Model: fable-5-1
Requested by sneak in chat, 2026-09-05.
`FetchBlogs` does an HTTP GET of `BlogsURL` (https://raw.githubusercontent.com/surprisetalk/blogs.hn/main/blogs.json) on first use, so the library needs network access at runtime and its results change under the caller.
Definition of done:
- `blogs.json` is fetched once and committed to the repo, and loaded with `go:embed`; no HTTP at runtime.
- The public API (`FetchBlogs`, `GetBlogs`, `RandomBlog`, `RandomBlogs`, `Blog`) keeps working; `FetchBlogs` becomes a parse of the embedded data (memoized as today) and cannot fail on network.
- A `make` target (e.g. `make update-data`) refreshes the vendored file from `BlogsURL`, so the dataset can be bumped by a commit.
- Tests do not touch the network.
- `README`/doc comments say the data is embedded and how to refresh it.
Model: fable-5-1
blogs.json is vendored and loaded with go:embed; net/http is gone from the package and a test fails on any net/net/* import returning to non-test code. FetchBlogs keeps its signature and sync.Once memoization, decoding the embedded bytes instead of fetching, and can now only error on a malformed committed dataset. make update-data refreshes the file, reading the URL from the BlogsURL constant so it has one definition, replacing blogs.json only on a complete download, then running the tests. Added a README.md, which the repo did not have.
make test, make lint and make docker pass; the Docker test stage was also run with --network=none to confirm the suite needs no network.
Two things needing your call: the dataset is committed verbatim (~8 MB, mostly per-blog post history the Blog struct ignores) rather than trimmed to the six fields it reads (~1.5 MB), because the issue asked for a refresh from BlogsURL rather than a transform of it. And the PR could not be labelled needs-review -- the repo defines no labels and clawbot has pull-only access, so it is opened from a fork.
Model: opus-5
Done in https://git.eeqj.de/sneak/hnblogs/pulls/2
`blogs.json` is vendored and loaded with `go:embed`; `net/http` is gone from the package and a test fails on any `net`/`net/*` import returning to non-test code. `FetchBlogs` keeps its signature and `sync.Once` memoization, decoding the embedded bytes instead of fetching, and can now only error on a malformed committed dataset. `make update-data` refreshes the file, reading the URL from the `BlogsURL` constant so it has one definition, replacing `blogs.json` only on a complete download, then running the tests. Added a `README.md`, which the repo did not have.
`make test`, `make lint` and `make docker` pass; the Docker test stage was also run with `--network=none` to confirm the suite needs no network.
Two things needing your call: the dataset is committed verbatim (~8 MB, mostly per-blog post history the `Blog` struct ignores) rather than trimmed to the six fields it reads (~1.5 MB), because the issue asked for a refresh from `BlogsURL` rather than a transform of it. And the PR could not be labelled `needs-review` -- the repo defines no labels and `clawbot` has pull-only access, so it is opened from a fork.
Model: opus-5
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Requested by sneak in chat, 2026-09-05.
FetchBlogsdoes an HTTP GET ofBlogsURL(https://raw.githubusercontent.com/surprisetalk/blogs.hn/main/blogs.json) on first use, so the library needs network access at runtime and its results change under the caller.Definition of done:
blogs.jsonis fetched once and committed to the repo, and loaded withgo:embed; no HTTP at runtime.FetchBlogs,GetBlogs,RandomBlog,RandomBlogs,Blog) keeps working;FetchBlogsbecomes a parse of the embedded data (memoized as today) and cannot fail on network.maketarget (e.g.make update-data) refreshes the vendored file fromBlogsURL, so the dataset can be bumped by a commit.README/doc comments say the data is embedded and how to refresh it.Model: fable-5-1
Done in #2
blogs.jsonis vendored and loaded withgo:embed;net/httpis gone from the package and a test fails on anynet/net/*import returning to non-test code.FetchBlogskeeps its signature andsync.Oncememoization, decoding the embedded bytes instead of fetching, and can now only error on a malformed committed dataset.make update-datarefreshes the file, reading the URL from theBlogsURLconstant so it has one definition, replacingblogs.jsononly on a complete download, then running the tests. Added aREADME.md, which the repo did not have.make test,make lintandmake dockerpass; the Docker test stage was also run with--network=noneto confirm the suite needs no network.Two things needing your call: the dataset is committed verbatim (~8 MB, mostly per-blog post history the
Blogstruct ignores) rather than trimmed to the six fields it reads (~1.5 MB), because the issue asked for a refresh fromBlogsURLrather than a transform of it. And the PR could not be labelledneeds-review-- the repo defines no labels andclawbothas pull-only access, so it is opened from a fork.Model: opus-5