This is an automated email from the ASF dual-hosted git repository. heneveld pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/brooklyn-ui.git
commit c41915466315d66e08be011b25561602af81f1c1 Author: Alex Heneveld <[email protected]> AuthorDate: Thu Apr 22 23:06:01 2021 +0100 show quick fix on issues in spec editor also fix another dsl error logged as debug --- .../app/components/quick-fix/quick-fix.js | 32 ++++++++++++---------- .../spec-editor/spec-editor.directive.js | 21 ++++++++++++++ .../app/components/spec-editor/spec-editor.less | 9 ++++++ .../spec-editor/spec-editor.template.html | 9 +++++- .../app/components/util/model/dsl.model.js | 10 ++++++- 5 files changed, 65 insertions(+), 16 deletions(-) diff --git a/ui-modules/blueprint-composer/app/components/quick-fix/quick-fix.js b/ui-modules/blueprint-composer/app/components/quick-fix/quick-fix.js index 36e1ce0..bd96735 100644 --- a/ui-modules/blueprint-composer/app/components/quick-fix/quick-fix.js +++ b/ui-modules/blueprint-composer/app/components/quick-fix/quick-fix.js @@ -52,22 +52,26 @@ export function computeQuickFixes(allIssues) { } v.issues.push(issueO); - let qfs = getQuickFixHintsForIssue(issue); - (qfs || []).forEach(qf => { - let qfi = getQuickFixProposer(qf['fix']); - if (!qfi) { - console.log("Skipping unknown quick fix", qf); - } else { - qfi.propose(issue, v.quickFixes); - // we could offer the fix per-issue, but no need as they can get that by navigating to the entity - //qfi.propose(issue, issueO.quickFixes); - } - }); + computeQuickFixesForIssue(issue, issue.entity, v.quickFixes) }); }); return allIssues; } +export function computeQuickFixesForIssue(issue, entity, proposalHolder) { + let qfs = getQuickFixHintsForIssue(issue, entity); + (qfs || []).forEach(qf => { + let qfi = getQuickFixProposer(qf['fix']); + if (!qfi) { + console.log("Skipping unknown quick fix", qf); + } else { + qfi.propose(issue, proposalHolder); + // we could offer the fix per-issue, but no need as they can get that by navigating to the entity + //qfi.propose(issue, issueO.quickFixes); // issueO from previous method + } + }); +} + const QUICK_FIX_PROPOSERS = { clear_config: { // the propose function updates the proposals object @@ -78,7 +82,7 @@ const QUICK_FIX_PROPOSERS = { if (!proposals.clear_config) { proposals.clear_config = { text: "Remove the current value (clear config \""+issue.ref+"\")", - apply: (issue) => issue.entity.removeConfig(issue.ref), + apply: (issue, entity) => (entity || issue.entity).removeConfig(issue.ref), issues: [], }; } @@ -91,9 +95,9 @@ export function getQuickFixProposer(type) { return QUICK_FIX_PROPOSERS[type]; } -export function getQuickFixHintsForIssue(issue) { +export function getQuickFixHintsForIssue(issue, entity) { if (issue.group === 'config') { - let hints = (issue.entity.miscData.get('ui-composer-hints') || {})['config-quick-fixes'] || []; + let hints = (entity.miscData.get('ui-composer-hints') || {})['config-quick-fixes'] || []; hints = hints.filter(h => h.key === issue.ref); if (!hints.length) return null; hints = hints.filter(h => !h['message-regex'] || new RegExp(h['message-regex']).test(issue.message)); diff --git a/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.directive.js b/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.directive.js index 9da1581..43ac178 100644 --- a/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.directive.js +++ b/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.directive.js @@ -29,6 +29,7 @@ import brooklynDslViewer from '../dsl-viewer/dsl-viewer'; import template from './spec-editor.template.html'; import {graphicalState} from '../../views/main/graphical/graphical.state'; import {SENSITIVE_FIELD_REGEX} from 'brooklyn-ui-utils/sensitive-field/sensitive-field'; +import {computeQuickFixesForIssue} from '../quick-fix/quick-fix'; const MODULE_NAME = 'brooklyn.components.spec-editor'; const ANY_MEMBERSPEC_REGEX = /(^.*[m,M]ember[s,S]pec$)/; @@ -246,9 +247,29 @@ export function specEditorDirective($rootScope, $templateCache, $injector, $sani return blueprintService.refreshConfigConstraints(scope.model); }).then(() => { refreshCustomValidation(scope.model); + }).then(() => { + scope.model.issuesWithFixes = []; + scope.model.issues.forEach(issue => { + // really messy copying the issue to add the fixes, but the easiest way + let issueCopy = { + ref: issue.ref, + group: issue.group, + message: issue.message, + }; + let issueWithFixes = Object.assign({}, issueCopy, { + quickFixes: {}, + }); + computeQuickFixesForIssue(issueCopy, scope.model, issueWithFixes.quickFixes); + scope.model.issuesWithFixes.push(issueWithFixes); + }); }); + }, true); + scope.applyQuickFix = (issue, fix) => { + fix.apply(issue, scope.model); + } + scope.getObjectSize = (object) => { return specEditor.defined(object) && object !== null ? Object.keys(object).length : 0; }; diff --git a/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.less b/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.less index 68fd6e3..4fcefca 100644 --- a/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.less +++ b/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.less @@ -459,6 +459,9 @@ spec-editor { max-width: 0; } } + .quick-fix { + display: none; + } } .hide-masked-sensitive-value { display: none !important; @@ -467,6 +470,12 @@ spec-editor { margin-top: 5px; //align with icons when expanded } } + .quick-fix { + .btn { + float: right; + color: @gray-lighter !important; + } + } .param-fields { width: 100%; margin-top: 8px; diff --git a/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.template.html b/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.template.html index 19b0371..d6ae606 100644 --- a/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.template.html +++ b/ui-modules/blueprint-composer/app/components/spec-editor/spec-editor.template.html @@ -547,7 +547,14 @@ </div> - <small ng-repeat="issue in model.issues | filter:{ref: item.name}:true | filter:{group: 'config'}:true" class="help-block issue" ng-bind-html="issue.message"></small> + <small ng-repeat="issue in model.issuesWithFixes | filter:{ref: item.name}:true | filter:{group: 'config'}:true" class="help-block issue"> + <span ng-bind-html="issue.message"></span> + <div ng-if="getObjectSize(issue.quickFixes)" class="quick-fix"> + <div ng-repeat="fix in issue.quickFixes"> + <a ng-click="applyQuickFix(issue, fix)" class="btn btn-xs btn-primary">{{ fix.text }}</a> + </div> + </div> + </small> <small ng-if="specEditor.customConfigWidgetError(item)" class="help-block issue"> Custom widget unavailable: {{ specEditor.customConfigWidgetError(item) }} diff --git a/ui-modules/blueprint-composer/app/components/util/model/dsl.model.js b/ui-modules/blueprint-composer/app/components/util/model/dsl.model.js index 323d73d..0caa5e4 100644 --- a/ui-modules/blueprint-composer/app/components/util/model/dsl.model.js +++ b/ui-modules/blueprint-composer/app/components/util/model/dsl.model.js @@ -772,7 +772,9 @@ export class DslParser { // a floating point number return new Dsl(KIND.NUMBER, t.nextNumber()); } - throw new DslError('Expected: CONSTANT but found: ' + t.toJSON()); + return new Dsl(KIND.STRING, t.remainder()); + // previously we did this, but it caused all kinds of errors, as non-json input is common + // throw new DslError('Expected: CONSTANT but found: ' + t.toJSON()); } /** @@ -973,6 +975,12 @@ export class Tokenizer { this.s = this.s.substring(num); } + remainder() { + let result = this.s; + this.s = ""; + return result; + } + /** * Return <code>true</code> if a call to <code>next(sym)</code> would succeed. * @param {string} sym one or more characters, e.g.,
