mirror of
https://github.com/OrchardCMS/Orchard.git
synced 2026-02-09 09:16:41 +08:00
Adding DynamicForm activities.
These activities are useful to perform customized form validation.
This commit is contained in:
@@ -0,0 +1,49 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using Orchard.ContentManagement;
|
||||||
|
using Orchard.Localization;
|
||||||
|
using Orchard.Workflows.Models;
|
||||||
|
using Orchard.Workflows.Services;
|
||||||
|
|
||||||
|
namespace Orchard.DynamicForms.Activities {
|
||||||
|
public class AddModelErrorActivity : Task {
|
||||||
|
public AddModelErrorActivity() {
|
||||||
|
T = NullLocalizer.Instance;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Localizer T { get; set; }
|
||||||
|
|
||||||
|
public override string Name {
|
||||||
|
get { return "AddModelError"; }
|
||||||
|
}
|
||||||
|
|
||||||
|
public override LocalizedString Category {
|
||||||
|
get { return T("Forms"); }
|
||||||
|
}
|
||||||
|
|
||||||
|
public override LocalizedString Description {
|
||||||
|
get { return T("Add a model validation error"); }
|
||||||
|
}
|
||||||
|
|
||||||
|
public override string Form {
|
||||||
|
get { return "AddModelError"; }
|
||||||
|
}
|
||||||
|
|
||||||
|
public override IEnumerable<LocalizedString> GetPossibleOutcomes(WorkflowContext workflowContext, ActivityContext activityContext) {
|
||||||
|
return new[] {T("Done")};
|
||||||
|
}
|
||||||
|
|
||||||
|
public override bool CanExecute(WorkflowContext workflowContext, ActivityContext activityContext) {
|
||||||
|
return workflowContext.Tokens.ContainsKey("Updater") && workflowContext.Tokens["Updater"] is IUpdateModel;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override IEnumerable<LocalizedString> Execute(WorkflowContext workflowContext, ActivityContext activityContext) {
|
||||||
|
var key = activityContext.GetState<string>("Key");
|
||||||
|
var message = activityContext.GetState<string>("ErrorMessage");
|
||||||
|
var updater = (IUpdateModel) workflowContext.Tokens["Updater"];
|
||||||
|
|
||||||
|
updater.AddModelError(key, T(message));
|
||||||
|
|
||||||
|
return new[] { T("Done") };
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,58 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using Orchard.DynamicForms.Services.Models;
|
||||||
|
using Orchard.Localization;
|
||||||
|
using Orchard.Workflows.Models;
|
||||||
|
using Orchard.Workflows.Services;
|
||||||
|
|
||||||
|
namespace Orchard.DynamicForms.Activities {
|
||||||
|
public abstract class DynamicFormActivity : Event {
|
||||||
|
protected DynamicFormActivity() {
|
||||||
|
T = NullLocalizer.Instance;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Localizer T { get; set; }
|
||||||
|
|
||||||
|
public override bool CanStartWorkflow {
|
||||||
|
get { return true; }
|
||||||
|
}
|
||||||
|
|
||||||
|
public override bool CanExecute(WorkflowContext workflowContext, ActivityContext activityContext) {
|
||||||
|
var forms = activityContext.GetState<string>("DynamicForms");
|
||||||
|
|
||||||
|
// "" means 'any'.
|
||||||
|
if (String.IsNullOrEmpty(forms)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
var submission = (FormSubmissionTokenContext)workflowContext.Tokens["FormSubmission"];
|
||||||
|
|
||||||
|
if (submission == null) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
var formNames = forms.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
|
||||||
|
return formNames.Any(x => x == submission.Form.Name);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override IEnumerable<LocalizedString> GetPossibleOutcomes(WorkflowContext workflowContext, ActivityContext activityContext) {
|
||||||
|
return new[] { T("Done") };
|
||||||
|
}
|
||||||
|
|
||||||
|
public override IEnumerable<LocalizedString> Execute(WorkflowContext workflowContext, ActivityContext activityContext) {
|
||||||
|
yield return T("Done");
|
||||||
|
}
|
||||||
|
|
||||||
|
public override string Form {
|
||||||
|
get {
|
||||||
|
return "SelectDynamicForms";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public override LocalizedString Category {
|
||||||
|
get { return T("Forms"); }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -1,66 +1,16 @@
|
|||||||
using System;
|
using Orchard.Localization;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using Orchard.DynamicForms.Elements;
|
|
||||||
using Orchard.DynamicForms.Services.Models;
|
|
||||||
using Orchard.Localization;
|
|
||||||
using Orchard.Workflows.Models;
|
|
||||||
using Orchard.Workflows.Services;
|
|
||||||
|
|
||||||
namespace Orchard.DynamicForms.Activities {
|
namespace Orchard.DynamicForms.Activities {
|
||||||
public class DynamicFormSubmittedActivity : Event {
|
public class DynamicFormSubmittedActivity : DynamicFormActivity {
|
||||||
|
|
||||||
public const string EventName = "DynamicFormSubmitted";
|
public const string EventName = "DynamicFormSubmitted";
|
||||||
|
|
||||||
public Localizer T { get; set; }
|
|
||||||
|
|
||||||
public override bool CanStartWorkflow {
|
|
||||||
get { return true; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public override bool CanExecute(WorkflowContext workflowContext, ActivityContext activityContext) {
|
|
||||||
var forms = activityContext.GetState<string>("DynamicForms");
|
|
||||||
|
|
||||||
// "" means 'any'.
|
|
||||||
if (String.IsNullOrEmpty(forms)) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
var submission = (FormSubmissionTokenContext)workflowContext.Tokens["FormSubmission"];
|
|
||||||
|
|
||||||
if (submission == null) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
var formNames = forms.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
|
|
||||||
return formNames.Any(x => x == submission.Form.Name);
|
|
||||||
}
|
|
||||||
|
|
||||||
public override IEnumerable<LocalizedString> GetPossibleOutcomes(WorkflowContext workflowContext, ActivityContext activityContext) {
|
|
||||||
return new[] { T("Done") };
|
|
||||||
}
|
|
||||||
|
|
||||||
public override IEnumerable<LocalizedString> Execute(WorkflowContext workflowContext, ActivityContext activityContext) {
|
|
||||||
yield return T("Done");
|
|
||||||
}
|
|
||||||
|
|
||||||
public override string Form {
|
|
||||||
get {
|
|
||||||
return "SelectDynamicForms";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public override string Name {
|
public override string Name {
|
||||||
get { return EventName; }
|
get { return EventName; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public override LocalizedString Category {
|
|
||||||
get { return T("Forms"); }
|
|
||||||
}
|
|
||||||
|
|
||||||
public override LocalizedString Description {
|
public override LocalizedString Description {
|
||||||
get { return T("A dynamic form is submitted."); }
|
get { return T("A dynamic form is submitted."); }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,54 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using Orchard.DynamicForms.Services.Models;
|
||||||
|
using Orchard.Localization;
|
||||||
|
using Orchard.Scripting.CSharp.Services;
|
||||||
|
using Orchard.Workflows.Models;
|
||||||
|
|
||||||
|
namespace Orchard.DynamicForms.Activities {
|
||||||
|
public class DynamicFormValidatingActivity : DynamicFormActivity {
|
||||||
|
private readonly ICSharpService _csharpService;
|
||||||
|
private readonly IOrchardServices _orchardServices;
|
||||||
|
private readonly IWorkContextAccessor _workContextAccessor;
|
||||||
|
|
||||||
|
public DynamicFormValidatingActivity(ICSharpService csharpService, IOrchardServices orchardServices, IWorkContextAccessor workContextAccessor) {
|
||||||
|
_csharpService = csharpService;
|
||||||
|
_orchardServices = orchardServices;
|
||||||
|
_workContextAccessor = workContextAccessor;
|
||||||
|
}
|
||||||
|
|
||||||
|
public const string EventName = "DynamicFormValidating";
|
||||||
|
|
||||||
|
public override string Name {
|
||||||
|
get { return EventName; }
|
||||||
|
}
|
||||||
|
|
||||||
|
public override LocalizedString Description {
|
||||||
|
get { return T("A dynamic form is being validated."); }
|
||||||
|
}
|
||||||
|
|
||||||
|
public override IEnumerable<LocalizedString> Execute(WorkflowContext workflowContext, ActivityContext activityContext) {
|
||||||
|
var script = activityContext.GetState<string>("Script");
|
||||||
|
|
||||||
|
if (!String.IsNullOrWhiteSpace(script)) {
|
||||||
|
var submission = (FormSubmissionTokenContext) workflowContext.Tokens["FormSubmission"];
|
||||||
|
|
||||||
|
// Start the script with the new token syntax.
|
||||||
|
script = "// #{ }" + System.Environment.NewLine + script;
|
||||||
|
|
||||||
|
if (workflowContext.Content != null)
|
||||||
|
_csharpService.SetParameter("ContentItem", (dynamic) workflowContext.Content.ContentItem);
|
||||||
|
|
||||||
|
_csharpService.SetParameter("Services", _orchardServices);
|
||||||
|
_csharpService.SetParameter("WorkContext", _workContextAccessor.GetContext());
|
||||||
|
_csharpService.SetParameter("Workflow", workflowContext);
|
||||||
|
_csharpService.SetFunction("T", (Func<string, string>) (x => T(x).Text));
|
||||||
|
_csharpService.SetFunction("AddModelError", (Action<string, LocalizedString>) ((key, message) => submission.ModelState.AddModelError(key, message.Text)));
|
||||||
|
|
||||||
|
_csharpService.Run(script);
|
||||||
|
}
|
||||||
|
|
||||||
|
return base.Execute(workflowContext, activityContext);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,28 @@
|
|||||||
|
using Orchard.Forms.Services;
|
||||||
|
|
||||||
|
namespace Orchard.DynamicForms.Forms {
|
||||||
|
public class AddModelErrorForm : Component, IFormProvider {
|
||||||
|
|
||||||
|
public void Describe(DescribeContext context) {
|
||||||
|
context.Form("AddModelError", factory => {
|
||||||
|
var shape = (dynamic)factory;
|
||||||
|
var form = shape.Form(
|
||||||
|
Id: "AddModelError",
|
||||||
|
_Key: shape.Textbox(
|
||||||
|
Id: "key",
|
||||||
|
Name: "Key",
|
||||||
|
Title: "Key",
|
||||||
|
Classes: new[] { "text", "large", "tokenized" },
|
||||||
|
Description: T("The key / form field name for which to add a model validation error.")),
|
||||||
|
_Message: shape.Textbox(
|
||||||
|
Id: "errorMessage",
|
||||||
|
Name: "ErrorMessage",
|
||||||
|
Title: "Error Message",
|
||||||
|
Classes: new[] { "text", "large", "tokenized" },
|
||||||
|
Description: T("The model validation error message to add.")));
|
||||||
|
|
||||||
|
return form;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,21 @@
|
|||||||
|
using Orchard.Forms.Services;
|
||||||
|
|
||||||
|
namespace Orchard.DynamicForms.Forms {
|
||||||
|
public class DynamicFormValidatingForm : Component, IFormProvider {
|
||||||
|
public void Describe(DescribeContext context) {
|
||||||
|
context.Form("DynamicFormValidatingScript", shapeFactory => {
|
||||||
|
var shape = (dynamic) shapeFactory;
|
||||||
|
var form = shape.Form(
|
||||||
|
Id: "DynamicFormValidatingScript",
|
||||||
|
_Script: shape.TextArea(
|
||||||
|
Id: "Script",
|
||||||
|
Name: "Script",
|
||||||
|
Title: T("Script"),
|
||||||
|
Description: T("The script to validate the submitted form. You can use ContentItem, Services, WorkContext, Workflow and T(). Call AddModelError(string key, LocalizedString errorMessage) to add modelstate errors."),
|
||||||
|
Classes: new[] {"tokenized"}));
|
||||||
|
|
||||||
|
return form;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,12 +1,8 @@
|
|||||||
using System;
|
using Orchard.DisplayManagement;
|
||||||
using System.Linq;
|
|
||||||
using System.Web.Mvc;
|
|
||||||
using Orchard.ContentManagement;
|
|
||||||
using Orchard.DisplayManagement;
|
|
||||||
using Orchard.Forms.Services;
|
using Orchard.Forms.Services;
|
||||||
using Orchard.Localization;
|
using Orchard.Localization;
|
||||||
|
|
||||||
namespace Orchard.DynamicForms.Activities {
|
namespace Orchard.DynamicForms.Forms {
|
||||||
public class SelectDynamicForms : IFormProvider {
|
public class SelectDynamicForms : IFormProvider {
|
||||||
protected dynamic Shape { get; set; }
|
protected dynamic Shape { get; set; }
|
||||||
public Localizer T { get; set; }
|
public Localizer T { get; set; }
|
||||||
@@ -0,0 +1,33 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using Orchard.DynamicForms.Activities;
|
||||||
|
using Orchard.DynamicForms.Services;
|
||||||
|
using Orchard.DynamicForms.Services.Models;
|
||||||
|
using Orchard.Layouts.Helpers;
|
||||||
|
using Orchard.Workflows.Services;
|
||||||
|
|
||||||
|
namespace Orchard.DynamicForms.Handlers {
|
||||||
|
public class WorkflowValidatorCoordinator : FormEventHandlerBase {
|
||||||
|
private readonly IWorkflowManager _workflowManager;
|
||||||
|
public WorkflowValidatorCoordinator(IWorkflowManager workflowManager) {
|
||||||
|
_workflowManager = workflowManager;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void Validating(FormValidatingEventContext context) {
|
||||||
|
var form = context.Form;
|
||||||
|
var values = context.Values;
|
||||||
|
var formValuesDictionary = values.ToTokenDictionary();
|
||||||
|
|
||||||
|
var formTokenContext = new FormSubmissionTokenContext {
|
||||||
|
Form = form,
|
||||||
|
ModelState = context.ModelState,
|
||||||
|
PostedValues = values
|
||||||
|
};
|
||||||
|
var tokensData = new Dictionary<string, object>(formValuesDictionary) {
|
||||||
|
{"Updater", context.Updater},
|
||||||
|
{"FormSubmission", formTokenContext},
|
||||||
|
};
|
||||||
|
|
||||||
|
_workflowManager.TriggerEvent(name: DynamicFormValidatingActivity.EventName, target: null, tokensContext: () => tokensData);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -10,7 +10,7 @@ Features:
|
|||||||
Name: Dynamic Forms
|
Name: Dynamic Forms
|
||||||
Description: Create custom forms like contact forms using layouts.
|
Description: Create custom forms like contact forms using layouts.
|
||||||
Category: Forms
|
Category: Forms
|
||||||
Dependencies: Orchard.Layouts, Orchard.Tokens, Orchard.Workflows, Orchard.Users, Orchard.AuditTrail, Common
|
Dependencies: Orchard.Layouts, Orchard.Scripting.CSharp, Orchard.Tokens, Orchard.Workflows, Orchard.Users, Orchard.AuditTrail, Common
|
||||||
Orchard.DynamicForms.AntiSpam:
|
Orchard.DynamicForms.AntiSpam:
|
||||||
Name: Anti-Spam Elements
|
Name: Anti-Spam Elements
|
||||||
Description: Provides anti-spam elements to protect your content from malicious submissions.
|
Description: Provides anti-spam elements to protect your content from malicious submissions.
|
||||||
|
|||||||
@@ -119,6 +119,10 @@
|
|||||||
<Project>{5531e894-d259-45a3-aa61-26dbe720c1ce}</Project>
|
<Project>{5531e894-d259-45a3-aa61-26dbe720c1ce}</Project>
|
||||||
<Name>Orchard.Projections</Name>
|
<Name>Orchard.Projections</Name>
|
||||||
</ProjectReference>
|
</ProjectReference>
|
||||||
|
<ProjectReference Include="..\Orchard.Scripting.CSharp\Orchard.Scripting.CSharp.csproj">
|
||||||
|
<Project>{5d13ef34-8b39-4ec5-847f-e12892acf841}</Project>
|
||||||
|
<Name>Orchard.Scripting.CSharp</Name>
|
||||||
|
</ProjectReference>
|
||||||
<ProjectReference Include="..\Orchard.Taxonomies\Orchard.Taxonomies.csproj">
|
<ProjectReference Include="..\Orchard.Taxonomies\Orchard.Taxonomies.csproj">
|
||||||
<Project>{e649ea64-d213-461b-87f7-d67035801443}</Project>
|
<Project>{e649ea64-d213-461b-87f7-d67035801443}</Project>
|
||||||
<Name>Orchard.Taxonomies</Name>
|
<Name>Orchard.Taxonomies</Name>
|
||||||
@@ -137,8 +141,12 @@
|
|||||||
</ProjectReference>
|
</ProjectReference>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
<Compile Include="Activities\DynamicFormActivity.cs" />
|
||||||
|
<Compile Include="Activities\AddModelErrorActivity.cs" />
|
||||||
|
<Compile Include="Activities\DynamicFormValidatingActivity.cs" />
|
||||||
<Compile Include="Activities\DynamicFormSubmittedActivity.cs" />
|
<Compile Include="Activities\DynamicFormSubmittedActivity.cs" />
|
||||||
<Compile Include="Activities\SelectDynamicForms.cs" />
|
<Compile Include="Forms\AddModelErrorForm.cs" />
|
||||||
|
<Compile Include="Forms\SelectDynamicForms.cs" />
|
||||||
<Compile Include="Bindings\TextFieldBindings.cs" />
|
<Compile Include="Bindings\TextFieldBindings.cs" />
|
||||||
<Compile Include="Bindings\BodyPartBindings.cs" />
|
<Compile Include="Bindings\BodyPartBindings.cs" />
|
||||||
<Compile Include="Bindings\UserPartBindings.cs" />
|
<Compile Include="Bindings\UserPartBindings.cs" />
|
||||||
@@ -157,7 +165,9 @@
|
|||||||
<Compile Include="Elements\ReCaptcha.cs" />
|
<Compile Include="Elements\ReCaptcha.cs" />
|
||||||
<Compile Include="Elements\ValidationMessage.cs" />
|
<Compile Include="Elements\ValidationMessage.cs" />
|
||||||
<Compile Include="Elements\ValidationSummary.cs" />
|
<Compile Include="Elements\ValidationSummary.cs" />
|
||||||
|
<Compile Include="Forms\DynamicFormValidatingForm.cs" />
|
||||||
<Compile Include="Handlers\ClientValidationRegistrationCoordinator.cs" />
|
<Compile Include="Handlers\ClientValidationRegistrationCoordinator.cs" />
|
||||||
|
<Compile Include="Handlers\WorkflowValidatorCoordinator.cs" />
|
||||||
<Compile Include="Services\Models\FormSubmissionTokenContext.cs" />
|
<Compile Include="Services\Models\FormSubmissionTokenContext.cs" />
|
||||||
<Compile Include="Handlers\ValidatorsCoordinator.cs" />
|
<Compile Include="Handlers\ValidatorsCoordinator.cs" />
|
||||||
<Compile Include="Handlers\FormSubmissionCoordinator.cs" />
|
<Compile Include="Handlers\FormSubmissionCoordinator.cs" />
|
||||||
|
|||||||
@@ -269,9 +269,11 @@ namespace Orchard.DynamicForms.Services {
|
|||||||
}
|
}
|
||||||
|
|
||||||
var contentTypeSettings = contentTypeDefinition.Settings.GetModel<ContentTypeSettings>();
|
var contentTypeSettings = contentTypeDefinition.Settings.GetModel<ContentTypeSettings>();
|
||||||
var versionOptions = form.Publication == "Publish" || !contentTypeSettings.Draftable ? VersionOptions.Published : VersionOptions.Draft;
|
_contentManager.Create(contentItem, VersionOptions.Draft);
|
||||||
|
|
||||||
_contentManager.Create(contentItem, versionOptions);
|
if (form.Publication == "Publish" || !contentTypeSettings.Draftable) {
|
||||||
|
_contentManager.Publish(contentItem);
|
||||||
|
}
|
||||||
|
|
||||||
return contentItem;
|
return contentItem;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user