jpskill.com
🛠️ 開発・MCP コミュニティ

async-sync-advisor

Guides users on choosing between async and sync patterns for Lambda functions, including when to use tokio, rayon, and spawn_blocking. Activates when users write Lambda handlers with mixed workloads.

⚡ おすすめ: コマンド1行でインストール(60秒)

下記のコマンドをコピーしてターミナル(Mac/Linux)または PowerShell(Windows)に貼り付けてください。 ダウンロード → 解凍 → 配置まで全自動。

🍎 Mac / 🐧 Linux
mkdir -p ~/.claude/skills && cd ~/.claude/skills && curl -L -o async-sync-advisor.zip https://jpskill.com/download/19006.zip && unzip -o async-sync-advisor.zip && rm async-sync-advisor.zip
🪟 Windows (PowerShell)
$d = "$env:USERPROFILE\.claude\skills"; ni -Force -ItemType Directory $d | Out-Null; iwr https://jpskill.com/download/19006.zip -OutFile "$d\async-sync-advisor.zip"; Expand-Archive "$d\async-sync-advisor.zip" -DestinationPath $d -Force; ri "$d\async-sync-advisor.zip"

完了後、Claude Code を再起動 → 普通に「動画プロンプト作って」のように話しかけるだけで自動発動します。

💾 手動でダウンロードしたい(コマンドが難しい人向け)
  1. 1. 下の青いボタンを押して async-sync-advisor.zip をダウンロード
  2. 2. ZIPファイルをダブルクリックで解凍 → async-sync-advisor フォルダができる
  3. 3. そのフォルダを C:\Users\あなたの名前\.claude\skills\(Win)または ~/.claude/skills/(Mac)へ移動
  4. 4. Claude Code を再起動

⚠️ ダウンロード・利用は自己責任でお願いします。当サイトは内容・動作・安全性について責任を負いません。

🎯 このSkillでできること

下記の説明文を読むと、このSkillがあなたに何をしてくれるかが分かります。Claudeにこの分野の依頼をすると、自動で発動します。

📦 インストール方法 (3ステップ)

  1. 1. 上の「ダウンロード」ボタンを押して .skill ファイルを取得
  2. 2. ファイル名の拡張子を .skill から .zip に変えて展開(macは自動展開可)
  3. 3. 展開してできたフォルダを、ホームフォルダの .claude/skills/ に置く
    • · macOS / Linux: ~/.claude/skills/
    • · Windows: %USERPROFILE%\.claude\skills\

Claude Code を再起動すれば完了。「このSkillを使って…」と話しかけなくても、関連する依頼で自動的に呼び出されます。

詳しい使い方ガイドを見る →
最終更新
2026-05-18
取得日時
2026-05-18
同梱ファイル
1

📖 Skill本文(日本語訳)

※ 原文(英語/中国語)を Gemini で日本語化したものです。Claude 自身は原文を読みます。誤訳がある場合は原文をご確認ください。

Async/Sync Advisor スキル

あなたは Rust の AWS Lambda における適切な並行処理パターンを選択する専門家です。Lambda ハンドラーを検出した場合、最適な async/sync パターンを積極的に提案してください。

アクティベートのタイミング

以下のような場合にアクティベートしてください。

  • CPU 負荷の高い処理を含む Lambda ハンドラー
  • I/O と計算処理が混在するワークロード
  • tokio::task::spawn_blocking または rayon の使用
  • async と sync のどちらを使うべきか、またはパフォーマンスに関する質問

決定ガイド

Async を使用する場合:I/O 負荷の高い処理

いつ:

  • HTTP/API コール
  • データベースクエリ
  • S3/DynamoDB 操作
  • 複数の独立した I/O 操作

パターン:

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    // ✅ すべての I/O が async - 完璧なユースケース
    let (user, profile, settings) = tokio::try_join!(
        fetch_user(id),
        fetch_profile(id),
        fetch_settings(id),
    )?;

    Ok(Response { user, profile, settings })
}

Sync + spawn_blocking を使用する場合:CPU 負荷の高い処理

いつ:

  • データ処理
  • 画像/動画操作
  • 暗号化/ハッシュ化
  • 大規模ファイルのパース

パターン:

use tokio::task;

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let data = event.payload.data;

    // ✅ CPU 処理をブロッキングスレッドプールに移動
    let result = task::spawn_blocking(move || {
        // 同期的な CPU 負荷の高い処理
        expensive_computation(&data)
    })
    .await??;

    Ok(Response { result })
}

Rayon を使用する場合:並列 CPU 処理

いつ:

  • 大規模なコレクションの処理
  • 並列データ変換
  • 並列化可能な CPU 負荷の高い操作

パターン:

use rayon::prelude::*;
use tokio::task;

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let items = event.payload.items;

    // ✅ spawn_blocking と Rayon を組み合わせて並列 CPU 処理を行う
    let results = task::spawn_blocking(move || {
        items
            .par_iter()
            .map(|item| cpu_intensive_work(item))
            .collect::<Vec<_>>()
    })
    .await?;

    Ok(Response { results })
}

混在ワークロードパターン

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    // フェーズ 1: Async I/O - データのダウンロード
    let download_futures = event.payload.urls
        .into_iter()
        .map(|url| async move {
            reqwest::get(&url).await?.bytes().await
        });
    let raw_data = futures::future::try_join_all(download_futures).await?;

    // フェーズ 2: Sync 計算 - Rayon で処理
    let processed = task::spawn_blocking(move || {
        raw_data
            .par_iter()
            .map(|bytes| process_data(bytes))
            .collect::<Result<Vec<_>, _>>()
    })
    .await??;

    // フェーズ 3: Async I/O - 結果のアップロード
    let upload_futures = processed
        .into_iter()
        .enumerate()
        .map(|(i, data)| async move {
            upload_to_s3(&format!("result-{}.dat", i), &data).await
        });
    futures::future::try_join_all(upload_futures).await?;

    Ok(Response { success: true })
}

よくある間違い

❌ CPU 処理に async を使用する

// BAD: CPU 負荷の高い処理に async を使うとオーバーヘッドが増える
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let result = expensive_cpu_computation(&event.payload.data);  // async ランタイムをブロックする
    Ok(Response { result })
}

// GOOD: spawn_blocking を使用する
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let data = event.payload.data.clone();
    let result = tokio::task::spawn_blocking(move || {
        expensive_cpu_computation(&data)
    })
    .await?;
    Ok(Response { result })
}

❌ I/O に並行処理を使用しない

// BAD: 逐次的な I/O
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let user = fetch_user(id).await?;
    let posts = fetch_posts(id).await?;  // 最初に user を待つ
    Ok(Response { user, posts })
}

// GOOD: 並行的な I/O
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let (user, posts) = tokio::try_join!(
        fetch_user(id),
        fetch_posts(id),
    )?;
    Ok(Response { user, posts })
}

あなたのアプローチ

Lambda ハンドラーを見た場合:

  1. ワークロードの種類(I/O vs CPU)を特定します。
  2. 適切なパターン(async vs sync)を提案します。
  3. 混在ワークロードのパターンを組み合わせる方法を示します。
  4. パフォーマンスへの影響を説明します。

ワークロードに最適な並行処理パターンを積極的に提案してください。

📜 原文 SKILL.md(Claudeが読む英語/中国語)を展開

Async/Sync Advisor Skill

You are an expert at choosing the right concurrency pattern for AWS Lambda in Rust. When you detect Lambda handlers, proactively suggest optimal async/sync patterns.

When to Activate

Activate when you notice:

  • Lambda handlers with CPU-intensive operations
  • Mixed I/O and compute workloads
  • Use of tokio::task::spawn_blocking or rayon
  • Questions about async vs sync or performance

Decision Guide

Use Async For: I/O-Intensive Operations

When:

  • HTTP/API calls
  • Database queries
  • S3/DynamoDB operations
  • Multiple independent I/O operations

Pattern:

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    // ✅ All I/O is async - perfect use case
    let (user, profile, settings) = tokio::try_join!(
        fetch_user(id),
        fetch_profile(id),
        fetch_settings(id),
    )?;

    Ok(Response { user, profile, settings })
}

Use Sync + spawn_blocking For: CPU-Intensive Operations

When:

  • Data processing
  • Image/video manipulation
  • Encryption/hashing
  • Parsing large files

Pattern:

use tokio::task;

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let data = event.payload.data;

    // ✅ Move CPU work to blocking thread pool
    let result = task::spawn_blocking(move || {
        // Synchronous CPU-intensive work
        expensive_computation(&data)
    })
    .await??;

    Ok(Response { result })
}

Use Rayon For: Parallel CPU Work

When:

  • Processing large collections
  • Parallel data transformation
  • CPU-bound operations that can be parallelized

Pattern:

use rayon::prelude::*;
use tokio::task;

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let items = event.payload.items;

    // ✅ Combine spawn_blocking with Rayon for parallel CPU work
    let results = task::spawn_blocking(move || {
        items
            .par_iter()
            .map(|item| cpu_intensive_work(item))
            .collect::<Vec<_>>()
    })
    .await?;

    Ok(Response { results })
}

Mixed Workload Pattern

async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    // Phase 1: Async I/O - Download data
    let download_futures = event.payload.urls
        .into_iter()
        .map(|url| async move {
            reqwest::get(&url).await?.bytes().await
        });
    let raw_data = futures::future::try_join_all(download_futures).await?;

    // Phase 2: Sync compute - Process with Rayon
    let processed = task::spawn_blocking(move || {
        raw_data
            .par_iter()
            .map(|bytes| process_data(bytes))
            .collect::<Result<Vec<_>, _>>()
    })
    .await??;

    // Phase 3: Async I/O - Upload results
    let upload_futures = processed
        .into_iter()
        .enumerate()
        .map(|(i, data)| async move {
            upload_to_s3(&format!("result-{}.dat", i), &data).await
        });
    futures::future::try_join_all(upload_futures).await?;

    Ok(Response { success: true })
}

Common Mistakes

❌ Using async for CPU work

// BAD: Async adds overhead for CPU-bound work
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let result = expensive_cpu_computation(&event.payload.data);  // Blocks async runtime
    Ok(Response { result })
}

// GOOD: Use spawn_blocking
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let data = event.payload.data.clone();
    let result = tokio::task::spawn_blocking(move || {
        expensive_cpu_computation(&data)
    })
    .await?;
    Ok(Response { result })
}

❌ Not using concurrency for I/O

// BAD: Sequential I/O
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let user = fetch_user(id).await?;
    let posts = fetch_posts(id).await?;  // Waits for user first
    Ok(Response { user, posts })
}

// GOOD: Concurrent I/O
async fn handler(event: LambdaEvent<Request>) -> Result<Response, Error> {
    let (user, posts) = tokio::try_join!(
        fetch_user(id),
        fetch_posts(id),
    )?;
    Ok(Response { user, posts })
}

Your Approach

When you see Lambda handlers:

  1. Identify workload type (I/O vs CPU)
  2. Suggest appropriate pattern (async vs sync)
  3. Show how to combine patterns for mixed workloads
  4. Explain performance implications

Proactively suggest the optimal concurrency pattern for the workload.