mirror of
https://git.bjxgj.com/xgj/xgj-actions.git
synced 2025-10-14 04:13:37 +08:00
298 lines
11 KiB
YAML
298 lines
11 KiB
YAML
name: '状态缓存管理'
|
||
description: '利用GitHub Actions缓存机制缓存和管理状态信息,支持默认值设置'
|
||
branding:
|
||
icon: 'database'
|
||
color: 'orange'
|
||
|
||
inputs:
|
||
state-key:
|
||
description: '状态键名(用于标识缓存的状态)'
|
||
required: true
|
||
|
||
state-value:
|
||
description: '要存储的状态值(用于 set 和 get-or-set 操作)'
|
||
required: false
|
||
default: ''
|
||
|
||
default-value:
|
||
description: '默认值(当缓存未命中时使用)'
|
||
required: false
|
||
default: ''
|
||
|
||
cache-prefix:
|
||
description: '缓存前缀名称'
|
||
required: false
|
||
default: 'state'
|
||
|
||
expiry-seconds:
|
||
description: '过期时间(秒)。0 表示依赖 GitHub Actions 缓存默认生命周期(最多7天)'
|
||
required: false
|
||
default: '0'
|
||
|
||
action:
|
||
description: '操作类型:get(获取), set(设置), get-or-set(获取或设置), del(删除)'
|
||
required: false
|
||
default: 'get-or-set'
|
||
|
||
outputs:
|
||
state-value:
|
||
description: '最终的状态值'
|
||
value: ${{ steps.result.outputs.value }}
|
||
|
||
cache-hit:
|
||
description: '是否命中缓存 (true/false)'
|
||
value: ${{ steps.result.outputs.cache-hit }}
|
||
|
||
used-default:
|
||
description: '是否使用了默认值 (true/false)'
|
||
value: ${{ steps.result.outputs.used-default }}
|
||
|
||
expired:
|
||
description: '缓存是否因过期而未命中 (true/false)'
|
||
value: ${{ steps.result.outputs.expired }}
|
||
|
||
deleted:
|
||
description: '是否执行了删除操作 (true/false)'
|
||
value: ${{ steps.result.outputs.deleted }}
|
||
|
||
cache-key:
|
||
description: '使用的缓存键'
|
||
value: ${{ steps.cache-key.outputs.key }}
|
||
|
||
runs:
|
||
using: 'composite'
|
||
steps:
|
||
- name: 验证输入参数
|
||
shell: bash
|
||
run: |
|
||
# 验证 action 参数
|
||
case "${{ inputs.action }}" in
|
||
"get"|"set"|"get-or-set"|"del")
|
||
echo "✅ 操作类型有效: ${{ inputs.action }}"
|
||
;;
|
||
*)
|
||
echo "❌ 无效的操作类型: ${{ inputs.action }}"
|
||
echo " 支持的操作类型: get, set, get-or-set, del"
|
||
exit 1
|
||
;;
|
||
esac
|
||
|
||
# 验证必需参数
|
||
if [[ -z "${{ inputs.state-key }}" ]]; then
|
||
echo "❌ state-key 参数不能为空"
|
||
exit 1
|
||
fi
|
||
|
||
# 验证过期时间参数
|
||
if ! [[ "${{ inputs.expiry-seconds }}" =~ ^[0-9]+$ ]]; then
|
||
echo "❌ expiry-seconds 必须是非负整数"
|
||
exit 1
|
||
fi
|
||
|
||
# 对于 set 操作,验证 state-value
|
||
if [[ "${{ inputs.action }}" == "set" && -z "${{ inputs.state-value }}" ]]; then
|
||
echo "❌ set 操作需要提供 state-value 参数"
|
||
exit 1
|
||
fi
|
||
|
||
echo "✅ 输入参数验证通过"
|
||
if [[ "${{ inputs.expiry-seconds }}" == "0" ]]; then
|
||
echo " - 过期时间: 使用默认生命周期(最多7天)"
|
||
else
|
||
echo " - 过期时间: ${{ inputs.expiry-seconds }}秒"
|
||
fi
|
||
|
||
- name: 生成缓存键
|
||
id: cache-key
|
||
shell: bash
|
||
run: |
|
||
# 清理状态键,移除特殊字符以确保安全性
|
||
STATE_KEY_CLEAN=$(echo "${{ inputs.state-key }}" | sed 's/[^a-zA-Z0-9._-]/_/g')
|
||
|
||
# 处理过期时间
|
||
EXPIRY_SECONDS="${{ inputs.expiry-seconds }}"
|
||
if [[ "${EXPIRY_SECONDS}" == "0" ]]; then
|
||
# 使用默认生命周期,使用基础缓存键
|
||
CACHE_KEY="${{ runner.os }}-${{ inputs.cache-prefix }}-${STATE_KEY_CLEAN}"
|
||
echo "🔑 生成缓存键(默认生命周期): ${CACHE_KEY}"
|
||
else
|
||
# 计算时间窗口,实现自动过期
|
||
CURRENT_TIME=$(date +%s)
|
||
TIME_WINDOW=$((CURRENT_TIME / EXPIRY_SECONDS))
|
||
CACHE_KEY="${{ runner.os }}-${{ inputs.cache-prefix }}-${STATE_KEY_CLEAN}-${TIME_WINDOW}"
|
||
echo "🔑 生成缓存键(${EXPIRY_SECONDS}秒过期): ${CACHE_KEY}"
|
||
echo "⏰ 时间窗口: ${TIME_WINDOW}"
|
||
fi
|
||
|
||
echo "key=${CACHE_KEY}" >> $GITHUB_OUTPUT
|
||
|
||
- name: 获取缓存状态
|
||
id: cache-get
|
||
if: inputs.action == 'get' || inputs.action == 'get-or-set' || inputs.action == 'del'
|
||
uses: actions/cache/restore@v4
|
||
with:
|
||
path: .cache-state-${{ inputs.state-key }}
|
||
key: ${{ steps.cache-key.outputs.key }}
|
||
|
||
- name: 读取缓存的状态值
|
||
id: read-cached
|
||
if: inputs.action == 'get' || inputs.action == 'get-or-set' || inputs.action == 'del'
|
||
shell: bash
|
||
run: |
|
||
CACHE_FILE=".cache-state-${{ inputs.state-key }}"
|
||
|
||
if [[ "${{ steps.cache-get.outputs.cache-hit }}" == "true" && -f "${CACHE_FILE}" ]]; then
|
||
CACHED_VALUE=$(cat "${CACHE_FILE}" 2>/dev/null || echo "")
|
||
|
||
# 检查是否是删除标记
|
||
if [[ "${CACHED_VALUE}" == "__DELETED__" ]]; then
|
||
echo "value=" >> $GITHUB_OUTPUT
|
||
echo "🗑️ 检测到删除标记,视为缓存未命中"
|
||
else
|
||
echo "value=${CACHED_VALUE}" >> $GITHUB_OUTPUT
|
||
echo "✅ 成功读取缓存值"
|
||
fi
|
||
else
|
||
echo "value=" >> $GITHUB_OUTPUT
|
||
echo "⚠️ 缓存未命中或文件不存在"
|
||
fi
|
||
|
||
- name: 处理状态值逻辑
|
||
id: result
|
||
shell: bash
|
||
run: |
|
||
USED_DEFAULT="false"
|
||
EXPIRED="false"
|
||
DELETED="false"
|
||
CACHE_HIT="false"
|
||
FINAL_VALUE=""
|
||
|
||
# 判断是否因过期而未命中缓存
|
||
if [[ "${{ steps.cache-get.outputs.cache-hit }}" != "true" && "${{ inputs.expiry-seconds }}" != "0" ]]; then
|
||
EXPIRED="true"
|
||
fi
|
||
|
||
case "${{ inputs.action }}" in
|
||
"get")
|
||
if [[ "${{ steps.cache-get.outputs.cache-hit }}" == "true" && -n "${{ steps.read-cached.outputs.value }}" ]]; then
|
||
FINAL_VALUE="${{ steps.read-cached.outputs.value }}"
|
||
CACHE_HIT="true"
|
||
echo "✅ 获取模式: 使用缓存值"
|
||
else
|
||
FINAL_VALUE="${{ inputs.default-value }}"
|
||
USED_DEFAULT="true"
|
||
if [[ "${EXPIRED}" == "true" ]]; then
|
||
echo "⚠️ 获取模式: 缓存已过期,使用默认值"
|
||
else
|
||
echo "⚠️ 获取模式: 缓存未命中,使用默认值"
|
||
fi
|
||
fi
|
||
;;
|
||
|
||
"set")
|
||
FINAL_VALUE="${{ inputs.state-value }}"
|
||
echo "✅ 设置模式: 将存储新的状态值"
|
||
;;
|
||
|
||
"get-or-set")
|
||
if [[ "${{ steps.cache-get.outputs.cache-hit }}" == "true" && -n "${{ steps.read-cached.outputs.value }}" ]]; then
|
||
FINAL_VALUE="${{ steps.read-cached.outputs.value }}"
|
||
CACHE_HIT="true"
|
||
echo "✅ 获取或设置模式: 使用缓存值"
|
||
else
|
||
if [[ -n "${{ inputs.state-value }}" ]]; then
|
||
FINAL_VALUE="${{ inputs.state-value }}"
|
||
if [[ "${EXPIRED}" == "true" ]]; then
|
||
echo "⚠️ 获取或设置模式: 缓存已过期,使用提供的新值"
|
||
else
|
||
echo "⚠️ 获取或设置模式: 缓存未命中,使用提供的新值"
|
||
fi
|
||
else
|
||
FINAL_VALUE="${{ inputs.default-value }}"
|
||
USED_DEFAULT="true"
|
||
if [[ "${EXPIRED}" == "true" ]]; then
|
||
echo "⚠️ 获取或设置模式: 缓存已过期,使用默认值"
|
||
else
|
||
echo "⚠️ 获取或设置模式: 缓存未命中,使用默认值"
|
||
fi
|
||
fi
|
||
fi
|
||
;;
|
||
|
||
"del")
|
||
DELETED="true"
|
||
FINAL_VALUE=""
|
||
if [[ "${{ steps.cache-get.outputs.cache-hit }}" == "true" && -n "${{ steps.read-cached.outputs.value }}" ]]; then
|
||
CACHE_HIT="true"
|
||
echo "🗑️ 删除模式: 删除现有缓存状态"
|
||
else
|
||
echo "🗑️ 删除模式: 状态不存在,执行删除标记"
|
||
fi
|
||
;;
|
||
esac
|
||
|
||
echo "value=${FINAL_VALUE}" >> $GITHUB_OUTPUT
|
||
echo "used-default=${USED_DEFAULT}" >> $GITHUB_OUTPUT
|
||
echo "expired=${EXPIRED}" >> $GITHUB_OUTPUT
|
||
echo "deleted=${DELETED}" >> $GITHUB_OUTPUT
|
||
echo "cache-hit=${CACHE_HIT}" >> $GITHUB_OUTPUT
|
||
|
||
- name: 保存状态到缓存
|
||
if: (inputs.action == 'set') || (inputs.action == 'get-or-set' && steps.cache-get.outputs.cache-hit != 'true') || (inputs.action == 'del')
|
||
shell: bash
|
||
run: |
|
||
CACHE_FILE=".cache-state-${{ inputs.state-key }}"
|
||
|
||
if [[ "${{ inputs.action }}" == "del" ]]; then
|
||
# 删除操作:写入删除标记
|
||
echo "__DELETED__" > "${CACHE_FILE}"
|
||
echo "🗑️ 删除标记已写入临时文件"
|
||
else
|
||
# 设置操作:写入实际值
|
||
echo "${{ steps.result.outputs.value }}" > "${CACHE_FILE}"
|
||
echo "✅ 状态值已写入临时文件"
|
||
fi
|
||
|
||
- name: 缓存状态值
|
||
id: cache-set
|
||
if: (inputs.action == 'set') || (inputs.action == 'get-or-set' && steps.cache-get.outputs.cache-hit != 'true') || (inputs.action == 'del')
|
||
uses: actions/cache/save@v4
|
||
with:
|
||
path: .cache-state-${{ inputs.state-key }}
|
||
key: ${{ steps.cache-key.outputs.key }}
|
||
|
||
- name: 清理临时文件
|
||
if: always()
|
||
shell: bash
|
||
run: |
|
||
CACHE_FILE=".cache-state-${{ inputs.state-key }}"
|
||
if [[ -f "${CACHE_FILE}" ]]; then
|
||
rm -f "${CACHE_FILE}"
|
||
echo "🧹 清理临时文件完成"
|
||
fi
|
||
|
||
- name: 操作总结
|
||
shell: bash
|
||
run: |
|
||
echo "📊 状态缓存操作总结:"
|
||
echo " - 操作类型: ${{ inputs.action }}"
|
||
echo " - 状态键名: ${{ inputs.state-key }}"
|
||
echo " - 缓存键名: ${{ steps.cache-key.outputs.key }}"
|
||
echo " - 缓存命中: ${{ steps.result.outputs.cache-hit }}"
|
||
echo " - 使用默认值: ${{ steps.result.outputs.used-default }}"
|
||
echo " - 缓存过期: ${{ steps.result.outputs.expired }}"
|
||
echo " - 执行删除: ${{ steps.result.outputs.deleted }}"
|
||
echo " - 过期时间: ${{ inputs.expiry-seconds }}秒"
|
||
|
||
if [[ "${{ steps.result.outputs.used-default }}" == "true" ]]; then
|
||
echo " ⚠️ 注意: 使用了默认值,这可能影响后续流程"
|
||
fi
|
||
|
||
if [[ "${{ steps.result.outputs.expired }}" == "true" ]]; then
|
||
echo " ⏰ 注意: 缓存因过期而失效"
|
||
fi
|
||
|
||
if [[ "${{ steps.result.outputs.deleted }}" == "true" ]]; then
|
||
echo " 🗑️ 注意: 已执行删除操作,状态已被清除"
|
||
fi
|