regex 如何在Jenkins / Groovy中使用多行正则表达式匹配

bihw5rsg  于 2023-08-08  发布在  Jenkins
关注(0)|答案(2)|浏览(146)

在Jenkins中,我正在构建一个读取CHANGELOG.md并使用正则表达式从给定版本中提取最新变更日志的步骤。
使用的.groovy代码:

#!/usr/bin/env groovy

import java.nio.file.Files
import java.nio.file.Paths
import java.util.regex.Pattern

def String currentTag = '0.1.0';
def String changelogFileName = 'CHANGELOG.md';

def changelogText = new String(Files.readAllBytes(Paths.get(changelogFileName)))
def pattern = Pattern.compile("(?s)^## ${currentTag}.*?(?=\n\n## |\\z)", Pattern.MULTILINE)
def matcher = pattern.matcher(changelogText)

if (matcher.find()) {
    def latestChangelog = matcher.group()
    println latestChangelog.strip()
}

字符串
使用的输入文件:

# Changelog - Project
All notable changes to this project will be documented in this file.
This project adheres to [Semantic Versioning](http://semver.org/).
Changelog based on guidelines from
[Keep a CHANGELOG](http://keepachangelog.com/).

## 0.3.0 - 2022-06-30
### Changed:
- MDN-XXXX: blabla
### Also Changed:
- MDN-XXXX: blabla

## 0.2.0 - 2022-06-09
### Added:
- MDN-XXXX: blabla

## 0.1.1 - 2022-06-08
### Fixed:
- MDN-XXXX: blabla

## 0.1.0 - 2022-06-08
### Added:
 - MDN-XXXX: blabla
 - MDN-XXXX: blabla


在本地,这段代码工作得很好。然而,我想在Jenkins中使用它,直接导入这些会有安全问题:

import java.nio.file.Files
import java.nio.file.Paths
import java.util.regex.Pattern


因此,我需要将其更改为Jenkins友好代码。
所以我把它改成了这个:

def changelogText = readFile(file: changelogFileName)

    def pattern = "(?s)^## ${currentTag}.*?(?=\n\n## |\\z)"
    def matcher = (changelogText =~ pattern)

    if (matcher.find()) {
        def latestChangelog = matcher.group();
        println(latestChangelog.strip());
    } else {
        println('Could not parse latest changelog.');
    }


但是,我总是得到“无法解析最新的更新日志”。
当我必须一直在Jenkins上运行它时,调试起来相当困难。有谁知道如何在本地提供Jenkins库,或者更好的是,如何使用Pattern.MULTILINE进行匹配?
或者是一个完全不同的方法的建议?

f4t66c6m

f4t66c6m1#

要匹配包括换行符在内的所有符号,可以使用[\s\S]。这将在没有任何标志的情况下工作。
考虑以下演示:

String changelogText = """
# Changelog - Project
All notable changes to this project will be documented in this file.
This project adheres to [Semantic Versioning](http://semver.org/).
Changelog based on guidelines from
[Keep a CHANGELOG](http://keepachangelog.com/).

## 0.3.0 - 2022-06-30
### Changed:
- MDN-XXXX: blabla
### Also Changed:
- MDN-XXXX: blabla

## 0.2.0 - 2022-06-09
### Added:
- MDN-XXXX: blabla

## 0.1.1 - 2022-06-08
### Fixed:
- MDN-XXXX: blabla

## 0.1.0 - 2022-06-08
### Added:
 - MDN-XXXX: blabla
 - MDN-XXXX: blabla
"""

def currentTag = "0.2.0 - 2022-06-09"
def pattern = /## ${currentTag}[\s\S]*?(?=\n\n## |\z)/
def matcher = (changelogText =~ pattern)

if (matcher.find()) {
    def latestChangelog = matcher[0];
    println(latestChangelog);
} else {
    println('Could not parse latest changelog.');
}

字符串
输出量:

## 0.2.0 - 2022-06-09
### Added:
- MDN-XXXX: blabla

3ks5zfa0

3ks5zfa02#

如果有人想使用awk,这是一个awk解决方案,但是,我仍然喜欢上面的一个,因为它更好的情况下,如果最后一个条目0.1.0有一些空行在它。

#!/usr/bin/env groovy

/**
 * Get latest changelog data from given filename and tag
 * @param currentTag string
 * @param changelogFileName string
 */
def call(
    String currentTag = '0.1.0',
    String changelogFileName = 'CHANGELOG.md'
) {
    def changelogText  = sh(returnStdout: true, script: "awk '{ RS=\"\" } /## ${currentTag}.*?(^## |\$)/' ${changelogFileName}").strip();
    if (changelogText) {
        return changelogText;
    } else {
        return "Could not parse the changelog of tag ${currentTag} in ${changelogFileName}. Is changelog pushed? Or perhaps the changelog contains a syntax error?";
    }
}

字符串

相关问题