Skip to content

Commit

Permalink
Handle plugins
Browse files Browse the repository at this point in the history
Signed-off-by: Pierangelo Di Pilato <[email protected]>
  • Loading branch information
pierDipi committed Sep 11, 2024
1 parent 51a852c commit 3a8988c
Showing 1 changed file with 105 additions and 63 deletions.
168 changes: 105 additions & 63 deletions pkg/maven/maven_pom.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ type Pom struct {
Version string `xml:"version"`
Dependencies Dependencies `xml:"dependencies"`
DependencyManagement DependencyManagement `xml:"dependencyManagement"`
Build Build `xml:"build"`
Properties Properties `xml:"properties"`
}

Expand All @@ -31,6 +32,19 @@ type Dependencies struct {
Dependency []Dependency `xml:"dependency"`
}

type Plugins struct {
Plugin []Dependency `xml:"plugin"`
}

type PluginManagement struct {
Plugins Plugins `xml:"plugins"`
}

type Build struct {
PluginManagement PluginManagement `xml:"pluginManagement"`
Plugins Plugins `xml:"plugins"`
}

// Dependency represents a single dependency block
type Dependency struct {
GroupID string `xml:"groupId"`
Expand Down Expand Up @@ -59,11 +73,6 @@ func UpdatePomFile(metadata []Metadata, url string, path string) error {
metadataByGA[depKey(m.GroupID, m.ArtifactID)] = m
}

propVariable := regexp.MustCompile("\\$\\{(\\S+)}")
propValue := regexp.MustCompile("([0-9a-z._-]+)")

versionRegex := regexp.MustCompile("([0-9]+)\\.?([0-9]+)?\\.?([0-9]+)?")

pomFileStr := string(pomFileBytes)

if !strings.Contains(pomFileStr, url) {
Expand Down Expand Up @@ -92,82 +101,115 @@ func UpdatePomFile(metadata []Metadata, url string, path string) error {
}

for _, d := range p.DependencyManagement.Dependencies.Dependency {
groupId := d.GroupID
if d.GroupID == "io.quarkus" {
groupId = "com.redhat.quarkus.platform"
pomFileStr, err = replaceDependency(metadataByGA, p, d, pomFileStr)
if err != nil {
return err
}
m, ok := metadataByGA[depKey(groupId, d.ArtifactID)]
if !ok {
continue
}
for _, d := range p.Dependencies.Dependency {
pomFileStr, err = replaceDependency(metadataByGA, p, d, pomFileStr)
if err != nil {
return err
}
version := d.Version
propNameMatch := propVariable.FindStringSubmatch(d.Version)
if len(propNameMatch) > 1 {
version, ok = p.Properties.Entries[propNameMatch[1]]
if !ok {
return fmt.Errorf("failed to replace variable %q from properties %#v", d.Version, p.Properties.Entries)
}
if match := propValue.FindStringSubmatch(version); len(match) > 1 {
version = match[1]
}
}
for _, d := range p.Build.PluginManagement.Plugins.Plugin {
pomFileStr, err = replaceDependency(metadataByGA, p, d, pomFileStr)
if err != nil {
return err
}
}
for _, d := range p.Build.Plugins.Plugin {
pomFileStr, err = replaceDependency(metadataByGA, p, d, pomFileStr)
if err != nil {
return err
}
}

if err := os.WriteFile(path, []byte(pomFileStr), 0666); err != nil {
return fmt.Errorf("failed to update POM file %q: %w", path, err)
}
return nil
}

log.Printf("Dependency %q:%q:%q\n%#v\n", d.GroupID, d.ArtifactID, version, m)
func replaceDependency(metadataByGA map[string]Metadata, p *Pom, d Dependency, pomFileStr string) (string, error) {

versionPieces := versionRegex.FindStringSubmatch(version)
if len(versionPieces) < 2 {
log.Printf("Version %q is not parsable", version)
continue
propVariable := regexp.MustCompile("\\$\\{(\\S+)}")
propValue := regexp.MustCompile("([0-9a-z._-]+)")

versionRegex := regexp.MustCompile("([0-9]+)\\.?([0-9]+)?\\.?([0-9]+)?")

groupId := d.GroupID
if d.GroupID == "io.quarkus" {
groupId = "com.redhat.quarkus.platform"
}
m, ok := metadataByGA[depKey(groupId, d.ArtifactID)]
if !ok {
return pomFileStr, nil
}
version := d.Version
propNameMatch := propVariable.FindStringSubmatch(d.Version)
if len(propNameMatch) > 1 {
version, ok = p.Properties.Entries[propNameMatch[1]]
if !ok {
return pomFileStr, fmt.Errorf("failed to replace variable %q from properties %#v", d.Version, p.Properties.Entries)
}
if match := propValue.FindStringSubmatch(version); len(match) > 1 {
version = match[1]
}
log.Printf("Version %q, pieces %#v", version, versionPieces)
}

versions := make([]string, len(m.Versioning.Versions.Version))
copy(versions, m.Versioning.Versions.Version)
slices.Reverse(versions)
log.Printf("Dependency %q:%q:%q\n%#v\n", d.GroupID, d.ArtifactID, version, m)

for _, v := range versions {
if v == version {
break
}
versionPieces := versionRegex.FindStringSubmatch(version)
if len(versionPieces) < 2 {
log.Printf("Version %q is not parsable", version)
return pomFileStr, nil
}
log.Printf("Version %q, pieces %#v", version, versionPieces)

vPieces := versionRegex.FindStringSubmatch(v)
if len(vPieces) < 2 {
log.Printf("Version %q in metadata is not parsable (%s:%s)", version, m.GroupID, m.ArtifactID)
continue
}
log.Printf("Red Hat Version %q, pieces %#v", v, vPieces)
versions := make([]string, len(m.Versioning.Versions.Version))
copy(versions, m.Versioning.Versions.Version)
slices.Reverse(versions)

if vPieces[1] != versionPieces[1] {
// major version doesn't match
log.Printf("Version %q doesn't match major version in %q", version, v)
continue
}
for _, v := range versions {
if v == version {
break
}

if len(versionPieces) >= 3 && len(vPieces) >= 3 && vPieces[2] != versionPieces[2] {
// minor version doesn't match
log.Printf("Version %q doesn't match minor version in %q", version, v)
continue
}
vPieces := versionRegex.FindStringSubmatch(v)
if len(vPieces) < 2 {
log.Printf("Version %q in metadata is not parsable (%s:%s)", version, m.GroupID, m.ArtifactID)
continue
}
log.Printf("Red Hat Version %q, pieces %#v", v, vPieces)

if vPieces[1] != versionPieces[1] {
// major version doesn't match
log.Printf("Version %q doesn't match major version in %q", version, v)
continue
}

rg := fmt.Sprintf("(.*<groupId>\\s*)%s(\\s*</groupId>\\s*<artifactId>\\s*)%s(\\s*</artifactId>\\s*<version>\\s*)%s(\\s*</version>.*)", regexp.QuoteMeta(d.GroupID), regexp.QuoteMeta(d.ArtifactID), regexp.QuoteMeta(d.Version))
log.Printf("Replacing %q:%q:%q with %q:%q:%q (regex %q)", d.GroupID, d.ArtifactID, version, m.GroupID, m.ArtifactID, v, rg)
if len(versionPieces) >= 3 && len(vPieces) >= 3 && vPieces[2] != versionPieces[2] {
// minor version doesn't match
log.Printf("Version %q doesn't match minor version in %q", version, v)
continue
}

artifactRegex := regexp.MustCompile(rg)
for _, match := range artifactRegex.FindAllStringSubmatch(pomFileStr, -1) {
oldM := fmt.Sprintf("%s%s%s%s%s%s%s", match[1], d.GroupID, match[2], d.ArtifactID, match[3], d.Version, match[4])
newM := fmt.Sprintf("%s%s%s%s%s%s%s", match[1], m.GroupID, match[2], m.ArtifactID, match[3], v, match[4])
rg := fmt.Sprintf("(.*<groupId>\\s*)%s(\\s*</groupId>\\s*<artifactId>\\s*)%s(\\s*</artifactId>\\s*<version>\\s*)%s(\\s*</version>.*)", regexp.QuoteMeta(d.GroupID), regexp.QuoteMeta(d.ArtifactID), regexp.QuoteMeta(d.Version))
log.Printf("Replacing %q:%q:%q with %q:%q:%q (regex %q)", d.GroupID, d.ArtifactID, version, m.GroupID, m.ArtifactID, v, rg)

log.Printf("match:\n%s\n%s\n", oldM, newM)
artifactRegex := regexp.MustCompile(rg)
for _, match := range artifactRegex.FindAllStringSubmatch(pomFileStr, -1) {
oldM := fmt.Sprintf("%s%s%s%s%s%s%s", match[1], d.GroupID, match[2], d.ArtifactID, match[3], d.Version, match[4])
newM := fmt.Sprintf("%s%s%s%s%s%s%s", match[1], m.GroupID, match[2], m.ArtifactID, match[3], v, match[4])

pomFileStr = strings.ReplaceAll(pomFileStr, oldM, newM)
}
log.Printf("match:\n%s\n%s\n", oldM, newM)

pomFileStr = strings.ReplaceAll(pomFileStr, oldM, newM)
}
}

if err := os.WriteFile(path, []byte(pomFileStr), 0666); err != nil {
return fmt.Errorf("failed to update POM file %q: %w", path, err)
}
return nil
return pomFileStr, nil
}

func depKey(groupId, artifactId string) string {
Expand Down

0 comments on commit 3a8988c

Please sign in to comment.