Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions pkg/document/values.go
Original file line number Diff line number Diff line change
Expand Up @@ -234,7 +234,7 @@ func createValueRowsFromList(

// We have a nonempty list with a description, document it, and mark that leaf nodes underneath it should not be
// documented without descriptions
if hasDescription || (autoDescription.Description != "" && autoDescription.NotationType == "") {
if (hasDescription || autoDescription.Description != "") && autoDescription.NotationType == "" {
jsonableObject := convertHelmValuesToJsonable(values)
listRow, err := createValueRow(prefix, jsonableObject, description, autoDescription, key.Column, key.Line)

Expand All @@ -244,7 +244,7 @@ func createValueRowsFromList(

valueRows = append(valueRows, listRow)
documentLeafNodes = false
} else if hasDescription || (autoDescription.Description != "" && autoDescription.NotationType != "") {
} else if hasDescription || autoDescription.Description != "" {
// If it has NotationType described, then use that
var notationValue interface{}
var err error
Expand Down Expand Up @@ -323,7 +323,7 @@ func createValueRowsFromObject(

// We have a nonempty object with a description, document it, and mark that leaf nodes underneath it should not be
// documented without descriptions
if hasDescription || (autoDescription.Description != "" && autoDescription.NotationType == "") {
if (hasDescription || autoDescription.Description != "") && autoDescription.NotationType == "" {
jsonableObject := convertHelmValuesToJsonable(values)
objectRow, err := createValueRow(nextPrefix, jsonableObject, description, autoDescription, key.Column, key.Line)

Expand All @@ -333,7 +333,7 @@ func createValueRowsFromObject(

valueRows = append(valueRows, objectRow)
documentLeafNodes = false
} else if hasDescription || (autoDescription.Description != "" && autoDescription.NotationType != "") {
} else if hasDescription || autoDescription.Description != "" {

// If it has NotationType described, then use that
var notationValue interface{}
Expand Down
25 changes: 25 additions & 0 deletions pkg/document/values_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1531,6 +1531,31 @@ animals:
assert.Equal(t, yamlType, valuesRows[4].NotationType)
}

func TestExtractValueNotationTypeWithDescription(t *testing.T) {
helmValues := parseYamlValues(`
# -- The deployment label
# @notationType -- yaml
labels:
client-name: my-boss
# -- Access modes
# @notationType -- yaml
accessModes:
- ReadWriteOnce
`)

descriptions := map[string]helm.ChartValueDescription{
"labels": {Description: "External description"},
"accessModes": {Description: "External description"},
}

valuesRows, err := getSortedValuesTableRows(helmValues, descriptions)

assert.Nil(t, err)
assert.Len(t, valuesRows, 2)
assert.Equal(t, "- ReadWriteOnce\n", valuesRows[0].Default)
assert.Equal(t, "client-name: my-boss\n", valuesRows[1].Default)
}

func TestExtractCustomDeclaredType(t *testing.T) {
helmValues := parseYamlValues(`
animals:
Expand Down
65 changes: 60 additions & 5 deletions pkg/helm/chart_info.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@ import (
"os"
"path/filepath"
"regexp"
"slices"
"sort"
"strconv"
"strings"

log "github.com/sirupsen/logrus"
Expand Down Expand Up @@ -251,15 +253,23 @@ func parseChartValuesFileComments(chartDirectory string, values *yaml.Node, lint
foundValuesComment := false
commentLines := make([]string, 0)
currentLineIdx := -1
currentValueKeySegments := make([]string, 0)

for scanner.Scan() {
currentLineIdx++
currentLine := scanner.Text()

// If we've not yet found a values comment with a key name, try and find one on each line
if currentLine == "" {
continue
}

// For value comments without keys we need to track previous keys to exactly know where we are at.
currentValueKeySegments = updateCurrentValueKeySegments(currentLine, currentValueKeySegments)

// If we've not yet found a values comment, try and find one on each line
if !foundValuesComment {
match := valuesDescriptionRegex.FindStringSubmatch(currentLine)
if len(match) < 3 || match[1] == "" {
if len(match) < 3 {
continue
}
foundValuesComment = true
Expand All @@ -285,10 +295,12 @@ func parseChartValuesFileComments(chartDirectory string, values *yaml.Node, lint

// If we haven't continued by this point, we didn't match any of the comment formats we want, so we need to add
// the in progress value to the map, and reset to looking for a new key
key, description := ParseComment(commentLines)
if key != "" {
keyToDescriptions[key] = description
key := strings.Join(currentValueKeySegments, ".")
if strings.HasPrefix(strings.Trim(commentLines[0], " "), "# -- ") {
commentLines[0] = strings.Replace(commentLines[0], "# -- ", "# "+key+" -- ", 1)
}
key, description := ParseComment(commentLines)
keyToDescriptions[key] = description

commentLines = make([]string, 0)
foundValuesComment = false
Expand All @@ -302,6 +314,49 @@ func parseChartValuesFileComments(chartDirectory string, values *yaml.Node, lint
return keyToDescriptions, nil
}

func updateCurrentValueKeySegments(currentLine string, currentValueKeySegments []string) []string {
valueKeyRegex := regexp.MustCompile("^(\\s*)(-?)\\s*([^:]+):?\\s*.*$")
valueKeyMatch := valueKeyRegex.FindStringSubmatch(currentLine)

if len(valueKeyMatch) == 4 {
// line is value key or group.
indentation := len(valueKeyMatch[1])
valueKey := valueKeyMatch[3]
if strings.HasPrefix(valueKey, "#") {
return currentValueKeySegments
}
isArrayElement := valueKeyMatch[2] != ""

// if current indentation is less than elements in list, we need to remove some elements.
if !isArrayElement && indentation/2 < len(currentValueKeySegments) {
currentValueKeySegments = slices.Delete(currentValueKeySegments, indentation/2, len(currentValueKeySegments))
}

// For yaml arrays we need the current index in the key
if isArrayElement {
previousValueKeySegment := currentValueKeySegments[len(currentValueKeySegments)-1]
currentValueKeySegments = slices.Delete(currentValueKeySegments, len(currentValueKeySegments)-1, len(currentValueKeySegments))
keyRegex := regexp.MustCompile("^(\\w+)\\[?(\\d+)?\\]?$")
keyMatches := keyRegex.FindStringSubmatch(previousValueKeySegment)
index := 0
if keyMatches[2] != "" {
valueInt, _ := strconv.Atoi(keyMatches[2])
index = valueInt + 1
}
valueKey = keyMatches[1] + "[" + strconv.Itoa(index) + "]"
}

// We need to quote the key if value key contains special characters
if strings.ContainsAny(valueKey, "-./") {
valueKey = "\"" + valueKey + "\""
}

currentValueKeySegments = append(currentValueKeySegments, valueKey)
}

return currentValueKeySegments
}

func ParseChartInformation(chartDirectory string, documentationParsingConfig ChartValuesDocumentationParsingConfig) (ChartDocumentationInfo, error) {
var chartDocInfo ChartDocumentationInfo
var err error
Expand Down
15 changes: 12 additions & 3 deletions pkg/helm/chart_info_test.go
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
package helm_test

import (
"github.com/norwoodj/helm-docs/pkg/helm"
"github.com/spf13/viper"
"github.com/stretchr/testify/suite"
"path/filepath"
"regexp"
"testing"

"github.com/norwoodj/helm-docs/pkg/helm"
"github.com/spf13/viper"
"github.com/stretchr/testify/suite"
)

type ChartParsingTestSuite struct {
Expand Down Expand Up @@ -94,3 +95,11 @@ func (suite *ChartParsingTestSuite) TestFullyDocumentedChartStrictModeOn() {
})
suite.NoError(err)
}

func (suite *ChartParsingTestSuite) TestFullyDocumentedChartNewStyleStrictModeOn() {
chartPath := filepath.Join("test-fixtures", "fully-documented-new-style")
_, err := helm.ParseChartInformation(chartPath, helm.ChartValuesDocumentationParsingConfig{
StrictMode: true,
})
suite.NoError(err)
}
28 changes: 28 additions & 0 deletions pkg/helm/comment_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package helm_test

import (
"testing"

"github.com/norwoodj/helm-docs/pkg/helm"
"github.com/stretchr/testify/assert"
)

func TestParseComment(t *testing.T) {
commentLines := []string{
"# controller.image.repository -- The repository of the controller image",
}
valueKey, c := helm.ParseComment(commentLines)

assert.Equal(t, "controller.image.repository", valueKey)
assert.Equal(t, "The repository of the controller image", c.Description)
}

func TestParseCommentNewStyle(t *testing.T) {
commentLines := []string{
"# -- The repository of the controller image",
}
valueKey, c := helm.ParseComment(commentLines)

assert.Equal(t, "", valueKey)
assert.Equal(t, "The repository of the controller image", c.Description)
}
6 changes: 2 additions & 4 deletions pkg/helm/test-fixtures/full-template/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -68,15 +68,15 @@ https://github.com/norwoodj/helm-docs/tree/master/example-charts/full-template

## `chart.maintainersTable`

| Name | Email | Url |
| Name | Email | URL |
| ---- | ------ | --- |
| John Norwood | <norwood.john.m@gmail.com> | |

## `chart.maintainersSection`

## Maintainers

| Name | Email | Url |
| Name | Email | URL |
| ---- | ------ | --- |
| John Norwood | <norwood.john.m@gmail.com> | |

Expand Down Expand Up @@ -162,5 +162,3 @@ Kubernetes: `<=1.18`
| controller.service.annotations."external-dns.alpha.kubernetes.io/hostname" | string | `"stupidchess.jmn23.com"` | Hostname to be assigned to the ELB for the service |
| controller.service.type | string | `"LoadBalancer"` | |

----------------------------------------------
Autogenerated from chart metadata using [helm-docs v1.11.0](https://github.com/norwoodj/helm-docs/releases/v1.11.0)
15 changes: 15 additions & 0 deletions pkg/helm/test-fixtures/fully-documented-new-style/Chart.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
apiVersion: v2
name: nginx-ingress
description: A simple wrapper around the stable/nginx-ingress chart that adds a few of our conventions
version: "0.2.0"
home: "https://github.com/norwoodj/helm-docs/tree/master/example-charts/nginx-ingress"
sources: ["https://github.com/norwoodj/helm-docs/tree/master/example-charts/nginx-ingress"]
engine: gotpl
type: application
maintainers:
- email: norwood.john.m@gmail.com
name: John Norwood
dependencies:
- name: nginx-ingress
version: "0.22.1"
repository: "@stable"
39 changes: 39 additions & 0 deletions pkg/helm/test-fixtures/fully-documented-new-style/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
# nginx-ingress

![Version: 0.2.0](https://img.shields.io/badge/Version-0.2.0-informational?style=flat-square) ![Type: application](https://img.shields.io/badge/Type-application-informational?style=flat-square)

A simple wrapper around the stable/nginx-ingress chart that adds a few of our conventions

**Homepage:** <https://github.com/norwoodj/helm-docs/tree/master/example-charts/nginx-ingress>

## Maintainers

| Name | Email | URL |
| ---- | ------ | --- |
| John Norwood | <norwood.john.m@gmail.com> | |

## Source Code

* <https://github.com/norwoodj/helm-docs/tree/master/example-charts/nginx-ingress>

## Requirements

| Repository | Name | Version |
|------------|------|---------|
| @stable | nginx-ingress | 0.22.1 |

## Values

| Key | Type | Default | Description |
|-----|------|---------|-------------|
| controller | object | `{"image":{"repository":"nginx-ingress-controller","tag":"18.0831"},"name":"controller"}` | The controller |
| controller.image | object | `{"repository":"nginx-ingress-controller","tag":"18.0831"}` | The image of the controller |
| controller.image.repository | string | `"nginx-ingress-controller"` | The repository of the controller |
| controller.image.tag | string | `"18.0831"` | The tag of the image of the controller |
| controller.name | string | `"controller"` | The name of the controller |
| image | object | `{"pullPolicy":"IfNotPresent","registry":"docker.io","repository":"lucernae/django-sample","tag":"3.1"}` | Image map |
| image.pullPolicy | string | `"IfNotPresent"` | Image pullPolicy |
| image.registry | string | `"docker.io"` | Image registry |
| image.repository | string | `"lucernae/django-sample"` | Image repository |
| image.tag | string | `"3.1"` | Image tag |

21 changes: 21 additions & 0 deletions pkg/helm/test-fixtures/fully-documented-new-style/values.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# -- The controller
controller:
# -- The name of the controller
name: controller
# -- The image of the controller
image:
# -- The repository of the controller
repository: nginx-ingress-controller
# -- The tag of the image of the controller
tag: "18.0831"

# -- Image map
image:
# -- Image registry
registry: docker.io
# -- Image repository
repository: lucernae/django-sample
# -- Image tag
tag: "3.1"
# -- Image pullPolicy
pullPolicy: IfNotPresent
7 changes: 6 additions & 1 deletion pkg/helm/test-fixtures/fully-documented/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ A simple wrapper around the stable/nginx-ingress chart that adds a few of our co

## Maintainers

| Name | Email | Url |
| Name | Email | URL |
| ---- | ------ | --- |
| John Norwood | <norwood.john.m@gmail.com> | |

Expand All @@ -31,4 +31,9 @@ A simple wrapper around the stable/nginx-ingress chart that adds a few of our co
| controller.image.repository | string | `"nginx-ingress-controller"` | The repository of the controller |
| controller.image.tag | string | `"18.0831"` | The tag of the image of the controller |
| controller.name | string | `"controller"` | The name of the controller |
| image | object | `{"pullPolicy":"IfNotPresent","registry":"docker.io","repository":"lucernae/django-sample","tag":"3.1"}` | Image map |
| image.pullPolicy | string | `"IfNotPresent"` | Image pullPolicy |
| image.registry | string | `"docker.io"` | Image registry |
| image.repository | string | `"lucernae/django-sample"` | Image repository |
| image.tag | string | `"3.1"` | Image tag |

11 changes: 11 additions & 0 deletions pkg/helm/test-fixtures/fully-documented/values.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,14 @@ controller:
repository: nginx-ingress-controller
# controller.image.tag -- The tag of the image of the controller
tag: "18.0831"

# image -- Image map
image:
# image.registry -- Image registry
registry: docker.io
# image.repository -- Image repository
repository: lucernae/django-sample
# image.tag -- Image tag
tag: "3.1"
# image.pullPolicy -- Image pullPolicy
pullPolicy: IfNotPresent