Wednesday, April 29, 2015

Web.config encrypt crib

 
I always seem to forget this.  Here is the short answer

If you are doing a physical path

Encrypt:
aspnet_regiis.exe -pef "connectionStrings" C:\path\to\application
Decrypt:
aspnet_regiis.exe -pdf "connectionStrings" C:\path\to\application
 
 
If you are doing it for a web application
 
 
Encrypt:

aspnet_regiis -pe "connectionStrings" -app "/MyWebsiteApp"
Decrypt:

aspnet_regiis -pd "connectionStrings" -app "/MyWebsiteApp"

Source:
https://msdn.microsoft.com/en-us/library/zhhddkxy(v=vs.140).aspx



Monday, April 27, 2015

MVVMCross Extended Splash Screen Crossplatform (iOS/Android/WP)

Problem:
Trying to get the splash screen of the application to run longer then the default for each platform.  The typical answer I see posted on most sites is to use the default properties for each of the platform projects.  I wanted something I had more control of.  We are using the MVVMCross pattern for the application and so I wanted to put the solution into the PCL for use on all 3 platforms.  This solution creates a View with the splash screen image which can be extended via the timer function.  This allows us to display the image as long or short as we need it.


Solution:
I found several sites with tips and some hints from Stuart Lodge.  I managed to come up with a solution which builds on some code I found over at the Xamarin developer site.  The timer class should be placed in the PCL of your project.  It can then be referenced by your ModelView and this in turn binds to the View.

1.) Timer Class

using System;
using System.Collections.Generic;
using System.Diagnostics.Contracts;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;

namespace iReport.Core
{
 

    /// <summary>
    /// Missing from PCL, except if targeting .NET 4.5.1 + Win8.1 + WP8.1
    /// </summary>
    internal sealed class Timer : CancellationTokenSource
    {
        internal Timer(Action<object> callback, object state, int millisecondsDueTime, int millisecondsPeriod, bool waitForCallbackBeforeNextPeriod = false)
        {
            //Contract.Assert(period == -1, "This stub implementation only supports dueTime.");

            Task.Delay(millisecondsDueTime, Token).ContinueWith(async (t, s) =>
            {
                var tuple = (Tuple<Action<object>, object>)s;

                while (!IsCancellationRequested)
                {
                    if (waitForCallbackBeforeNextPeriod)
                        tuple.Item1(tuple.Item2);
                    else
                        Task.Run(() => tuple.Item1(tuple.Item2));

                    await Task.Delay(millisecondsPeriod, Token).ConfigureAwait(false);
                }

            }, Tuple.Create(callback, state), CancellationToken.None, TaskContinuationOptions.ExecuteSynchronously | TaskContinuationOptions.OnlyOnRanToCompletion, TaskScheduler.Default);
        }

        protected override void Dispose(bool disposing)
        {
            if (disposing)
                Cancel();

            base.Dispose(disposing);
        }
    }


}

2.)Model View

using Cirrious.MvvmCross.ViewModels;
using iReport.Core.Services.Collections;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Input;


namespace iReport.Core.ViewModels
{
    public class TimerViewModel : MvxViewModel
    {
        private DateTime? _whenToFinish;
        private Timer _timer;
        public TimerViewModel()
        {
                    _timer = new Timer(OnTick, null, 1000, 1000);
                    _whenToFinish = DateTime.UtcNow.AddSeconds(3);
        }

        #region Timer Test
            private void OnTick(object state)
            {
                if (!_whenToFinish.HasValue)
                    return;

                if (DateTime.UtcNow >= _whenToFinish.Value)
                {
                    base.ShowViewModel<MainViewModel>();

                    _whenToFinish = null;
                }
            }

        
        
        #endregion

    }
}


3.)View


using Cirrious.MvvmCross.Binding.BindingContext;
using Cirrious.MvvmCross.Touch.Views;
using Cirrious.MvvmCross.ViewModels;
using iReport.Core.ViewModels;
using iReport.Touch.Controls;
using MonoTouch.Foundation;
using MonoTouch.UIKit;
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Text;

namespace iReport.Touch.Views
{

    [Register("TimerView")]
    public class TimerView : MvxViewController
    {
        private BindableProgress _bindableProgress;


        public override void ViewDidLoad()
        {

            View = new UIView() { BackgroundColor = UIColor.Gray };

            base.ViewDidLoad();

            this.NavigationController.ToolbarHidden = true;
            this.NavigationController.NavigationBarHidden = true;

            UIImage splashscreen = MaxResizeImage(UIImage.FromFile("Default.png", UIScreen.MainScreen.Bounds.Width,UiScreen.MainScreen.Bounds.Height);

             UIImageView splashView = new UIImageView(splashscreen);
             Add(splashView);

            var set = this.CreateBindingSet<TimerView, Core.ViewModels.TimerViewModel>();
           

          
            set.Apply();

        }
    }
 // resize the image to be contained within a maximum width and height, keeping aspect ratio
public UIImage MaxResizeImage(UIImage sourceImage, float maxWidth, float maxHeight)
{
    var sourceSize = sourceImage.Size;
    var maxResizeFactor = Math.Max(maxWidth / sourceSize.Width, maxHeight / sourceSize.Height);
    if (maxResizeFactor > 1) return sourceImage;
    var width = maxResizeFactor * sourceSize.Width;
    var height = maxResizeFactor * sourceSize.Height;
    UIGraphics.BeginImageContext(new SizeF(width, height));
    sourceImage.Draw(new RectangleF(0, 0, width, height));
    var resultImage = UIGraphics.GetImageFromCurrentImageContext();
    UIGraphics.EndImageContext();
    return resultImage;
}



}

Source:

  1. http://stackoverflow.com/questions/5429746/how-to-get-width-and-height-of-iphone-ipad-using-monotouch
  2. http://forums.xamarin.com/discussion/4170/resize-images-and-save-thumbnails
  3. http://forums.xamarin.com/discussion/27327/ios-background-image-scale
  4. http://stackoverflow.com/questions/20447787/system-threading-timer-issue-only-timer-in-mvvmcross
  5. http://stackoverflow.com/questions/15961664/viewmodel-lifecycle-when-does-it-get-disposed
  6. https://code.msdn.microsoft.com/windowsapps/Splash-screen-sample-89c1dc78
 

Wednesday, April 22, 2015

A simple ComboBox for MVVMCross (Xamarin)

Working on getting a "ComboBox" control for our current iOS project.  We are using the MVVMCross libraries by Stuart Lodge.  I am surprised at the relutance of the Apple/Windows to support a simple combo box.  The best iOS option appears to be the UIPickerView.  I found a large number of sample projects and code snippets for straight Objective C and even Xamarin/Monotouch projects. 

A Start...

I was looking for an implementation using the MVVMCross pattern.  I found something very close in https://github.com/MvvmCross/MvvmCross-Tutorials/tree/master/ApiExamples.  The touch project contains the FirstView.cs

Line 144:
public override void ViewDidLoad()
{
base.ViewDidLoad();
var picker = new UIPickerView();
var pickerViewModel = new MvxPickerViewModel(picker);
picker.Model = pickerViewModel;
picker.ShowSelectionIndicator = true;
var textView = new UITextField(new RectangleF(10, 100, 300, 30));
Add(textView);
textView.InputView = picker;
var label = new UILabel(new RectangleF(10, 130, 300, 30));
Add(label);
var set = this.CreateBindingSet<SpinnerView, SpinnerViewModel>();
set.Bind(pickerViewModel).For(p => p.SelectedItem).To(vm => vm.SelectedItem);
set.Bind(pickerViewModel).For(p => p.ItemsSource).To(vm => vm.Items);
set.Bind(textView).To(vm => vm.SelectedItem);
set.Bind(label).To(vm => vm.SelectedItem);
set.Apply();
}

This gets us part of the way there but what this binding does is simply bring up the picker view and displays the 4 options in the Model.  The PickerView contains no way to exit out of the control except using the default back in the iOS navigation bar.  This is not going to work for my use case.  I needed to have a way to close out the pickerview once the selection had been made.

Getting Closer ...

Over at 13daysaweek blog I stumbled across the article Combobox Type Input With iOS and MonoTouch "Combobox Type Input With iOS and MonoTouch".  This is trying to solve the problem I was having but it was not using MVVM.  It was however critical to understanding that the UITextField has two properties which allow a user to associate the pickerview with the textview object.  The properties:
  • TextField.InputView
  • TextField.InputAccessoryView
These properties allow a user to associate the PickerView with the Textbox

"I noticed another interesting property on the UITextField class, InputAccessoryView. It turns out that if a view is assigned to this property, it will be displayed above the view specified by the InputView property. With that in mind, I created a UIToolBar, added a button and set that as the InputAccessorView. "

A Solution ...

So combining both the approaches yielded the following solution


public override void ViewDidLoad()
{
base.ViewDidLoad();
var picker = new UIPickerView();
var pickerViewModel = new MvxPickerViewModel(picker);
picker.Model = pickerViewModel;
picker.ShowSelectionIndicator = true;
var textView = new UITextField(new RectangleF(10, 100, 300, 30));
Add(textView);

UIToolbar = new UIToolbar();
toolbar.BarStyle = UIBarStyle.Black;
toolbar.Translucent = true;
toolbar.SizeToFit();
UIBarButtonItem doneButton = new UIBarButtonItem("Done", UIBarButtonItemStyle.Done, (s, e) =>
{
   //This dismisses the picker view and returns control to the main screen.
   textView.ResignFirstResponder();
}
toolbar.SetItems(new UIBarButtonItem[] { doneButton }, true);

 //This associates the picker view with the textview          
textView.InputView = picker;

//This will insert the toolbar into the pickerview.  This will allow the user to dismiss the
//view once a choice has been made.
textView.InputAccessoryView = toolbar;
var set = this.CreateBindingSet<SpinnerView, SpinnerViewModel>();
set.Bind(pickerViewModel).For(p => p.SelectedItem).To(vm => vm.SelectedItem);
set.Bind(pickerViewModel).For(p => p.ItemsSource).To(vm => vm.Items);
set.Bind(textView).To(vm => vm.SelectedItem);
set.Bind(label).To(vm => vm.SelectedItem);
set.Apply();
}

The toolbar control has been added so that a user selecting from the picker view can close the view once they have selected the value.  This allows the control to be more standalone as it does not depend on the navigation bar as the original code base provided in the MVVM sample.  The critical element in the view is the remember to assign the ResignFirstResponder method to the doneButton action.  If you do not do this then the activation of the done button will not close the PickerView leaving the user stranded on the control.


Source:
  1. https://github.com/MvvmCross/MvvmCross-Tutorials/blob/master/ApiExamples/ApiExamples.Touch/Views/FirstView.cs
  2. http://thirteendaysaweek.com/2012/09/19/combobox-type-input-with-ios-and-monotouch/
  3. https://github.com/13daysaweek/MonoTouchUIPickerView
  4. http://forums.xamarin.com/discussion/5805/uipickerview-example

Tuesday, April 21, 2015

Navigation Bar customization iOS (NavigationItem.SetRightBarButtonItems)

Working an issue on a project.  We needed to modify the navigation bar in iOS.
I was not sure how to do this but turns out we can use the NavigationItem class in the MonoTouch library. 

var btnEmail = new UIBarButtonItem(UIImage.FromFile("image/mail.png"),UIBarButtonItemStyle.Plain, (s,e) => {});
NavigationItem.SetRightBarButtonItems(new UIBarButtonItem[] { btnEmail}, true);


Source:
  1. http://forums.xamarin.com/discussion/16413/navigation-uibarbuttonitem-creation

Wednesday, April 15, 2015

Hosted web site smtp mails failure to forward to another internal email domain

Issue:
Just finished troubleshooting a annoying issue.  We have moved some public facing IIS servers on to shared hosting.  We had configured SMTP to forward to our other closed network.  The issue we were having was that our emails from each of the web apps were going out but not ever arriving within our local domains. 

The issue was the smtp forwarder inside our local network.  The smtp forwarder has a white list which was refusing any mail sent from this new public service.  We added the new domain into the white list and now the emails are passed through from our externally hosted servers.

Solution:
Each web application needs to have the from domain set correctly or the whitelist will block it.  If you find your emails blocked don't forget to view the badmail folder on your IIS server.  This is by default located at C:\Inetpub\mailroot\badmail.

Thursday, April 9, 2015

Geocoding in C# using Google Maps

I was curious about KML and other things to do with Googlemap.  I found this great post about
how to change a street address to a lat/lng.

Sample web service request to get lat/lng:
http://maps.googleapis.com/maps/api/geocode/xml?sensor=false&address=...

C# to use the web service

Geocoding Example

The following method accepts a comma separated address string and returns the longitude and latitude.
public static GeocoderLocation Locate(string query)
{
   WebRequest request = WebRequest
      .Create("http://maps.googleapis.com/maps/api/geocode/xml?sensor=false&address="
         + HttpUtility.UrlEncode(query));

   using (WebResponse response = request.GetResponse())
   {
      using (Stream stream = response.GetResponseStream())
      {
         XDocument document = XDocument.Load(new StreamReader(stream));

         XElement longitudeElement = document.Descendants("lng").FirstOrDefault();
         XElement latitudeElement = document.Descendants("lat").FirstOrDefault();

         if (longitudeElement != null && latitudeElement != null)
         {
            return new GeocoderLocation
            {
               Longitude = Double.Parse(longitudeElement.Value, CultureInfo.InvariantCulture),
               Latitude = Double.Parse(latitudeElement.Value, CultureInfo.InvariantCulture)
            };
         }
      }
   }

   return null;
}

Location Class

[Serializable]
public class GeocoderLocation
{
   public double Longitude { get; set; }
   public double Latitude { get; set; }
 
   public override string ToString()
   {
      return String.Format("{0}, {1}", Latitude, Longitude);
   }
}
 
source:
 

Wednesday, April 8, 2015

STIG finding APP4050

I am trying to close out this finding.  It requires that I confirm that the source code files were not
tampered with in transit from developer to me.  Robert Mcmurray had the same issue and cooked up
this console application using the Cryptography namespace in .Net.

 using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Security.Cryptography;
using System.Text;
using System.Threading.Tasks;
namespace CheckSumUtility
{
   class Hash
{
    static void Main(string[] args)
    {
        // Verify the correct number of command-line arguments.
        if (args.Length != 2)
        {
            // Show the help message if an incorrect number of arguments was specified.
            ShowHelp();
            return;
        }
        else
        {
            byte[] hashValue = null;
            // Verify that the specified file exists.
            if (!File.Exists(args[1]))
            {
                // Show the help message if a non-existent filename was specified.
                ShowHelp();
                return;
            }
            else
            {
                try
                {
                    // Create a fileStream for the file.
                    FileStream fileStream = File.OpenRead(args[1]);
                    // Be sure it's positioned to the beginning of the stream.
                    fileStream.Position = 0;
                    // Use the specified hash algorithm.
                    switch (args[0].ToUpper())
                    {
                        case "MD5":
                            // Compute the MD5 hash of the fileStream.
                            hashValue = MD5.Create().ComputeHash(fileStream);
                            break;
                        case "SHA1":
                            // Compute the SHA1 hash of the fileStream.
                            hashValue = SHA1.Create().ComputeHash(fileStream);
                            break;
                        case "SHA256":
                            // Compute the SHA256 hash of the fileStream.
                            hashValue = SHA256.Create().ComputeHash(fileStream);
                            break;
                        case "SHA384":
                            // Compute the SHA384 hash of the fileStream.
                            hashValue = SHA384.Create().ComputeHash(fileStream);
                            break;
                        case "SHA512":
                            // Compute the SHA512 hash of the fileStream.
                            hashValue = SHA512.Create().ComputeHash(fileStream);
                            break;
                        case "BASE64":
                            // Compute the BASE64 hash of the fileStream.
                            byte[] binaryData = new Byte[fileStream.Length];
                            long bytesRead = fileStream.Read(binaryData, 0, (int)fileStream.Length);
                            if (bytesRead != fileStream.Length)
                            {
                                throw new Exception(String.Format("Number of bytes read ({0}) does not match file size ({1}).", bytesRead, fileStream.Length));
                            }
                            string base64String = System.Convert.ToBase64String(binaryData, 0, binaryData.Length);
                            Console.WriteLine("File: {0}\r\nBASE64 Hash: {1}", fileStream.Name, base64String);
                            hashValue = null;
                            break;
                        default:
                            // Display the help message if an unrecognized hash algorithm was specified.
                            ShowHelp();
                            return;
                    }
                    if (hashValue != null)
                    {
                        // Write the hash value to the Console.
                        PrintHashData(args[0].ToUpper(), fileStream.Name, hashValue);
                    }
                    // Close the file.
                    fileStream.Close();
                }
                catch (Exception ex)
                {
                    Console.WriteLine("Error: {0}", ex.Message);
                }
            }
        }
    }
    // Display the help message.
    private static void ShowHelp()
    {       Console.WriteLine("HASH.exe <hash algorithm> <file name>\n\n" +
            "\tWhere <hash algorithm> is one of the following:\n" +
            "\t\tBASE64\n\t\tMD5\n\t\tSHA1\n\t\tSHA256\n\t\tSHA384\n\t\tSHA512\n");
    }
    // Print the hash data in a readable format.
    private static void PrintHashData(string algorithm, string fileName, byte[] array)
    {
        Console.Write("File: {0}\r\n{1} Hash: ", fileName,algorithm);
        for (int i = 0; i < array.Length; i++)
        {
            Console.Write(String.Format("{0:X2}", array[i]));
        }
        Console.WriteLine();
    }
   }
}


Source:
http://blogs.iis.net/robert_mcmurray/archive/2014/05/16/simple-utility-to-calculate-file-hashes.aspx

How do I get just the SQL Server Management Studio?

SQL Server Express 2012 consists of the packages

Version:
11.0.2100.60
File Name:
ENU\x64\SQLEXPR_x64_ENU.exe
ENU\x64\SQLEXPRADV_x64_ENU.exe
ENU\x64\SQLEXPRWT_x64_ENU.exe
ENU\x64\SqlLocalDB.MSI
ENU\x64\SQLManagementStudio_x64_ENU.exe
Date Published:
5/14/2012
 
But How do I get just the Management Studio?

Run ENU\x64\SQLManagementStudio_x64_ENU.exe

I had to choose the following options to get the management Tools:
 1."New SQL Server stand-alone installation or add features to an existing installation."
 2."Add features to an existing instance of SQL Server 2012"
 3.Accept the license.
 4.Check the box for "Management Tools - Basic".
 5.Wait a long time as it installs.

When I was done I had an option "SQL Server Management Studio" within my Start Menu.
Searching for "Management" pulled it up faster within the Start Menu.


 Source:
  1. http://www.jasonstrate.com/2013/05/get-just-the-tools-ssms-download/
  2. https://www.microsoft.com/betaexperience/pd/SQLEXPNOCTAV2/enus/default.aspx