Raspberry Pi 上面直接對 Framebuffer 與觸控介面操作

清 tab,看到這個 2019 年的文章:「Writing GUI applications on the Raspberry Pi without a desktop environment (2019) (avikdas.com)」,原文在 Raspberry Pi 上面希望操作觸控螢幕,但不想要把整包 X.Org 都裝起來,所以直接操作了 Framebuffer,並且自己處理了觸控介面的事件:「Writing GUI applications on the Raspberry Pi without a desktop environment」。

這看起來是作者的成品:

當年作者用 Raylib 實作,不過 2024 年的 Hacker News 倒是提到了不少 library 可以用,之後如果有遇到需求可以當作切入點去研究...

dotenvx

清一清 tab... 兩個禮拜前還在日本時在 Hacker News 的「Show HN: From dotenv to dotenvx – better config management (dotenvx.com)」看到的東西,原文在推廣 dotenvx:「From dotenv to dotenvx: Next Generation Config Management」。

GitHub 的文件上可以看到幾個用法,一種是直接用,像是一般的 dotenv 的用法:

// index.js
require('@dotenvx/dotenvx').config()
console.log(`Hello ${process.env.HELLO}`)

另外一個是當 wrapper 用,像是這樣:

$ dotenvx run -- node index.js
Hello World # with dotenvx
> :-D

然後後者可以指定不同的 .env 多環境使用:

$ dotenvx run -f .env.production -- node index.js
[dotenvx][info] loading env (1) from .env.production
Hello production

另外還支援了 encrypt/decrypt 的能力降低 secret 的風險?不過這應該已經不是目前比較安全的方法了,這十年下來已經知道把 secret 放在環境變數裡太容易洩漏。

環境變數在呼叫外部程式時會被繼承,算是常見的 leaking 管道,另外就算不考慮外部程式,也會遇到環境變數算是一種全域變數,在寫測試時也很頭痛。

目前被提出來比較好的方法是把 secret 都放到 vault service 裡面,由 vault service 給一把讀取用的 API key,放進 dotenv 或是其他地方 (被稱為 secret zero)。

這樣這把 API key 去 vault service 抓取真正的 secret 放到程式內的物件取用 (像是資料庫的帳號密碼),而不是環境變數。

這樣做的 threat model 在 Hacker News 上有對應的討論,另外 AWS 的服務其實也做了類似的事情:「Amazon EC2 的 IMDSv2 計畫」。

所以 dotenvx 大概就看看,有個印象就好?

直接在 library 層將 MongoDB 用法轉換成 PostgreSQL 底層的 Pongo

看到這個「Mongo but on Postgres and with strong consistency benefits (github.com/event-driven-io)」算是另外一種用 PostgreSQL 取代 MongoDB 的嘗試,先前其他的方案是 proxy server 的方式實作 (像是 FerretDB),也就是 TCP 裡面傳的東西還是 MongoDB protocol,然後 proxy server 會轉譯成 PostgreSQL 的 SQL 語法。

這個作法的好處是不用管既有 application 是什麼程式語言開發的,另外改動比較少 (改個連線資訊 + 然後把目前還不支援的功能改寫),但缺點是多了一組 service 要維護 (如果是 HA 的話又還要設定 failover 或是 load balancer 的機制)。

Pongo 的作法則是移到 library 這邊做掉,所以就有程式語言的限制了:這個專案是用 TypeScript 開發,所以會是 JavaScript + TypeScript 生態系的方案。

不過好處就很明顯了,少了一組 service 要維護 (如果包括 HA 機制的話可能是兩組或三組),另外因為轉譯的部分在 application 端處理,沒有了 proxy server 也等於少了一個可能的 bottleneck。

這幾天上 Hacker News 後看 commit 頗熱鬧,從 Releases 頁可以看到連續出新版本。

不過... 不考慮直接用 PostgreSQL 嗎?

polyfill.io 被放 malicious code 的事件

台灣的圈子蠻多人是從「請儘速遠離 cdn.polyfill.io 之惡意程式碼淺析」這邊看到的,一些 code 相關的分析部分可以移駕過去看。裡面提到的 GitHub 上面 alitonium 所寫的 comment 蠻值得讀一下 (第一次點的時候會出現 GitHub 的警告,再點一次應該就會跳到正確的 comment 上)。

polyfill.js 算是老專案了,從 https://github.com/polyfillpolyfill/polyfill-service/graphs/contributors 這邊可以看到是 2013 年開始有記錄,主要是針對舊的瀏覽器 (像是 IE11),透過 javascript 的方式補上對應的功能。

現在的瀏覽器都是一直在更新,大多數的情況不太需要 polyfill 了,但畢竟很多舊的案子還在用,在這次 domain 被中國公司拿走後,Cloudflare 在今年 2024/2/29 就有先寫一篇算是預警的文章了:「polyfill.io now available on cdnjs: reduce your supply chain risk」,不過這種事情都是還沒發生前大家不會有太多重視,接下來就是 GitHub 上面的討論,然後是真的被動手加 malicious code 進去後,有人發現的討論。

後續大家都被迫要開始處理這件事情,GitHub 的作法看起來沒什麼問題:先標注 malicious repository 但是還是讓人可以進去翻歷史資料與討論。

不過 Cloudflare 這邊動作有點大,直接主動幫 CDN 客戶過濾了:「Automatically replacing polyfill.io links with Cloudflare’s mirror for a safer Internet」,這篇在 Hacker News 上也有討論:「Cloudflare automatically fixes Polyfill.io for free sites (cloudflare.com)」。

這個「越界」有點多,這應該也是直接讓 CEO Matthew Prince 出來掛文章作者的原因。這次 Cloudflare 主動做的事情包括了將免費的客戶預設開啟過濾,而付費的客戶則不會主動開啟,但提供一鍵開關:

Any website on the free plan has this feature automatically activated now. Websites on any paid plan can turn on this feature with a single click.

另外也允許所有客戶關掉這個保護:

All customers can turn off the feature at any time.

所以後續就會有另外一條大支線討論:在使用者沒有事前同意的情況下,以「安全」為名主動更改使用者頁面上的東西,這件事情是不是可以接受?如果以「安全」為名可以接受,為什麼是免費的先動,付費的卻不動?雖然我猜 Cloudflare 會裝死到底就是了...

用 libtree 來看 library dependency

在「Libtree: Ldd as a tree saying why a library is found or not (github.com/haampie)」這邊看到的,本來看到名字以為是與樹狀資料結構有關的 library,結果實際看了發現這邊的 libtree 指的是將執行檔裡面使用到的 dependency (library) 展成樹狀:

比起 ldd 的輸出多了更多資訊,這個在想辦法解決 library 問題時比 ldd 好用不少。

OpenSSL 決定把 release site 改到 GitHub 上

OpenSSL 宣佈了之後會以 GitHub 為主要發佈平台:「Releases Distribution Changes」。

舊的 ftp & rsync 以及 git protocol (9418/tcp 的協定) 都打算淘汰掉:

We’re no longer using our old ftp, rsync, and git links for distributing OpenSSL. These were great in their day, but it’s time to move on to something better and safer.

其中 FTP 與 rsync 都已經停掉了,接下來是今年六月要停掉 ftp.openssl.org 的 HTTPS 介面以及 git.openssl.org 的 git protocol:

ftp://ftp.openssl.org and rsync://rsync.openssl.org are not available anymore. As of June 1, 2024, we’re also going to shut down https://ftp.openssl.org and git://git.openssl.org/openssl.git mirrors.

然後主力轉戰到 GitHub 上面:

GitHub is becoming the main distributor of the OpenSSL releases.

算是省事的作法,畢竟自己弄 infrastructure 不算太輕鬆

另外 OpenSSL 畢竟是個歷史頗久的軟體了,有「遵循古法」所以 release 都會有 PGP/GPG sign,這部分如果還是獨立於 GitHub 平台的話就沒什麼問題,代表還是有非 HTTPS 的 integrity 方法可以確認檔案沒被抽換過。

(但如果綁進 CI/CD 流程的話就廢了?)

jQuery 官方鼓勵大家記得使用新版的 jQuery...

的確是很多人掛完 jQuery 後就沒動過了:「Upgrading jQuery: Working Towards a Healthy Web」。

jQuery 官方提供的三個切入點都是安全性的問題,Security Vulnerabilities、Security Best Practices 以及 Compliance Requirements。

相容性是 jQuery 的強項,有些 deprecated 的功能,官方還是有提供 jQuery Migrate 讓這些功能先補回來繼續用。

目前 jQuery 3.x 支援的瀏覽器環境,以今天的角度來看其實還是很誇張:「Browser Support」,桌機上有 IE9+ (在 Windows Vista SP2 以及之後的版本),而行動裝置上 Android 是 4.0+ (2011 年),Safari 是 iOS 7+ (iPhone 4,CDMA 版 2011 年)。

即使是 jQuery 4 (目前是 beta,參考「jQuery 4.0.0 BETA!」) 也還是支援 IE11 (Windows 7 SP1),算是對於舊系統照顧的很好的 javascript library。

Google 推出 Jpegli:JPEG 的 encoder 以及 decoder

Hacker News 上看到「Jpegli: A new JPEG coding library (googleblog.com)」,原文是「Introducing Jpegli: A New JPEG Coding Library」。

裡面是有提到檔案大小可以更小:

Our results show that Jpegli can compress high quality images 35% more than traditional JPEG codecs.

但這邊沒有講壓縮率的部分是哪個「traditional JPEG codec」比較,大概就是「WebP 的檔案大小未必比 JPEG 小...」這邊的老招了,應該是跟 cjpeg 比,如果跟 MozJPEG 比的話就未必有那麼高了。

想要寫起來的是 Hacker News 留言有提到命名的邏輯,這個 -li 結尾的用法可以看出來是 Google 蘇黎世團隊的產品:

The suffix -li is used in Swiss German dialects. It forms a diminutive of the root word, by adding -li to the end of the root word to convey the smallness of the object and to convey a sense of intimacy or endearment.

This obviously comes out of Google Zürich.

這點還可以從其他的產品看到類似的命名,比較熟的是 Zopfli 以及 Brotli

Go 的 net/http 在 1.22 的 routing 新功能

Gonet/http 在 1.22 引入了更方便的 pattern matching:「Routing Enhancements for Go 1.22」。

用官方的範例,現在可以處理路徑裡的參數了:

http.Handle("GET /posts/{id}", handlePost2)

後續可以透過 PathValue() 取出來:

idString := req.PathValue("id")

而優先順序則是依照吻合度定義:

The precedence rule is simple: the most specific pattern wins. This rule matches our intuition that posts/latests should be preferred to posts/{id}, and /users/{u}/posts/latest should be preferred to /users/{u}/posts/{id}. It also makes sense for methods. For example, GET /posts/{id} takes precedence over /posts/{id} because the first only matches GET and HEAD requests, while the second matches requests with any method.

但是當有重疊卻無法判斷相對吻合度的 rule 被加進去時,會直接 panic()

What if two patterns overlap but neither is more specific? For example, /posts/{id} and /{resource}/latest both match /posts/latest. There is no obvious answer to which takes precedence, so we consider these patterns to conflict with each other. Registering both of them (in either order!) will panic.

這的確是種方法啦... 而且留有之後處理的空間,真的有好的方法就可以把 panic() 的邏輯改成新的共識。

jQuery 4.0.0 Beta (啊,居然)

看到 jQuery 的公告「jQuery 4.0.0 BETA!」這篇,有種「啊,居然」的感覺冒出來...

要注意這個版本放掉了 IE10 以及更早的版本,但還是有支援 IE11,目前計畫到 jQuery 5.0 才會拔掉:

jQuery 4.0 drops support for IE 10 and older. Some may be asking why we didn’t remove support for IE 11. We plan to removes support in stages, and the next step will happen in jQuery 5.0.

另外一個頗大的改變是 source 端改成 ES module 了,這樣對 jQuery 團隊開發上應該會方便不少 (很多現代工具的引入):

jQuery source migrated to ES modules

It was a special day when the jQuery source on the main branch was migrated from AMD to ES modules. The jQuery source has always been published with jQuery releases on npm and GitHub, but could not be imported directly as modules without RequireJS, which was jQuery’s build tool of choice. We have since switched to Rollup for packaging jQuery. And we also run tests on the ES modules before packaging them.

這有種古蹟改建的味道啊...