github.com/replicatedhq/ship@v0.55.0/pkg/api/spec.go (about)

     1  package api
     2  
     3  import (
     4  	"fmt"
     5  	"regexp"
     6  	"strings"
     7  	"time"
     8  
     9  	"github.com/replicatedhq/ship/pkg/constants"
    10  )
    11  
    12  var releaseNameRegex = regexp.MustCompile(`[^a-zA-Z0-9\-]`)
    13  
    14  // Spec is the top level Ship document that defines an application
    15  type Spec struct {
    16  	Assets    Assets    `json:"assets" yaml:"assets" hcl:"asset"`
    17  	Lifecycle Lifecycle `json:"lifecycle" yaml:"lifecycle" hcl:"lifecycle"`
    18  	Config    Config    `json:"config" yaml:"config" hcl:"config"`
    19  }
    20  
    21  // Image
    22  type Image struct {
    23  	URL      string `json:"url" yaml:"url" hcl:"url" meta:"url"`
    24  	Source   string `json:"source" yaml:"source" hcl:"source" meta:"source"`
    25  	AppSlug  string `json:"appSlug" yaml:"appSlug" hcl:"appSlug" meta:"appSlug"`
    26  	ImageKey string `json:"imageKey" yaml:"imageKey" hcl:"imageKey" meta:"imageKey"`
    27  }
    28  
    29  type GithubContent struct {
    30  	Repo  string       `json:"repo" yaml:"repo" hcl:"repo" meta:"repo"`
    31  	Path  string       `json:"path" yaml:"path" hcl:"path" meta:"path"`
    32  	Ref   string       `json:"ref" yaml:"ref" hcl:"ref" meta:"ref"`
    33  	Files []GithubFile `json:"files" yaml:"files" hcl:"files" meta:"files"`
    34  }
    35  
    36  // Not using json.Marshal because I want to omit the file data, and don't feel like
    37  // writing a custom marshaller
    38  func (g GithubContent) String() string {
    39  
    40  	fileStr := "["
    41  	for _, file := range g.Files {
    42  		fileStr += fmt.Sprintf("%s, ", file.String())
    43  	}
    44  	fileStr += "]"
    45  
    46  	return fmt.Sprintf("GithubContent{ repo:%s path:%s ref:%s files:%s }", g.Repo, g.Path, g.Ref, fileStr)
    47  }
    48  
    49  // GithubFile
    50  type GithubFile struct {
    51  	Name string `json:"name" yaml:"name" hcl:"name" meta:"name"`
    52  	Path string `json:"path" yaml:"path" hcl:"path" meta:"path"`
    53  	Sha  string `json:"sha" yaml:"sha" hcl:"sha" meta:"sha"`
    54  	Size int64  `json:"size" yaml:"size" hcl:"size" meta:"size"`
    55  	Data string `json:"data" yaml:"data" hcl:"data" meta:"data"`
    56  }
    57  
    58  func (file GithubFile) String() string {
    59  	return fmt.Sprintf("GitHubFile{ name:%s path:%s sha:%s size:%d dataLen:%d }",
    60  		file.Name, file.Path, file.Sha, file.Size, len(file.Data))
    61  
    62  }
    63  
    64  type ShipAppMetadata struct {
    65  	Description  string `json:"description" yaml:"description" hcl:"description" meta:"description"`
    66  	Version      string `json:"version" yaml:"version" hcl:"version" meta:"version"`
    67  	Icon         string `json:"icon" yaml:"icon" hcl:"icon" meta:"icon"`
    68  	Name         string `json:"name" yaml:"name" hcl:"name" meta:"name"`
    69  	Readme       string `json:"readme" yaml:"readme" hcl:"readme" meta:"readme"`
    70  	URL          string `json:"url" yaml:"url" hcl:"url" meta:"url"`
    71  	ContentSHA   string `json:"contentSHA" yaml:"contentSHA" hcl:"contentSHA" meta:"contentSHA"`
    72  	ReleaseNotes string `json:"releaseNotes" yaml:"releaseNotes" hcl:"releaseNotes" meta:"release-notes"`
    73  }
    74  
    75  type License struct {
    76  	ID        string    `json:"id" yaml:"id" hcl:"id" meta:"id"`
    77  	Assignee  string    `json:"assignee" yaml:"assignee" hcl:"assignee" meta:"assignee"`
    78  	CreatedAt time.Time `json:"createdAt" yaml:"createdAt" hcl:"createdAt" meta:"created-at"`
    79  	ExpiresAt time.Time `json:"expiresAt" yaml:"expiresAt" hcl:"expiresAt" meta:"expires-at"`
    80  	Type      string    `json:"type" yaml:"type" hcl:"type" meta:"type"`
    81  }
    82  
    83  // ReleaseMetadata
    84  type ReleaseMetadata struct {
    85  	ReleaseID       string          `json:"releaseId" yaml:"releaseId" hcl:"releaseId" meta:"release-id"`
    86  	Sequence        int64           `json:"sequence" yaml:"sequence" hcl:"sequence" meta:"sequence"`
    87  	CustomerID      string          `json:"customerId" yaml:"customerId" hcl:"customerId" meta:"customer-id"`
    88  	InstallationID  string          `json:"installation" yaml:"installation" hcl:"installation" meta:"installation-id"`
    89  	ChannelID       string          `json:"channelId" yaml:"channelId" hcl:"channelId" meta:"channel-id"`
    90  	AppSlug         string          `json:"appSlug" yaml:"appSlug" hcl:"appSlug" meta:"app-slug"`
    91  	LicenseID       string          `json:"licenseId" yaml:"licenseId" hcl:"licenseId" meta:"license-id"`
    92  	ChannelName     string          `json:"channelName" yaml:"channelName" hcl:"channelName" meta:"channel-name"`
    93  	ChannelIcon     string          `json:"channelIcon" yaml:"channelIcon" hcl:"channelIcon" meta:"channel-icon"`
    94  	Semver          string          `json:"semver" yaml:"semver" hcl:"semver" meta:"release-version"`
    95  	ReleaseNotes    string          `json:"releaseNotes" yaml:"releaseNotes" hcl:"releaseNotes" meta:"release-notes"`
    96  	Created         string          `json:"created" yaml:"created" hcl:"created" meta:"release-date"`
    97  	Installed       string          `json:"installed" yaml:"installed" hcl:"installed" meta:"install-date"`
    98  	RegistrySecret  string          `json:"registrySecret" yaml:"registrySecret" hcl:"registrySecret" meta:"registry-secret"`
    99  	Images          []Image         `json:"images" yaml:"images" hcl:"images" meta:"images"`
   100  	GithubContents  []GithubContent `json:"githubContents" yaml:"githubContents" hcl:"githubContents" meta:"githubContents"`
   101  	ShipAppMetadata ShipAppMetadata `json:"shipAppMetadata" yaml:"shipAppMetadata" hcl:"shipAppMetadata" meta:"shipAppMetadata"`
   102  	Entitlements    Entitlements    `json:"entitlements" yaml:"entitlements" hcl:"entitlements" meta:"entitlements"`
   103  	EntitlementSpec string          `json:"entitlementSpec" yaml:"entitlementSpec" hcl:"entitlementSpec" meta:"entitlementSpec"`
   104  	ConfigSpec      string          `json:"configSpec" yaml:"configSpec" hcl:"configSpec" meta:"configSpec"`
   105  	CollectSpec     string          `json:"collectSpec" yaml:"collectSpec" hcl:"collectSpec" meta:"collectSpec"`
   106  	AnalyzeSpec     string          `json:"analyzeSpec" yaml:"analyzeSpec" hcl:"analyzeSpec" meta:"analyzeSpec"`
   107  	Type            string          `json:"type" yaml:"type" hcl:"type" meta:"type"`
   108  	License         License         `json:"license" yaml:"license" hcl:"license" meta:"license"`
   109  }
   110  
   111  func (r ReleaseMetadata) ReleaseName() string {
   112  	var releaseName string
   113  
   114  	if r.ChannelName != "" {
   115  		releaseName = r.ChannelName
   116  	}
   117  
   118  	if r.ShipAppMetadata.Name != "" {
   119  		releaseName = r.ShipAppMetadata.Name
   120  	}
   121  
   122  	if releaseName == "" && r.AppSlug != "" {
   123  		releaseName = r.AppSlug
   124  	}
   125  
   126  	if len(releaseName) == 0 {
   127  		return "ship"
   128  	}
   129  
   130  	releaseName = strings.ToLower(releaseName)
   131  	return releaseNameRegex.ReplaceAllLiteralString(releaseName, "-")
   132  }
   133  
   134  // Release
   135  type Release struct {
   136  	Metadata ReleaseMetadata
   137  	Spec     Spec
   138  }
   139  
   140  func (r *Release) FindRenderStep() *Render {
   141  	for _, step := range r.Spec.Lifecycle.V1 {
   142  		if step.Render != nil {
   143  			return step.Render
   144  		}
   145  	}
   146  	return nil
   147  }
   148  
   149  func (r *Release) FindRenderRoot() string {
   150  	render := r.FindRenderStep()
   151  	if render == nil {
   152  		return constants.InstallerPrefixPath
   153  	}
   154  
   155  	return render.RenderRoot()
   156  }