Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Display list of commands from the local devfile in odo describe component output #6944

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
27 changes: 27 additions & 0 deletions docs/website/docs/command-reference/describe-component.md
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,32 @@ Supported odo features:
• Deploy: true
• Debug: true

Commands:
• my-install
Type: exec
Group: build
Command Line: "npm install"
Component: runtime
Component Type: container
• my-run
Type: exec
Group: run
Command Line: "npm start"
Component: runtime
Component Type: container
• build-image
Type: apply
Component: prod-image
Component Type: image
Image Name: devfile-nodejs-deploy:latest
• deploy-deployment
Type: apply
Component: outerloop-deploy
Component Type: kubernetes
• deploy
Type: composite
Group: deploy

Container components:
• runtime

Expand All @@ -55,6 +81,7 @@ Kubernetes Routes:
This command returns information extracted from the Devfile:
- metadata (name, display name, project type, language, version, description and tags)
- supported odo features, indicating if the Devfile defines necessary information to run `odo dev`, `odo dev --debug` and `odo deploy`
- the list of commands, if any, along with some useful information about each command
- the list of container components,
- the list of Kubernetes components.
- the list of forwarded ports if the component is running in Dev mode.
Expand Down
40 changes: 40 additions & 0 deletions docs/website/docs/command-reference/json-output.md
Original file line number Diff line number Diff line change
Expand Up @@ -139,6 +139,7 @@ When the `describe component` command is executed without parameter from a direc
- the path of the Devfile,
- the content of the Devfile,
- supported `odo` features, indicating if the Devfile defines necessary information to run `odo dev`, `odo dev --debug` and `odo deploy`
- the list of commands, if any, along with some useful information about each command
- ingress or routes created in Deploy mode
- the status of the component
- the forwarded ports if odo is currently running in Dev mode,
Expand All @@ -155,6 +156,45 @@ odo describe component -o json
"schemaVersion": "2.0.0",
[ devfile.yaml file content ]
},
"commands": [
{
"name": "my-install",
"type": "exec",
"group": "build",
"isDefault": true,
"commandLine": "npm install",
"component": "runtime",
"componentType": "container"
},
{
"name": "my-run",
"type": "exec",
"group": "run",
"isDefault": true,
"commandLine": "npm start",
"component": "runtime",
"componentType": "container"
},
{
"name": "build-image",
"type": "apply",
"component": "prod-image",
"componentType": "image",
"imageName": "devfile-nodejs-deploy"
},
{
"name": "deploy-deployment",
"type": "apply",
"component": "outerloop-deploy",
"componentType": "kubernetes"
},
{
"name": "deploy",
"type": "composite",
"group": "deploy",
"isDefault": true
}
],
"supportedOdoFeatures": {
"dev": true,
"deploy": false,
Expand Down
39 changes: 39 additions & 0 deletions pkg/api/devfile-data.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import "github.com/devfile/library/v2/pkg/devfile/parser/data"
// DevfileData describes a devfile content
type DevfileData struct {
Devfile data.DevfileData `json:"devfile"`
Commands []DevfileCommand `json:"commands,omitempty"`
SupportedOdoFeatures *SupportedOdoFeatures `json:"supportedOdoFeatures,omitempty"`
}

Expand All @@ -14,3 +15,41 @@ type SupportedOdoFeatures struct {
Deploy bool `json:"deploy"`
Debug bool `json:"debug"`
}

type DevfileCommand struct {
Name string `json:"name,omitempty"`
Type DevfileCommandType `json:"type,omitempty"`
Group DevfileCommandGroup `json:"group,omitempty"`
IsDefault *bool `json:"isDefault,omitempty"`
CommandLine string `json:"commandLine,omitempty"`
Component string `json:"component,omitempty"`
ComponentType DevfileComponentType `json:"componentType,omitempty"`
ImageName string `json:"imageName,omitempty"`
}

type DevfileCommandType string

const (
ExecCommandType DevfileCommandType = "exec"
ApplyCommandType DevfileCommandType = "apply"
CompositeCommandType DevfileCommandType = "composite"
)

type DevfileCommandGroup string

const (
BuildCommandGroup DevfileCommandGroup = "build"
RunCommandGroup DevfileCommandGroup = "run"
TestCommandGroup DevfileCommandGroup = "test"
DebugCommandGroup DevfileCommandGroup = "debug"
DeployCommandGroup DevfileCommandGroup = "deploy"
)

type DevfileComponentType string

const (
ImageComponentType DevfileComponentType = "image"
ContainerComponentType DevfileComponentType = "container"
KubernetesComponentType DevfileComponentType = "kubernetes"
OpenshiftComponentType DevfileComponentType = "openshift"
)
101 changes: 99 additions & 2 deletions pkg/api/utils.go
Original file line number Diff line number Diff line change
@@ -1,16 +1,24 @@
package api

import (
v1alpha2 "github.com/devfile/api/v2/pkg/apis/workspaces/v1alpha2"
"github.com/devfile/library/v2/pkg/devfile/parser"
"github.com/devfile/library/v2/pkg/devfile/parser/data"
"github.com/devfile/library/v2/pkg/devfile/parser/data/v2/common"

"github.com/redhat-developer/odo/pkg/libdevfile"
)

func GetDevfileData(devfileObj parser.DevfileObj) *DevfileData {
func GetDevfileData(devfileObj parser.DevfileObj) (*DevfileData, error) {
commands, err := getDevfileCommands(devfileObj.Data)
if err != nil {
return nil, err
}
return &DevfileData{
Devfile: devfileObj.Data,
Commands: commands,
SupportedOdoFeatures: getSupportedOdoFeatures(devfileObj.Data),
}
}, nil
}

func getSupportedOdoFeatures(devfileData data.DevfileData) *SupportedOdoFeatures {
Expand All @@ -20,3 +28,92 @@ func getSupportedOdoFeatures(devfileData data.DevfileData) *SupportedOdoFeatures
Debug: libdevfile.HasDebugCommand(devfileData),
}
}

func getDevfileCommands(devfileData data.DevfileData) ([]DevfileCommand, error) {
commands, err := devfileData.GetCommands(common.DevfileOptions{})
if err != nil {
return nil, err
}

toGroupFn := func(g *v1alpha2.CommandGroup) (group DevfileCommandGroup, isDefault *bool) {
if g == nil {
return "", nil
}
switch g.Kind {
case v1alpha2.BuildCommandGroupKind:
group = BuildCommandGroup
case v1alpha2.RunCommandGroupKind:
group = RunCommandGroup
case v1alpha2.DebugCommandGroupKind:
group = DebugCommandGroup
case v1alpha2.TestCommandGroupKind:
group = TestCommandGroup
case v1alpha2.DeployCommandGroupKind:
group = DeployCommandGroup
}

return group, g.IsDefault
}

var result []DevfileCommand
for _, cmd := range commands {
var (
cmdType DevfileCommandType
cmdComponent string
cmdCompType DevfileComponentType
cmdLine string
)
var cmdGroup *v1alpha2.CommandGroup
switch {
case cmd.Apply != nil:
cmdType = ApplyCommandType
cmdComponent = cmd.Apply.Component
cmdGroup = cmd.Apply.Group
case cmd.Exec != nil:
cmdType = ExecCommandType
cmdComponent = cmd.Exec.Component
cmdGroup = cmd.Exec.Group
cmdLine = cmd.Exec.CommandLine
case cmd.Composite != nil:
cmdType = CompositeCommandType
cmdGroup = cmd.Composite.Group
}

var imageName string
var comp v1alpha2.Component
if cmdComponent != "" {
var ok bool
comp, ok, err = libdevfile.FindComponentByName(devfileData, cmdComponent)
if err != nil {
return nil, err
}
if ok {
switch {
case comp.Kubernetes != nil:
cmdCompType = KubernetesComponentType
case comp.Openshift != nil:
cmdCompType = OpenshiftComponentType
case comp.Container != nil:
cmdCompType = ContainerComponentType
case comp.Image != nil:
cmdCompType = ImageComponentType
imageName = comp.Image.ImageName
}
}
}
g, isDefault := toGroupFn(cmdGroup)
c := DevfileCommand{
Name: cmd.Id,
Type: cmdType,
Group: g,
IsDefault: isDefault,
CommandLine: cmdLine,
Component: cmdComponent,
ComponentType: cmdCompType,
ImageName: imageName,
}
result = append(result, c)
}

return result, nil
}
10 changes: 8 additions & 2 deletions pkg/component/describe/describe.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ import (
"github.com/devfile/library/v2/pkg/devfile/generator"
"github.com/devfile/library/v2/pkg/devfile/parser"
"github.com/devfile/library/v2/pkg/devfile/parser/data/v2/common"
"k8s.io/klog"

"github.com/redhat-developer/odo/pkg/api"
"github.com/redhat-developer/odo/pkg/component"
"github.com/redhat-developer/odo/pkg/kclient"
Expand All @@ -20,7 +22,6 @@ import (
odocontext "github.com/redhat-developer/odo/pkg/odo/context"
"github.com/redhat-developer/odo/pkg/podman"
"github.com/redhat-developer/odo/pkg/state"
"k8s.io/klog"
)

// DescribeDevfileComponent describes the component defined by the devfile in the current directory
Expand All @@ -36,6 +37,11 @@ func DescribeDevfileComponent(
componentName = odocontext.GetComponentName(ctx)
)

devfileData, err := api.GetDevfileData(*devfileObj)
if err != nil {
return api.Component{}, nil, err
}

isPlatformFeatureEnabled := feature.IsEnabled(ctx, feature.GenericPlatformFlag)
platform := fcontext.GetPlatform(ctx, "")
switch platform {
Expand Down Expand Up @@ -115,7 +121,7 @@ func DescribeDevfileComponent(

cmp := api.Component{
DevfilePath: devfilePath,
DevfileData: api.GetDevfileData(*devfileObj),
DevfileData: devfileData,
DevForwardedPorts: forwardedPorts,
RunningIn: api.MergeRunningModes(runningOn),
RunningOn: runningOn,
Expand Down
14 changes: 14 additions & 0 deletions pkg/libdevfile/libdevfile.go
Original file line number Diff line number Diff line change
Expand Up @@ -451,6 +451,20 @@ func GetContainerComponentsForCommand(devfileObj parser.DevfileObj, cmd v1alpha2
}
}

// FindComponentByName returns the Devfile component that matches the specified name.
func FindComponentByName(d data.DevfileData, n string) (v1alpha2.Component, bool, error) {
comps, err := d.GetComponents(common.DevfileOptions{})
if err != nil {
return v1alpha2.Component{}, false, err
}
for _, c := range comps {
if c.Name == n {
return c, true, nil
}
}
return v1alpha2.Component{}, false, nil
}

// GetK8sManifestsWithVariablesSubstituted returns the full content of either a Kubernetes or an Openshift
// Devfile component, either Inlined or referenced via a URI.
// No matter how the component is defined, it returns the content with all variables substituted
Expand Down
31 changes: 31 additions & 0 deletions pkg/odo/cli/describe/component.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import (
"github.com/devfile/library/v2/pkg/devfile/parser/data/v2/common"
"github.com/spf13/cobra"
ktemplates "k8s.io/kubectl/pkg/util/templates"
"k8s.io/utils/pointer"

"github.com/redhat-developer/odo/pkg/api"
"github.com/redhat-developer/odo/pkg/component/describe"
Expand Down Expand Up @@ -192,6 +193,36 @@ func printHumanReadableOutput(ctx context.Context, cmp api.Component, devfileObj
}
fmt.Println()

if cmp.DevfileData != nil && len(cmp.DevfileData.Commands) != 0 {
log.Info("Commands:")
for _, cmd := range cmp.DevfileData.Commands {
item := cmd.Name
if pointer.BoolDeref(cmd.IsDefault, false) {
item = log.Sbold(cmd.Name)
}
if cmd.Type != "" {
item += fmt.Sprintf("\n Type: %s", cmd.Type)
}
if cmd.Group != "" {
item += fmt.Sprintf("\n Group: %s", cmd.Group)
}
if cmd.CommandLine != "" {
item += fmt.Sprintf("\n Command Line: %q", cmd.CommandLine)
}
if cmd.Component != "" {
item += fmt.Sprintf("\n Component: %s", cmd.Component)
}
if cmd.ComponentType != "" {
item += fmt.Sprintf("\n Component Type: %s", cmd.ComponentType)
}
if cmd.ImageName != "" {
item += fmt.Sprintf("\n Image Name: %s", cmd.ImageName)
}
log.Printf(item)
}
}
fmt.Println()

err := listComponentsNames("Container components:", devfileObj, v1alpha2.ContainerComponentType)
if err != nil {
return err
Expand Down
6 changes: 5 additions & 1 deletion pkg/odo/cli/init/init.go
Original file line number Diff line number Diff line change
Expand Up @@ -161,9 +161,13 @@ func (o *InitOptions) RunForJsonOutput(ctx context.Context) (out interface{}, er
if err != nil {
return nil, err
}
devfileData, err := api.GetDevfileData(devfileObj)
if err != nil {
return nil, err
}
return api.Component{
DevfilePath: devfilePath,
DevfileData: api.GetDevfileData(devfileObj),
DevfileData: devfileData,
DevForwardedPorts: []api.ForwardedPort{},
RunningIn: api.NewRunningModes(),
ManagedBy: "odo",
Expand Down
7 changes: 6 additions & 1 deletion pkg/registry/registry.go
Original file line number Diff line number Diff line change
Expand Up @@ -445,5 +445,10 @@ func (o RegistryClient) retrieveDevfileDataFromRegistry(ctx context.Context, reg

// Convert DevfileObj to DevfileData
// use api.GetDevfileData to get supported features
return *api.GetDevfileData(devfileObj), nil
devfileData, err := api.GetDevfileData(devfileObj)
if err != nil {
return api.DevfileData{}, err
}

return *devfileData, nil
}
Loading