[小ネタ] Amazon Bedrock AgentCore Code Interpreter で Node.js Runtime が選べるようになっていた

[小ネタ] Amazon Bedrock AgentCore Code Interpreter で Node.js Runtime が選べるようになっていた

2026.04.13

はじめに

こんにちは、ラーメンも大好きなコンサルティング部の神野です。

Amazon Bedrock AgentCore の Code Interpreter は JavaScript / TypeScript を実行できますが、これまではどのランタイムで動いているかをあまり意識していませんでした。それが今回 InvokeCodeInterpreter API の argumentsruntime が追加され、Node.js を明示できるようになりました。

https://awsapichanges.com/archive/changes/08282c-bedrock-agentcore.html

逆に今までの実行環境はDenoだったんですかね。早速試してみようと思います!

前提

  • AWS アカウント
  • Python 3.12 以上(今回は 3.13.11 で確認)
  • boto3 1.42.78 以上(runtime パラメータに対応したバージョン)
  • Bedrock AgentCore Code Interpreter が利用可能なリージョン(今回は us-east-1

何が変わったのか

公式ドキュメントでは、ToolArgumentsruntimenodejs | deno | python が指定でき、未指定時は JavaScript / TypeScript で deno が使われると記載されています。

https://docs.aws.amazon.com/bedrock-agentcore/latest/APIReference/API_ToolArguments.html

また、ランタイム選択のページでは、nodejs Runtime では JavaScript は CommonJS、TypeScript は ESM をサポートすると明記されています。実際に試した結果も、この記載どおりになるか確認してみます。

https://docs.aws.amazon.com/bedrock-agentcore/latest/devguide/code-interpreter-runtime-selection.html

実際にやってみた

セッションを作成する

最初にセッションを作成します。以降のコード片はすべて同じセッションで実行します。

code_interpreter_nodejs.py
import boto3

client = boto3.client("bedrock-agentcore", region_name="us-east-1")

session_response = client.start_code_interpreter_session(
    codeInterpreterIdentifier="aws.codeinterpreter.v1",
    name="nodejs-runtime-test",
    sessionTimeoutSeconds=900,
)

session_id = session_response["sessionId"]
print(f"Session ID: {session_id}")

続けて、実行結果だけを見やすくするための小さなヘルパー関数も用意しておきます。

code_interpreter_nodejs.py
def execute_and_print(code: str, language="javascript", runtime=None):
    arguments = {
        "language": language,
        "code": code,
    }
    if runtime:
        arguments["runtime"] = runtime

    response = client.invoke_code_interpreter(
        codeInterpreterIdentifier="aws.codeinterpreter.v1",
        sessionId=session_id,
        name="executeCode",
        arguments=arguments,
    )

    for event in response["stream"]:
        if "result" not in event:
            continue

        result = event["result"]
        if "structuredContent" not in result:
            continue

        stdout = result["structuredContent"].get("stdout", "")
        stderr = result["structuredContent"].get("stderr", "")

        if stdout:
            print(stdout)
        if stderr:
            print(stderr)

runtime を省略すると Deno のままか

まずは runtime を付けずに JavaScript を実行してみます。Denoprocess の両方を見て、どちらの Runtime で動いているかを確認します。

code_interpreter_nodejs.py
execute_and_print("console.log(typeof Deno); console.log(typeof process);")
実行結果(runtime 未指定)
object
object

Deno グローバルオブジェクトが見えているので、未指定時は従来どおり Deno で動いていますね! process も存在していますが、これは Deno の Node.js 互換レイヤーによるものです。

runtime: "nodejs" で Node.js に切り替わるか

次に、同じコードを runtime: "nodejs" 付きで実行します。

code_interpreter_nodejs.py
execute_and_print(
    "console.log(typeof Deno); console.log(typeof process);",
    runtime="nodejs",
)
実行結果(runtime=nodejs)
undefined
object

今度は Denoundefined になりました。runtime: "nodejs" を渡すと、ちゃんと Node.js Runtime に切り替わっていますね!

Node.js のバージョンを確認する

ついでに、どのバージョンの Node.js が使われているかも見ておきます。

code_interpreter_nodejs.py
execute_and_print("console.log(process.version);", runtime="nodejs")
実行結果
v24.14.0

2026年4月5日に確認した時点では、Node.js v24.14.0 でした。

Node.js の組み込みモジュールを使ってみる

Node.js Runtime で、組み込みモジュールの読み込みと簡単なファイル操作を試します。

code_interpreter_nodejs.py
execute_and_print(
    """
const fs = require("fs");
const os = require("os");

console.log("Platform:", os.platform());
console.log("Architecture:", os.arch());
console.log("Node.js Path:", process.execPath);
console.log("CWD:", process.cwd());
console.log("Temp Dir:", os.tmpdir());

fs.writeFileSync("/tmp/test.txt", "Hello from Node.js runtime!");
const content = fs.readFileSync("/tmp/test.txt", "utf-8");
console.log("File content:", content);
""",
    runtime="nodejs",
)
実行結果
Platform: linux
Architecture: arm64
Node.js Path: /opt/amazon/genesis1p-tools/nodejs/bin/node
CWD: /opt/amazon/genesis1p-tools/var/nodejs-js-execution
Temp Dir: /tmp
File content: Hello from Node.js runtime!

少なくとも組み込みモジュールの require()/tmp へのファイル操作は問題なく動きました。

require() は Deno だと失敗し、Node.js だと通るか

今どき require() を使う場面は少ないかもしれませんが、ランタイムの違いが一番はっきり出るポイントなので確認しておきます。

code_interpreter_nodejs.py
require_test_code = """
try {
    const os = require("os");
    console.log("Platform:", os.platform());
} catch (e) {
    console.log("Error:", e.message);
}
"""

execute_and_print(require_test_code)
実行結果(Deno)
Error: require is not defined
code_interpreter_nodejs.py
execute_and_print(require_test_code, runtime="nodejs")
実行結果(Node.js)
Platform: linux

require() を使う既存の JavaScript を持ち込みたいなら、runtime: "nodejs" を使えば良さそうですね。

JavaScript の import はどうなるか

次に、ESM の import 文を試します。まずは JavaScript です。

code_interpreter_nodejs.py
esm_code = """
import { join } from "node:path";
import { platform } from "node:os";

console.log("Platform:", platform());
console.log("Joined:", join("/tmp", "test", "file.txt"));
"""

execute_and_print(esm_code)
実行結果(Deno)
Platform: linux
Joined: /tmp/test/file.txt
code_interpreter_nodejs.py
execute_and_print(esm_code, runtime="nodejs")
実行結果(Node.js)
SyntaxError: Cannot use import statement outside a module

JavaScript では、Deno はそのまま通りましたが、Node.js Runtime では失敗しました。公式ドキュメントにあるとおり、Node.js Runtime の JavaScript は CommonJS と想定すればOKみたいですね。

For the nodejs runtime, we support CommonJS (CJS) modules for JavaScript and ECMAScript (ESM) modules for TypeScript.

https://docs.aws.amazon.com/bedrock-agentcore/latest/devguide/code-interpreter-runtime-selection.html

TypeScript の import はどうなるか

同じことを TypeScript でも試します。

code_interpreter_nodejs.py
ts_code = """
import { join } from "node:path";

const result: string = join("/tmp", "hello.ts");
console.log("TypeScript result:", result);
console.log("Type check passed!");
"""

execute_and_print(ts_code, language="typescript")
実行結果(Deno + TypeScript)
TypeScript result: /tmp/hello.ts
Type check passed!
code_interpreter_nodejs.py
execute_and_print(ts_code, language="typescript", runtime="nodejs")
実行結果(Node.js + TypeScript)
TypeScript result: /tmp/hello.ts
Type check passed!

TypeScript では Deno / Node.js の両方で import が通りました。ここも公式ドキュメントどおりの結果になりましたね!

補足

なお、Node.js 自体は ESM にも対応していますが、Code Interpreter の Node.js Runtime では JavaScript は CommonJS として実行されるため、import は使えません。同様に、Deno 2.x は require() の互換サポートがありますが、Code Interpreter 上では利用できませんでした。あくまで Code Interpreter 固有の挙動である点に注意してください。

https://nodejs.org/api/esm.html

https://docs.deno.com/runtime/fundamentals/node/#node.js-built-in-modules

実際のところ、最近は TypeScript で書くケースが主流になってきているので、TypeScript であれば Deno / Node.js どちらでも import が使えるという結果のほうが実用上は重要かもしれません。

Strands Agents から Node.js Runtime を使うには

boto3 を直接使った挙動は確認できたので、Strands Agents から使う場合も確認してみます。strands-agents-tools 0.4.1AgentCoreCodeInterpreter は下記のようになっていました。

strands_tools/code_interpreter/agent_core_code_interpreter.py
params = {
    "code": action.code,
    "language": action.language.value,
    "clearContext": action.clear_context,
}

https://github.com/strands-agents/tools

この実装では runtime が渡されていないので、組み込みツール経由では Node.js Runtime を明示できません。2026年4月5日時点では、Node.js Runtime を使いたい場合は code_session を使ったカスタムツールにする形で利用するのかなと思います。

strands_nodejs_agent.py
import json
from strands import Agent, tool
from bedrock_agentcore.tools.code_interpreter_client import code_session

@tool
def execute_nodejs(code: str) -> str:
    """Execute JavaScript code with Node.js runtime."""
    with code_session("us-east-1") as code_client:
        response = code_client.invoke(
            "executeCode",
            {
                "code": code,
                "language": "javascript",
                "runtime": "nodejs",
            },
        )
        for event in response["stream"]:
            if "result" in event:
                return json.dumps(event["result"])
    return ""

agent = Agent(
    tools=[execute_nodejs],
    system_prompt="Use execute_nodejs when you need Node.js runtime.",
)

やっていることはシンプルで、invoke() に渡す引数へ "runtime": "nodejs" を足すだけです。
TypeScript の場合は "language": "typescript" にすればOKです。

おわりに

Node.js 前提のコードを Code Interpreter に持ち込みたいときは、選択肢として考えたいですね。
Strands Agents の組み込みツールは本稿執筆時点では未対応でしたが、カスタムでツールを作ってcode_session を使えば対応はできそうです。

本記事が少しでも参考になりましたら幸いです。最後までご覧いただきありがとうございました!

この記事をシェアする

関連記事