Files
zot/pkg/common/common.go
T
Vishwas R be5ad66797 refactor(http): refactor http client to accept more customisable options (#2414)
refactor(http): refactor http client to take options struct

This commit updates the arguments for the `CreateHTTPClient`
function to consume a struct which can be extended as required.
It replaces the certPath argument with a struct of 3 paths for
client ertificate, client key, and ca cert. It also adds
a TLSEnabled option for when an HTTP Client is required
without any further TLS config.

Existing consumers of this function have been updated so that
they can work as they do today. This change is a no-op for
existing features.

This allows for certificate paths to be customised and
allows other modules to re-use the same HTTP client and get
the benefits of mTLS support and per-host certificates.

Signed-off-by: Vishwas Rajashekar <vrajashe@cisco.com>
2024-05-06 13:43:41 -07:00

148 lines
2.9 KiB
Go

package common
import (
"context"
"encoding/json"
"errors"
"fmt"
"io/fs"
"os"
"regexp"
"strings"
"syscall"
"time"
"unicode/utf8"
)
const (
httpTimeout = 5 * time.Minute
certsPath = "/etc/containers/certs.d"
homeCertsDir = ".config/containers/certs.d"
ClientCertFilename = "client.cert"
ClientKeyFilename = "client.key"
CaCertFilename = "ca.crt"
CosignSignature = "cosign"
CosignSigKey = "dev.cosignproject.cosign/signature"
NotationSignature = "notation"
// same value as github.com/notaryproject/notation-go/registry.ArtifactTypeNotation (assert by internal test).
// reason used: to reduce zot minimal binary size (otherwise adds oras.land/oras-go/v2 deps).
ArtifactTypeNotation = "application/vnd.cncf.notary.signature"
ArtifactTypeCosign = "application/vnd.dev.cosign.artifact.sig.v1+json"
)
var cosignTagRule = regexp.MustCompile(`sha256\-.+\.sig`)
func IsCosignTag(tag string) bool {
return cosignTagRule.MatchString(tag)
}
func Contains[T comparable](elems []T, v T) bool {
for _, s := range elems {
if v == s {
return true
}
}
return false
}
// first match of item in [].
func Index(slice []string, item string) int {
for k, v := range slice {
if item == v {
return k
}
}
return -1
}
// remove matches of item in [].
func RemoveFrom(inputSlice []string, item string) []string {
var newSlice []string
for _, v := range inputSlice {
if item != v {
newSlice = append(newSlice, v)
}
}
return newSlice
}
func TypeOf(v interface{}) string {
return fmt.Sprintf("%T", v)
}
func DirExists(d string) bool {
if !utf8.ValidString(d) {
return false
}
fileInfo, err := os.Stat(d)
if err != nil {
if e, ok := err.(*fs.PathError); ok && errors.Is(e.Err, syscall.ENAMETOOLONG) || //nolint: errorlint
errors.Is(e.Err, syscall.EINVAL) {
return false
}
}
if err != nil && os.IsNotExist(err) {
return false
}
if !fileInfo.IsDir() {
return false
}
return true
}
// Used to filter a json fields by using an intermediate struct.
func MarshalThroughStruct(obj interface{}, throughStruct interface{}) ([]byte, error) {
toJSON, err := json.Marshal(obj)
if err != nil {
return []byte{}, err
}
err = json.Unmarshal(toJSON, throughStruct)
if err != nil {
return []byte{}, err
}
toJSON, err = json.Marshal(throughStruct)
if err != nil {
return []byte{}, err
}
return toJSON, nil
}
func ContainsStringIgnoreCase(strSlice []string, str string) bool {
for _, val := range strSlice {
if strings.EqualFold(val, str) {
return true
}
}
return false
}
// this function will check if tag is a referrers tag
// (https://github.com/opencontainers/distribution-spec/blob/main/spec.md#referrers-tag-schema).
func IsReferrersTag(tag string) bool {
referrersTagRule := regexp.MustCompile(`sha256\-[A-Za-z0-9]*$`)
return referrersTagRule.MatchString(tag)
}
func IsContextDone(ctx context.Context) bool {
select {
case <-ctx.Done():
return true
default:
return false
}
}