Skip to content

Commit

Permalink
handle empty command, start ui work (#11)
Browse files Browse the repository at this point in the history
* Add types for CMP announcement

Signed-off-by: zachaller <[email protected]>

* Reorg

Signed-off-by: zachaller <[email protected]>

* finish type

Signed-off-by: zachaller <[email protected]>

* First pass at working GetParametersAnnouncement

Signed-off-by: zachaller <[email protected]>

* Typos

Signed-off-by: zachaller <[email protected]>

* Make all fields optional

Signed-off-by: zachaller <[email protected]>

* Make sure response makes it to repo server

Signed-off-by: zachaller <[email protected]>

* Refactor for testing

Signed-off-by: zachaller <[email protected]>

* values types for parameters

Signed-off-by: Michael Crenshaw <[email protected]>

* lint

Signed-off-by: Michael Crenshaw <[email protected]>

* send build env to param announcement gen

Signed-off-by: Michael Crenshaw <[email protected]>

* test parameter announcement

* tests

Signed-off-by: Michael Crenshaw <[email protected]>

* environ tests

Signed-off-by: Michael Crenshaw <[email protected]>

* Rename workdir to app dir

Signed-off-by: zachaller <[email protected]>

* handle empty command, start ui work

Signed-off-by: Michael Crenshaw <[email protected]>

* fix order

Signed-off-by: Michael Crenshaw <[email protected]>

* fix map merging, make params read-only

Signed-off-by: Michael Crenshaw <[email protected]>

Co-authored-by: zachaller <[email protected]>
  • Loading branch information
crenshaw-dev and zachaller authored Apr 27, 2022
1 parent c4a7511 commit 479155b
Show file tree
Hide file tree
Showing 5 changed files with 120 additions and 13 deletions.
27 changes: 16 additions & 11 deletions cmpserver/plugin/plugin.go
Original file line number Diff line number Diff line change
Expand Up @@ -332,9 +332,9 @@ func (s *Service) GetParametersAnnouncement(stream apiclient.ConfigManagementPlu
}

func getParametersAnnouncement(ctx context.Context, appDir string, staticAnnouncements []Static, command Command) (*apiclient.ParametersAnnouncementResponse, error) {
var staticParamAnnouncements []*apiclient.ParameterAnnouncement
var announcements []*apiclient.ParameterAnnouncement
for _, static := range staticAnnouncements {
staticParamAnnouncements = append(staticParamAnnouncements, &apiclient.ParameterAnnouncement{
announcements = append(announcements, &apiclient.ParameterAnnouncement{
Name: static.Name,
Title: static.Title,
Tooltip: static.Tooltip,
Expand All @@ -347,19 +347,24 @@ func getParametersAnnouncement(ctx context.Context, appDir string, staticAnnounc
})
}

stdout, err := runCommand(ctx, command, appDir, os.Environ())
if err != nil {
return nil, fmt.Errorf("error executing dynamic parameter output command: %s", err)
}
if len(command.Command) > 0 {
stdout, err := runCommand(ctx, command, appDir, os.Environ())
if err != nil {
return nil, fmt.Errorf("error executing dynamic parameter output command: %s", err)
}

var dynamicParamAnnouncements []*apiclient.ParameterAnnouncement
err = json.Unmarshal([]byte(stdout), &dynamicParamAnnouncements)
if err != nil {
return nil, fmt.Errorf("error unmarshaling dynamic parameter output into ParametersAnnouncementResponse: %s", err)
var dynamicParamAnnouncements []*apiclient.ParameterAnnouncement
err = json.Unmarshal([]byte(stdout), &dynamicParamAnnouncements)
if err != nil {
return nil, fmt.Errorf("error unmarshaling dynamic parameter output into ParametersAnnouncementResponse: %s", err)
}

// dynamic goes first, because static should take precedence by being later.
announcements = append(dynamicParamAnnouncements, announcements...)
}

repoResponse := &apiclient.ParametersAnnouncementResponse{
ParameterAnnouncements: append(staticParamAnnouncements, dynamicParamAnnouncements...),
ParameterAnnouncements: announcements,
}
return repoResponse, nil
}
28 changes: 26 additions & 2 deletions cmpserver/plugin/plugin_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -246,6 +246,20 @@ func Test_getParametersAnnouncement_empty_command(t *testing.T) {
assert.Equal(t, []*apiclient.ParameterAnnouncement{{Name: "static-a"}, {Name: "static-b"}}, res.ParameterAnnouncements)
}

func Test_getParametersAnnouncement_no_command(t *testing.T) {
staticYAML := `
- name: static-a
- name: static-b
`
static := &[]Static{}
err := yaml.Unmarshal([]byte(staticYAML), static)
require.NoError(t, err)
command := Command{}
res, err := getParametersAnnouncement(context.Background(), "", *static, command)
require.NoError(t, err)
assert.Equal(t, []*apiclient.ParameterAnnouncement{{Name: "static-a"}, {Name: "static-b"}}, res.ParameterAnnouncements)
}

func Test_getParametersAnnouncement_static_and_dynamic(t *testing.T) {
staticYAML := `
- name: static-a
Expand All @@ -261,10 +275,10 @@ func Test_getParametersAnnouncement_static_and_dynamic(t *testing.T) {
res, err := getParametersAnnouncement(context.Background(), "", *static, command)
require.NoError(t, err)
expected := []*apiclient.ParameterAnnouncement{
{Name: "static-a"},
{Name: "static-b"},
{Name: "dynamic-a"},
{Name: "dynamic-b"},
{Name: "static-a"},
{Name: "static-b"},
}
assert.Equal(t, expected, res.ParameterAnnouncements)
}
Expand All @@ -278,3 +292,13 @@ func Test_getParametersAnnouncement_invalid_json(t *testing.T) {
assert.Error(t, err)
assert.Contains(t, err.Error(), "unexpected end of JSON input")
}

func Test_getParametersAnnouncement_bad_command(t *testing.T) {
command := Command{
Command: []string{"exit"},
Args: []string{"1"},
}
_, err := getParametersAnnouncement(context.Background(), "", []Static{}, command)
assert.Error(t, err)
assert.Contains(t, err.Error(), "error executing dynamic parameter output command")
}
14 changes: 14 additions & 0 deletions test/cmp/plugin.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -11,3 +11,17 @@ spec:
glob: "**/kustomization.yaml"
allowConcurrency: true
lockRepo: false
parameters:
static:
- name: string-param
string: value
- name: array-param
collectionType: array
array:
- value1
- value2
- name: map-param
collectionType: map
map:
key: value
key2: value2
Original file line number Diff line number Diff line change
Expand Up @@ -278,6 +278,36 @@ export const ApplicationParameters = (props: {
view: app.spec.source.plugin && (app.spec.source.plugin.env || []).map(i => `${i.name}='${i.value}'`).join(' '),
edit: (formApi: FormApi) => <FormField field='spec.source.plugin.env' formApi={formApi} component={ArrayInputField} />
});
if (props.details.plugin.parametersAnnouncement) {
for (const announcement of props.details.plugin.parametersAnnouncement) {
const liveParam = app.spec.source.plugin.parameters?.find(param => param.name === announcement.name);
if (announcement.collectionType === undefined || announcement.collectionType === '' || announcement.collectionType === 'string') {
attributes.push({
title: announcement.title ?? announcement.name,
view: liveParam?.string || announcement.string,
edit: () => liveParam?.string || announcement.string
});
} else if (announcement.collectionType === 'array') {
attributes.push({
title: announcement.title ?? announcement.name,
view: (liveParam?.array || announcement.array || []).join(' '),
edit: () => (liveParam?.array || announcement.array || []).join(' ')
});
} else if (announcement.collectionType === 'map') {
const entries = concatMaps(announcement.map, liveParam?.map).entries();
attributes.push({
title: announcement.title ?? announcement.name,
view: Array.from(entries)
.map(([key, value]) => `${key}='${value}'`)
.join(' '),
edit: () =>
Array.from(entries)
.map(([key, value]) => `${key}='${value}'`)
.join(' ')
});
}
}
}
} else if (props.details.type === 'Directory') {
const directory = app.spec.source.directory || ({} as ApplicationSourceDirectory);
attributes.push({
Expand Down Expand Up @@ -344,3 +374,16 @@ export const ApplicationParameters = (props: {
/>
);
};

// concatMaps merges two maps. Later args take precedence where there's a key conflict.
function concatMaps(...maps: (Map<string, string> | null)[]): Map<string, string> {
const newMap = new Map<string, string>();
for (const map of maps) {
if (map) {
for (const entry of Object.entries(map)) {
newMap.set(entry[0], entry[1]);
}
}
}
return newMap;
}
21 changes: 21 additions & 0 deletions ui/src/app/shared/models.ts
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,14 @@ export interface EnvEntry {
export interface ApplicationSourcePlugin {
name: string;
env: EnvEntry[];
parameters?: Parameter[];
}

export interface Parameter {
name: string;
string?: string;
array?: string[];
map?: Map<string, string>;
}

export interface JsonnetVar {
Expand Down Expand Up @@ -579,6 +587,19 @@ export interface KustomizeAppSpec {
export interface PluginAppSpec {
name: string;
env: EnvEntry[];
parametersAnnouncement?: ParameterAnnouncement[];
}

export interface ParameterAnnouncement {
name?: string;
title?: string;
tooltip?: string;
required?: boolean;
itemType?: string;
collectionType?: string;
string?: string;
array?: string[];
map?: Map<string, string>;
}

export interface ObjectReference {
Expand Down

0 comments on commit 479155b

Please sign in to comment.