V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
• 请不要在回答技术问题时复制粘贴 AI 生成的内容
wsgzao
V2EX  ›  程序员

Bash 脚本递归查询批量修改文件名

  •  
  •   wsgzao ·
    wsgzao · 2020-06-02 11:14:52 +08:00 · 1763 次点击
    这是一个创建于 1653 天前的主题,其中的信息可能已经有所发展或是发生改变。

    前言

    需求是批量修改*.crt 和*.key 为 ssl.chain.crt 和 server.key ,为什么会有这样的需求主要是踩了一个大坑Sectigo AddTrust External CA Root Expiring May 30, 2020,说多了都是泪。

    更新历史

    2020 年 05 月 31 日 - 初稿

    阅读原文 - https://wsgzao.github.io/post/bash-recursive/


    解题思路

    1. 需要遍历目录
    2. 需要重命名*.key 和*.crt 结尾的文件为 server.key 和 ssl.chain.crt

    linux 命令 递归修改文件名(包括文件夹)

    网上搜索了关键词,发现这个脚本写得比较清晰,但还是需要修改下

    #!/bin/bash
    
    function changeName(){
        #new=`echo $1|sed 's/^/abc/g'`
        new=`echo $1|sed -r 's/abc(.*$)/\1/g'`
        echo changeName old: $1 new: $new
        if [ $1 != $new ];then
            mv $1 $new
        fi
    }
    
    function travFolder(){
        #echo "travFolder start"
        flist=`ls $1`
        cd $1
        for f in $flist
        do
            #echo traverse do $f
            local old=$f
            if test -d $f
            then
                #echo "traverse dir:${f}"
                travFolder $f
                #echo "traverse rename dir:${f}"
                changeName $old #rename folder
            else
                #echo "traverse file:$f"
                changeName $f
            fi
        done
        cd ../
    }
    
    param=$1
    if [ -z "$1" ]
        then
        param="./"
        echo "empty string: $param"
    else
        param=$1
    fi
    travFolder $param
    

    修改后的代码

    如果你考虑使用 rename 简化代码,可以参考 Stack Overflow 的一篇文章

    How to Batch Rename Files in a macOS Terminal?

    #!/bin/bash
    
    function travFolder(){
        #echo "travFolder start"
        flist=`ls $1`
        cd $1
        for f in *.key; do mv "$f" "server.key"; done
        for f in *.crt; do mv "$f" "ssl.chain.crt"; done
        for f in $flist
        do
            #echo traverse do $f
            if test -d $f
            then
                #echo "traverse dir:${f}"
                travFolder $f
            fi
        done
        cd ../
    }
    
    param=$1
    if [ -z "$1" ]
        then
        param="./"
        echo "empty string: $param"
    else
        param=$1
    fi
    travFolder $param
    
    

    参考文章

    Bash 教程

    linux 命令 递归修改文件名(包括文件夹)

    8 条回复    2020-06-02 21:17:29 +08:00
    ddsfeng
        1
    ddsfeng  
       2020-06-02 11:57:21 +08:00
    看来楼主对 `find` 是一无所知...
    hackerang
        2
    hackerang  
       2020-06-02 12:00:25 +08:00
    ...
    hejingyuan199
        3
    hejingyuan199  
       2020-06-02 12:02:45 +08:00
    楼主在练习递归和二叉查找树算法。
    ( joking )
    jimliang
        4
    jimliang  
       2020-06-02 12:18:54 +08:00
    find xxxx | xargs xxx | mv xxx
    alsas
        5
    alsas  
       2020-06-02 12:32:33 +08:00
    xargs 神器用起
    aloxaf
        6
    aloxaf  
       2020-06-02 12:46:08 +08:00
    此时一位使用 zmv 的 zsh 用户路过:
    ```
    autoload -Uz zmv
    zmv -n '(**/)*.key' '${1}server.key'
    ```

    并且附赠了使用 perl-rename 的方式:
    ```
    perl-rename 's/[^\/]+\.key/server.key/' **/*.key
    ```
    pmispig
        7
    pmispig  
       2020-06-02 16:49:02 +08:00
    复杂的功能统统用 python 来写,用 shell 太憋屈
    wqtacc
        8
    wqtacc  
       2020-06-02 21:17:29 +08:00
    linux 有个命令叫 rename 或者 rename.pl
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   840 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 28ms · UTC 20:29 · PVG 04:29 · LAX 12:29 · JFK 15:29
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.