From 64f061697059bc21209d304ebff50972e077a126 Mon Sep 17 00:00:00 2001 From: Kris De Volder Date: Mon, 8 May 2017 17:48:40 -0700 Subject: [PATCH] Better handle 'driver' property in semver resource --- .../yaml/completion/YTypeAssistContext.java | 10 +- .../commons/yaml/schema/YTypeFactory.java | 14 ++- .../commons/yaml/schema/YTypedProperty.java | 2 +- .../vscode/concourse/PipelineYmlSchema.java | 2 +- .../vscode/concourse/ConcourseEditorTest.java | 109 ++++++++++++++++++ 5 files changed, 129 insertions(+), 8 deletions(-) diff --git a/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/completion/YTypeAssistContext.java b/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/completion/YTypeAssistContext.java index 0d34ac348..46eb40643 100644 --- a/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/completion/YTypeAssistContext.java +++ b/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/completion/YTypeAssistContext.java @@ -112,12 +112,12 @@ public class YTypeAssistContext extends AbstractYamlAssistContext { if (CollectionUtil.hasElements(allProperties)) { List> tieredProperties = sortIntoTiers(allProperties); Set definedProps = dynamicCtxt.getDefinedProperties(); + List proposals = new ArrayList<>(); for (List thisTier : tieredProperties) { List undefinedProps = thisTier.stream() .filter(p -> !definedProps.contains(p.getName())) .collect(Collectors.toList()); if (!undefinedProps.isEmpty()) { - List proposals = new ArrayList<>(); for (YTypedProperty p : undefinedProps) { String name = p.getName(); double score = FuzzyMatcher.matchScore(query, name); @@ -137,9 +137,13 @@ public class YTypeAssistContext extends AbstractYamlAssistContext { ); } } - return proposals; + } + //We should only move on to the next tier if all required properties in this tier are defined. + if (undefinedProps.stream().anyMatch(p -> p.isRequired())) { + return proposals; //stop here, take no more from next tier! } } + return proposals; } return Collections.emptyList(); } @@ -147,7 +151,7 @@ public class YTypeAssistContext extends AbstractYamlAssistContext { /** * Divides a given list of properties into tiers of decreasing significance. Property tiering * is a mechanism to reduce 'noise' in content assist proposals. Only properties of the - * first tier that some still undefined properties will be used to generate proposals. + * first X tiers will be used, until those tiers no longer have undefined required properties. *

* This allows, for example, to only suggest a 'name' property when starting to define * a new named entity. This is what a sane user would probably want, even though diff --git a/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypeFactory.java b/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypeFactory.java index 07b6745c4..3d0e3e06b 100644 --- a/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypeFactory.java +++ b/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypeFactory.java @@ -772,7 +772,7 @@ public class YTypeFactory { @Override public boolean isRequired() { - return isRequired || isPrimary; + return isRequired; } public void isDeprecated(boolean isDeprecated) { @@ -784,8 +784,16 @@ public class YTypeFactory { return this.isDeprecated; } - public YTypedPropertyImpl isPrimary(boolean b) { - this.isPrimary = b; + + public YTypedPropertyImpl isPrimary(boolean primary) { + this.isPrimary = primary; + this.isRequired = primary; + return this; + } + + public YTypedPropertyImpl isPrimary(boolean primary, boolean required) { + this.isPrimary = primary; + this.isRequired = required; return this; } diff --git a/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypedProperty.java b/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypedProperty.java index 36da3cd76..ddfc941a3 100644 --- a/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypedProperty.java +++ b/headless-services/commons/commons-yaml/src/main/java/org/springframework/ide/vscode/commons/yaml/schema/YTypedProperty.java @@ -19,7 +19,7 @@ public interface YTypedProperty { String getName(); YType getType(); Renderable getDescription(); - default boolean isRequired() { return isPrimary() || false; } + default boolean isRequired() { return false; } default boolean isDeprecated() { return false; } default boolean isPrimary() { return false; } } diff --git a/headless-services/concourse-language-server/src/main/java/org/springframework/ide/vscode/concourse/PipelineYmlSchema.java b/headless-services/concourse-language-server/src/main/java/org/springframework/ide/vscode/concourse/PipelineYmlSchema.java index d61fc10cc..d3551bc1d 100644 --- a/headless-services/concourse-language-server/src/main/java/org/springframework/ide/vscode/concourse/PipelineYmlSchema.java +++ b/headless-services/concourse-language-server/src/main/java/org/springframework/ide/vscode/concourse/PipelineYmlSchema.java @@ -563,7 +563,7 @@ public class PipelineYmlSchema implements YamlSchema { } }).treatAsBean(); addProp(source, "initial_version", t_semver); - addProp(source, "driver", f.yenum("SemverDriver", "git", "s3", "swift")); + addProp(source, "driver", f.yenum("SemverDriver", "git", "s3", "swift")).isPrimary(true, false); for (AbstractType s : driverSpecificSources) { for (YTypedProperty p : source.getProperties()) { s.addProperty(p); diff --git a/headless-services/concourse-language-server/src/test/java/org/springframework/ide/vscode/concourse/ConcourseEditorTest.java b/headless-services/concourse-language-server/src/test/java/org/springframework/ide/vscode/concourse/ConcourseEditorTest.java index c12595eea..193fe65fc 100644 --- a/headless-services/concourse-language-server/src/test/java/org/springframework/ide/vscode/concourse/ConcourseEditorTest.java +++ b/headless-services/concourse-language-server/src/test/java/org/springframework/ide/vscode/concourse/ConcourseEditorTest.java @@ -2126,6 +2126,115 @@ public class ConcourseEditorTest { editor.assertHoverContains("git_user", "The git identity to use"); } + @Test public void semverResourceSourcePrimaryContentAssist() throws Exception { + + //S3 completions + assertContextualCompletions(PLAIN_COMPLETION, + "resources:\n" + + "- name: fff\n" + + " type: semver\n" + + " source:\n" + + " <*>" + , ///////////// + "<*>" + , // ==> + "bucket: <*>", + "driver: <*>" + ); + + assertContextualCompletions(PLAIN_COMPLETION, + "resources:\n" + + "- name: fff\n" + + " type: semver\n" + + " source:\n" + + " driver: s3\n" + + " <*>" + , ///////////// + "<*>" + , // ==> + "bucket: <*>" + ); + + assertContextualCompletions(PLAIN_COMPLETION, + "resources:\n" + + "- name: fff\n" + + " type: semver\n" + + " source:\n" + + " driver: s3\n" + + " bucket: some-bucket\n" + + " <*>" + , ///////////// + "<*>" + , // ==> + "access_key_id: <*>", + "key: <*>", + "secret_access_key: <*>" + ); + + assertContextualCompletions(PLAIN_COMPLETION, + "resources:\n" + + "- name: fff\n" + + " type: semver\n" + + " source:\n" + + " bucket: some-bucket\n" + + " <*>" + , ///////////// + "<*>" + , // ==> + "access_key_id: <*>", + "driver: <*>", + "key: <*>", + "secret_access_key: <*>" + ); + + //git completions + assertContextualCompletions(PLAIN_COMPLETION, + "resources:\n" + + "- name: fff\n" + + " type: semver\n" + + " source:\n" + + " driver: git\n" + + " <*>" + , ///////////// + "<*>" + , // ==> + "uri: <*>" + ); + assertContextualCompletions(PLAIN_COMPLETION, + "resources:\n" + + "- name: fff\n" + + " type: semver\n" + + " source:\n" + + " driver: git\n" + + " uri: blah\n" + + " <*>" + , ///////////// + "<*>" + , // ==> + "branch: <*>", + "file: <*>" + ); + assertContextualCompletions(PLAIN_COMPLETION, + "resources:\n" + + "- name: fff\n" + + " type: semver\n" + + " source:\n" + + " driver: git\n" + + " uri: blah\n" + + " branch: master\n" + + " file: version-file\n"+ + " <*>" + , ///////////// + "<*>" + , // ==> + "git_user: <*>", + "initial_version: <*>", + "password: <*>", + "private_key: <*>", + "username: <*>" + ); + } + @Test public void semverS3ResourceSourceReconcileAndHovers() throws Exception { Editor editor;