This is an automated email from the ASF dual-hosted git repository. pgil pushed a commit to branch trunk in repository https://gitbox.apache.org/repos/asf/ofbiz-framework.git
The following commit(s) were added to refs/heads/trunk by this push: new b4e46ff Implemented : New child element set-callback on link to control dynamism (OFBIZ-11812) b4e46ff is described below commit b4e46ff0703b640c93f2e69a5e78b473a8be34c3 Author: Gil Portenseigne <p...@apache.org> AuthorDate: Thu Jun 24 16:13:00 2021 +0200 Implemented : New child element set-callback on link to control dynamism (OFBIZ-11812) Refreshment information are controlled by the calling object, instead of the called form. This avoid dependency between called form and parent screens. The set-callback tag generate a jwt encoded UpdateArea widget, that is transmitted through submits and links until a submit with no update-area information is met. This specific submit ends the process launched by the link, and trigger the refresh action contained into the JWT token. --- framework/widget/dtd/widget-common.xsd | 21 ++++++ .../ofbiz/widget/model/CommonWidgetModels.java | 57 +++++++++++--- .../org/apache/ofbiz/widget/model/ModelForm.java | 86 ++++++++++++++++++++++ .../apache/ofbiz/widget/model/ModelMenuItem.java | 10 +++ .../ofbiz/widget/model/ModelScreenWidget.java | 4 + .../widget/renderer/html/HtmlMenuRenderer.java | 9 ++- .../widget/renderer/macro/MacroCommonRenderer.java | 22 ++++-- .../widget/renderer/macro/MacroFormRenderer.java | 9 ++- .../widget/renderer/macro/MacroMenuRenderer.java | 14 ++-- .../widget/renderer/macro/MacroScreenRenderer.java | 11 ++- 10 files changed, 205 insertions(+), 38 deletions(-) diff --git a/framework/widget/dtd/widget-common.xsd b/framework/widget/dtd/widget-common.xsd index 7b18e40..4445fe6 100644 --- a/framework/widget/dtd/widget-common.xsd +++ b/framework/widget/dtd/widget-common.xsd @@ -526,6 +526,7 @@ under the License. <xs:element minOccurs="0" ref="auto-parameters-entity"/> <xs:element minOccurs="0" maxOccurs="unbounded" ref="parameter" /> <xs:element minOccurs="0" name="image" type="image" /> + <xs:element minOccurs="0" ref="set-callback"/> </xs:sequence> <xs:attribute type="xs:string" name="text" /> <xs:attribute type="xs:string" name="id"> @@ -613,4 +614,24 @@ under the License. </xs:simpleType> </xs:attribute> </xs:complexType> + <xs:element name="set-callback"> + <xs:annotation> + <xs:documentation>When actions behind a link are terminated, follow the given information + to update a screen</xs:documentation> + </xs:annotation> + <xs:complexType> + <xs:sequence> + <xs:element minOccurs="0" ref="auto-parameters-service"/> + <xs:element minOccurs="0" ref="auto-parameters-entity"/> + <xs:element minOccurs="0" maxOccurs="unbounded" ref="parameter"/> + </xs:sequence> + <xs:attribute name="area-id" type="xs:string"> + <xs:annotation> + <xs:documentation>Identification of the area to update. If empty, by default the screen engine + auto resolve it on the first parent referent screen present in the widget hierarchy</xs:documentation> + </xs:annotation> + </xs:attribute> + <xs:attribute name="area-target" type="xs:string" use="required" /> + </xs:complexType> + </xs:element> </xs:schema> diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/CommonWidgetModels.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/CommonWidgetModels.java index 042f50d..87661e5 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/CommonWidgetModels.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/CommonWidgetModels.java @@ -32,6 +32,7 @@ import java.util.TimeZone; import org.apache.ofbiz.base.util.Debug; import org.apache.ofbiz.base.util.UtilCodec; import org.apache.ofbiz.base.util.UtilDateTime; +import org.apache.ofbiz.base.util.UtilGenerics; import org.apache.ofbiz.base.util.UtilValidate; import org.apache.ofbiz.base.util.UtilXml; import org.apache.ofbiz.base.util.collections.FlexibleMapAccessor; @@ -53,6 +54,7 @@ import org.w3c.dom.Element; public final class CommonWidgetModels { private static final String MODULE = CommonWidgetModels.class.getName(); + public static final String JWT_CALLBACK = "JWT_CALLBACK"; private CommonWidgetModels() { } @@ -345,6 +347,7 @@ public final class CommonWidgetModels { // FIXME: These don't belong in this class (might have been used for image) private final String height; private final String width; + private final ModelForm.UpdateArea callback; public Link(Element linkElement) { this.textExdr = FlexibleStringExpander.getInstance(linkElement.getAttribute("text")); @@ -408,12 +411,18 @@ public final class CommonWidgetModels { this.confirmationMsgExdr = FlexibleStringExpander.getInstance(linkElement.getAttribute("confirmation-message")); this.width = linkElement.getAttribute("width"); this.height = linkElement.getAttribute("height"); + + Element updateAreaElement = UtilXml.firstChildElement(linkElement, "set-callback"); + this.callback = updateAreaElement != null + ? new ModelForm.UpdateArea(updateAreaElement) + : null; } // Portal constructor public Link(GenericValue portalPage, List<Parameter> parameterList, String target, Locale locale) { this.autoEntityParameters = null; this.autoServiceParameters = null; + this.callback = null; this.encode = false; this.fullPath = false; this.idExdr = FlexibleStringExpander.getInstance(""); @@ -443,6 +452,10 @@ public final class CommonWidgetModels { return autoServiceParameters; } + public ModelForm.UpdateArea getCallback() { + return callback; + } + public String getConfirmationMsg(Map<String, Object> context) { return this.confirmationMsgExdr.expandString(context); } @@ -495,7 +508,16 @@ public final class CommonWidgetModels { return parameterList; } - public Map<String, String> getParameterMap(Map<String, Object> context, String defaultEntityName, String defaultServiceName) { + public Map<String, String> getParameterMap(Map<String, Object> context, + String defaultEntityName, + String defaultServiceName) { + return getParameterMap(context, defaultEntityName, defaultServiceName, true); + } + + public Map<String, String> getParameterMap(Map<String, Object> context, + String defaultEntityName, + String defaultServiceName, + boolean propagateMyCallback) { Map<String, String> fullParameterMap = new HashMap<>(); for (Parameter parameter : this.parameterList) { fullParameterMap.put(parameter.getName(), parameter.getValue(context)); @@ -506,21 +528,32 @@ public final class CommonWidgetModels { if (autoEntityParameters != null) { fullParameterMap.putAll(autoEntityParameters.getParametersMap(context, defaultEntityName)); } + propagateCallbackInParameterMap(context, propagateMyCallback, fullParameterMap); return fullParameterMap; } - public Map<String, String> getParameterMap(Map<String, Object> context) { - Map<String, String> fullParameterMap = new HashMap<>(); - for (Parameter parameter : this.parameterList) { - fullParameterMap.put(parameter.getName(), parameter.getValue(context)); - } - if (autoServiceParameters != null) { - fullParameterMap.putAll(autoServiceParameters.getParametersMap(context, null)); - } - if (autoEntityParameters != null) { - fullParameterMap.putAll(autoEntityParameters.getParametersMap(context, null)); + // If a call back is present on link or present on context, adding it to the parameters list + private void propagateCallbackInParameterMap(Map<String, Object> context, boolean propagateMyCallback, Map<String, String> fullParameterMap) { + if (getCallback() != null && propagateMyCallback) { + fullParameterMap.put(JWT_CALLBACK, getCallback().toJwtToken(context)); + } else if (context.containsKey(JWT_CALLBACK)) { + fullParameterMap.put(JWT_CALLBACK, (String) context.get(JWT_CALLBACK)); + } else { + if (context.containsKey("parameters")) { + Map<String, Object> parameters = UtilGenerics.cast(context.get("parameters")); + if (parameters.containsKey(JWT_CALLBACK)) { + fullParameterMap.put(JWT_CALLBACK, (String) parameters.get(JWT_CALLBACK)); + } + } } - return fullParameterMap; + } + + public Map<String, String> getParameterMap(Map<String, Object> context) { + return getParameterMap(context, null, null, true); + } + + public Map<String, String> getParameterMap(Map<String, Object> context, boolean propagateMyCallback) { + return getParameterMap(context, null, null, propagateMyCallback); } public String getPrefix(Map<String, Object> context) { diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelForm.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelForm.java index 1869d2b..75b20cc 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelForm.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelForm.java @@ -31,6 +31,10 @@ import java.util.Map; import java.util.Set; import java.util.concurrent.atomic.AtomicInteger; +import java.util.stream.Collectors; +import org.apache.ofbiz.base.conversion.ConversionException; +import org.apache.ofbiz.base.conversion.JSONConverters; +import org.apache.ofbiz.base.lang.JSON; import org.apache.ofbiz.base.util.Debug; import org.apache.ofbiz.base.util.GroovyUtil; import org.apache.ofbiz.base.util.StringUtil; @@ -42,6 +46,7 @@ import org.apache.ofbiz.base.util.UtilValidate; import org.apache.ofbiz.base.util.UtilXml; import org.apache.ofbiz.base.util.collections.FlexibleMapAccessor; import org.apache.ofbiz.base.util.string.FlexibleStringExpander; +import org.apache.ofbiz.entity.Delegator; import org.apache.ofbiz.entity.GenericEntityException; import org.apache.ofbiz.entity.model.ModelEntity; import org.apache.ofbiz.entity.model.ModelField; @@ -50,6 +55,7 @@ import org.apache.ofbiz.service.DispatchContext; import org.apache.ofbiz.service.GenericServiceException; import org.apache.ofbiz.service.ModelParam; import org.apache.ofbiz.service.ModelService; +import org.apache.ofbiz.webapp.control.JWTManager; import org.apache.ofbiz.widget.WidgetWorker; import org.apache.ofbiz.widget.renderer.FormStringRenderer; import org.apache.ofbiz.widget.renderer.VisualTheme; @@ -2342,6 +2348,23 @@ public abstract class ModelForm extends ModelWidget { this.autoEntityParameters = null; } + /** String constructor. + * @param areaId The id of the widget element to be updated + * @param areaTarget The target URL called to update the area + * @param parameterList The list of parameters + */ + public UpdateArea(String eventType, String areaId, String areaTarget, + List<CommonWidgetModels.Parameter> parameterList) { + this.eventType = eventType; + this.areaId = areaId; + this.areaTarget = areaTarget; + this.defaultServiceName = null; + this.defaultEntityName = null; + this.parameterList = parameterList; + this.autoServiceParameters = null; + this.autoEntityParameters = null; + } + @Override public boolean equals(Object obj) { return obj instanceof UpdateArea && obj.hashCode() == this.hashCode(); @@ -2444,5 +2467,68 @@ public abstract class ModelForm extends ModelWidget { public List<CommonWidgetModels.Parameter> getParameterList() { return parameterList; } + + /** + * Extract updateArea information as a Jwt token + * @return the Jwt token + */ + public String toJwtToken(Map<String, Object> context) { + Delegator delegator = (Delegator) context.get("delegator"); + + Map<String, String> claims = UtilMisc.toMap( + "areaId", WidgetWorker.getScreenStack(context).resolveScreenAreaId(getAreaId()), + "areaTarget", getAreaTarget()); + + JSONConverters.MapToJSON converter = new JSONConverters.MapToJSON(); + Map<String, Object> parameters = UtilGenerics.cast(getParameterMap(context)); + try { + claims.put("parameters", converter.convert(parameters).toString()); + } catch (ConversionException e) { + Debug.logWarning("Failed to convert parameters to JSON with " + parameters, MODULE); + } + return JWTManager.createJwt(delegator, claims, -1); + } + + /** + * Retrieva Jwt from context, validate it and generate UpdateArea Object + * @return UpdateArea object + */ + public static ModelForm.UpdateArea fromJwtToken(Map<String, Object> context) { + Delegator delegator = (Delegator) context.get("delegator"); + + String jwtToken = (String) context.get(CommonWidgetModels.JWT_CALLBACK); + if (jwtToken == null && context.containsKey("parameters")) { + Map<String, Object> parameters = UtilGenerics.cast(context.get("parameters")); + jwtToken = (String) parameters.get(CommonWidgetModels.JWT_CALLBACK); + } + if (jwtToken == null) return null; + + Map<String, Object> claims = JWTManager.validateToken(jwtToken, JWTManager.getJWTKey(delegator)); + if (claims.containsKey(ModelService.ERROR_MESSAGE)) { + // Something unexpected happened here + Debug.logWarning("There was a problem with the JWT token, signature not valid.", MODULE); + return null; + } + + String areaId = (String) claims.remove("areaId"); + String areaTarget = (String) claims.remove("areaTarget"); + + Map<String, Object> parameters = null; + if (claims.containsKey("parameters")) { + JSONConverters.JSONToMap converter = new JSONConverters.JSONToMap(); + try { + parameters = converter.convert(JSON.from((String) claims.get("parameters"))); + } catch (ConversionException e) { + Debug.logWarning("Failed to convert JSON to with " + claims.get("parameters"), MODULE); + } + } + return new UpdateArea("", areaId, areaTarget, + parameters != null + ? parameters.entrySet() + .stream() + .map(entry -> new CommonWidgetModels.Parameter(entry.getKey(), (String) entry.getValue(), true)) + .collect(Collectors.toList()) + : new ArrayList<>()); + } } } diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelMenuItem.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelMenuItem.java index c0f8d04..5898bcb 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelMenuItem.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelMenuItem.java @@ -791,6 +791,16 @@ public class ModelMenuItem extends ModelWidget { } /** + * Gets parameter map. + * @param context the context + * @param propagateCallback indicate if we need to propagate callback element + * @return the parameter map + */ + public Map<String, String> getParameterMap(Map<String, Object> context, boolean propagateCallback) { + return link.getParameterMap(context, propagateCallback); + } + + /** * Gets prefix. * @param context the context * @return the prefix diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelScreenWidget.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelScreenWidget.java index 83b9028..17ce2fe 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelScreenWidget.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/model/ModelScreenWidget.java @@ -1754,6 +1754,10 @@ public abstract class ModelScreenWidget extends ModelWidget { return link.getParameterMap(context); } + public Map<String, String> getParameterMap(Map<String, Object> context, boolean propagateCallback) { + return link.getParameterMap(context, propagateCallback); + } + public FlexibleStringExpander getTextExdr() { return link.getTextExdr(); } diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/html/HtmlMenuRenderer.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/html/HtmlMenuRenderer.java index c8f5a6d..9b7046d 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/html/HtmlMenuRenderer.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/html/HtmlMenuRenderer.java @@ -428,7 +428,8 @@ public class HtmlMenuRenderer extends HtmlWidgetRenderer implements MenuStringRe + UtilMisc.<String>addToBigDecimalInMap(context, "menuUniqueItemIndex", BigDecimal.ONE); String linkType = WidgetWorker.determineAutoLinkType(link.getLinkType(), target, link.getUrlMode(), request); - if ("hidden-form".equals(linkType)) { + boolean isHiddenForm = "hidden-form".equals(linkType); + if (isHiddenForm) { writer.append("<form method=\"post\""); writer.append(" action=\""); // note that this passes null for the parameterList on purpose so they won't be put into the URL @@ -449,7 +450,7 @@ public class HtmlMenuRenderer extends HtmlWidgetRenderer implements MenuStringRe writer.append("\">"); UtilCodec.SimpleEncoder simpleEncoder = (UtilCodec.SimpleEncoder) context.get("simpleEncoder"); - for (Map.Entry<String, String> parameter: link.getParameterMap(context).entrySet()) { + for (Map.Entry<String, String> parameter: link.getParameterMap(context, false).entrySet()) { writer.append("<input name=\""); writer.append(parameter.getKey()); writer.append("\" value=\""); @@ -484,7 +485,7 @@ public class HtmlMenuRenderer extends HtmlWidgetRenderer implements MenuStringRe writer.append(name); writer.append("\""); } - if (!"hidden-form".equals(linkType)) { + if (!isHiddenForm) { if (UtilValidate.isNotEmpty(targetWindow)) { writer.append(" target=\""); writer.append(targetWindow); @@ -493,7 +494,7 @@ public class HtmlMenuRenderer extends HtmlWidgetRenderer implements MenuStringRe } writer.append(" href=\""); - if ("hidden-form".equals(linkType)) { + if (isHiddenForm) { writer.append("javascript:document."); writer.append(uniqueItemName); writer.append(".submit()"); diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroCommonRenderer.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroCommonRenderer.java index 997317f..b2bb62c 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroCommonRenderer.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroCommonRenderer.java @@ -122,7 +122,7 @@ public class MacroCommonRenderer { * @return */ public static String getLinkUrl(CommonWidgetModels.Link link, Map<String, Object> context) { - String linkUrl; + String linkUrl = ""; HttpServletRequest request = (HttpServletRequest) context.get("request"); HttpServletResponse response = (HttpServletResponse) context.get("response"); @@ -134,12 +134,22 @@ public class MacroCommonRenderer { linkUrl = createAjaxParamsFromUpdateAreas(UtilMisc.toList(resolveUpdateArea), UtilGenerics.cast(link.getParameterMap(context)), null, null, context); break; + case "hidden-form": + if (link.getCallback() != null) { + // we assume that the post request + // wait an immediate response, so we execute the callback directly + linkUrl = createAjaxParamsFromUpdateAreas(UtilMisc.toList(link.getCallback()), null, null, null, context); + } + break; default: - final URI linkUri = WidgetWorker.buildHyperlinkUri(link.getTarget(context), link.getUrlMode(), - "layered-modal".equals(link.getLinkType()) ? null : link.getParameterMap(context), link.getPrefix(context), - link.getFullPath(), link.getSecure(), link.getEncode(), - request, response); - linkUrl = linkUri.toString(); + String target = link.getTarget(context); + if (UtilValidate.isNotEmpty(target)) { + final URI linkUri = WidgetWorker.buildHyperlinkUri(target, link.getUrlMode(), + "layered-modal".equals(link.getLinkType()) ? null : link.getParameterMap(context), link.getPrefix(context), + link.getFullPath(), link.getSecure(), link.getEncode(), + request, response); + linkUrl = linkUri.toString(); + } } return linkUrl; } diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroFormRenderer.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroFormRenderer.java index c807021..9f33bee 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroFormRenderer.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroFormRenderer.java @@ -1012,14 +1012,19 @@ public final class MacroFormRenderer implements FormStringRenderer { // This is here for backwards compatibility. Use on-event-update-area // elements instead. String backgroundSubmitRefreshTarget = submitField.getBackgroundSubmitRefreshTarget(context); + ModelForm.UpdateArea jwtCallback = ModelForm.UpdateArea.fromJwtToken(context); if (UtilValidate.isNotEmpty(backgroundSubmitRefreshTarget)) { if (updateAreas == null) { updateAreas = new LinkedList<>(); } updateAreas.add(new ModelForm.UpdateArea("submit", formId, backgroundSubmitRefreshTarget)); } - boolean ajaxEnabled = (UtilValidate.isNotEmpty(updateAreas) || UtilValidate.isNotEmpty(backgroundSubmitRefreshTarget)) - && this.javaScriptEnabled; + + // In context a callback is present and no other update area to call after the submit, so trigger it. + if (UtilValidate.isEmpty(updateAreas) && jwtCallback != null) { + updateAreas = UtilMisc.toList(jwtCallback); + } + boolean ajaxEnabled = UtilValidate.isNotEmpty(updateAreas) && this.javaScriptEnabled; String ajaxUrl = ""; if (ajaxEnabled) { ajaxUrl = MacroCommonRenderer.createAjaxParamsFromUpdateAreas(updateAreas, null, modelForm, "", context); diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroMenuRenderer.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroMenuRenderer.java index 9613dae..418c9aa 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroMenuRenderer.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroMenuRenderer.java @@ -234,18 +234,19 @@ public class MacroMenuRenderer implements MenuStringRenderer { linkType = WidgetWorker.determineAutoLinkType(link.getLinkType(), target, link.getUrlMode(), request); } parameters.put("linkType", linkType); - String linkUrl = ""; String actionUrl = ""; - StringBuilder targetParameters = new StringBuilder(); - if ("hidden-form".equals(linkType) || "layered-modal".equals(linkType)) { + + boolean isModal = "layered-modal".equals(linkType); + if ("hidden-form".equals(linkType) || isModal) { final URI actionUri = WidgetWorker.buildHyperlinkUri(target, link.getUrlMode(), null, link.getPrefix(context), link.getFullPath(), link.getSecure(), link.getEncode(), request, response); actionUrl = actionUri.toString(); targetParameters.append("["); - for (Map.Entry<String, String> parameter : link.getParameterMap(context).entrySet()) { + // Callback propagation only if displaying a modal + for (Map.Entry<String, String> parameter : link.getParameterMap(context, isModal).entrySet()) { if (targetParameters.length() > 1) { targetParameters.append(","); } @@ -262,10 +263,7 @@ public class MacroMenuRenderer implements MenuStringRenderer { if (targetParameters.length() == 0) { targetParameters.append("\"\""); } - if (UtilValidate.isNotEmpty(target) && !"hidden-form".equals(linkType)) { - linkUrl = MacroCommonRenderer.getLinkUrl(link.getLink(), context); - } - parameters.put("linkUrl", linkUrl); + parameters.put("linkUrl", MacroCommonRenderer.getLinkUrl(link.getLink(), context)); parameters.put("actionUrl", actionUrl); parameters.put("parameterList", targetParameters); String imgStr = ""; diff --git a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroScreenRenderer.java b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroScreenRenderer.java index 5fdb210..f0f91b1 100644 --- a/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroScreenRenderer.java +++ b/framework/widget/src/main/java/org/apache/ofbiz/widget/renderer/macro/MacroScreenRenderer.java @@ -275,7 +275,6 @@ public class MacroScreenRenderer implements ScreenStringRenderer { + UtilMisc.<String>addToBigDecimalInMap(context, "screenUniqueItemIndex", BigDecimal.ONE); String linkType = WidgetWorker.determineAutoLinkType(link.getLinkType(), target, link.getUrlMode(), request); - String linkUrl = ""; String actionUrl = ""; StringBuilder parameters = new StringBuilder(); String width = link.getWidth(); @@ -286,13 +285,15 @@ public class MacroScreenRenderer implements ScreenStringRenderer { if (UtilValidate.isEmpty(height)) { height = String.valueOf(modelTheme.getLinkDefaultLayeredModalHeight()); } - if ("hidden-form".equals(linkType) || "layered-modal".equals(linkType)) { + boolean isModal = "layered-modal".equals(linkType); + if ("hidden-form".equals(linkType) || isModal) { final URI actionUri = WidgetWorker.buildHyperlinkUri(target, link.getUrlMode(), null, link.getPrefix(context), link.getFullPath(), link.getSecure(), link.getEncode(), request, response); actionUrl = actionUri.toString(); parameters.append("["); - for (Map.Entry<String, String> parameter: link.getParameterMap(context).entrySet()) { + // Callback propagation only if displaying a modal + for (Map.Entry<String, String> parameter: link.getParameterMap(context, isModal).entrySet()) { if (parameters.length() > 1) { parameters.append(","); } @@ -309,9 +310,7 @@ public class MacroScreenRenderer implements ScreenStringRenderer { String style = link.getStyle(context); String name = link.getName(context); String text = link.getText(context); - if (UtilValidate.isNotEmpty(target)) { - linkUrl = MacroCommonRenderer.getLinkUrl(link.getLink(), context); - } + String linkUrl = MacroCommonRenderer.getLinkUrl(link.getLink(), context); String imgStr = ""; ModelScreenWidget.ScreenImage img = link.getImage(); if (img != null) {