2
\$\begingroup\$

When it comes to the Umbraco CMS, there are components called "Macro-Scripts" which are essentially a Razor View (.cshtml). They allow you to code a bunch of C# and HTML in a page and display this "Macro-Script" on any CMS page that you choose.

In my tutorial (which I completed well over 2 months ago), I thought I remembered reading something about never mixing conditional logic and C# with HTML, and that it's better to use Models and Controllers? I'm a bit confused because we don't really build controllers in the first place for our websites because they are CMS pages and if they need to be anything besides Rich-Text, then we just create a "Macro-Script" and place it on the page which needs extended functionality.

I found that I could save a lot of time if I was able to make my code re-usable across the website, but I'm not really sure how to do that in a way that's "MVC friendly"? The following code is an example "Macro-Script" which displays a form created in the CMS, and then attempts to grab the companies "contact" information and display it underneath the form. The example I've attached is extremely simple, but some of these Macro-Scripts that I've seen become an atrocious mess of 500+ lines with huge for-each loops, switches, and blocks of unreadable code.

I'd like to know the following things:

  1. Is it possible to split this type of code into a Model for use in this View?
  2. Is there any benefit to splitting the code as opposed to having it all in the same view? (I would like to present this to my co-workers and change coding standards if there are enough benefits).
  3. Could someone give me an example of how this would look if it were to be split-up into proper "MVC"?

Macro-Script to grab CMS Form and Company Information

@inherits umbraco.MacroEngines.DynamicNodeContext

@*
    Model = The current page the macro is executed on
            @Model.bodyText

    Parameter = collection of parameter values passed from the macro
            @Paramter.myParam

    Library = utillity library with common methods
            @Library.NodeById(1233)
*@

@* The fun starts here *@

@{
    string formClass = "form-content";
    var configNode = Model.AncestorOrSelf().Descendants("ConfigurationContainer").FirstOrDefault();
    if (configNode != null && configNode.Id > 0)
    {
        formClass = "form-content show-address";
    }
    if (custom.Library.NodeHasPropertyAndValue(Model, "bodyText"))
    {
        <hr />
    }

    <div class="form-page contact-us">
        <div>
            <div class="@formClass">
               @Html.Raw(umbraco.library.RenderMacroContent("<?UMBRACO_MACRO macroAlias=\"umbracoContour.RazorRenderForm\" formGuid=\""+Model.selectedForm+"\" ></?UMBRACO_MACRO>", Model.Id))
            </div>
        @if (configNode != null && configNode.Id > 0)
        {
            <address class="address-content">
                @if (custom.Library.NodeHasPropertyAndValue(configNode, "officeAddress"))
                {
                    var addressDisplay = (custom.Library.NodeHasPropertyAndValue(configNode, "officeAddress2")) ? string.Format("{0}, {1}", configNode.officeAddress, configNode.officeAddress2) : configNode.officeAddress;
                    string locationString = string.Empty;
                    string cityDisplay = (custom.Library.NodeHasPropertyAndValue(configNode, "officeCity")) ? configNode.officeCity : string.Empty,
                    stateDisplay = (custom.Library.NodeHasPropertyAndValue(configNode, "officeState")) ? configNode.officeState : string.Empty,
                    zipDisplay = (custom.Library.NodeHasPropertyAndValue(configNode, "officeZip")) ? configNode.officeZip : string.Empty;
                    if (!string.IsNullOrEmpty(cityDisplay) && !string.IsNullOrEmpty(stateDisplay))
                    {
                        locationString = string.Format("<br />{0}, {1} {2}", cityDisplay, stateDisplay, zipDisplay);
                    }

                    @addressDisplay@Html.Raw(locationString)

                }
                @if (custom.Library.NodeHasPropertyAndValue(configNode, "officePhone"))
                {
                    <br /><i class="fa fa-phone"></i> @configNode.officePhone
                }
                @if (custom.Library.NodeHasPropertyAndValue(configNode, "officeFax"))
                {
                    <br /><i class="fa fa-fax"></i> @configNode.officeFax
                }
                @if (custom.Library.NodeHasPropertyAndValue(configNode, "officeEmail"))
                {
                    <br /><i class="fa fa-envelope"></i> <a href="mailto:@configNode.officeEmail">@configNode.officeEmail</a>
                }
            </address>
        }
        </div>
    </div>

    if (custom.Library.NodeHasPropertyAndValue(Model, "lowerText"))
    {
        @Html.Raw(Model.lowerText)
    }
}
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.