首页 > 解决方案 > 从 python 在符号链接目录中运行 Makefile

问题描述

我有一个~/PROJECTS包含几个子目录的目录,其中一些是指向其他目录的符号链接。

.
├── proj1_symlink_dir
├── proj2_symlink_dir
├── proj3_symlink_dir
├── backup_1_dir
├── backup_2_dir

这些符号链接目录中的每一个(指向我硬盘上的其他目录),即 [proj1_symlink_dir, proj2_symlink_dir, proj3_symlink_dir] 每个都包含一个Makefile.

我想写一个python脚本来:

  1. 仅循环访问活动目录中的符号链接
  2. 对于这些符号链接中的每一个,进入目录并运行make clean(或允许包含 make 命令的字符串参数)

任何人都可以协助编写一个紧凑的pythonic脚本来帮助执行上述任务吗?

到目前为止,我有以下打印符号链接(改编自此处):

dirname = os.getcwd()
for name in os.listdir(dirname):
    if name not in (os.curdir, os.pardir):
        full = os.path.join(dirname, name)
        if os.path.islink(full):
            print(name, '->', os.readlink(full))

我不确定如何Makefile安全地处理 python 中的运行命令

更新

在@Marat 的帮助下,我现在创建了以下名为 runmke.py.

#!/Usr/bin/env python

import argparse
import os
import json

def run_symlink_makefile_cmd(dirname, make_cmds, verbose):
    """
    Run common make commands from makefiles from 
    all symlinked directories that are located 
    in a specified directory
    """
    make_cmds_str = " ".join(make_cmds)
    for name in os.listdir(dirname):
        if name not in (os.curdir, os.pardir):
            full = os.path.join(dirname, name)
            if os.path.islink(full):
                if verbose:
                    print(f"\n>>>>> Running the Make command:")
                    print(f"make -C {full} {make_cmds_str}")
                os.system(f"make -C {full} {make_cmds_str}")

def main(dirname, make_cmds, verbose):
    # Display parameters passed for the given run (includes defaults)
    print(f"""The parameters for this run are:\n {json.dumps(locals(), indent=2, default=str)}""")
    run_symlink_makefile_cmd(dirname=dirname,
                             make_cmds=make_cmds,
                             verbose=verbose)
    
if __name__ == '__main__':
    parser = argparse.ArgumentParser()
    parser.add_argument('-d', '--dirname', action='store', default=os.getcwd(),
                        help='The directory in which symlink directories, default is the current directory')
    parser.add_argument('-m', '--make_cmds', nargs='+',
                        default=["clean", "latex_style"],
                        help='These are the Makefile commands to run')
    parser.add_argument('-v', '--verbose', action='store_true', default=True,
                        help='If true, print updates while processing.')
    argument_parsed = parser.parse_args()

    main(
        dirname=argument_parsed.dirname,
        make_cmds=argument_parsed.make_cmds,
        verbose=argument_parsed.verbose
    )

但是,当我./runmke.py -m latex_style -v False 在终端中运行时,出现错误:

usage: runmke.py [-h] [-d DIRNAME] [-m MAKE_CMDS [MAKE_CMDS ...]] [-v]
runmke.py: error: unrecognized arguments: False

verbose为什么逻辑论证没有被识别的任何想法。它有效,当我不手动传递它时。

标签: pythonmakefile

解决方案


在@Marat 的帮助下,我现在创建了以下名为 runmke.py.

#!/Usr/bin/env python

import argparse
import os
import json

def run_symlink_makefile_cmd(dirname, make_cmds, verbose):
    """
    Run common make commands from makefiles from 
    all symlinked directories that are located 
    in a specified directory
    """
    make_cmds_str = " ".join(make_cmds)
    for name in os.listdir(dirname):
        if name not in (os.curdir, os.pardir):
            full = os.path.join(dirname, name)
            if os.path.islink(full):
                if verbose:
                    print(f"\n>>>>> Running the Make command:")
                    print(f"make -C {full} {make_cmds_str}")
                os.system(f"make -C {full} {make_cmds_str}")

def main(dirname, make_cmds, verbose):
    # Display parameters passed for the given run (includes defaults)
    print(f"""The parameters for this run are:\n {json.dumps(locals(), indent=2, default=str)}""")
    run_symlink_makefile_cmd(dirname=dirname,
                             make_cmds=make_cmds,
                             verbose=verbose)
    
if __name__ == '__main__':
    parser = argparse.ArgumentParser()
    parser.add_argument('-d', '--dirname', action='store', default=os.getcwd(),
                        help='The directory in which symlink directories, default is the current directory')
    parser.add_argument('-m', '--make_cmds', nargs='+',
                        default=["clean", "latex_style"],
                        help='These are the Makefile commands to run')
    parser.add_argument('-v', '--verbose', action='store_true', default=True,
                        help='If true, print updates while processing.')
    argument_parsed = parser.parse_args()

    main(
        dirname=argument_parsed.dirname,
        make_cmds=argument_parsed.make_cmds,
        verbose=argument_parsed.verbose
    )

它可以在终端使用./runmke.py -m latex_style -v


推荐阅读