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

pitfalls-security

Security patterns for session keys, caching, logging, and environment variables. Use when implementing authentication, caching sensitive data, or setting up logging. Triggers on: session key, private key, cache, logging, secrets, environment variable.

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

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

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

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

💾 手動でダウンロードしたい(コマンドが難しい人向け)
  1. 1. 下の青いボタンを押して pitfalls-security.zip をダウンロード
  2. 2. ZIPファイルをダブルクリックで解凍 → pitfalls-security フォルダができる
  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 自身は原文を読みます。誤訳がある場合は原文をご確認ください。

セキュリティの落とし穴

セキュリティに関するよくある落とし穴と正しいパターンについて説明します。

どのような時に使うか

  • セッションキー管理の実装
  • データのキャッシュ(特に機密性の高いデータ)
  • 構造化ロギングの設定
  • 環境変数の取り扱い
  • セキュリティ上重要なコードのレビュー

ワークフロー

ステップ 1: キーのストレージの確認

プレーンテキストで秘密鍵が保存されていないことを確認します。

ステップ 2: キャッシュの安全性の確認

機密データが不適切にキャッシュされていないことを確認します。

ステップ 3: ロギングの確認

ログにシークレットが含まれていないことを確認します。


セッションキーのセキュリティ

// ❌ 秘密鍵を絶対に保存しないでください
localStorage.setItem('privateKey', key);  // 壊滅的

// ✅ 制限された権限を持つセッションキーを使用する
interface SessionKey {
  address: Address;
  permissions: Permission[];
  expiresAt: Date;
  maxPerTrade: bigint;
}

// ✅ 保存されたクレデンシャルには AES-256-GCM を使用する
import { createCipheriv, randomBytes } from 'crypto';
const iv = randomBytes(16);
const cipher = createCipheriv('aes-256-gcm', key, iv);

// ✅ すべてのキー操作の監査ログ
await auditLog.create({
  action: 'SESSION_KEY_CREATED',
  userId,
  metadata: { permissions, expiresAt },
});

環境変数

// Frontend (Vite)
const apiUrl = import.meta.env.VITE_API_URL;  // ✅ VITE_ プレフィックスが必要
// ❌ process.env.API_URL はフロントエンドでは動作しません

// Backend
const dbUrl = process.env.DATABASE_URL;

// ❌ シークレットを絶対にログに記録しないでください
console.log('Config:', config);  // シークレットが含まれている可能性があります!
// ✅ 安全にログを記録する
console.log('Config loaded for:', config.environment);

キャッシュ戦略

// ✅ コストのかかる計算のためのサーバーサイドキャッシュ
const priceCache = new Map<string, { value: number; expires: number }>();

function getCachedPrice(token: string): number | null {
  const cached = priceCache.get(token);
  if (cached && cached.expires > Date.now()) {
    return cached.value;
  }
  return null;
}

// ✅ データの鮮度ニーズに基づいた TTL
const CACHE_TTL = {
  tokenPrice: 10_000,      // 10s - 価格はすぐに変わる
  poolReserves: 5_000,     // 5s - スワップに不可欠
  gasPrice: 15_000,        // 15s
  userBalance: 30_000,     // 30s
  tokenMetadata: 3600_000, // 1 時間 - めったに変わらない
};

// ❌ ユーザー固有の機密データをキャッシュしないでください
cache.set(`user:${userId}:privateKey`, key);  // 絶対にしないでください!

構造化ロギング

// ✅ 構造化ロギング (JSON 形式)
const logger = {
  info: (message: string, context?: object) => {
    console.log(JSON.stringify({
      level: 'info',
      message,
      timestamp: new Date().toISOString(),
      ...context,
    }));
  },
  error: (message: string, error: Error, context?: object) => {
    console.error(JSON.stringify({
      level: 'error',
      message,
      error: error.message,
      stack: error.stack,
      timestamp: new Date().toISOString(),
      ...context,
    }));
  },
};

// ✅ コンテキストを含める
logger.info('Trade executed', {
  userId: 'user123',
  txHash: '0x...',
  chain: 'ethereum',
  profit: '12.34',
});

// ❌ シークレットを絶対にログに記録しないでください
logger.info('Config', { apiKey: process.env.API_KEY });  // 絶対にしないでください!

監査ロギング

// ✅ 重要な操作の監査ログ
await auditLog.create({
  action: 'TRADE_EXECUTED',
  userId,
  before: previousState,
  after: newState,
  timestamp: new Date(),
  metadata: { txHash, chain },
});

簡単なチェックリスト

  • [ ] localStorage に秘密鍵がないこと
  • [ ] セッションキーに有効期限と制限があること
  • [ ] 保存されたクレデンシャルに AES-256-GCM を使用していること
  • [ ] 重要な操作の監査ログ
  • [ ] console.log にシークレットがないこと
  • [ ] 機密データが不適切にキャッシュされていないこと
  • [ ] フロントエンドの環境変数に VITE_ プレフィックスが付いていること
📜 原文 SKILL.md(Claudeが読む英語/中国語)を展開

Security Pitfalls

Common pitfalls and correct patterns for security.

When to Use

  • Implementing session key management
  • Caching data (especially sensitive)
  • Setting up structured logging
  • Handling environment variables
  • Reviewing security-sensitive code

Workflow

Step 1: Check Key Storage

Verify no private keys stored in plaintext.

Step 2: Verify Cache Safety

Ensure sensitive data not cached inappropriately.

Step 3: Check Logging

Confirm no secrets in logs.


Session Key Security

// ❌ NEVER store private keys
localStorage.setItem('privateKey', key);  // CATASTROPHIC

// ✅ Use session keys with limited permissions
interface SessionKey {
  address: Address;
  permissions: Permission[];
  expiresAt: Date;
  maxPerTrade: bigint;
}

// ✅ AES-256-GCM for any stored credentials
import { createCipheriv, randomBytes } from 'crypto';
const iv = randomBytes(16);
const cipher = createCipheriv('aes-256-gcm', key, iv);

// ✅ Audit logging for all key operations
await auditLog.create({
  action: 'SESSION_KEY_CREATED',
  userId,
  metadata: { permissions, expiresAt },
});

Environment Variables

// Frontend (Vite)
const apiUrl = import.meta.env.VITE_API_URL;  // ✅ VITE_ prefix required
// ❌ process.env.API_URL won't work in frontend

// Backend
const dbUrl = process.env.DATABASE_URL;

// ❌ NEVER log secrets
console.log('Config:', config);  // May contain secrets!
// ✅ Log safely
console.log('Config loaded for:', config.environment);

Caching Strategies

// ✅ Server-side cache for expensive computations
const priceCache = new Map<string, { value: number; expires: number }>();

function getCachedPrice(token: string): number | null {
  const cached = priceCache.get(token);
  if (cached && cached.expires > Date.now()) {
    return cached.value;
  }
  return null;
}

// ✅ TTL based on data freshness needs
const CACHE_TTL = {
  tokenPrice: 10_000,      // 10s - prices change fast
  poolReserves: 5_000,     // 5s - critical for swaps
  gasPrice: 15_000,        // 15s
  userBalance: 30_000,     // 30s
  tokenMetadata: 3600_000, // 1 hour - rarely changes
};

// ❌ Never cache user-specific sensitive data
cache.set(`user:${userId}:privateKey`, key);  // NEVER!

Structured Logging

// ✅ Structured logging (JSON format)
const logger = {
  info: (message: string, context?: object) => {
    console.log(JSON.stringify({
      level: 'info',
      message,
      timestamp: new Date().toISOString(),
      ...context,
    }));
  },
  error: (message: string, error: Error, context?: object) => {
    console.error(JSON.stringify({
      level: 'error',
      message,
      error: error.message,
      stack: error.stack,
      timestamp: new Date().toISOString(),
      ...context,
    }));
  },
};

// ✅ Include context
logger.info('Trade executed', {
  userId: 'user123',
  txHash: '0x...',
  chain: 'ethereum',
  profit: '12.34',
});

// ❌ NEVER log secrets
logger.info('Config', { apiKey: process.env.API_KEY });  // NEVER!

Audit Logging

// ✅ Audit logging for sensitive operations
await auditLog.create({
  action: 'TRADE_EXECUTED',
  userId,
  before: previousState,
  after: newState,
  timestamp: new Date(),
  metadata: { txHash, chain },
});

Quick Checklist

  • [ ] No private keys in localStorage
  • [ ] Session keys have expiry and limits
  • [ ] AES-256-GCM for stored credentials
  • [ ] Audit logging for sensitive operations
  • [ ] No secrets in console.log
  • [ ] Sensitive data not cached inappropriately
  • [ ] VITE_ prefix for frontend env vars