{"id":88737,"date":"2020-10-19T18:30:47","date_gmt":"2020-10-19T18:30:47","guid":{"rendered":"https:\/\/www.red-gate.com\/simple-talk\/?p=88737"},"modified":"2022-04-24T20:27:25","modified_gmt":"2022-04-24T20:27:25","slug":"building-cross-platform-apps-with-net-and-uno","status":"publish","type":"post","link":"https:\/\/www.red-gate.com\/simple-talk\/development\/dotnet-development\/building-cross-platform-apps-with-net-and-uno\/","title":{"rendered":"Building cross-platform apps with .NET and Uno"},"content":{"rendered":"<p>Back in 2016, Microsoft raised the company\u2019s level of confidence in the mobile world with the acquisition of <a href=\"https:\/\/dotnet.microsoft.com\/apps\/xamarin\">Xamari<\/a><a href=\"https:\/\/dotnet.microsoft.com\/apps\/xamarin\">n<\/a>. Xamarin is Microsoft\u2019s open source platform for building Android and iOS apps with .NET and C#.<\/p>\n<p>C# has proven its worth through all these years and brought with it tons of mature projects as well as having a solid community. When it comes to the in-house solutions for mobile development, no one has beaten <a href=\"https:\/\/dotnet.microsoft.com\/apps\/xamarin\/xamarin-forms\">Xamarin.Forms<\/a>. It extends the .NET developer platform to Android, iOS, and, of course, Windows apps. This is all from a single and shared codebase.<\/p>\n<p>However, it\u2019s not the only option out there. Now there is the <a href=\"https:\/\/platform.uno\/\">Uno Platform<\/a>. It offers even more options like targeting all the major platforms (iOS, Android, Windows), as well as native mobiles and web browsers.<\/p>\n<p>The official documentation states:<\/p>\n<p><em>Familiarity and richness of C# and XAML combined with productivity boosts of hot reload, hot restart, edit, and continue and more.<\/em><\/p>\n<p>In addition to those features, Uno also supports WebAssembly, dev loops, automatic responsive designs, and more. You will find a couple of <a href=\"https:\/\/platform.uno\/code-samples\/\">showcases<\/a> on their official website, which you can browse through to learn more about Uno capabilities. However, this article explores the framework via the installation and creation of a simple app that converts a given temperature from Celsius to Fahrenheit and vice-versa. This way, you might experience the platform a bit deeper. So, come with me!<\/p>\n<h2>Install and configure<\/h2>\n<p>First, you need Visual Studio installed. The Community edition is just fine for this example.<\/p>\n<p>You can also develop for Uno <a href=\"https:\/\/platform.uno\/docs\/articles\/get-started.html#vs-code\">with VS Code<\/a>, but this article sticks with Visual Studio since it offers more flexibility and ready-to-use options.<\/p>\n<p>If you have already installed Visual Studio, chances are that you didn\u2019t install at least one of the following workloads:<\/p>\n<ul>\n<li>Universal Windows Platform development<\/li>\n<li>Mobile Development with .NET<\/li>\n<li>ASP.NET and web<\/li>\n<\/ul>\n<p>If that\u2019s the case, no worries. I\u2019ll help you to fix that.<\/p>\n<p>Search for the <em>Visual Studio Installer<\/em> program and run it. Once it pops up, make sure that it has no available updates to install. If it has, just push the update button and wait until it gets finished.<\/p>\n<p>Click the <em>Modify<\/em> button and select the needed workloads, then click the <em>Install<\/em> button.<\/p>\n<p>Then, download the latest version of <a href=\"https:\/\/dotnet.microsoft.com\/download\/dotnet-core\/3.0\">.NET Core<\/a> for your OS, to make sure Uno will have the proper version to work with.<\/p>\n<h3>The Android Studio<\/h3>\n<p>You\u2019ll also need to install the <a href=\"https:\/\/developer.android.com\/studio\">Android Studio<\/a> on your computer. The reason I\u2019m picking only Android to make the tests is that it is OS-agnostic, which means that anyone can run it regardless of if you have a Windows or macOS. However, feel free to go with iOS if you are comfortable enough to work with it.<\/p>\n<p>Go ahead and install it according to the official installation instructions. Just remember that when you start the Android Studio for the first time, it\u2019ll download several required libraries and dependencies, so make sure to start it right after the installation.<\/p>\n<p>Finally, install the Uno extension for Visual Studio. To install it, open your Visual Studio IDE and go to <em>Extensions &gt; Manage Extensions<\/em>, then search for the term <em>uno<\/em>. In the result list, select the option <em>Uno Platform Solution Templates<\/em> and download it.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"1178\" height=\"816\" class=\"wp-image-88738\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-37.png\" \/><\/p>\n<p><strong>Figure 1.<\/strong> Installing Uno extension.<\/p>\n<p>You\u2019ll have to close Visual Studio to get it fully installed since the Uno extension only starts after such action. When the installation finishes, you\u2019ll get a pop-up warning.<\/p>\n<h3>The project setup<\/h3>\n<p>When you start the IDE again, select the option <em>Create a new project<\/em> and, in the next window, once again, search for <em>uno<\/em>.<\/p>\n<p>Select the option called <em>Cross-Platform App (Uno Platform)<\/em> and click <em>Next<\/em>. The window that follows will ask for a project and solution name, as well as the place to store the project (Figure 2).<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"1280\" height=\"850\" class=\"wp-image-88739\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-38.png\" \/><\/p>\n<p><strong>Figure 2.<\/strong> Setting up the new project.<\/p>\n<p>When you do it, depending on the version of the Android you\u2019ve installed, there are some chances that Uno will ask to update the Android SDK. If that happens, just click the <em>Accept<\/em> button as many times as it is prompted and then, click the OK button.<\/p>\n<p>Also, Visual Studio may detect that the Windows SDK is not in the right version. In that case, a window like the one below may appear. Click the <em>Install<\/em> button and make sure to go through the steps until the end.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"674\" height=\"426\" class=\"wp-image-88740\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-39.png\" \/><\/p>\n<p><strong>Figure 3.<\/strong> Updating the platform SDK<\/p>\n<p>After this, Visual Studio will take some time to process the project creation.<\/p>\n<p>One interesting thing to note is the number of auto-created projects on the solution. Take a look at Figure 4.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"445\" height=\"300\" class=\"wp-image-88741\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-40.png\" \/><\/p>\n<p><strong>Figure 4.<\/strong> Auto-generated projects for the Uno solution.<\/p>\n<h3>Testing the project<\/h3>\n<p>To test it out, you just need to click the button <em>Android Emulator<\/em> at the top bar of the IDE:<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"711\" height=\"44\" class=\"wp-image-88742\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-41.png\" \/><\/p>\n<p><strong>Figure 5.<\/strong> Running project on Android Emulator<\/p>\n<p>This will trigger the setup of a new emulator, considering that you have none yet. Just leave things as they are and keep moving on (Figure 6).<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"1122\" height=\"750\" class=\"wp-image-88743\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-42.png\" \/><\/p>\n<p><strong>Figure 6.<\/strong> Creating a new Android device.<\/p>\n<p>Accept the terms and wait until the device\u2019s download finishes. When it\u2019s done, click the <em>Start<\/em> button to start up the emulator.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"1264\" height=\"686\" class=\"wp-image-88744\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-43.png\" \/><\/p>\n<p><strong>Figure 7.<\/strong> Downloaded Android device.<\/p>\n<p>Normally, it takes a while to load since it is a bit heavy. Once it\u2019s done, you should see the screen shown in Figure 8.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"467\" height=\"864\" class=\"wp-image-88745\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-44.png\" \/><\/p>\n<p><strong>Figure 8.<\/strong> Hello World, Uno!<\/p>\n<h3>Fixing up the Uno packages<\/h3>\n<p>There are still some fixes to make. The first one is related to the Uno-related packages update. Right-click your solution and select the <em>Manage NuGet Packages for Solution&#8230;<\/em> option.<\/p>\n<p>Then, go to the <em>Updates<\/em> tab, and you\u2019ll probably see some pending updates to be made as shown in Figure 9.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"1530\" height=\"664\" class=\"wp-image-88746\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-45.png\" \/><\/p>\n<p><strong>Figure 9.<\/strong> Pending update dependencies.<\/p>\n<p>Select all the packages related to Uno and make sure to check the <em>Include prerelease<\/em> option too. Then, click <em>Install<\/em> making sure to mark all the projects of your solution.<\/p>\n<p><em>Attention: be careful not to update all the listed dependencies, but just the ones related to Uno.<\/em><\/p>\n<p>After that, go to the <em>Browse<\/em> tab and search for the <em>Refractored.MvvmHelpers<\/em> package, and install it (Figure 10). It will help with the two-way binding feature for the views and controllers.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"1430\" height=\"628\" class=\"wp-image-88747\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-46.png\" \/><\/p>\n<p><strong>Figure 10.<\/strong> Installing MVVM Helpers package.<\/p>\n<h2>The model<\/h2>\n<p>Models are very important to Uno projects since the framework also adopts the MVVM pattern.<\/p>\n<p>Within the UnoSimpleTalk.Shared project, create a new folder called <em>Models<\/em> as well as a new class called <em>TempItem.cs<\/em> in it. Place the code shown in Listing 1 into the file:<\/p>\n<p><strong>Listing 1. <\/strong>Temp Item model<\/p>\n<pre class=\"lang:c# theme:vs2012 \">using System;\r\nusing MvvmHelpers;\r\nnamespace UnoSimpleTalk.Models\r\n{\r\n    public class TempItem : ObservableObject\r\n    {\r\n        private int id;\r\n        public int Id\r\n        {\r\n            get =&gt; id;\r\n            set =&gt; SetProperty(ref id, value);\r\n        }\r\n        private TempType type;\r\n        public TempType Type\r\n        {\r\n            get =&gt; type;\r\n            set =&gt; SetProperty(ref type, value);\r\n        }\r\n        private double tempValue;\r\n        public double TempValue\r\n        {\r\n            get =&gt; tempValue;\r\n            set =&gt; SetProperty(ref tempValue, value);\r\n        }\r\n        private double convertedValue;\r\n        public double ConvertedValue\r\n        {\r\n            get =&gt; convertedValue;\r\n            set =&gt; SetProperty(ref convertedValue, value);\r\n        }\r\n        private DateTimeOffset createdAt = \r\nDateTimeOffset.Now.ToLocalTime();\r\n        public DateTimeOffset CreatedAt\r\n        {\r\n            get =&gt; createdAt;\r\n            set =&gt; SetProperty(ref createdAt, value);\r\n        }\r\n    }\r\n    public enum TempType\r\n    {\r\n        Celsius, Fahrenheit\r\n    }\r\n}<\/pre>\n<p>Note that the ObservableObject class is imported to help with the auto-binding mentioned earlier. The rest of the model is very simple, with attributes that will bind to the view\u2019s input fields.<\/p>\n<h2><a id=\"post-88737-_heading=h.1t3h5sf\"><\/a>The main page<\/h2>\n<p>The home page\u2019s XAML code and the controller\u2019s C# code is placed in MainPage.xaml.cs.<\/p>\n<p>Start by opening the MainPage.xaml.cs file and substituting its contents by the following:<\/p>\n<p><strong>Listing 2.<\/strong> MainPage.xaml.cs code<\/p>\n<pre class=\"lang:c# theme:vs2012 \">using UnoSimpleTalk.Models;\r\nusing System;\r\nusing System.Collections.Generic;\r\nusing System.IO;\r\nusing System.Linq;\r\nusing System.Runtime.InteropServices.WindowsRuntime;\r\nusing Windows.Foundation;\r\nusing Windows.Foundation.Collections;\r\nusing Windows.UI;\r\nusing Windows.UI.Xaml;\r\nusing Windows.UI.Xaml.Controls;\r\nusing Windows.UI.Xaml.Controls.Primitives;\r\nusing Windows.UI.Xaml.Data;\r\nusing Windows.UI.Xaml.Input;\r\nusing Windows.UI.Xaml.Media;\r\nusing Windows.UI.Xaml.Navigation;\r\n\/\/ The Blank Page item template is documented \r\n\/\/ at http:\/\/go.microsoft.com\/fwlink\/?LinkId=402352&amp;clcid=0x409\r\nnamespace UnoSimpleTalk\r\n{\r\n    \/\/\/ &lt;summary&gt;\r\n    \/\/\/ An empty page that can be used on its own or \r\n    \/\/\/ navigated to within a Frame.\r\n    \/\/\/ &lt;\/summary&gt;\r\n    public sealed partial class MainPage : Page\r\n    {\r\n        public static readonly DependencyProperty ItemProperty = \r\n            DependencyProperty.Register(nameof(Item), typeof(TempItem), \r\n            typeof(MainPage), new PropertyMetadata(default(TempItem)));\r\n        public MainPage()\r\n        {\r\n            Item = new TempItem\r\n            {\r\n                Id = 1,\r\n                Type = TempType.Celsius,\r\n                TempValue = 23,\r\n                CreatedAt = new DateTimeOffset(),\r\n                ConvertedValue = (23 * 1.8) + 32\r\n            };\r\n            this.InitializeComponent();\r\n        }\r\n        public TempItem Item\r\n        {\r\n            get =&gt; (TempItem)GetValue(ItemProperty);\r\n            set =&gt; SetValue(ItemProperty, value);\r\n        }\r\n        public TempType[] TempTypeList =&gt; new[]\r\n        {\r\n            TempType.Celsius,\r\n            TempType.Fahrenheit\r\n        };\r\n        private void Calculate_Temp(object sender, RoutedEventArgs args)\r\n        {\r\n            switch (TempTypeBox.SelectedItem)\r\n            {\r\n                case TempType.Fahrenheit:\r\n                    Item.ConvertedValue = (Item.TempValue * 1.8) + 32;\r\n                    break;\r\n                case TempType.Celsius:\r\n                    Item.ConvertedValue = (Item.TempValue - 32) * 0.5556;\r\n                    break;\r\n            }\r\n        }\r\n        public string FormatTemperature(double temp) =&gt; \r\n                         $\"{Math.Round(temp, 2)}\u00ba\";\r\n    }\r\n}<\/pre>\n<p>Chances are that your code shows some errors, like:<\/p>\n<ul>\n<li><em>App does not contain a definition for InitializeComponent<\/em>. If that happens, just ignore it for a while. Apparently, Uno has a <a href=\"https:\/\/github.com\/unoplatform\/uno\/issues\/318\">bug<\/a> to recognize this method before the first couple of builds. After some runs, and IDE restarts, you\u2019ll see that the error disappears.<\/li>\n<li>It can\u2019t find <em>TempTypeBox<\/em> either. This also happens due to the lack of builds and runs, since VS needs to run the whole codebase first to generate the object links. Don\u2019t worry; it won\u2019t affect the execution on the device.<\/li>\n<\/ul>\n<p>The first line of the class starts with a DependencyProperty object. In Uno, every time you want to make a controller object visible to the views, you need to expose it via this class. The first parameter refers to a name, the second is the property type, the third\u2019s the owner of this object, and the last one relates to the metadata information to construct this object and make it injectable to the views.<\/p>\n<p>Following it, you may find the constructor. It\u2019s nothing special; it just initiates an item object to make sure the view will have something to show right after the startup.<\/p>\n<p>The <code>TempTypeList<\/code> method is important because it provides the list of temperature scales for the combo that\u2019ll be built in a few minutes. The <code>Calculate_Temp<\/code> method is the one which receives the click action to calculate the new temperature based on the form inputs. Finally, the <code>FormatTemperature<\/code> method helps with text formatting. It also rounds up the decimal places of the temperature value, since it is a double number.<\/p>\n<p>Now, open the MainPage.xaml file and place the contents shown in Listing 3.<\/p>\n<p><strong>Listing 3.<\/strong> Mainpage.xaml code<\/p>\n<pre class=\"lang:c# theme:vs2012\">&lt;Page\r\n    x:Class=\"     UnoSimpleTalk.MainPage\"\r\n    xmlns=\"http:\/\/schemas.microsoft.com\/winfx\/2006\/xaml\/presentation\"\r\n    xmlns:x=\"http:\/\/schemas.microsoft.com\/winfx\/2006\/xaml\"\r\n    xmlns:local=\"using:App1\"\r\n    xmlns:d=\"http:\/\/schemas.microsoft.com\/expression\/blend\/2008\"\r\n    xmlns:mc=\"http:\/\/schemas.openxmlformats.org\/markup-compatibility\/2006\"\r\n    mc:Ignorable=\"d\"&gt;\r\n    &lt;Grid Background=\"{ThemeResource ApplicationPageBackgroundThemeBrush}\" RowSpacing=\"8\"&gt;\r\n        &lt;Grid.RowDefinitions&gt;\r\n            &lt;RowDefinition Height=\"Auto\" \/&gt;\r\n            &lt;RowDefinition Height=\"Auto\" \/&gt;\r\n            &lt;RowDefinition Height=\"Auto\" \/&gt;\r\n            &lt;RowDefinition Height=\"Auto\" \/&gt;\r\n            &lt;RowDefinition Height=\"Auto\" \/&gt;\r\n        &lt;\/Grid.RowDefinitions&gt;\r\n        &lt;TextBlock Text=\"Temperature Converter\" \r\n            Grid.Row=\"0\" \r\n            HorizontalTextAlignment=\"Center\"\r\n            HorizontalAlignment=\"Center\"\r\n            \r\n            Margin=\"30\"\r\n            FontWeight=\"Bold\" \r\n            FontSize=\"30\"  \/&gt;\r\n        &lt;TextBox Text=\"{x:Bind Item.TempValue,Mode=TwoWay}\"\r\n             AcceptsReturn=\"True\"\r\n             Grid.Row=\"1\"\r\n             Header=\"Temperature:\"\r\n             Margin=\"10,0\"\r\n             FontSize=\"20\"\r\n             PlaceholderText=\"Enter your temperature here\" \/&gt;\r\n        &lt;ComboBox x:Name=\"TempTypeBox\"\r\n            Header=\"Convert to:\"\r\n            Grid.Row=\"2\"\r\n            FontSize=\"20\"\r\n            Margin=\"10,0\"\r\n            ItemsSource=\"{x:Bind TempTypeList}\"\r\n            SelectedItem=\"{x:Bind Item.Type,Mode=TwoWay}\"\r\n            HorizontalAlignment=\"Stretch\"\r\n            \/&gt;\r\n        &lt;Button Grid.Row=\"3\" Click=\"Calculate_Temp\" Margin=\"10,0\" FontSize=\"20\"&gt;Calculate&lt;\/Button&gt;\r\n        &lt;StackPanel Background=\"LightGray\" Padding=\"20\" Grid.Row=\"4\" Margin=\"10,0\"&gt;\r\n            &lt;TextBlock Text=\"Converted Temperature:\" FontWeight=\"Bold\" FontSize=\"26\"  \/&gt;\r\n            &lt;TextBlock Text=\"{x:Bind FormatTemperature(Item.ConvertedValue),Mode=OneWay}\" FontWeight=\"Bold\" FontSize=\"20\" \/&gt;\r\n        &lt;\/StackPanel&gt;\r\n    &lt;\/Grid&gt;\r\n&lt;\/Page&gt;<\/pre>\n<p>You\u2019re probably going to see a bunch of errors on this file. They happen because of <a href=\"https:\/\/docs.microsoft.com\/en-us\/visualstudio\/ide\/using-intellisense?view=vs-2019\">Intellisense<\/a>, the code-completion tool for XAML pages, is only supported when the UWP head is active. Make sure to select it as shown in Figure 11.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"497\" height=\"206\" class=\"wp-image-88748\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-47.png\" \/><\/p>\n<p><strong>Figure 11.<\/strong> Selecting the UWP head.<\/p>\n<p>If the error persists, try closing the XAML document as well as restarting VS.<\/p>\n<p>Here, it\u2019s being mounted a basic template for the view. Since every screen component must be stacked on top of each other within the Grid tag, you need first to define how this stacking must happen.<\/p>\n<p>The Grid.RowDefinitions tag does exactly this. It sets the blank spaces in which the next components will be placed, one after another. The tags are very intuitive and self-explanatory. It also resembles the HTML tags, if you\u2019re familiar with them.<\/p>\n<p>Special attention goes to the x:Bind spread through the code. This represents the structure Uno uses to inform that there\u2019s an injection going on there.<\/p>\n<p>You also need to specify which binding mode you want:<\/p>\n<ul>\n<li><em>TwoWay<\/em> indicates that the binding happens back and fourthly<\/li>\n<li><em>OneWay<\/em> indicates that it only happens from views to classes<\/li>\n<\/ul>\n<h2>Testing the calculator<\/h2>\n<p>Well, this is it! Now, you can move on to the tests. Just hit the Android start button again, wait for the build to end, and check out the result on the emulator. Figure 12 shows how your app will look:<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"467\" height=\"864\" class=\"wp-image-88749\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-48.png\" \/><\/p>\n<p><strong>Figure 12.<\/strong> Temperature app on the Android device<\/p>\n<p>You can also test it on other devices, like your own Windows (or in a built-in Windows simulator). Just remember that you\u2019ll need to enable the developer mode of your Windows, as shown below.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" width=\"813\" height=\"584\" class=\"wp-image-88750\" src=\"https:\/\/www.red-gate.com\/simple-talk\/wp-content\/uploads\/2020\/10\/word-image-49.png\" \/><\/p>\n<p><strong>Figure 12.<\/strong> Enabling Developer Mode on Windows<\/p>\n<p>Visual Studio will automatically open this configuration window for you when you try to run on this mode.<\/p>\n<h2>Conclusion<\/h2>\n<p>Even though the Uno platform is new compared to other, more mature players, it is very promising and powerful. Its community is growing and embracing more and more members all the time. Make sure to spend some time going over its <a href=\"https:\/\/github.com\/unoplatform\">GitHub repository<\/a> and the <a href=\"https:\/\/platform.uno\/docs\">official docs<\/a>.<\/p>\n<p>As homework, you can increment the sample to add more advanced features from the docs or even incorporate some of the available ones provided by the <a href=\"https:\/\/platform.uno\/code-samples\/\">Uno Platform Code Samples<\/a> page.<\/p>\n<p>&nbsp;<\/p>\n","protected":false},"excerpt":{"rendered":"<p>You can use Xamarin to develop .NET apps to run on iOS or Android instead of Windows. In this article, Julio Sampaio demonstrates the Uno Platform. You can build cross-platform applications using Uno which has even more options.&hellip;<\/p>\n","protected":false},"author":323407,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[143538],"tags":[5134],"coauthors":[93894],"class_list":["post-88737","post","type-post","status-publish","format-standard","hentry","category-dotnet-development","tag-sql-prompt"],"acf":[],"_links":{"self":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/88737","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/users\/323407"}],"replies":[{"embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/comments?post=88737"}],"version-history":[{"count":5,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/88737\/revisions"}],"predecessor-version":[{"id":88755,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/posts\/88737\/revisions\/88755"}],"wp:attachment":[{"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/media?parent=88737"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/categories?post=88737"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/tags?post=88737"},{"taxonomy":"author","embeddable":true,"href":"https:\/\/www.red-gate.com\/simple-talk\/wp-json\/wp\/v2\/coauthors?post=88737"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}