🛠️

Codemod PlatformでCodemodがより身近になる日が来るかもしれない

2024/08/02に公開

Codemod Platform とは

Codemod Platform は codemod の開発とシェアに特化したプラットフォームです。
様々な開発者が開発した codemod を VSCode の拡張機能・コマンドラインから実行できることで以下のような作業の効率化を目指しています。

  • フレームワークのアップグレード
  • 大規模なリファクタリング
  • 定型的なプログラミング作業

どんな codemod が公開されているのか

公開されている codemod の数 は 160 個ほどです。また、ほとんどがこのツールの開発元自身が作成・公開しているものになっています。(2024/08/01 時点)

codemod の種類に関しては Next.js や React に関する codemod を中心に公開されており、React18 から 19 へのマイグレーションに関する codemod を紹介しているページがあったり、バリデーションのライブラリであるvalibotv0.31.0 へのマイグレーションを行うための codemod もあります。

気になる方はぜひどんなものがあるか確認してみてください。
https://codemod.com/registry

どうやって開発するのか

Codemod Studio というブラウザのエディターを使用して開発することができます。
画面上で AST の確認をしながら jscodeshiftts-morph を使用した codemod の開発が可能です。
タブ切り替えで gpt-4o を利用した質問を投げれたり、テストの実行ができたりといった機能があり、簡単に開発を始めることができます。

まだ選択できませんが、piranha という code engine も今後使用できるようになりそうです。

どこに公開するのか

Codemod Registry という独自のレジストリに作成した codemod を公開することができます。
https://codemod.com/registry

とりあえず試す

簡単にremove-consoleという、JavaScript, Typescript のファイルから console expression (console.log や console.error など)を削除するような codemod を作成してみます。

codemod を作成する

基本的に以下のガイド通りに進めます。
https://docs.codemod.com/guides/building-codemods/build-package#scaffolding-a-codemod-package

init するコマンドを実行

codemod init

codemod の名前を入力します

? Provide a name for your codemod: remove-console

使用する codemod engine を選択します。今回は jscodeshift を使用します。

❯ jscodeshift
  recipe
  ts-morph
  filemod
  ast-grep
  workflow
使用できる codemod engines について

詳しくはこちら
https://docs.codemod.com/guides/building-codemods/package-requirements#supported-codemod-engines

すると最低限の構成で package が作成されます。

Codemod package created at /**/**/remove-console.
✔ Dependencies installed.

まずは.codemodrc.jsonを調整します。このファイルには作成する codemod の詳細な情報を記述します。
https://docs.codemod.com/guides/building-codemods/package-requirements#codemodrc-json-reference

.codemodrc.json
{
  "$schema": "https://codemod-utils.s3.us-west-1.amazonaws.com/configuration_schema.json",
   "name": "typescript/remove-console",
  "version": "1.0.0",
  "private": false,
  "description": "This codemod removes console statements.",
  "engine": "jscodeshift",
  "meta": {
    "tags": ["migration"],
    "git": "https://github.com/yoshi2no/remove-console"
  },
  "include": ["**/*.js", "**/*.ts"]
}

設定が完了したら どのように transform されるべきか、transform 実行前(before)と実行後(after)の結果を意識してテストを書いていきましょう

fixture1.input.ts
const greeting = "hello world!";

console.log("good morning y'all!");

const sayHi = () => {
  console.error("oops!");
};
fixture1.output.ts
const greeting = "hello world!";

const sayHi = () => {};

上記のようにテストを書いたら、とりあえず実行してみます。

 FAIL  test/test.ts > remove-console > test #1
AssertionError: Expected values to be loosely deep-equal:

テストが失敗しました。transform の処理をちゃんと書いていないので当然ですね。では、このテストが成功するように transform の処理を書いていきます。

src/index.ts
const transform: Transform = (
  fileInfo: FileInfo,
  api: API,
  options: Options
) => {
 const j = api.jscodeshift.withParser("tsx");
  const root = j(fileInfo.source);

  root.find(j.CallExpression, {
    callee: {
      object: { name: "console" }
    }
  }).remove();

  return root.toSource();
};

export default transform;

テストを実行してみます。

 ✓ test/test.ts (1)
   ✓ remove-console (1)
     ✓ test #1

 Test Files  1 passed (1)
      Tests  1 passed (1)

うまくいきました。
では、公開しましょう!

codemod を公開する

package のルートディレクトリで publish コマンドを打つだけで公開が完了します

codemod publish
✔ Publishing the codemod using name from .codemodrc.json file: "typescript/remove-console"
Codemod was successfully published to the registry under the name "typescript/remove-console".

Now, you can run the codemod anywhere:
$ codemod typescript/remove-console

公開されました!が、description と example が初期のままなので修正します。

README.md に簡単な説明と before, after のコード例を載せて再度codemod publishすると反映されました。v1.0.1 へのバージョニングも自動でやってくれました。

公開した codemod を実行する

公開されている codemod を実行するには CLI や VSCode の拡張機能から実行できます。

CLI

codemod typescript/remove-console
Execution progress | ████████████████████████████████████████ | 100% || 5/5 files || Current: test/test.ts

VSCode 拡張機能

VSCode のサイドバーから実行したい codemod を指定して実行が可能です。
ただ、筆者が試したときにはなかなか実行が終了しなかったので、当分は CLI から実行したほうが良いかもしれません。

おわりに

個人的に今気になっている Codemod Platform の紹介でした。
これから定期的に Watch していこうと思います 👀


実際に公開した codemod
https://codemod.com/registry/typescript-remove-console

レポジトリ
https://github.com/yoshi2no/remove-console

ファンタラクティブテックブログ

Discussion