简体   繁体   English

如何使用Ant搜索文件中的字符串(确保在源文件中找不到某些字符串)

[英]How to search for a string in files with Ant (make sure certain string isn't found in source files)

I'd like to search for a string within my source files with Ant. 我想用Ant在源文件中搜索一个字符串。 (I'd like my build to fail in case certain string is found within my source files). (如果在我的源文件中找到某些字符串,我希望我的构建失败)。

So, I should be able to recursively search for a certain string within a file set. 所以,我应该能够递归地搜索文件集中的某个字符串。

I already found that I can use loadfile task to check whether a string pattern is found within one file . 我已经发现我可以使用loadfile任务来检查是否在一个文件中找到了字符串模式 But that seems to be working & sensible only with a single file. 但这似乎只对单个文件有效且合理。

On the other hand, replace task would provide recursively search-and-replace. 另一方面, replace task将提供递归搜索和替换。 I guess I could do that before build and replace my string with something that would break the build but I wonder if there is some cleaner solution? 我想我可以在构建之前做到这一点,并用可能破坏构建的东西替换我的字符串,但我想知道是否有更清洁的解决方案?

br, Touko br,Touko

You might consider using fileset selectors to do this. 您可以考虑使用文件集选择器来执行此操作。 Selectors allow you to choose files based on content, size, editability and so on. 选择器允许您根据内容,大小,可编辑性等选择文件。 You can combine selectors with name-based includes and excludes, or patternsets. 您可以将选择器与基于名称的包含和排除或模式集组合在一起。

Below is an example. 以下是一个例子。 The second fileset is derived from the first, with a selector that simply matches on file content. 第二个文件集派生自第一个文件集,其中一个选择器只匹配文件内容。 For more sophisticated matching there is the containsregexp selector . 对于更复杂的匹配,有containsregexp选择器 The result is a fileset containing only files matching the string. 结果是一个文件集只包含与字符串匹配的文件。 A fail task with a resourcecount condition is then used to fail the build, unless that fileset is empty. 然后使用具有resourcecount条件的失败任务来使构建失败,除非该文件集为空。

<property name="src.dir" value="src" />
<property name="search.string" value="BAD" />

<fileset id="existing" dir="${src.dir}">
    <patternset id="files">
        <!-- includes/excludes for your source here -->
    </patternset>
</fileset>

<fileset id="matches" dir="${src.dir}">
    <patternset refid="files" />
    <contains text="${search.string}" />
</fileset>

<fail message="Found '${search.string}' in one or more files in '${src.dir}'">
    <condition>
        <resourcecount when="greater" count="0" refid="matches" />
    </condition>
</fail>

( Old answer ): If adjusting or reusing filesets might be problematic, here's an illustration of a relatively simple alternative. 旧答案 ):如果调整或重用文件集可能会有问题,这里有一个相对简单的替代方案的说明。

The idea is to make a copy of the files, then replace the string you wish to search for with some flag value in the copied files. 我们的想法是复制文件,然后用复制文件中的某个标志值替换您要搜索的字符串。 This will update the last modified time on any matching file. 这将更新任何匹配文件的上次修改时间。 The uptodate task can then be used to look for affected files. 然后可以使用uptodate任务查找受影响的文件。 Finally, unless no files matched, you can fail the build. 最后,除非没有匹配的文件,否则您可能fail构建。

<property name="src.dir" value="src" />
<property name="work.dir" value="work" />
<property name="search.string" value="BAD" />

<delete dir="${work.dir}" />
<mkdir dir="${work.dir}" />
<fileset dir="${src.dir}" id="src.files">
    <include name="*.txt" />
</fileset>
<copy todir="${work.dir}" preservelastmodified="true">
    <fileset refid="src.files" />
</copy>
<fileset dir="${work.dir}" id="work.files">
    <include name="*.txt" />
</fileset>
<replaceregexp match="${search.string}"
               replace="FOUND_${search.string}">
    <fileset refid="work.files" />
</replaceregexp>
<uptodate property="files.clean">
    <srcfiles refid="work.files" />
    <regexpmapper from="(.*)" to="${basedir}/${src.dir}/\1" />
</uptodate>
<fail message="Found '${search.string}' in one or more files in dir '${src.dir}'"
      unless="files.clean" />

This was very helpful as a start, but I have a list of strings which should be checked in a fileset . 这作为一个开始非常有用,但我有一个字符串列表应该在文件集中检查

My current code sofar is: 我目前的代码是:

<property name="search4" value="XYZ"/>

<fileset id="existing" dir="../src">
    <patternset id="files">
    <include name="content/**/*.txt"/>
    </patternset>
</fileset>

<resourcecount property="count">
    <fileset id="matches" dir="../src">
    <patternset refid="files" />
    <contains text="${search4}" />
    </fileset>
</resourcecount>
<echo message="Found '${search4}' in files : '${count}'"/>

That works well, but how to expand that so the ${search4} is read from a list. 这很好,但如何扩展,以便从列表中读取$ {search4}。 Actually the list can be read from a file containing each search item is on a separate line. 实际上,可以从包含每个搜索项的文件中读取列表在单独的行上。

Slightly more concise variation on the first part of @martinclayton's answer: @ martinclayton答案的第一部分稍微简洁一点:

<property name="log.dir" value="logs" />
<property name="fail.string" value=" FAILED " />

<fileset id="build.failures" dir="${log.dir}" includes="*.log">
    <contains text="${fail.string}"/>
</fileset>
<fail status="1" message="One or more failures detected">
    <condition>
        <resourcecount when="greater" count="0" refid="build.failures" />
    </condition>
</fail>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM