## 事象
[[🦉Various Complements]]のリリース作業で実行する[[GitHub Actions]] Releaseジョブが失敗する。
<div class="link-card-v2">
<div class="link-card-v2-site">
<img class="link-card-v2-site-icon" src="https://github.githubassets.com/favicons/favicon.svg" />
<span class="link-card-v2-site-name">GitHub</span>
</div>
<div class="link-card-v2-title">
Release · tadashi-aikawa/obsidian-various-complements-plugin@4b67692
</div>
<div class="link-card-v2-content">
This plugin for Obsidian enables you complete words like the auto-completion of IDE. - Release · tadashi-aikawa/ ...
</div>
<img class="link-card-v2-image" src="https://opengraph.githubassets.com/cea2c8bbc7c6dd8cbcf15e4877ca741e1efd4216898b436841ba5720659c8a96/tadashi-aikawa/obsidian-various-complements-plugin" />
<a href="https://github.com/tadashi-aikawa/obsidian-various-complements-plugin/actions/runs/15806310449/job/44551561088"></a>
</div>
ログの関係箇所。
```console
>
[email protected] typecheck /home/runner/work/obsidian-various-complements-plugin/obsidian-various-complements-plugin
> tsgo -noEmit -skipLibCheck
src/keys.ts:46:15 - error TS2550: Property 'at' does not exist on type 'string[]'. Do you need to change your target library? Try changing the 'lib' compiler option to 'es2022' or later.
46 key: keys.at(-1)!.replace("Space", " "),
~~
src/storage/SelectionHistoryStorage.ts:110:12 - error TS2550: Property 'at' does not exist on type 'number[]'. Do you need to change your target library? Try changing the 'lib' compiler option to 'es2022' or later.
110 .at(-1) ?? 0;
~~
Found 2 errors in 2 files.
Errors Files
1 src/keys.ts:46
1 src/storage/SelectionHistoryStorage.ts:110
```
[[TSConfig]]の[[lib (tsconfig)|lib]]に`es2022`を指定すれば解決すると言われるが、以下のパターンはなぜか成功している。
- [Testsジョブ](https://github.com/tadashi-aikawa/obsidian-various-complements-plugin/actions/runs/15806302390)
- [1か月前くらいのReleaseジョブ](https://github.com/tadashi-aikawa/obsidian-various-complements-plugin/actions/runs/15301842470)
また、ローカルで `pnpm ci` など `tsgo --noEmit -sskipLibCheck` に関するコマンドを実行しても成功する。関連するもののバージョンも同じ。
唯一の違いとしては[[semantic-release]]を通して、その中のスクリプトで実行されているところ。
また、エラーが出るコード箇所に移動し、`at(-1)` の定義に飛んだら、`@types/node/globals.d.ts` を見ており、[[@types.node|@types/node]]のバージョンは20.5.1だった。[[@types.node|@types/node]]は[[🦉Various Complements]]の[[package.json]]には記載がなく、`@jest/globals`の依存でインストールされていた。([[pnpm why]]で確認)
### 環境
省略 (リモートのため)
## 原因
[[Array.prototype.at (JavaScript)|Array.prototype.at]]は[[ES2022]]から実装されたにもかかわらず、[[tsconfig.json]]はそれに対応していないから。
```json
{
"extends": "@tsconfig/svelte/tsconfig.json",
"compilerOptions": {
// 一部抜粋
"module": "ESNext",
"target": "es2018",
"moduleResolution": "bundler",
// es7(ES2016) までしかない
"lib": ["dom", "es5", "es6", "es7"],
},
"include": ["**/*.ts", "**/*.mts"]
}
```
[[ES2022]]のlibと[[@types.node|@types/node]]で同じIFがあったためすり抜けてしまうという厄介な問題。しかも[[Obsidian Mobile]]以外では問題なく動いてしまうのが余計に厄介。
> [!question] ローカルで動いていたのは?
> ローカルで動いていたのは、[[Jest]]によって[[@types.node|@types/node]]がインストールされており、その影響。Testジョブで動いていたのも、[[Jest]]がインストールされていたことによる可能性が高い。
> [!question] Releaseジョブがこのタイミングでエラーになったのは?
> 謎。[[Node.js]]のバージョンがv22.15.0からv22.16.0に上がっているという差分はあるが、ローカルをv22.16.0にアップデートしても差分は発生しなかった。( [[@types.node|@types/node]]は入っている )
## 解決方法
[[Array.prototype.at (JavaScript)|Array.prototype.at]]を使わないようにする。`.at(-1)` であれば `.last()` が[[obsidian.d.ts]]で定義されている。
<div class="link-card-v2">
<div class="link-card-v2-site">
<img class="link-card-v2-site-icon" src="https://github.githubassets.com/favicons/favicon.svg" />
<span class="link-card-v2-site-name">GitHub</span>
</div>
<div class="link-card-v2-title">
obsidian-api/obsidian.d.ts at master · obsidianmd/obsidian-api
</div>
<div class="link-card-v2-content">
Type definitions for the latest Obsidian API. Contribute to obsidianmd/obsidian-api development by creating an a ...
</div>
<img class="link-card-v2-image" src="https://opengraph.githubassets.com/cf9cfd842d315ce2a90737aca540e28ae255508a44b9c7e673b1c78343698525/obsidianmd/obsidian-api" />
<a href="https://github.com/obsidianmd/obsidian-api/blob/master/obsidian.d.ts#L22"></a>
</div>
`at` の完全代替にはならないが、使えそうなものはいくつかある。
### tsconfig.jsonのlibを変更しないほうがいい理由
[[tsconfig.json]]の`lib`に`es2022`を追加したりすることも考えたが、[[Claude Code]]から以下の回答をもらったのでやめたほうがよさそう。多分、[[Obsidian Mobile]]で動かなくなる。
> [!right-bubble] ![[minerva-face-right.webp]]
> obsidian pluginは["dom", "es5", "es6", "es7"]を指定しているのに意味はありそうですか? Webで調べてみて
> [!left-bubble] ![[claude-san-face.webp]]
> 調査結果に基づくと、Obsidianプラグインで["dom", "es5", "es6", "es7"]を指定する理由があります:
>
> 主な理由
>
> 1. モバイル端末との互換性
> - ObsidianはデスクトップだけでなくAndroid/iOSでも動作
> - 古いモバイル端末では最新のWebViewにアップデートできない場合がある
> - プラグインがデスクトップでのみ動作することを避けるため
> 2. 段階的なES機能対応
> - es5, es6, es7を個別指定することで、特定のES機能のみを明示的に利用
> - 意図しない新しいAPI使用を防止
>
> 現在のアプローチ
>
> あなたが"lib": ["dom", "ES2022"]に変更したのは妥当です:
>
> - デスクトップ専用なら問題なし(ES2022は現在のElectron/Chromiumで100%サポート)
> - ES2022には便利な機能が多数(Optional chaining、Nullish coalescing、Promise.allSettled等)
> - TypeScriptのES2022指定は以前のすべてのES機能を自動的に含む
>
> 結論
>
> - クロスプラットフォーム重視:["dom", "es5", "es6", "es7"]
> - デスクトップ専用・モダン機能重視:["dom", "ES2022"]
>
> あなたの変更は技術的に正しく、より簡潔で現代的な設定です。
> [!right-bubble] ![[minerva-face-right.webp]]
> Obsidianのモバイルは https://capacitorjs.jp/ を使っていると思います。この観点でも["dom", "es5", "es6", "es7"]が必要になりますか? ES2022対応してたりしない?
> [!left-bubble] ![[claude-san-face.webp]]
> Capacitorの観点から調査した結果、ES2022サポートは制限的です:
>
> Capacitorの技術的制約
>
> Chrome 60の制限
>
> - Chrome 60リリース: 2017年7月25日
> - サポート範囲: ES2017(ES8)まで
> - ES2022との差: 約5年分の機能ギャップ
>
> ES2022の主要機能(Chrome 60では未対応)
>
> 1. Array.at() メソッド
> 2. Object.hasOwn()
> 3. プライベートクラスフィールド(#privateField)
> 4. Top-level await
> 5. Error.cause
> 6. Static class fields
>
> Android WebViewの現実
>
> - Android 6-10: System WebViewを使用(Chrome 60相当)
> - 更新困難: 古い端末では最新WebViewに更新できない
> - 市場シェア: Android 6+が99%だが、Chrome 60制約あり
>
> 結論
>
> ["dom", "es5", "es6", "es7"]の使用は依然として妥当です:
>
> 理由
> 1. Chrome 60制約: ES2022機能の多くが未対応
> 2. 段階的対応: 明示的にサポートする機能を制御
> 3. モバイル互換性: 古いWebView環境での動作保証
> あなたの["dom", "ES2022"]設定について
>
> - デスクトップ: 完全に問題なし
> - モバイル: 一部機能でエラーの可能性あり
> - 推奨: プラグインがモバイル対応重要なら["dom", "ES2020"]程度が安全
>
> Capacitor使用でもES2022の完全サポートは期待できません。