Tags

, , , ,

Depending on whether the user is logged into the application, either an editor or a div containing the data will be displayed. The editor appears like this, during an authenticated session:

Visual Studio’s Solution Explorer lists the available plugins for TinyMCE under /tinymce/plugins. All the options in the following code are included with the free version of TinyMCE.


tinymce.init({
selector: '.test',
plugins: 'table, lists, link',
toolbar: 'table, numlist, bullist, link',
menubar: false,
statusbar: false
});

Adding plugins to the toolbar causes all the default buttons to disappear, as TinyMCE reverts to this if nothing is specified in the init(). Everything must therefore be specified, so the options would be:


plugins: 'table, lists, link',
toolbar: 'undo, redo, styleselect, bold, italic, alignleft, aligncenter, alignright, alignjustify, table, numlist, bullist, indent, outdent, link',

The application needed a tabbed UI that enables switching between the three data fields. Here I have a separate instance of TinyMCE for each tab pane. Initially the tab buttons weren’t showing, so I’ve used Bootstrap.css buttons, and added margin-right‘ attribute to two of them for spacing.

The initial code for the tab content included LINQ statements to fetch in-memory data, and creates an instance of TinyMCE for each pane.

For cases in which you don’t want the user to modify the data using the editor, it’s possible to use
tinymce.activeEditor.setMode(‘readonly’), but it’s more efficient to simply replace the tinymce() call with a div containing a Razor helper to fetch the decoded content from the model.

View-Based Authorisation

If the user doesn’t have permission to modify the data, the ‘Save’ button shouldn’t be displayed. This is a simple matter of adding an ‘if’ statement in the view.


@if (sessionStatus != null && sessionStatus.HasRole("Editor"))
{
Save
}
Close

The above uses our own in-house authentication service, but ASP.NET Core has a native feature that’s similar:


@using Microsoft.AspNetCore.Authorization
@inject IAuthorizationService AuthorizationService

@if ((await AuthorizationService.AuthorizeAsync(User, "PolicyName")).Succeeded)
{

You are authorized.
}
else
{

Go away!

}

Passing Data from TinyMCE to the Entity Framework Model

At first the application refused to save modifications made in the TinyMCE editor. I put a breakpoint at the line:
return Json(new { success = model.Put(_uow), errors = model.errors });

And got the following errors:
'System.Data.Entity.Infrastructure.DbUpdateException' in EntityFramework.dll
and
A potentially dangerous Request.Form value was detected […]

The problem is the model really doesn’t like to accept data posted back as HTML. We have to disable input validation to allow this. For simple projects, we can add the [AllowHtml] attribute to whichever model properties represent data entered in the TinyMCE editor, e.g.


[AllowHtml]
public string ItemDescription { get; set; }

[AllowHtml]
public string ItemSummary [ get; set; }

Apparently, the recommended way is to disable validation at the controller, by giving it the following attributes:

[HttpPost]
[ValidateInput(False)]

I’m not sure why the latter is recommended over the former. As you can probably see, the model attribute is more specific in allowing only HTML for selected items, whereas the controller attribute disables validation entirely for whatever is posted back.