Skip to content

Commit

Permalink
feat: add PEMEncodedCertificate wrapper
Browse files Browse the repository at this point in the history
Now we have cert & key, key and cert only wrappers.

For siderolabs/talos#8440

Signed-off-by: Andrey Smirnov <andrey.smirnov@siderolabs.com>
  • Loading branch information
smira committed Mar 14, 2024
1 parent 1c94bb3 commit 2f4f911
Show file tree
Hide file tree
Showing 8 changed files with 163 additions and 50 deletions.
77 changes: 44 additions & 33 deletions .conform.yaml
Original file line number Diff line number Diff line change
@@ -1,37 +1,48 @@
# THIS FILE WAS AUTOMATICALLY GENERATED, PLEASE DO NOT EDIT.
#
# Generated on 2022-06-22T12:59:39Z by kres 65530e7.
# Generated on 2024-03-14T16:15:48Z by kres latest.

---
policies:
- type: commit
spec:
dco: true
gpg:
required: true
identity:
gitHubOrganization: siderolabs
spellcheck:
locale: US
maximumOfOneCommit: true
header:
length: 89
imperative: true
case: lower
invalidLastCharacters: .
body:
required: true
conventional:
types: ["chore","docs","perf","refactor","style","test","release"]
scopes: [".*"]
- type: license
spec:
skipPaths:
- .git/
- testdata/
includeSuffixes:
- .go
excludeSuffixes:
- .pb.go
- .pb.gw.go
header: "// This Source Code Form is subject to the terms of the Mozilla Public\u000A// License, v. 2.0. If a copy of the MPL was not distributed with this\u000A// file, You can obtain one at http://mozilla.org/MPL/2.0/.\u000A"
- type: commit
spec:
dco: true
gpg:
required: true
identity:
gitHubOrganization: siderolabs
spellcheck:
locale: US
maximumOfOneCommit: true
header:
length: 89
imperative: true
case: lower
invalidLastCharacters: .
body:
required: true
conventional:
types:
- chore
- docs
- perf
- refactor
- style
- test
- release
scopes:
- .*
- type: license
spec:
root: .
skipPaths:
- .git/
- testdata/
includeSuffixes:
- .go
excludeSuffixes:
- .pb.go
- .pb.gw.go
header: |
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
6 changes: 3 additions & 3 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# THIS FILE WAS AUTOMATICALLY GENERATED, PLEASE DO NOT EDIT.
#
# Generated on 2024-02-16T10:24:06Z by kres latest.
# Generated on 2024-03-14T16:15:48Z by kres latest.

name: default
concurrency:
Expand Down Expand Up @@ -48,8 +48,8 @@ jobs:
uses: docker/setup-buildx-action@v3
with:
driver: remote
endpoint: tcp://localhost:1234
timeout-minutes: 1
endpoint: tcp://127.0.0.1:1234
timeout-minutes: 10
- name: base
run: |
make base
Expand Down
6 changes: 3 additions & 3 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -1,16 +1,16 @@
# syntax = docker/dockerfile-upstream:1.6.0-labs
# syntax = docker/dockerfile-upstream:1.7.0-labs

# THIS FILE WAS AUTOMATICALLY GENERATED, PLEASE DO NOT EDIT.
#
# Generated on 2024-02-16T10:24:06Z by kres latest.
# Generated on 2024-03-14T16:15:48Z by kres latest.

ARG TOOLCHAIN

# cleaned up specs and compiled versions
FROM scratch AS generate

# runs markdownlint
FROM docker.io/node:21.6.1-alpine3.19 AS lint-markdown
FROM docker.io/node:21.7.1-alpine3.19 AS lint-markdown
WORKDIR /src
RUN npm i -g markdownlint-cli@0.39.0
RUN npm i sentences-per-line@0.2.1
Expand Down
14 changes: 7 additions & 7 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
# THIS FILE WAS AUTOMATICALLY GENERATED, PLEASE DO NOT EDIT.
#
# Generated on 2024-02-16T10:24:06Z by kres latest.
# Generated on 2024-03-14T16:15:48Z by kres latest.

# common variables

SHA := $(shell git describe --match=none --always --abbrev=8 --dirty)
TAG := $(shell git describe --tag --always --dirty)
TAG := $(shell git describe --tag --always --dirty --match v[0-9]\*)
ABBREV_TAG := $(shell git describe --tags >/dev/null 2>/dev/null && git describe --tag --always --match v[0-9]\* --abbrev=0 || echo 'undefined')
BRANCH := $(shell git rev-parse --abbrev-ref HEAD)
ARTIFACTS := _out
Expand All @@ -14,15 +14,15 @@ WITH_RACE ?= false
REGISTRY ?= ghcr.io
USERNAME ?= siderolabs
REGISTRY_AND_USERNAME ?= $(REGISTRY)/$(USERNAME)
PROTOBUF_GO_VERSION ?= 1.32.0
PROTOBUF_GO_VERSION ?= 1.33.0
GRPC_GO_VERSION ?= 1.3.0
GRPC_GATEWAY_VERSION ?= 2.19.1
VTPROTOBUF_VERSION ?= 0.6.0
DEEPCOPY_VERSION ?= v0.5.5
GOLANGCILINT_VERSION ?= v1.56.1
DEEPCOPY_VERSION ?= v0.5.6
GOLANGCILINT_VERSION ?= v1.56.2
GOFUMPT_VERSION ?= v0.6.0
GO_VERSION ?= 1.22.0
GOIMPORTS_VERSION ?= v0.17.0
GO_VERSION ?= 1.22.1
GOIMPORTS_VERSION ?= v0.19.0
GO_BUILDFLAGS ?=
GO_LDFLAGS ?=
CGO_ENABLED ?= 0
Expand Down
4 changes: 2 additions & 2 deletions go.mod
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
module github.com/siderolabs/crypto

go 1.22.0
go 1.22.1

require (
github.com/stretchr/testify v1.8.4
github.com/stretchr/testify v1.9.0
gopkg.in/yaml.v3 v3.0.1
)

Expand Down
4 changes: 2 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/stretchr/testify v1.8.4 h1:CcVxjf3Q8PM0mHUKJCdn+eZZtm5yQwehR5yeSVQQcUk=
github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo=
github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg=
github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
Expand Down
77 changes: 77 additions & 0 deletions x509/x509.go
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,11 @@ type PEMEncodedKey struct {
Key []byte `json:"Key"`
}

// PEMEncodedCertificate represents a PEM encoded certificate.
type PEMEncodedCertificate struct {
Crt []byte `json:"Crt"`
}

// Options is the functional options struct.
//
//nolint:govet
Expand Down Expand Up @@ -1135,6 +1140,78 @@ func (p *PEMEncodedKey) DeepCopyInto(out *PEMEncodedKey) {
}
}

// UnmarshalYAML implements the yaml.Unmarshaler interface for
// PEMEncodedCertificateAndKey. It is expected that the Crt is a base64
// encoded string in the YAML file. This function decodes the strings into byte
// slices.
func (p *PEMEncodedCertificate) UnmarshalYAML(unmarshal func(interface{}) error) error {
var aux struct {
Crt string `yaml:"crt"`
}

if err := unmarshal(&aux); err != nil {
return err
}

decodedCrt, err := base64.StdEncoding.DecodeString(aux.Crt)
if err != nil {
return err
}

p.Crt = decodedCrt

return nil
}

// MarshalYAML implements the yaml.Marshaler interface for
// PEMEncodedCertificate. It is expected that the Crt is a base64
// encoded string in the YAML file. This function encodes the byte slices into
// strings.
func (p *PEMEncodedCertificate) MarshalYAML() (interface{}, error) {
var aux struct {
Crt string `yaml:"crt"`
}

aux.Crt = base64.StdEncoding.EncodeToString(p.Crt)

return aux, nil
}

// GetCert parses PEM-encoded certificate as x509.Certificate.
func (p *PEMEncodedCertificate) GetCert() (*x509.Certificate, error) {
block, _ := pem.Decode(p.Crt)
if block == nil {
return nil, fmt.Errorf("failed to parse PEM block")
}

cert, err := x509.ParseCertificate(block.Bytes)
if err != nil {
return nil, fmt.Errorf("failed to parse certificate: %w", err)
}

return cert, nil
}

// DeepCopy implements DeepCopy interface.
func (p *PEMEncodedCertificate) DeepCopy() *PEMEncodedCertificate {
if p == nil {
return nil
}

out := new(PEMEncodedCertificate)
p.DeepCopyInto(out)

return out
}

// DeepCopyInto implements DeepCopy interface.
func (p *PEMEncodedCertificate) DeepCopyInto(out *PEMEncodedCertificate) {
if p.Crt != nil {
out.Crt = make([]byte, len(p.Crt))
copy(out.Crt, p.Crt)
}
}

// NewCertficateAndKey is the NewCertificateAndKey with a typo in the name.
//
// Deprecated: use NewCertificateAndKey instead.
Expand Down
25 changes: 25 additions & 0 deletions x509/x509_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -390,3 +390,28 @@ func TestPEMEncodedCertificateAndKeyYAMLMarshaling(t *testing.T) {

assert.Equal(t, []byte(x509.Redacted), unmarshalPair.Key)
}

func TestPEMEncodedCertificate(t *testing.T) {
t.Parallel()

ca, err := x509.NewSelfSignedCertificateAuthority(x509.ECDSA(true))
require.NoError(t, err)

pemEncoded := &x509.PEMEncodedCertificate{
Crt: ca.CrtPEM,
}

marshaled, err := yaml.Marshal(pemEncoded)
require.NoError(t, err)

var decoded x509.PEMEncodedCertificate

require.NoError(t, yaml.Unmarshal(marshaled, &decoded))

assert.Equal(t, ca.CrtPEM, decoded.Crt)

decodedCert, err := decoded.GetCert()
require.NoError(t, err)

assert.True(t, decodedCert.Equal(ca.Crt))
}

0 comments on commit 2f4f911

Please sign in to comment.