Não pode escolher mais do que 25 tópicos Os tópicos devem começar com uma letra ou um número, podem incluir traços ('-') e podem ter até 35 caracteres.
 
 
 

139 linhas
3.5 KiB

  1. #!/usr/bin/env bash
  2. set -euo pipefail
  3. if [[ -z "${ANTHROPIC_API_KEY:-}" ]]; then
  4. echo "ANTHROPIC_API_KEY is required" >&2
  5. exit 1
  6. fi
  7. if ! command -v jq >/dev/null 2>&1; then
  8. echo "jq is required to build the JSON payload and summarize usage" >&2
  9. exit 1
  10. fi
  11. MODEL="${MODEL:-claude-opus-4-6}"
  12. ANTHROPIC_VERSION="${ANTHROPIC_VERSION:-2023-06-01}"
  13. API_URL="${ANTHROPIC_API_URL:-https://lancerouter.ai/v1/messages}"
  14. CACHE_SENTENCE_COUNT="${CACHE_SENTENCE_COUNT:-240}"
  15. REQUEST_COUNT="${REQUEST_COUNT:-2}"
  16. SAME_USER_PROMPT="${SAME_USER_PROMPT:-0}"
  17. CACHE_MODE="${CACHE_MODE:-explicit}"
  18. DRY_RUN="${DRY_RUN:-0}"
  19. case "$CACHE_MODE" in
  20. explicit | automatic)
  21. ;;
  22. *)
  23. echo "CACHE_MODE must be 'explicit' or 'automatic'" >&2
  24. exit 1
  25. ;;
  26. esac
  27. build_payload() {
  28. local question="$1"
  29. jq -n \
  30. --arg model "$MODEL" \
  31. --arg question "$question" \
  32. --arg cache_mode "$CACHE_MODE" \
  33. --argjson sentence_count "$CACHE_SENTENCE_COUNT" '
  34. def zpad4:
  35. tostring as $raw | ("0000" + $raw) | .[-4:];
  36. (reduce range(1; $sentence_count + 1) as $i
  37. ("";
  38. . + "Cache test invariant sentence " + ($i | zpad4) + ": this exact line must remain unchanged across requests. "
  39. )) as $ctx
  40. | ({
  41. model: $model,
  42. max_tokens: 20,
  43. system: [
  44. {
  45. type: "text",
  46. text: $ctx
  47. }
  48. ],
  49. messages: [
  50. {
  51. role: "user",
  52. content: $question
  53. }
  54. ]
  55. }
  56. | if $cache_mode == "automatic" then
  57. . + { cache_control: { type: "ephemeral" } }
  58. else
  59. .system[0].cache_control = { type: "ephemeral" }
  60. end)
  61. '
  62. }
  63. send_request() {
  64. local question="$1"
  65. build_payload "$question" | curl --silent --show-error "$API_URL" \
  66. --header "x-api-key: $ANTHROPIC_API_KEY" \
  67. --header "anthropic-version: $ANTHROPIC_VERSION" \
  68. --header "content-type: application/json" \
  69. -D /tmp/cache_test_headers.txt \
  70. --data @-
  71. }
  72. extract_header() {
  73. local header_name="$1"
  74. grep -i "^${header_name}:" /tmp/cache_test_headers.txt 2>/dev/null \
  75. | head -1 \
  76. | sed 's/^[^:]*: *//' \
  77. | tr -d '\r\n' \
  78. || echo "N/A"
  79. }
  80. summarize_response() {
  81. jq 'if has("error") then
  82. {
  83. type,
  84. error
  85. }
  86. elif (.content | type) == "array" then
  87. {
  88. id,
  89. model,
  90. stop_reason,
  91. usage,
  92. text: (.content | map(select(.type == "text") | .text) | join(""))
  93. }
  94. else
  95. .
  96. end'
  97. }
  98. for i in $(seq 1 "$REQUEST_COUNT"); do
  99. if [[ "$SAME_USER_PROMPT" == "1" ]]; then
  100. question="Reply with only: cache-test"
  101. else
  102. question="Reply with only: request-$i"
  103. fi
  104. if [[ "$DRY_RUN" == "1" ]]; then
  105. build_payload "$question" | jq
  106. else
  107. echo "=== Request $i/$REQUEST_COUNT: $question ==="
  108. send_request "$question" | tee /tmp/anthropic_cache_response.json | summarize_response
  109. echo "x-oneapi-request-id: $(extract_header 'X-Oneapi-Request-Id')"
  110. echo "x-request-id: $(extract_header 'X-Request-Id')"
  111. echo
  112. fi
  113. done
  114. if [[ "$DRY_RUN" != "1" ]]; then
  115. echo "Expected cache signal:"
  116. echo "- First response usage.cache_creation_input_tokens should be greater than 0."
  117. echo "- Later responses usage.cache_read_input_tokens should be greater than 0."
  118. echo
  119. echo "Diagnostic mode:"
  120. echo "REQUEST_COUNT=10 SAME_USER_PROMPT=1 MODEL=\"$MODEL\" ./test/anthropic_cache_test.sh"
  121. echo
  122. echo "Automatic caching mode:"
  123. echo "CACHE_MODE=automatic MODEL=\"$MODEL\" ./test/anthropic_cache_test.sh"
  124. fi