Skip to content
Merged
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
162 changes: 146 additions & 16 deletions cmd/project-metadata/metadata.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,13 +21,35 @@ type Response struct {
}

type ProjectMetadata struct {
ProjectName string `json:"project"`
Type string `json:"type"`
Maintainer string `json:"maintainer"`
SectionIoApplication string `json:"section-io-application"`
ApexDomain string `json:"apex-domain"`
BackendProject string `json:"backend-project"`
ProductionDomain string `json:"production-domain"`
ProjectName string `json:"project"`
Type string `json:"type"`
Maintainer string `json:"maintainer"`
SectionIoApplication string `json:"section-io-application"`
ApexDomain string `json:"apex-domain"`
BackendProject string `json:"backend-project"`
ProductionDomain string `json:"production-domain"`
Facts map[string]string `json:"facts,omitempty"`
}

// Fact represents a single fact from the Lagoon API
type Fact struct {
Name string `json:"name"`
Value string `json:"value"`
Description string `json:"description"`
}

// Environment represents an environment with facts
type Environment struct {
Name string `json:"name"`
Facts []Fact `json:"facts"`
}

// ProjectByNameResponse represents the response from the ProjectByName query
type ProjectByNameResponse struct {
ProjectByName struct {
Name string `json:"name"`
Environments []Environment `json:"environments"`
} `json:"projectByName"`
}

// parseTypes parses a comma-separated string of types and returns a slice of types
Expand Down Expand Up @@ -87,6 +109,7 @@ func Metadata(ctx context.Context, c *cli.Command) error {

all := c.Bool("all")
metadataType := c.String("type")
includeFacts := c.Bool("include-facts")
args := make([]string, 0)

// Parse the type parameter to handle comma-separated values
Expand Down Expand Up @@ -124,6 +147,13 @@ func Metadata(ctx context.Context, c *cli.Command) error {
return err
}

// Get extended project info to access productionEnvironment field
extendedProject := &schema.Project{}
err = client.ProjectByNameExtended(ctx, v, extendedProject)
if err != nil {
return err
}

item := ProjectMetadata{
ProjectName: project.Name,
Type: project.Metadata["type"],
Expand All @@ -134,6 +164,75 @@ func Metadata(ctx context.Context, c *cli.Command) error {
ProductionDomain: project.Metadata["production-domain"],
}

// Fetch facts if requested
if includeFacts {
facts := make(map[string]string)

// Use the specific GraphQL query to fetch facts from production environment
query := `
query ProjectByName(
$name: String!
$type: EnvType
$keyFacts: Boolean
$summary: Boolean
) {
projectByName(name: $name) {
name
environments(type: $type) {
name
facts(keyFacts: $keyFacts, summary: $summary) {
name
value
description
}
}
}
}
`

variables := map[string]interface{}{
"name": project.Name,
"type": "PRODUCTION",
"keyFacts": true,
"summary": false,
}

response, err := client.ProcessRaw(ctx, query, variables)
if err != nil {
facts["status"] = fmt.Sprintf("Unable to fetch facts: %v", err)
} else {
// Parse the response
responseBytes, err := json.Marshal(response)
if err != nil {
facts["status"] = fmt.Sprintf("Unable to marshal response: %v", err)
} else {
var projectResponse ProjectByNameResponse
err = json.Unmarshal(responseBytes, &projectResponse)
if err != nil {
facts["status"] = fmt.Sprintf("Unable to parse response: %v", err)
} else {
// Extract facts from production environments
if len(projectResponse.ProjectByName.Environments) > 0 {
for _, env := range projectResponse.ProjectByName.Environments {
for _, fact := range env.Facts {
if fact.Name != "" && fact.Value != "" {
facts[fact.Name] = fact.Value
}
}
}
if len(facts) == 0 {
facts["status"] = "No facts available for production environment"
}
} else {
facts["status"] = "No production environment found"
}
}
}
}

item.Facts = facts
}

output.Items = append(output.Items, item)
}

Expand All @@ -154,6 +253,9 @@ func Metadata(ctx context.Context, c *cli.Command) error {
"Backend Project",
"Production Domain",
}
if includeFacts {
header = append(header, "Facts")
}
writer.Write(header)

// Write CSV data rows
Expand All @@ -167,21 +269,37 @@ func Metadata(ctx context.Context, c *cli.Command) error {
item.BackendProject,
item.ProductionDomain,
}
if includeFacts {
factsStr := ""
if item.Facts != nil {
for key, value := range item.Facts {
if factsStr != "" {
factsStr += "; "
}
factsStr += fmt.Sprintf("%s: %s", key, value)
}
}
record = append(record, factsStr)
}
writer.Write(record)
}
} else {
table := simpletable.New()

headerCells := []*simpletable.Cell{
{Align: simpletable.AlignLeft, Text: "Project"},
{Align: simpletable.AlignLeft, Text: "Type"},
{Align: simpletable.AlignLeft, Text: "Maintainer"},
{Align: simpletable.AlignLeft, Text: "SectionIO App"},
{Align: simpletable.AlignLeft, Text: "Apex Domain"},
{Align: simpletable.AlignLeft, Text: "Backend Project"},
{Align: simpletable.AlignLeft, Text: "Production Domain"},
}
if includeFacts {
headerCells = append(headerCells, &simpletable.Cell{Align: simpletable.AlignLeft, Text: "Facts"})
}
table.Header = &simpletable.Header{
Cells: []*simpletable.Cell{
{Align: simpletable.AlignLeft, Text: "Project"},
{Align: simpletable.AlignLeft, Text: "Type"},
{Align: simpletable.AlignLeft, Text: "Maintainer"},
{Align: simpletable.AlignLeft, Text: "SectionIO App"},
{Align: simpletable.AlignLeft, Text: "Apex Domain"},
{Align: simpletable.AlignLeft, Text: "Backend Project"},
{Align: simpletable.AlignLeft, Text: "Production Domain"},
},
Cells: headerCells,
}

for _, item := range output.Items {
Expand All @@ -194,6 +312,18 @@ func Metadata(ctx context.Context, c *cli.Command) error {
{Text: item.BackendProject},
{Text: item.ProductionDomain},
}
if includeFacts {
factsStr := ""
if item.Facts != nil {
for key, value := range item.Facts {
if factsStr != "" {
factsStr += "\n"
}
factsStr += fmt.Sprintf("%s: %s", key, value)
}
}
r = append(r, &simpletable.Cell{Text: factsStr})
}
table.Body.Cells = append(table.Body.Cells, r)
}
table.SetStyle(simpletable.StyleCompactLite)
Expand Down
4 changes: 4 additions & 0 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,10 @@ func main() {
DefaultText: "all",
Value: "all",
},
&cli.BoolFlag{
Name: "include-facts",
Usage: "Include project facts (base image, Drupal version, etc.)",
},
&cli.StringFlag{
Name: "output",
Usage: "Output format - supports json, table, csv",
Expand Down
Loading