生产redis数据出问题了_shell脚本刷redis数据

java程序员_shell脚本之路_redis刷数据

业务需求描述

  • 需求描述,由于线上事故,现在急需将线上redis某个业务规则的key的数据刷下

  • 赋予shell脚本 执行权限

  • chmod +x update_redis_values.sh

shell 脚本编写

bash 复制代码
#!/bin/bash

prefixes=("WSH" "WBJ")

REDIS_HOST="172.22.197.5"
REDIS_PORT="6379"
REDIS_PASSWORD='V3gk5OAZ'
REDIS_DB=3

for item in "${prefixes[@]}"; do
  # 生成Redis的key
  key="wms:shsc:${item}:serial_number:PREFIX:${item}"

  # 从Redis中获取当前值
  value=$(redis-cli -h $REDIS_HOST -p $REDIS_PORT -a $REDIS_PASSWORD -n $REDIS_DB GET "$key")

  if [ "$value" != "" ]; then
    # 提取数字部分(假设前缀部分是WXA,剩下的是数字)
    item2=$(echo "$value" | sed 's/[0-9]//g' | sed 's/"//g')
    number=$(echo "$value" | sed 's/[^0-9]//g')

    if [[ "$number" =~ ^[0-9]+$ ]]; then
      # 获取数值的长度
      length=${#number}

      # 判断数值是否符合预期长度(比如13位数字)
      if [ "$length" -ge 9 ]; then
        # 将倒数第九位数字替换为2
        # 使用字符串操作,保留前面的部分,替换倒数第九位为2,后面的部分不变
        new_number="${number:0:$(($length-9))}2${number:$(($length-8))}"

        # 构造新的值,保留原始前缀和新的数字
        new_value_str="\"${item2}${new_number}\""

        # 将新的值设置回Redis
        redis-cli -h $REDIS_HOST -p $REDIS_PORT -a $REDIS_PASSWORD -n $REDIS_DB SET "$key" "$new_value_str"

        echo "Updated $key: $value -> $new_value_str"
      else
        echo "Value is too short to replace: $value"
      fi
    else
      echo "Invalid value format for key $key: $value"
    fi
  else
    echo "Key $key not found"
  fi
done

上面用到的语法讲解

1: "" 与 ''

    1. 单引号 ( '' ):

作用:单引号中的内容会被完全按字面意思处理。也就是说,Shell不会对单引号中的任何字符进行变量替换、命令替换或转义。特点:单引号中的特殊字符(如 $ 、 " 、 \ 等)都被当做普通字符处理,不会触发任何特殊操作。

shell 复制代码
variable="World"
echo '$variable' 


输出: $variable

因为使用了单引号, $variable 会被当作普通字符串输出,而不会进行变量替换。

    1. 双引号 ( "" ):

    作用 :双引号中的内容允许变量替换和命令替换。也就是说,Shell会在双引号内解析 $、`````(反引号,命令替换)等特殊字符。

    特点:双引号保留了空格和换行等字符,因此通常用于包含空格或特殊字符的字符串,但仍然允许变量替换。

shell 复制代码
variable="World"
echo "$variable"  

# 输出: World

结果:因为使用了双引号,$variable 会被解析为其值 "World",并输出。

    1. 其他细节:

在双引号中,可以使用反斜杠 () 来转义特殊字符,如 `"` 或 `$` 等。 单引号中的反斜杠()是普通字符,不会被用来转义后面的字符。

bash 复制代码
echo "It\'s a test"  # 输出: It's a test
echo 'It\'s a test'  # 输出: It\'s a test
  • 总结:

    单引号:内容严格按照字面量处理,不做任何替换或转义。

    双引号:允许变量替换、命令替换和转义,通常用于包含空格或

2: Bash中的数组

在Shell脚本中,数组的定义和使用方式依赖于你使用的Shell类型(如 Bash)。以下是一些常见的数组定义方法和示例:

1. Bash中的数组定义

  • 在Bash中,数组是通过将元素用空格分隔并用括号括起来的方式定义的。
bash 复制代码
# 使用括号定义数组
array=(1 2 3 4 5)
  • 访问数组元素
  • 数组元素的访问通过索引来实现。索引从 0 开始。
bash 复制代码
echo ${array[0]}  
# 输出: 1
echo ${array[1]} 
# 输出: 2
  • 获取数组的长度(元素个数) 可以使用 ${#array[@]} 来获取数组的长度。
bash 复制代码
echo ${#array[@]}  # 输出: 5
  • 遍历数组 使用 for 循环可以遍历数组中的所有元素:
bash 复制代码
for element in "${array[@]}"; do
    echo $element
done

2. 其他注意事项

  • 在使用索引时,数组索引是从0开始的。

  • 定义数组时如果没有使用括号,就会定义一个普通变量,而不是数组。

  • 示例:

bash 复制代码
my_var="Hello"
echo $my_var  # 输出: Hello
  • 总结:
  • 一维数组 :通过 ( ) 来定义,使用索引访问元素。
  • 关联数组 :使用 declare -A 来定义,使用键(字符串)访问值。

这些是Shell脚本中常见的数组定义和使用方法。

3: shell $

在Shell脚本中,$ 符号有多种用途,主要用于表示变量、命令替换和特殊参数。以下是 $ 的一些常见用法:

    1. 变量引用 $ 用于引用变量的值。
bash 复制代码
name="Alice"
echo "Hello, $name"  # 输出: Hello, Alice
    1. 命令替换 使用反引号(`````)或 $(...) 语法可以执行命令并将其输出作为字符串返回。
bash 复制代码
current_date=$(date)
echo "Today's date is: $current_date"
    1. 特殊变量 $ 后面可以跟一些特殊字符,表示特定的含义。
  • $0:脚本的名称。

  • $1, $2, ... :脚本的参数,$1 是第一个参数,$2 是第二个参数,以此类推。

  • $#:传递给脚本的参数个数。

  • $@:所有参数的列表(以空格分隔)。

  • $*:所有参数的列表(作为一个单一的字符串)。

  • $?:上一个命令的退出状态(返回值)。

  • $$:当前Shell进程的PID(进程ID)。

bash 复制代码
echo "Script name: $0"
echo "First argument: $1"
echo "Number of arguments: $#"
    1. 变量赋值 在赋值时,$ 不用于变量名。
bash 复制代码
my_var="Hello"  # 正确
echo $my_var    # 输出: Hello
    1. 其他用法 转义字符 :如果需要在字符串中使用 $ 符号而不进行变量替换,可以使用反斜杠 \ 进行转义。
bash 复制代码
echo "This is a dollar sign: \$"  # 输出: This is a特殊参数: $
- 了解 `$` 的用法对于编写和调试Shell脚本非常重要。

### 4 赋值操作符(`=`)两边不能有空格
在Shell脚本中,赋值操作符(`=`)两边不能有空格。这是因为Shell认为空格分隔了命令的不同部分,所以如果你在等号两边放置空格,Shell会将其解析为多个不同的命令或参数,从而导致语法错误。

#### 正确的变量赋值:
```bash
my_var="Hello"   # 正确,等号两边没有空格
错误的变量赋值:
my_var = "Hello"  # 错误,等号两边有空格
在第二个示例中,Shell会将 `my_var` 和 `= "Hello"` 分开解释,这会导致错误。
小结:赋值时,等号两边**不能**有空格。

4: redis-cli 客户端命令

shell 复制代码
redis-cli 客户端命令

value=$(redis-cli -h $REDIS_HOST -p $REDIS_PORT -a $REDIS_PASSWORD -n $REDIS_DB GET "$key")  



#!/bin/bash
# 定义 Redis 连接参数
REDIS_HOST="127.0.0.1"
REDIS_PORT="6379"

# 定义一个函数来获取键的值
get_redis_value() {
    redis-cli -h $REDIS_HOST -p $REDIS_PORT GET "$1"
}

# 获取键的值
value1=$(get_redis_value 123)
value2=$(get_redis_value 456)

# 输出结果
echo "Value for key 123: $value1"
echo "Value for key 456: $value2"

5: if "$value" != "" ; then

讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解讲解 复制代码
这段代码是一个 Shell 脚本中的条件判断语句,具体来说,它是用于检查变量 `$value` 是否不为空。下面是对这段代码的详细解释:

`if`: 这是一个条件语句的开始,后面跟着一个条件表达式。
  
`[ "$value" != "" ]`: 这是条件表达式,使用方括号 `[]` 来进行测试。具体解释如下:
`"$value"`: 这是对变量 `value` 的引用。使用双引号包裹变量是一个好习惯,可以防止变量为空或包含空格时引发错误。
`!=`: 这是一个比较运算符,表示"不等于"。
`""`: 这是一个空字符串,用于与变量 `$value` 进行比较。
  
`then`: 如果条件成立(即 `$value` 不为空),将执行 `then` 后面的代码块。

整体逻辑
这段代码的逻辑是:如果变量 `value` 的值不是空字符串,那么就执行 `then` 后面的代码。这通常用于确保在执行某些操作之前,变量中确实有值。





以下是一个简单的示例,展示如何使用这段代码:

```bash
value="Hello, World!"

if [ "$value" != "" ]; then
    echo "Value is not empty: $value"
else
    echo "Value is empty"
fi

在这个示例中,由于 value 变量被赋值为 "Hello, World!",所以输出将是 Value is not empty: Hello, World!

  • 注意事项
  • 在 Shell 脚本中,使用方括号 [] 进行条件测试时,通常需要注意空格的使用。例如,[ "$value" != "" ] 中的空格是必须的。
  • 在某些情况下,使用 [[ ]] 代替 [ ] 可以提供更强大的功能和
相关推荐
颜酱几秒前
# 02 | 搭骨架:用 LangGraph 编排 12 步工作流(思路)
前端·人工智能·后端
颜酱1 分钟前
02 | 搭骨架:用 LangGraph 编排 12 步工作流
前端·人工智能·后端
嘉伟桑1 小时前
Python调用电价API返回JSON示例:分时电价、现货电价和字段解析
后端
武子康1 小时前
Shippy:确定性工具、会话级 Sandbox 与 Live-Data Eval(4 类收敛 + 7 步实现方案 + 6 类评测指标)
前端·人工智能·后端
我叫黑大帅2 小时前
我为什么单一消费者的场景下,要用 Redis List 当消息队列?
redis·后端·面试
AskHarries2 小时前
文件上传系统
后端
止语Lab3 小时前
好的 DX 不等于少写代码——三种语言的摩擦力设计课
后端
吃饱了得干活3 小时前
别再手动解析 LLM 输出了!LangChain 四种结构化输出方案对比
后端·python·langchain
程序员天天困3 小时前
Arthas trace 命令怎么用?一行定位最慢那行代码
jvm·后端
Huiturn3 小时前
GPT 5.6 连续编码 10 小时,纯 Python 啃下 Word 二进制格式——doc2docx 实现拆解
后端