AWS 提供 Console-to-Code 功能

這個是在 Reddit 上看到的:「Convert AWS console actions to reusable code with AWS Console-to-Code, now generally available (aws.amazon.com)」,原文在「Convert AWS console actions to reusable code with AWS Console-to-Code, now generally available」。

先前是在 GCP 上用到這個功能,把操作的指令拉出來改,放到 shell script 裡面管理還蠻好用的。

現在 AWS 搞的是可以錄影轉指令,所以就是把操作都轉換成指令的意思,不過兩者骨子裡還是類似的想法。

從文章裡面有提到,現在的版本只支援 Amazon EC2Amazon VPCAmazon RDS

At GA, AWS Console-to-Code only records actions in Amazon EC2, Amazon VPC and Amazon RDS consoles.

這樣用途就大打折扣了,在 GCP 上這個功能最好用的地方是在還不熟悉的產品上,可以降低你要查一堆文件才知道 web console 上操作對應到 cli 的指令是哪些...

<button> 與 <input type="button"> 的差異

在追奇怪的問題時發現的,實際上是個當年沒學好 (或是太久沒用忘記了),現在回頭重新學的東西,在 Stack Overflow 上很久前就有人問過了:「<button> vs. <input type="button"> -- which to use?」。

我遇到的問題是 <button> 預設會觸發 submit 事件 (<input type="button"> 不會,然後我以為 <button> 也不會)。

而這邊又遇到 <button> 上綁定了 click() 事件的後續行為在 ChromiumFirefox 不同。

我在 click() 事件裡修改某些 input field 後想要觸發 submit() 事件時透過 document.querySelector('#second_submit_button').click() 觸發第二個 submit 按鈕,但在 Chromium 上會走到第一個 submit,而在 Firefox 上則是會走第二個 submit...

不確定這種複雜的行為是怎麼被定義的 (也蠻有機會是沒定義的),所以只先查了比較單純的東西。

首先是現代的 HTML 規格中定義 <button> 的行為是在「The button element」這邊,裡面提到:

The type attribute controls the behavior of the button when it is activated. It is an enumerated attribute with the following keywords and states:

中間列了一張表列出 type 可以設定的值,然後說如果沒有指定 type 的話就是 submit:

The attribute's missing value default and invalid value default are both the Submit Button state.

If the type attribute is in the Submit Button state, the element is specifically a submit button.

知道為什麼後就能夠規劃解法了,解法看起來有兩條路:

第一條是用 <input type="button">,這樣就不會觸發瀏覽器的預設 submit 行為,就不會有後續的分支要處理。

第二條是用 event.preventDefault() 躲開問題,就... 會動。

不過這代表小時候沒學好啊... 如果我記得 <button> 預設會 submit 的話,我就會習慣用 <input type="button">,避免常態性中獎 @_@

Conventional Commits

查資料的時候翻到的,寫 commit 常有 feat: 或是 fix: 這樣的 prefix,剛剛才突然想到這應該是有人訂規範的,翻了一下應該是「Conventional Commits」這個,裡面也引用了另外一個專案:「commitlint」。

所以 type 的部分可以有很多種類,剛剛前面提到的 feat: 以及 fix: 都在裡面:

build
chore
ci
docs
feat
fix
perf
refactor
revert
style
test

對於有規範用英文寫 commit log 的單位可以直接套用,不算太複雜。

馬上想到的好處大概是這樣對於 junior engineer 可以很自然的把 fixfeat 拆開 (其他的也類似),而且對於 code reviewer 也可以注意變化。

64-bit time_t 的事情

看到「The perils of transition to 64-bit time_t (gentoo.org)」這篇,原文在「The perils of transition to 64-bit time_t」,Gentoo 的人在討論將 time_t 從 32-bit 換成 64-bit 遇到的困難。

這邊會想把 32-bit time_t 換到 64-bit time_t 的動力是 32-bit 的 time_t 會在 2038 年遇到 integer overflow,這是接下來的十幾年得想辦法的問題。

不過有意思的是 id=41684857 這邊提到了,當初 FreeBSD 在 porting amd64 時 (大約二十年前) 就直接把一堆變數換成 64-bit 了,其中也包括了 time_t,從第一天解決掉相容性的問題:

Every time I see people struggling with this, I am so incredibly glad that I forced the issue for FreeBSD when I did the initial amd64 port. I got to set the fundamental types in the ABI and decided to look forward rather than backward.

The amd64 architecture did have some interesting features that made this much easier than it might have been for other cpu architectures. One of which was the automatic cast of 32 bit function arguments to 64 bit during the function call. In most cases, if you passed a 32 bit time integer to a function expecting a 64 bit time_t, it Just Worked(TM) during the platform bringup. This meant that a lot of the work on the loose ends could be deferred.

We did have some other 64 bit platforms at the time, but they did not have a 64 bit time_t. FreeBSD/amd64 was the first in its family, back in 2003/2004/2005. If I remember correctly, sparc64 migrated to 64 bit time_t.

這算是個 Day 1 沒換就會有技術債包袱的問題 (遲早還是得換),只是要討論哪種善後的方式是可以接受的。

追 MediaWiki 頁面很慢的問題

我自己有個 wiki 拿來堆一些資料,前陣子覺得 Live 這頁很慢,實際測試發現要跑五秒多,想說到底是什麼鬼...

先從 MediaWiki 的各種 optimization 設定開始看,像是 Manual:Cache 這邊提到的東西,一路看下來看起來都已經設好最佳化了。

只好拿 profiling 工具來翻,在 PHP 上面用的是 Xdebug,裝了以後希望是特殊的情況才跑 profiling,所以參考了「Profiling」這邊的說明,在 php.ini 裡面這樣設定:

xdebug.mode=profile
xdebug.start_with_request=trigger
xdebug.trigger_value=StartProfileForMe

接著依照說明,你要找個地方把這個值傳進去:

Xdebug's profiler will only start when either the environment variable XDEBUG_TRIGGER is set to StartProfileForMe, the GET or POST variable XDEBUG_TRIGGER is set to StartProfileForMe, or when the cookie XDEBUG_TRIGGER has the value StartProfileForMe.

我是在網址列上直接用 ?XDEBUG_TRIGGER=StartProfileForMe 觸發,預設值會把 profiling 結果丟到 /tmp 下面,接下來就是把 callgrind 檔案視覺化了。

首先是把 xdebug 的 callgrind 格式輸出檔案轉成 DOT 格式,這邊參考「Interpreting callgrind data」的說明,先裝 gprof2dot,這個軟體在 PyPI 上有,所以可以用 pipx 裝,接著把 callgrind 轉完後再轉成 PNG 檔案。

我把圖放到最後面 (點開可以看大圖),第一張是 Live 這頁的 profiling,第二張是 Hosting 這頁的。

我注意到在 Live 這頁 php::mysqli 這邊被呼叫了幾千次,這邊就算是本地端的資料庫,幾千次的 latency 累積起來還是很驚人,畢竟是跨 process 之間的溝通,而且已知是 ping-pong 要等待的情況。

接著去翻是什麼造成的,看起來跟 selectRow 有關,但線索到這邊就斷掉了,上面的 User->load 看起來並沒有 loop 導致大量呼叫 selectRow

但至少有個方向,從網路上沒什麼討論看起來,應該不會是本體的效能問題,而是 extension 造成的,從這個角度開始追與帳號 & 權限有關的 extension,第一發懷疑是 Extension:AccessControl 造成的,結果果然沒錯... 拔掉後頁面的速度就從 5.1 秒左右降到 1.5 秒左右了。

沒有實際追程式碼,但猜測是 wiki 裡面用的 Template 造成 AccessControl 都會去檢查權限,加上這邊沒有上 cache,造成頁面上 Template 一多效能很差...

最後,這是 Live 頁的 profiling graph:

這是 Hosting 頁的 profiling graph:

用 C 語言寫 Android 版本的 Flappy Bird

也是在 Hacker News Daily 上看到的專案,用 C 寫的 Android 版本的 Flappy Bird,而且支援度還頗廣的,Android 5.1+ 都可以執行:「VadimBoev/FlappyBird」。

看起來也因為這篇的關係,用 C 寫 Android 程式的計畫也被再次貼到 Hacker News 上:「Rawdrawandroid – Build Android apps without any Java, in C and Make (github.com/cnlohr)」,專案在「cnlohr/rawdrawandroid」這邊,我找了一下之前提過:「用 C 與 Makefile 開發的 Android 專案」。

用 C 寫的好處就是可以很小,像是這次用 C 寫 Flappy Bird 的 Android 版本直接包出 <100KB (對,<0.1MB) 的 ARM 平台 binary package (看起來是 32bit + 64bit 的雙版本),這種大小的遊戲已經很少見了...

不過開發起來又是另外一回事了,應該算是作者的興趣?

LINE 推出的 ts-remove-unused,移除掉沒有用到的程式碼

出國前看到的東西,LINEGitHub 上發表了整理 TypeScript 程式碼的套件:「Show HN: ts-remove-unused – Remove unused code from your TypeScript project (github.com/line)」,專案在「line/ts-remove-unused」這邊:

Remove unused code from your TypeScript project

不過 Hacker News 上的反應其實頗差,其中一個原因是預設值不太友善,沒有好的 ignore path 設定,test case 這種從 entry point 不會接觸到的就會被誤判了:

It deleted 100s of files, most of which were Jest test files, and potentially all of which were a mistake. I restored them all with `git restore $(git ls-files -d)`.

另外改出來的東西是爛的:

I then ran `tsc` on the remaining _modified_ files and `Found 3920 errors in 511 files.`

另外有不少人抱怨預設不是 dry run mode,被砍了一堆東西:

You should switch the default to not delete any files and modify/remove the files only with some flag (--dry-run=false, --rm, --delete, etc). I just deleted all files accidentally in a monorepo :D Luckily I didn't had any uncommitted changes and could recover using git

反倒是有人提了另外一個已經在停止發展,但運作的很好的 project:

I've been using ts-prune[1] for years at this point. The project is in maintenance mode but works fine so I've kept using it. I've been looking into Knip[2] which is recommended by the authors of ts-prune though it's been slow mostly because there's little incentive with the current tool working fine.

[1]: https://github.com/nadeesha/ts-prune

[2]: https://github.com/webpro-nl/knip

這邊反而值得看看...

Winamp 官方放出 Legacy 版本的程式碼

看到「Winamp Legacy player source code (github.com/winampdesktop)」這個,官方放出 Winamp 程式碼:「Winamp」,主要算是歷史的記錄,用電腦聽音樂如果是有設備的人應該會挑 foobar2000 之類的軟體,如果只是隨意聽的話應該就是開各家 streaming 的應用程式?

話說 Nullsoft 做了不少有名的東西,除了 Winamp 以外還有 SHOUTcastNSIS 這兩個比較有名的軟體,不過都算是歷史了。

AWS CodeBuild 宣佈支援 GitLab Runner?

看到 AWS CodeBuild 宣佈支援 GitLab Runner 的公告:「AWS CodeBuild now supports managed GitLab runners」。

第一眼看到有點問號,看了公告說明後的確就是把工作丟進 GitLab Runner 跑:

AWS CodeBuild now supports managed GitLab self-hosted runners. Customers can configure their CodeBuild projects to receive GitLab CI/CD job events and run them on CodeBuild ephemeral hosts.

但沒看懂支援 GitLab Runner 這個的用途... 會用 AWS CodeBuild 的人會需要這個嗎?有自己架 GitLab Runner 的人不是都應該用 GitLab 了嗎?

我再多想看看到底會有什麼情境會這樣架...

nginx 專案搬到 GitHub 上

在「Nginx has moved to GitHub (nginx.org)」看到的,原連結是「[nginx-announce] NGINX has moved to Github!」。

這次搬移也順便將本來是 Mercurial 的專案換到 Git 上了...

Hacker News 有不少人在討論現在 nginx 目前的情況,像是之前有提到分家的事情:「nginx 分家:freenginx」。

不過基本功能都算成熟很久了,算是還好?