<?xml version="1.0" encoding="utf-8"?>
<?xml-stylesheet type="text/xsl" href="https://www.proworks.com/blog/rss/xslt"?>
<rss xmlns:a10="http://www.w3.org/2005/Atom" version="2.0">
  <channel>
    <title>ProWorks Web Design, Development, and Umbraco Blog</title>
    <link>https://www.proworks.com/blog/</link>
    <description>ProWorks</description>
    <generator>Articulate, blogging built on Umbraco</generator>
    <item>
      <guid isPermaLink="false">4626</guid>
      <link>https://www.proworks.com/blog/archive/how-to-upgrade-umbraco-version-7-to-version-8/</link>
      <category>upgrade v8</category>
      <title>How to Upgrade Umbraco Version 7 to Version 8</title>
      <description>&lt;p&gt;Do you need an in depth, step-by-step walkthrough of how to deal with Umbraco version upgrades from version 7 to version 8?  Then this is the post for you!&lt;/p&gt;
&lt;p&gt;Over the last year, we have upgraded several of our clients from Umbraco version 7 to Umbraco version 8. With each upgrade we find small surprises that we get to work through.  This post shares what we have learned so far.&lt;/p&gt;
&lt;p&gt;Disclaimer: this post won't go into detail on a lot of the code changes that need to be made. We won't try to list or describe how to write custom Examine indexes in Umbraco 8 or how to convert an ApplicationStarting event handler in Umbraco 7 to Umbraco 8 Composers and Compositions. Instead, this is more of a roadmap to an Umbraco 8 upgrade that focuses on solving problems upgrading the database without losing data.&lt;/p&gt;
&lt;p&gt;Umbraco 8 upgrades are complex and every Umbraco site is different. You will almost certainly have to add your own steps throughout the process and will run into unique challenges, but we think the following steps will get you close.&lt;/p&gt;
&lt;div&gt;
&lt;h2&gt;Things to know before you get started&lt;/h2&gt;
&lt;div&gt;
&lt;h3&gt;What is a Migration?&lt;/h3&gt;
&lt;p&gt;In Umbraco 7.3.9, Umbraco introduced the concept of Migrations. A Migration in Umbraco is a one-off process that is run automatically when the site starts up. Umbraco uses Migrations to apply database changes during Umbraco upgrades. The executions of these migrations are tracked in the database, so Umbraco is able to tell which migrations have already been run.&lt;/p&gt;
&lt;p&gt;Developers can write their own, custom Umbraco Migrations to automate any one-off process. ProWorks uses migrations to help migrate from one datatype to another without data loss. We created an Umbraco 7 package called &lt;a rel="noopener" href="https://bitbucket.org/proworks/our.umbraco.migration/src/master/" target="_blank" aria-label="Our.Umbraco.Migration source code"&gt;Our.Umbraco.Migration&lt;/a&gt; to help developers bootstrap their own migrations into an Umbraco site. It comes with built in migration base classes which convert Content, Media, and Member pickers from id pickers to udi pickers. We also wrote a Skrift article about using Migrations: &lt;a rel="noopener" href="https://skrift.io/issues/umbraco-migrations-made-easy/" target="_blank" aria-label="Skrift Article: Umbraco Migrations Made Easy"&gt;Skrift: Umbraco Migrations Made Easy&lt;/a&gt;&lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Important Umbraco Version Thresholds&lt;/h3&gt;
&lt;p&gt;These are important Umbraco version "thresholds" to be mindful of when upgrading Umbraco sites. Some of these are breaking changes that have bit us in the past. Others are just versions where important features are released.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;When upgrading past Umbraco 7.3.0&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;
&lt;p&gt;Make sure any and all public access settings at "/App_Data/access.config" are present on disk at the time of the upgrade. The public access settings are migrated to the database at this time and if the settings are not present at /App_Data/access.config, you will miss your chance to have all of the public access settings migrated automatically.&lt;/p&gt;
&lt;p&gt;This is where the "umbracoMigrations" table is introduced. From this point forward, Umbraco is better able to handle the database components of Umbraco upgrades. Once an Umbraco site reaches this point, developers can begin to write custom migrations of their own.&lt;/p&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;When upgrading past Umbraco 7.6.0&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;
&lt;p&gt;Umbraco &lt;a rel="noopener" href="https://our.umbraco.com/documentation/reference/querying/Udi" target="_blank" aria-label="Udi Querying"&gt;added Udis to the database&lt;/a&gt; in Umbraco 7.6.0. The primary way to uniquely identify Umbraco nodes changed from the node id to the Udi. New versions of the Content, Media, and Member Picker property editors were created to pick these nodes by Udi instead of node id. At this point, migrations can be written to convert any and id pickers to Udi pickers. The migrations do not need to be added immediately, but this is the earliest that they can be added.&lt;/p&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;When upgrading past Umbraco 7.7.0&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;
&lt;p&gt;Umbraco changed the member role system from being user based to role/group based. The user specific permissions that the content editors are familiar with will be converted to role based permissions. You will notice new "migrated section access" groups. One of these new groups is created for each combination of specific user permissions. This is an important change to inform content editors of.&lt;/p&gt;
&lt;p&gt;Umbraco.NestedContent was added to the Umbraco core. At this point, migrations can be written to convert any and all Our.Umbraco.NestedContent data to the new, core Umbraco.NestedContent. The migrations do not need to be added immediately, but this is the earliest that they can be added.&lt;/p&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;When upgrading past Umbraco 7.14.0&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;
&lt;p&gt;The Umbraco.MultiUrlPicker was added to the Umbraco core. At this point, migrations can be written to convert any and all RJP.MultiUrlPicker data to the new, core Umbraco.MultiUrlPicker. The migrations do not need to be added immediately, but this is the earliest that they can be added.&lt;/p&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;When upgrading past Umbraco 7.15.0&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;
&lt;p&gt;Umbraco released the following fix: &lt;a rel="noopener" href="https://github.com/umbraco/Umbraco-CMS/issues/3869" target="_blank" aria-label="Umbraco Issue 3869"&gt;issues/3869&lt;/a&gt;. The purpose is to handle cases where content editors upload new images to existing media items that are picked in rich text editors. In these cases, the data in the rich text editors would still point to the old media file. This new feature updates the media path at render time using the "data-udi" property on the &amp;lt;img&amp;gt; tag. This is a great feature. However, we have found that some content editors who are more familiar with html will sometimes edit the img src manually. If content editors are in the habit of doing this, when the site is upgraded past Umbraco 7.15.0, the images edited this way could display the wrong file.&lt;/p&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;When upgrading past Umbraco 8.0.0&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;
&lt;p&gt;There is a bug during the Umbraco 8 upgrade that will cause published nodes to become unpublished when those nodes have versions in the database that are saved but not published. A migration must be added to tweak the database and fix each of these unpublished nodes.&lt;/p&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h2&gt;Overview of Upgrade Process&lt;/h2&gt;
&lt;p&gt;This is the birds eye view to all of the steps that go into an Umbraco 7 to Umbraco 8 upgrade. To help conceptualize an Umbraco upgrade, I find it helps to separate the upgrade of the database from the upgrade of the files in my mind. I'll list the upgrade steps for each separately below.&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;
&lt;div&gt;
&lt;h3&gt;Upgrade the Umbraco database&lt;/h3&gt;
&lt;p&gt;Umbraco is getting better and better about supporting upgrades, but some of the earlier v7 upgrades are a still little more rough. When Upgrading to latest v7 and v8, there are some intermediate upgrades that must be completed first. You have to take a pit stop at each of these on your way to the latest and greatest. Below is a list of the intermediate upgrades and a short description of why we need to stop at each of these.&lt;/p&gt;
&lt;p&gt;For each of the "Upgrade Umbraco database" steps below, you can point a vanilla Umbraco site of the new version at the existing Umbraco database and run through the upgrade wizard. This allows you to focus on the database upgrade without spending time moving and merging config files. Step #4 where the custom migrations run is the most complex part of the database upgrade.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;Upgrade the Umbraco database to 7.3.9&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;Umbraco introduces Migrations&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;Upgrade the Umbraco database to 7.6.14&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;Umbraco introduces UDIs. Stop here to prevent errors during the upgrade.&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;Upgrade the Umbraco database to 7.15.x (latest v7)&lt;/strong&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;Run custom v7 Migrations to convert datatypes&lt;/strong&gt;&lt;/div&gt;
&lt;div class="list-item-content"&gt;
&lt;ul&gt;
&lt;li&gt;Node Id Pickers to Udi Pickers&lt;/li&gt;
&lt;li&gt;RJP.MultiUrlPicker (or other link picker) to Umbraco.MultiUrlPicker&lt;/li&gt;
&lt;li&gt;Our.Umbraco.NestedContent to Umbraco.NestedContent&lt;/li&gt;
&lt;li&gt;Our.Umbraco.StackedContent to Umbraco.BlockList&lt;/li&gt;
&lt;li&gt;Other datatypes that might need migration&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Upgrade the Umbraco database to the latest v8 with the ProWorks.Umbraco8.Migrations package&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;
&lt;div class="list-item-title"&gt;&lt;strong&gt;Run custom v8 Migrations as needed&lt;/strong&gt;&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h3&gt;Upgrade the files&lt;/h3&gt;
&lt;p&gt;This upgrade of the files can usually happen after the Umbraco database upgrade to v8 complete.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Fix any custom code, so the site compiles. This includes an upgrade of the project to .NET Framework 4.7.2&lt;/li&gt;
&lt;li&gt;Fix the templates&lt;/li&gt;
&lt;li&gt;Deal with packages and extensions. Update/replace packages with v8 equivalents or remove them&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h2&gt;Step By Step&lt;/h2&gt;
&lt;p&gt;Here it is. This is probably what everyone really wants to see. This is a step by step process to upgrading an Umbraco 7 site to an Umbraco 8 site.&lt;/p&gt;
&lt;div&gt;
&lt;h3&gt;Step 1: Upgrade the Umbraco database to 7.3.9&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel="noopener" href="https://our.umbraco.com/download/releases/739" target="_blank" aria-label="Umbraco 7.3.9 release"&gt;Download a vanilla Umbraco 7.3.9&lt;/a&gt; site&lt;/li&gt;
&lt;li&gt;Ensure that any public access data in your "/App_Data/access.config" is in place on the vanilla 7.3.9 site&lt;/li&gt;
&lt;li&gt;Point the vanilla 7.3.9 site at the Umbraco database you want to upgrade&lt;/li&gt;
&lt;li&gt;Run through the upgrade wizard&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 2: Upgrade the Umbraco database to 7.6.14&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel="noopener" href="https://our.umbraco.com/download/releases/7614" target="_blank" aria-label="Umbraco 7.6.14 release"&gt;Download a vanilla Umbraco 7.6.14&lt;/a&gt; site&lt;/li&gt;
&lt;li&gt;Point the vanilla 7.6.14 site at the Umbraco database you want to upgrade&lt;/li&gt;
&lt;li&gt;Run through the upgrade wizard&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 3: Upgrade the Umbraco database to 7.15.6 (or latest)&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel="noopener" href="https://our.umbraco.com/download/releases/7156" target="_blank" aria-label="Umbraco 7.15.6 release"&gt;Download a vanilla Umbraco 7.15.6&lt;/a&gt; site&lt;/li&gt;
&lt;li&gt;Point the vanilla 7.15.6 site at the Umbraco database you want to upgrade&lt;/li&gt;
&lt;li&gt;Run through the upgrade wizard&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 4: Run v7 migrations to convert node id pickers to Udi pickers&lt;/h3&gt;
&lt;p&gt;Prior to Umbraco 7.6.0, the node pickers (Content Picker, Media Picker, Member Picker, Related Links, and Multinode Treepicker) all picked nodes by node id. New versions of these pickers that picked by udi have been introduced and before upgrading to Umbraco 8, all of the datatypes should be migrated to the new property editors and the data in the database should be converted to avoid data loss. ProWorks has written migrations to handle the following datatype conversions already:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Umbraco.RelatedLinks to Umbraco.RelatedLinks2&lt;/li&gt;
&lt;li&gt;Umbraco.MultiNodeTreePicker to Umbraco.MultiNodeTreePicker2&lt;/li&gt;
&lt;li&gt;Umbraco.MultipleMediaPicker to Umbraco.MediaPicker2&lt;/li&gt;
&lt;li&gt;Umbraco.ContentPicker to Umbraco.ContentPicker2&lt;/li&gt;
&lt;li&gt;Umbraco.MediaPicker to Umbraco.MediaPicker2&lt;/li&gt;
&lt;li&gt;Umbraco.MemberPicker to Umbraco.MemberPicker2&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;We perform all of the above datatype migrations using the Our.Umbraco.Migrations package we created. To perform the above migrations using the Our.Umbraco.Migrations package follow these steps:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Install the &lt;a rel="noopener" href="https://www.nuget.org/packages/Our.Umbraco.Migration/" target="_blank" aria-label="Nuget Our.Umbraco.Migrations"&gt;Our.Umbraco.Migrations&lt;/a&gt; package via nuget&lt;/li&gt;
&lt;li&gt;Add the following to the web.config
&lt;pre&gt;&amp;lt;configuration&amp;gt;
  &amp;lt;migrationResolvers&amp;gt;
    &amp;lt;add name="ProductMigrations" type="Our.Umbraco.Migration.ProductMigrationResolver, Our.Umbraco.Migration"&amp;gt;
    &amp;lt;add key="MonitoredProductNames" value="ProWorks.Default.IdToUdi" /&amp;gt;
    &amp;lt;/add&amp;gt;
  &amp;lt;/migrationResolvers&amp;gt;
&amp;lt;/configuration&amp;gt;&lt;/pre&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 5: Run v7 migration to convert link pickers to the Umbraco.MultiUrlPicker&lt;/h3&gt;
&lt;p&gt;In all of our Umbraco 7 sites, we installed and made use of the RJP.MultiUrlPicker package for our link pickers. In Umbraco 7.14.0, Umbraco pulled it into the core. If your site uses the RJP.MultiUrlPicker property editor, it will need to be converted to the Umbraco.MultiUrlPicker before you upgrade to Umbraco 8. There is no migration required. The values picked in the database are similar enough. You just need to locate the datatypes and select the new Umbraco.MultiUrlPicker property editor.&lt;/p&gt;
&lt;p&gt;If your site makes use of a different 3rd party link picker. You should check to see if that link picker is supported in Umbraco 8. If not, consider writing a migration to convert the datatypes and data to the Umbraco.MultiUrlPicker.&lt;/p&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 6: Convert Our.Umbraco.NestedContent to Umbraco.NestedContent&lt;/h3&gt;
&lt;p&gt;In Umbraco 7.7.0, Umbraco pulled the 3rd party Our.Umbraco.NestedContent property editor into the core. If your site uses the Our.Umbraco.NestedContent property editor, it will need to be converted to the Umbraco.NestedContent property editor before you upgrade to Umbraco 8. There is no migration required. The values picked in the database are similar enough. You just need to locate the datatypes and select the new Umbraco.NestedContent property editor.&lt;/p&gt;
&lt;p&gt;If your site makes use of any other similar packages like Our.Umbraco.StackedContent, consider writing a migration to convert the datatypes and data to the Umbraco.NestedContent. In Umbraco 8, a new property editor called the Block List Editor was created. You could also wait until Umbraco 8 and attempt to migrate your data to the Block List Editor.&lt;/p&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 7: Upgrade the Umbraco database to the latest version of Umbraco 8&lt;/h3&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel="noopener" href="https://our.umbraco.com/download/releases/" target="_blank" aria-label="Umbraco Releases"&gt;Download a vanilla Umbraco 8 latest&lt;/a&gt; site&lt;/li&gt;
&lt;li&gt;Use NuGet to add the &lt;a href="https://www.nuget.org/packages/ProWorks.Umbraco8.Migrations"&gt;ProWorks.Umbraco8.Migrations&lt;/a&gt; package to the site&lt;/li&gt;
&lt;li&gt;Point the site at the Umbraco database you want to upgrade&lt;/li&gt;
&lt;li&gt;Start the site, and run through the upgrade wizard&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 9: Nuget install Umbraco 8.x.x (latest) into your project&lt;/h3&gt;
&lt;p&gt;See the following nuget packages:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a rel="noopener" href="https://www.nuget.org/packages/UmbracoCms/" target="_blank" aria-label="Nuget UmbracoCms"&gt;UmbracoCms&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a rel="noopener" href="https://www.nuget.org/packages/UmbracoCms.Core/" target="_blank" aria-label="Nuget UmbracoCms.Core"&gt;UmbracoCms.Core&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 10: Upgrade the projects to .NET Framework 4.7.2&lt;br /&gt;&lt;br /&gt;&lt;/h3&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 11: Convert Umbraco 7 code to Umbraco 8 so that the site compiles&lt;/h3&gt;
&lt;p&gt;In Umbraco 7, when you log errors you might make a call that looks like the following with the exception as the final argument of the method.&lt;/p&gt;
&lt;pre&gt;Logger.Error("Oops", ex);&lt;/pre&gt;
&lt;p&gt;In Umbraco 8, when you log an error, the exception is the first argument. If you don't fix this, it won't throw any exceptions. It will just ruin your logs.&lt;/p&gt;
&lt;pre&gt;Logger.Error(ex, "Oops");&lt;/pre&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 12: Convert Umbraco 7 Views, Partial Views, and Macros to Umbraco 8&lt;/h3&gt;
&lt;p&gt;I won't go into detail here. See the &lt;a rel="noopener" href="https://our.umbraco.com/documentation/getting-started/setup/upgrading/migrating-to-v8" target="_blank" aria-label="Rendering Content in Umbraco 8"&gt;Umbraco 8 documentation on rendering content&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;I found a small breaking change with the ".Siblings()" method that I hadn't seen documented elsewhere, so I'm describing that here. In Umbraco 7, calling ".Siblings()" would retrieve a list of sibling nodes including self. In Umbraco 8, if you want the same effect, call ".SiblingsAndSelf()".&lt;/p&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 13: Deal with packages and extensions. Update/replace packages with v8 equivalents or remove them&lt;br /&gt;&lt;br /&gt;&lt;/h3&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;h3&gt;Step 14: Add custom v8 migrations as needed&lt;/h3&gt;
&lt;/div&gt;
&lt;div&gt;
&lt;p&gt;You may encounter other issues not covered here with custom components and controls.  You, or the package developer, may need to create custom migrations to convert the database content from the v7 version to their v8 version.  You can see an example of how to do this in the &lt;a rel="noopener" href="https://bitbucket.org/proworks/proworks.umbraco8.migrations/src/master/" target="_blank" aria-label="Source code for ProWorks.Umbraco8.Migrations"&gt;source code for the ProWorks.Umbraco8.Migrations package&lt;/a&gt;. In particular, take a look at the ProWorksMigrationComponent and ProWorksMigrationPlan classes for examples of how to register and trigger your custom migrations.&lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt;Let us know in the comments if you have any questions or if we need to clear anything up!&lt;/p&gt;
&lt;/div&gt;
&lt;/div&gt;</description>
      <pubDate>Tue, 02 Feb 2021 12:00:00 Z</pubDate>
      <a10:updated>2021-02-02T12:00:00Z</a10:updated>
    </item>
    <item>
      <guid isPermaLink="false">4594</guid>
      <link>https://www.proworks.com/blog/archive/umbraco-query-benchmarking-round-1/</link>
      <category>umbraco</category>
      <category>benchmarking</category>
      <title>Umbraco Query Benchmarking Round 1</title>
      <description>&lt;p&gt;We did a presentation on some anti-patterns we've seen used in umbraco sites. These are both sites that we've created and sites that we've inherited. I've converted the powerpoint into a PDF that you can look at if you are curious. &lt;a href="/umbraco/.pdf /media/1011/anti-patterns-presentation-uwest17.pdf"&gt;Umbraco Anti-Patterns&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;One of the most interesting part of the presentation, to me, was the part where we did a little bit of light benchmarking of some of the ways that you can query umbraco for data. I wanted to post more background information about the data in our presentation and how we did our benchmarking, so everyone can have more context for that part of our presentation. The explanation below includes more research that we were able to do after uWestFest '17. I think it paints a more accurate picture.&lt;/p&gt;
&lt;p&gt;All of the testing I did was from a website running on my laptop. The website had 13403 published nodes. 415 of those nodes were BlogArticles that I would query for in all of the ways that I could think of. For each type of query, I would follow these steps:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;I would put two copies of the query one after the other on an empty home page of the site.&lt;/li&gt;
&lt;li&gt;I would recycle the application pool.&lt;/li&gt;
&lt;li&gt;I would load the page initially (the first load after App Startup)&lt;/li&gt;
&lt;li&gt;I would load the page 4 more additional times without an app pool recycle&lt;/li&gt;
&lt;li&gt;I would check the logs for the timings and record them&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;What I was able to see was some info about how these queries performed the first time they were run after an app pool recycle AND how they would run on subsequent requests. I've included a screenshot of the data that I recorded and a zip of a bunch of the files I was using to do the benchmarking. The zip includes a couple of small files that helped me log my results to a separate log file and a view where I actually did all the querying:/Views/QueryBenchmarkPage.cshtml.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="https://www.proworks.com/blog/media/1008/query_benchmarking_table.png" title="query_benchmarking_table.png"&gt;Benchmarking Table Screenshot&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.proworks.com/blog/media/1009/querybenchmarker.zip"&gt;Benchmarking Files&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The first thing I noticed is that both the Examine and the UmbracoHelper Linq queries take a really long time the first time they are run. After that, they speed up quite a bit and even begin to perform a little faster than the UmbracoHelper XPath queries, but I'd like to know exactly what is happening to cause the slow first load of all of the data. It would be interesting to run these tests on a much larger site. I hope to blog again with more learnings.&lt;/p&gt;</description>
      <pubDate>Sun, 19 Mar 2017 16:21:44 Z</pubDate>
      <a10:updated>2017-03-19T16:21:44Z</a10:updated>
    </item>
    <item>
      <guid isPermaLink="false">4494</guid>
      <link>https://www.proworks.com/blog/archive/uwestfest-automated-deployment-talk/</link>
      <title>uWestFest Automated Deployment Talk</title>
      <description>&lt;p&gt;I was fortunate enough to attend the 2016 uWestFest, Umbraco conference in San Diego, California a couple of weeks ago. The highlight was definitely the people, but the sessions were really interesting as well. My only conference regret is that I couldn't see them all.&lt;/p&gt;
&lt;p&gt;I was able to present at my own session this year and I talked about "Automated Deployment with Umbraco". We've been investing a lot over the past couple of years in tuning our deployment strategies, and it has made a world of difference. My goal was to spread the good news of TeamCity and Octopus Deploy to any interested Umbraco users.&lt;/p&gt;
&lt;p&gt;I'v included &lt;a href="https://www.proworks.com/blog/media/1017/automateddeployment.pdf"&gt;a link to the slides&lt;/a&gt;, but the big takeaways are:&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;1. It isn't very hard.&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;I'm a web developer. I know my way around IIS, but I wouldn't call myself an IT guy or a server guy by any stretch of the imagination. Even so, I am able to get TeamCity and Octopus Deploy installed without a lot of pain. In the past, I HAVE run into pain getting things all connected to each other when I use TeamCity as a stand-alone tool, but Octopus Deploy handles a lot of those problems for me.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;2. It enforces good practices&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Before we started using TeamCity, being on-boarded to an existing project was always painful. I'd check out the latest code from source control and, more often than not, it wouldn't build. I'd need to add some special config changes or make sure such and such a file as dropped into the bin. When you set up automated deployment, you all of a sudden have a dumb computer attempting to build and deploy your code on a daily basis. It REQUIRES that your project is set up to be easy to build and run. Amazing.&lt;/p&gt;
&lt;p&gt;Automated deployment also requires developers and designers to be more conscious of the way they work with branches in source control. Because your deployment server doesn't exercise common sense, you will be forced to set up branching structures that are clear and purposeful.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;3. It improves site stability&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;You no longer need to worry about missing a file when you deploy code. All of the code is automatically deployed in a consistent and dependable way.&lt;/p&gt;</description>
      <pubDate>Sun, 20 Mar 2016 16:13:59 Z</pubDate>
      <a10:updated>2016-03-20T16:13:59Z</a10:updated>
    </item>
    <item>
      <guid isPermaLink="false">4503</guid>
      <link>https://www.proworks.com/blog/archive/teamcity-and-web-deploy-silent-unlogged-failure/</link>
      <title>TeamCity and Web Deploy: Silent unlogged failure</title>
      <description>&lt;p&gt;&lt;strong&gt;C:\TeamCity\buildAgent\work\7f00d1c4099cfbe0\src\TestSite.Umbraco\TestSite.Umbraco.csproj(3364, 3): error MSB4019: The imported project "C:\Program Files (x86)\MSBuild\Microsoft\VisualStudio\v11.0\WebApplications\Microsoft.WebApplication.targets" was not found. Confirm that the path in the &amp;lt;Import&amp;gt; declaration is correct, and that the file exists on disk.&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;I was setting up a new TeamCity build server the other day and was writing my first Build Configuration for that build server. On my first attempt to deploy code using MSBuild and Web Deploy, I got the error above.&lt;/p&gt;
&lt;p&gt;First, I tried installing the &lt;a rel="noopener noreferrer" href="http://www.microsoft.com/en-in/download/details.aspx?id=40760" target="_blank" title="Microsoft Build Tools 2013"&gt;Microsoft Build Tools 2013&lt;/a&gt; in hopes that the correct target would be installed. This did not help us. After installation, the only directory inside of th C:\Program Files (x86)\MSBuild directory was 12.0. We were still missing the \Microsoft\VisualStudio directories.&lt;/p&gt;
&lt;p&gt;Next, I tried installing the &lt;a rel="noopener noreferrer" href="http://www.microsoft.com/en-us/download/details.aspx?id=30670" target="_blank" title="Microsoft Visual Studio 2012 Shell (Isolated) Redistributable Package"&gt;Microsoft Visual Studio 2012 Shell (Isolated) Redistributable Package&lt;/a&gt;. This resulted in the most confusing problem yet. The error I experienced above went away, but I could not deploy my site via web deploy, and there was no error. I observed that a web deploy was never attempted. There were absolutely no logs that shed any light on what I was experiencing. I did a lot of digging and found out that the visual studio isolated shell does not install the Microsoft.Web.Publishing.targets file. This resulted in MSBuild not knowing that Web Deploy existed. When I would pass /p:DeployOnBuild=True, MSBuild would dismiss it as an invalid argument. This &lt;a rel="noopener noreferrer" href="http://stackoverflow.com/questions/13185897/teamcity-vs-2010-solution-fails-to-deploy-after-converting-to-vs-2012-solution" target="_blank" title="Teamcity: VS 2010 Solution fails to deploy after converting to VS 2012 Solution"&gt;StackOverflow post&lt;/a&gt; is where I found the solution. It presents several options:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Copy the .target files from your local machine to the build server. This works.&lt;/li&gt;
&lt;li&gt;Install the the a full version of Visual Studio 2012 (Visual Studio Express 2012 worked for us).&lt;/li&gt;
&lt;li&gt;Install the Azure SDK. Never tried this, but that stack over flow post said it might work. Has anyone tried it yet?&lt;/li&gt;
&lt;/ol&gt;</description>
      <pubDate>Wed, 09 Jul 2014 14:47:21 Z</pubDate>
      <a10:updated>2014-07-09T14:47:21Z</a10:updated>
    </item>
    <item>
      <guid isPermaLink="false">4519</guid>
      <link>https://www.proworks.com/blog/archive/guide-for-setting-up-teamcity-for-umbraco-development/</link>
      <title>Guide for setting up TeamCity for Umbraco development</title>
      <description>&lt;p&gt;&lt;meta name="generator" content="HTML Tidy for HTML5 (experimental) for Windows https://github.com/w3c/tidy-html5/tree/c63cc39" /&gt;
&lt;title&gt;&lt;/title&gt;
&lt;meta name="generator" content="HTML Tidy for HTML5 (experimental) for Windows https://github.com/w3c/tidy-html5/tree/c63cc39" /&gt;&lt;meta name="generator" content="HTML Tidy for HTML5 (experimental) for Windows https://github.com/w3c/tidy-html5/tree/c63cc39" /&gt;&lt;meta name="generator" content="HTML Tidy for HTML5 (experimental) for Windows https://github.com/w3c/tidy-html5/tree/c63cc39" /&gt;&lt;meta name="generator" content="HTML Tidy for HTML5 (experimental) for Windows https://github.com/w3c/tidy-html5/tree/c63cc39" /&gt;&lt;/p&gt;
&lt;p&gt;TeamCity is an awesome tool for automating builds, deploys, and tests. For each of our projects, we might have many developers/designers working away on a site. We needed a way for our dev site to stay up-to-date without someone having to manually push code. This is why we like TeamCity. We can set TeamCity up to watch our code repositories, automatically publish new changes, and run all sorts of unit tests without anyone lifting a finger.&lt;/p&gt;
&lt;h3&gt;Part 1 - Installing TeamCity on Windows Server&lt;/h3&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;&lt;a target="_blank" title="Download TeamCity" href="http://www.jetbrains.com/teamcity/download/"&gt;Download&lt;/a&gt; the latest TeamCity.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Install it on your build server. This guy has a great &lt;a target="_blank" title="a-step-by-step-guide-to-hosting-teamcity-in-iis-7" href="http://blogs.endjin.com/2010/11/a-step-by-step-guide-to-hosting-teamcity-in-iis-7/"&gt;blog&lt;/a&gt; about it. The process is really straight forward. Some things to keep in mind are that TeamCity and IIS don't play nice together. I've had success installing TeamCity on an isolated server where IIS is not installed. If you do choose to install TeamCity on a server where IIS lives. Definitely don't go with the default port 80 for teamcity. 8080 is a solid choice. Follow the directions on the &lt;a target="_blank" title="a-step-by-step-guide-to-hosting-teamcity-in-iis-7" href="http://blogs.endjin.com/2010/11/a-step-by-step-guide-to-hosting-teamcity-in-iis-7/"&gt;blog&lt;/a&gt; I referenced above. Good luck. It is definitely possible to set up TeamCity side by side with IIS, I just haven't worked through that myself yet. &lt;/p&gt;
&lt;p&gt;During the installation, you will be asked to install a Build Agent. Give it a descriptive name and take note of the port that the Build Agent will be listening on. When you are asked which account the Build Agent Service should run under, select 'SYSTEM account'.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Once TeamCity is installed, you will be prompted to log in. You may want this UI to be accessible from a remote machine. Basically, what you need is an actual domain for your TeamCity UI. Here is how I did it.&lt;/p&gt;
&lt;p&gt;Find the TeamCity directory where TeamCity is installed (likely at C:\TeamCity). Open the \TeamCity\conf\server.xml file.&lt;/p&gt;
&lt;p&gt;Find the &amp;lt;Host&amp;gt; element and add an &amp;lt;Alias&amp;gt; under it like this:&lt;/p&gt;
&lt;p&gt;&amp;lt;Host name="localhost" appBase="webapps" unpackWARs="true" autoDeploy="true"&amp;gt; &lt;br /&gt;&amp;lt;Alias&amp;gt;teamcity.mydomain.com&amp;lt;/Alias&amp;gt;&lt;/p&gt;
&lt;p&gt;You should now be able to add a host file entry to a remote machine like this:&lt;/p&gt;
&lt;p&gt;xxx.xxx.xxx.xxx teamcity.mydomain.com&lt;/p&gt;
&lt;p&gt;Need more &lt;a target="_blank" title="How Do I Modify My Host File?" href="http://www.rackspace.com/knowledge_center/article/how-do-i-modify-my-hosts-file"&gt;instructions&lt;/a&gt; on modifying your host file?&lt;/p&gt;
&lt;p&gt;If you have your teamcity server hosted with Azure, follow these &lt;a target="_blank" title="TeamCity on Azure VM" href="http://www.danmusk.com/setting-up-teamcity-8-on-an-azure-virtual-machine/"&gt;instructions&lt;/a&gt;. There are additional endpoints that need to be configured.&lt;/p&gt;
&lt;p&gt;If you are still having problems, you may need to check your firewall settings.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Useful References:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a target="_blank" title="a-step-by-step-guide-to-hosting-teamcity-in-iis-7" href="http://blogs.endjin.com/2010/11/a-step-by-step-guide-to-hosting-teamcity-in-iis-7/"&gt;http://blogs.endjin.com/2010/11/a-step-by-step-guide-to-hosting-teamcity-in-iis-7/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a target="_blank" title="TeamCity on Azure VM" href="http://www.danmusk.com/setting-up-teamcity-8-on-an-azure-virtual-machine/"&gt;http://www.danmusk.com/setting-up-teamcity-8-on-an-azure-virtual-machine/&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;/p&gt;
&lt;h3&gt;Part 2 - Installing Additional Build Agents&lt;/h3&gt;
&lt;p&gt;In the TeamCity UI, you should see an "Agents" tab on top. This is where you manage all of your Build Agents. If you just installed TeamCity, you should see only one build agent under the "Connected" tab. This is the Build Agent that you installed and configured when you installed TeamCity. The easiest way to install additional build agents is to go into the 'Administration' section and click 'Install Build Agents'. Once you have download the .msi, install it on the server where you want the Build Agent to live.&lt;/p&gt;
&lt;p&gt;You may need to manually configure your new Build Agent. To do this, find the install location of the Build Agent (likely at C:\BuildAgent).&lt;/p&gt;
&lt;p&gt;Open the \BuildAgent\conf\buildAgent.properties. Here, you can modify the name of your build agent as well as point it towards your teamcity server. After modifying the Build Agent this way, you will need to restart the windows service corresponding to that Build Agent for the changes to show up.&lt;/p&gt;
&lt;p&gt;Once you think that your Build Agent is configured correctly you can log back in to your TeamCity UI and navigate to the Agent tab. Click on the Unauthorized tab. From here, you should be able to manually authorize the build agent. I've found some logs to be helpful in this authorization process at \BuildAgent\logs\teamcity-agent.log. By viewing this log file, you can determine if your build agent has run into problems (probably firewall related) or is still in the process of trying to connect to TeamCity.&lt;/p&gt;
&lt;h3&gt;Part 3 - Writing Your First Build Configuration&lt;/h3&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;The first thing we are going to want to do is to create a Sub Project for our Build Configuration. Go to the 'Administration' Section of the TeamCity UI. Click the &amp;lt;Root project&amp;gt;&lt;/p&gt;
&lt;p&gt;Click the "Create subproject" button. Give your subproject a description and a name. We like to create a subproject for each of our clients. For example, ours might be called, "The Business That Builds All The Widgets"&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;At this point, you can create a Build Configuration under your subproject. I usually like to go one level deeper. I might create another subproject called, "Umbraco CMS". I like to do this because I might end up building a separate website for "The Business That Builds All The Widgets". Structure your Sub Projects so that they make sense to you.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Now click "Create build configuration". I'd give it a name like, "Dev" or "Staging".&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Click "VCS settings &amp;gt;&amp;gt;" This is the area where you can let your Build Configuration know about any Source Control repos you might have. Follow the steps. Make sure the VCS is assigned to your build configuration.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Click "Add build step &amp;gt;&amp;gt;". This is where you tell your build agent to do work. Select a runner type. I'm going to choose "MSBuild" for the sake of example. Once you have created a build step, your Build Configuration is considered valid and is created, and you should see a sidebar on the right where you can adjust various aspects of the Build Configuration.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Click "Build Triggers". You use build triggers to trigger builds when a specific action occurs. Add a VCS trigger to trigger a build when new code is checked in to source control.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h3&gt;Part 4 - Using Web Deploy to Deploy to a Remote Server&lt;/h3&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;This is a great &lt;a target="_blank" title="Automating Deployment with Web Deploy" href="http://weblogs.asp.net/scottgu/archive/2010/09/13/automating-deployment-with-microsoft-web-deploy.aspx"&gt;blog&lt;/a&gt; about how to install Web Deploy. The short story is that you can use the Microsoft Web Platform Installer to install the Web Deployment Tool. Remember not to just install Web Deploy 3.5 with the recommended settings. You probably want to do the custom install and make sure that the Management Service Delegation is installed. If you forget, you can change the installation in Control Panel.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Once Web Deploy is installed, make sure that the Web Deployment Agent Service is installed and running.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Now that your web server has the Web Deployment Agent Service running, you can configure TeamCity to use WebDeploy to deploy your site. Go to your Build Configuration and make sure there is a step with a runner type of MSBuild. Add the following Command line parameters:&lt;/p&gt;
&lt;p&gt;/p:VisualStudioVersion=11.0 &lt;br /&gt;/p:Configuration=Release &lt;br /&gt;/p:DeployOnBuild=True &lt;br /&gt;/p:DeployTarget=MSDeployPublish &lt;br /&gt;/p:MsDeployServiceUrl=DevWebServer/MsDeployAgentService &lt;br /&gt;/p:AllowUntrustedCertificate=True &lt;br /&gt;/p:MSDeployPublishMethod=RemoteAgent &lt;br /&gt;/p:CreatePackageOnPublish=True &lt;br /&gt;/p:DeployIisAppPath=MySite &lt;br /&gt;/p:IgnoreDeployManagedRuntimeVersion=True &lt;br /&gt;/p:FilesToIncludeForPublish=AllFilesInProjectFolder &lt;br /&gt;/p:SkipExtraFilesOnServer=True &lt;br /&gt;/p:ExcludeFoldersFromDeployment="App_Data\Logs;App_Data\preview" &lt;br /&gt;/p:IncludeSetAclProviderOnDestination=False &lt;br /&gt;/p:AutoParameterizationWebConfigConnectionStrings=False &lt;br /&gt;/p:AuthType=NTML /p:Username=&lt;/p&gt;
&lt;p&gt;Using "/p:AuthType=NTML /p:Username=" will cause webdeploy to use Windows Authentication. If you want to use an IIS User's username and password, see &lt;span style="text-decoration: underline;"&gt;&lt;a href="http://www.iis.net/learn/publish/troubleshooting-web-deploy/web-deploy-error-codes" title="Web Deploy Error Codes" target="_blank"&gt;this link about Web Deploy Error Codes&lt;/a&gt;&lt;/span&gt; and &lt;a href="http://windows.microsoft.com/en-us/windows/add-user-account-to-group#1TC=windows-7" title="Add Local User To Group" target="_blank"&gt;this documentation about local user groups&lt;/a&gt; or maybe &lt;a href="http://blogs.iis.net/krolson/archive/2009/11/04/using-iis-manager-accounts-for-web-deployment-tool-msdeploy-delegation.aspx" title="Using IIS Manager Accounts for Web Deploy" target="_blank"&gt;this link&lt;/a&gt;. I haven't had any success with the second method yet.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Useful References:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a target="_blank" title="Automating Deployment with Web Deploy" href="http://weblogs.asp.net/scottgu/archive/2010/09/13/automating-deployment-with-microsoft-web-deploy.aspx"&gt;http://weblogs.asp.net/scottgu/archive/2010/09/13/automating-deployment-with-microsoft-web-deploy.aspx &lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a target="_blank" title="TeamCity Deployment Using Windows Authentication" href="http://www.yaplex.com/deployment/teamcity-deployment-using-msbuild-and-web-deploy-using-windows-authentication/"&gt;http://www.yaplex.com/deployment/teamcity-deployment-using-msbuild-and-web-deploy-using-windows-authentication/ &lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a target="_blank" title="You're Doing It Wrong" href="http://www.troyhunt.com/2010/11/you-deploying-it-wrong-teamcity_24.html"&gt;http://www.troyhunt.com/2010/11/you-deploying-it-wrong-teamcity_24.html &lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a target="_blank" title="Web Deploy and NTLM" href="http://forums.iis.net/t/1180199.aspx"&gt;http://forums.iis.net/t/1180199.aspx&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a target="_blank" title="The Right Approach To Web Deployment" href="http://www.asp.net/web-forms/tutorials/deployment/configuring-server-environments-for-web-deployment/choosing-the-right-approach-to-web-deployment"&gt;http://www.asp.net/web-forms/tutorials/deployment/configuring-server-environments-for-web-deployment/choosing-the-right-approach-to-web-deployment&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="http://blogs.iis.net/krolson/archive/2009/11/04/using-iis-manager-accounts-for-web-deployment-tool-msdeploy-delegation.aspx" title="Using IIS Manager Accounts for Web Deploy" target="_blank"&gt;http://blogs.iis.net/krolson/archive/2009/11/04/using-iis-manager-accounts-for-web-deployment-tool-msdeploy-delegation.aspx&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;/p&gt;
&lt;p&gt;If any of this isn't working for you, shoot me a comment. This blog post will probably turn out to be a living document that I will have to update periodically as I find better ways to use TeamCity.&lt;/p&gt;</description>
      <pubDate>Mon, 23 Jun 2014 17:07:17 Z</pubDate>
      <a10:updated>2014-06-23T17:07:17Z</a10:updated>
    </item>
    <item>
      <guid isPermaLink="false">4591</guid>
      <link>https://www.proworks.com/blog/archive/umbraco-602-upgrade-bug-solution/</link>
      <title>Umbraco 6.0.2 upgrade bug solution</title>
      <description>&lt;p&gt;We were developing some sites on umbraco 6.0.1. When version 6.0.2 was released with&lt;br&gt;some great fixes, we went ahead and ran the provided upgrade script on our sites in developement. Everything appeared fine for a few weeks. We had created lots of content and templates as well as modifying doc types.&lt;/p&gt;
&lt;p&gt;We finally noticed a problem when we tried to modify the doc type for our Home page and Event page. We got the following error:&lt;/p&gt;
&lt;p&gt;&lt;span&gt;[InvalidOperationException: Sequence contains more than one matching element]&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span&gt;It turns out that there were some issues with the upgrade script.&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span&gt;&lt;a rel="noopener noreferrer" href="http://umbraco.com/follow-us/blog-archive/2013/3/4/umbraco-602-released.aspx/" target="_blank" title="Umbraco 6.0.2 released"&gt;http://umbraco.com/follow-us/blog-archive/2013/3/4/umbraco-602-released.aspx/&lt;/a&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span&gt;Umbraco has since fixed the problem with that script, and everything is probably fine, but we needed a quick fix for our now damaged site, so that we could resume development. Here's how we did it.&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;span&gt;1. The problem has to do with duplicate tabs or duplicate properties in the database. The tabs can be found in a table called, 'cmsPropertyTypeGroup'. The properties can be found in a table called, 'cmsPropertyType'.&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;First, take a look at the 'cmsPropertyTypeGroup' table. We found that two doc types had duplicated tabs. &lt;/p&gt;
&lt;p&gt;&lt;img style="width: 450.45045045045043px; height:500px;" src="https://www.proworks.com/media/1208/v6_fix_backend_sm_500x555.jpg?width=450.45045045045043&amp;amp;height=500" alt="v6 Backend Fix"&gt;&lt;/p&gt;
&lt;p&gt;The bottom two records were our duplicates. By changing the parentGroupId of both of these records to NULL and renaming the 'text', we were able to fix our broken docTypes. We could now log into our umbraco back-end and modify those two docTypes. Make sure to delete your renamed, duplicate tabs.&lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt;The problem can go farther than just duplicated properties and/or tabs. We found cases where we had properties and tabs deleted. If you try a fix like the one I just presented above, make sure you take a quick look through your doc types for missing properties. Remember, if a tab was deleted, some of your properties will probably be under the 'Generic Property' tab.&lt;/p&gt;</description>
      <pubDate>Sat, 09 Mar 2013 17:17:16 Z</pubDate>
      <a10:updated>2013-03-09T17:17:16Z</a10:updated>
    </item>
    <item>
      <guid isPermaLink="false">4556</guid>
      <link>https://www.proworks.com/blog/archive/umbraco-6-views-partial-views-and-partial-view-macro-files/</link>
      <title>Umbraco 6: Views, Partial Views, and Partial View Macro Files</title>
      <description>&lt;p&gt;Here's some handy info that can help you get started with the switch-over from the Umbraco Masterpages to the new Views.&lt;/p&gt;
&lt;h3&gt;&lt;span style="font-size: 1.17em;"&gt;Check out Umbraco's Cheat Sheet&lt;/span&gt;&lt;/h3&gt;
&lt;p&gt;First of all, check out this nifty &lt;a rel="noopener noreferrer" href="http://our.umbraco.org/documentation/cheatsheets/masterpages2views.pdf" target="_blank" title="Umbraco Masterpages to Views Cheat Sheet"&gt;cheat sheet&lt;/a&gt; from Umbraco. There are a few typos, but it's definitely helpful to have around.&lt;/p&gt;
&lt;p&gt;The @Section should be lowercased. If you uppercase it, it will not work.&lt;/p&gt;
&lt;pre&gt;@Section BodyElement{&lt;br /&gt;    &amp;lt;p&amp;gt;Hello&amp;lt;/p&amp;gt;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@section SidebarElement{&lt;br /&gt;    &amp;lt;p&amp;gt;Hello&amp;lt;/p&amp;gt;&lt;br /&gt;}&lt;/pre&gt;
&lt;p&gt; &lt;/p&gt;
&lt;h3&gt;@RenderSection default content&lt;/h3&gt;
&lt;p&gt;In the old &amp;lt;ContentPlaceholder&amp;gt; syntax, it was really easy to specify the default content of a ContentPlaceHolder:&lt;/p&gt;
&lt;pre&gt;&amp;lt;asp:ContentPlaceHolder Id="innerContent" runat="server"&amp;gt;&lt;br /&gt;    &amp;lt;umbraco:Item field="bodyText" runat="server" /&amp;gt;&lt;br /&gt;&amp;lt;/asp:ContentPlaceHolder&amp;gt;&lt;/pre&gt;
&lt;p&gt;In the new View system, this is a little more tricky.&lt;/p&gt;
&lt;pre&gt;@If(IsSectionDefined("innerContent"))&lt;br /&gt;{&lt;br /&gt;    @RenderSection("innerContent")&lt;br /&gt;}&lt;br /&gt;else&lt;br /&gt;{&lt;br /&gt;    @CurrentPage.bodyText&lt;br /&gt;}&lt;/pre&gt;
&lt;p&gt;You need to be careful with the @RenderSection function. If you call something like&lt;/p&gt;
&lt;pre&gt;@RenderSection("headerScripts")&lt;/pre&gt;
&lt;p&gt;and the child view does not provide a&lt;/p&gt;
&lt;pre&gt;@section headerScripts{&lt;/pre&gt;
&lt;pre&gt;}&lt;/pre&gt;
&lt;p&gt;everything will explode. If you aren't completely certain that every single child view will provide the @section, you should call @RenderSection as follows:&lt;/p&gt;
&lt;pre&gt;@RenderSection("headerScripts", false)&lt;/pre&gt;
&lt;p&gt; &lt;/p&gt;
&lt;h3&gt;Page property default values + recursion&lt;/h3&gt;
&lt;p&gt;We had a situation the other day where a page's heading would be the node's Name in most cases but in some cases needed to be manually specified. In masterpages, we did this:&lt;/p&gt;
&lt;pre&gt;&amp;lt;umbraco:Item field="pageHeader" useIfEmpty="pageName"&amp;gt;&lt;/pre&gt;
&lt;p&gt;Now, we do things like this&lt;/p&gt;
&lt;pre&gt;@Umbraco.Field("pageHeader", "pageName")&lt;/pre&gt;
&lt;p&gt;OR&lt;/p&gt;
&lt;pre&gt;@Umbraco.Field("pageHeader", altFieldAlias: "pageName")&lt;/pre&gt;
&lt;p&gt;You can also set the property to be recursive like so:&lt;/p&gt;
&lt;pre&gt;@Umbraco.Field("pageHeader", recursive: true)&lt;/pre&gt;
&lt;h3&gt;Handling Partial Views&lt;/h3&gt;
&lt;p&gt;For those of you new to the MVC way of things, here's a really basic example of partial views:&lt;/p&gt;
&lt;p&gt;In one of your Views, you might call:&lt;/p&gt;
&lt;pre&gt;@Html.Action("RenderTestForm", "TestSurface")&lt;/pre&gt;
&lt;p&gt;This calls the RenderTestForm method of a TestSurfaceController that I wrote. Let's take a look at that SurfaceController.&lt;/p&gt;
&lt;pre&gt;[ChildActionOnly]&lt;br /&gt;public ActionResult RenderTestForm()&lt;br /&gt;{&lt;br /&gt;    return PartialView("TestForm", new Models.TestViewModel());&lt;br /&gt;}&lt;/pre&gt;
&lt;p&gt;That method renders the PartialView called TestForm. Let's take a look at TestForm:&lt;/p&gt;
&lt;pre&gt;&lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nx"&gt;model&lt;/span&gt; &lt;span class="nx"&gt;TestProject.Models.TestViewModel&lt;/span&gt;&lt;br /&gt;&lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nx"&gt;using&lt;/span&gt; &lt;span class="nx"&gt;TestProject.Controllers.SurfaceControllers&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;&lt;/pre&gt;
&lt;pre&gt;@using (Html.BeginUmbracoForm&amp;lt;TestSurfaceController&amp;gt;("HandleTestActions", new { returnNodeId = 1146 }))&lt;br /&gt;{&lt;br /&gt;    &amp;lt;!-- Rendering the test form here --&amp;gt;&lt;/pre&gt;
&lt;pre&gt;&lt;span class="p"&gt;    @&lt;/span&gt;&lt;span class="nx"&gt;Html.TextBoxFor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nx"&gt;model.SomeProperty)&lt;/span&gt;&lt;/pre&gt;
&lt;pre&gt;&lt;br /&gt;    ...&lt;br /&gt;}&lt;/pre&gt;
&lt;p&gt;This PartialView is rendering a form that will be submitted back to the HandleTestActions method of the TestSurfaceController. In this scenario, the TestViewModel is being implicitly passed to the HandleTestActions method. If you want to pass more parameters, you have to do it manually. In the above example, we are passing an additional parameter, returnNodeId. Let's take a look at the TestSurfaceController again.&lt;/p&gt;
&lt;pre&gt;[HttpPost]&lt;br /&gt;public ActionResult HandleTestActions(Models.TestViewModel model, int? returnNodeId)&lt;br /&gt;{&lt;br /&gt;    // doing something interesting here&lt;br /&gt;    ...&lt;br /&gt;	&lt;br /&gt;    // redirect to a Success! page maybe?&lt;br /&gt;    if (returnNodeId != null)&lt;br /&gt;    {&lt;br /&gt;        return RedirectToUmbracoPage(returnNodeId.Value);&lt;br /&gt;    }&lt;br /&gt;    else&lt;br /&gt;    {&lt;br /&gt;        return RedirectToCurrentUmbracoPage();&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;
&lt;p&gt;You can see that the TestViewModel was being passed into the HandleTestActions method as well as the returnNodeId.&lt;/p&gt;
&lt;h3&gt;Partial View Macro Files&lt;/h3&gt;
&lt;p&gt;These are pretty simple. With Partial View Macro Files, we can wrap our PartialView in a Macro. What usually happens to me is that I'll write my SurfaceController and my PartialView, but instead of calling it from my View, I'll write a Partial View Macro File and call&lt;/p&gt;
&lt;pre&gt;@Html.Action("RenderTestForm", "TestSurface")&lt;/pre&gt;
&lt;p&gt;from there. Now I can do things like put parameters inside of my macro or even call the partial view from within a richTextEditor if I so desire.&lt;/p&gt;</description>
      <pubDate>Wed, 20 Feb 2013 12:19:04 Z</pubDate>
      <a10:updated>2013-02-20T12:19:04Z</a10:updated>
    </item>
    <item>
      <guid isPermaLink="false">4492</guid>
      <link>https://www.proworks.com/blog/archive/umbraco-6-whats-new/</link>
      <title>Umbraco 6: What's new?</title>
      <description>&lt;p&gt; &lt;/p&gt;
&lt;p&gt;I just got back from the Umbraco Masterclass in Seattle. I'm now a Level 2 certified Umbraco developer. Yay! During the training, we covered everything from the basics (e.g. What's a doctype?) to some more advanced concepts involving the new and improved Umbraco API. The best part was that this training was conducted entirely on Umbraco 6.&lt;/p&gt;
&lt;h1&gt;What's new in Umbraco 6?&lt;/h1&gt;
&lt;ul&gt;
&lt;li&gt;PetaPoco ORM&lt;/li&gt;
&lt;li&gt;Content and Media APIs revamped&lt;/li&gt;
&lt;li&gt;MVC&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;PetaPoco&lt;/h2&gt;
&lt;p&gt;I wont go into a lot of detail on PetaPoco. This is mostly because we didn't go into detail during the training. The long story short is that PetaPoco is lightweight and fast. The introduction of PetaPoco into Umbraco's data layer has definitely helped Umbraco in the ways of consistency.&lt;/p&gt;
&lt;h2&gt;Umbraco API revamped&lt;/h2&gt;
&lt;p&gt;The good news is that Umbraco's Content and Media APIs have been revamped into something simple, coherent, and consistent. The bad news is that we have to wait for the other APIs to catch up. Here are a couple of examples:&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;New Content API&lt;/strong&gt;:&lt;/p&gt;
&lt;pre&gt;var cs = Services.ContentServices;&lt;br /&gt;&lt;em&gt;var parentNodeId = UmbracoContext.PageId.Value;&lt;/em&gt;&lt;br /&gt;&lt;em&gt;var content = cs.CreateContent("Name", parentNodeId, "NodeTypeAlias");&lt;/em&gt;&lt;br /&gt;&lt;br /&gt;&lt;em&gt;content.SetValue("bodyText", model.Body);&lt;/em&gt;&lt;br /&gt;&lt;em&gt;content.SetValue("memberId", Member.CurrentMemberId());&lt;/em&gt;&lt;br /&gt;&lt;em&gt;content.SetValue("Synopsis", model.Synopsis);&lt;/em&gt;&lt;br /&gt;&lt;br /&gt;&lt;em&gt;cs.SaveAndPublish(content);&lt;/em&gt;&lt;/pre&gt;
&lt;p&gt;&lt;strong&gt;N&lt;/strong&gt;ew Media API:&lt;/p&gt;
&lt;pre&gt;var ms = Services.MediaService;&lt;br /&gt;var parentFolder = ms.GetById(1173);&lt;br /&gt;var newFile = ms.CreateMedia(model.FileName, parentFolder.Id, "Image");&lt;br /&gt;&lt;br /&gt;newFile.SetValue("umbracoFile", file);&lt;br /&gt;&lt;br /&gt;ms.Save(attachedFile);&lt;/pre&gt;
&lt;h2&gt;MVC&lt;/h2&gt;
&lt;p&gt;This is the big stuff (and probably the hardest to explain via blog entry). I'll try to keep it understandable.&lt;/p&gt;
&lt;p&gt;First of all, you don't have to use MVC. There's a magic switch you flip in the webconfig, and no one will make you flip it.&lt;/p&gt;
&lt;p&gt;Second, it is definitely possible to convert your existing Umbraco webform sites to MVC. It sounds to me like some packages will soon be released that can do most of this automatically.&lt;/p&gt;
&lt;h3&gt;How does MVC work in Umbraco?&lt;/h3&gt;
&lt;p&gt;In Umbraco MVC, we now have:&lt;/p&gt;
&lt;p&gt;&lt;em&gt;Views&lt;/em&gt;&lt;br /&gt; &lt;em&gt;Partial Views&lt;/em&gt;&lt;br /&gt; &lt;em&gt;Partial View Macro Files&lt;/em&gt;&lt;br /&gt;Models&lt;br /&gt;SurfaceControllers&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Views&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Views are easy. They perform the same function as Templates do in Umbraco webforms. They show up under the &lt;em&gt;Settings-&amp;gt;Templates&lt;/em&gt; folder right alongside the webform Masterpages. Once you flip the switch and move into MVC mode, you will be creating Views by default instead of Masterpages.&lt;/p&gt;
&lt;p&gt;You can actually use masterpages concurrently with Views. They kind of get jumbled together in the &lt;em&gt;Settings-&amp;gt;Templates&lt;/em&gt; folder, and it seems that Umbraco can begin to have a lot of difficulty if you try to name your Views the same as your Masterpages. This renaming issue is especially relevant if you are converting an existing Umbraco webform site to MVC. It seems to me that it's more simple to just go with one or the other.&lt;/p&gt;
&lt;p&gt;There are some definite syntactic differences between the Views and the Masterpages. The following two snippets of code would do the exact same thing:&lt;/p&gt;
&lt;p&gt; &lt;/p&gt;
&lt;pre&gt;&amp;lt;asp:Content ContentPlaceHolderId="BodyElement" runat="server"&amp;gt;
  &amp;lt;asp:ContentPlaceHolder Id="BodyElement" runat="server" /&amp;gt;
&amp;lt;/asp:Content&amp;gt;&lt;br /&gt;
&amp;lt;asp:Content ContentPlaceHolderId="SidebarElement" runat="server"&amp;gt;
  &lt;em&gt;&lt;span class="xml-punctuation"&gt; &amp;lt;&lt;/span&gt;&lt;span class="xml-tagname"&gt;umbraco:Macro&lt;/span&gt;&lt;span class="xml-attribute"&gt; &lt;/span&gt;&lt;span class="xml-attname"&gt;Alias&lt;/span&gt;&lt;span class="xml-punctuation"&gt;=&lt;/span&gt;&lt;span class="xml-attribute"&gt;"Sidebar" &lt;/span&gt;&lt;span class="xml-attname"&gt;runat&lt;/span&gt;&lt;span class="xml-punctuation"&gt;=&lt;/span&gt;&lt;span class="xml-attribute"&gt;"server"&lt;/span&gt;&lt;span class="xml-punctuation"&gt;&amp;gt;&lt;/span&gt;&lt;span class="xml-punctuation"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="xml-tagname"&gt;umbraco:Macro&lt;/span&gt;&lt;span class="xml-punctuation"&gt;&amp;gt;&lt;/span&gt;&lt;/em&gt;
&amp;lt;/asp:Content&amp;gt;&lt;/pre&gt;
&lt;pre&gt;@section BodyElement{&lt;br /&gt;  @RenderSection("BodyElement")&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@section SidebarElement{&lt;br /&gt;  @Umbraco.RenderMacro("Sidebar")&lt;br /&gt;}&lt;/pre&gt;
&lt;p&gt;&lt;span class="xml-punctuation"&gt; &lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Partial Views &amp;amp; Partial View Macro Files&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;The only difference between the Partial Views and the Partial View Macro Files is that the Partial View Macro Files can be wrapped in an Umbraco Macro and, thus, can have Macro Parameters passed to them.&lt;/p&gt;
&lt;p&gt;Both of these are very similar to the old Razor Scripting Files.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Models&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;These are just regular Classes. Nothing super fancy. They just represent entities in the system.&lt;/p&gt;
&lt;p&gt;SurfaceControllers&lt;/p&gt;
&lt;p&gt;These are the heart of Umbraco MVC. SurfaceControllers are just MVC controllers that already have routes set up for them. They are the MVC replacement of a UserControl.&lt;/p&gt;
&lt;p&gt;Instead of writing a UserControl to handle a particular piece of functionality on one of my pages, we could write a SurfaceController paired with some Models and Partial Views.&lt;/p&gt;
&lt;p&gt;Imagine a scenario where you had a form to process. We might write a UserControl that displays this form and processes it. In that case, our Masterpage would have something like this:&lt;/p&gt;
&lt;pre&gt;&lt;em&gt;&lt;span class="xml-punctuation"&gt;&amp;lt;&lt;/span&gt;&lt;span class="xml-tagname"&gt;umbraco:Macro&lt;/span&gt;&lt;span class="xml-attribute"&gt; &lt;/span&gt;&lt;span class="xml-attname"&gt;Alias&lt;/span&gt;&lt;span class="xml-punctuation"&gt;=&lt;/span&gt;&lt;span class="xml-attribute"&gt;"HandleForm" &lt;/span&gt;&lt;span class="xml-attname"&gt;runat&lt;/span&gt;&lt;span class="xml-punctuation"&gt;=&lt;/span&gt;&lt;span class="xml-attribute"&gt;"server"&lt;/span&gt;&lt;span class="xml-punctuation"&gt;&amp;gt;&lt;/span&gt;&lt;span class="xml-punctuation"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="xml-tagname"&gt;umbraco:Macro&lt;/span&gt;&lt;span class="xml-punctuation"&gt;&amp;gt;&lt;/span&gt;&lt;/em&gt;&lt;/pre&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt;If we were to do this MVC style with SurfaceControllers, in our View, we might see this:&lt;/p&gt;
&lt;pre&gt;&lt;em&gt;@Html.Action("RenderForm", "FormSurface")&lt;/em&gt;&lt;/pre&gt;
&lt;p&gt; &lt;/p&gt;
&lt;p&gt;Our SurfaceController would then render the "Form" partial view. The user could fill out the form (represented by a Model) and submit it back to the SurfaceController for processing. &lt;/p&gt;
&lt;p&gt;These SurfaceControllers are the really cool part to me. Imagine a UserControl where the brain is hidden inside of a DLL. It is never wrapped in an Umbraco Macro, but all of the views and partial views are exposed in the Umbraco back-end GUI. As an added bonus, you can tell, immediately, by looking at the &lt;em&gt;@html.Action(...)&lt;/em&gt; which SurfaceController was being referenced and which method was executed.&lt;/p&gt;</description>
      <pubDate>Tue, 05 Feb 2013 18:32:07 Z</pubDate>
      <a10:updated>2013-02-05T18:32:07Z</a10:updated>
    </item>
  </channel>
</rss>