用 Python 创建你自己的 Shell

介绍很多人讨厌bash脚本。每当我要做最简单的事情时,我都必须查阅文档。如何将函数的参数转发给子命令?如何将字符串分配给变量,然后作为命令调用该字符串?如何检查两个字符串变量是否相等?如何...
摘要由CSDN通过智能技术生成

介绍

很多人讨厌bash脚本。每当我要做最简单的事情时,我都必须查阅文档。如何将函数的参数转发给子命令?如何将字符串分配给变量,然后作为命令调用该字符串?如何检查两个字符串变量是否相等?如何分割字符串并获得后半部分?等等。不是我找不到这些答案,而是每次都必须查找它们。

但是,我们不能否认将整个程序当作纯粹的功能发挥作用的能力,以及将一个程序的输出传递到另一个程序的自然程度。因此,我想知道,我们能否将bash的某些功能与Python结合起来?

基础知识

让我们从一个类开始。这是一个简单的方法,将其初始化参数保存到局部变量,然后使用subprocess.run对其自身进行延迟求值并保存结果。

import subprocess

class PipePy:
    def __init__(self, *args):
        self._args = args
        self._result = None

    def _evaluate(self):
        if self._result is not None:
            return
        self._result = subprocess.run(self._args,
                                      capture_output=True,
                                      text=True)

    @property
    def returncode(self):
        self._evaluate()
        return self._result.returncode

    @property
    def stdout(self):
        self._evaluate()
        return self._result.stdout

    def __str__(self):
        return self.stdout

    @property
    def stderr(self):
        self._evaluate()
        return self._result.stderr

我们让它旋转一下:

ls = PipePy('ls')
ls_l = PipePy('ls', '-l')

print(ls)
# <<< files.txt
# ... main.py
# ... tags
print(ls_l)
# <<< total 16
# ... -rw-r--r-- 1 kbairak kbairak  125 Jan 22 08:53 files.txt
# ... -rw-r--r-- 1 kbairak kbairak 5425 Feb  1 21:54 main.py
# ... -rw-r--r-- 1 kbairak kbairak 1838 Feb  1 21:54 tags

使其看起来更像“命令式”

不用每次我们要自定义命令时都去调用PipePy。

ls_l = PipePy('ls', '-l')
print(ls_l)

相当于

ls = PipePy('ls')
print(ls('-l'))

换句话说,我们要使:

PipePy('ls', '-l')

相当于

PipePy('ls')('-l')

值得庆幸的是,我们的类创建了惰性对象这一事实在很大程度上帮助了我们:

class PipePy:
    # __init__, etc

    def __call__(self, *args):
        args = self._args + args
        return self.__class__(*args)

ls = PipePy('ls')
print(ls('-l'))
# <<< total 16
# ... -rw-r--r-- 1 kbairak kbairak  125 Jan 22 08:53 files.txt
# ... -rw-r--r-- 1 kbairak kbairak 5425 Feb  1 21:54 main.py
# ... -rw-r--r-- 1 kbairak kbairak 1838 Feb  1 21:54 tags

关键字参数

如果要向ls传递更多参数,则可能会遇到--sort = size。我们可以轻松地执行ls('-l','--sort = size')。我们可以做得更好吗?

 class PipePy:
-    def __init__(self, *args):
+    def __init__(self, *args, **kwargs):
         self._args = args
+        self._kwargs = kwargs
         self._result = None

     def _evaluate(self):
         if self._result is not None:
             return
-        self._result = subprocess.run(self._args,
+        self._result = subprocess.run(self._convert_args(),
                                       
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值