<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>負荷テスト - CayTech Lab</title>
	<atom:link href="https://caymezon.com/tag/%e8%b2%a0%e8%8d%b7%e3%83%86%e3%82%b9%e3%83%88/feed/" rel="self" type="application/rss+xml" />
	<link>https://caymezon.com</link>
	<description></description>
	<lastBuildDate>Mon, 17 Aug 2026 04:42:25 +0000</lastBuildDate>
	<language>ja</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=7.0.4</generator>

<image>
	<url>https://caymezon.com/wp-content/uploads/2026/01/cropped-CayTechLab-32x32.jpg</url>
	<title>負荷テスト - CayTech Lab</title>
	<link>https://caymezon.com</link>
	<width>32</width>
	<height>32</height>
</image> 
	<atom:link rel='hub' href='https://caymezon.com/?pushpress=hub'/>
	<item>
		<title>セッション管理があるWebアプリのJMeter負荷テスト：sessionKey動的化のハマりどころ</title>
		<link>https://caymezon.com/jmeter-session-key-testing-guide/</link>
					<comments>https://caymezon.com/jmeter-session-key-testing-guide/#respond</comments>
		
		<dc:creator><![CDATA[caymezon]]></dc:creator>
		<pubDate>Mon, 17 Aug 2026 04:42:25 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[AIエージェント]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[JMeter]]></category>
		<category><![CDATA[セッション管理]]></category>
		<category><![CDATA[正規表現抽出器]]></category>
		<category><![CDATA[負荷テスト]]></category>
		<guid isPermaLink="false">https://caymezon.com/jmeter-session-key-testing-guide/</guid>

					<description><![CDATA[<p>目次 はじめにこの記事で分かることなぜ「記録したシナリオをそのまま再生」が通用しないのか正規表現抽出器でsessionKeyを動的に取得するStep 1: レスポンスの中身を確認するStep 2: 正規表現抽出器を追加す [&#8230;]</p>
<p>The post <a href="https://caymezon.com/jmeter-session-key-testing-guide/">セッション管理があるWebアプリのJMeter負荷テスト：sessionKey動的化のハマりどころ</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></description>
										<content:encoded><![CDATA[<div id="toc" class="toc tnt-number toc-center tnt-number border-element"><input type="checkbox" class="toc-checkbox" id="toc-checkbox-2" checked><label class="toc-title" for="toc-checkbox-2">目次</label>
    <div class="toc-content">
    <ol class="toc-list open"><li><a href="#toc1" tabindex="0">はじめに</a></li><li><a href="#toc2" tabindex="0">この記事で分かること</a></li><li><a href="#toc3" tabindex="0">なぜ「記録したシナリオをそのまま再生」が通用しないのか</a></li><li><a href="#toc4" tabindex="0">正規表現抽出器でsessionKeyを動的に取得する</a><ol><li><a href="#toc5" tabindex="0">Step 1: レスポンスの中身を確認する</a></li><li><a href="#toc6" tabindex="0">Step 2: 正規表現抽出器を追加する</a></li></ol></li><li><a href="#toc7" tabindex="0">抽出した値を後続リクエストに反映させる（JMXファイルの一括置換）</a><ol><li><a href="#toc8" tabindex="0">一括置換の基本の流れ</a></li></ol></li><li><a href="#toc9" tabindex="0">一括置換で実際にハマったポイント</a><ol><li><a href="#toc10" tabindex="0">1. sessionKeyの値が途中で複数存在するケース</a></li><li><a href="#toc11" tabindex="0">2. 置換後に余分な数字が残ってしまうケース</a></li><li><a href="#toc12" tabindex="0">3. コマンドプロンプト経由のPowerShell実行でのエスケープ文字混入</a></li><li><a href="#toc13" tabindex="0">4. JMeterの「保存しますか？」に「はい」と答えると変数が巻き戻る</a></li></ol></li><li><a href="#toc14" tabindex="0">動作確認：正しく動的化できているかの検証手順</a><ol><li><a href="#toc15" tabindex="0">1. 結果をツリーで表示でリクエストの色を確認する</a></li><li><a href="#toc16" tabindex="0">2. 実際に送信された値を目視で確認する</a></li><li><a href="#toc17" tabindex="0">3. JMXファイル内を機械的にチェックする</a></li></ol></li><li><a href="#toc18" tabindex="0">応用：CSRFトークンなど他の動的値にも同じ考え方が使える</a></li><li><a href="#toc19" tabindex="0">この記事のハマりどころまとめ</a></li><li><a href="#toc20" tabindex="0">Udemy講座で「相関（Correlation）」の理解を深めたい方へ</a><ol><li><a href="#toc21" tabindex="0">JMeter — Complete Performance & Load Testing Bootcamp</a></li></ol></li><li><a href="#toc22" tabindex="0">このシリーズの構成</a></li><li><a href="#toc23" tabindex="0">まとめ</a></li></ol>
    </div>
  </div>

<h2><span id="toc1">はじめに</span></h2>
<p>JMeterでシナリオを記録し、実行ボタンを押したら<strong>いきなりConnection resetや500エラーで止まった</strong>——セッション管理のあるJavaのWebアプリを対象に負荷テストを組んだことがある人なら、一度は経験する壁だと思います。</p>
<p>筆者は実務でJavaアプリの画面負荷テストにJMeterを使った際、まさにこの壁にぶつかりました。原因は、ログインのたびにサーバーが発行する<strong>sessionKey（セッション識別用のパラメータ）<strong>が、シナリオ記録時の値のままJMXファイルに固定値として書き込まれてしまうことでした。この記事は、その実体験をベースにした</strong>JMeter実務体験記シリーズの4本目</strong>として、sessionKeyの動的化（パラメータ化）を深掘りします。</p>
<p>JMeterの基本操作がまだの方は、まず基本編（<a href="/jmeter-overview-guide/">JMeterとは？基本概念とインストール</a>）と、ブラウザ操作をそのまま記録する方法を扱った<a href="/jmeter-scenario-recording-guide/">シナリオ記録実践ガイド</a>を先に読んでおくことをおすすめします。この記事は「シナリオの記録は終わっているが、再生すると途中でエラーになる」という状態から話を始めます。</p>
<hr>
<h2><span id="toc2">この記事で分かること</span></h2>
<ul>
<li>セッション管理があるWebアプリで、記録したシナリオをそのまま再生できない理由</li>
<li>正規表現抽出器（Regular Expression Extractor）を使ったsessionKeyの動的取得手順</li>
<li>抽出した値をJMXファイル内の後続リクエストへ反映させる方法（一括置換の実践）</li>
<li>一括置換で実際にハマったポイントと回避策</li>
<li>動的化が正しくできているかを検証する具体的な手順</li>
</ul>
<hr>
<h2><span id="toc3">なぜ「記録したシナリオをそのまま再生」が通用しないのか</span></h2>
<p>JMeterのHTTP(S) Test Script Recorderでブラウザ操作を記録すると、その時にブラウザとサーバーの間でやり取りされた<strong>すべてのパラメータがそのままJMXファイルに書き込まれます</strong>。ログインID・パスワードのような固定値なら問題ありませんが、厄介なのは<strong>ログインのたびにサーバーが動的に発行する値</strong>です。</p>
<p>多くのJava系Webアプリ（Spring Boot・Struts系フレームワークなど）では、セッションを以下の2つの仕組みで二重に管理しています。</p>
<table>
<thead>
<tr>
<th>仕組み</th>
<th>内容</th>
</tr>
</thead>
<tbody>
<tr>
<td>Cookie（<code>JSESSIONID</code>）</td>
<td>JMeterのHTTPクッキーマネージャが自動的に管理・引き継いでくれる</td>
</tr>
<tr>
<td>URLパラメータ／POSTパラメータの<code>sessionKey</code>（アプリ独自の命名の場合もある）</td>
<td><strong>JMeterが自動では面倒を見てくれない</strong>。記録時の値がJMXにハードコードされる</td>
</tr>
</tbody>
</table>
<p>再生時、HTTPクッキーマネージャのおかげで新しい<code>JSESSIONID</code>は正しく発行されるのですが、URLパラメータの<code>sessionKey</code>は記録時の固定値のまま送信されてしまいます。サーバー側がこの2つの整合性をチェックしている場合、「Cookieは新しいセッションなのに、sessionKeyは古い記録時の値」という矛盾した状態になり、サーバーがリクエストを拒否します。</p>
<p>実際に発生する症状はアプリの実装によってさまざまですが、代表的なものは以下の通りです。</p>
<ul>
<li><strong>Connection reset</strong>（コネクション強制切断）</li>
<li><strong>500 Internal Server Error</strong></li>
<li>ログイン直後の画面（初期表示リクエスト）だけは成功し、<strong>その次のリクエストから失敗し始める</strong>（セッション確立自体は成功しているため）</li>
</ul>
<p>この最後の特徴は原因の切り分けに役立ちます。<strong>「最初の1〜2リクエストだけ緑（成功）で、その後が軒並み赤（失敗）」というパターンが出たら、まずsessionKey系のパラメータを疑う</strong>というのが実務での経験則です。</p>
<p><!-- ![結果をツリーで表示で最初のリクエストだけ成功しその後が失敗しているスクリーンショット](images/result-tree-session-error.jpg) --></p>
<hr>
<h2><span id="toc4">正規表現抽出器でsessionKeyを動的に取得する</span></h2>
<p>対処法は、<strong>ログイン直後のレスポンスからsessionKeyの値を毎回自動で読み取り、後続のリクエストに動的に渡す</strong>ことです。JMeterではこれを「後処理（Post Processor）」の一つである**正規表現抽出器（Regular Expression Extractor）**で実現します。</p>
<h3><span id="toc5">Step 1: レスポンスの中身を確認する</span></h3>
<p>まず、ログイン直後の画面初期表示リクエスト（記録時に最初に成功しているリクエスト）を「結果をツリーで表示」リスナーで選択し、「応答データ」タブでHTMLの中身を確認します。多くの場合、以下のようなhidden inputフィールドとしてsessionKeyの値が埋め込まれています。</p>
<pre><code class="language-html">&lt;input type="hidden" id="sessionKey" name="sessionKey" value="1406005051" /&gt;</code></pre>
<p>この<code>value</code>属性の値が、リクエストのたびに変わる動的な値です。フィールド名やid属性の付け方はアプリのフレームワークによって異なるため、まずは自分の対象システムでどう埋め込まれているかを確認するのが最初のステップになります。</p>
<h3><span id="toc6">Step 2: 正規表現抽出器を追加する</span></h3>
<p>ログイン直後のリクエスト（初期表示リクエスト）を左ペインで選択し、右クリック→追加→後処理→<strong>正規表現抽出器</strong>を追加します。</p>
<table>
<thead>
<tr>
<th>設定項目</th>
<th>設定値の例</th>
<th>補足</th>
</tr>
</thead>
<tbody>
<tr>
<td>参照名</td>
<td><code>sessionKey</code></td>
<td>以降<code>${sessionKey}</code>という変数名で参照できるようになる</td>
</tr>
<tr>
<td>正規表現</td>
<td><code>id=&quot;sessionKey&quot; value=&quot;(.+?)&quot;</code></td>
<td>実際のHTML構造に合わせて調整する。<code>(.+?)</code>が値をキャプチャする部分</td>
</tr>
<tr>
<td>テンプレート</td>
<td><code>$1$</code></td>
<td>1つ目のキャプチャグループを使う、という意味</td>
</tr>
<tr>
<td>一致番号（0でランダム）</td>
<td><code>1</code></td>
<td>複数マッチした場合に何番目を使うか。1件目でよければ<code>1</code></td>
</tr>
<tr>
<td>初期値</td>
<td><code>NOT_FOUND</code></td>
<td>抽出に失敗した場合の値。失敗時にすぐ気づけるようにしておく</td>
</tr>
</tbody>
</table>
<p><code>NOT_FOUND</code>を初期値にしておくと、抽出がうまくいかなかった場合にリクエストのパラメータに<code>NOT_FOUND</code>という文字列がそのまま入るため、失敗に気づきやすくなります（数値が入るはずの場所に文字列が入っていれば一目瞭然です）。</p>
<p>設定後は必ずJMeterで保存し、この時点で一度1スレッドだけデバッグ実行して、変数<code>${sessionKey}</code>に実際の値が格納されているか（「結果をツリーで表示」の該当リクエストで、後処理タブや変数を確認）をチェックしておくと、次のステップで問題を切り分けやすくなります。</p>
<hr>
<h2><span id="toc7">抽出した値を後続リクエストに反映させる（JMXファイルの一括置換）</span></h2>
<p>正規表現抽出器を追加しただけでは、まだ何も変わりません。<strong>後続のすべてのリクエストで、記録時に固定値として埋め込まれたsessionKeyを<code>${sessionKey}</code>という変数参照に書き換える</strong>作業が必要です。</p>
<p>リクエスト数が数個であればJMeterのGUI上で1つずつ書き換えても構いませんが、実際の業務システムのシナリオでは数十〜数百箇所に同じ固定値が出現することも珍しくありません。この場合は、<strong>JMXファイル（実体はXML）をテキストエディタ・スクリプトで一括置換</strong>するのが現実的です。</p>
<h3><span id="toc8">一括置換の基本の流れ</span></h3>
<ol>
<li>JMeterを<strong>閉じた状態で</strong>JMXファイルを開く（JMeterが開いたまま編集すると、保存時に上書きされてしまう）</li>
<li>記録時のsessionKey固定値（何箇所出現するか事前に検索して確認）を特定する</li>
<li><code>検索: [固定値の数値] → 置換: ${sessionKey}</code> で一括置換する</li>
<li>JMeterを再起動してJMXファイルを開き直し、デバッグ実行で確認する</li>
</ol>
<p>以下はPowerShellでの置換スクリプトの例です（実際に使う際はファイルパス・置換対象の値を自分のJMXに合わせて書き換えてください）。</p>
<pre><code class="language-powershell">$file = 'jmx\scenario.jmx'
$bytes = [System.IO.File]::ReadAllBytes($file)
$text = [System.Text.Encoding]::UTF8.GetString($bytes)

# 記録時のsessionKey固定値を指定（記録ごとに値が変わるので事前に確認する）
$keys = @('-715584741', '-411593308')

foreach ($key in $keys) {
    $text = $text.Replace($key, '${sessionKey}')
}

$utf8NoBom = New-Object System.Text.UTF8Encoding $false
[System.IO.File]::WriteAllText($file, $text, $utf8NoBom)

Write-Host "置換完了"</code></pre>
<p>JMXファイルはUTF-8のXMLなので、書き戻す際は<strong>BOMなしUTF-8</strong>で保存することを意識しておくと、後々の文字コード絡みのトラブルを避けられます。</p>
<hr>
<h2><span id="toc9">一括置換で実際にハマったポイント</span></h2>
<p>ここからが、実務でこの作業をやってみて実際につまずいた点です。単純な文字列置換に見えて、いくつか見落としやすい罠がありました。</p>
<h3><span id="toc10">1. sessionKeyの値が途中で複数存在するケース</span></h3>
<p>一つのシナリオの中で、<strong>ログイン直後に発行される値</strong>と、<strong>別の画面に遷移した後に再発行される値</strong>の2種類が混在していることがありました。片方だけ置換して満足していると、後半のリクエストだけ失敗し続けるという状態になります。置換前に、JMXファイル内でそれらしき数値パターンが<strong>何種類・何箇所出現するか</strong>を必ず確認してから作業する習慣をつけておくと安全です。</p>
<h3><span id="toc11">2. 置換後に余分な数字が残ってしまうケース</span></h3>
<p>JMeterのHTTPプロキシサーバーには、記録したリクエストの名前に連番を自動付与する機能があります。この連番がたまたまパラメータの値の末尾にくっついて記録されてしまうことがあり、単純な文字列置換をすると<code>${sessionKey}-261</code>のように<strong>変数の後ろに余計な数字が残る</strong>ケースがありました。この場合は、置換後にさらに正規表現で末尾の余分な数字を除去する処理を挟む必要があります。</p>
<pre><code class="language-powershell"># ${sessionKey}-261 のような連番の残骸を除去
$text = [regex]::Replace($text, '\$\{sessionKey\}-\d+', '${sessionKey}')</code></pre>
<h3><span id="toc12">3. コマンドプロンプト経由のPowerShell実行でのエスケープ文字混入</span></h3>
<p><code>cmd.exe</code>経由でPowerShellのワンライナーを実行した際、<code>${sessionKey}</code>の<code>$</code>記号がPowerShell側の変数展開と解釈されないようにバッククォート（<code>`</code>）でエスケープしたところ、**そのバッククォート自体が文字としてファイルに書き込まれてしまい**、<code>`${sessionKey}</code>という壊れた変数参照になっていたことがありました。JMeterはこの状態でも変数を正しく解決できず、リクエストのパラメータに<code>~</code>（チルダ）を含む不正な値が展開されてURLとして無効になる、という分かりにくいエラーにつながりました。</p>
<p><strong>対策は、cmd経由のワンライナーではなく<code>.ps1</code>ファイルとして保存してから実行すること</strong>です。ファイルとして実行すればエスケープの問題が発生しません。</p>
<h3><span id="toc13">4. JMeterの「保存しますか？」に「はい」と答えると変数が巻き戻る</span></h3>
<p>一括置換が完了してJMeterで開き直したところ、一見正しく動いたように見えたのに、次にJMeterを終了する際「変更を保存しますか？」と聞かれて保存を選んだところ、<strong>なぜか置換前の状態（バッククォート付き）に巻き戻ってしまった</strong>ことがありました。JMeterが内部的に変数表記を再解釈してファイルに書き戻す挙動が影響していたようです。</p>
<p>これを踏まえた運用ルールとして、以下を徹底するようにしました。</p>
<blockquote>
<p><strong>JMXファイルの一括置換後、JMeterで開き直した際に「保存しますか？」と聞かれても、正規表現抽出器の追加などGUI上での変更を行っていない限りは「保存しない」を選ぶ。</strong><br />一括置換とJMeter GUI上での編集を同じタイミングで混在させないのが安全です。</p>
</blockquote>
<hr>
<h2><span id="toc14">動作確認：正しく動的化できているかの検証手順</span></h2>
<p>一括置換が終わったら、以下の手順で検証します。</p>
<h3><span id="toc15">1. 結果をツリーで表示でリクエストの色を確認する</span></h3>
<p>1スレッド×1回のループでデバッグ実行し、「結果をツリーで表示」リスナーで<strong>全リクエストが緑（成功）になっているか</strong>を確認します。途中から赤（失敗）が続く場合は、その直前のリクエストの「リクエスト」タブで実際に送信されたパラメータの値を確認し、<code>${sessionKey}</code>が数値に正しく解決されているかをチェックします。</p>
<h3><span id="toc16">2. 実際に送信された値を目視で確認する</span></h3>
<p>「結果をツリーで表示」の該当リクエストの「リクエスト」タブを開き、URLやPOSTデータの中の<code>sessionKey</code>パラメータが<strong>実際のセッションに対応した数値</strong>になっているかを確認します。ここで<code>NOT_FOUND</code>という文字列や、記録時のまま変化しない固定値が見えている場合は、正規表現抽出器の設定（正規表現のパターンや抽出対象のリクエスト）を見直します。</p>
<h3><span id="toc17">3. JMXファイル内を機械的にチェックする</span></h3>
<p>目視だけでなく、置換後のJMXファイルに対して以下のような機械的なチェックを行うと確実です。</p>
<ul>
<li><code>${sessionKey}</code>という文字列が<strong>期待した箇所数だけ</strong>出現しているか（置換前に数えた固定値の出現数と一致するか）</li>
<li>記録時の固定値（元の数値パターン）が<strong>まだ残っていないか</strong>（置換漏れの検出）</li>
<li>バッククォートなど、意図しない文字が変数表記の前後に混入していないか</li>
</ul>
<pre><code class="language-powershell"># 置換後の検証例
$text = Get-Content 'jmx\scenario.jmx' -Raw
([regex]::Matches($text, '\$\{sessionKey\}')).Count   # ${sessionKey}の出現数を確認</code></pre>
<p>この一連の確認をしてから複数スレッドでの実行に進むことで、「スレッド数を増やしてから初めてsessionKey絡みのエラーに気づく」という手戻りを防げます。</p>
<hr>
<h2><span id="toc18">応用：CSRFトークンなど他の動的値にも同じ考え方が使える</span></h2>
<p>sessionKey以外にも、<strong>Spring Bootなどのフレームワークが持つCSRFトークン</strong>や、画面遷移のたびにサーバーが発行する遷移シーケンス番号のような値も、同じ「正規表現抽出器で前の画面のレスポンスから取得し、<code>${変数名}</code>として後続に渡す」というアプローチで対応できます。</p>
<p>考え方はいずれも共通です。</p>
<ol>
<li>固定値のままだと再生時にエラーになる値を特定する</li>
<li>その値がどのレスポンスに含まれているかを確認する</li>
<li>正規表現抽出器で変数化する</li>
<li>後続リクエストの固定値を変数参照に置き換える</li>
<li>動作確認する</li>
</ol>
<p>一つのシナリオの中に動的化が必要な値が複数ある場合は、焦って全部一度に対応しようとせず、<strong>1つずつ動的化→動作確認</strong>のサイクルを回す方が、結果的に原因の切り分けが早くなります。</p>
<hr>
<h2><span id="toc19">この記事のハマりどころまとめ</span></h2>
<table>
<thead>
<tr>
<th>症状</th>
<th>原因</th>
<th>対処</th>
</tr>
</thead>
<tbody>
<tr>
<td>最初の1〜2リクエストは成功、その後が軒並みConnection reset/500</td>
<td>sessionKeyが記録時の固定値のまま送信されている</td>
<td>正規表現抽出器で動的取得し<code>${sessionKey}</code>に置換</td>
</tr>
<tr>
<td>一部のリクエストだけ置換後も失敗する</td>
<td>シナリオ内に複数種類のsessionKey値が混在している</td>
<td>置換対象の値を事前に全種類洗い出す</td>
</tr>
<tr>
<td><code>${sessionKey}-261</code>のような余分な数字が残る</td>
<td>JMeterのリクエスト連番がパラメータ値に混入していた</td>
<td>置換後に正規表現で連番の残骸を除去</td>
</tr>
<tr>
<td>パラメータに<code>~</code>を含む不正な値が展開される</td>
<td>cmd経由のPowerShell実行でバッククォートが混入した</td>
<td><code>.ps1</code>ファイルとして実行する</td>
</tr>
<tr>
<td>置換したはずが元に戻っている</td>
<td>JMeterの「保存しますか？」で保存を選んでしまった</td>
<td>一括置換後は原則「保存しない」を選ぶ</td>
</tr>
</tbody>
</table>
<hr>
<h2><span id="toc20">Udemy講座で「相関（Correlation）」の理解を深めたい方へ</span></h2>
<p>sessionKeyの動的化は、JMeterの世界では一般的に**「相関（Correlation）」**と呼ばれるテクニックの一種です。この記事の内容を実際に手を動かしながらもう一段体系立てて学びたい場合、以下の講座が候補になります。</p>
<h3><span id="toc21">JMeter — Complete Performance & Load Testing Bootcamp</span></h3>
<p>👉 <a href="https://trk.udemy.com/2R7zvg">講座の詳細を見る（Udemyで確認）</a></p>
<p>講師Vishwanatha Hebbar氏による講座で、評価4.3・レビュー1,144件、受講者数10,624名です。カリキュラムの中に「Correlation in JMeter」という独立した講義や、HTTPクッキーマネージャ・パラメータ化（Parameterisation）を扱う講義が含まれており、この記事で扱った内容と直接重なる構成になっています。</p>
<p><strong>メリット</strong></p>
<ul>
<li>「相関（Correlation）」というJMeterの重要概念が独立した講義として用意されており、この記事の内容を体系的な位置付けで復習できる</li>
<li>パラメータ化・クッキーマネージャなど、動的値の扱いに関連する周辺トピックもまとめてカバーしている</li>
<li>分散テストやCI/CD連携など、この記事の範囲を超えた発展的な内容も含む</li>
</ul>
<p><strong>正直なデメリット</strong></p>
<ul>
<li>講義は英語（自動翻訳字幕での視聴が前提になる）</li>
<li>実際の業務アプリ特有の実装（フレームワークごとのフィールド命名など）はカバーされないため、応用は結局自分のアプリのレスポンスを見ながら試行錯誤する必要がある</li>
</ul>
<blockquote>
<p><strong>こんな人におすすめ</strong>：この記事でsessionKey動的化の考え方は掴めたので、「相関」という概念そのものをJMeterの体系の中で位置付けて理解し直したい人。</p>
</blockquote>
<hr>
<h2><span id="toc22">このシリーズの構成</span></h2>
<p>本記事はJMeter実務体験記シリーズの4本目（sessionKey動的化編）です。</p>
<ul>
<li>① <a href="/jmeter-overview-guide/">JMeterとは？基本概念とインストール・環境構築</a> — JMeterの基本概念とWindows環境でのインストール手順</li>
<li>② <a href="/jmeter-scenario-recording-guide/">JMeterでシナリオを記録する実践ガイド</a> — HTTPプロキシサーバー機能を使った画面操作の記録方法</li>
<li>③ <a href="/jmeter-access-log-scenario-design/">本番アクセスログからのJMeterシナリオ設計</a> — 実際のアクセスログを参考にした、実態に近いシナリオの組み立て方</li>
<li>④ sessionKey動的化のハマりどころ（本記事）</li>
<li>⑤ <a href="/jmeter-ai-troubleshooting-story/">AIエージェントとのトラブルシューティング体験記</a> — 実際に発生したエラーをAIエージェントと一緒に切り分けた記録</li>
</ul>
<hr>
<h2><span id="toc23">まとめ</span></h2>
<p>セッション管理があるWebアプリでは、JMeterのHTTPクッキーマネージャに任せておくだけでは不十分で、**URLパラメータやPOSTパラメータに含まれる独自のセッション識別値（sessionKey）**を正規表現抽出器で動的に取得し、後続リクエストに引き継ぐ作業が必須になります。この作業自体はシンプルですが、一括置換の副作用（余分な文字の混入、変数表記の巻き戻りなど）でハマりやすいポイントがいくつもあるため、動作確認を1つずつ丁寧に積み重ねることが結果的に一番の近道でした。</p>
<p>次のステップとして、この動的化作業も含めてAIエージェントと一緒にトラブルシューティングを進めた実際のやり取りをシリーズ⑤で紹介しています。あわせて参考にしてください。</p>
<p>👉 <a href="/jmeter-ai-troubleshooting-story/">AIエージェントとのトラブルシューティング体験記</a></p><p>The post <a href="https://caymezon.com/jmeter-session-key-testing-guide/">セッション管理があるWebアプリのJMeter負荷テスト：sessionKey動的化のハマりどころ</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></content:encoded>
					
					<wfw:commentRss>https://caymezon.com/jmeter-session-key-testing-guide/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>JMeterでシナリオを記録する実践ガイド（HTTP(S) Test Script Recorder）</title>
		<link>https://caymezon.com/jmeter-scenario-recording-guide/</link>
					<comments>https://caymezon.com/jmeter-scenario-recording-guide/#respond</comments>
		
		<dc:creator><![CDATA[caymezon]]></dc:creator>
		<pubDate>Mon, 17 Aug 2026 04:42:16 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[HTTP(S) Test Script Recorder]]></category>
		<category><![CDATA[JMeter]]></category>
		<category><![CDATA[QA]]></category>
		<category><![CDATA[Udemy]]></category>
		<category><![CDATA[オンライン講座]]></category>
		<category><![CDATA[パフォーマンステスト]]></category>
		<category><![CDATA[負荷テスト]]></category>
		<guid isPermaLink="false">https://caymezon.com/jmeter-scenario-recording-guide/</guid>

					<description><![CDATA[<p>目次 はじめにこの記事で分かることHTTP(S) Test Script Recorderとは手動でリクエストを組むより効率的な理由Recorderの設定手順全体構成静的リソースを除外するフィルタ設定（重要）プロキシ設定 [&#8230;]</p>
<p>The post <a href="https://caymezon.com/jmeter-scenario-recording-guide/">JMeterでシナリオを記録する実践ガイド（HTTP(S) Test Script Recorder）</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></description>
										<content:encoded><![CDATA[<div id="toc" class="toc tnt-number toc-center tnt-number border-element"><input type="checkbox" class="toc-checkbox" id="toc-checkbox-4" checked><label class="toc-title" for="toc-checkbox-4">目次</label>
    <div class="toc-content">
    <ol class="toc-list open"><li><a href="#toc1" tabindex="0">はじめに</a></li><li><a href="#toc2" tabindex="0">この記事で分かること</a></li><li><a href="#toc3" tabindex="0">HTTP(S) Test Script Recorderとは</a><ol><li><a href="#toc4" tabindex="0">手動でリクエストを組むより効率的な理由</a></li></ol></li><li><a href="#toc5" tabindex="0">Recorderの設定手順</a><ol><li><a href="#toc6" tabindex="0">全体構成</a></li><li><a href="#toc7" tabindex="0">静的リソースを除外するフィルタ設定（重要）</a></li><li><a href="#toc8" tabindex="0">プロキシ設定（ブラウザ側）</a></li><li><a href="#toc9" tabindex="0">HTTPS環境での証明書設定</a></li></ol></li><li><a href="#toc10" tabindex="0">シナリオを記録する具体的な流れ</a><ol><li><a href="#toc11" tabindex="0">Step 1: 記録を開始する</a></li><li><a href="#toc12" tabindex="0">Step 2: ブラウザで一連の業務操作を行う</a></li><li><a href="#toc13" tabindex="0">Step 3: 記録を停止する</a></li><li><a href="#toc14" tabindex="0">Step 4: 記録内容を確認する</a></li><li><a href="#toc15" tabindex="0">Step 5: プロキシ設定を元に戻す</a></li></ol></li><li><a href="#toc16" tabindex="0">記録後のシナリオ整理</a><ol><li><a href="#toc17" tabindex="0">1. 不要なリクエストの削除</a></li><li><a href="#toc18" tabindex="0">2. リクエストへの名前付け</a></li><li><a href="#toc19" tabindex="0">3. Think Time（操作間隔）の調整</a></li></ol></li><li><a href="#toc20" tabindex="0">jmxファイルとして保存・管理するポイント</a></li><li><a href="#toc21" tabindex="0">AIエージェントにシナリオを解析・整理させる活用アイデア</a></li><li><a href="#toc22" tabindex="0">まとめ</a></li></ol>
    </div>
  </div>

<h2><span id="toc1">はじめに</span></h2>
<p>JMeterで負荷テストを組む際、最初の壁になりやすいのが「テストシナリオ（HTTPリクエストの並び）をどう作るか」です。ログイン→画面遷移→データ登録、といった一連の業務操作をHTTPリクエストとして手作業で組み立てるのは非常に骨が折れますが、JMeterには<strong>HTTP(S) Test Script Recorder</strong>というブラウザ操作をそのまま記録できる機能が用意されています。</p>
<p>この記事は、実際にJava製のWebアプリケーションを対象にRecorderを使ってシナリオを記録した実務経験をもとに、手順と実際にハマったポイントをまとめた実践ガイドです。</p>
<blockquote>
<p>まだJMeterを触ったことがない方は、先に基本編（<a href="/jmeter-overview-guide/">JMeterとは？基本概念とインストール</a>）で全体像とインストール方法を確認しておくことをおすすめします。この記事はJMeterのインストールが完了している前提で、シナリオ記録の手順にフォーカスします。</p>
</blockquote>
<p>体系的にJMeterを学びたい方には、Udemyの講座も選択肢になります。特に<a href="https://trk.udemy.com/2R7zvg">JMeter — Complete Performance & Load Testing Bootcamp</a>（Vishwanatha Hebbar講師）は、この記事のテーマであるHTTP(S) Test Script Recorderの使い方に14分程度の専用レクチャーを割いて解説しており、証明書設定やBlazeMeterプラグインとの使い分けまでカバーしています。全25セクション・約36時間とボリュームがあるため、記録以外の負荷テスト全体（シナリオ設計・実行・結果分析）まで体系的に学びたい人に向いています。</p>
<p>👉 <a href="https://trk.udemy.com/2R7zvg">講座の詳細を見る（Udemyで確認）</a></p>
<hr>
<h2><span id="toc2">この記事で分かること</span></h2>
<ul>
<li>HTTP(S) Test Script Recorderとは何か、手動でHTTPリクエストを組むより何が効率的なのか</li>
<li>Recorderの設定手順（プロキシ設定・証明書設定を含む）</li>
<li>ブラウザ操作をキャプチャしてシナリオを記録する具体的な流れ</li>
<li>記録後にやっておくべきシナリオ整理（不要なリクエストの除去・静的リソースの除外設定）</li>
<li>jmxファイルとして保存・管理する際のポイント</li>
<li>AIエージェント（Claude Code等）に記録済みシナリオを解析・整理させる活用アイデア</li>
</ul>
<hr>
<h2><span id="toc3">HTTP(S) Test Script Recorderとは</span></h2>
<p>HTTP(S) Test Script Recorderは、JMeterが内蔵しているローカルプロキシサーバーです。ブラウザの通信をこのプロキシ経由に設定した状態で画面を操作すると、ブラウザとサーバーの間でやり取りされたHTTPリクエストをJMeterがそのままキャプチャし、テスト計画の中にHTTPリクエストサンプラーとして自動で並べてくれます。</p>
<p>JMeter 5.x系では、日本語UIでは「<strong>HTTPプロキシサーバ</strong>」という名前で表示されます。内部的な機能名（HTTP(S) Test Script Recorder）と日本語表示名（HTTPプロキシサーバ）が異なるため、日本語版JMeterでメニューを探すときは「Non-Testエレメント → HTTPプロキシサーバ」を選ぶ点に注意してください。</p>
<h3><span id="toc4">手動でリクエストを組むより効率的な理由</span></h3>
<table>
<thead>
<tr>
<th>方法</th>
<th>手間</th>
<th>正確性</th>
</tr>
</thead>
<tbody>
<tr>
<td>手動でHTTPリクエストサンプラーを組む</td>
<td>パラメータ・ヘッダー・Cookieを1件ずつ手打ちする必要があり非常に時間がかかる</td>
<td>入力ミスが起きやすい、セッション管理系のパラメータを見落としやすい</td>
</tr>
<tr>
<td>Recorderで記録</td>
<td>ブラウザで通常通り操作するだけ</td>
<td>実際に発生したリクエストをそのまま取得できるため抜け漏れが少ない</td>
</tr>
</tbody>
</table>
<p>特に、ログイン後に発行されるセッションID・CSRFトークンのような<strong>動的なパラメータ</strong>は、手動で組むと見落としがちです。Recorderであれば実際の通信をそのままキャプチャするため、まず「動いているシナリオ」を素早く作れるのが最大のメリットです（動的パラメータの変数化そのものは記録後の別作業になります。この点は<a href="/jmeter-session-key-testing-guide/">sessionKey動的化のハマりどころ</a>で詳しく扱います）。</p>
<hr>
<h2><span id="toc5">Recorderの設定手順</span></h2>
<h3><span id="toc6">全体構成</span></h3>
<p>まずテスト計画に以下の要素を追加します。</p>
<pre><code class="language-plaintext">テスト計画
└── スレッドグループ
    ├── HTTPクッキーマネージャ        ← セッション維持に必須
    └── 記録コントローラ              ← 記録の格納先
              （日本語版では「記録コントローラ」、英語版では Recording Controller）
テスト計画（直下）
└── HTTPプロキシサーバ                ← プロキシ本体
              （英語版では HTTP(S) Test Script Recorder）</code></pre>
<ol>
<li><strong>スレッドグループを追加</strong><br />テスト計画を右クリック → 追加 → Threads(Users) → スレッドグループ</li>
<li><strong>HTTPクッキーマネージャを追加</strong><br />スレッドグループを右クリック → 追加 → 設定エレメント → HTTPクッキーマネージャ（設定はデフォルトのままでOK）。セッションCookieを維持するために、記録前に必ず入れておきます。</li>
<li><strong>記録コントローラを追加</strong><br />スレッドグループを右クリック → 追加 → ロジックコントローラ → 記録コントローラ（記録されたリクエストの格納先になります）</li>
<li><strong>HTTPプロキシサーバを追加</strong><br />テスト計画を右クリック → 追加 → Non-Testエレメント → HTTPプロキシサーバ
<ul>
<li>ポート: <code>8888</code>（デフォルトのままでOK）</li>
<li>対象となるコントローラ: 手順3で作った「記録コントローラ」を選択</li>
</ul>
</li>
</ol>
<p>この「対象となるコントローラ」の指定を間違えると、記録自体は動いているのにリクエストがどこにも格納されない、という事象が起きます。記録が終わったのに記録コントローラの下が空、という場合はまずここを疑ってください。</p>
<h3><span id="toc7">静的リソースを除外するフィルタ設定（重要）</span></h3>
<p>HTTPプロキシサーバの「Requests Filtering」タブにある**「除外するパターン」**に、以下を1行ずつ追加します。</p>
<pre><code class="language-plaintext">.*\.css
.*\.js
.*\.png
.*\.gif
.*\.jpg
.*\.ico
.*\.woff
.*\.woff2
.*\.ttf
.*\.svg</code></pre>
<p>これを設定しておかないと、画面を1つ開くだけでCSS・JS・画像などの静的リソースへのリクエストが何十件も記録され、業務ロジックに関係するリクエストが埋もれてしまいます。実務では、この設定を忘れたまま記録したところ、本来25件程度で済むはずの業務リクエストに対して静的リソースが1,000件以上記録されてしまい、後から手作業で選別する羽目になったことがありました。<strong>記録を始める前に必ず設定しておく</strong>ことを強くおすすめします。</p>
<blockquote>
<p><strong>つまずきポイント</strong>: 除外パターンは「1行に1パターン」で登録する必要があります。カンマ区切りやスペース区切りで1行にまとめて入力すると正規表現として認識されず、除外が効きません。「追加」ボタンで1行ずつ登録してください。</p>
</blockquote>
<p><!-- ![HTTPプロキシサーバのRequests Filtering設定画面](images/proxy-filtering-settings.jpg) --></p>
<h3><span id="toc8">プロキシ設定（ブラウザ側）</span></h3>
<p>Windowsのシステムプロキシ設定を、JMeterのプロキシ（<code>localhost:8888</code>）経由に切り替えます。</p>
<ol>
<li>Windowsの検索バーで「プロキシ」→「プロキシの設定を変更する」を開く</li>
<li>「自動プロキシセットアップ」の「セットアップスクリプトを使う」を<strong>オフ</strong>にする</li>
<li>「手動プロキシセットアップ」で以下を設定
<ul>
<li>プロキシサーバーを使う: <strong>オン</strong></li>
<li>アドレス: <code>localhost</code></li>
<li>ポート: <code>8888</code></li>
</ul>
</li>
<li>「保存」</li>
</ol>
<blockquote>
<p>⚠️ この設定をしている間は、通常のWebアクセス（他サイトの閲覧等）ができなくなります。記録が終わったら忘れずに元に戻してください（手順は後述）。</p>
</blockquote>
<h3><span id="toc9">HTTPS環境での証明書設定</span></h3>
<p>対象アプリがHTTPSの場合、JMeterが動的に生成する証明書をブラウザ側で信頼する必要があります。プロキシ経由でアクセスすると証明書の警告ダイアログが出るので、内容を確認したうえで「信頼する」を選択してください。対象がHTTP（暗号化なし）の場合はこの手順は不要です。</p>
<hr>
<h2><span id="toc10">シナリオを記録する具体的な流れ</span></h2>
<h3><span id="toc11">Step 1: 記録を開始する</span></h3>
<p>HTTPプロキシサーバの設定画面で「<strong>開始</strong>」ボタンを押します。証明書の警告ダイアログが出た場合はここで許可を確定させてください（自動的に閉じてしまい許可し忘れる、というトラブルも実際に起きたので、ダイアログが出たら確実にクリックすることをおすすめします）。</p>
<p>「開始」を押した後、ボタンが「停止」に変わってアクティブになっていることを確認します。ここがグレーアウトしたまま、あるいは反応がない場合はプロキシが正常に起動していない可能性があります。</p>
<h3><span id="toc12">Step 2: ブラウザで一連の業務操作を行う</span></h3>
<p>記録対象のブラウザでアプリにアクセスし、テストしたい一連の操作を通しで行います。例えば以下のような流れです。</p>
<pre><code class="language-plaintext">① ログイン画面を開く
② ID・パスワードを入力してログイン
③ メニュー画面から対象機能を選択
④ 一覧画面で対象データを選択して詳細画面に遷移
⑤ 明細ごとに入力・登録操作を繰り返す（複数件ある場合はその件数分）
⑥ 画面を閉じてメニューに戻る</code></pre>
<p>セッションはログインから始まるため、<strong>記録は必ずログイン操作から含める</strong>のが基本です。途中から記録を始めると、後からログイン部分だけ別途組み立て直す手間が発生します。</p>
<p>操作中の注意点は以下の3つです。</p>
<ul>
<li><strong>普通の操作ペースで行う</strong>: 速すぎる連続操作は記録漏れの原因になることがあります</li>
<li><strong>余計な操作をしない</strong>: 記録中に別タブで無関係なサイトを開いたりすると、それも全部記録されてしまいます</li>
<li><strong>できれば1回でミスなく通す</strong>: 記録はやり直せますが、途中で操作ミスがあると後の整理が余計に大変になります。可能であれば事前にテストデータを用意し、1回できれいに操作を通すのが理想です</li>
</ul>
<h3><span id="toc13">Step 3: 記録を停止する</span></h3>
<p>一連の操作が終わったら、HTTPプロキシサーバの設定画面で「<strong>停止</strong>」ボタンを押します。</p>
<h3><span id="toc14">Step 4: 記録内容を確認する</span></h3>
<p>左ペインの「記録コントローラ」の左にある展開マーク（▶）をクリックし、配下にHTTPリクエストが時系列で並んでいるかを確認します。</p>
<pre><code class="language-plaintext">記録コントローラ
├── /webapp/login.do
├── /webapp/menu/init.do
├── /webapp/menu/select.do
├── /webapp/detail/init.do
├── /webapp/detail/regist.do  ← 1件目
├── /webapp/detail/regist.do  ← 2件目
├── ...
└── /webapp/detail/regist.do  ← N件目</code></pre>
<p><strong>何も表示されていない場合は記録に失敗しています。</strong> よくある原因は以下の3つです。</p>
<table>
<thead>
<tr>
<th>原因</th>
<th>確認方法</th>
</tr>
</thead>
<tbody>
<tr>
<td>プロキシ設定が正しくない</td>
<td>ブラウザからプロキシ経由でアプリにアクセスできているか（アクセスできない時点で記録以前の問題）</td>
</tr>
<tr>
<td>対象となるコントローラの指定ミス</td>
<td>HTTPプロキシサーバの設定で、記録コントローラが正しく選択されているか</td>
</tr>
<tr>
<td>ブラウザが実際にはプロキシを経由していない</td>
<td>特にイントラネット環境で発生しやすい落とし穴です。次の項で詳しく説明します</td>
</tr>
</tbody>
</table>
<blockquote>
<p><strong>実務で実際にハマった例</strong>: プロキシ設定・対象コントローラの指定はすべて正しいのに、ブラウザは問題なくアプリにアクセスできて、それでも記録コントローラが空、という状態に遭遇しました。原因は「ローカル（イントラネット）アドレスにはプロキシサーバーを使わない」というWindowsのプロキシ設定でした。社内向けのホスト名へのアクセスが「ローカルアドレス」と判定されてプロキシがバイパスされ、JMeterを経由していなかったのです。イントラネット環境の対象システムで記録がうまくいかない場合は、この設定と、ブラウザ起動時に<code>--proxy-server</code>オプションでプロキシを直接指定する方法を試してみてください。このあたりの一連のトラブルシューティングの流れは、<a href="/jmeter-ai-troubleshooting-story/">AIエージェントとのトラブルシューティング体験記</a>で詳しく紹介しています。</p>
</blockquote>
<h3><span id="toc15">Step 5: プロキシ設定を元に戻す</span></h3>
<p>記録が終わったら、Windowsのプロキシ設定を元に戻します。</p>
<ol>
<li>「自動プロキシセットアップ」の「セットアップスクリプトを使う」を<strong>オン</strong>に戻す</li>
<li>「手動プロキシセットアップ」の「プロキシサーバーを使う」を<strong>オフ</strong>にする</li>
<li>「保存」</li>
</ol>
<p>これを忘れると、通常のWebアクセスができない状態が続いてしまうので注意してください。</p>
<hr>
<h2><span id="toc16">記録後のシナリオ整理</span></h2>
<p>Recorderで記録した直後のシナリオは、そのままでは負荷テストに使いにくい状態になっていることがほとんどです。以下の整理を行いましょう。</p>
<h3><span id="toc17">1. 不要なリクエストの削除</span></h3>
<p>除外フィルタを設定し忘れていた場合や、フィルタの設定ミス（前述の「1行1パターン」を守っていない等）があった場合、静的リソースへのリクエストが大量に記録されてしまいます。この場合は左ペインで該当リクエストを選択し、手作業で削除します。</p>
<p>また、<code>/favicon.ico</code>や特定ブラウザの自動更新チェック用リクエスト（<code>/connecttest.txt</code>等）のように、業務ロジックと無関係なリクエストが紛れ込むこともあります。除外パターンに追加しておくか、記録後に個別に削除してください。</p>
<h3><span id="toc18">2. リクエストへの名前付け</span></h3>
<p>記録直後のリクエスト名はURLのパスがそのまま使われるため、どの業務操作に対応するのか分かりにくいことがあります。「ログイン」「詳細画面表示」「1件目登録」のように分かりやすい名前を付け直しておくと、後で結果ツリーを見たときの可読性が大きく上がります。</p>
<h3><span id="toc19">3. Think Time（操作間隔）の調整</span></h3>
<p>Recorderは実際の操作間隔をそのまま記録しないため、必要に応じてタイマー（一様乱数タイマー等）を追加し、実際のユーザーの操作間隔に近い待機時間を設定します。本番のアクセスログから実際の操作間隔を逆算する方法は、<a href="/jmeter-access-log-scenario-design/">本番アクセスログからのシナリオ設計</a>で扱います。</p>
<hr>
<h2><span id="toc20">jmxファイルとして保存・管理するポイント</span></h2>
<ul>
<li><strong>業務パターンごとにファイルを分ける</strong>: 複数の業務パターンを記録する場合、最初から1つの巨大なjmxにまとめようとせず、パターンごとに個別のjmxファイルとして保存しておくと、それぞれを単体でデバッグしやすくなります。最終的に複数パターンを統合する場合も、個別ファイルが手元に残っていれば問題箇所の切り分けがしやすくなります。</li>
<li><strong>命名規則を決めておく</strong>: 「対象パターン名_スレッド数_対象環境」のように命名規則を決めておくと、後から見返したときにどの条件で記録・実行したファイルか一目で分かります。</li>
<li><strong>フォルダ構成を最初に決めておく</strong>: jmxファイル置き場、テストデータ（CSV）置き場、実行ログ・レポート出力先を分けておくと、ファイルが増えてきたときに管理しやすくなります。</li>
</ul>
<pre><code class="language-plaintext">project/
├── jmx/     ← テスト計画ファイル（.jmx）
├── data/    ← CSVデータ（ユーザーID、テストデータ等）
├── log/     ← 本番アクセスログの抽出結果など
└── report/  ← 実行結果レポートの出力先</code></pre>
<ul>
<li><strong>バックアップを取ってから編集する</strong>: jmxはXML形式のテキストファイルですが、後述するように機械的な文字列置換（正規表現抽出器の追加やパラメータの変数化など）を行うことが多く、編集に失敗するとXML構造が壊れて開けなくなることがあります。編集前に日時付きでバックアップを取っておく習慣をつけておくと安心です。</li>
</ul>
<hr>
<h2><span id="toc21">AIエージェントにシナリオを解析・整理させる活用アイデア</span></h2>
<p>記録直後のjmxファイルは1行の巨大なXMLになっていることが多く、人間の目でリクエストの中身をひとつずつ追うのは非効率です。ここでClaude CodeのようなAIエージェントを使うと、以下のような作業を効率化できます。</p>
<ul>
<li><strong>リクエスト一覧の抽出</strong>: jmxファイル内の<code>testname</code>属性（各リクエストサンプラーの名前）を抽出させ、記録されたリクエストの全体像を一覧化させる</li>
<li><strong>記録済みシナリオの解析</strong>: 「このjmxファイルにはどんな業務操作が何件記録されているか整理して」と依頼し、記録内容の棚卸しをさせる</li>
<li><strong>複数jmxファイルの統合支援</strong>: あるパターンのシナリオ（例: ログイン〜A画面操作）と別のパターンのシナリオ（例: ログイン〜B画面操作）を1本の統合シナリオにまとめたい場合、それぞれのXMLブロックのうち必要な部分（ログイン部分の重複を除いた業務リクエスト群）を特定し、統合用のスクリプトを組んでもらう</li>
<li><strong>固定値のパラメータ化</strong>: 記録時に埋め込まれてしまったID等の固定値を、CSVデータや変数に置き換えるスクリプトを組んでもらう（sessionKeyのような動的パラメータの変数化については<a href="/jmeter-session-key-testing-guide/">sessionKey動的化のハマりどころ</a>で詳しく扱います）</li>
</ul>
<p>実務で実際にAIエージェントにPowerShellスクリプトでjmxファイルの一括置換をやってもらった際、<strong>PowerShellスクリプト（.ps1）ファイル自体の文字コードが原因で日本語部分が文字化けし、置換がうまく動かない</strong>というトラブルに繰り返し遭遇しました。Windows PowerShell 5.1は、<code>.ps1</code>ファイルに日本語（マルチバイト文字）を含む場合、<strong>BOM付きUTF-8で保存しないと正しく解釈できない</strong>という制約があります。BOMなしのUTF-8で保存すると、システムの既定コードページ（日本語環境ではShift-JIS）として読み込まれてしまい、シングルクォートの対応がずれる、<code>printf</code>の書式指定が文字化けする、といった不可解なエラーが発生します。</p>
<p>AIエージェントにjmxファイルの一括編集用スクリプトを組んでもらう際は、<strong>「日本語を含むPowerShellスクリプトは必ずBOM付きUTF-8で保存すること」を明示的に指示しておく</strong>か、そもそもスクリプト内に日本語のリテラルを含めず外部データファイル（CSV/TSV等）から読み込む方式にしておくと、無用なトラブルを避けられます。</p>
<hr>
<h2><span id="toc22">まとめ</span></h2>
<ul>
<li>HTTP(S) Test Script Recorder（日本語版では「HTTPプロキシサーバ」）を使えば、ブラウザ操作をそのままJMeterのテストシナリオとして記録できる</li>
<li>記録前に「除外するパターン」で静的リソースを除外しておくのが重要（1行1パターンで登録すること）</li>
<li>プロキシ設定・証明書設定・対象コントローラの指定など、記録がうまくいかない原因はいくつかのパターンに絞り込める。特にイントラネット環境ではローカルアドレスのプロキシバイパスに注意</li>
<li>記録後は不要なリクエストの削除・命名・Think Timeの調整といった整理作業が必要</li>
<li>jmxファイルの整理・統合・パラメータ化はAIエージェントに任せると効率化できるが、PowerShellスクリプトの文字コード（BOM付きUTF-8）には注意が必要</li>
</ul>
<p>シナリオが記録できたら、次は実際の業務利用パターンに近づけるための設計や、動的パラメータへの対応が必要になります。</p>
<ul>
<li>次のステップ①: <a href="/jmeter-access-log-scenario-design/">本番アクセスログからのシナリオ設計</a> — 本番のアクセスログを使って、より実態に近い操作パターン・Think Timeを設計する方法</li>
<li>次のステップ②: <a href="/jmeter-session-key-testing-guide/">sessionKey動的化のハマりどころ</a> — 記録時に固定値として埋め込まれてしまう動的パラメータへの対処法</li>
</ul>
<p>体系的にJMeterを学びたい場合は、記事冒頭で紹介したUdemy講座も参考にしてみてください。HTTP(S) Test Script Recorderの使い方だけでなく、負荷テスト全体の設計・実行・分析までカバーされています。</p><p>The post <a href="https://caymezon.com/jmeter-scenario-recording-guide/">JMeterでシナリオを記録する実践ガイド（HTTP(S) Test Script Recorder）</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></content:encoded>
					
					<wfw:commentRss>https://caymezon.com/jmeter-scenario-recording-guide/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>JMeterとは？基本概念とインストール・環境構築【Windows11対応】</title>
		<link>https://caymezon.com/jmeter-overview-guide/</link>
					<comments>https://caymezon.com/jmeter-overview-guide/#respond</comments>
		
		<dc:creator><![CDATA[caymezon]]></dc:creator>
		<pubDate>Mon, 17 Aug 2026 04:42:06 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[AIエージェント]]></category>
		<category><![CDATA[Claude Code]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[JMeter]]></category>
		<category><![CDATA[パフォーマンステスト]]></category>
		<category><![CDATA[負荷テスト]]></category>
		<guid isPermaLink="false">https://caymezon.com/jmeter-overview-guide/</guid>

					<description><![CDATA[<p>目次 はじめにこの記事で分かることJMeterとは対応プロトコルJMeterでできることなぜAIエージェント（Claude Code等）と組み合わせると効率的かインストール手順（Windows11対応）Java実行環境の [&#8230;]</p>
<p>The post <a href="https://caymezon.com/jmeter-overview-guide/">JMeterとは？基本概念とインストール・環境構築【Windows11対応】</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></description>
										<content:encoded><![CDATA[<div id="toc" class="toc tnt-number toc-center tnt-number border-element"><input type="checkbox" class="toc-checkbox" id="toc-checkbox-6" checked><label class="toc-title" for="toc-checkbox-6">目次</label>
    <div class="toc-content">
    <ol class="toc-list open"><li><a href="#toc1" tabindex="0">はじめに</a></li><li><a href="#toc2" tabindex="0">この記事で分かること</a></li><li><a href="#toc3" tabindex="0">JMeterとは</a><ol><li><a href="#toc4" tabindex="0">対応プロトコル</a></li><li><a href="#toc5" tabindex="0">JMeterでできること</a></li></ol></li><li><a href="#toc6" tabindex="0">なぜAIエージェント（Claude Code等）と組み合わせると効率的か</a></li><li><a href="#toc7" tabindex="0">インストール手順（Windows11対応）</a><ol><li><a href="#toc8" tabindex="0">Java実行環境の要件</a></li><li><a href="#toc9" tabindex="0">JMeter本体のダウンロード・インストール</a></li><li><a href="#toc10" tabindex="0">日本語化（任意）</a></li><li><a href="#toc11" tabindex="0">動作確認</a></li></ol></li><li><a href="#toc12" tabindex="0">基本的な画面構成・テスト計画の階層構造</a><ol><li><a href="#toc13" tabindex="0">スレッドグループ（Thread Group）</a></li><li><a href="#toc14" tabindex="0">HTTPリクエスト（HTTP Request Sampler）</a></li><li><a href="#toc15" tabindex="0">HTTPクッキーマネージャ</a></li><li><a href="#toc16" tabindex="0">タイマー（Timer）</a></li><li><a href="#toc17" tabindex="0">リスナー（結果の収集・表示）</a></li></ol></li><li><a href="#toc18" tabindex="0">Javaの知識があると理解が早くなる場面</a></li><li><a href="#toc19" tabindex="0">Udemy講座で体系的に学びたい方へ</a><ol><li><a href="#toc20" tabindex="0">Learn JMETER from Scratch on Live Apps -Performance Testing</a></li></ol></li><li><a href="#toc21" tabindex="0">このシリーズの構成</a></li><li><a href="#toc22" tabindex="0">まとめ</a></li></ol>
    </div>
  </div>

<h2><span id="toc1">はじめに</span></h2>
<p><strong>Apache JMeter</strong>は、Webアプリケーションの負荷テスト・性能テストに使われるオープンソースツールです。「本番リリース前に、想定される同時アクセス数に耐えられるか確認したい」「特定の画面だけレスポンスが遅くなる原因を調べたい」といった場面で使われます。</p>
<p>筆者は実務でJavaアプリの画面負荷テストにJMeterを使った経験があり、この記事はその実体験をベースにしています。本記事はJMeter入門シリーズの1本目として、<strong>JMeterの基本概念とインストール・環境構築</strong>を扱います。実際にシナリオを記録して負荷をかけるところまでは踏み込まず、まず「JMeterとは何か」「手元の環境をどう整えるか」を押さえることがゴールです。</p>
<p>さらにこのシリーズでは、JMeterの操作そのものだけでなく、<strong>Claude Codeなどの AIエージェントと組み合わせて負荷テストを進めるとどう効率化できるか</strong>という観点も扱っていきます。JMeterはGUI操作が中心の伝統的なツールですが、テスト計画ファイル（JMX）の中身はXMLテキストであり、設定エレメントの追加手順やエラーメッセージの調査はAIエージェントとの相性が良い作業です。</p>
<hr>
<h2><span id="toc2">この記事で分かること</span></h2>
<ul>
<li>Apache JMeterとは何か、何ができるツールなのか</li>
<li>JMeterとAIエージェントを組み合わせるメリット（シリーズ全体の導入）</li>
<li>Windows環境でのインストール手順とJavaの動作要件</li>
<li>テスト計画の基本的な階層構造（スレッドグループ・HTTPリクエストなど）</li>
<li>シリーズ後続記事（シナリオ記録・アクセスログ分析・sessionKey動的化・トラブルシューティング）への案内</li>
</ul>
<hr>
<h2><span id="toc3">JMeterとは</span></h2>
<p>Apache JMeterは、Apacheソフトウェア財団が開発するオープンソースの負荷テストツールです。Webアプリケーションを中心に、さまざまなプロトコルの性能・負荷テストを実施できます。</p>
<table>
<thead>
<tr>
<th>項目</th>
<th>内容</th>
</tr>
</thead>
<tbody>
<tr>
<td>正式名称</td>
<td>Apache JMeter</td>
</tr>
<tr>
<td>ライセンス</td>
<td>Apache License 2.0（無料）</td>
</tr>
<tr>
<td>実装言語</td>
<td>Java（GUI/CUIどちらの実行モードもあり）</td>
</tr>
<tr>
<td>動作要件</td>
<td>Java 8以上（最新版はJava 17以降を推奨）</td>
</tr>
<tr>
<td>公式サイト</td>
<td><a href="https://jmeter.apache.org/">https://jmeter.apache.org/</a></td>
</tr>
</tbody>
</table>
<h3><span id="toc4">対応プロトコル</span></h3>
<p>JMeterはHTTP/HTTPS以外にも幅広いプロトコルに対応しています。</p>
<ul>
<li><strong>HTTP/HTTPS</strong> — Webアプリの画面テスト（本シリーズで扱うメインの用途）</li>
<li><strong>JDBC</strong> — DBに対する直接の負荷テスト</li>
<li><strong>FTP</strong> — ファイル転送テスト</li>
<li><strong>SOAP/REST</strong> — Web APIのテスト</li>
<li><strong>LDAP</strong> — ディレクトリサービスのテスト</li>
<li><strong>JMS</strong> — メッセージキューのテスト</li>
<li><strong>TCP</strong> — 汎用TCP通信のテスト</li>
</ul>
<h3><span id="toc5">JMeterでできること</span></h3>
<ul>
<li>同時接続ユーザーのシミュレーション（数十〜数千ユーザー規模）</li>
<li>シナリオベースのテスト（ログイン→画面操作→ログアウトという一連の流れを再現）</li>
<li>レスポンスタイム・スループット（リクエスト/秒）の計測</li>
<li>リアルタイムグラフ表示</li>
<li>HTMLレポートの自動生成</li>
<li>CSV/XML形式での結果出力</li>
</ul>
<p>「Webサイトに一定数のアクセスが集中したときにどれくらいの応答時間になるか」「エラー率が上がり始めるアクセス数はどこか」といった問いに、実際に近い負荷をかけて答えを出せるのがJMeterの役割です。</p>
<hr>
<h2><span id="toc6">なぜAIエージェント（Claude Code等）と組み合わせると効率的か</span></h2>
<p>JMeterはGUIで設定エレメントをポチポチ追加していく操作が基本のツールです。一見AIエージェントとは縁が薄そうに見えますが、実務で使ってみると相性の良いポイントがいくつもあります。</p>
<table>
<thead>
<tr>
<th>場面</th>
<th>AIエージェントが役立つ理由</th>
</tr>
</thead>
<tbody>
<tr>
<td>テスト計画の設計相談</td>
<td>「スレッドグループを画面パターンごとに分けるべきか、1つにまとめるべきか」といった設計判断を、実務の制約（セッション管理の仕組みなど）を伝えながら相談できる</td>
</tr>
<tr>
<td>JMXファイルの中身の確認・一括置換</td>
<td>JMX（テスト計画ファイル）の実体はXMLテキストなので、正規表現抽出器の設定や固定値のパラメータ化を、GUI操作とファイル編集の両面から支援してもらえる</td>
</tr>
<tr>
<td>エラーメッセージの読み解き</td>
<td>「結果をツリーで表示」リスナーに出るレスポンスエラーやスタックトレースを貼り付けて、原因の仮説出しを手伝ってもらえる</td>
</tr>
<tr>
<td>手順の言語化・ドキュメント化</td>
<td>実施したテストシナリオや設定変更の経緯を、後から読み返せる形にまとめる作業を任せられる</td>
</tr>
</tbody>
</table>
<p>特に効果を感じたのは、<strong>「GUI操作の手順」と「JMXファイルの中身（XML）」を両方参照しながら会話できる</strong>点です。JMeterのGUIだけでは「今どこで何が起きているか」を追いにくい場面でも、AIエージェントにファイルの中身を見せながら質問すると、設定の食い違いに気づきやすくなります。</p>
<p>このシリーズの後続記事（シナリオ記録・アクセスログからのシナリオ設計・sessionKeyの動的化・実際のトラブルシューティング体験記）では、この組み合わせを具体的にどう使ったかを紹介していきます。</p>
<hr>
<h2><span id="toc7">インストール手順（Windows11対応）</span></h2>
<h3><span id="toc8">Java実行環境の要件</span></h3>
<p>JMeterはJavaで動作するツールのため、事前にJavaの実行環境（JRE または JDK）が必要です。</p>
<ul>
<li><strong>最低要件</strong>: Java 8以上</li>
<li><strong>推奨</strong>: Java 17以降（JMeterの最新安定版はJava 17以降を前提にしていることが多いため）</li>
<li>keytool（証明書関連のコマンド）を使う場合はJRE単体ではなくJDKが必要</li>
</ul>
<p>Windowsのコマンドプロンプトまたは PowerShell で、以下のコマンドを実行してJavaのバージョンを確認します。</p>
<pre><code class="language-powershell">java -version</code></pre>
<p>Javaが未インストール、またはバージョンが古い場合は、<a href="https://adoptium.net/">Eclipse Temurin</a>（旧AdoptOpenJDK）などから最新のJDKをインストールしておきます。</p>
<blockquote>
<p>補足：業務で使っているPCの場合、社内標準で古いJavaランタイムがインストール済みのケースもあります。その場合はJMeterのバージョン側をインストール済みのJavaバージョンに合わせて選ぶ（新しすぎるJMeterを使わない）という選択肢もあります。JMeterのバージョンはサーバー側のJavaバージョンに合わせる必要は必ずしもなく、<strong>手元の実行環境（クライアント側）のJavaバージョンに合わせる</strong>のが基本です。</p>
</blockquote>
<h3><span id="toc9">JMeter本体のダウンロード・インストール</span></h3>
<p>JMeterのインストールは、実行ファイルをインストーラーで入れる形式ではなく、<strong>ZIPファイルを展開するだけ</strong>で完了します。</p>
<ol>
<li><a href="https://jmeter.apache.org/download_jmeter.cgi">Apache JMeter公式サイトのダウンロードページ</a>にアクセスする</li>
<li>「Binaries」セクションから <code>apache-jmeter-x.x.x.zip</code> をダウンロードする</li>
<li>任意のフォルダ（例: <code>C:\tools\jmeter</code>）に展開する</li>
<li><code>bin</code> フォルダ内の <code>jmeter.bat</code> をダブルクリックして起動する</li>
</ol>
<pre><code class="language-plaintext">C:\tools\jmeter\
├── bin\
│   ├── jmeter.bat          ← Windowsでの起動用バッチ
│   ├── jmeter               ← macOS/Linux用シェルスクリプト
│   └── ...
├── lib\
├── docs\
└── ...</code></pre>
<p>起動すると、JMeterのGUI画面が立ち上がります。初回起動時は少し時間がかかることがありますが、エラーが出なければインストールは成功です。</p>
<h3><span id="toc10">日本語化（任意）</span></h3>
<p>JMeterのGUIは初期状態では英語表示ですが、メニューから日本語に切り替えられます。</p>
<pre><code class="language-plaintext">Options（オプション） &gt; Choose Language（言語選択） &gt; Japanese</code></pre>
<p>日本語化すると各項目のラベルが日本語になり、初学者には扱いやすくなります。ただし、Web検索で見つかる情報や公式ドキュメントは英語表記が前提になっていることが多いため、慣れてきたら英語表示のまま使うのも一つの選択です。</p>
<h3><span id="toc11">動作確認</span></h3>
<p>インストールが完了したら、起動時にエラーが出ていないかコンソールログ（<code>jmeter.bat</code> を実行したコマンドプロンプトの出力）を確認しておきます。特に以下のようなメッセージが出ていれば、Javaのバージョンとの紐付けも含めて正常に起動できています。</p>
<pre><code class="language-plaintext">Created the tree successfully using ...
Starting the test @ ...</code></pre>
<hr>
<h2><span id="toc12">基本的な画面構成・テスト計画の階層構造</span></h2>
<p>JMeterの操作を理解する上で最初に押さえておきたいのが、<strong>「テスト計画（Test Plan）」を頂点とした階層構造</strong>です。GUI画面の左ペインにはこの階層がツリー表示され、右クリックで各要素を追加していく操作が基本になります。</p>
<pre><code class="language-plaintext">テスト計画 (Test Plan)
├── スレッドグループ (Thread Group)         ← 仮想ユーザー数・ランプアップ時間・ループ回数
│   ├── HTTPリクエスト (HTTP Request)       ← 実際に送信するリクエストの定義
│   ├── HTTPリクエスト ...
│   ├── タイマー (Timer)                    ← リクエスト間の待機時間
│   ├── アサーション (Assertion)            ← レスポンス内容の検証
│   └── 前処理/後処理                       ← 動的パラメータの抽出など
├── HTTPクッキーマネージャ                   ← セッション管理（Cookie）
├── HTTP ヘッダマネージャ                    ← 共通ヘッダの設定
├── CSVデータセット                         ← テストデータの外部ファイル読み込み
└── リスナー (Listener)                     ← 結果の表示・集計
    ├── 結果をツリーで表示
    ├── 統計レポート
    └── グラフ結果</code></pre>
<p><!-- ![JMeterのテスト計画ツリー構造のスクリーンショット](images/test-plan-tree.jpg) --></p>
<h3><span id="toc13">スレッドグループ（Thread Group）</span></h3>
<p>仮想ユーザーの振る舞いを定義する、最も重要なコンポーネントです。</p>
<table>
<thead>
<tr>
<th>設定項目</th>
<th>意味</th>
<th>例</th>
</tr>
</thead>
<tbody>
<tr>
<td>スレッド数</td>
<td>同時に実行する仮想ユーザー数</td>
<td>50</td>
</tr>
<tr>
<td>Ramp-Up期間</td>
<td>全スレッドが起動しきるまでの秒数</td>
<td>10秒（5ユーザー/秒のペースで増加）</td>
</tr>
<tr>
<td>ループ回数</td>
<td>各スレッドが繰り返す回数</td>
<td>10回、または無限</td>
</tr>
</tbody>
</table>
<h3><span id="toc14">HTTPリクエスト（HTTP Request Sampler）</span></h3>
<p>実際にサーバーへ送信するリクエストを定義する要素です。プロトコル・サーバー名・ポート・メソッド（GET/POST）・パス・パラメータなどを設定します。</p>
<h3><span id="toc15">HTTPクッキーマネージャ</span></h3>
<p>多くのWebアプリはログイン後のセッションをCookie（<code>JSESSIONID</code>など）で管理しています。HTTPクッキーマネージャを追加しておくと、JMeterがこのCookieを自動的に管理し、ログイン後のセッションを維持したまま複数リクエストを実行できます。ログインが必要なシステムを対象にする場合は、ほぼ必須の設定です。</p>
<h3><span id="toc16">タイマー（Timer）</span></h3>
<p>実際のユーザーは画面を見ながら次の操作をするまでに間（Think Time）を置きます。この間隔を再現するのがタイマーです。</p>
<table>
<thead>
<tr>
<th>種類</th>
<th>用途</th>
</tr>
</thead>
<tbody>
<tr>
<td>固定タイマー</td>
<td>常に一定間隔（例: 2秒）で次のリクエストを送る</td>
</tr>
<tr>
<td>ガウシアンタイマー</td>
<td>ランダムな待機時間で、実ユーザーの操作に近い揺らぎを再現する</td>
</tr>
<tr>
<td>均一乱数タイマー</td>
<td>指定した範囲内でランダムな待機時間にする</td>
</tr>
</tbody>
</table>
<h3><span id="toc17">リスナー（結果の収集・表示）</span></h3>
<table>
<thead>
<tr>
<th>リスナー名</th>
<th>用途</th>
</tr>
</thead>
<tbody>
<tr>
<td>結果をツリーで表示</td>
<td>デバッグ用。個々のリクエスト/レスポンスの詳細を確認する</td>
</tr>
<tr>
<td>統計レポート</td>
<td>平均・最大・最小レスポンスタイムやエラー率を集計表示する</td>
</tr>
<tr>
<td>グラフ結果</td>
<td>レスポンスタイムの時系列変化をグラフで確認する</td>
</tr>
<tr>
<td>集約レポート</td>
<td>サンプラーごとの集約統計を表形式で確認する</td>
</tr>
</tbody>
</table>
<blockquote>
<p>注意点として、リスナーで結果を詳細表示しながらの実行（GUIモード）はJMeter自体がリソースを消費し、負荷テストの結果に影響を与えます。本番相当の負荷をかける段階では、GUIを使わない<strong>CUIモード</strong>（<code>jmeter -n -t test.jmx -l result.jtl -e -o report/</code>）での実行が推奨されます。この使い分けはシリーズ後続記事で詳しく扱います。</p>
</blockquote>
<hr>
<h2><span id="toc18">Javaの知識があると理解が早くなる場面</span></h2>
<p>JMeter自体はJava製のツールであり、JavaのWebアプリ（Spring Bootなど）を対象にテストする場合、Java側の知識があると原因調査がスムーズになる場面が多くあります。例えばセッション管理の仕組みやCSRFトークンの扱いは、Javaのフレームワークの動作を理解しているかどうかで調査スピードが変わってきます。</p>
<p>これからJavaを体系的に学びたい・資格取得と合わせて基礎を固めたいという方は、以下の記事も参考にしてください。</p>
<p>👉 <a href="https://caymezon.com/java-silver-udemy-courses-guide/">Java Silver（Oracle認定資格） おすすめUdemy講座比較【2026年版】</a></p>
<hr>
<h2><span id="toc19">Udemy講座で体系的に学びたい方へ</span></h2>
<p>ハンズオンで手を動かす前に、JMeterの操作全体を動画でまとめて学びたい場合は、以下の講座が候補になります。</p>
<h3><span id="toc20">Learn JMETER from Scratch on Live Apps -Performance Testing</span></h3>
<p>👉 <a href="https://trk.udemy.com/OYE0Mz">講座の詳細を見る（Udemyで確認）</a></p>
<p>8時間19分・48講義というボリュームで、JMeterの基本操作から実際のアプリケーションを使った負荷テストまでを一通り扱う入門〜初中級向け講座です。評価4.6・レビュー26,000件超、受講者数12万人超と、JMeter関連講座の中でも特に実績が豊富です。講義は英語ですが、Udemyの自動翻訳字幕（日本語含む）に対応しています。</p>
<p><strong>メリット</strong></p>
<ul>
<li>受講者数12万人超・評価4.6という、この分野では際立った実績</li>
<li>「ゼロから」を掲げている通り、JMeter未経験でも迷わず追える構成</li>
<li>スレッドグループ・リスナー・アサーション・コントローラー・タイマー・正規表現抽出など、本記事や後続記事で扱う要素を体系的にカバー</li>
</ul>
<p><strong>正直なデメリット</strong></p>
<ul>
<li>講義そのものは英語（自動翻訳字幕での視聴が前提になる）</li>
<li>実務の細かいユースケース（社内システム特有のセッション管理など）までは当然カバーしていないため、応用は自分で行う必要がある</li>
</ul>
<blockquote>
<p><strong>こんな人におすすめ</strong>：この記事でJMeterの概念は掴めたので、次は動画で実際の操作画面を見ながら体系的に基礎を固めたい人。</p>
</blockquote>
<hr>
<h2><span id="toc21">このシリーズの構成</span></h2>
<p>本記事はJMeter実務体験記シリーズの1本目（基礎編）です。実際にシナリオを記録して負荷をかけ、トラブルを解決していく後続記事もあわせてご覧ください。</p>
<ul>
<li><strong>① JMeterとは？基本概念とインストール・環境構築</strong>（本記事）</li>
<li>② <a href="https://caymezon.com/jmeter-scenario-recording-guide/">JMeterでシナリオを記録する実践ガイド</a> — HTTPプロキシサーバー機能を使った画面操作の記録方法</li>
<li>③ <a href="https://caymezon.com/jmeter-access-log-scenario-design/">本番アクセスログからのJMeterシナリオ設計</a> — 実際のアクセスログを参考にした、実態に近いシナリオの組み立て方</li>
<li>④ <a href="https://caymezon.com/jmeter-session-key-testing-guide/">sessionKey動的化のハマりどころ</a> — 正規表現抽出器を使ったセッション値の動的パラメータ化と、そこで起きたトラブル</li>
<li>⑤ <a href="https://caymezon.com/jmeter-ai-troubleshooting-story/">AIエージェントとのトラブルシューティング体験記</a> — 実際に発生したエラーをAIエージェントと一緒に切り分けた記録</li>
</ul>
<hr>
<h2><span id="toc22">まとめ</span></h2>
<p>JMeterは、Webアプリの同時アクセスをシミュレーションしてレスポンスタイムやエラー率を計測できる、無料のオープンソース負荷テストツールです。インストール自体はZIPを展開するだけとシンプルですが、テスト計画の階層構造（スレッドグループ・HTTPリクエスト・クッキーマネージャ・タイマー・リスナー）を理解しておくと、この後のシナリオ作成がぐっとスムーズになります。</p>
<p>次のステップとして、実際にブラウザ操作を記録してテストシナリオを組み立てる方法をシリーズ②で解説しています。あわせて参考にしてください。</p>
<p>👉 <a href="https://caymezon.com/jmeter-scenario-recording-guide/">JMeterでシナリオを記録する実践ガイド</a></p><p>The post <a href="https://caymezon.com/jmeter-overview-guide/">JMeterとは？基本概念とインストール・環境構築【Windows11対応】</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></content:encoded>
					
					<wfw:commentRss>https://caymezon.com/jmeter-overview-guide/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>AIエージェントと二人三脚で進める負荷テストのトラブルシューティング体験記</title>
		<link>https://caymezon.com/jmeter-ai-troubleshooting-story/</link>
					<comments>https://caymezon.com/jmeter-ai-troubleshooting-story/#respond</comments>
		
		<dc:creator><![CDATA[caymezon]]></dc:creator>
		<pubDate>Mon, 17 Aug 2026 04:41:58 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[AIエージェント]]></category>
		<category><![CDATA[Claude Code]]></category>
		<category><![CDATA[JMeter]]></category>
		<category><![CDATA[PowerShell]]></category>
		<category><![CDATA[トラブルシューティング]]></category>
		<category><![CDATA[体験記]]></category>
		<category><![CDATA[負荷テスト]]></category>
		<guid isPermaLink="false">https://caymezon.com/jmeter-ai-troubleshooting-story/</guid>

					<description><![CDATA[<p>目次 はじめにこの記事で分かること第1話：記録はできたのに、再生すると繋がらない第2話：犯人はプロキシだと思っていた第3話：本当の犯人はsessionKeyだった第4話：見えないバックティックとの戦い第5話：実はこれ2回 [&#8230;]</p>
<p>The post <a href="https://caymezon.com/jmeter-ai-troubleshooting-story/">AIエージェントと二人三脚で進める負荷テストのトラブルシューティング体験記</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></description>
										<content:encoded><![CDATA[<div id="toc" class="toc tnt-number toc-center tnt-number border-element"><input type="checkbox" class="toc-checkbox" id="toc-checkbox-8" checked><label class="toc-title" for="toc-checkbox-8">目次</label>
    <div class="toc-content">
    <ol class="toc-list open"><li><a href="#toc1" tabindex="0">はじめに</a></li><li><a href="#toc2" tabindex="0">この記事で分かること</a></li><li><a href="#toc3" tabindex="0">第1話：記録はできたのに、再生すると繋がらない</a></li><li><a href="#toc4" tabindex="0">第2話：犯人はプロキシだと思っていた</a></li><li><a href="#toc5" tabindex="0">第3話：本当の犯人はsessionKeyだった</a></li><li><a href="#toc6" tabindex="0">第4話：見えないバックティックとの戦い</a></li><li><a href="#toc7" tabindex="0">第5話：実はこれ2回目です——BOMなしUTF-8の文字化け</a></li><li><a href="#toc8" tabindex="0">第6話：スレッド数10→50、まさかの伏兵</a></li><li><a href="#toc9" tabindex="0">まとめ：AIエージェントと二人三脚で進めて分かったこと</a></li><li><a href="#toc10" tabindex="0">シリーズ記事一覧</a></li><li><a href="#toc11" tabindex="0">AIエージェントとの協働をもっと学びたい方へ</a></li></ol>
    </div>
  </div>

<h2><span id="toc1">はじめに</span></h2>
<p>JMeterで社内Webアプリの負荷テストを一から組み立てることになり、AIエージェント（Claude Code / Kiro）とペアを組んで進めることにしました。この記事は、その過程で実際にぶつかったトラブルと、AIエージェントとのやり取りを通じてどう切り分け・解決していったかを振り返る体験記です。</p>
<p>このブログでは「JMeter × AIエージェント活用」というテーマで、以下の5本立てのシリーズ記事を公開しています。手順そのものを知りたい方は、まず①の基本ガイドから読むことをおすすめします。</p>
<ol>
<li><a href="/jmeter-overview-guide/">JMeterとは？基本概念とインストール</a></li>
<li><a href="/jmeter-scenario-recording-guide/">シナリオ記録実践ガイド</a></li>
<li><a href="/jmeter-access-log-scenario-design/">本番アクセスログからのシナリオ設計</a></li>
<li><a href="/jmeter-session-key-testing-guide/">sessionKey動的化のハマりどころ</a></li>
<li>本記事（体験記）</li>
</ol>
<p><!-- ![JMeterの結果ツリーで赤いエラーが並ぶスクリーンショット風イメージ](images/error-tree.jpg) --></p>
<hr>
<h2><span id="toc2">この記事で分かること</span></h2>
<ul>
<li>HTTP接続エラーに遭遇したときに、AIエージェントとどう原因を切り分けていったか</li>
<li>プロキシ設定・DNS周りの調査が思わぬ方向に転がった顛末</li>
<li>PowerShellの一括置換で再発した「BOMなしUTF-8の文字化け」という実務あるある</li>
<li>スレッド数を10→50に増やしたときに初めて見えてきた問題</li>
<li>AIエージェントと二人三脚で進めることで得た気づき</li>
</ul>
<hr>
<h2><span id="toc3">第1話：記録はできたのに、再生すると繋がらない</span></h2>
<p>シナリオの記録自体は思ったよりスムーズに終わりました。ブラウザ操作をJMeterのHTTPプロキシ機能で記録し、余計な静的リソース（CSS/JS/画像）を除外フィルタで取り除く。ここまでは<a href="/jmeter-scenario-recording-guide/">シナリオ記録実践ガイド</a>で解説している手順どおりです。</p>
<p>問題は「記録した内容をそのまま再生」した瞬間に起きました。</p>
<pre><code class="language-plaintext">Response code: Non HTTP response code: java.net.SocketException
Response message: Non HTTP response message: Connection reset</code></pre>
<p>「さっきブラウザで普通に見えていたページに、なぜJMeterから繋がらないのか」——ここから長い調査が始まりました。AIエージェントに状況を伝えると、まず整理してくれたのはこういう構図です。</p>
<blockquote>
<p>記録時はブラウザ→JMeterプロキシ→サーバーという経路だったが、再生時はJMeterが直接サーバーに接続しにいく。社内ネットワークのルーティング次第では、この直接接続が失敗することがある。</p>
</blockquote>
<p>「記録できた＝再生できる」ではない、という当たり前のようで見落としがちな事実に、AIエージェントの説明で気づかされた瞬間でした。</p>
<hr>
<h2><span id="toc4">第2話：犯人はプロキシだと思っていた</span></h2>
<p>接続できない原因を切り分けるため、AIエージェントの指示に従って<code>curl</code>や<code>nslookup</code>で一つずつ確認していきました。</p>
<ul>
<li><code>nslookup</code>で対象サーバーの名前解決はできている</li>
<li>直接IPアドレス指定の<code>curl</code>はタイムアウト</li>
<li>社内プロキシ経由の<code>curl</code>は504 Gateway Timeout</li>
</ul>
<p>「名前解決はできているのに繋がらない」「ブラウザでは見えるのにcurlやJMeterでは繋がらない」という矛盾した状況に、正直かなり混乱しました。ここでAIエージェントが提案したのが、ブラウザが参照しているPACファイル（プロキシ自動設定ファイル）の中身を確認することでした。</p>
<p>PACファイルを開いてみると、こんなロジックが書かれていました（内容は一般化して要約しています）。</p>
<pre><code class="language-javascript">// 社内ドメイン宛のリクエストは判定関数がDIRECT（プロキシなし直接接続）を返す
if (isPlainHostName(host) || isPrivate(host) || isSpecify(host))
    return "DIRECT";

// ただし、PCが属するネットワークによってはプロキシ経由になる分岐もある
if (isInNet(myIpAddress(), "社内サブネット", "サブネットマスク") &amp;&amp; 条件)
    return "PROXY プロキシサーバー:ポート";</code></pre>
<p>つまり「社内の対象システム宛は直接接続」というルールがある一方で、PCの所属ネットワークによっては別のプロキシ経由になる分岐も存在していました。ブラウザはPACファイルの指示どおり賢くルーティングしてくれるのに対し、curlやJMeterは何も考えずに直接接続を試みるため、経路がズレて失敗していたわけです。</p>
<p>ここでJMeterの起動オプションにプロキシ設定（ホスト・ポート・認証情報）を追加し、504 Gateway Timeoutを回避しようとタイムアウト値を伸ばしたりプロキシの有無を切り替えたり……何度も条件を変えて試行錯誤しました。プロキシ設定の変更点は、<a href="/jmeter-scenario-recording-guide/">シナリオ記録実践ガイド</a>で解説しているHTTPプロキシサーバの記録手順とは別物で、「記録用プロキシ」と「再生時にJMeterが使うプロキシ」を混同しないよう整理するのに時間がかかりました。</p>
<p>結果として一部のリクエストは成功するようになったものの、後続の特定のリクエストだけがどうしても<code>Connection reset</code>で失敗し続けます。「プロキシの経路はもう合っているはずなのに、なぜこの1本だけ通らないのか」——この違和感が、次の展開への伏線でした。</p>
<hr>
<h2><span id="toc5">第3話：本当の犯人はsessionKeyだった</span></h2>
<p>行き詰まってAIエージェントに状況を整理してもらったところ、思いがけない指摘がありました。</p>
<blockquote>
<p>今の設定（デフォルトのプロキシ状態）のままブラウザで対象システムに普通にアクセスできるなら、JMeterの再生にプロキシ設定変更は不要かもしれません。最初のConnection resetは、プロキシではなくsessionKeyの不整合が原因だった可能性があります。</p>
</blockquote>
<p>半信半疑でプロキシ設定を元のデフォルト状態に戻し、ブラウザでアクセスを確認すると、あっさり繋がりました。つまり数時間かけて追いかけていたプロキシ問題は、そもそも本質的な原因ではなかったのです。</p>
<p>振り返ってみると、経緯はこうでした。</p>
<ol>
<li>最初の実行（プロキシなし）→ <code>Connection reset</code> → <strong>実はsessionKeyが原因だった</strong></li>
<li>プロキシ設定を試行錯誤 → 504 Gateway Timeout（プロキシが社内サーバーへの中継に対応していなかっただけ）</li>
<li>プロキシ設定を調整 → 一部成功するも、特定のリクエストだけ<code>Connection reset</code>が継続</li>
<li>sessionKeyを動的化 → <strong>すべて成功</strong></li>
</ol>
<p>対象システムは、URLパラメータの<code>sessionKey</code>とCookieのセッションIDの両方でセッションを検証する作りになっており、記録時に固定値として保存された<code>sessionKey</code>と、再生時に新しく発行されるセッションが食い違うことでサーバー側が接続を拒否していました。プロキシ関連のエラーメッセージ（504やConnection reset）に気を取られすぎて、アプリケーション層の問題を疑うのが遅れてしまったのが反省点です。</p>
<p>sessionKeyを動的に抽出してパラメータ化する具体的な手順は、<a href="/jmeter-session-key-testing-guide/">sessionKey動的化のハマりどころ</a>にまとめています。</p>
<p><strong>この体験から得た教訓</strong>: 「同じようなエラーメッセージが出ているから同じ原因だろう」と決めつけず、成功しているリクエストと失敗しているリクエストの違いを一つずつ洗い出す。AIエージェントに「これとこれの違いは何？」と聞き返すだけでも、思い込みに気づけることがあります。</p>
<hr>
<h2><span id="toc6">第4話：見えないバックティックとの戦い</span></h2>
<p>sessionKeyを動的化する対応として、正規表現抽出器でレスポンスからセッション値を取得し、JMXファイル（JMeterのテスト計画ファイル）内に散らばる固定値を<code>${sessionKey}</code>という変数参照に一括置換する作業に入りました。手作業で100箇所以上を書き換えるのは非現実的なので、PowerShellスクリプトでの一括置換を選択しました。</p>
<p>置換自体はあっさり完了したのですが、実行してみると再びエラーが発生します。ファイルの中身を確認してもらうと、AIエージェントが原因を特定してくれました。</p>
<blockquote>
<p><code>loginParam=</code> の後ろに、<code>${sessionKey}</code> ではなく **バックティック付きの <code>`${sessionKey}</code> ** が入り込んでいます。</p>
</blockquote>
<p>cmd経由でPowerShellを実行する際、<code>$</code>記号がシェル側の変数展開として解釈されないようにバックティックでエスケープしたのですが、そのバックティック自体が文字としてファイルに書き込まれてしまっていたのです。画面表示ではほぼ気づけないレベルの見た目の違いで、「なぜ変数参照のはずなのに認識されないのか」と数十分悩みました。</p>
<p>さらにもう一つ落とし穴がありました。JMeterで置換後のJMXファイルを開いた際、「保存しますか？」というダイアログで「はい」を選ぶと、JMeterが内部処理でバックティック付きの表記をそのまま保存し直してしまうという挙動です。せっかく手直ししても、保存操作一つで元に戻ってしまう。</p>
<p>この一件から得た運用ルールは次の3点です。</p>
<ol>
<li>JMXファイルの一括置換は、JMeterを閉じた状態で行う</li>
<li>置換後にJMeterで開いて「保存しますか？」と聞かれたら、基本は「いいえ」を選ぶ</li>
<li>cmd経由のエスケープ処理はトラブルの元になりやすいので、PS1ファイル（PowerShellスクリプトファイル）を直接実行する方式に切り替える</li>
</ol>
<hr>
<h2><span id="toc7">第5話：実はこれ2回目です——BOMなしUTF-8の文字化け</span></h2>
<p>第4話の教訓を踏まえてPS1ファイル方式に切り替えたのですが、今度は<strong>日本語を含むPS1ファイルが文字化けし、パーサーエラーで止まる</strong>という別の問題にぶつかりました。しかも後で気づいたのですが、これは今回のプロジェクトで初めてではなく、実は2回目の再発でした。</p>
<p>AIエージェントに「なぜ何度も同じ問題が起きるのか」と聞いたところ、根本原因を整理してくれました。</p>
<blockquote>
<p>Windows PowerShell 5.1が<code>-File</code>パラメータでPS1ファイルを読み込む際、<strong>BOMなしUTF-8をUTF-8として認識しません</strong>。BOMがない場合、システムの既定エンコーディング（日本語環境ではShift-JIS / CP932）として解釈してしまいます。</p>
<ul>
<li>BOMなしUTF-8 → Shift-JISとして読む → 日本語が文字化け → パーサーエラー</li>
<li>BOM付きUTF-8 → UTF-8として正しく読む → OK</li>
</ul>
<p>AIエージェントのファイル書き込み機能は既定でBOMなしUTF-8で保存するため、日本語を含むPS1ファイルを作成するたびにこの問題が再発しています。</p>
</blockquote>
<p>「UTF-8なのに日本語が含まれているのが問題」ではなく、「PowerShell 5.1がBOMの有無でエンコーディングを判定している」というのが本質でした。これは<code>.ps1</code>や<code>.bat</code>といったレガシーなインタプリタ特有の挙動で、<code>.py</code>や<code>.js</code>のような他の言語では起きません（実際、このブログのプロジェクトルールにも「Windows用スクリプト作成時の必須ルール」として明文化されるきっかけになった問題です）。</p>
<p>対処としては次の2段構えにしました。</p>
<ul>
<li><strong>恒久対策</strong>: PS1ファイルに日本語を直書きしない。名前データなどはCSV/TSVなど外部ファイルから読み込む方式に変更する</li>
<li><strong>保険</strong>: それでも完全には避けきれない場合に備え、PS1ファイル作成後に必ずBOM付きUTF-8へ変換するコマンドを実行する運用ルールを追加する</li>
</ul>
<p>さらに、この問題は一度で終わりませんでした。テストデータをCSVから読み込む方式に変えた後も、<code>[char]</code>コードでUnicode文字を組み立てる行がBOMなしUTF-8のまま解釈された結果、シングルクォートの対応が崩れて別の構文エラーが発生。「日本語リテラルさえ避ければ安全」という思い込みも通用しないケースがあることを学びました。最終的には「PS1ファイルを生成したら、内容に関わらず機械的にBOM付きUTF-8へ変換する」という一手間を運用フローに組み込むことで、この問題からようやく解放されました。</p>
<p>同じ失敗を繰り返さないために、AIエージェントとのやり取りの中でルール化・文書化しておく——これが地味ですが一番効いた対策でした。</p>
<hr>
<h2><span id="toc8">第6話：スレッド数10→50、まさかの伏兵</span></h2>
<p>sessionKeyの動的化まで終わり、10スレッドでの実行がようやく安定して成功するようになりました。次のステップは、本番のピーク時間帯の同時アクセス数に近づけるためのスケールアップです。<a href="/jmeter-access-log-scenario-design/">本番アクセスログからのシナリオ設計</a>で分析した実際のアクセスパターンをもとに、まずは50スレッドを目標に設定しました。</p>
<p>スケールアップにあたって必要だったのは、主に次の3つです。</p>
<ol>
<li>テストデータ（CSV/TSV）を10件分から50件分に拡張する</li>
<li>DB側にも50件分のテストデータを投入する</li>
<li>スレッドグループのRamp-Up期間（起動間隔）を見直す</li>
</ol>
<p>Ramp-Upの設定では、AIエージェントとこんなやり取りがありました。10スレッド時はRamp-Up 30秒（3秒間隔で1スレッドずつ起動）にしていたので、単純に同じ比率で計算すると50スレッドでは150秒になります。しかし——</p>
<blockquote>
<p>本番のピーク時間帯には多数のユーザーがほぼ同時に操作を開始していました。実態に近づけるなら、150秒（3秒間隔）ではなく、もっと短い間隔で起動する方が適切かもしれません。</p>
</blockquote>
<p>比率をそのまま引き延ばすのではなく、「何のためにスレッド数を増やすのか」という目的（本番ピークの再現）に立ち返って間隔を決め直す。数字の整合性だけでなく目的に立ち返って判断する視点は、一人で黙々と設定変更していたら見落としていたかもしれません。</p>
<p>そして実際に50スレッドで実行してみると、10スレッドでは一度も出なかった新しいエラーが発生しました。エラーが起きたスレッドとタイミングをAIエージェントに集計してもらったところ、興味深いパターンが見えてきました。</p>
<ul>
<li>同じ10本のスレッドが、2回とも一貫してエラーになっている</li>
<li>エラーはランダムではなく特定のスレッドに偏っている</li>
</ul>
<p>「ランダムに失敗するならデータの偶然、特定のスレッドだけが毎回失敗するなら処理ロジックか競合状態」——この切り分けの視点はAIエージェントに教わったものでした。サーバー側のアプリケーションログを確認すると、原因は「型キャスト例外」。同時アクセス数が増えたことで、セッションへの書き込みタイミングが競合し、一部のスレッドで想定と異なるオブジェクトがセッションに格納されてしまっていたのです。10スレッドでは発生しなかった競合状態が、50スレッドという同時実行数の増加によって初めて表面化した典型例でした。</p>
<p>あわせて、サーバーのCPU使用率も90%近くまで到達しており、「これ以上スレッド数を増やすなら、開発環境ではなく本番相当のスペックを持つ環境で検証すべき」という判断材料も得られました。スレッド数を上げること自体は成功しても、それによって初めて可視化される問題があるという点は、負荷テストの本来の目的を再確認させられる出来事でした。</p>
<hr>
<h2><span id="toc9">まとめ：AIエージェントと二人三脚で進めて分かったこと</span></h2>
<p>一連のトラブルシューティングを振り返って、AIエージェントと組んで進めたことで良かった点と、逆に自分自身が気をつけるべきだと感じた点をまとめます。</p>
<p><strong>良かった点</strong></p>
<ul>
<li>エラーメッセージだけを見て思考停止せず、「成功しているリクエストと失敗しているリクエストの違いは何か」といった切り分けの視点を毎回言語化して示してくれる</li>
<li>一度解決した問題（BOM文字化けなど）を「なぜ起きるのか」の根本原因まで説明してもらえるので、その場しのぎで終わらせず再発防止のルール化につなげやすい</li>
<li>プロキシ、DNS、sessionKey、セッション競合と、レイヤーの異なる複数の仮説を出してくれるので、自分一人では気づきにくい方向にも調査を広げられる</li>
</ul>
<p><strong>自分自身が気をつけたい点</strong></p>
<ul>
<li>AIエージェントが提示した仮説（今回で言えばプロキシ）に飛びつきすぎず、「本当にそれで説明がつくか」を都度立ち止まって検証する。第3話のように、実は的外れな仮説を数時間追いかけてしまうこともある</li>
<li>再発した問題（BOM文字化け）に対しては、その場の対処だけでなく、プロジェクトのルールとして明文化しておく。次に同じ罠にハマる時間を減らせる</li>
<li>スレッド数を増やすといった変更は、「動くかどうか」だけでなく「何のためにその設定にするのか」という目的に立ち返って判断する</li>
</ul>
<p>今後は、こうした試行錯誤の過程そのものを事後にまとめ直すのではなく、AIエージェントとの対話ログを都度メモ化しておき、次のプロジェクトで同じ壁にぶつかったときにすぐ参照できる形にしていきたいと考えています。</p>
<hr>
<h2><span id="toc10">シリーズ記事一覧</span></h2>
<ul>
<li><a href="/jmeter-overview-guide/">① JMeterとは？基本概念とインストール</a></li>
<li><a href="/jmeter-scenario-recording-guide/">② シナリオ記録実践ガイド</a></li>
<li><a href="/jmeter-access-log-scenario-design/">③ 本番アクセスログからのシナリオ設計</a></li>
<li><a href="/jmeter-session-key-testing-guide/">④ sessionKey動的化のハマりどころ</a></li>
<li>⑤ 本記事（トラブルシューティング体験記）</li>
</ul>
<hr>
<h2><span id="toc11">AIエージェントとの協働をもっと学びたい方へ</span></h2>
<p>今回の体験記で紹介したように、AIエージェント（Claude Code）とのペア作業は「原因の切り分け」「再発防止のルール化」といった場面で特に力を発揮します。Claude Codeを使ったハンズオン形式の入門講座もあるので、興味のある方はチェックしてみてください。</p>
<p>👉 <a href="https://trk.udemy.com/9VqD70">講座の詳細を見る（Udemyで確認）</a></p><p>The post <a href="https://caymezon.com/jmeter-ai-troubleshooting-story/">AIエージェントと二人三脚で進める負荷テストのトラブルシューティング体験記</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></content:encoded>
					
					<wfw:commentRss>https://caymezon.com/jmeter-ai-troubleshooting-story/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>本番アクセスログから現実的な負荷テストシナリオを設計する方法</title>
		<link>https://caymezon.com/jmeter-access-log-scenario-design/</link>
					<comments>https://caymezon.com/jmeter-access-log-scenario-design/#respond</comments>
		
		<dc:creator><![CDATA[caymezon]]></dc:creator>
		<pubDate>Mon, 17 Aug 2026 04:41:46 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<category><![CDATA[access_log]]></category>
		<category><![CDATA[AIエージェント活用]]></category>
		<category><![CDATA[Apache]]></category>
		<category><![CDATA[JMeter]]></category>
		<category><![CDATA[パフォーマンステスト]]></category>
		<category><![CDATA[ログ解析]]></category>
		<category><![CDATA[負荷テスト]]></category>
		<guid isPermaLink="false">https://caymezon.com/jmeter-access-log-scenario-design/</guid>

					<description><![CDATA[<p>目次 はじめにこの記事で分かること1. なぜ「思いつきのシナリオ」では負荷テストが意味をなさないのか2. 本番Apache access_logから実アクセスパターンを抽出する2-1. access_logのフォーマット [&#8230;]</p>
<p>The post <a href="https://caymezon.com/jmeter-access-log-scenario-design/">本番アクセスログから現実的な負荷テストシナリオを設計する方法</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></description>
										<content:encoded><![CDATA[<div id="toc" class="toc tnt-number toc-center tnt-number border-element"><input type="checkbox" class="toc-checkbox" id="toc-checkbox-10" checked><label class="toc-title" for="toc-checkbox-10">目次</label>
    <div class="toc-content">
    <ol class="toc-list open"><li><a href="#toc1" tabindex="0">はじめに</a></li><li><a href="#toc2" tabindex="0">この記事で分かること</a></li><li><a href="#toc3" tabindex="0">1. なぜ「思いつきのシナリオ」では負荷テストが意味をなさないのか</a></li><li><a href="#toc4" tabindex="0">2. 本番Apache access_logから実アクセスパターンを抽出する</a><ol><li><a href="#toc5" tabindex="0">2-1. access_logのフォーマットを確認する</a></li><li><a href="#toc6" tabindex="0">2-2. 抽出1：ピーク時間帯を丸ごと抜く（最優先）</a></li><li><a href="#toc7" tabindex="0">2-3. 抽出2：アクティブなユーザー（IP）を特定する</a></li><li><a href="#toc8" tabindex="0">2-4. 抽出3：特定ユーザーの1セッションを追跡し、操作フローを再現する</a></li><li><a href="#toc9" tabindex="0">2-5. Windows端末での代替手段</a></li></ol></li><li><a href="#toc10" tabindex="0">3. 抽出データが教えてくれるシナリオ設計の勘所</a></li><li><a href="#toc11" tabindex="0">4. 既存のExcel設計資料をAIエージェントでMarkdown化・構造化する</a><ol><li><a href="#toc12" tabindex="0">方法A：CSVに変換してから読み込ませる</a></li><li><a href="#toc13" tabindex="0">方法B：PowerShellのCOM経由でAIエージェントに直接読ませる</a></li></ol></li><li><a href="#toc14" tabindex="0">5. 抽出したアクセスパターンをJMeterシナリオに落とし込む</a><ol><li><a href="#toc15" tabindex="0">5-1. スレッド数・Ramp-up</a></li><li><a href="#toc16" tabindex="0">5.2. Think Time（Uniform Random Timer）</a></li><li><a href="#toc17" tabindex="0">5-3. 操作比率の再現（Throughput Controller / 重み付け）</a></li><li><a href="#toc18" tabindex="0">5-4. テストデータのバリエーション</a></li></ol></li><li><a href="#toc19" tabindex="0">6. 実務での注意点：本番ログの取り扱い</a></li><li><a href="#toc20" tabindex="0">まとめ</a></li></ol>
    </div>
  </div>

<h2><span id="toc1">はじめに</span></h2>
<p>JMeterの基本的な使い方は <a href="/jmeter-overview-guide/">JMeterとは？基本概念とインストール</a> で、ブラウザ操作をシナリオとして記録する方法は <a href="/jmeter-scenario-recording-guide/">シナリオ記録実践ガイド</a> で解説しました。この2つを押さえれば、「動くシナリオ」は作れます。</p>
<p>ですが、負荷テストの担当者として実際に業務で向き合うと、もっと手前に大きな壁があることに気づきます。それは、**「そのシナリオ、本当に本番の使われ方に近いんですか？」**という問いです。</p>
<p>この記事では、筆者が実務のWebアプリケーション負荷テストで実際に行った、<strong>本番のApache access_logからアクセスパターンを抽出してシナリオ設計に反映させる工程</strong>を、AIエージェントとの実際のやり取りをベースに一般化してまとめます。検索してもほとんど情報が出てこない領域ですが、負荷テストの「結果の信頼性」を左右する、地味だが非常に重要な工程です。</p>
<blockquote>
<p><strong>社内情報の取り扱いについて</strong>：この記事で示すログ・画面名・IPアドレス・数値はすべて説明用のダミーデータです。実際に筆者が扱った本番データそのものは一切含まれていません。</p>
</blockquote>
<hr>
<h2><span id="toc2">この記事で分かること</span></h2>
<ul>
<li>「思いつきのシナリオ」がなぜ負荷テストの結果を無意味にしてしまうのか</li>
<li>本番のApache access_logからgrepで実アクセスパターンを抽出する具体的な手順</li>
<li>既存のExcel設計資料をAIエージェントに読み込ませてMarkdown化・再利用可能な形に構造化するアイデア</li>
<li>抽出したアクセスパターンをJMeterのスレッドグループ・Think Time設定に落とし込む流れ</li>
<li>本番ログを扱う上での注意点（アクセス権限・個人情報マスキング等）</li>
</ul>
<hr>
<h2><span id="toc3">1. なぜ「思いつきのシナリオ」では負荷テストが意味をなさないのか</span></h2>
<p>負荷テストのシナリオを作るとき、つい「よく使われていそうな画面」を経験と勘で並べてしまいがちです。ログイン→一覧画面→検索→詳細→ログアウト、のような「いかにもありそうな流れ」です。</p>
<p>しかし、これには大きな落とし穴があります。<strong>負荷テストは「本番に近い負荷をかけて、本番で起きうる問題を事前に見つける」ことが目的</strong>です。シナリオが実際の使われ方とズレていれば、以下のような事態が起こります。</p>
<ul>
<li>実際にはほとんど使われない画面に負荷をかけて「問題なし」と結論づけてしまう（本当のボトルネックを見逃す）</li>
<li>逆に、実際には少人数しか同時操作しない画面を過大な同時ユーザー数でテストし、不要な改修コストをかけてしまう</li>
<li>本番でよく発生する「検索条件を変えて何度も再検索する」といった連続操作を再現できず、DBキャッシュ効果込みの楽観的な結果しか得られない</li>
</ul>
<p>筆者が担当した案件でも、最初は「画面ごとのアクセス数」を集計したExcelの調査資料（時間帯別・画面別のアクセス回数一覧）だけがあり、これをもとにシナリオを検討していました。ですが、AIエージェントに相談する中で次の指摘を受け、認識を改めることになりました。</p>
<blockquote>
<p>画面アクセス数だけでは「その画面に何人がアクセスしたか」しか分かりません。<strong>負荷テストのシナリオ設計に必要なのは、それに加えて「操作順序」「操作間隔（Think Time）」「同時セッション数」の3つです。</strong></p>
</blockquote>
<p>つまり、集計済みのサマリーデータは「入口」に過ぎず、<strong>生のaccess_logまで遡って初めて実態に近いシナリオが組める</strong>、ということです。</p>
<hr>
<h2><span id="toc4">2. 本番Apache access_logから実アクセスパターンを抽出する</span></h2>
<p>ここからが本題です。本番のaccess_logは通常、数GB〜数十GB単位で溜まっているため、全量を持ち出すのは現実的ではありません。<strong>「何を知りたいか」から逆算して、必要な範囲だけをgrepで抜き出す</strong>のがポイントです。</p>
<h3><span id="toc5">2-1. access_logのフォーマットを確認する</span></h3>
<p>まず対象システムのaccess_logがどのフォーマットで出力されているかを確認します。よくあるCombined Log Format＋レスポンスタイム付与のパターンだと、以下のようなイメージになります（<strong>以下はすべて説明用のダミーデータです</strong>）。</p>
<pre><code class="language-plaintext">10.0.0.23 - - [10/Aug/2026:09:03:12 +0900] "GET /dummy-app/order/init.do HTTP/1.1" 200 15234 187
10.0.0.23 - - [10/Aug/2026:09:03:34 +0900] "POST /dummy-app/order/search.do HTTP/1.1" 200 8123 342
10.0.0.45 - - [10/Aug/2026:09:03:36 +0900] "POST /dummy-app/receiving/regist.do HTTP/1.1" 200 512 1204</code></pre>
<p>この1行から読み取れる情報は多いです。</p>
<table>
<thead>
<tr>
<th>項目</th>
<th>読み取れる情報</th>
</tr>
</thead>
<tbody>
<tr>
<td>送信元IP</td>
<td>セッション（ユーザー）単位の追跡キー</td>
</tr>
<tr>
<td>タイムスタンプ</td>
<td>操作間隔（Think Time）の算出元</td>
</tr>
<tr>
<td>URLパス</td>
<td>画面・処理の遷移順序</td>
</tr>
<tr>
<td>HTTPメソッド</td>
<td>GET＝画面表示系、POST＝検索・登録系の目安</td>
</tr>
<tr>
<td>末尾の数値（レスポンスタイム）</td>
<td>性能ベースラインの把握、重い処理の特定</td>
</tr>
</tbody>
</table>
<h3><span id="toc6">2-2. 抽出1：ピーク時間帯を丸ごと抜く（最優先）</span></h3>
<p>まずは「その時間、同時に何人がどんなリクエストを投げていたか」の全体像を掴むため、ピークと思われる時間帯を丸ごと抽出します。</p>
<pre><code class="language-bash">grep "10/Aug/2026:09:0" /var/log/apache2/access_log \
  &gt; extract_access_log_0900-0910.log</code></pre>
<p>日付・時刻の文字列パターンでgrepするだけなので単純ですが、<strong>「その時間帯に何件のリクエストが飛んでいたか」「業務系リクエストと静的リソース（css/js/img等）の比率」がすぐ見える</strong>のが利点です。</p>
<h3><span id="toc7">2-3. 抽出2：アクティブなユーザー（IP）を特定する</span></h3>
<p>次に、その時間帯で特にアクセス数が多かった送信元を洗い出します。<code>awk</code> と <code>sort</code> の組み合わせが定番です。</p>
<pre><code class="language-bash"># 時間帯を絞ったログから、アクセス数の多い送信元IPトップ10を確認
grep "10/Aug/2026:09:" /var/log/apache2/access_log \
  | awk '{print $1}' | sort | uniq -c | sort -rn | head -10</code></pre>
<p>このコマンド1本で、「その時間帯にヘビーに操作していたユーザー」の見当がつきます。負荷テストのシナリオで再現すべき「代表的な操作パターン」の候補が、ここから見えてきます。</p>
<h3><span id="toc8">2-4. 抽出3：特定ユーザーの1セッションを追跡し、操作フローを再現する</span></h3>
<p>トップに挙がったIPを対象に、そのユーザーの全リクエストを時系列で抜き出すと、<strong>1人のユーザーが実際にどの画面をどんな間隔で操作していたか</strong>が丸ごと再現できます。</p>
<pre><code class="language-bash">grep "10.0.0.23" /var/log/apache2/access_log \
  | grep "09:0" \
  &gt; extract_access_log_user_10.0.0.23_09h.log</code></pre>
<p>これを整理すると、以下のような「実測の操作フロー」が得られます（数値・画面名はすべて説明用のダミーです）。</p>
<pre><code class="language-plaintext">09:03:12  /dummy-app/menu/init.do        (187ms)  メインメニュー表示
09:03:20  /dummy-app/menu/clickButton.do (98ms)   メニュー選択
09:03:34  /dummy-app/order/init.do       (245ms)  発注入力画面 起動
09:03:52  /dummy-app/order/search.do     (342ms)  ★検索実行（1回目）
09:04:29  /dummy-app/order/search.do     (318ms)  ★検索実行（2回目・条件変更）
09:04:41  /dummy-app/order/regist.do     (1204ms) ★登録処理</code></pre>
<p>このレベルまで見えると、「画面表示→検索を複数回繰り返す→条件を変えて再検索→最後に登録」という<strong>現実的な操作単位のブロック</strong>が見えてきます。タイムスタンプの差分を取れば、操作間隔（Think Time）も実測値として算出できます。</p>
<table>
<thead>
<tr>
<th>区間</th>
<th>実測間隔</th>
</tr>
</thead>
<tbody>
<tr>
<td>メニュー表示→選択</td>
<td>約8秒</td>
</tr>
<tr>
<td>選択→画面起動</td>
<td>約14秒</td>
</tr>
<tr>
<td>起動→検索1回目</td>
<td>約18秒</td>
</tr>
<tr>
<td>検索1回目→2回目</td>
<td>約37秒</td>
</tr>
<tr>
<td>検索2回目→登録</td>
<td>約12秒</td>
</tr>
</tbody>
</table>
<p>「Think Timeは何となく30秒にしておく」ではなく、<strong>実測で「検索操作の間隔はおよそ20〜40秒」という根拠</strong>が持てるようになります。</p>
<h3><span id="toc9">2-5. Windows端末での代替手段</span></h3>
<p>grepやawkが使える環境がない場合や、ログサイズが大きすぎて素直なgrepでは処理が重い場合は、PowerShellの <code>Select-String</code> や <code>Get-Content</code> ＋オブジェクト集計でも同様の集計が可能です。抽出済みのログをAIエージェントに読み込ませて、リクエスト数の分単位推移・IPごとの集計・レスポンスタイムのパーセンタイル（50%ile、90%ile等）まで一気に統計化してもらう、という使い方も実務では有効でした。人力でExcelに貼り付けて集計するより圧倒的に早く、かつ「異常値（極端に遅いリクエスト）」にも気づきやすくなります。</p>
<p><!-- ![access_logからアクセスパターンを抽出する流れを示したフロー図](images/access-log-extraction-flow.jpg) --></p>
<hr>
<h2><span id="toc10">3. 抽出データが教えてくれるシナリオ設計の勘所</span></h2>
<p>生ログを解析すると、Excelのサマリーだけでは分からなかった以下のような情報が見えてきます。</p>
<ul>
<li><strong>書き込み系（登録・更新）処理の比率</strong>：DBへの書き込みを伴う処理は読み取り系より負荷が高いため、比率を正確に再現する価値が大きい</li>
<li><strong>同一画面への「検索を繰り返す」実務パターン</strong>：1回の検索で終わらず、条件を変えて何度も検索するのが実際の使われ方であるケースは多い。シナリオも1回のリクエストで終わらせず、ループさせて再現すべき</li>
<li><strong>異常に遅いリクエストの存在</strong>：CSV出力や大量データ処理など、一部のリクエストだけ突出して遅いケースがある。これは負荷テストのシナリオに含めるかどうかを意図的に判断する材料になる（含めないと本番相当の負荷にならないが、含めすぎるとテスト結果が偏る）</li>
</ul>
<p>こうした「量」だけでなく「質」の情報が、実データを見ることで初めて手に入ります。</p>
<hr>
<h2><span id="toc11">4. 既存のExcel設計資料をAIエージェントでMarkdown化・構造化する</span></h2>
<p>もう一つ、実務で効果があった工程を紹介します。負荷テストのノウハウは往々にして<strong>過去の別システムでの実施手順がExcelにまとまっている</strong>形で社内に眠っています。今回のケースでも、別システムで過去に作成された「JMeterシナリオ作成手順書」（環境構築・シナリオ記録・実行方法などをシート分けしたExcel）がありました。</p>
<p>これをそのまま参照したかったのですが、AIエージェント（Kiro／Claude Code等のCLIエージェント）は標準ではExcelのバイナリ形式を直接読み取れません。ここで実務上有効だったアプローチが以下の2つです。</p>
<h3><span id="toc12">方法A：CSVに変換してから読み込ませる</span></h3>
<p>Excel側で各シートを「CSV UTF-8」で書き出し、テキストファイルとして配置する方法です。シンプルですが、シートが多いと手間がかかります。</p>
<h3><span id="toc13">方法B：PowerShellのCOM経由でAIエージェントに直接読ませる</span></h3>
<p>Windows環境であれば、PowerShellのCOMオブジェクト（<code>New-Object -ComObject Excel.Application</code>）を使ってExcelアプリケーションを裏で操作し、シートの内容をテキストとして取得できます。AIエージェントにこの手順を依頼すると、変換作業なしで元のExcelの構成（シート名・表形式）を保ったままMarkdownとして整理してもらえます。</p>
<p>実際には、以下のような構成で整理し直してもらいました。</p>
<pre><code class="language-plaintext"># 対象システム JMeter負荷テスト手順書（Markdown化）

## 環境構築
- Java／JMeterのバージョン対応表
- インストール手順

## シナリオ作成時の注意点
- ループ実行しても問題ない操作かの確認
- 複数スレッドで同時実行しても問題ない操作かの確認
- 日付など、実施日に依存するパラメータの動的化方針

## シナリオ記録手順
- HTTPプロキシサーバーの設定〜記録〜復元までの手順

## 実行と計測
- スレッド数／Ramp-up／ループ回数の設定例
- 非GUIモードでのコマンドライン実行例</code></pre>
<p>これにより、<strong>紙（Excel）でしか存在しなかった過去のノウハウが、AIエージェントが検索・参照できるMarkdown資料として再利用可能になり</strong>、新しい対象システム向けにカスタマイズする際の土台として使えるようになりました。「Excelは読めないから手打ちで転記する」という手間を省ける、という意味で地味に効果の大きい工程です。</p>
<blockquote>
<p>補足：Excel内に埋め込まれた画像（スクリーンショットや図解）まではAIエージェントが自動で読み取れないケースが多く、その部分は別途チャットへの手動貼り付けなどで補完する必要がありました。表・テキスト情報の構造化は自動化できても、画像情報は人手を挟む前提で考えておくのが実務的です。</p>
</blockquote>
<p><!-- ![Excel設計資料をAIエージェントでMarkdown化する前後のイメージ](images/excel-to-markdown-structuring.jpg) --></p>
<hr>
<h2><span id="toc14">5. 抽出したアクセスパターンをJMeterシナリオに落とし込む</span></h2>
<p>ここまでの解析結果を、実際のJMeterのスレッドグループ設定に反映していきます。</p>
<h3><span id="toc15">5-1. スレッド数・Ramp-up</span></h3>
<p>「ユニークIP数＝同時アクセスユーザー数」ではない点に注意が必要です。ある時間帯にアクセスしてきたユニークIPが多くても、その全員が<strong>同じ瞬間に</strong>操作していたとは限りません。実測のリクエスト密度（1分あたりのリクエスト数）と1ユーザーあたりの操作ペースから逆算し、「同時にアクティブだったであろうセッション数」を見積もったうえでスレッド数を決めます。</p>
<pre><code class="language-plaintext">例）ユニークIP数が多くても、実際に同時にアクティブなセッションは
    その6〜8割程度に収まることが多い、という前提で調整する</code></pre>
<h3><span id="toc16">5.2. Think Time（Uniform Random Timer）</span></h3>
<p>2-4で実測した操作間隔をもとに、JMeterの「Uniform Random Timer」の最小値・最大値を設定します。「検索操作の間隔は実測で20〜40秒だった」であれば、そのままレンジとして反映できます。固定値（Constant Timer）ではなく、実測のばらつきをレンジで表現できるUniform Random Timerの方が、実際のユーザー行動に近いゆらぎを再現できます。</p>
<h3><span id="toc17">5-3. 操作比率の再現（Throughput Controller / 重み付け）</span></h3>
<p>抽出したログから算出した「書き込み系〇%・照会系〇%・画面遷移系〇%」といった構成比を、JMeterの「Throughput Controller」や、コントローラを複数用意して実行頻度に重み付けする方法で再現します。1本のシナリオを全スレッドが同じ順序でなぞるのではなく、実測の比率に応じて「このスレッドは照会だけを繰り返す」「このスレッドは登録中心」といったユーザータイプ別のシナリオを複数用意し、それぞれの比率でスレッドを配分する構成が実態に近づきます。</p>
<h3><span id="toc18">5-4. テストデータのバリエーション</span></h3>
<p>実測ログから、同じ処理でも複数のユーザーが異なる検索条件・入力データで操作していることが分かります。CSV Data Set Configで複数パターンのテストデータを用意し、スレッドごとに異なる値を使わせることで、DBキャッシュだけが効いてしまう非現実的に速い結果を避けられます。</p>
<hr>
<h2><span id="toc19">6. 実務での注意点：本番ログの取り扱い</span></h2>
<p>本番のaccess_logやアプリケーションログには、IPアドレス・ユーザーID・場合によっては入力データそのものが含まれます。負荷テストのために便利だからといって無造作に扱ってよいものではありません。実務では最低限、次の点を徹底しました。</p>
<ul>
<li><strong>アクセス権限の確認</strong>：本番ログの取得・閲覧は、情報システム部門などログへの正式なアクセス権限を持つ担当者が行い、許可されたメンバー以外に共有しない</li>
<li><strong>必要な範囲だけを抜き出す</strong>：全量をコピーせず、「対象時間帯」「対象IP」など目的に応じた範囲だけをgrepで抽出する（2章の手法はこの観点でも有効）。ログの持ち出し自体を最小化できる</li>
<li><strong>作業後の削除</strong>：解析用に一時的に抽出したログファイルは、シナリオ設計が完了したら削除する。ローカル端末や共有フォルダに残さない</li>
<li><strong>記事・資料化する際のマスキング</strong>：この記事のように社外に知見を共有する場合は、IPアドレス・画面名・URLパス・ユーザーIDなどをすべてダミーデータに置き換える（実データの数値そのものを転記しない）</li>
<li><strong>社内の情報管理規程の確認</strong>：本番ログの取り扱いに関するルールは組織によって異なるため、着手前に情報管理部門・上長に確認を取る</li>
</ul>
<p>「実データに近づけたシナリオを作る」ことと「実データをそのまま扱う」ことは別問題です。<strong>目的を達成するのに必要な情報の粒度まで抽象化・匿名化してから手元に置く</strong>、という意識が重要になります。</p>
<hr>
<h2><span id="toc20">まとめ</span></h2>
<ul>
<li>画面アクセス数の集計だけでは、負荷テストのシナリオ設計には情報が不足している。<strong>操作順序・Think Time・同時セッション数</strong>まで踏み込む必要がある</li>
<li>本番のApache access_logは、①時間帯 → ②アクティブユーザー → ③1セッションの操作フロー、という順に絞り込んでgrepすれば、現実的なボリュームで実アクセスパターンを抽出できる</li>
<li>過去のExcel設計資料は、AIエージェント（PowerShell COM経由での読み取りなど）を使ってMarkdown化しておくと、次のプロジェクトでも再利用できる資産になる</li>
<li>抽出したデータは、スレッド数・Think Time・操作比率・テストデータのバリエーションという形でJMeterシナリオに反映する</li>
<li>本番ログはアクセス権限・保管期間・マスキングを徹底して扱う。実データに近づけることと、実データをそのまま持ち出すことは別問題</li>
</ul>
<p>「思いつき」ではなく「実測」に基づいたシナリオを組めるようになると、負荷テストの結果そのものへの説得力が大きく変わります。</p>
<p>シナリオが実データに近づいてくると、次にぶつかるのが「JSESSIONIDなど動的な値をどう扱うか」という問題です。次の記事では、この<strong>sessionKeyの動的化でハマったポイント</strong>を実体験ベースで解説します。</p>
<p>👉 次のステップ：<a href="/jmeter-session-key-testing-guide/">sessionKey動的化のハマりどころ</a></p>
<p>まだ読んでいない方は、基礎編もあわせてどうぞ。</p>
<ul>
<li><a href="/jmeter-overview-guide/">JMeterとは？基本概念とインストール</a></li>
<li><a href="/jmeter-scenario-recording-guide/">シナリオ記録実践ガイド</a></li>
</ul><p>The post <a href="https://caymezon.com/jmeter-access-log-scenario-design/">本番アクセスログから現実的な負荷テストシナリオを設計する方法</a> first appeared on <a href="https://caymezon.com">CayTech Lab</a>.</p>]]></content:encoded>
					
					<wfw:commentRss>https://caymezon.com/jmeter-access-log-scenario-design/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
