【问题标题】:bash grep - negative matchbash grep - 否定匹配
【发布时间】:2016-04-13 17:30:30
【问题描述】:

我想在我的 Python 单元测试中显示我一直懒惰和停用测试的标志位置。

但我也有条件执行,它们不是懒惰的,它们是由测试时的性能或系统条件驱动的。这些是 skipUnless 的,我想完全忽略它们。

让我们使用一些 cmets 放入文件 test_so_bashregex.txt 中的一些输入。

!ignore this, because skipUnless means I have an acceptable conditional flag
@unittest.skipUnless(do_test, do_test_msg)
def test_conditional_function():
    xxx

!catch these 2, lazy test-passing
@unittest.skip("fb212.test_urls_security_usergroup Test_Detail.test_related fails with 302")
def sometest_function():
    xxx
@unittest.expectedFailure
def test_another_function():
    xxx

!bonus points... ignore things that are commented out
   # @unittest.expectedFailure

此外,我不能在管道中使用grep -v skipUnless,因为我真的想使用egrep -A 3 xxx *.py 来提供一些上下文,例如:

grep -A 3 "@unittest\." *.py

test_backend_security_meta.py:    @unittest.skip("rewrite - data can be legitimately missing")
test_backend_security_meta.py-    def test_storage(self):
test_backend_security_meta.py-        with getMultiDb() as mdb:
test_backend_security_meta.py-

我尝试过的:

正在尝试@https://www.debuggex.com/

我尝试了@unittest\.(.+)(?!(Unless\()),但没有成功,因为它与前 3 个匹配。

同上@unittest\.[a-zA-Z]+(?!(Unless\())

@unittest\.skip(?!(Unless\()) 部分工作,在 2 上跳过。

尽管存在 Unless,但所有这些都进行了部分匹配。

在 bash egrep 上,这将结束,事情看起来并没有好多少。

jluc@explore$ egrep '@unittest\..*(?!(Unless))' test_so_bashregex.txt
egrep:重复运算符操作数无效

【问题讨论】:

    标签: regex bash regex-negation


    【解决方案1】:

    你可以try this regex:

    (?<!#\s)@unittest\.(?!skipUnless)(skip|expectedFailure).*
    

    如果您不在乎是否出现“skip”或“expectedFailure”,您可以简化它:

    (?<!#\s)@unittest\.(?!skipUnless).*
    

    【讨论】:

    • 不,skip 和 expectedFailure 并不重要。这只是skip除非我在乎,为了避免它。 @unittest\.(?!skipUnless).* 在线测试效果很好。但是在 bash 上,我得到 repetition-operator 操作数无效。我要补充一点,它是 OSX 上的 bash,因为我知道 grep/egrep 与 Linux 变体相比略有不同。
    【解决方案2】:

    这样的事情怎么样 - grep 似乎有点限制

    items=$(find . -name "*.py")
    for item in $items; do
        cat $item | awk ' 
        /^\@unittest.*expectedFailure/{seen_skip=1;}
        /^\@unittest.*skip/{seen_skip=1;}
        /^def/{
            if (seen_skip == 1)
                print "Being lazy at " $1
            seen_skip=0;
        }
        '
    done
    

    【讨论】:

    • 嗯,在现实生活中,这些行并不存在于 test.txt 文件中,它们是由 grep xxx *.py 提取的.所以我不会得到文件名和行#s,除非我有一个额外的步骤将信息传递给awk。您的代码确实有效,打印出 'Being lazy at def' 3 次。
    • 已更新为遍历所有 py 文件 - 应该能够扩展该查找,但您拥有测试文件结构
    • 好的,它显然选择了 *.py,但输出仍然只是 Being at def。所以 $1 一直都是'def'。没有 @unittest 指令、文件名、行号,甚至没有实际的函数代码。感谢您的努力,这就是我为您投票的原因,但到目前为止,它看起来比我的解决方案更不稳定和更复杂。
    【解决方案3】:

    好的,我会在 sweaver2112 的帮助下把我找到的东西贴出来,但是如果有人有一个很好的单阶段 grep-ready 正则表达式,我会接受它。

    bash 的 egrep/grep 不喜欢 ?!(参考 grep: repetition-operator operand invalid)。故事到此结束。

    我所做的是将它传递给一些额外的过滤器:负 grep -v skipUnless 和另一个去除前导 cmets。这两个去掉了不需要的线条。但是,然后使用 -A 3 标志一次又一次地将它们的输出返回到另一个 grep 中寻找 @unittest。

    如果负 grep 清除了一行,则它不会显示在最后一个管道阶段,因此会从输入中删除。如果没有,我会立即恢复我的上下文。

    egrep -A 3 -n '@unittest\.' test_so_bashregex.txt  | egrep -v "^\s*#" | egrep -v "skipUnless\(" | grep @unittest -A 3
    

    输出:

    7:@unittest.skip("fb212.test_urls_security_usergroup Test_Detail.test_related fails with 302")
    8-def sometest_function():
    9-  xxx
    10:@unittest.expectedFailure
    11-def test_another_function():
    12- xxx    
    

    我在 * *.py* 上运行它的实际输出,而不是我的 test.txt 文件:

     egrep -A 3 -n '@unittest\.' *.py  | egrep -v "\d:\s*#" | egrep -v "skipUnless\(" | grep @unittest -A 3
    

    输出:

    test_backend_security_meta.py:77:    @unittest.skip("rewrite - data can be legitimately missing")
    test_backend_security_meta.py-78-    def test_storage(self):
    test_backend_security_meta.py-79-        with getMultiDb() as mdb:
    test_backend_security_meta.py-80-
    --
    test_backend_security_meta.py:98:    @unittest.skip("rewrite - data can be legitimately missing")
    test_backend_security_meta.py-99-    def test_get_li_tag_for_object(self):
    test_backend_security_meta.py-100-        li = self.mgr.get_li_tag()
    test_backend_security_meta.py-101-
    

    【讨论】:

      猜你喜欢
      • 2011-09-16
      • 1970-01-01
      • 2011-06-15
      • 2013-06-11
      • 2021-09-19
      • 1970-01-01
      • 1970-01-01
      • 2014-03-04
      相关资源
      最近更新 更多