aboutsummaryrefslogtreecommitdiff
AgeCommit message (Collapse)Author
2026-02-15lib/http: fix possible data race in SSE connectionShulhan
When server's handler call Write or WriteRaw, there is possibility that the worker for keeping the connection alive also call Write at the same time, which cause the data race.
2026-02-13lib/http: realign the fields in struct ServerShulhan
Previous struct size is 384 pointer bytes, now realign to 336 bytes (-48 bytes).
2026-02-13lib/path: remove reference to old repository "share"Shulhan
2026-02-13lib/websocket: remove generated HTML filesShulhan
The generated HTML files is outdated and it is not referenced anywhere.
2026-02-11go.mod: update all dependenciesShulhan
2026-02-11cmd/httpdfs: add option to set base path and shutdown idle durationShulhan
The `-base-path` option set the URL prefix for serving HTTP request. The `-shutdown-idle` option set the duration when server will stop accepting new connections and shutting down.
2026-02-11lib/http: implement server auto shutdown when idleShulhan
In the `ServerOptions`, we add option `ShutdownIdleDuration` when set to non-zero value it will start a timer. When the timer expired, the server will stop accepting new connection and then shutting down. This allow de-activating HTTP server when no connections received after specific duration to reduce the system resources.
2026-02-11lib/http: add BasePath to the ServerOptionsShulhan
The BasePath allow server to serve HTTP from custom prefix, other than "/". Each request that server received will remove the BasePath first from the [http.Request.URL.Path] before passing to the handler. Each redirect that server sent will add the BasePath as the prefix to redirect URL. Any trailing slash in the BasePath will be removed.
2026-02-09lib/git: skip test LogFollow when repository is shallow clonedShulhan
In CI, the repository is cloned with depth=1, while test for LogFollow compare the last 3 commits. This cause the test on LogFollow fail in CI environment.
2026-02-09lib/git: fix tests due to missing .git directoryShulhan
In lib/git, we have test data "testdata/Equal" and "testdata/IsIgnored" that require the directory named ".git". Somehow those directory is missing from previous commit, which cause the test failed when run in new clone. After we inspect it, git does not allow adding a file under directory named ".git" (to include it inside the commit), so to fix the test we need to create the ".git" directory manually before running the tests.
2026-02-09go.mod: update the Go version to 1.25Shulhan
This include updating the Go version in actions.
2026-02-09Release pakakeh.go v0.61.0 (2026-02-09)v0.61.0Shulhan
=== all šŸ’§ all: convert license and copyright to use SPDX identifiers With the help of spdxconv tool, we able to bulk update all files license and copyright format to comply with SPDX formats. === cmd/httpdfs 🌼 cmd/httpdfs: implement systemd socket activation The httpdfs program now can be activated using systemd.socket(5). === lib/dns 🌼 lib/dns: use separate ServeMux for handling DoH Using the [http.DefaultServeMux] will cause panic when the server restarted manually using Stop-Start flow. 🌼 lib/dns: skip caching empty answer only for query type A Previously, we did not store response with empty RR answer for all record types. Meanwhile, some domains still does not have AAAA(28) and HTTPS(65) records set, but browser will requesting them. So, to minimize traffic for those query we skip caching only for query type A and cache the rest of types. 🌼 lib/dns: remove DebugLevelDNS The DebugLevelDNS log the error on DNS level, for example empty answer, error on name, class not implemented, refused; which is now on by default. 🌱 lib/dns: add option to set hook on server when receiving answer The hook function, OnAnswerReceived, will be triggered when server receive valid answer but before its put to caches. 🌱 lib/dns: add method to set TTL on Message The SetTTL method set all RRs answer time to live. 🌼 lib/dns: print the answer TTL in DebugLevelCache The log level cache changed to the following format, ... {MSG_ID QNAME TYPE TTL} ... where MSG_ID is the message ID, QNAME is the question name, TYPE is the type of question, and TTL is the time-to-live of the answer. 🌼 lib/dns: simplify log message for DebugLevelCache For each logged request, there should be one line of response logged, success or fail. This changes remove redundant log "^" (request forwarded) and "~" (answer is expired). The final log would be only "+" (new answer cached), or "#" (answer updated), or "!" (error). 🌼 lib/dns: increase the client default timeout from 6 to 60 seconds The 6 seconds timeout will works only on fast, stable connection. On some environment with bad network connection, it will cause I/O timeout during recv and this affect the whole internet connections, like browsing. Since the browser wait for domain to be resolved but it does not get the response, it send another query. The next query also got timeout again. Increasing to 10-30 seconds also does not help on that environment. After some tests, 60 seconds is the lower timeout limit that reduce the I/O timeout. It is better that we receive the response and store it to caches, so the next query can be handled quickly, rather than timeout and retrying with the same error. This method accept second paramter "format", default to '%h,%at,%an,%ae,%s’ which print short hash, author commit timestamp, author name, author email, and subject; respectively separated by comma. === lib/git 🌱 lib/git: expose the API for IgnorePattern The IgnorePattern is not exclusive to git only. Some program, like REUSE, use the same pattern in the REUSE.toml path configuration. 🌱 lib/git: add method LogFollow The LogFollow method return history of single file path, following rename. 🌱 lib/git: add Git type with method IsIgnored The Git type is for working with single git repository. The [Git.IsIgnored] method is to check if the path is ignored by git. This is processed by matching it with all of the pattern in the ".gitignore" file from the path directory and its parent until the root of Git repository. The Git type implement Equaler interface. The Equaler interface provide the method Equal that when implemented can be used to compare two instances of struct. 🌱 lib/git: implement Gitignore Gitignore is a type that represent ".gitignore" file. There are two ways to populate Gitignore, by using [LoadGitignore] function, or by using [Gitignore.Parse] method. After the Gitignore created, one can check if a path is ignored by using [Gitignore.IsIgnored] method, relative to the Gitignore directory. === lib/http 🪵 lib/http: change HandleFS redirect status code to 301 According to MDN Redirections in HTTP the HTTP status 302 Found use case is for "Web page (that) is temporarily unavailable for unforeseen reasons.". This probably to re-route the page until the original page is fixed. While HTTP status 301 is for "Reorganization of a website.". Since the redirection in HandleFS only happen when user access directory without slash, we should make it permanent. 🌼 lib/http: set HandleFS to always end with slash "/" Previously, if request to directory does not end with "/", the HTTP server will return the index.html of that directory. This cause relative link inside the index.html broken when visited from browser. This changes make the request to directory always end with "/" by redirecting the request with status 303 Found. 🌱 lib/http: add field Listener to ServerOptions The field Listener allow user to pass [net.Listener] for accepting new connection using [http.Serve] or [http.ServeTLS]. 🪵 lib/http: add second return value, statusCode, to FSHandler Non-zero status code indicates that the function already response to the request, and the server will return immediately. Zero status code indicates that the function did not process the request, it is up to server to process the returned node out. === lib/ini 🌼 lib/ini: improve error message when parsing variable name Display the invalid character in the error message with quote, so space can detected. Also, export the error variable so external caller can detect it using the variable. === lib/os 🌱 lib/os: add function IsBinaryStream The IsBinaryStream return true if the content has more than 75% non-printable characters, excluding spaces. While at it, replace the body of IsBinary with it and update the test cases to use the internal files. === lib/systemd 🌱 lib/systemd: new package for socket-based activation The lib/systemd package implement function Listeners that return list of file descriptor as [net.Listener], that enable program to run with systemd.socket(5) based activation. === lib/test 🌼 lib/test: ignore line prefixed with "//" The first line in test data file may contains line prefixed with "//" as comment. The use case is for license and copyright lines. 🌱 lib/test: implement method ExtractInput on Data Given the path to directory destDir, create all of the [test.Data.Input] with key as its file name. If the input name contains "/", the path before the base name will be created along with its parent as long as it is under the destDir. For example, given input name "a/b/c.txt", it will create path "a/b/" inside destDir first, followed by file "c.txt" inside that path. 🌼 lib/test: export the constant for default data file name suffix Also, fix typo on the LoadDataDir regarding suffix by replacing it with the exported constant.
2026-02-08go.mod: update all dependenciesShulhan
2026-02-08_doc: split the changelog for 2025Shulhan
While at it, use consistent title in the changelog files.
2026-02-08_doc: remove ":sectlinks:" attribute from adoc filesShulhan
The sectlinks attribute cause the sections header become hyperlinks, which is misleading since it is not link to other page or sites.
2026-02-06_doc: fix typo on RFC 4686 "Analysis of Threats Motivating DKIM"Shulhan
2026-02-05lib/http: change HandleFS redirect status code to 301 Moved PermanentlyShulhan
According to MDN [Redirections in HTTP], the HTTP status 302 Found use case is The Web page is temporarily unavailable for unforeseen reasons. This probably to re-route the page until the original page is fixed. While HTTP status 301 is for Reorganization of a website. Since the redirection in HandleFS only happen when user access directory without slash, we should make it permanent. [Redirections in HTTP]: https://developer.mozilla.org/en-US/docs/Web/HTTP/Guides/Redirections
2026-02-05lib/http: handle file system with canonical directory end with slash "/"Shulhan
Previously, if request to directory does not end with "/", the HTTP server will return the index.html of that directory. This cause relative link inside the index.html broken when visited from browser. This changes make the request to directory always end with "/" by redirecting the request with status 303 Found.
2026-02-05cmd/httpdfs: fix call to log.FatalShulhan
2026-02-03lib/os: fix IsBinary that return true if file size less than 1024Shulhan
If file size less than half of 1024, the rest of bytes will be `0` and it will counted as binary character.
2026-02-02cmd/httpdfs: implement systemd socket activationShulhan
The httpdfs program now can be activated using systemd.socket(5).
2026-02-02lib/http: add field Listener to ServerOptionsShulhan
The field Listener allow user to pass [net.Listener] for accepting new connection using [http.Serve] or [http.ServeTLS].
2026-02-02lib/systemd: new package for socket-based activationShulhan
The `lib/systemd` package implement function `Listeners` that return list of file descriptor as [net.Listener], that enable program to run with systemd.socket(5) based activation.
2026-02-02lib/play: set the minimum Go tool version to 1.25.0Shulhan
2026-02-02lib/dns: remove unnessary log prefix on forwarderShulhan
The "tag" prefix already indicate the forwarder type.
2026-02-02lib/dns: minimize use of appendShulhan
In handleDoHRequest, we did not need to call append, just copy it as is. In DoTClient and TCPClient, since we already do make, use direct copy instead of another append.
2026-02-02lib/dns: use separate ServeMux for handling DoHShulhan
Using the [http.DefaultServeMux] will cause panic when the server restarted automatically.
2026-02-02lib/dns: skip caching empty answer only for query type AShulhan
Previously, we did not store response with empty RR answer for all record types. Meanwhile, some domains still does not have AAAA(28) and HTTPS(65) records set, but browser will requesting them. So, to minimize traffic for those query we skip caching only for query type A and cache the rest of types.
2026-02-02lib/dns: remove DebugLevelDNSShulhan
The DebugLevelDNS log the error on DNS level, for example empty answer, error on name, class not implemented, refused; which is now on by default.
2026-02-02lib/dns: changes the request's kind field to stringShulhan
This is to minimize lookup on map each time we need the string representation.
2026-02-02lib/dns: add option to set hook on server when receiving answerShulhan
The hook function, OnAnswerReceived, will be triggered when server receive valid answer but before its put to caches.
2026-01-26lib/dns: add method to set TTL on MessageShulhan
The SetTTL method set all RRs answer time to live.
2026-01-26lib/dns: print the answer TTL in DebugLevelCacheShulhan
The log level cache changed to the following format, ... {MSG_ID QNAME TYPE TTL} ... where MSG_ID is the message ID, QNAME is the question name, TYPE is the type of question, and TTL is the time-to-live of the answer. This changes require adding field TTL to Answer and exporting the field Message.
2026-01-26make: increase test timeout to 2m due to lib/email/dkim takes more 60sShulhan
Just for record, with 1m timeout, it will cause the following error, ---- panic: test timed out after 1m0s running tests: TestSignatureSign (0s) goroutine 8 [running]: testing.(*M).startAlarm.func1() /home/ms/local/share/go/src/testing/testing.go:2806 +0x605 created by time.goFunc /home/ms/local/share/go/src/time/sleep.go:215 +0x45 goroutine 1 [chan receive]: testing.(*T).Run(0xc000148488, {0x82e9cf, 0x11}, 0xb1eed8) /home/ms/local/share/go/src/testing/testing.go:2109 +0xb3e testing.runTests.func1(0xc000148488) /home/ms/local/share/go/src/testing/testing.go:2589 +0x86 testing.tRunner(0xc000148488, 0xc00013dab0) /home/ms/local/share/go/src/testing/testing.go:2036 +0x21d testing.runTests({0x83415e, 0x1d}, {0x83b055, 0x2c}, 0xc000016588, {0xb7aee0, 0x14, 0x14}, {0xc255bab7b14073ac, 0xdf8581351, ...}) /home/ms/local/share/go/src/testing/testing.go:2587 +0xb18 testing.(*M).Run(0xc00014a460) /home/ms/local/share/go/src/testing/testing.go:2443 +0xf45 main.main() _testmain.go:94 +0x165 goroutine 24 [runnable]: crypto/internal/fips140/bigmod.(*Nat).montgomeryMul(0xc000298da8?, 0xc0002996e8?, 0xc000298da8?, 0xc000065cc0?) /home/ms/local/share/go/src/crypto/internal/fips140/bigmod/nat.go:779 +0xab8 crypto/internal/fips140/bigmod.(*Nat).Exp(0xc0002996e8, 0xc000299700, {0xc0000254c0, 0x40, 0xc000065ca0?}, 0xc000065cc0) /home/ms/local/share/go/src/crypto/internal/fips140/bigmod/nat.go:1028 +0xa57 crypto/internal/fips140/rsa.decrypt(0xc00001a2a0, {0xc00006f300, 0x80, 0x80}, 0x1) /home/ms/local/share/go/src/crypto/internal/fips140/rsa/rsa.go:428 +0x466 crypto/internal/fips140/rsa.signPKCS1v15(0xc00001a2a0, {0x82a7e6, 0x5}, {0xc00001f4a0, 0x14, 0x14}) /home/ms/local/share/go/src/crypto/internal/fips140/rsa/pkcs1v15.go:60 +0xc5 crypto/internal/fips140/rsa.SignPKCS1v15(0xc00001a2a0, {0x82a7e6, 0x5}, {0xc00001f4a0, 0x14, 0x14}) /home/ms/local/share/go/src/crypto/internal/fips140/rsa/pkcs1v15.go:51 +0x259 crypto/rsa.SignPKCS1v15({0xc0002999b8?, 0x45b525?}, 0xc00001a230, 0x3, {0xc00001f4a0, 0x14, 0x14}) /home/ms/local/share/go/src/crypto/rsa/fips.go:353 +0x289 git.sr.ht/~shulhan/pakakeh.go/lib/email/dkim.(*Signature).Sign(0xc000299db0, 0xc00001a230, {0xc00001f4a0, 0x14, 0x14}) /home/ms/kilabit.info/_project/src/pakakeh.go/lib/email/dkim/signature.go:281 +0x192 git.sr.ht/~shulhan/pakakeh.go/lib/email/dkim.TestSignatureSign(0xc00017a908) /home/ms/kilabit.info/_project/src/pakakeh.go/lib/email/dkim/signature_test.go:354 +0x62c testing.tRunner(0xc00017a908, 0xb1eed8) /home/ms/local/share/go/src/testing/testing.go:2036 +0x21d created by testing.(*T).Run in goroutine 1 /home/ms/local/share/go/src/testing/testing.go:2101 +0xb13 FAIL git.sr.ht/~shulhan/pakakeh.go/lib/email/dkim 60.085s ---- I think it is related to fips140 has been merged to the go tip that increase the time.
2026-01-26lib/dns: simplify log message for DebugLevelCacheShulhan
For each logged request, there should be one line of response logged, success or fail. This changes remove redundant log "^" (request forwarded) and "~" (answer is expired). The final log would be only "+" (new answer cached), or "#" (answer updated), or "!" (error).
2026-01-25lib/dns: increase the client default timeout from 6 to 60 secondsShulhan
The 6 seconds timeout will works only on fast, stable connection. On some environment with bad network connection, it will cause I/O timeout during recv and this affect the whole internet connections, like browsing. Since the browser wait for domain to be resolved but it does not get the response, it send another query. The next query also got timeout again. Increasing to 10-30 seconds also does not help on that environment. After some tests, 60 seconds is the lower timeout limit that reduce the I/O timeout. It is better that we receive the response and store it to caches, so the next query can be handled quickly, rather than timeout and retrying with the same error.
2026-01-25README: fix broken link and simplify license sectionShulhan
2026-01-15CHANGELOG: record all of the latest changesShulhan
2026-01-15all: convert license and copyright to use SPDX identifiersShulhan
With help of spdxconv tool [1], we able to bulk update all files license and copyright format to comply with SPDX formats. [1] https://kilabit.info/project/spdxconv/
2026-01-15lib/test: ignore line prefixed with "//"Shulhan
The first line in test data file may contains line prefixed with "//" as comment. The use case is for license and copyright lines.
2026-01-15lib/git: handle pattern "**/foo/**"Shulhan
The "**/foo/**" means accept any files as long as there is foo directory in the middle.
2026-01-14lib/git: expose the API for IgnorePatternShulhan
The IgnorePattern is not exclusive to git only. Some program, like REUSE, use the same pattern in the REUSE.toml path configuration.
2026-01-14lib/git: pass "--" when running LogFollow commandShulhan
The "--" prevent ambiguous argument, to separate a path from revision. While at it, add more test case for LogFollow.
2026-01-13README: format the file using prettierShulhan
2026-01-13lib/git: add method LogFollowShulhan
The LogFollow method return history of single file `path`, following rename. This method accept second paramter "format", default to '%h,%at,%an,%ae,%s' which print short hash, author commit timestamp, author name, author email, and subject; respectively separated by comma.
2026-01-11lib/git: fix ignore pattern with single wildcard '*'Shulhan
Single wildcard should ignore everything inside it.
2026-01-09lib/os: add function IsBinaryStreamShulhan
The IsBinaryStream return true if the content has more than 75% non-printable characters, excluding spaces. While at it, replace the body of IsBinary with it and update the test cases to use the internal files.
2026-01-08lib/ini: improve error message when parsing variable nameShulhan
Display the invalid character in the error message with quote, so space can detected. Also, export the error variable so external caller can detect it using the variable.
2026-01-06lib/http: add second return value, statusCode, to FSHandlerShulhan
Non-zero status code indicates that the function already response to the request, and the server will return immediately. Zero status code indicates that the function did not process the request, it is up to server to process the returned node `out`.
2026-01-06lib/git: implement Equaler interface on GitShulhan
The Equaler interface provide the method Equal that when implemented can be used to compare two instances of struct.