Problem with rule validation - valid on save, invalid on load - rule-engine

While testing the unchanged CodeEffects asp.net core demo application (Editor 5.0.4.8, Engine 5.0.2.6) I've found an interesting problem.
If I create an execution rule that checks for example if FirstName contains two spaces, I can save this rule without a problem, and in SaveRule action it passes the validation using editor.Rule.IsValid. Here is an example of the rule definition:
<if>
<clause>
<condition type="contains" stringComparison="OrdinalIgnoreCase">
<property name="FirstName" />
<value> </value>
</condition>
</clause>
<then>
<method name="Register">
<value>aaaa</value>
</method>
</then>
</if>
But when refreshing the editor and trying to load this saved rule it won't load into editor. The reason is that the LoadRule controller action returns empty json.
While investigating this further it looks that the editor.GetClientRuleData returns null because the rule is invalid. If I check editor.Rule.IsValid just before calling editor.GetClientRuleData I can see it return false and the editor.Rule.InvalidElements holds one element:
{{c:"",h:"v120"}}
The error message would be "The only allowed operators for empty string values are IS and IS NOT" but of course it's not shown in the editor in the demo project as this is not expected to happen.
Not sure if this is in any way related to the problem, but one obvious difference between LoadRule and SaveRule actions is how the rule is loaded.
When saving the rule, the rule data (coming from the UI) is loaded into editor with
editor.LoadClientData(data.Data);
and when loading the rule it's loaded using the xml (from the storage) effectively calling this:
editor.Rule = Rule.Models.RuleModel.Create(ruleXml, typeof(Models.Patient))
So my question is why can invalid rule pass the validation on save, and then the same rule fails the validation on load? Any fix I can try or a workaround?

This issue has been fixed in the latest version of Rule Editor. You need to update Code Effects references from NuGet:
CodeEffects.Rule.Common - 5.0.2.4, CodeEffects.Rule.Editor.Core - 5.0.4.1 (this is the assembly that contains that fix), CodeEffects.Rule.Editor.Web.Core - 5.0.4.8

Related

Struts 2.3 form with multiple submit tags with action attribute

This is something quite simple which worked perfectly with Struts 2.1.x. But we recently upgraded to 2.3.15.2 and it broke. Basically we have a form (actually, many forms) with multiple submits:
<s:form>
<s:submit action="save" />
<s:submit action="resetPassword" />
</s:form>
If I stick the action in the tag all is well. But if instead it is in the tag, I get a 404 error. And it's the same action!
I've been debugging and discovered that when you use the "action" attribute in the tag, the generated html is:
<input type="submit" name="action:save">
<input type="submit" name="action:resetPassword">
Supposedly Struts should take this "action" prefix and say "A-ha! This is an action!" and execute it. And it more or less does this. Or at least tries to. What I've discovered is that at a very low level, the DefaultActionMapper.handleSpecialParameters() method goes through all the parameters and tries to create a ParameterAction for each one, and if it's not null, it is executed. Most of the parameters produce a "null" ParameterAction, but not "action:".
In the docs I found this about ParameterAction:
Defines a parameter action prefix. This is executed when the configured prefix key is
matched in a parameter name, allowing the implementation to manipulate the action mapping
accordingly. For example, if the "action:foo" parameter name was found, and a
ParameterAction implementation was registered to handle the "action" prefix, the execute
method would be called, allowing the implementation to set the "method" value on the
ActionMapping
So what it does is set the mapping's result to a new ServletDispatcherResult with the name of the Action:
mapping.setResult(new ServletDispatcherResult(actionName));
On the other hand, when the action is specified in the s:form tag, the mapping's result is null.
So that when finally we get to Dispatcher.serviceAction():
if (mapping.getResult() != null) {
Result result = mapping.getResult();
result.execute(proxy.getInvocation());
} else {
proxy.execute();
}
So when the action is specified in the tag, proxy.execute() is called, which just calls the Action/method itself. Which is what should happen! But when the action is specified in the tag, since the mapping has a result, the proxy's invocation is passed to result.execute(), which calls ServletDispatcherResult ... and in the end, I get a 404.
This seems like a whole lot of work just to get multiple submit buttons with action attributes working. Is this a known issue for Struts 2.3? Do I need to implement a ParameterAction for the "action" prefix as stated in the docs?
EDIT
Ok, known bug, opened just a few days ago. In the meantime I can either downgrade to 2.3.15.1 or use the "method" attribute rather than the "action" attribute.
Hopefully it will be fixed soon ...
this is b/c in struts2.3.16.
Disables support for action: prefix
by default struts.mapper.action.prefix.enabled = false
set
<constant name="struts.mapper.action.prefix.enabled" value="true"/>
in struts.xml
Internal Changes of struts2-core 2.3.16
The action: and method: prefixes are be by default excluded and changed order to first check excludeParams and then acceptedParams in ParametersInterceptor
This is supposed to be in the process of being fixed for 2.3.15.3.
The specific jira is:
https://issues.apache.org/jira/browse/WW-4204

Orbeon 4.1 custom REST persistence

I have been struggling for over a week with trying to setup a custom ORBEON REST persistence.
I am using the Struts 2 MVC framework with the following configuration:
<action name="/crud/{appName}/{formName}/form/form.xhtml" class="com.example.CrudController" method="executeForm" />
<action name="/crud/{appName}/{formName}/data/{uuid}/data.xml" class="com.example.CrudController" method="executeData" />
<action name="/search/{appName}/{formName}" class="com.example.SearchController" />
The problem is that only the first action is being called.
From the Form Builder, when I click on a form record (say "foo"), this is called:
GET http://localhost:8080/mycontext/app/crud/myapp/library/form/form.xhtml
Notice that, myapp is the correct application name but library is not the correct form name (which should be "foo").
From Form Runner, when I try the "foo" summary or new pages, this is called:
GET http://localhost:8080/mycontext/app/crud/myapp/foo/form/form.xhtml
This time the form name is correct, however I expected a /search/... call instead. Nevertheless I tried responding with either the xform xml or a query result with no success.
The call to /crud/myapp/library/form/form.xhtml is normal: it isn't done by Form Runner to load your form, but to load your app-specific section templates library, which is stored in the reserved library form name. So most likely your implementation of the persistence API should return a 404, since it doesn't have a form myapp/library.
As to the query to /crud/myapp/foo/form/form.xhtml when you access the new page for a myapp/foo, this is just Form Runner loading the form definition for myapp/foo. The query to the search API is only done by the summary page, to list data for a specific form.

Creating a working copy for Plone 4 custom content types

I have created a custom Plone content type in my package i.e. my.product.
I am in need of integrating a working copy support: so that a "published" document (in my case, a published content type) stays online while it is being edited. Basically, I want to take advantage of 'Working Copy Support (Iterate)' provided by plone.app.iterate to achieve what is explained here. This will provide me with ability to check-in/check-out my changes.
Is this possible in Plone 4 with custom content types using Archetypes? How would one go about it if yes?
I added the following two files inside my.product/my/product/profiles/default folder and it appears to work:
diff_tool.xml
<?xml version="1.0"?>
<object>
<difftypes>
<type portal_type="MyCustomType">
<field name="any" difftype="Compound Diff for AT types"/>
</type>
</difftypes>
</object>
repositorytool.xml
<?xml version="1.0"?>
<repositorytool>
<policymap>
<type name="MyCustomType">
<policy name="at_edit_autoversion"/>
<policy name="version_on_revert"/>
</type>
</policymap>
</repositorytool>
I have never used plone.app.iterate, but this is the generic approach how to solve the problem.
Actions are installed by plone.app.iterate GenericSetup profile. You can see actions here:
https://github.com/plone/plone.app.iterate/blob/master/plone/app/iterate/profiles/default/actions.xml
Pay note to the line *available_expr* which tells when to show the action or not. It points to helper view with the conditition.
The view is defined here
https://github.com/plone/plone.app.iterate/blob/master/plone/app/iterate/browser/configure.zcml#L7
The checks that are performed for the content item if it's archiveable
https://github.com/plone/plone.app.iterate/blob/master/plone/app/iterate/browser/control.py#L47
Most likely the failure comes from if not interfaces.IIterateAware.providedBy condition. Your custom contennt must declare this interface. However, you can confirm this putting a pdb breakpoint in checkin_allowed(self) and step it though line-by-line and see what happens with your content type.

Entity Framework: List of invalid characters in Entity Name

I am working on a designer which is very similar to Edmx designer in Visual Studio. I want to add the same validation that Edmx designer applies to Entity and Property Names. Can someone share what are the validation rules i.e. What characters are allowed and what are not. What might be the length of Entity/Property name and other such rules?
Look at the xsds. When loading artifacts (CSDL/MSL/SSDL) there is two step validation 1 - using xsd, 2 internal validation checking additional rules that in most cases cannot be expressed in xsd.
EF6 is open source now but xsd schemas for previous versions have not changed. You can find them here. (Schemas for mapping are in the MappingSpecification folder).
If you look at v3 CSDL schema the name of the property is specified as follows:
<xs:simpleType name="TSimpleIdentifier">
<xs:restriction base="xs:string">
<xs:maxLength value="480" />
<!-- The below pattern represents the allowed identifiers in ECMA specification -->
<xs:pattern value="[\p{L}\p{Nl}][\p{L}\p{Nl}\p{Nd}\p{Mn}\p{Mc}\p{Pc}\p{Cf}]{0,}" />
</xs:restriction>
</xs:simpleType>
If you don't want to bother with xsds and would like to take advantage of the internal validation you can just load your xml to the corresponding item collection. Again in EF6 there have been some overloads added that allows you load artifacts but will not throw an exception if they are invalid but would return null and a list of errors as an out parameter (look for public static factory methods on item collections).

WiX: Preserve on major upgrade, remove on uninstall

I have defined a component to cleanup a generated (not installed) file on uninstall but leave intact on a major upgrade after reading this post
<Component Id="C_RemoveOnUninstall" Guid="XXX">
<RemoveFile Id="DeleteGeneratedFile" Name="ProgramGeneratedFile" On="uninstall"/>
<Condition>REMOVE="ALL" AND NOT UPGRADINGPRODUCTCODE</Condition>
</Component>
With condition above, the file is left behind for both upgrade and uninstall.
Without the condition, the file is deleted for both upgrade and uinstall.
I have tried RemoveFile for each of On="install/uninstall/both" but it does not seem to matter. Have read this post but I am hoping to make component conditions work and avoid writing custom action for this.
Does this code look correct? Any solutions or work around?
This approach assumes the RemoveFiles action ignores an item in the RemoveFile table when the property DirProperty referrers to has a value of null. The property DirProperty referrers to will be set during uninstall though not during an upgrade.
Conditionally set the property:
<SetProperty Id="prop_GeneratedFileDir" Value="[GeneratedFileDir]" After="InstallInitialize" Sequence="execute">
REMOVE="ALL" AND NOT UPGRADINGPRODUCTCODE
</SetProperty>
Define an element for the RemoveFile table:
<Component Id="C_RemoveOnUninstall" Guid="XXX">
<RemoveFile Id="DeleteGeneratedFile" Property="prop_GeneratedFileDir" Name="ProgramGeneratedFile" On="uninstall"/>
<CreateFolder/>
</Component>
Some helpful links:
wix-users, RemoveFile Table, RemoveFile Element, RemoveFolderEx Element