├── .gitattributes
├── .gitignore
├── .nuget
├── NuGet.Config
├── NuGet.exe
└── NuGet.targets
├── CheckForDotNet45
├── CheckForDotNet45.csproj
├── Program.cs
├── Properties
│ └── AssemblyInfo.cs
└── app.config
├── README.md
├── SmallestDotNet.sln
├── SmallestDotNet
├── Default.aspx
├── Default.aspx.cs
├── Default.aspx.designer.cs
├── Properties
│ └── AssemblyInfo.cs
├── SmallestDotNet.csproj
├── VersionCheck.ashx
├── VersionCheck.ashx.cs
├── Web.Debug.config
├── Web.Release.config
├── Web.config
├── css
│ ├── bootstrap-responsive.min.css
│ ├── bootstrap.min.css
│ ├── font-awesome-ie7.css
│ ├── font-awesome.css
│ ├── m-buttons.min.css
│ └── main.css
├── font
│ ├── fontawesome-webfont.eot
│ ├── fontawesome-webfont.svg
│ ├── fontawesome-webfont.ttf
│ └── fontawesome-webfont.woff
├── img
│ ├── glyphicons-halflings-white.png
│ ├── glyphicons-halflings.png
│ └── hero_home.jpg
├── javascript.ashx
├── javascriptdom.ashx
├── js
│ ├── bootstrap.min.js
│ └── jquery-1.8.1.min.js
└── testjs.html
├── SmallestDotNetLib
├── BrowserSupport.cs
├── CLRVersion.cs
├── CLRVersions.cs
├── Constants.cs
├── Helpers.cs
├── JsonVersions.cs
├── OperatingSystemSupport.cs
├── Properties
│ └── AssemblyInfo.cs
├── SmallestDotNetLib.csproj
└── UpdateInformationResponse.cs
├── SmallestTest
├── CLRVersionDictionaryTests.cs
├── JavascriptDomTests.cs
├── OperatingSystemVersionTests.cs
├── Properties
│ └── AssemblyInfo.cs
├── SmallestTest.csproj
├── VersionCheckTest.cs
└── VersionWriterTests.cs
└── license.txt
/.gitattributes:
--------------------------------------------------------------------------------
1 | # Auto detect text files and perform LF normalization
2 | * text=auto
3 |
4 | # Custom for Visual Studio
5 | *.cs diff=csharp
6 | *.sln merge=union
7 | *.csproj merge=union
8 | *.vbproj merge=union
9 | *.fsproj merge=union
10 | *.dbproj merge=union
11 |
12 | # Standard to msysgit
13 | *.doc diff=astextplain
14 | *.DOC diff=astextplain
15 | *.docx diff=astextplain
16 | *.DOCX diff=astextplain
17 | *.dot diff=astextplain
18 | *.DOT diff=astextplain
19 | *.pdf diff=astextplain
20 | *.PDF diff=astextplain
21 | *.rtf diff=astextplain
22 | *.RTF diff=astextplain
23 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Build Folders (you can keep bin if you'd like, to store dlls and pdbs)
2 | bin
3 | obj
4 |
5 | #VSArtifacts
6 | *suo
7 |
8 | # mstest test results
9 | TestResults
10 |
11 | *suo
12 | *user
13 |
14 | [Pp]ackages
15 |
16 | # Visual Studio 2015/17 cache/options directory
17 | .vs/
--------------------------------------------------------------------------------
/.nuget/NuGet.Config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/.nuget/NuGet.exe:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shanselman/SmallestDotNet/8a60a223929137d036b0730f24b44c83ecb8cbe4/.nuget/NuGet.exe
--------------------------------------------------------------------------------
/.nuget/NuGet.targets:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | $(MSBuildProjectDirectory)\..\
5 |
6 |
7 | false
8 |
9 |
10 | false
11 |
12 |
13 | true
14 |
15 |
16 | false
17 |
18 |
19 |
20 |
21 |
25 |
26 |
27 |
28 |
29 | $([System.IO.Path]::Combine($(SolutionDir), ".nuget"))
30 | $([System.IO.Path]::Combine($(ProjectDir), "packages.config"))
31 | $([System.IO.Path]::Combine($(SolutionDir), "packages"))
32 |
33 |
34 |
35 |
36 | $(SolutionDir).nuget
37 | packages.config
38 | $(SolutionDir)packages
39 |
40 |
41 |
42 |
43 | $(NuGetToolsPath)\nuget.exe
44 | @(PackageSource)
45 |
46 | "$(NuGetExePath)"
47 | mono --runtime=v4.0.30319 $(NuGetExePath)
48 |
49 | $(TargetDir.Trim('\\'))
50 |
51 | -RequireConsent
52 |
53 | $(NuGetCommand) install "$(PackagesConfig)" -source "$(PackageSources)" $(RequireConsentSwitch) -o "$(PackagesDir)"
54 | $(NuGetCommand) pack "$(ProjectPath)" -p Configuration=$(Configuration) -o "$(PackageOutputDir)" -symbols
55 |
56 |
57 |
58 | RestorePackages;
59 | $(BuildDependsOn);
60 |
61 |
62 |
63 |
64 | $(BuildDependsOn);
65 | BuildPackage;
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
79 |
80 |
83 |
84 |
85 |
86 |
88 |
89 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 |
121 |
122 |
123 |
124 |
125 |
126 |
127 |
128 |
129 |
130 |
131 |
132 |
133 |
140 |
141 |
142 |
143 |
--------------------------------------------------------------------------------
/CheckForDotNet45/CheckForDotNet45.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Debug
6 | AnyCPU
7 | {2D8463F4-3C7A-42C8-9A2D-8F585460EE74}
8 | Exe
9 | Properties
10 | CheckForDotNet45
11 | CheckForDotNet45
12 | v4.0
13 | 512
14 | Client
15 |
16 |
17 | AnyCPU
18 | true
19 | full
20 | false
21 | bin\Debug\
22 | DEBUG;TRACE
23 | prompt
24 | 4
25 |
26 |
27 | AnyCPU
28 | pdbonly
29 | true
30 | bin\Release\
31 | TRACE
32 | prompt
33 | 4
34 |
35 |
36 | false
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
62 |
--------------------------------------------------------------------------------
/CheckForDotNet45/Program.cs:
--------------------------------------------------------------------------------
1 | // -----------------------------------------------------------------------
2 | //
3 | // Copyright © Scott Hanselman, Michael Sarchet and Friends 2012. All rights reserved.
4 | //
5 | // -----------------------------------------------------------------------
6 | namespace CheckForDotNet45
7 | {
8 | using System;
9 | using System.Diagnostics;
10 |
11 | using Microsoft.Win32;
12 |
13 | ///
14 | /// Class containing all application logic
15 | ///
16 | public class Program
17 | {
18 | #region Fields
19 |
20 | /// Site URL with release key parameter
21 | private const string SiteWithReleaseKey = "https://smallestdotnet.com/?releaseKey={0}";
22 |
23 | /// Site URL with version parameter
24 | private const string SiteWithVersion = "https://smallestdotnet.com/?realversion={0}";
25 |
26 | #endregion Fields
27 |
28 | #region Methods
29 |
30 | ///
31 | /// Main entry point for program.
32 | ///
33 | public static void Main()
34 | {
35 | try
36 | {
37 | Console.Write("Checking .NET version...");
38 |
39 | int releaseKey = 0;
40 | string version = null;
41 | if (IsNet45OrNewer())
42 | {
43 | releaseKey = GetDotnetReleaseKeyFromRegistry();
44 | }
45 | else
46 | {
47 | version = Environment.Version.ToString();
48 | }
49 |
50 | string url = string.IsNullOrEmpty(version)
51 | ? string.Format(SiteWithReleaseKey, releaseKey)
52 | : string.Format(SiteWithVersion, version);
53 | try
54 | {
55 | Process.Start(url);
56 | }
57 | catch (Exception)
58 | {
59 | Console.WriteLine("\nApplication was unable to launch browser to go to {0}", url);
60 | if (version != null)
61 | {
62 | Console.WriteLine("Your current .NET version is: " + version);
63 | }
64 | else
65 | {
66 | Console.WriteLine("Please browse to the URL to get version information.");
67 | }
68 |
69 | Console.ReadLine(); // Pause
70 | }
71 | }
72 | catch (Exception ex)
73 | {
74 | Console.WriteLine("An error occurred:");
75 | Console.ForegroundColor = ConsoleColor.Red;
76 | Console.WriteLine(ex.ToString());
77 | Console.ResetColor();
78 | Console.WriteLine("Please log an issue including the error information at https://github.com/shanselman/SmallestDotNet/issues/");
79 | Console.ReadLine(); // Pause
80 | }
81 | }
82 |
83 | ///
84 | /// Gets the .Net release key from registry "SOFTWARE\Microsoft\NET Framework Setup\NDP\v4\Full\".
85 | ///
86 | /// Release key or -1 if not found
87 | private static int GetDotnetReleaseKeyFromRegistry()
88 | {
89 | int releaseKey = -1;
90 |
91 | // Based on http://msdn.microsoft.com/en-us/library/hh925568%28v=vs.110%29.aspx#net_d
92 | using (
93 | RegistryKey ndpKey =
94 | RegistryKey.OpenBaseKey(RegistryHive.LocalMachine, RegistryView.Registry32)
95 | .OpenSubKey(@"SOFTWARE\Microsoft\NET Framework Setup\NDP\v4\Full\"))
96 | {
97 | if (ndpKey != null)
98 | {
99 | object releaseKeyValue = ndpKey.GetValue("Release") ?? "-1";
100 | int.TryParse(releaseKeyValue.ToString(), out releaseKey);
101 | }
102 |
103 | return releaseKey;
104 | }
105 | }
106 |
107 | ///
108 | /// Determines whether we have .net 4.5 or newer.
109 | ///
110 | /// true if we have .net 4.5 or newer
111 | private static bool IsNet45OrNewer()
112 | {
113 | // Class "ReflectionContext" exists in .NET 4.5 .
114 | return Type.GetType("System.Reflection.ReflectionContext", false) != null;
115 | }
116 |
117 | #endregion Methods
118 | }
119 | }
--------------------------------------------------------------------------------
/CheckForDotNet45/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Reflection;
2 | using System.Runtime.InteropServices;
3 |
4 | // General Information about an assembly is controlled through the following
5 | // set of attributes. Change these attribute values to modify the information
6 | // associated with an assembly.
7 | [assembly: AssemblyTitle("CheckForDotNet45")]
8 | [assembly: AssemblyDescription("")]
9 | [assembly: AssemblyConfiguration("")]
10 | [assembly: AssemblyCompany("")]
11 | [assembly: AssemblyProduct("CheckForDotNet45")]
12 | [assembly: AssemblyCopyright("Copyright © 2012")]
13 | [assembly: AssemblyTrademark("")]
14 | [assembly: AssemblyCulture("")]
15 |
16 | // Setting ComVisible to false makes the types in this assembly not visible
17 | // to COM components. If you need to access a type in this assembly from
18 | // COM, set the ComVisible attribute to true on that type.
19 | [assembly: ComVisible(false)]
20 |
21 | // The following GUID is for the ID of the typelib if this project is exposed to COM
22 | [assembly: Guid("19ff6b37-745e-4dec-826c-540d921e2acb")]
23 |
24 | // Version information for an assembly consists of the following four values:
25 | //
26 | // Major Version
27 | // Minor Version
28 | // Build Number
29 | // Revision
30 | //
31 | // You can specify all the values or you can default the Build and Revision Numbers
32 | // by using the '*' as shown below:
33 | // [assembly: AssemblyVersion("1.0.*")]
34 | [assembly: AssemblyVersion("1.0.0.0")]
35 | [assembly: AssemblyFileVersion("1.0.0.0")]
36 |
--------------------------------------------------------------------------------
/CheckForDotNet45/app.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | [](https://app.fossa.io/projects/git%2Bgithub.com%2Fshanselman%2FSmallestDotNet?ref=badge_shield)
2 |
3 | SmallestDotNet
4 | ==============
5 |
6 | SmallestDotNet - [SmallestDotNet.com](https://smallestdotnet.com) is a single page site that does one thing. It tells you the smallest, easiest download you'd need to get the .NET Framework on your system.
7 |
8 | The code sucks. I did it in an hour and I'm sad.
9 |
10 | Thanks to Calin Balauru for his help. Anything good here is him. All the bad is me.
11 |
12 |
13 | ## License
14 | [](https://app.fossa.io/projects/git%2Bgithub.com%2Fshanselman%2FSmallestDotNet?ref=badge_large)
--------------------------------------------------------------------------------
/SmallestDotNet.sln:
--------------------------------------------------------------------------------
1 |
2 | Microsoft Visual Studio Solution File, Format Version 12.00
3 | # Visual Studio 2012
4 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SmallestDotNet", "SmallestDotNet\SmallestDotNet.csproj", "{F80F0719-0AC1-4B4D-9F44-7D78C90FAEE3}"
5 | EndProject
6 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SmallestDotNetLib", "SmallestDotNetLib\SmallestDotNetLib.csproj", "{3ECC85DC-EBC0-4A2E-930D-711ABC481388}"
7 | EndProject
8 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CheckForDotNet45", "CheckForDotNet45\CheckForDotNet45.csproj", "{2D8463F4-3C7A-42C8-9A2D-8F585460EE74}"
9 | EndProject
10 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SmallestTest", "SmallestTest\SmallestTest.csproj", "{21BD13C9-725E-447D-8CF9-07E8CBE797B1}"
11 | EndProject
12 | Global
13 | GlobalSection(SolutionConfigurationPlatforms) = preSolution
14 | Debug|Any CPU = Debug|Any CPU
15 | Release|Any CPU = Release|Any CPU
16 | EndGlobalSection
17 | GlobalSection(ProjectConfigurationPlatforms) = postSolution
18 | {F80F0719-0AC1-4B4D-9F44-7D78C90FAEE3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
19 | {F80F0719-0AC1-4B4D-9F44-7D78C90FAEE3}.Debug|Any CPU.Build.0 = Debug|Any CPU
20 | {F80F0719-0AC1-4B4D-9F44-7D78C90FAEE3}.Release|Any CPU.ActiveCfg = Release|Any CPU
21 | {F80F0719-0AC1-4B4D-9F44-7D78C90FAEE3}.Release|Any CPU.Build.0 = Release|Any CPU
22 | {3ECC85DC-EBC0-4A2E-930D-711ABC481388}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
23 | {3ECC85DC-EBC0-4A2E-930D-711ABC481388}.Debug|Any CPU.Build.0 = Debug|Any CPU
24 | {3ECC85DC-EBC0-4A2E-930D-711ABC481388}.Release|Any CPU.ActiveCfg = Release|Any CPU
25 | {3ECC85DC-EBC0-4A2E-930D-711ABC481388}.Release|Any CPU.Build.0 = Release|Any CPU
26 | {2D8463F4-3C7A-42C8-9A2D-8F585460EE74}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
27 | {2D8463F4-3C7A-42C8-9A2D-8F585460EE74}.Debug|Any CPU.Build.0 = Debug|Any CPU
28 | {2D8463F4-3C7A-42C8-9A2D-8F585460EE74}.Release|Any CPU.ActiveCfg = Release|Any CPU
29 | {2D8463F4-3C7A-42C8-9A2D-8F585460EE74}.Release|Any CPU.Build.0 = Release|Any CPU
30 | {21BD13C9-725E-447D-8CF9-07E8CBE797B1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
31 | {21BD13C9-725E-447D-8CF9-07E8CBE797B1}.Debug|Any CPU.Build.0 = Debug|Any CPU
32 | {21BD13C9-725E-447D-8CF9-07E8CBE797B1}.Release|Any CPU.ActiveCfg = Release|Any CPU
33 | {21BD13C9-725E-447D-8CF9-07E8CBE797B1}.Release|Any CPU.Build.0 = Release|Any CPU
34 | EndGlobalSection
35 | GlobalSection(SolutionProperties) = preSolution
36 | HideSolutionNode = FALSE
37 | EndGlobalSection
38 | EndGlobal
39 |
--------------------------------------------------------------------------------
/SmallestDotNet/Default.aspx:
--------------------------------------------------------------------------------
1 | <%@ Page Language="C#" AutoEventWireup="true" Inherits="_Default" CodeBehind="Default.aspx.cs" %>
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 | Get the .NET Framework Fast - Download the smallest .NET Framework Distribution possible
19 |
20 |
21 |
37 |
38 |
39 |
40 |
60 |
61 |
62 |
63 |
78 |
79 |
80 |
81 |
What about .NET 4.5 or later?
82 |
83 | Download this application
.NET Checker and run it.
84 | This harmless code signed application will tell us if you have .NET 4.5, 4.6, 4.7 or 4.8 (including minor versions). Don't trust us? Here's
the code .
85 |
86 |
87 |
88 |
89 |
90 |
What happened
91 | This site looked at your browser's "UserAgent" and figured out what version (if any) of the .NET Framework you have (or don't have) installed, then calculated the total size if you chose to download the .NET Framework.
92 |
93 |
94 | There's no database, no cookies, and nothing about your computer has been stored or kept. We just look at the information your browser already reports about your computer and make a suggestion as to the best .NET Framework download for you.
95 |
96 |
97 |
98 |
99 |
Offline Download
100 |
101 |
Online Download
102 |
103 |
104 |
105 |
106 |
107 |
Are you a .NET Programmer?
108 | If you're a programmer/developer, you might be trying to figure out which .NET Framework for your users to use.
109 |
110 |
111 | Sometimes finding the right .NET Framework is confusing because different kinds of machines (x86, x64, ia64) that may or may not have different versions of .NET already on them.
112 |
113 |
114 | If you look for .NET Downloads on Microsoft's site, it might look like the .NET Framework is 200+ megs. It's not. Those big downloads are the Complete Offline Versions of every version of the .NET Framework for every kind of machine possible. The big .NET download includes x86, x64, and ia64. It includes .NET 2.0, 3.0, and 3.5 code for all systems all in one super-archive. The downloads for .NET 4.5, 4.6, 4.7 and 4.8 are even smaller.
115 |
116 |
117 | Why would you EVER want to download the whole archive? Only if you're a developer and you want to distribute the .NET Framework the widest possible audience in a format like a CD or DVD.
118 |
119 |
120 |
Your User Agent
121 | For technical or debugging purposes, this is exactly what your browser said about itself:
122 |
123 |
124 |
125 |
126 |
127 |
128 |
129 |
Integration
130 | Want SmallestDotNet functionality for your own site? Add this chunk of JavaScript, it'll spit out HTML and you can style to taste.
131 |
132 |
<script type="text/javascript" src="https://www.smallestdotnet.com/javascript.ashx"></script>
133 |
134 |
135 |
136 |
137 |
138 | Prefer a JavaScript Object (JSON) to detect .NET Framework installations? Try this instead:
139 |
140 |
<script type="text/javascript" src="https://www.smallestdotnet.com/javascriptdom.ashx"></script>
141 | Get examples on
how to use the JSON object on Scott's Blog.
142 |
143 |
144 |
145 |
146 |
147 |
148 |
157 |
158 |
159 |
160 |
161 |
164 |
165 |
166 |
186 |
187 |
198 |
199 |
200 |
--------------------------------------------------------------------------------
/SmallestDotNet/Default.aspx.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Web;
3 |
4 | using SmallestDotNetLib;
5 |
6 | public partial class _Default : System.Web.UI.Page
7 | {
8 | protected void Page_Load(object sender, EventArgs e)
9 | {
10 | string realVersion = null;
11 | int releaseKey = 0;
12 | bool runFromChecker = false;
13 | string userAgentText = this.Request.UserAgent ?? string.Empty;
14 |
15 | // set the Get.NET link button to the latest offline version
16 | getdotnet.HRef = HttpUtility.HtmlEncode(Constants.LatestDotNetRawUrl);
17 | getdotnet.Target = "_blank";
18 |
19 | userAgent.Text = HttpUtility.HtmlEncode(userAgentText);
20 |
21 | if (Request.QueryString["realversion"] != null || this.Request.QueryString["releaseKey"] != null)
22 | {
23 | realVersion = this.Request.QueryString["realversion"];
24 | int.TryParse(this.Request.QueryString["releaseKey"], out releaseKey);
25 | runFromChecker = true;
26 | }
27 |
28 |
29 | UpdateInformationResponse response = Helpers.GetUpdateInformation(userAgentText, realVersion, releaseKey);
30 |
31 | userResult.Text = response.Text;
32 | developerOnline.Text = String.Format(@"If your users have internet connectivity, the .NET Framework is only between {1} and {2} megs. Why such a wide range? Well, it depends on if they already have some version of .NET.
33 | If you point your users to the online setup for the {0}, that {3} MB download will automatically detect and download the smallest archive possible to get the job done.", Constants.DotNetOnline, Constants.DotNetOfflineMB - Constants.Version3OfflineMB, Constants.DotNetOfflineMB, Constants.DotNetOnlineMB);
34 |
35 | developerOfflineResult.Text = String.Format(@"If you are a developer and are distributing your code on CD or DVD, you might want to download the
36 | {0} on your media. The download is about {1} MB", Constants.DotNetOffline, Constants.DotNetOfflineMB);
37 | getdotnet.Visible = response.VersionCanBeDetermined;
38 |
39 | if (response.VersionIsLatest)
40 | getdotnet.Visible = false;
41 |
42 | checkdotnet.Visible = response.CanRunCheckApp;
43 |
44 | // Hide the 4.5 checker section if
45 | // (a) we can't determine the dotnet version or
46 | // (b) we're on an OS that doesn't support .Net or
47 | // (c) the user has already run the checker so we know exactly what version they're on.
48 | // Note that the checkdotnet section in the header will still be displayed as long as the OS supports it
49 | dotnet45.Visible = response.VersionCanBeDetermined && response.CanRunCheckApp && !runFromChecker;
50 | }
51 |
52 | }
53 |
--------------------------------------------------------------------------------
/SmallestDotNet/Default.aspx.designer.cs:
--------------------------------------------------------------------------------
1 | //------------------------------------------------------------------------------
2 | //
3 | // This code was generated by a tool.
4 | //
5 | // Changes to this file may cause incorrect behavior and will be lost if
6 | // the code is regenerated.
7 | //
8 | //------------------------------------------------------------------------------
9 |
10 |
11 |
12 | public partial class _Default {
13 |
14 | ///
15 | /// userResult control.
16 | ///
17 | ///
18 | /// Auto-generated field.
19 | /// To modify move field declaration from designer file to code-behind file.
20 | ///
21 | protected global::System.Web.UI.WebControls.Literal userResult;
22 |
23 | ///
24 | /// getdotnet control.
25 | ///
26 | ///
27 | /// Auto-generated field.
28 | /// To modify move field declaration from designer file to code-behind file.
29 | ///
30 | protected global::System.Web.UI.HtmlControls.HtmlAnchor getdotnet;
31 |
32 | ///
33 | /// checkdotnet control.
34 | ///
35 | ///
36 | /// Auto-generated field.
37 | /// To modify move field declaration from designer file to code-behind file.
38 | ///
39 | protected global::System.Web.UI.HtmlControls.HtmlAnchor checkdotnet;
40 |
41 | ///
42 | /// dotnet45 control.
43 | ///
44 | ///
45 | /// Auto-generated field.
46 | /// To modify move field declaration from designer file to code-behind file.
47 | ///
48 | protected global::System.Web.UI.HtmlControls.HtmlGenericControl dotnet45;
49 |
50 | ///
51 | /// developerOfflineResult control.
52 | ///
53 | ///
54 | /// Auto-generated field.
55 | /// To modify move field declaration from designer file to code-behind file.
56 | ///
57 | protected global::System.Web.UI.WebControls.Literal developerOfflineResult;
58 |
59 | ///
60 | /// developerOnline control.
61 | ///
62 | ///
63 | /// Auto-generated field.
64 | /// To modify move field declaration from designer file to code-behind file.
65 | ///
66 | protected global::System.Web.UI.WebControls.Literal developerOnline;
67 |
68 | ///
69 | /// userAgent control.
70 | ///
71 | ///
72 | /// Auto-generated field.
73 | /// To modify move field declaration from designer file to code-behind file.
74 | ///
75 | protected global::System.Web.UI.WebControls.Literal userAgent;
76 | }
77 |
--------------------------------------------------------------------------------
/SmallestDotNet/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Reflection;
2 | using System.Runtime.InteropServices;
3 |
4 | // General Information about an assembly is controlled through the following
5 | // set of attributes. Change these attribute values to modify the information
6 | // associated with an assembly.
7 | [assembly: AssemblyTitle("SmallestDotNet")]
8 | [assembly: AssemblyDescription("")]
9 | [assembly: AssemblyConfiguration("")]
10 | [assembly: AssemblyCompany("")]
11 | [assembly: AssemblyProduct("SmallestDotNet")]
12 | [assembly: AssemblyCopyright("Copyright © 2012")]
13 | [assembly: AssemblyTrademark("")]
14 | [assembly: AssemblyCulture("")]
15 |
16 | // Setting ComVisible to false makes the types in this assembly not visible
17 | // to COM components. If you need to access a type in this assembly from
18 | // COM, set the ComVisible attribute to true on that type.
19 | [assembly: ComVisible(false)]
20 |
21 | // The following GUID is for the ID of the typelib if this project is exposed to COM
22 | [assembly: Guid("e6cfcac0-158c-48ba-bf1f-71b0c81cc456")]
23 |
24 | // Version information for an assembly consists of the following four values:
25 | //
26 | // Major Version
27 | // Minor Version
28 | // Build Number
29 | // Revision
30 | //
31 | // You can specify all the values or you can default the Revision and Build Numbers
32 | // by using the '*' as shown below:
33 | [assembly: AssemblyVersion("1.0.0.0")]
34 | [assembly: AssemblyFileVersion("1.0.0.0")]
35 |
--------------------------------------------------------------------------------
/SmallestDotNet/SmallestDotNet.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Debug
6 | AnyCPU
7 |
8 |
9 | 2.0
10 | {F80F0719-0AC1-4B4D-9F44-7D78C90FAEE3}
11 | {349c5851-65df-11da-9384-00065b846f21};{fae04ec0-301f-11d3-bf4b-00c04f79efbc}
12 | Library
13 | Properties
14 | SmallestDotNet
15 | SmallestDotNet
16 | v4.5
17 | true
18 |
19 |
20 |
21 |
22 |
23 |
24 | true
25 | full
26 | false
27 | bin\
28 | DEBUG;TRACE
29 | prompt
30 | 4
31 | false
32 |
33 |
34 | pdbonly
35 | true
36 | bin\
37 | TRACE
38 | prompt
39 | 4
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 | Designer
77 |
78 |
79 |
80 |
81 | Default.aspx
82 |
83 |
84 | Default.aspx
85 | ASPXCodeBehind
86 |
87 |
88 |
89 | VersionCheck.ashx
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 | Web.config
101 |
102 |
103 | Web.config
104 |
105 |
106 |
107 |
108 | {3ecc85dc-ebc0-4a2e-930d-711abc481388}
109 | SmallestDotNetLib
110 |
111 |
112 |
113 | 10.0
114 | $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)
115 |
116 |
117 |
118 |
119 |
120 |
121 |
122 |
123 | True
124 | True
125 | 0
126 | /
127 | http://localhost:57099/
128 | False
129 | False
130 |
131 |
132 | False
133 |
134 |
135 |
136 |
137 |
144 |
--------------------------------------------------------------------------------
/SmallestDotNet/VersionCheck.ashx:
--------------------------------------------------------------------------------
1 | <%@ WebHandler Language="C#" CodeBehind="VersionCheck.ashx.cs" Class="SmallestDotNet.VersionCheck" %>
2 |
--------------------------------------------------------------------------------
/SmallestDotNet/VersionCheck.ashx.cs:
--------------------------------------------------------------------------------
1 | using System.Web;
2 |
3 | namespace SmallestDotNet
4 | {
5 | ///
6 | /// Summary description for VersionCheck
7 | ///
8 | public class VersionCheck : IHttpHandler
9 | {
10 |
11 | public void ProcessRequest(HttpContext context)
12 | {
13 | if (context.Request.RequestType == "GET")
14 | {
15 | var userAgent = context.Request["userAgent"];
16 | context.Response.ContentType = "text/plain";
17 | context.Response.Write(Helpers.GetUpdateInformation(userAgent).Text);
18 | }
19 | }
20 |
21 | public bool IsReusable
22 | {
23 | get
24 | {
25 | return false;
26 | }
27 | }
28 | }
29 | }
--------------------------------------------------------------------------------
/SmallestDotNet/Web.Debug.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
17 |
18 |
29 |
30 |
--------------------------------------------------------------------------------
/SmallestDotNet/Web.Release.config:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
17 |
18 |
19 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
--------------------------------------------------------------------------------
/SmallestDotNet/Web.config:
--------------------------------------------------------------------------------
1 |
2 |
10 |
11 |
12 |
13 |
14 |
20 |
21 |
26 |
27 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
--------------------------------------------------------------------------------
/SmallestDotNet/css/bootstrap-responsive.min.css:
--------------------------------------------------------------------------------
1 | /*!
2 | * Bootstrap Responsive v2.1.1
3 | *
4 | * Copyright 2012 Twitter, Inc
5 | * Licensed under the Apache License v2.0
6 | * http://www.apache.org/licenses/LICENSE-2.0
7 | *
8 | * Designed and built with all the love in the world @twitter by @mdo and @fat.
9 | */.clearfix{*zoom:1}.clearfix:before,.clearfix:after{display:table;line-height:0;content:""}.clearfix:after{clear:both}.hide-text{font:0/0 a;color:transparent;text-shadow:none;background-color:transparent;border:0}.input-block-level{display:block;width:100%;min-height:30px;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.hidden{display:none;visibility:hidden}.visible-phone{display:none!important}.visible-tablet{display:none!important}.hidden-desktop{display:none!important}.visible-desktop{display:inherit!important}@media(min-width:768px) and (max-width:979px){.hidden-desktop{display:inherit!important}.visible-desktop{display:none!important}.visible-tablet{display:inherit!important}.hidden-tablet{display:none!important}}@media(max-width:767px){.hidden-desktop{display:inherit!important}.visible-desktop{display:none!important}.visible-phone{display:inherit!important}.hidden-phone{display:none!important}}@media(min-width:1200px){.row{margin-left:-30px;*zoom:1}.row:before,.row:after{display:table;line-height:0;content:""}.row:after{clear:both}[class*="span"]{float:left;min-height:1px;margin-left:30px}.container,.navbar-static-top .container,.navbar-fixed-top .container,.navbar-fixed-bottom .container{width:1170px}.span12{width:1170px}.span11{width:1070px}.span10{width:970px}.span9{width:870px}.span8{width:770px}.span7{width:670px}.span6{width:570px}.span5{width:470px}.span4{width:370px}.span3{width:270px}.span2{width:170px}.span1{width:70px}.offset12{margin-left:1230px}.offset11{margin-left:1130px}.offset10{margin-left:1030px}.offset9{margin-left:930px}.offset8{margin-left:830px}.offset7{margin-left:730px}.offset6{margin-left:630px}.offset5{margin-left:530px}.offset4{margin-left:430px}.offset3{margin-left:330px}.offset2{margin-left:230px}.offset1{margin-left:130px}.row-fluid{width:100%;*zoom:1}.row-fluid:before,.row-fluid:after{display:table;line-height:0;content:""}.row-fluid:after{clear:both}.row-fluid [class*="span"]{display:block;float:left;width:100%;min-height:30px;margin-left:2.564102564102564%;*margin-left:2.5109110747408616%;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.row-fluid [class*="span"]:first-child{margin-left:0}.row-fluid .span12{width:100%;*width:99.94680851063829%}.row-fluid .span11{width:91.45299145299145%;*width:91.39979996362975%}.row-fluid .span10{width:82.90598290598291%;*width:82.8527914166212%}.row-fluid .span9{width:74.35897435897436%;*width:74.30578286961266%}.row-fluid .span8{width:65.81196581196582%;*width:65.75877432260411%}.row-fluid .span7{width:57.26495726495726%;*width:57.21176577559556%}.row-fluid .span6{width:48.717948717948715%;*width:48.664757228587014%}.row-fluid .span5{width:40.17094017094017%;*width:40.11774868157847%}.row-fluid .span4{width:31.623931623931625%;*width:31.570740134569924%}.row-fluid .span3{width:23.076923076923077%;*width:23.023731587561375%}.row-fluid .span2{width:14.52991452991453%;*width:14.476723040552828%}.row-fluid .span1{width:5.982905982905983%;*width:5.929714493544281%}.row-fluid .offset12{margin-left:105.12820512820512%;*margin-left:105.02182214948171%}.row-fluid .offset12:first-child{margin-left:102.56410256410257%;*margin-left:102.45771958537915%}.row-fluid .offset11{margin-left:96.58119658119658%;*margin-left:96.47481360247316%}.row-fluid .offset11:first-child{margin-left:94.01709401709402%;*margin-left:93.91071103837061%}.row-fluid .offset10{margin-left:88.03418803418803%;*margin-left:87.92780505546462%}.row-fluid .offset10:first-child{margin-left:85.47008547008548%;*margin-left:85.36370249136206%}.row-fluid .offset9{margin-left:79.48717948717949%;*margin-left:79.38079650845607%}.row-fluid .offset9:first-child{margin-left:76.92307692307693%;*margin-left:76.81669394435352%}.row-fluid .offset8{margin-left:70.94017094017094%;*margin-left:70.83378796144753%}.row-fluid .offset8:first-child{margin-left:68.37606837606839%;*margin-left:68.26968539734497%}.row-fluid .offset7{margin-left:62.393162393162385%;*margin-left:62.28677941443899%}.row-fluid .offset7:first-child{margin-left:59.82905982905982%;*margin-left:59.72267685033642%}.row-fluid .offset6{margin-left:53.84615384615384%;*margin-left:53.739770867430444%}.row-fluid .offset6:first-child{margin-left:51.28205128205128%;*margin-left:51.175668303327875%}.row-fluid .offset5{margin-left:45.299145299145295%;*margin-left:45.1927623204219%}.row-fluid .offset5:first-child{margin-left:42.73504273504273%;*margin-left:42.62865975631933%}.row-fluid .offset4{margin-left:36.75213675213675%;*margin-left:36.645753773413354%}.row-fluid .offset4:first-child{margin-left:34.18803418803419%;*margin-left:34.081651209310785%}.row-fluid .offset3{margin-left:28.205128205128204%;*margin-left:28.0987452264048%}.row-fluid .offset3:first-child{margin-left:25.641025641025642%;*margin-left:25.53464266230224%}.row-fluid .offset2{margin-left:19.65811965811966%;*margin-left:19.551736679396257%}.row-fluid .offset2:first-child{margin-left:17.094017094017094%;*margin-left:16.98763411529369%}.row-fluid .offset1{margin-left:11.11111111111111%;*margin-left:11.004728132387708%}.row-fluid .offset1:first-child{margin-left:8.547008547008547%;*margin-left:8.440625568285142%}input,textarea,.uneditable-input{margin-left:0}.controls-row [class*="span"]+[class*="span"]{margin-left:30px}input.span12,textarea.span12,.uneditable-input.span12{width:1156px}input.span11,textarea.span11,.uneditable-input.span11{width:1056px}input.span10,textarea.span10,.uneditable-input.span10{width:956px}input.span9,textarea.span9,.uneditable-input.span9{width:856px}input.span8,textarea.span8,.uneditable-input.span8{width:756px}input.span7,textarea.span7,.uneditable-input.span7{width:656px}input.span6,textarea.span6,.uneditable-input.span6{width:556px}input.span5,textarea.span5,.uneditable-input.span5{width:456px}input.span4,textarea.span4,.uneditable-input.span4{width:356px}input.span3,textarea.span3,.uneditable-input.span3{width:256px}input.span2,textarea.span2,.uneditable-input.span2{width:156px}input.span1,textarea.span1,.uneditable-input.span1{width:56px}.thumbnails{margin-left:-30px}.thumbnails>li{margin-left:30px}.row-fluid .thumbnails{margin-left:0}}@media(min-width:768px) and (max-width:979px){.row{margin-left:-20px;*zoom:1}.row:before,.row:after{display:table;line-height:0;content:""}.row:after{clear:both}[class*="span"]{float:left;min-height:1px;margin-left:20px}.container,.navbar-static-top .container,.navbar-fixed-top .container,.navbar-fixed-bottom .container{width:724px}.span12{width:724px}.span11{width:662px}.span10{width:600px}.span9{width:538px}.span8{width:476px}.span7{width:414px}.span6{width:352px}.span5{width:290px}.span4{width:228px}.span3{width:166px}.span2{width:104px}.span1{width:42px}.offset12{margin-left:764px}.offset11{margin-left:702px}.offset10{margin-left:640px}.offset9{margin-left:578px}.offset8{margin-left:516px}.offset7{margin-left:454px}.offset6{margin-left:392px}.offset5{margin-left:330px}.offset4{margin-left:268px}.offset3{margin-left:206px}.offset2{margin-left:144px}.offset1{margin-left:82px}.row-fluid{width:100%;*zoom:1}.row-fluid:before,.row-fluid:after{display:table;line-height:0;content:""}.row-fluid:after{clear:both}.row-fluid [class*="span"]{display:block;float:left;width:100%;min-height:30px;margin-left:2.7624309392265194%;*margin-left:2.709239449864817%;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.row-fluid [class*="span"]:first-child{margin-left:0}.row-fluid .span12{width:100%;*width:99.94680851063829%}.row-fluid .span11{width:91.43646408839778%;*width:91.38327259903608%}.row-fluid .span10{width:82.87292817679558%;*width:82.81973668743387%}.row-fluid .span9{width:74.30939226519337%;*width:74.25620077583166%}.row-fluid .span8{width:65.74585635359117%;*width:65.69266486422946%}.row-fluid .span7{width:57.18232044198895%;*width:57.12912895262725%}.row-fluid .span6{width:48.61878453038674%;*width:48.56559304102504%}.row-fluid .span5{width:40.05524861878453%;*width:40.00205712942283%}.row-fluid .span4{width:31.491712707182323%;*width:31.43852121782062%}.row-fluid .span3{width:22.92817679558011%;*width:22.87498530621841%}.row-fluid .span2{width:14.3646408839779%;*width:14.311449394616199%}.row-fluid .span1{width:5.801104972375691%;*width:5.747913483013988%}.row-fluid .offset12{margin-left:105.52486187845304%;*margin-left:105.41847889972962%}.row-fluid .offset12:first-child{margin-left:102.76243093922652%;*margin-left:102.6560479605031%}.row-fluid .offset11{margin-left:96.96132596685082%;*margin-left:96.8549429881274%}.row-fluid .offset11:first-child{margin-left:94.1988950276243%;*margin-left:94.09251204890089%}.row-fluid .offset10{margin-left:88.39779005524862%;*margin-left:88.2914070765252%}.row-fluid .offset10:first-child{margin-left:85.6353591160221%;*margin-left:85.52897613729868%}.row-fluid .offset9{margin-left:79.8342541436464%;*margin-left:79.72787116492299%}.row-fluid .offset9:first-child{margin-left:77.07182320441989%;*margin-left:76.96544022569647%}.row-fluid .offset8{margin-left:71.2707182320442%;*margin-left:71.16433525332079%}.row-fluid .offset8:first-child{margin-left:68.50828729281768%;*margin-left:68.40190431409427%}.row-fluid .offset7{margin-left:62.70718232044199%;*margin-left:62.600799341718584%}.row-fluid .offset7:first-child{margin-left:59.94475138121547%;*margin-left:59.838368402492065%}.row-fluid .offset6{margin-left:54.14364640883978%;*margin-left:54.037263430116376%}.row-fluid .offset6:first-child{margin-left:51.38121546961326%;*margin-left:51.27483249088986%}.row-fluid .offset5{margin-left:45.58011049723757%;*margin-left:45.47372751851417%}.row-fluid .offset5:first-child{margin-left:42.81767955801105%;*margin-left:42.71129657928765%}.row-fluid .offset4{margin-left:37.01657458563536%;*margin-left:36.91019160691196%}.row-fluid .offset4:first-child{margin-left:34.25414364640884%;*margin-left:34.14776066768544%}.row-fluid .offset3{margin-left:28.45303867403315%;*margin-left:28.346655695309746%}.row-fluid .offset3:first-child{margin-left:25.69060773480663%;*margin-left:25.584224756083227%}.row-fluid .offset2{margin-left:19.88950276243094%;*margin-left:19.783119783707537%}.row-fluid .offset2:first-child{margin-left:17.12707182320442%;*margin-left:17.02068884448102%}.row-fluid .offset1{margin-left:11.32596685082873%;*margin-left:11.219583872105325%}.row-fluid .offset1:first-child{margin-left:8.56353591160221%;*margin-left:8.457152932878806%}input,textarea,.uneditable-input{margin-left:0}.controls-row [class*="span"]+[class*="span"]{margin-left:20px}input.span12,textarea.span12,.uneditable-input.span12{width:710px}input.span11,textarea.span11,.uneditable-input.span11{width:648px}input.span10,textarea.span10,.uneditable-input.span10{width:586px}input.span9,textarea.span9,.uneditable-input.span9{width:524px}input.span8,textarea.span8,.uneditable-input.span8{width:462px}input.span7,textarea.span7,.uneditable-input.span7{width:400px}input.span6,textarea.span6,.uneditable-input.span6{width:338px}input.span5,textarea.span5,.uneditable-input.span5{width:276px}input.span4,textarea.span4,.uneditable-input.span4{width:214px}input.span3,textarea.span3,.uneditable-input.span3{width:152px}input.span2,textarea.span2,.uneditable-input.span2{width:90px}input.span1,textarea.span1,.uneditable-input.span1{width:28px}}@media(max-width:767px){body{padding-right:20px;padding-left:20px}.navbar-fixed-top,.navbar-fixed-bottom,.navbar-static-top{margin-right:-20px;margin-left:-20px}.container-fluid{padding:0}.dl-horizontal dt{float:none;width:auto;clear:none;text-align:left}.dl-horizontal dd{margin-left:0}.container{width:auto}.row-fluid{width:100%}.row,.thumbnails{margin-left:0}.thumbnails>li{float:none;margin-left:0}[class*="span"],.row-fluid [class*="span"]{display:block;float:none;width:100%;margin-left:0;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.span12,.row-fluid .span12{width:100%;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.input-large,.input-xlarge,.input-xxlarge,input[class*="span"],select[class*="span"],textarea[class*="span"],.uneditable-input{display:block;width:100%;min-height:30px;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.input-prepend input,.input-append input,.input-prepend input[class*="span"],.input-append input[class*="span"]{display:inline-block;width:auto}.controls-row [class*="span"]+[class*="span"]{margin-left:0}.modal{position:fixed;top:20px;right:20px;left:20px;width:auto;margin:0}.modal.fade.in{top:auto}}@media(max-width:480px){.nav-collapse{-webkit-transform:translate3d(0,0,0)}.page-header h1 small{display:block;line-height:20px}input[type="checkbox"],input[type="radio"]{border:1px solid #ccc}.form-horizontal .control-label{float:none;width:auto;padding-top:0;text-align:left}.form-horizontal .controls{margin-left:0}.form-horizontal .control-list{padding-top:0}.form-horizontal .form-actions{padding-right:10px;padding-left:10px}.modal{top:10px;right:10px;left:10px}.modal-header .close{padding:10px;margin:-10px}.carousel-caption{position:static}}@media(max-width:979px){body{padding-top:0}.navbar-fixed-top,.navbar-fixed-bottom{position:static}.navbar-fixed-top{margin-bottom:20px}.navbar-fixed-bottom{margin-top:20px}.navbar-fixed-top .navbar-inner,.navbar-fixed-bottom .navbar-inner{padding:5px}.navbar .container{width:auto;padding:0}.navbar .brand{padding-right:10px;padding-left:10px;margin:0 0 0 -5px}.nav-collapse{clear:both}.nav-collapse .nav{float:none;margin:0 0 10px}.nav-collapse .nav>li{float:none}.nav-collapse .nav>li>a{margin-bottom:2px}.nav-collapse .nav>.divider-vertical{display:none}.nav-collapse .nav .nav-header{color:#777;text-shadow:none}.nav-collapse .nav>li>a,.nav-collapse .dropdown-menu a{padding:9px 15px;font-weight:bold;color:#777;-webkit-border-radius:3px;-moz-border-radius:3px;border-radius:3px}.nav-collapse .btn{padding:4px 10px 4px;font-weight:normal;-webkit-border-radius:4px;-moz-border-radius:4px;border-radius:4px}.nav-collapse .dropdown-menu li+li a{margin-bottom:2px}.nav-collapse .nav>li>a:hover,.nav-collapse .dropdown-menu a:hover{background-color:#f2f2f2}.navbar-inverse .nav-collapse .nav>li>a:hover,.navbar-inverse .nav-collapse .dropdown-menu a:hover{background-color:#111}.nav-collapse.in .btn-group{padding:0;margin-top:5px}.nav-collapse .dropdown-menu{position:static;top:auto;left:auto;display:block;float:none;max-width:none;padding:0;margin:0 15px;background-color:transparent;border:0;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0;-webkit-box-shadow:none;-moz-box-shadow:none;box-shadow:none}.nav-collapse .dropdown-menu:before,.nav-collapse .dropdown-menu:after{display:none}.nav-collapse .dropdown-menu .divider{display:none}.nav-collapse .nav>li>.dropdown-menu:before,.nav-collapse .nav>li>.dropdown-menu:after{display:none}.nav-collapse .navbar-form,.nav-collapse .navbar-search{float:none;padding:10px 15px;margin:10px 0;border-top:1px solid #f2f2f2;border-bottom:1px solid #f2f2f2;-webkit-box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1);-moz-box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1);box-shadow:inset 0 1px 0 rgba(255,255,255,0.1),0 1px 0 rgba(255,255,255,0.1)}.navbar-inverse .nav-collapse .navbar-form,.navbar-inverse .nav-collapse .navbar-search{border-top-color:#111;border-bottom-color:#111}.navbar .nav-collapse .nav.pull-right{float:none;margin-left:0}.nav-collapse,.nav-collapse.collapse{height:0;overflow:hidden}.navbar .btn-navbar{display:block}.navbar-static .navbar-inner{padding-right:10px;padding-left:10px}}@media(min-width:980px){.nav-collapse.collapse{height:auto!important;overflow:visible!important}}
10 |
--------------------------------------------------------------------------------
/SmallestDotNet/css/font-awesome-ie7.css:
--------------------------------------------------------------------------------
1 | [class^="icon-"],
2 | [class*=" icon-"] {
3 | font-family: FontAwesome;
4 | font-style: normal;
5 | font-weight: normal;
6 | }
7 | .btn.dropdown-toggle [class^="icon-"],
8 | .btn.dropdown-toggle [class*=" icon-"] {
9 | /* keeps button heights with and without icons the same */
10 |
11 | line-height: 1.4em;
12 | }
13 | .icon-large {
14 | font-size: 1.3333em;
15 | }
16 | .icon-glass {
17 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
18 | }
19 | .icon-music {
20 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
21 | }
22 | .icon-search {
23 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
24 | }
25 | .icon-envelope {
26 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
27 | }
28 | .icon-heart {
29 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
30 | }
31 | .icon-star {
32 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
33 | }
34 | .icon-star-empty {
35 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
36 | }
37 | .icon-user {
38 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
39 | }
40 | .icon-film {
41 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
42 | }
43 | .icon-th-large {
44 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
45 | }
46 | .icon-th {
47 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
48 | }
49 | .icon-th-list {
50 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
51 | }
52 | .icon-ok {
53 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
54 | }
55 | .icon-remove {
56 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
57 | }
58 | .icon-zoom-in {
59 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
60 | }
61 | .icon-zoom-out {
62 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
63 | }
64 | .icon-off {
65 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
66 | }
67 | .icon-signal {
68 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
69 | }
70 | .icon-cog {
71 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
72 | }
73 | .icon-trash {
74 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
75 | }
76 | .icon-home {
77 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
78 | }
79 | .icon-file {
80 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
81 | }
82 | .icon-time {
83 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
84 | }
85 | .icon-road {
86 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
87 | }
88 | .icon-download-alt {
89 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
90 | }
91 | .icon-download {
92 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
93 | }
94 | .icon-upload {
95 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
96 | }
97 | .icon-inbox {
98 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
99 | }
100 | .icon-play-circle {
101 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
102 | }
103 | .icon-repeat {
104 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
105 | }
106 | .icon-refresh {
107 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
108 | }
109 | .icon-list-alt {
110 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
111 | }
112 | .icon-lock {
113 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
114 | }
115 | .icon-flag {
116 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
117 | }
118 | .icon-headphones {
119 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
120 | }
121 | .icon-volume-off {
122 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
123 | }
124 | .icon-volume-down {
125 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
126 | }
127 | .icon-volume-up {
128 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
129 | }
130 | .icon-qrcode {
131 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
132 | }
133 | .icon-barcode {
134 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
135 | }
136 | .icon-tag {
137 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
138 | }
139 | .icon-tags {
140 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
141 | }
142 | .icon-book {
143 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
144 | }
145 | .icon-bookmark {
146 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
147 | }
148 | .icon-print {
149 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
150 | }
151 | .icon-camera {
152 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
153 | }
154 | .icon-font {
155 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
156 | }
157 | .icon-bold {
158 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
159 | }
160 | .icon-italic {
161 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
162 | }
163 | .icon-text-height {
164 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
165 | }
166 | .icon-text-width {
167 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
168 | }
169 | .icon-align-left {
170 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
171 | }
172 | .icon-align-center {
173 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
174 | }
175 | .icon-align-right {
176 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
177 | }
178 | .icon-align-justify {
179 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
180 | }
181 | .icon-list {
182 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
183 | }
184 | .icon-indent-left {
185 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
186 | }
187 | .icon-indent-right {
188 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
189 | }
190 | .icon-facetime-video {
191 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
192 | }
193 | .icon-picture {
194 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
195 | }
196 | .icon-pencil {
197 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
198 | }
199 | .icon-map-marker {
200 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
201 | }
202 | .icon-adjust {
203 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
204 | }
205 | .icon-tint {
206 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
207 | }
208 | .icon-edit {
209 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
210 | }
211 | .icon-share {
212 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
213 | }
214 | .icon-check {
215 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
216 | }
217 | .icon-move {
218 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
219 | }
220 | .icon-step-backward {
221 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
222 | }
223 | .icon-fast-backward {
224 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
225 | }
226 | .icon-backward {
227 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
228 | }
229 | .icon-play {
230 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
231 | }
232 | .icon-pause {
233 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
234 | }
235 | .icon-stop {
236 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
237 | }
238 | .icon-forward {
239 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
240 | }
241 | .icon-fast-forward {
242 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
243 | }
244 | .icon-step-forward {
245 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
246 | }
247 | .icon-eject {
248 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
249 | }
250 | .icon-chevron-left {
251 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
252 | }
253 | .icon-chevron-right {
254 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
255 | }
256 | .icon-plus-sign {
257 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
258 | }
259 | .icon-minus-sign {
260 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
261 | }
262 | .icon-remove-sign {
263 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
264 | }
265 | .icon-ok-sign {
266 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
267 | }
268 | .icon-question-sign {
269 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
270 | }
271 | .icon-info-sign {
272 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
273 | }
274 | .icon-screenshot {
275 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
276 | }
277 | .icon-remove-circle {
278 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
279 | }
280 | .icon-ok-circle {
281 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
282 | }
283 | .icon-ban-circle {
284 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
285 | }
286 | .icon-arrow-left {
287 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
288 | }
289 | .icon-arrow-right {
290 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
291 | }
292 | .icon-arrow-up {
293 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
294 | }
295 | .icon-arrow-down {
296 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
297 | }
298 | .icon-share-alt {
299 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
300 | }
301 | .icon-resize-full {
302 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
303 | }
304 | .icon-resize-small {
305 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
306 | }
307 | .icon-plus {
308 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
309 | }
310 | .icon-minus {
311 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
312 | }
313 | .icon-asterisk {
314 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
315 | }
316 | .icon-exclamation-sign {
317 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
318 | }
319 | .icon-gift {
320 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
321 | }
322 | .icon-leaf {
323 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
324 | }
325 | .icon-fire {
326 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
327 | }
328 | .icon-eye-open {
329 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
330 | }
331 | .icon-eye-close {
332 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
333 | }
334 | .icon-warning-sign {
335 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
336 | }
337 | .icon-plane {
338 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
339 | }
340 | .icon-calendar {
341 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
342 | }
343 | .icon-random {
344 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
345 | }
346 | .icon-comment {
347 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
348 | }
349 | .icon-magnet {
350 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
351 | }
352 | .icon-chevron-up {
353 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
354 | }
355 | .icon-chevron-down {
356 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
357 | }
358 | .icon-retweet {
359 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
360 | }
361 | .icon-shopping-cart {
362 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
363 | }
364 | .icon-folder-close {
365 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
366 | }
367 | .icon-folder-open {
368 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
369 | }
370 | .icon-resize-vertical {
371 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
372 | }
373 | .icon-resize-horizontal {
374 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
375 | }
376 | .icon-bar-chart {
377 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
378 | }
379 | .icon-twitter-sign {
380 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
381 | }
382 | .icon-facebook-sign {
383 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
384 | }
385 | .icon-camera-retro {
386 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
387 | }
388 | .icon-key {
389 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
390 | }
391 | .icon-cogs {
392 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
393 | }
394 | .icon-comments {
395 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
396 | }
397 | .icon-thumbs-up {
398 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
399 | }
400 | .icon-thumbs-down {
401 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
402 | }
403 | .icon-star-half {
404 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
405 | }
406 | .icon-heart-empty {
407 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
408 | }
409 | .icon-signout {
410 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
411 | }
412 | .icon-linkedin-sign {
413 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
414 | }
415 | .icon-pushpin {
416 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
417 | }
418 | .icon-external-link {
419 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
420 | }
421 | .icon-signin {
422 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
423 | }
424 | .icon-trophy {
425 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
426 | }
427 | .icon-github-sign {
428 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
429 | }
430 | .icon-upload-alt {
431 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
432 | }
433 | .icon-lemon {
434 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
435 | }
436 | .icon-phone {
437 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
438 | }
439 | .icon-check-empty {
440 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
441 | }
442 | .icon-bookmark-empty {
443 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
444 | }
445 | .icon-phone-sign {
446 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
447 | }
448 | .icon-twitter {
449 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
450 | }
451 | .icon-facebook {
452 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
453 | }
454 | .icon-github {
455 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
456 | }
457 | .icon-unlock {
458 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
459 | }
460 | .icon-credit-card {
461 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
462 | }
463 | .icon-rss {
464 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
465 | }
466 | .icon-hdd {
467 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
468 | }
469 | .icon-bullhorn {
470 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
471 | }
472 | .icon-bell {
473 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
474 | }
475 | .icon-certificate {
476 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
477 | }
478 | .icon-hand-right {
479 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
480 | }
481 | .icon-hand-left {
482 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
483 | }
484 | .icon-hand-up {
485 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
486 | }
487 | .icon-hand-down {
488 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
489 | }
490 | .icon-circle-arrow-left {
491 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
492 | }
493 | .icon-circle-arrow-right {
494 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
495 | }
496 | .icon-circle-arrow-up {
497 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
498 | }
499 | .icon-circle-arrow-down {
500 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
501 | }
502 | .icon-globe {
503 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
504 | }
505 | .icon-wrench {
506 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
507 | }
508 | .icon-tasks {
509 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
510 | }
511 | .icon-filter {
512 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
513 | }
514 | .icon-briefcase {
515 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
516 | }
517 | .icon-fullscreen {
518 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
519 | }
520 | .icon-group {
521 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
522 | }
523 | .icon-link {
524 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
525 | }
526 | .icon-cloud {
527 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
528 | }
529 | .icon-beaker {
530 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
531 | }
532 | .icon-cut {
533 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
534 | }
535 | .icon-copy {
536 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
537 | }
538 | .icon-paper-clip {
539 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
540 | }
541 | .icon-save {
542 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
543 | }
544 | .icon-sign-blank {
545 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
546 | }
547 | .icon-reorder {
548 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
549 | }
550 | .icon-list-ul {
551 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
552 | }
553 | .icon-list-ol {
554 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
555 | }
556 | .icon-strikethrough {
557 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
558 | }
559 | .icon-underline {
560 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
561 | }
562 | .icon-table {
563 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
564 | }
565 | .icon-magic {
566 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
567 | }
568 | .icon-truck {
569 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
570 | }
571 | .icon-pinterest {
572 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
573 | }
574 | .icon-pinterest-sign {
575 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
576 | }
577 | .icon-google-plus-sign {
578 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
579 | }
580 | .icon-google-plus {
581 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
582 | }
583 | .icon-money {
584 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
585 | }
586 | .icon-caret-down {
587 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
588 | }
589 | .icon-caret-up {
590 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
591 | }
592 | .icon-caret-left {
593 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
594 | }
595 | .icon-caret-right {
596 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
597 | }
598 | .icon-columns {
599 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
600 | }
601 | .icon-sort {
602 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
603 | }
604 | .icon-sort-down {
605 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
606 | }
607 | .icon-sort-up {
608 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
609 | }
610 | .icon-envelope-alt {
611 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
612 | }
613 | .icon-linkedin {
614 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
615 | }
616 | .icon-undo {
617 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
618 | }
619 | .icon-legal {
620 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
621 | }
622 | .icon-dashboard {
623 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
624 | }
625 | .icon-comment-alt {
626 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
627 | }
628 | .icon-comments-alt {
629 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
630 | }
631 | .icon-bolt {
632 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
633 | }
634 | .icon-sitemap {
635 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
636 | }
637 | .icon-umbrella {
638 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
639 | }
640 | .icon-paste {
641 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
642 | }
643 | .icon-user-md {
644 | *zoom: expression( this.runtimeStyle['zoom'] = '1', this.innerHTML = ' ');
645 | }
646 |
--------------------------------------------------------------------------------
/SmallestDotNet/css/font-awesome.css:
--------------------------------------------------------------------------------
1 | /* Font Awesome
2 | the iconic font designed for use with Twitter Bootstrap
3 | -------------------------------------------------------
4 | The full suite of pictographic icons, examples, and documentation
5 | can be found at: http://fortawesome.github.com/Font-Awesome/
6 |
7 | License
8 | -------------------------------------------------------
9 | The Font Awesome webfont, CSS, and LESS files are licensed under CC BY 3.0:
10 | http://creativecommons.org/licenses/by/3.0/ A mention of
11 | 'Font Awesome - http://fortawesome.github.com/Font-Awesome' in human-readable
12 | source code is considered acceptable attribution (most common on the web).
13 | If human readable source code is not available to the end user, a mention in
14 | an 'About' or 'Credits' screen is considered acceptable (most common in desktop
15 | or mobile software).
16 |
17 | Contact
18 | -------------------------------------------------------
19 | Email: dave@davegandy.com
20 | Twitter: http://twitter.com/fortaweso_me
21 | Work: http://lemonwi.se co-founder
22 |
23 | */
24 | @font-face {
25 | font-family: "FontAwesome";
26 | src: url('../font/fontawesome-webfont.eot');
27 | src: url('../font/fontawesome-webfont.eot?#iefix') format('eot'), url('../font/fontawesome-webfont.woff') format('woff'), url('../font/fontawesome-webfont.ttf') format('truetype'), url('../font/fontawesome-webfont.svg#FontAwesome') format('svg');
28 | font-weight: normal;
29 | font-style: normal;
30 | }
31 |
32 | /* Font Awesome styles
33 | ------------------------------------------------------- */
34 | [class^="icon-"]:before, [class*=" icon-"]:before {
35 | font-family: FontAwesome;
36 | font-weight: normal;
37 | font-style: normal;
38 | display: inline-block;
39 | text-decoration: inherit;
40 | }
41 | a [class^="icon-"], a [class*=" icon-"] {
42 | display: inline-block;
43 | text-decoration: inherit;
44 | }
45 | /* makes the font 33% larger relative to the icon container */
46 | .icon-large:before {
47 | vertical-align: top;
48 | font-size: 1.3333333333333333em;
49 | }
50 | .btn [class^="icon-"], .btn [class*=" icon-"] {
51 | /* keeps button heights with and without icons the same */
52 |
53 | line-height: .9em;
54 | }
55 | li [class^="icon-"], li [class*=" icon-"] {
56 | display: inline-block;
57 | width: 1.25em;
58 | text-align: center;
59 | }
60 | li .icon-large[class^="icon-"], li .icon-large[class*=" icon-"] {
61 | /* 1.5 increased font size for icon-large * 1.25 width */
62 |
63 | width: 1.875em;
64 | }
65 | li[class^="icon-"], li[class*=" icon-"] {
66 | margin-left: 0;
67 | list-style-type: none;
68 | }
69 | li[class^="icon-"]:before, li[class*=" icon-"]:before {
70 | text-indent: -2em;
71 | text-align: center;
72 | }
73 | li[class^="icon-"].icon-large:before, li[class*=" icon-"].icon-large:before {
74 | text-indent: -1.3333333333333333em;
75 | }
76 | /* Font Awesome uses the Unicode Private Use Area (PUA) to ensure screen
77 | readers do not read off random characters that represent icons */
78 | .icon-glass:before { content: "\f000"; }
79 | .icon-music:before { content: "\f001"; }
80 | .icon-search:before { content: "\f002"; }
81 | .icon-envelope:before { content: "\f003"; }
82 | .icon-heart:before { content: "\f004"; }
83 | .icon-star:before { content: "\f005"; }
84 | .icon-star-empty:before { content: "\f006"; }
85 | .icon-user:before { content: "\f007"; }
86 | .icon-film:before { content: "\f008"; }
87 | .icon-th-large:before { content: "\f009"; }
88 | .icon-th:before { content: "\f00a"; }
89 | .icon-th-list:before { content: "\f00b"; }
90 | .icon-ok:before { content: "\f00c"; }
91 | .icon-remove:before { content: "\f00d"; }
92 | .icon-zoom-in:before { content: "\f00e"; }
93 |
94 | .icon-zoom-out:before { content: "\f010"; }
95 | .icon-off:before { content: "\f011"; }
96 | .icon-signal:before { content: "\f012"; }
97 | .icon-cog:before { content: "\f013"; }
98 | .icon-trash:before { content: "\f014"; }
99 | .icon-home:before { content: "\f015"; }
100 | .icon-file:before { content: "\f016"; }
101 | .icon-time:before { content: "\f017"; }
102 | .icon-road:before { content: "\f018"; }
103 | .icon-download-alt:before { content: "\f019"; }
104 | .icon-download:before { content: "\f01a"; }
105 | .icon-upload:before { content: "\f01b"; }
106 | .icon-inbox:before { content: "\f01c"; }
107 | .icon-play-circle:before { content: "\f01d"; }
108 | .icon-repeat:before { content: "\f01e"; }
109 |
110 | /* \f020 doesn't work in Safari. all shifted one down */
111 | .icon-refresh:before { content: "\f021"; }
112 | .icon-list-alt:before { content: "\f022"; }
113 | .icon-lock:before { content: "\f023"; }
114 | .icon-flag:before { content: "\f024"; }
115 | .icon-headphones:before { content: "\f025"; }
116 | .icon-volume-off:before { content: "\f026"; }
117 | .icon-volume-down:before { content: "\f027"; }
118 | .icon-volume-up:before { content: "\f028"; }
119 | .icon-qrcode:before { content: "\f029"; }
120 | .icon-barcode:before { content: "\f02a"; }
121 | .icon-tag:before { content: "\f02b"; }
122 | .icon-tags:before { content: "\f02c"; }
123 | .icon-book:before { content: "\f02d"; }
124 | .icon-bookmark:before { content: "\f02e"; }
125 | .icon-print:before { content: "\f02f"; }
126 |
127 | .icon-camera:before { content: "\f030"; }
128 | .icon-font:before { content: "\f031"; }
129 | .icon-bold:before { content: "\f032"; }
130 | .icon-italic:before { content: "\f033"; }
131 | .icon-text-height:before { content: "\f034"; }
132 | .icon-text-width:before { content: "\f035"; }
133 | .icon-align-left:before { content: "\f036"; }
134 | .icon-align-center:before { content: "\f037"; }
135 | .icon-align-right:before { content: "\f038"; }
136 | .icon-align-justify:before { content: "\f039"; }
137 | .icon-list:before { content: "\f03a"; }
138 | .icon-indent-left:before { content: "\f03b"; }
139 | .icon-indent-right:before { content: "\f03c"; }
140 | .icon-facetime-video:before { content: "\f03d"; }
141 | .icon-picture:before { content: "\f03e"; }
142 |
143 | .icon-pencil:before { content: "\f040"; }
144 | .icon-map-marker:before { content: "\f041"; }
145 | .icon-adjust:before { content: "\f042"; }
146 | .icon-tint:before { content: "\f043"; }
147 | .icon-edit:before { content: "\f044"; }
148 | .icon-share:before { content: "\f045"; }
149 | .icon-check:before { content: "\f046"; }
150 | .icon-move:before { content: "\f047"; }
151 | .icon-step-backward:before { content: "\f048"; }
152 | .icon-fast-backward:before { content: "\f049"; }
153 | .icon-backward:before { content: "\f04a"; }
154 | .icon-play:before { content: "\f04b"; }
155 | .icon-pause:before { content: "\f04c"; }
156 | .icon-stop:before { content: "\f04d"; }
157 | .icon-forward:before { content: "\f04e"; }
158 |
159 | .icon-fast-forward:before { content: "\f050"; }
160 | .icon-step-forward:before { content: "\f051"; }
161 | .icon-eject:before { content: "\f052"; }
162 | .icon-chevron-left:before { content: "\f053"; }
163 | .icon-chevron-right:before { content: "\f054"; }
164 | .icon-plus-sign:before { content: "\f055"; }
165 | .icon-minus-sign:before { content: "\f056"; }
166 | .icon-remove-sign:before { content: "\f057"; }
167 | .icon-ok-sign:before { content: "\f058"; }
168 | .icon-question-sign:before { content: "\f059"; }
169 | .icon-info-sign:before { content: "\f05a"; }
170 | .icon-screenshot:before { content: "\f05b"; }
171 | .icon-remove-circle:before { content: "\f05c"; }
172 | .icon-ok-circle:before { content: "\f05d"; }
173 | .icon-ban-circle:before { content: "\f05e"; }
174 |
175 | .icon-arrow-left:before { content: "\f060"; }
176 | .icon-arrow-right:before { content: "\f061"; }
177 | .icon-arrow-up:before { content: "\f062"; }
178 | .icon-arrow-down:before { content: "\f063"; }
179 | .icon-share-alt:before { content: "\f064"; }
180 | .icon-resize-full:before { content: "\f065"; }
181 | .icon-resize-small:before { content: "\f066"; }
182 | .icon-plus:before { content: "\f067"; }
183 | .icon-minus:before { content: "\f068"; }
184 | .icon-asterisk:before { content: "\f069"; }
185 | .icon-exclamation-sign:before { content: "\f06a"; }
186 | .icon-gift:before { content: "\f06b"; }
187 | .icon-leaf:before { content: "\f06c"; }
188 | .icon-fire:before { content: "\f06d"; }
189 | .icon-eye-open:before { content: "\f06e"; }
190 |
191 | .icon-eye-close:before { content: "\f070"; }
192 | .icon-warning-sign:before { content: "\f071"; }
193 | .icon-plane:before { content: "\f072"; }
194 | .icon-calendar:before { content: "\f073"; }
195 | .icon-random:before { content: "\f074"; }
196 | .icon-comment:before { content: "\f075"; }
197 | .icon-magnet:before { content: "\f076"; }
198 | .icon-chevron-up:before { content: "\f077"; }
199 | .icon-chevron-down:before { content: "\f078"; }
200 | .icon-retweet:before { content: "\f079"; }
201 | .icon-shopping-cart:before { content: "\f07a"; }
202 | .icon-folder-close:before { content: "\f07b"; }
203 | .icon-folder-open:before { content: "\f07c"; }
204 | .icon-resize-vertical:before { content: "\f07d"; }
205 | .icon-resize-horizontal:before { content: "\f07e"; }
206 |
207 | .icon-bar-chart:before { content: "\f080"; }
208 | .icon-twitter-sign:before { content: "\f081"; }
209 | .icon-facebook-sign:before { content: "\f082"; }
210 | .icon-camera-retro:before { content: "\f083"; }
211 | .icon-key:before { content: "\f084"; }
212 | .icon-cogs:before { content: "\f085"; }
213 | .icon-comments:before { content: "\f086"; }
214 | .icon-thumbs-up:before { content: "\f087"; }
215 | .icon-thumbs-down:before { content: "\f088"; }
216 | .icon-star-half:before { content: "\f089"; }
217 | .icon-heart-empty:before { content: "\f08a"; }
218 | .icon-signout:before { content: "\f08b"; }
219 | .icon-linkedin-sign:before { content: "\f08c"; }
220 | .icon-pushpin:before { content: "\f08d"; }
221 | .icon-external-link:before { content: "\f08e"; }
222 |
223 | .icon-signin:before { content: "\f090"; }
224 | .icon-trophy:before { content: "\f091"; }
225 | .icon-github-sign:before { content: "\f092"; }
226 | .icon-upload-alt:before { content: "\f093"; }
227 | .icon-lemon:before { content: "\f094"; }
228 | .icon-phone:before { content: "\f095"; }
229 | .icon-check-empty:before { content: "\f096"; }
230 | .icon-bookmark-empty:before { content: "\f097"; }
231 | .icon-phone-sign:before { content: "\f098"; }
232 | .icon-twitter:before { content: "\f099"; }
233 | .icon-facebook:before { content: "\f09a"; }
234 | .icon-github:before { content: "\f09b"; }
235 | .icon-unlock:before { content: "\f09c"; }
236 | .icon-credit-card:before { content: "\f09d"; }
237 | .icon-rss:before { content: "\f09e"; }
238 |
239 | .icon-hdd:before { content: "\f0a0"; }
240 | .icon-bullhorn:before { content: "\f0a1"; }
241 | .icon-bell:before { content: "\f0a2"; }
242 | .icon-certificate:before { content: "\f0a3"; }
243 | .icon-hand-right:before { content: "\f0a4"; }
244 | .icon-hand-left:before { content: "\f0a5"; }
245 | .icon-hand-up:before { content: "\f0a6"; }
246 | .icon-hand-down:before { content: "\f0a7"; }
247 | .icon-circle-arrow-left:before { content: "\f0a8"; }
248 | .icon-circle-arrow-right:before { content: "\f0a9"; }
249 | .icon-circle-arrow-up:before { content: "\f0aa"; }
250 | .icon-circle-arrow-down:before { content: "\f0ab"; }
251 | .icon-globe:before { content: "\f0ac"; }
252 | .icon-wrench:before { content: "\f0ad"; }
253 | .icon-tasks:before { content: "\f0ae"; }
254 |
255 | .icon-filter:before { content: "\f0b0"; }
256 | .icon-briefcase:before { content: "\f0b1"; }
257 | .icon-fullscreen:before { content: "\f0b2"; }
258 |
259 | .icon-group:before { content: "\f0c0"; }
260 | .icon-link:before { content: "\f0c1"; }
261 | .icon-cloud:before { content: "\f0c2"; }
262 | .icon-beaker:before { content: "\f0c3"; }
263 | .icon-cut:before { content: "\f0c4"; }
264 | .icon-copy:before { content: "\f0c5"; }
265 | .icon-paper-clip:before { content: "\f0c6"; }
266 | .icon-save:before { content: "\f0c7"; }
267 | .icon-sign-blank:before { content: "\f0c8"; }
268 | .icon-reorder:before { content: "\f0c9"; }
269 | .icon-list-ul:before { content: "\f0ca"; }
270 | .icon-list-ol:before { content: "\f0cb"; }
271 | .icon-strikethrough:before { content: "\f0cc"; }
272 | .icon-underline:before { content: "\f0cd"; }
273 | .icon-table:before { content: "\f0ce"; }
274 |
275 | .icon-magic:before { content: "\f0d0"; }
276 | .icon-truck:before { content: "\f0d1"; }
277 | .icon-pinterest:before { content: "\f0d2"; }
278 | .icon-pinterest-sign:before { content: "\f0d3"; }
279 | .icon-google-plus-sign:before { content: "\f0d4"; }
280 | .icon-google-plus:before { content: "\f0d5"; }
281 | .icon-money:before { content: "\f0d6"; }
282 | .icon-caret-down:before { content: "\f0d7"; }
283 | .icon-caret-up:before { content: "\f0d8"; }
284 | .icon-caret-left:before { content: "\f0d9"; }
285 | .icon-caret-right:before { content: "\f0da"; }
286 | .icon-columns:before { content: "\f0db"; }
287 | .icon-sort:before { content: "\f0dc"; }
288 | .icon-sort-down:before { content: "\f0dd"; }
289 | .icon-sort-up:before { content: "\f0de"; }
290 |
291 | .icon-envelope-alt:before { content: "\f0e0"; }
292 | .icon-linkedin:before { content: "\f0e1"; }
293 | .icon-undo:before { content: "\f0e2"; }
294 | .icon-legal:before { content: "\f0e3"; }
295 | .icon-dashboard:before { content: "\f0e4"; }
296 | .icon-comment-alt:before { content: "\f0e5"; }
297 | .icon-comments-alt:before { content: "\f0e6"; }
298 | .icon-bolt:before { content: "\f0e7"; }
299 | .icon-sitemap:before { content: "\f0e8"; }
300 | .icon-umbrella:before { content: "\f0e9"; }
301 | .icon-paste:before { content: "\f0ea"; }
302 |
303 | .icon-user-md:before { content: "\f200"; }
304 |
--------------------------------------------------------------------------------
/SmallestDotNet/css/m-buttons.min.css:
--------------------------------------------------------------------------------
1 | /*!
2 | * CSS3 Microsoft Metro Buttons
3 | * Inspired by Tim O'Donnell's CSS3 Google Buttons, Twitter Bootstrap, and Microsoft. Icons from glyphicons.com and Syncfusion's Metro Studio.
4 | * I do not claim ownership on the origin of design and icons.
5 | * Built by Ace Subido (http://github.com/ace-subido)
6 | */article,aside,details,figcaption,figure,footer,header,hgroup,nav,section{display:block}audio,canvas,video{display:inline-block;*display:inline;*zoom:1}audio:not([controls]){display:none}html{font-size:100%;-webkit-text-size-adjust:100%;-ms-text-size-adjust:100%}a:focus{outline:thin dotted;outline:5px auto -webkit-focus-ring-color;outline-offset:-2px}a:hover,a:active{outline:0}sub,sup{position:relative;font-size:75%;line-height:0;vertical-align:baseline}sup{top:-0.5em}sub{bottom:-0.25em}img{max-width:100%;height:auto;border:0;-ms-interpolation-mode:bicubic}button,input,select,textarea{margin:0;font-size:100%}button,input{*overflow:visible;line-height:normal}button::-moz-focus-inner,input::-moz-focus-inner{padding:0;border:0}button,input[type="button"],input[type="reset"],input[type="submit"]{cursor:pointer;-webkit-appearance:button;-moz-appearance:none}@-moz-document url-prefix(){button,input[type="button"],input[type="reset"],input[type="submit"]{cursor:pointer;padding:6px 14px}}input[type="search"]{-webkit-appearance:textfield;-webkit-box-sizing:content-box;-moz-box-sizing:content-box;box-sizing:content-box}input[type="search"]::-webkit-search-decoration,input[type="search"]::-webkit-search-cancel-button{-webkit-appearance:none}textarea{overflow:auto;vertical-align:top}.dropdown{position:relative}.dropdown-toggle{*margin-bottom:-3px}.dropdown-toggle:active,.open .dropdown-toggle{outline:0}.caret{display:inline-block;width:0;height:0;text-indent:-99999px;*text-indent:0;vertical-align:top;margin-top:5px;margin-left:2px;margin-right:2px;border-left:4px solid transparent;border-right:4px solid transparent;border-top:4px solid black;opacity:.5;filter:alpha(opacity=50);content:"\2193"}.caret.white{border-left:4px solid transparent;border-right:4px solid transparent;border-top:4px solid white;opacity:.95;filter:alpha(opacity=95)}.dropdown .caret{margin-top:8px;margin-left:2px}.dropdown:hover .caret,.open.dropdown .caret{opacity:1;filter:alpha(opacity=100)}.m-dropdown-menu{position:absolute;top:98%;left:0;z-index:1000;float:left;display:none;min-width:225px;max-width:225px;padding:0 0 6px 0;margin:0;list-style:none;background-color:white;-webkit-box-shadow:0 1px 8px rgba(0,0,0,0.1);-moz-box-shadow:0 1px 8px rgba(0,0,0,0.1);box-shadow:0 1px 8px rgba(0,0,0,0.1);font-size:14px;font-family:"Segoe UI",Helvetica,Arial,sans-serif;border:1px solid #eee}.m-dropdown-menu.bottom-up{top:auto;bottom:100%;margin-bottom:2px}.m-dropdown-menu .divider{border-top:1px solid #ebebeb;margin-top:9px;margin-bottom:10px;padding:0;cursor:default}.m-dropdown-menu a{position:relative;padding:6px 0 6px 30px;color:#333;text-decoration:none;display:block;clear:both;font-weight:normal;line-height:18px;white-space:nowrap}.m-dropdown-menu a [class^="icon-"]{position:absolute;left:7px;top:9px}.m-dropdown-menu li>a:hover,.m-dropdown-menu .active>a,.m-dropdown-menu .active>a:hover{text-decoration:none;background-color:#eee}.dropdown.open{*z-index:1000}.dropdown.open .dropdown-toggle{color:#08c;background:#ccc;background:rgba(0,0,0,0.3)}.dropdown.open .m-dropdown-menu{display:block}.m-btn{border-style: none;
7 | border-color: inherit;
8 | border-width: 0;
9 | position:relative;display:inline-block;overflow:visible;padding:10px 14px;margin-top:8px;cursor:pointer;outline:0;background-color:#eee;background-repeat: repeat-x;
10 | -webkit-background-clip: padding;
11 | -moz-background-clip: padding;
12 | background-clip: padding;
13 | zoom: 1;
14 | z-index: 1;
15 | display: inline;
16 | font-family: "Segoe UI", Helvetica, Arial, sans-serif;
17 | font-size: 14px;
18 | line-height: 14px;
19 | color: #333;
20 | min-width: 42px;
21 | text-shadow: #fff 0 1px 0;
22 | text-align: center;
23 | text-decoration: none;
24 | white-space: nowrap;
25 | vertical-align: inherit;
26 | background-image: linear-gradient(top,#eee,#eee);
27 | *margin-left: 0;
28 | margin-right: 0;
29 | margin-bottom: 0;
30 | }.m-btn:hover,.m-btn:focus,.m-btn:active,.m-btn.active{color:#333;text-decoration:none;background-color:#dcdcdc;background-repeat: repeat-x;
31 | z-index: 100;
32 | outline: 0;
33 | background-image: linear-gradient(top,#dcdcdc,#dcdcdc);
34 | }.m-btn:active,.m-btn.active{background-color:#eee;background-repeat: repeat-x;
35 | -webkit-box-shadow: inset 0 1px 8px rgba(0, 0, 0, 0.25);
36 | -moz-box-shadow: inset 0 1px 8px rgba(0, 0, 0, 0.25);
37 | box-shadow: inset 0 1px 8px rgba(0, 0, 0, 0.25);
38 | background-image: linear-gradient(top,#eee,#dcdcdc);
39 | }.m-btn:focus{border-color:#4d90fe}.m-btn::-moz-focus-inner{padding:0;border:0}.m-btn.red-stripe{border-left:3px solid #d84a38}.m-btn.blue-stripe{border-left:3px solid #4d90fe}.m-btn.purple-stripe{border-left:3px solid #852b99}.m-btn.green-stripe{border-left:3px solid #35aa47}.m-btn.red:active,.m-btn.red.active,.m-btn.red.disabled,.m-btn.red[disabled],.m-btn.blue:active,.m-btn.blue.active,.m-btn.blue.disabled,.m-btn.blue[disabled],.m-btn.purple:active,.m-btn.purple.active,.m-btn.purple.disabled,.m-btn.purple[disabled],.m-btn.green:active,.m-btn.green.active,.m-btn.green.disabled,.m-btn.green[disabled]{-webkit-box-shadow:inset 0 1px 8px rgba(0,0,0,0.25);-moz-box-shadow:inset 0 1px 8px rgba(0,0,0,0.25);box-shadow:inset 0 1px 8px rgba(0,0,0,0.25);color:white!important}.m-btn.red.disabled,.m-btn.red[disabled],.m-btn.blue.disabled,.m-btn.blue[disabled],.m-btn.purple.disabled,.m-btn.purple[disabled],.m-btn.green.disabled,.m-btn.green[disabled]{opacity:.7}.m-btn.red{color:white;text-shadow:none;background-color:#d84a38;background-repeat: repeat-x;
40 | background-image: linear-gradient(top,#dd4b39,#d14836);
41 | }.m-btn.red:hover,.m-btn.red:focus,.m-btn.red:active,.m-btn.red.active,.m-btn.red[disabled],.m-btn.red.disabled{background-color:#c53727;background-repeat: repeat-x;
42 | background-image: linear-gradient(top,#c53727,#c53727);
43 | }.m-btn.red:active,.m-btn.red.active{background-color:#dd4b39;background-repeat: repeat-x;
44 | background-image: linear-gradient(top,#dd4b39,#c53727);
45 | }.m-btn.blue{color:white;text-shadow:none;background-color:#4d90fe;background-repeat: repeat-x;
46 | background-image: linear-gradient(top,#4d90fe,#4787ed);
47 | }.m-btn.blue:hover,.m-btn.blue:focus,.m-btn.blue:active,.m-btn.blue.active,.m-btn.blue[disabled],.m-btn.blue.disabled{background-color:#0072bb;background-repeat: repeat-x;
48 | background-image: linear-gradient(top,#0072bb,#0072bb);
49 | }.m-btn.blue:active,.m-btn.blue.active{background-color:#4d90fe;background-repeat: repeat-x;
50 | background-image: linear-gradient(top,#4d90fe,#0072bb);
51 | }.m-btn.green{color:white;text-shadow:none;background-color:#35aa47;background-repeat: repeat-x;
52 | background-image: linear-gradient(top,#35aa47,#35aa47);
53 | }.m-btn.green:hover,.m-btn.green:focus,.m-btn.green:active,.m-btn.green.active,.m-btn.green.disabled,.m-btn.green[disabled]{background-color:#1d943b;background-repeat: repeat-x;
54 | background-image: linear-gradient(top,#1d943b,#1d943b);
55 | }.m-btn.green:active,.m-btn.green.active{background-color:#35aa47;background-repeat: repeat-x;
56 | background-image: linear-gradient(top,#35aa47,#1d943b);
57 | }.m-btn.purple{color:white;text-shadow:none;background-color:#852b99;background-repeat: repeat-x;
58 | background-image: linear-gradient(top,#852b99,#852b99);
59 | }.m-btn.purple:hover,.m-btn.purple:focus,.m-btn.purple:active,.m-btn.purple.active,.m-btn.purple.disabled,.m-btn.purple[disabled]{background-color:#6d1b81;background-repeat: repeat-x;
60 | background-image: linear-gradient(top,#6d1b81,#6d1b81);
61 | }.m-btn.purple:active,.m-btn.purple.active{background-color:#35aa47;background-repeat: repeat-x;
62 | background-image: linear-gradient(top,#852b99,#6d1b81);
63 | }.sm{font-size:11px}.mini{height:13px;font-size:11px;line-height:13px;padding:4px 10px}.big{height:38px;font-size:18px;line-height:38px;padding:20px 26px}.m-btn.disabled,.m-btn[disabled]{color:#999;background-color:#f5f5f5;background-repeat: repeat-x;
64 | cursor: default;
65 | -webkit-box-shadow: inset 0 1px 6px rgba(0, 0, 0, 0.25);
66 | -moz-box-shadow: inset 0 1px 6px rgba(0, 0, 0, 0.25);
67 | box-shadow: inset 0 1px 6px rgba(0, 0, 0, 0.25);
68 | background-image: linear-gradient(top,#eee,#ddd);
69 | }.m-btn.icn-only{min-width:14px}.m-btn.bigicn-only{min-width:34px}.m-btn-group{position:relative;display:inline-block;list-style:none;padding:0;margin:0;zoom:1;*display:inline}.m-btn+.m-btn,.m-btn+.m-btn-group,.m-btn-group+.m-btn,.m-btn-group+.m-btn-group{margin-left:15px}.m-btn.dropdown-carettoggle{min-width:5px;height:18px;padding:8px}.m-btn.dropdown-carettoggle>.caret{margin-top:8px}.m-btn.caret:hover{opacity:1}.m-btn-group .m-btn{position:relative;float:left;margin-left:-1px;-webkit-border-radius:0;-moz-border-radius:0;border-radius:0}.m-btn-group .m-btn:first-child{margin-left:0}.m-btn-strip .m-btn,.m-btn-strip .m-btn-group{vertical-align:top}.m-btn-group.open{*z-index:1000}.m-btn-group.open .dropdown-carettoggle,.m-btn-group.open .dropdown-toggle{background-image:none;-webkit-box-shadow:inset 0 1px 6px rgba(0,0,0,0.2);-moz-box-shadow:inset 0 1px 6px rgba(0,0,0,0.2);box-shadow:inset 0 1px 6px rgba(0,0,0,0.2)}.m-btn-group.open .m-dropdown-menu{display:block;margin-top:1px}
--------------------------------------------------------------------------------
/SmallestDotNet/css/main.css:
--------------------------------------------------------------------------------
1 | .green
2 | {
3 | color: #9EC630;
4 | }
5 |
6 | .gray
7 | {
8 | color: #BFBFBF;
9 | }
10 |
11 | #header h1#logo
12 | {
13 | margin: 0;
14 | padding: 0;
15 | font: bolder 4.1em 'Trebuchet MS', Arial, Sans-serif;
16 | letter-spacing: -2px;
17 | text-transform: lowercase;
18 | top: 0;
19 | left: 5px;
20 | }
21 |
22 | #header h2#slogan
23 | {
24 | color: #666666;
25 | text-indent: 0;
26 | font: bold 11px Tahoma, 'trebuchet MS', Sans-serif;
27 | text-transform: none;
28 | }
29 |
30 | .result-header
31 | {
32 | background-image: url(/img/hero_home.jpg);
33 | -moz-background-size: 100%;
34 | -o-background-size: 100%;
35 | -webkit-background-size: 100%;
36 | background-size: 100%;
37 | color: #fff;
38 | padding: 15px 15px 30px 15px
39 | }
40 |
41 | .result-header a
42 | {
43 | color: #fff;
44 | text-decoration: underline;
45 | }
46 |
47 | .result-header a:hover
48 | {
49 | color: #aaa;
50 | }
51 |
52 | #getdotnet, #checkdotnet
53 | {
54 | color: #000;
55 | text-decoration: none;
56 | font-size: 40px;
57 | }
58 |
59 | body
60 | {
61 | margin-top: 50px;
62 | }
63 |
64 |
65 | @media (max-width: 980px)
66 | {
67 | body
68 | {
69 | margin-top: 0;
70 | }
71 | .result-header
72 | {
73 | background: #2080c0;
74 |
75 | }
76 |
77 | .m-btn.blue
78 | {
79 | clear: both;
80 | float: left;
81 | margin: 20px;
82 | }
83 |
84 | #getdotnet, #checkdotnet
85 | {
86 | color: #000;
87 | text-decoration: none;
88 | font-size: 24px;
89 | }
90 |
91 | }
92 |
--------------------------------------------------------------------------------
/SmallestDotNet/font/fontawesome-webfont.eot:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shanselman/SmallestDotNet/8a60a223929137d036b0730f24b44c83ecb8cbe4/SmallestDotNet/font/fontawesome-webfont.eot
--------------------------------------------------------------------------------
/SmallestDotNet/font/fontawesome-webfont.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shanselman/SmallestDotNet/8a60a223929137d036b0730f24b44c83ecb8cbe4/SmallestDotNet/font/fontawesome-webfont.ttf
--------------------------------------------------------------------------------
/SmallestDotNet/font/fontawesome-webfont.woff:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shanselman/SmallestDotNet/8a60a223929137d036b0730f24b44c83ecb8cbe4/SmallestDotNet/font/fontawesome-webfont.woff
--------------------------------------------------------------------------------
/SmallestDotNet/img/glyphicons-halflings-white.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shanselman/SmallestDotNet/8a60a223929137d036b0730f24b44c83ecb8cbe4/SmallestDotNet/img/glyphicons-halflings-white.png
--------------------------------------------------------------------------------
/SmallestDotNet/img/glyphicons-halflings.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shanselman/SmallestDotNet/8a60a223929137d036b0730f24b44c83ecb8cbe4/SmallestDotNet/img/glyphicons-halflings.png
--------------------------------------------------------------------------------
/SmallestDotNet/img/hero_home.jpg:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/shanselman/SmallestDotNet/8a60a223929137d036b0730f24b44c83ecb8cbe4/SmallestDotNet/img/hero_home.jpg
--------------------------------------------------------------------------------
/SmallestDotNet/javascript.ashx:
--------------------------------------------------------------------------------
1 | <%@ WebHandler Language="C#" Class="SmallestDotNet" %>
2 |
3 | using System;
4 | using System.Web;
5 |
6 | public class SmallestDotNet : IHttpHandler
7 | {
8 |
9 | public void ProcessRequest(HttpContext context)
10 | {
11 | WriteToResponse("");
12 | context.Response.ContentType = "text/javascript";
13 |
14 | WriteToResponse(Helpers.GetUpdateInformation(context.Request.UserAgent, context.Request.Browser.ClrVersion.ToString()).Text.Replace("'", @"\'").Replace(Environment.NewLine, " "));
15 | WriteToResponse(" ");
16 | }
17 |
18 | private void WriteToResponse(string s)
19 | {
20 | HttpResponse r = HttpContext.Current.Response;
21 | r.Write(String.Format("document.write('{0}')\r\n", s));
22 | }
23 |
24 | public bool IsReusable
25 | {
26 | get
27 | {
28 | return false;
29 | }
30 | }
31 |
32 | }
--------------------------------------------------------------------------------
/SmallestDotNet/javascriptdom.ashx:
--------------------------------------------------------------------------------
1 | <%@ WebHandler Language="C#" Class="SmallestDotNet" %>
2 |
3 | using System;
4 | using System.Web;
5 | using SmallestDotNetLib;
6 |
7 | public class SmallestDotNet : IHttpHandler
8 | {
9 |
10 | public void ProcessRequest(HttpContext context)
11 | {
12 | context.Response.ContentType = "text/javascript";
13 |
14 | dr("SmallestDotNet = {};");
15 |
16 | dr(JsonVersions.WriteLatestVersions(context.Request.UserAgent));
17 |
18 | dr(JsonVersions.WriteAllVersions(context.Request.UserAgent));
19 |
20 | dr(JsonVersions.WriteDownloads().Trim());
21 |
22 |
23 | if (context.Request.UserAgent.Contains("Mac") || context.Request.UserAgent.Contains("nix"))
24 | {
25 | dr(@"
26 | SmallestDotNet = {};
27 | SmallestDotNet.latestVersion = null;
28 | SmallestDotNet.allVersions = [];
29 | ");
30 | }
31 |
32 | }
33 |
34 | private static void dr(string s)
35 | {
36 | HttpResponse r = HttpContext.Current.Response;
37 | r.Write(s);
38 | }
39 |
40 | public bool IsReusable
41 | {
42 | get
43 | {
44 | return false;
45 | }
46 | }
47 |
48 | }
49 |
--------------------------------------------------------------------------------
/SmallestDotNet/js/bootstrap.min.js:
--------------------------------------------------------------------------------
1 | /*!
2 | * Bootstrap.js by @fat & @mdo
3 | * Copyright 2012 Twitter, Inc.
4 | * http://www.apache.org/licenses/LICENSE-2.0.txt
5 | */
6 | !function(e){e(function(){"use strict";e.support.transition=function(){var e=function(){var e=document.createElement("bootstrap"),t={WebkitTransition:"webkitTransitionEnd",MozTransition:"transitionend",OTransition:"oTransitionEnd otransitionend",transition:"transitionend"},n;for(n in t)if(e.style[n]!==undefined)return t[n]}();return e&&{end:e}}()})}(window.jQuery),!function(e){"use strict";var t='[data-dismiss="alert"]',n=function(n){e(n).on("click",t,this.close)};n.prototype.close=function(t){function s(){i.trigger("closed").remove()}var n=e(this),r=n.attr("data-target"),i;r||(r=n.attr("href"),r=r&&r.replace(/.*(?=#[^\s]*$)/,"")),i=e(r),t&&t.preventDefault(),i.length||(i=n.hasClass("alert")?n:n.parent()),i.trigger(t=e.Event("close"));if(t.isDefaultPrevented())return;i.removeClass("in"),e.support.transition&&i.hasClass("fade")?i.on(e.support.transition.end,s):s()},e.fn.alert=function(t){return this.each(function(){var r=e(this),i=r.data("alert");i||r.data("alert",i=new n(this)),typeof t=="string"&&i[t].call(r)})},e.fn.alert.Constructor=n,e(function(){e("body").on("click.alert.data-api",t,n.prototype.close)})}(window.jQuery),!function(e){"use strict";var t=function(t,n){this.$element=e(t),this.options=e.extend({},e.fn.button.defaults,n)};t.prototype.setState=function(e){var t="disabled",n=this.$element,r=n.data(),i=n.is("input")?"val":"html";e+="Text",r.resetText||n.data("resetText",n[i]()),n[i](r[e]||this.options[e]),setTimeout(function(){e=="loadingText"?n.addClass(t).attr(t,t):n.removeClass(t).removeAttr(t)},0)},t.prototype.toggle=function(){var e=this.$element.closest('[data-toggle="buttons-radio"]');e&&e.find(".active").removeClass("active"),this.$element.toggleClass("active")},e.fn.button=function(n){return this.each(function(){var r=e(this),i=r.data("button"),s=typeof n=="object"&&n;i||r.data("button",i=new t(this,s)),n=="toggle"?i.toggle():n&&i.setState(n)})},e.fn.button.defaults={loadingText:"loading..."},e.fn.button.Constructor=t,e(function(){e("body").on("click.button.data-api","[data-toggle^=button]",function(t){var n=e(t.target);n.hasClass("btn")||(n=n.closest(".btn")),n.button("toggle")})})}(window.jQuery),!function(e){"use strict";var t=function(t,n){this.$element=e(t),this.options=n,this.options.slide&&this.slide(this.options.slide),this.options.pause=="hover"&&this.$element.on("mouseenter",e.proxy(this.pause,this)).on("mouseleave",e.proxy(this.cycle,this))};t.prototype={cycle:function(t){return t||(this.paused=!1),this.options.interval&&!this.paused&&(this.interval=setInterval(e.proxy(this.next,this),this.options.interval)),this},to:function(t){var n=this.$element.find(".item.active"),r=n.parent().children(),i=r.index(n),s=this;if(t>r.length-1||t<0)return;return this.sliding?this.$element.one("slid",function(){s.to(t)}):i==t?this.pause().cycle():this.slide(t>i?"next":"prev",e(r[t]))},pause:function(t){return t||(this.paused=!0),this.$element.find(".next, .prev").length&&e.support.transition.end&&(this.$element.trigger(e.support.transition.end),this.cycle()),clearInterval(this.interval),this.interval=null,this},next:function(){if(this.sliding)return;return this.slide("next")},prev:function(){if(this.sliding)return;return this.slide("prev")},slide:function(t,n){var r=this.$element.find(".item.active"),i=n||r[t](),s=this.interval,o=t=="next"?"left":"right",u=t=="next"?"first":"last",a=this,f=e.Event("slide",{relatedTarget:i[0]});this.sliding=!0,s&&this.pause(),i=i.length?i:this.$element.find(".item")[u]();if(i.hasClass("active"))return;if(e.support.transition&&this.$element.hasClass("slide")){this.$element.trigger(f);if(f.isDefaultPrevented())return;i.addClass(t),i[0].offsetWidth,r.addClass(o),i.addClass(o),this.$element.one(e.support.transition.end,function(){i.removeClass([t,o].join(" ")).addClass("active"),r.removeClass(["active",o].join(" ")),a.sliding=!1,setTimeout(function(){a.$element.trigger("slid")},0)})}else{this.$element.trigger(f);if(f.isDefaultPrevented())return;r.removeClass("active"),i.addClass("active"),this.sliding=!1,this.$element.trigger("slid")}return s&&this.cycle(),this}},e.fn.carousel=function(n){return this.each(function(){var r=e(this),i=r.data("carousel"),s=e.extend({},e.fn.carousel.defaults,typeof n=="object"&&n),o=typeof n=="string"?n:s.slide;i||r.data("carousel",i=new t(this,s)),typeof n=="number"?i.to(n):o?i[o]():s.interval&&i.cycle()})},e.fn.carousel.defaults={interval:5e3,pause:"hover"},e.fn.carousel.Constructor=t,e(function(){e("body").on("click.carousel.data-api","[data-slide]",function(t){var n=e(this),r,i=e(n.attr("data-target")||(r=n.attr("href"))&&r.replace(/.*(?=#[^\s]+$)/,"")),s=!i.data("modal")&&e.extend({},i.data(),n.data());i.carousel(s),t.preventDefault()})})}(window.jQuery),!function(e){"use strict";var t=function(t,n){this.$element=e(t),this.options=e.extend({},e.fn.collapse.defaults,n),this.options.parent&&(this.$parent=e(this.options.parent)),this.options.toggle&&this.toggle()};t.prototype={constructor:t,dimension:function(){var e=this.$element.hasClass("width");return e?"width":"height"},show:function(){var t,n,r,i;if(this.transitioning)return;t=this.dimension(),n=e.camelCase(["scroll",t].join("-")),r=this.$parent&&this.$parent.find("> .accordion-group > .in");if(r&&r.length){i=r.data("collapse");if(i&&i.transitioning)return;r.collapse("hide"),i||r.data("collapse",null)}this.$element[t](0),this.transition("addClass",e.Event("show"),"shown"),e.support.transition&&this.$element[t](this.$element[0][n])},hide:function(){var t;if(this.transitioning)return;t=this.dimension(),this.reset(this.$element[t]()),this.transition("removeClass",e.Event("hide"),"hidden"),this.$element[t](0)},reset:function(e){var t=this.dimension();return this.$element.removeClass("collapse")[t](e||"auto")[0].offsetWidth,this.$element[e!==null?"addClass":"removeClass"]("collapse"),this},transition:function(t,n,r){var i=this,s=function(){n.type=="show"&&i.reset(),i.transitioning=0,i.$element.trigger(r)};this.$element.trigger(n);if(n.isDefaultPrevented())return;this.transitioning=1,this.$element[t]("in"),e.support.transition&&this.$element.hasClass("collapse")?this.$element.one(e.support.transition.end,s):s()},toggle:function(){this[this.$element.hasClass("in")?"hide":"show"]()}},e.fn.collapse=function(n){return this.each(function(){var r=e(this),i=r.data("collapse"),s=typeof n=="object"&&n;i||r.data("collapse",i=new t(this,s)),typeof n=="string"&&i[n]()})},e.fn.collapse.defaults={toggle:!0},e.fn.collapse.Constructor=t,e(function(){e("body").on("click.collapse.data-api","[data-toggle=collapse]",function(t){var n=e(this),r,i=n.attr("data-target")||t.preventDefault()||(r=n.attr("href"))&&r.replace(/.*(?=#[^\s]+$)/,""),s=e(i).data("collapse")?"toggle":n.data();n[e(i).hasClass("in")?"addClass":"removeClass"]("collapsed"),e(i).collapse(s)})})}(window.jQuery),!function(e){"use strict";function r(){i(e(t)).removeClass("open")}function i(t){var n=t.attr("data-target"),r;return n||(n=t.attr("href"),n=n&&/#/.test(n)&&n.replace(/.*(?=#[^\s]*$)/,"")),r=e(n),r.length||(r=t.parent()),r}var t="[data-toggle=dropdown]",n=function(t){var n=e(t).on("click.dropdown.data-api",this.toggle);e("html").on("click.dropdown.data-api",function(){n.parent().removeClass("open")})};n.prototype={constructor:n,toggle:function(t){var n=e(this),s,o;if(n.is(".disabled, :disabled"))return;return s=i(n),o=s.hasClass("open"),r(),o||(s.toggleClass("open"),n.focus()),!1},keydown:function(t){var n,r,s,o,u,a;if(!/(38|40|27)/.test(t.keyCode))return;n=e(this),t.preventDefault(),t.stopPropagation();if(n.is(".disabled, :disabled"))return;o=i(n),u=o.hasClass("open");if(!u||u&&t.keyCode==27)return n.click();r=e("[role=menu] li:not(.divider) a",o);if(!r.length)return;a=r.index(r.filter(":focus")),t.keyCode==38&&a>0&&a--,t.keyCode==40&&a ').appendTo(document.body),this.options.backdrop!="static"&&this.$backdrop.click(e.proxy(this.hide,this)),i&&this.$backdrop[0].offsetWidth,this.$backdrop.addClass("in"),i?this.$backdrop.one(e.support.transition.end,t):t()}else!this.isShown&&this.$backdrop?(this.$backdrop.removeClass("in"),e.support.transition&&this.$element.hasClass("fade")?this.$backdrop.one(e.support.transition.end,e.proxy(this.removeBackdrop,this)):this.removeBackdrop()):t&&t()}},e.fn.modal=function(n){return this.each(function(){var r=e(this),i=r.data("modal"),s=e.extend({},e.fn.modal.defaults,r.data(),typeof n=="object"&&n);i||r.data("modal",i=new t(this,s)),typeof n=="string"?i[n]():s.show&&i.show()})},e.fn.modal.defaults={backdrop:!0,keyboard:!0,show:!0},e.fn.modal.Constructor=t,e(function(){e("body").on("click.modal.data-api",'[data-toggle="modal"]',function(t){var n=e(this),r=n.attr("href"),i=e(n.attr("data-target")||r&&r.replace(/.*(?=#[^\s]+$)/,"")),s=i.data("modal")?"toggle":e.extend({remote:!/#/.test(r)&&r},i.data(),n.data());t.preventDefault(),i.modal(s).one("hide",function(){n.focus()})})})}(window.jQuery),!function(e){"use strict";var t=function(e,t){this.init("tooltip",e,t)};t.prototype={constructor:t,init:function(t,n,r){var i,s;this.type=t,this.$element=e(n),this.options=this.getOptions(r),this.enabled=!0,this.options.trigger=="click"?this.$element.on("click."+this.type,this.options.selector,e.proxy(this.toggle,this)):this.options.trigger!="manual"&&(i=this.options.trigger=="hover"?"mouseenter":"focus",s=this.options.trigger=="hover"?"mouseleave":"blur",this.$element.on(i+"."+this.type,this.options.selector,e.proxy(this.enter,this)),this.$element.on(s+"."+this.type,this.options.selector,e.proxy(this.leave,this))),this.options.selector?this._options=e.extend({},this.options,{trigger:"manual",selector:""}):this.fixTitle()},getOptions:function(t){return t=e.extend({},e.fn[this.type].defaults,t,this.$element.data()),t.delay&&typeof t.delay=="number"&&(t.delay={show:t.delay,hide:t.delay}),t},enter:function(t){var n=e(t.currentTarget)[this.type](this._options).data(this.type);if(!n.options.delay||!n.options.delay.show)return n.show();clearTimeout(this.timeout),n.hoverState="in",this.timeout=setTimeout(function(){n.hoverState=="in"&&n.show()},n.options.delay.show)},leave:function(t){var n=e(t.currentTarget)[this.type](this._options).data(this.type);this.timeout&&clearTimeout(this.timeout);if(!n.options.delay||!n.options.delay.hide)return n.hide();n.hoverState="out",this.timeout=setTimeout(function(){n.hoverState=="out"&&n.hide()},n.options.delay.hide)},show:function(){var e,t,n,r,i,s,o;if(this.hasContent()&&this.enabled){e=this.tip(),this.setContent(),this.options.animation&&e.addClass("fade"),s=typeof this.options.placement=="function"?this.options.placement.call(this,e[0],this.$element[0]):this.options.placement,t=/in/.test(s),e.remove().css({top:0,left:0,display:"block"}).appendTo(t?this.$element:document.body),n=this.getPosition(t),r=e[0].offsetWidth,i=e[0].offsetHeight;switch(t?s.split(" ")[1]:s){case"bottom":o={top:n.top+n.height,left:n.left+n.width/2-r/2};break;case"top":o={top:n.top-i,left:n.left+n.width/2-r/2};break;case"left":o={top:n.top+n.height/2-i/2,left:n.left-r};break;case"right":o={top:n.top+n.height/2-i/2,left:n.left+n.width}}e.css(o).addClass(s).addClass("in")}},setContent:function(){var e=this.tip(),t=this.getTitle();e.find(".tooltip-inner")[this.options.html?"html":"text"](t),e.removeClass("fade in top bottom left right")},hide:function(){function r(){var t=setTimeout(function(){n.off(e.support.transition.end).remove()},500);n.one(e.support.transition.end,function(){clearTimeout(t),n.remove()})}var t=this,n=this.tip();return n.removeClass("in"),e.support.transition&&this.$tip.hasClass("fade")?r():n.remove(),this},fixTitle:function(){var e=this.$element;(e.attr("title")||typeof e.attr("data-original-title")!="string")&&e.attr("data-original-title",e.attr("title")||"").removeAttr("title")},hasContent:function(){return this.getTitle()},getPosition:function(t){return e.extend({},t?{top:0,left:0}:this.$element.offset(),{width:this.$element[0].offsetWidth,height:this.$element[0].offsetHeight})},getTitle:function(){var e,t=this.$element,n=this.options;return e=t.attr("data-original-title")||(typeof n.title=="function"?n.title.call(t[0]):n.title),e},tip:function(){return this.$tip=this.$tip||e(this.options.template)},validate:function(){this.$element[0].parentNode||(this.hide(),this.$element=null,this.options=null)},enable:function(){this.enabled=!0},disable:function(){this.enabled=!1},toggleEnabled:function(){this.enabled=!this.enabled},toggle:function(){this[this.tip().hasClass("in")?"hide":"show"]()},destroy:function(){this.hide().$element.off("."+this.type).removeData(this.type)}},e.fn.tooltip=function(n){return this.each(function(){var r=e(this),i=r.data("tooltip"),s=typeof n=="object"&&n;i||r.data("tooltip",i=new t(this,s)),typeof n=="string"&&i[n]()})},e.fn.tooltip.Constructor=t,e.fn.tooltip.defaults={animation:!0,placement:"top",selector:!1,template:'',trigger:"hover",title:"",delay:0,html:!0}}(window.jQuery),!function(e){"use strict";var t=function(e,t){this.init("popover",e,t)};t.prototype=e.extend({},e.fn.tooltip.Constructor.prototype,{constructor:t,setContent:function(){var e=this.tip(),t=this.getTitle(),n=this.getContent();e.find(".popover-title")[this.options.html?"html":"text"](t),e.find(".popover-content > *")[this.options.html?"html":"text"](n),e.removeClass("fade top bottom left right in")},hasContent:function(){return this.getTitle()||this.getContent()},getContent:function(){var e,t=this.$element,n=this.options;return e=t.attr("data-content")||(typeof n.content=="function"?n.content.call(t[0]):n.content),e},tip:function(){return this.$tip||(this.$tip=e(this.options.template)),this.$tip},destroy:function(){this.hide().$element.off("."+this.type).removeData(this.type)}}),e.fn.popover=function(n){return this.each(function(){var r=e(this),i=r.data("popover"),s=typeof n=="object"&&n;i||r.data("popover",i=new t(this,s)),typeof n=="string"&&i[n]()})},e.fn.popover.Constructor=t,e.fn.popover.defaults=e.extend({},e.fn.tooltip.defaults,{placement:"right",trigger:"click",content:"",template:''})}(window.jQuery),!function(e){"use strict";function t(t,n){var r=e.proxy(this.process,this),i=e(t).is("body")?e(window):e(t),s;this.options=e.extend({},e.fn.scrollspy.defaults,n),this.$scrollElement=i.on("scroll.scroll-spy.data-api",r),this.selector=(this.options.target||(s=e(t).attr("href"))&&s.replace(/.*(?=#[^\s]+$)/,"")||"")+" .nav li > a",this.$body=e("body"),this.refresh(),this.process()}t.prototype={constructor:t,refresh:function(){var t=this,n;this.offsets=e([]),this.targets=e([]),n=this.$body.find(this.selector).map(function(){var t=e(this),n=t.data("target")||t.attr("href"),r=/^#\w/.test(n)&&e(n);return r&&r.length&&[[r.position().top,n]]||null}).sort(function(e,t){return e[0]-t[0]}).each(function(){t.offsets.push(this[0]),t.targets.push(this[1])})},process:function(){var e=this.$scrollElement.scrollTop()+this.options.offset,t=this.$scrollElement[0].scrollHeight||this.$body[0].scrollHeight,n=t-this.$scrollElement.height(),r=this.offsets,i=this.targets,s=this.activeTarget,o;if(e>=n)return s!=(o=i.last()[0])&&this.activate(o);for(o=r.length;o--;)s!=i[o]&&e>=r[o]&&(!r[o+1]||e<=r[o+1])&&this.activate(i[o])},activate:function(t){var n,r;this.activeTarget=t,e(this.selector).parent(".active").removeClass("active"),r=this.selector+'[data-target="'+t+'"],'+this.selector+'[href="'+t+'"]',n=e(r).parent("li").addClass("active"),n.parent(".dropdown-menu").length&&(n=n.closest("li.dropdown").addClass("active")),n.trigger("activate")}},e.fn.scrollspy=function(n){return this.each(function(){var r=e(this),i=r.data("scrollspy"),s=typeof n=="object"&&n;i||r.data("scrollspy",i=new t(this,s)),typeof n=="string"&&i[n]()})},e.fn.scrollspy.Constructor=t,e.fn.scrollspy.defaults={offset:10},e(window).on("load",function(){e('[data-spy="scroll"]').each(function(){var t=e(this);t.scrollspy(t.data())})})}(window.jQuery),!function(e){"use strict";var t=function(t){this.element=e(t)};t.prototype={constructor:t,show:function(){var t=this.element,n=t.closest("ul:not(.dropdown-menu)"),r=t.attr("data-target"),i,s,o;r||(r=t.attr("href"),r=r&&r.replace(/.*(?=#[^\s]*$)/,""));if(t.parent("li").hasClass("active"))return;i=n.find(".active a").last()[0],o=e.Event("show",{relatedTarget:i}),t.trigger(o);if(o.isDefaultPrevented())return;s=e(r),this.activate(t.parent("li"),n),this.activate(s,s.parent(),function(){t.trigger({type:"shown",relatedTarget:i})})},activate:function(t,n,r){function o(){i.removeClass("active").find("> .dropdown-menu > .active").removeClass("active"),t.addClass("active"),s?(t[0].offsetWidth,t.addClass("in")):t.removeClass("fade"),t.parent(".dropdown-menu")&&t.closest("li.dropdown").addClass("active"),r&&r()}var i=n.find("> .active"),s=r&&e.support.transition&&i.hasClass("fade");s?i.one(e.support.transition.end,o):o(),i.removeClass("in")}},e.fn.tab=function(n){return this.each(function(){var r=e(this),i=r.data("tab");i||r.data("tab",i=new t(this)),typeof n=="string"&&i[n]()})},e.fn.tab.Constructor=t,e(function(){e("body").on("click.tab.data-api",'[data-toggle="tab"], [data-toggle="pill"]',function(t){t.preventDefault(),e(this).tab("show")})})}(window.jQuery),!function(e){"use strict";var t=function(t,n){this.$element=e(t),this.options=e.extend({},e.fn.typeahead.defaults,n),this.matcher=this.options.matcher||this.matcher,this.sorter=this.options.sorter||this.sorter,this.highlighter=this.options.highlighter||this.highlighter,this.updater=this.options.updater||this.updater,this.$menu=e(this.options.menu).appendTo("body"),this.source=this.options.source,this.shown=!1,this.listen()};t.prototype={constructor:t,select:function(){var e=this.$menu.find(".active").attr("data-value");return this.$element.val(this.updater(e)).change(),this.hide()},updater:function(e){return e},show:function(){var t=e.extend({},this.$element.offset(),{height:this.$element[0].offsetHeight});return this.$menu.css({top:t.top+t.height,left:t.left}),this.$menu.show(),this.shown=!0,this},hide:function(){return this.$menu.hide(),this.shown=!1,this},lookup:function(t){var n;return this.query=this.$element.val(),!this.query||this.query.length"+t+""})},render:function(t){var n=this;return t=e(t).map(function(t,r){return t=e(n.options.item).attr("data-value",r),t.find("a").html(n.highlighter(r)),t[0]}),t.first().addClass("active"),this.$menu.html(t),this},next:function(t){var n=this.$menu.find(".active").removeClass("active"),r=n.next();r.length||(r=e(this.$menu.find("li")[0])),r.addClass("active")},prev:function(e){var t=this.$menu.find(".active").removeClass("active"),n=t.prev();n.length||(n=this.$menu.find("li").last()),n.addClass("active")},listen:function(){this.$element.on("blur",e.proxy(this.blur,this)).on("keypress",e.proxy(this.keypress,this)).on("keyup",e.proxy(this.keyup,this)),(e.browser.chrome||e.browser.webkit||e.browser.msie)&&this.$element.on("keydown",e.proxy(this.keydown,this)),this.$menu.on("click",e.proxy(this.click,this)).on("mouseenter","li",e.proxy(this.mouseenter,this))},move:function(e){if(!this.shown)return;switch(e.keyCode){case 9:case 13:case 27:e.preventDefault();break;case 38:e.preventDefault(),this.prev();break;case 40:e.preventDefault(),this.next()}e.stopPropagation()},keydown:function(t){this.suppressKeyPressRepeat=!~e.inArray(t.keyCode,[40,38,9,13,27]),this.move(t)},keypress:function(e){if(this.suppressKeyPressRepeat)return;this.move(e)},keyup:function(e){switch(e.keyCode){case 40:case 38:break;case 9:case 13:if(!this.shown)return;this.select();break;case 27:if(!this.shown)return;this.hide();break;default:this.lookup()}e.stopPropagation(),e.preventDefault()},blur:function(e){var t=this;setTimeout(function(){t.hide()},150)},click:function(e){e.stopPropagation(),e.preventDefault(),this.select()},mouseenter:function(t){this.$menu.find(".active").removeClass("active"),e(t.currentTarget).addClass("active")}},e.fn.typeahead=function(n){return this.each(function(){var r=e(this),i=r.data("typeahead"),s=typeof n=="object"&&n;i||r.data("typeahead",i=new t(this,s)),typeof n=="string"&&i[n]()})},e.fn.typeahead.defaults={source:[],items:8,menu:'',item:' ',minLength:1},e.fn.typeahead.Constructor=t,e(function(){e("body").on("focus.typeahead.data-api",'[data-provide="typeahead"]',function(t){var n=e(this);if(n.data("typeahead"))return;t.preventDefault(),n.typeahead(n.data())})})}(window.jQuery),!function(e){"use strict";var t=function(t,n){this.options=e.extend({},e.fn.affix.defaults,n),this.$window=e(window).on("scroll.affix.data-api",e.proxy(this.checkPosition,this)),this.$element=e(t),this.checkPosition()};t.prototype.checkPosition=function(){if(!this.$element.is(":visible"))return;var t=e(document).height(),n=this.$window.scrollTop(),r=this.$element.offset(),i=this.options.offset,s=i.bottom,o=i.top,u="affix affix-top affix-bottom",a;typeof i!="object"&&(s=o=i),typeof o=="function"&&(o=i.top()),typeof s=="function"&&(s=i.bottom()),a=this.unpin!=null&&n+this.unpin<=r.top?!1:s!=null&&r.top+this.$element.height()>=t-s?"bottom":o!=null&&n<=o?"top":!1;if(this.affixed===a)return;this.affixed=a,this.unpin=a=="bottom"?r.top-n:null,this.$element.removeClass(u).addClass("affix"+(a?"-"+a:""))},e.fn.affix=function(n){return this.each(function(){var r=e(this),i=r.data("affix"),s=typeof n=="object"&&n;i||r.data("affix",i=new t(this,s)),typeof n=="string"&&i[n]()})},e.fn.affix.Constructor=t,e.fn.affix.defaults={offset:0},e(window).on("load",function(){e('[data-spy="affix"]').each(function(){var t=e(this),n=t.data();n.offset=n.offset||{},n.offsetBottom&&(n.offset.bottom=n.offsetBottom),n.offsetTop&&(n.offset.top=n.offsetTop),t.affix(n)})})}(window.jQuery);
--------------------------------------------------------------------------------
/SmallestDotNet/testjs.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 | SmallestDotNet - Get the Smallest .NET Framework Download possible
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
31 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/BrowserSupport.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestDotNetLib
2 | {
3 | using System.Collections.Generic;
4 | using System.Linq;
5 |
6 | public class Browser
7 | {
8 | public string BrowserString { get; set; }
9 | public string BrowserPretty { get; set; }
10 | public bool CanGetCLRVersion { get; set; }
11 | }
12 |
13 | public class BrowserSupport
14 | {
15 | private static Browser Chrome = new Browser { BrowserPretty = "Google Chrome", BrowserString = "Chrome", CanGetCLRVersion = false };
16 | private static Browser Firefox = new Browser { BrowserPretty = "Mozilla Firefox", BrowserString = "Firefox", CanGetCLRVersion = false };
17 | private static Browser InternetExplorer = new Browser { BrowserPretty = "Internet Explorer", BrowserString = "Trident", CanGetCLRVersion = true };
18 | public static List Browsers = new List
19 | {
20 | Chrome,
21 | Firefox,
22 | InternetExplorer
23 | };
24 |
25 | public static Browser GetBrowser(string UserAgent)
26 | {
27 | return Browsers.FirstOrDefault(b => UserAgent.Contains(b.BrowserString));
28 | }
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/CLRVersion.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestDotNetLib
2 | {
3 | ///
4 | /// Represent A .NET CLR Version
5 | ///
6 | public class CLRVersion
7 | {
8 | ///
9 | /// The Major Version
10 | ///
11 | public int Major { get; set; }
12 |
13 | ///
14 | /// The Minor Version
15 | ///
16 | public int Minor { get; set;}
17 |
18 | ///
19 | /// The .NET CLR Profile (Full or Client)
20 | ///
21 | public string Profile { get; set; }
22 |
23 | ///
24 | /// Service Pack Version, null if none
25 | ///
26 | public int? ServicePack { get; set; }
27 |
28 | ///
29 | /// A URL to download the CLR Version Installer
30 | ///
31 | public string Url { get; set; }
32 |
33 | ///
34 | /// A Human readable string of the .NET CLR Version
35 | ///
36 | public string PrettyVersion { get; set; }
37 |
38 |
39 | public override bool Equals(object obj)
40 | {
41 | var version = (CLRVersion)obj;
42 |
43 | return version.Major == this.Major && version.Minor == this.Minor && version.Profile == this.Profile && version.ServicePack == this.ServicePack;
44 | }
45 |
46 | }
47 | }
48 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/CLRVersions.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestDotNetLib
2 | {
3 | using System;
4 | using System.Collections.Generic;
5 | using System.Linq;
6 |
7 | ///
8 | /// Contains Methods for discovering information about CLR Versions
9 | ///
10 | public class CLRVersions
11 | {
12 | public static CLRVersion NET10Full = new CLRVersion() { Major = 1, Minor = 0, Profile = "full", PrettyVersion = ".NET 1.0" };
13 | public static CLRVersion NET11Full = new CLRVersion() { Major = 1, Minor = 1, Profile = "full", Url = Constants.Version11URL, PrettyVersion = ".NET 1.1" };
14 | public static CLRVersion NET20Full = new CLRVersion() { Major = 2, Minor = 0, Profile = "full", Url = Constants.Version20URL, PrettyVersion = ".NET 2.0" };
15 | public static CLRVersion NET30Full = new CLRVersion() { Major = 3, Minor = 0, Profile = "full", Url = Constants.Version30URL, PrettyVersion = ".NET 3.0" };
16 | public static CLRVersion NET35Full = new CLRVersion() { Major = 3, Minor = 5, Profile = "full", PrettyVersion = ".NET 3.5" };
17 | public static CLRVersion NET35SP1Client = new CLRVersion() { Major = 3, Minor = 5, Profile = "client", ServicePack = 1, Url = Constants.Version35SP1ClientURL, PrettyVersion = ".NET 3.5 Client SP1" };
18 | public static CLRVersion NET35SP1Full = new CLRVersion() { Major = 3, Minor = 5, Profile = "full", ServicePack = 1, Url = Constants.Version35SP1FullURL, PrettyVersion = ".NET 3.5 SP1" };
19 | public static CLRVersion NET40Client = new CLRVersion() { Major = 4, Minor = 0, Profile = "client", Url = Constants.Version40ClientURL, PrettyVersion = ".NET 4.0 Client" };
20 | public static CLRVersion NET40Full = new CLRVersion() { Major = 4, Minor = 0, Profile = "full", Url = Constants.Version40FullURL, PrettyVersion = ".NET 4.0" };
21 | public static CLRVersion NET45Full = new CLRVersion() { Major = 4, Minor = 5, Profile = "full", Url = Constants.Version45URL, PrettyVersion = ".NET 4.5" };
22 | public static CLRVersion NET46Full = new CLRVersion() { Major = 4, Minor = 6, Profile = "full", Url = Constants.Version46URL, PrettyVersion = ".NET 4.6" };
23 |
24 | ///
25 | /// A Dictionary of CLR Versions with information
26 | ///
27 | public static Dictionary Versions = new Dictionary
28 | {
29 | {Constants.Version10Full, NET10Full},
30 | {Constants.Version11Full, NET11Full},
31 | {Constants.Version20Full, NET20Full},
32 | {Constants.Version30Full, NET30Full},
33 | {Constants.Version35Full, NET35Full},
34 | {Constants.Version35SP1Client, NET35SP1Client},
35 | {Constants.Version35SP1Full, NET35SP1Full},
36 | {Constants.Version40Client, NET40Client},
37 | {Constants.Version40Full, NET40Full},
38 | {Constants.Version45Full, NET45Full},
39 | {Constants.Version46Full, NET46Full}
40 | };
41 |
42 | ///
43 | /// Gets all downloadable CLR Versions represented in the Versions Dictionary
44 | ///
45 | /// A Dictionary containing Versions with a download url
46 | public static Dictionary GetDownloadableVersions()
47 | {
48 | return Versions.Where(pair => pair.Value.Url != "").ToDictionary(pair => pair.Key, pair => pair.Value);
49 | }
50 |
51 | public string UserAgent { get; set; }
52 | public CLRVersions(string userAgent)
53 | {
54 | UserAgent = userAgent;
55 | }
56 |
57 | public Dictionary GetInstalledVersions()
58 | {
59 | var results = new Dictionary();
60 |
61 | var foundVersions = UserAgent.Split(new[] { ";" }, StringSplitOptions.RemoveEmptyEntries).Where(s => s.Contains(".NET"));
62 |
63 |
64 | foreach (string match in foundVersions)
65 | {
66 | var v = match.Trim();
67 | //this really sucks and makes me mad
68 | if (v.Contains(Constants.Version35Full) && !v.Contains(Constants.Version35SP1Client) && !v.Contains(Constants.Version35SP1Full)) v = Constants.Version35Full;
69 | if (v.Contains(Constants.Version30Full)) v = Constants.Version30Full;
70 | if (v.Contains(Constants.Version20Full)) v = Constants.Version20Full;
71 | if (v.Contains(Constants.Version11Full)) v = Constants.Version11Full;
72 | if (v.Contains(Constants.Version10Full)) v = Constants.Version10Full;
73 | if (Versions.ContainsKey(v))
74 | {
75 | var version = Versions[v];
76 | results.Add(v, version);
77 | }
78 | }
79 |
80 | if (Helpers.HasWindows8(UserAgent))
81 | {
82 | results.Add(Constants.Version45Full, Versions[Constants.Version45Full]);
83 | }
84 |
85 | return results;
86 | }
87 |
88 | public CLRVersion GetLatestVersion()
89 | {
90 | var installedVersions = GetInstalledVersions();
91 |
92 | installedVersions = installedVersions.OrderByDescending(p => p.Value.Major)
93 | .ThenByDescending(p => p.Value.Minor)
94 | .ThenByDescending(p => p.Value.Profile)
95 | .ThenByDescending(p => p.Value.ServicePack ?? 0)
96 | .ToDictionary(p => p.Key, p => p.Value);
97 |
98 | if (installedVersions.Any())
99 | {
100 | return installedVersions.First().Value;
101 | }
102 |
103 | return null;
104 | }
105 |
106 | }
107 | }
108 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/Constants.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 |
4 | ///
5 | /// A Place for the Strings
6 | ///
7 | public static class Constants
8 | {
9 | public static readonly string DotNet = "4.8";
10 | public static readonly string DotNetOnline = String.Format(".NET {1} Web ", Version48WebUrl, DotNet);
11 | public static readonly string DotNetOffline = String.Format(".NET {1} Offline ", Version48OfflineUrl, DotNet);
12 |
13 | // this variable can be updated with whatever constant is holiding the latest release URL and then should cascade to the Get.NET link
14 | public static readonly string LatestDotNetRawUrl = Version48OfflineUrl;
15 |
16 |
17 | public const double DotNetOnlineMB = Version48WebMB;
18 | public const double DotNetOfflineMB = Version48OfflineMB;
19 |
20 | public const string WindowsUpdate = "Windows Update ";
21 | public const string WhyItIsSmall = @" The .NET installer is smart enough to look at your system and automatically download the smallest upgrade package possible.
22 | For you, it'll probably be around {0} megabytes total .";
23 |
24 | public const string InferredText = "You have at least {0} on your machine. We can only infer this as the user agent of your browser doesn't give us the version. Try the .Net Checker application to get more accurate version information.";
25 | public const string CheckerFound = "The .Net Checker application determined that you have {0} on your machine. ";
26 | public const string CheckerFoundNotExact = "The application was not able to determine the exact version you have. Please log an issue including this information: releaseKey={1} so we can get it exact in the future.";
27 |
28 | public static readonly Dictionary OldWindows = new Dictionary
29 | {
30 | {"Windows NT 5.0", "Windows 2000"},
31 | {"Windows 95", "Windows 95"},
32 | {"Windows 98", "Windows 98"}
33 | };
34 |
35 | ///
36 | /// The .Net versions (4.5 and above) keyed by the registry key value.
37 | ///
38 | public static readonly SortedDictionary ReleaseVersions = new SortedDictionary
39 | {
40 | { int.MinValue, "4.5" },
41 | { 378389, "4.5" },
42 | { 378675, "4.5.1" },
43 | { 378758, "4.5.1" },
44 | { 379893, "4.5.2" },
45 | { 381029, "4.6 Preview" },
46 | { 393273, "4.6 RC1" },
47 | { 393292, "4.6 RC2" },
48 | { 393295, "4.6" },
49 | { 393297, "4.6" },
50 | { 394254, "4.6.1" },
51 | { 394271, "4.6.1" },
52 | { 394747, "4.6.2 Preview" },
53 | { 394748, "4.6.2 Preview" },
54 | { 394757, "4.6.2 Preview" },
55 | { 394802, "4.6.2" },
56 | { 394806, "4.6.2" },
57 | { 460798, "4.7" },
58 | { 460805, "4.7" },
59 | { 461308, "4.7.1" },
60 | { 461310, "4.7.1" },
61 | { 461808, "4.7.2" },
62 | { 461814, "4.7.2" },
63 | { 528040, "4.8" },
64 | { 528049, "4.8" },
65 | };
66 |
67 | public const string Windows8 = "Windows NT 6.2";
68 | public const string Windows81 = "Windows NT 6.3";
69 | public const string Windows10 = "Windows NT 10";
70 |
71 | public const string Version461Full = ".NET 4.6.1";
72 | public const string Version46Full = ".NET 4.6";
73 | public const string Version45Full = ".NET 4.5";
74 | public const string Version40Full = ".NET4.0E";
75 | public const string Version40Client = ".NET4.0C";
76 | public const string Version35SP1Full = ".NET CLR 3.5.30729";
77 | public const string Version35SP1Client = ".NET Client 3.5";
78 | public const string Version35Full = ".NET CLR 3.5";
79 | public const string Version30Full = ".NET CLR 3.0";
80 | public const string Version20Full = ".NET CLR 2.0";
81 | public const string Version11Full = ".NET CLR 1.1";
82 | public const string Version10Full = ".NET CLR 1.0";
83 |
84 |
85 | private const string Version48WebUrl = "https://dotnet.microsoft.com/download/thank-you/net48"; // or "https://go.microsoft.com/fwlink/?LinkId=2085155";
86 | private const string Version48OfflineUrl = "https://dotnet.microsoft.com/download/thank-you/net48-offline"; // Or "https://go.microsoft.com/fwlink/?linkid=2088631"
87 |
88 | private const string Version472WebUrl = "https://go.microsoft.com/fwlink/?LinkId=863262";
89 | private const string Version472OfflineUrl = "https://go.microsoft.com/fwlink/?LinkId=863265";
90 |
91 | private const string Version461WebUrl = "https://www.microsoft.com/en-us/download/details.aspx?id=49981";
92 | private const string Version461OfflineUrl = "https://www.microsoft.com/en-us/download/details.aspx?id=49982";
93 |
94 | private const string Version46WebUrl = "https://go.microsoft.com/fwlink/?LinkId=528259";
95 | private const string Version46OfflineUrl = "https://go.microsoft.com/fwlink/?LinkId=528233";
96 |
97 | public const string Version11URL = "https://www.microsoft.com/downloads/details.aspx?FamilyID=a8f5654f-088e-40b2-bbdb-a83353618b38&DisplayLang=en";
98 | public const string Version20URL = "https://www.microsoft.com/downloads/details.aspx?familyid=5B2C0358-915B-4EB5-9B1D-10E506DA9D0F&displaylang=en";
99 | public const string Version30URL = "https://www.microsoft.com/downloads/details.aspx?FamilyId=10CC340B-F857-4A14-83F5-25634C3BF043&displaylang=en";
100 | public const string Version35SP1FullURL = "https://www.microsoft.com/en-us/download/details.aspx?id=22";
101 | public const string Version35SP1ClientURL = "https://www.microsoft.com/downloads/details.aspx?FamilyId=8CEA6CD1-15BC-4664-B27D-8CEBA808B28B&displaylang=en";
102 | public const string Version40FullURL = "https://www.microsoft.com/downloads/details.aspx?FamilyID=9f5e8774-c8dc-4ff6-8285-03a4c387c0db&displaylang=en";
103 | public const string Version40ClientURL = "https://www.microsoft.com/downloads/details.aspx?FamilyID=68a7173d-7ee5-4213-a06f-f2e943ec9249&displaylang=en";
104 | public const string Version45URL = "https://www.microsoft.com/en-us/download/details.aspx?id=30653";
105 | public const string Version46URL = "https://www.microsoft.com/en-us/download/details.aspx?id=30653";
106 |
107 | private const double Version48WebMB = 1.4;
108 | private const double Version48OfflineMB = 69.3;
109 | private const double Version472WebMB = 1.4;
110 | private const double Version472OfflineMB = 63.8;
111 | private const double Version461WebMB = 1.4;
112 | private const double Version461OfflineMB = 64.5;
113 | private const double Version46WebMB = 1.4;
114 | private const int Version46OfflineMB = 63;
115 | public const int Version3OfflineMB = 38;
116 | public const int Version2OfflineMB = 15;
117 | public const int Version1OfflineMB = 7;
118 | }
119 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/Helpers.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using SmallestDotNetLib;
5 |
6 | ///
7 | /// A Class containing general purposes methods
8 | ///
9 | public class Helpers
10 | {
11 | public static UpdateInformationResponse GetUpdateInformation(string userAgent)
12 | {
13 | return GetUpdateInformation(userAgent, null, 0);
14 | }
15 |
16 | public static UpdateInformationResponse GetUpdateInformation(string UserAgent, string realVersion)
17 | {
18 | return GetUpdateInformation(UserAgent, realVersion, 0);
19 | }
20 |
21 | public static UpdateInformationResponse GetUpdateInformation(string UserAgent, string realVersion, int releaseKey)
22 | {
23 | bool net4 = false;
24 | string netInfoString = "";
25 | var response = new UpdateInformationResponse();
26 |
27 | // We should check this first since we don't need to check .NET versions if they can't have .NET versions
28 | // Check for windows phone first as it may contain 'Mac' in User Agent
29 | if (UserAgent.Contains("Windows Phone"))
30 | {
31 | response.Text = "It looks like you're running a Windows Phone, awesome! There's no .NET Framework download for the Windows phone, but you might check out the Windows Dev Center or the Windows Phone Store ";
32 | return response;
33 | }
34 | if (UserAgent.Contains("Mac"))
35 | {
36 | response.Text = "It looks like you're running a Mac or an iPhone. You currently have two options: .NET Core for Mac , or Mono , which is an Open Source platform that can run .NET code on a Mac. For your mobile devices, check out Xamarin and write .NET apps for iOS and Android!";
37 | return response;
38 | }
39 | if (UserAgent.Contains("nix"))
40 | {
41 | response.Text = "It looks like you're running a Unix machine. There's no .NET Framework download from Microsoft for Unix, but you might check out Mono , which is an Open Source platform that can run .NET code on Unix.";
42 | return response;
43 | }
44 |
45 | response.CanRunCheckApp = true;
46 | response.VersionCanBeDetermined = true;
47 |
48 | net4 = GetWindows8Or10Message(UserAgent, ref netInfoString) || Get40Message(UserAgent, ref netInfoString);
49 | if (!string.IsNullOrEmpty(realVersion) || releaseKey != 0)
50 | {
51 | netInfoString = GetRealVersionMessage(ref realVersion, releaseKey);
52 | }
53 | else if (Helpers.Has35(UserAgent) || Helpers.Has35SP1C(UserAgent) || Helpers.Has35SP1E(UserAgent))
54 | {
55 | netInfoString += DotNet3_5Message((Helpers.Has35SP1C(UserAgent) || Helpers.Has35SP1E(UserAgent)), net4);
56 | }
57 | else if (Helpers.Has30(UserAgent))
58 | {
59 | netInfoString += DotNet3Message(net4);
60 | }
61 | else if (Helpers.Has20(UserAgent))
62 | {
63 | netInfoString += DotNet2Message(net4);
64 | }
65 | else if (Helpers.Has11(UserAgent) || Helpers.Has10(UserAgent))
66 | {
67 | netInfoString += DotNet1Message(net4);
68 | }
69 | else if (!net4)
70 | {
71 | if (UserAgent.Contains("fox"))
72 | {
73 | netInfoString += MessageForBrowser("Firefox");
74 | }
75 | else if (UserAgent.Contains("Chrome"))
76 | {
77 | netInfoString += MessageForBrowser("Chrome");
78 | }
79 | else if (UserAgent.Contains("Safari")) // Chrome also uses safari in the user agent so this check must come after
80 | {
81 | netInfoString += MessageForBrowser("Safari");
82 | }
83 | else
84 | {
85 | netInfoString += UnknownBrowserMessage();
86 | }
87 |
88 | response.VersionCanBeDetermined = false;
89 | }
90 |
91 | if (response.VersionCanBeDetermined)
92 | {
93 | response.VersionIsLatest = Helpers.CheckVersionLatest(realVersion, ref netInfoString);
94 | }
95 |
96 | //need to see if windows 2000 has the latest version
97 | foreach (KeyValuePair windowsVersion in Constants.OldWindows)
98 | {
99 | netInfoString += CheckDotNet3_5UnSupportedOs(UserAgent, windowsVersion.Key, windowsVersion.Value);
100 | }
101 |
102 | response.Text = netInfoString;
103 | return response;
104 | }
105 |
106 | ///
107 | /// Gets the .Net version based on release key.
108 | ///
109 | /// The release key found in registry.
110 | /// if set to true then an exact match was found; otherwise the return value will contain "X.Y or greater".
111 | /// Version number text e.g. "4.5.1"
112 | private static string GetDotnetVersionFromReleaseKey(int releaseKey, out bool exact)
113 | {
114 | string version;
115 | if (Constants.ReleaseVersions.TryGetValue(releaseKey, out version))
116 | {
117 | exact = true;
118 | return version;
119 | }
120 |
121 | exact = false;
122 | var releaseVersion = Constants.ReleaseVersions.Last(kvp => kvp.Key < releaseKey);
123 | return releaseVersion.Value + " or greater";
124 | }
125 |
126 | ///
127 | /// Gets a message based on the "real" version as determined by the .Net Checker application.
128 | ///
129 | /// The real version.
130 | /// The release key.
131 | /// A message like "The .Net Checker application determined that you've got X.Y on your machine."
132 | private static string GetRealVersionMessage(ref string realVersion, int releaseKey)
133 | {
134 | bool exact = true;
135 | if (releaseKey != 0)
136 | {
137 | realVersion = GetDotnetVersionFromReleaseKey(releaseKey, out exact);
138 | }
139 |
140 | return exact
141 | ? string.Format(Constants.CheckerFound, realVersion)
142 | : string.Format(Constants.CheckerFound + Constants.CheckerFoundNotExact, realVersion, releaseKey);
143 | }
144 |
145 | ///
146 | /// Gets a message for the Windows 8 OS.
147 | ///
148 | /// The user agent.
149 | /// The user message.
150 | /// True if the user agent has
151 | private static bool GetWindows8Or10Message(string userAgent, ref string userMessage)
152 | {
153 | bool hasWindows10 = Helpers.HasWindows10(userAgent);
154 | if (Helpers.HasWindows8(userAgent) || hasWindows10)
155 | {
156 | var version = hasWindows10 ? "4.6" : "4.5";
157 | userMessage += string.Format(Constants.InferredText, version);
158 | return true;
159 | }
160 |
161 | return false;
162 | }
163 |
164 | private static bool Get40Message(string UserAgent, ref string userMessage)
165 | {
166 |
167 | var whichVersion = "";
168 | var ret = false;
169 | if (Helpers.Has40E(UserAgent))
170 | {
171 | whichVersion = ".NET 4.0";
172 | ret = true;
173 | }
174 | else if (Helpers.Has40C(UserAgent))
175 | {
176 | whichVersion = ".NET 4.0 Client Profile";
177 | ret = true;
178 | }
179 |
180 | if (ret)
181 | {
182 | userMessage += String.Format(@"You have {0}, this is a recent version of .NET. Download an installer for the newest version {1} .", whichVersion, Constants.DotNetOnline);
183 | }
184 |
185 | return ret;
186 | }
187 |
188 | private static string MessageForBrowser(string browser)
189 | {
190 | return String.Format(@"Looks like you're running {0}. That's totally cool, but I can't tell if you've got .NET installed from {0}.
191 | Consider running this little application , just once, and we'll tell you what version of .NET you're running.", browser);
192 | }
193 |
194 | private static string UnknownBrowserMessage()
195 | {
196 | string explain = String.Format(Constants.WhyItIsSmall, Constants.DotNetOfflineMB);
197 | return String.Format(@"I can't see what browser you have. That's totally cool, but I can't tell if you've got .NET installed.
198 | Consider running this little application , just once, and we'll tell you what version of .NET you're running.");
199 | }
200 |
201 | private static string DotNet1Message(bool hasDotNet4)
202 | {
203 | string explain = String.Format(Constants.WhyItIsSmall, Constants.DotNetOfflineMB - Constants.Version1OfflineMB);
204 | return String.Format("Looks like you've {3} got a pretty old version of .NET . You should make sure your computer is up to date by visiting {0} then downloading the {1} from Microsoft. {2}", Constants.WindowsUpdate, Constants.DotNetOnline, explain, hasDotNet4 ? "also" : "");
205 | }
206 |
207 | private static string DotNet2Message(bool hasDotNet4)
208 | {
209 | string explain = String.Format(Constants.WhyItIsSmall, Constants.DotNetOfflineMB - Constants.Version2OfflineMB);
210 | return String.Format(@"Looks like you {2} have .NET version 2.0 .
211 | That's a fairly recent version of the .NET Framework, but you can upgrade fairly easily to the .NET {4} by downloading the {3} MB isntaller for {0}. {1}", Constants.DotNetOnline, explain, hasDotNet4 ? "also" : "", Constants.DotNetOnlineMB, Constants.DotNet);
212 | }
213 |
214 | private static string DotNet3Message(bool hasDotNet4)
215 | {
216 | string explain = String.Format(Constants.WhyItIsSmall, Constants.DotNetOfflineMB - Constants.Version3OfflineMB);
217 | return String.Format(@"Looks like you {2} have .NET version 3.0 .
218 | That's a very recent version of the .NET Framework, but you can upgrade fairly easily to .NET {4} by downloading the {3} MB installer for {0}. {1}", Constants.DotNetOnline, explain, hasDotNet4 ? "also" : "", Constants.DotNetOnlineMB, Constants.DotNet);
219 | }
220 |
221 | private static string DotNet3_5Message(bool hasSp1, bool hasDotNet4)
222 | {
223 |
224 | if (!hasDotNet4)
225 | {
226 | return String.Format(@"You have .NET 3.5{0}, this is a recent version of .NET. Download an installer for the newest version {1} .", hasSp1 ? " Service Pack 1" : "", Constants.DotNetOnline);
227 | }
228 |
229 | return "";
230 | }
231 |
232 | private static string CheckDotNet3_5UnSupportedOs(string UserAgent, string agent, string friendlyName)
233 | {
234 | if (UserAgent.Contains(agent))
235 | {
236 | return String.Format("It looks like you're running {1}. Sorry, but .NET 3.5 isn't supported on {1}, but you can still run NET Framework 2.0 SP1 ", "https://www.microsoft.com/downloads/details.aspx?familyid=79BC3B77-E02C-4AD3-AACF-A7633F706BA5&displaylang=en", friendlyName);
237 | }
238 |
239 | return "";
240 | }
241 |
242 | private static bool CheckVersionLatest(string realVersion, ref string netInfoString)
243 | {
244 | if (realVersion != null && realVersion.Contains(Constants.DotNet))
245 | {
246 | netInfoString += String.Format(@"You have {0}, this is a recent version of .NET. Download an installer for the newest version {1} .", Constants.DotNet, Constants.DotNetOnline);
247 | return true;
248 | }
249 | return false;
250 | }
251 |
252 | public static bool Has45(String UserAgent)
253 | {
254 | return UserAgent.StartsWith("4.5");
255 | }
256 |
257 | public static string GetJsonPayload(String UserAgent)
258 | {
259 | var OperatingSystem = OperatingSystems.GetOperatingSystem(UserAgent);
260 | if (OperatingSystem.LatestCLRVersion != null)
261 | {
262 | var Browser = BrowserSupport.GetBrowser(UserAgent);
263 |
264 | if (Browser.CanGetCLRVersion)
265 | {
266 | var parsedVersions = new CLRVersions(UserAgent);
267 |
268 | var LatestVersion = parsedVersions.GetLatestVersion();
269 |
270 | var UpToDate = (LatestVersion == OperatingSystem.LatestCLRVersion);
271 | }
272 | }
273 |
274 | return "Not Implemented";
275 | }
276 |
277 | ///
278 | /// Determines if the User Agent String indicates Windows 8
279 | ///
280 | /// A User Agent String
281 | /// True if user agent contains "Windows NT 6.2" or "Windows NT 6.3"
282 | public static bool HasWindows8(String userAgent)
283 | {
284 | // User Agent from Win 8.1 IE11:
285 | // Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; LCJB; rv:11.0) like Gecko
286 | // User Agent from Windows 10 build 10074 IE11:
287 | // "Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; Touch; MALCJS; rv:11.0) like Gecko";
288 | return userAgent.Contains(Constants.Windows8) ||
289 | (userAgent.Contains(Constants.Windows81) && !userAgent.Contains("MALCJS"));
290 | }
291 |
292 | ///
293 | /// Determines if the User Agent String indicates Windows 8
294 | ///
295 | /// A User Agent String
296 | /// True if user agent contains "Windows NT 10"
297 | public static bool HasWindows10(string userAgent)
298 | {
299 | // User Agent from Win 8.1 IE11:
300 | // Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; LCJB; rv:11.0) like Gecko
301 | // User Agent from Windows 10 build 10074 IE11:
302 | // "Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; Touch; MALCJS; rv:11.0) like Gecko";
303 | return userAgent.Contains(Constants.Windows10)
304 | || (userAgent.Contains(Constants.Windows81) && userAgent.Contains("MALCJS"));
305 | }
306 |
307 | ///
308 | /// Determines if the User Agent String indicates .NET 4.0 Full
309 | ///
310 | /// A User Agent String
311 | ///
312 | public static bool Has40E(String UserAgent)
313 | {
314 | return UserAgent.Contains(Constants.Version40Full) || UserAgent.StartsWith("4.0");
315 | }
316 |
317 | ///
318 | /// Determines if the User Agent String indicates .NET 40 Client
319 | ///
320 | /// A User Agent String
321 | ///
322 | public static bool Has40C(String UserAgent)
323 | {
324 | return UserAgent.Contains(Constants.Version40Client) || UserAgent.StartsWith("4.0");
325 | }
326 |
327 | ///
328 | /// Determines if the User Agent String indicates .NET 3.5 SP1 Full
329 | ///
330 | /// A User Agent String
331 | ///
332 | public static bool Has35SP1E(String UserAgent)
333 | {
334 | return UserAgent.Contains(Constants.Version35SP1Full);
335 | }
336 |
337 | ///
338 | /// Determines if the User Agent String indicates .NET 3.5 SP1 Client
339 | ///
340 | /// A User Agent String
341 | ///
342 | public static bool Has35SP1C(String UserAgent)
343 | {
344 | return UserAgent.Contains(Constants.Version35SP1Client);
345 | }
346 |
347 | ///
348 | /// Determines if the User Agent String indicates .NET 3.5
349 | ///
350 | /// A User Agent String
351 | ///
352 | public static bool Has35(String UserAgent)
353 | {
354 | return UserAgent.Contains(Constants.Version35Full);
355 | }
356 |
357 | ///
358 | /// Determines if the User Agent String indicates .NET 3.0
359 | ///
360 | /// A User Agent String
361 | ///
362 | public static bool Has30(String UserAgent)
363 | {
364 | return UserAgent.Contains(Constants.Version30Full);
365 | }
366 |
367 | ///
368 | /// Determines if the User Agent String indicates .NET 2.0
369 | ///
370 | /// A User Agent String
371 | ///
372 | public static bool Has20(String UserAgent)
373 | {
374 | return UserAgent.Contains(Constants.Version20Full);
375 | }
376 |
377 | ///
378 | /// Determines if the User Agent String indicates .NET 1.1
379 | ///
380 | /// A User Agent String
381 | ///
382 | public static bool Has11(String UserAgent)
383 | {
384 | return UserAgent.Contains(Constants.Version11Full);
385 | }
386 |
387 | ///
388 | /// Determines if the User Agent String indicates .NET 1.0
389 | ///
390 | /// A User Agent String
391 | ///
392 | public static bool Has10(String UserAgent)
393 | {
394 | return UserAgent.Contains(Constants.Version10Full);
395 | }
396 | }
397 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/JsonVersions.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestDotNetLib
2 | {
3 | using System;
4 | using System.Collections.Generic;
5 | using System.Linq;
6 |
7 | public class JsonVersions
8 | {
9 | ///
10 | /// Writes the Latest Version Json
11 | ///
12 | /// Major Version
13 | /// Minor Version
14 | /// Profile
15 | /// Service Pack
16 | /// A Json String Representing the latest version
17 | public static string WriteLatestVersion(int major, int minor, string profile, int? sp)
18 | {
19 | return String.Format(@"SmallestDotNet.latestVersion = {0};", WriteVersion(major, minor, profile, sp));
20 | }
21 |
22 | ///
23 | /// Writes the Version Json
24 | ///
25 | /// Major Version
26 | /// Minor Version
27 | /// Profile
28 | /// Service Pack
29 | /// A Json string representing the version
30 | public static string WriteVersion(int major, int minor, string profile, int? sp)
31 | {
32 | return String.Format(@"{{
33 | major: {0},
34 | minor: {1},
35 | profile: ""{2}"",
36 | servicePack: {3}
37 | }}", major, minor, profile, sp.HasValue ? sp.ToString() : "null");
38 | }
39 |
40 | ///
41 | /// Writes the Version Json
42 | ///
43 | /// CLRVersion Struct
44 | /// A Json string representing the version
45 | public static string WriteVersion(CLRVersion version)
46 | {
47 | return String.Format(@"{{
48 | major: {0},
49 | minor: {1},
50 | profile: ""{2}"",
51 | servicePack: {3}
52 | }}", version.Major, version.Minor, version.Profile, version.ServicePack.HasValue ? version.ServicePack.ToString() : "null");
53 | }
54 |
55 | ///
56 | /// Write the Download Information Json
57 | ///
58 | /// Major Version
59 | /// Minor Version
60 | /// .NET CLR Profile
61 | /// Service Pack
62 | /// Download URL
63 | /// A Json string representing the version with a download url
64 | public static string WriteVersionWithDownload(int major, int minor, string profile, int? sp, string url)
65 | {
66 | return String.Format(@"{{
67 | major: {0},
68 | minor: {1},
69 | profile: ""{2}"",
70 | servicePack: {3},
71 | url: {4}
72 | }}", major, minor, profile, sp.HasValue ? sp.ToString() : "null", url);
73 | }
74 |
75 | ///
76 | /// Write the Download Information Json
77 | ///
78 | /// CLRVersion Struct
79 | /// A Json string representing the version with a download url
80 | public static string WriteVersionWithDownload(CLRVersion version)
81 | {
82 | return String.Format(@"{{
83 | major: {0},
84 | minor: {1},
85 | profile: '{2}',
86 | servicePack: {3},
87 | url: '{4}'
88 | }}",
89 | version.Major,
90 | version.Minor,
91 | version.Profile,
92 | version.ServicePack.HasValue ? version.ServicePack.Value.ToString() : "null",
93 | version.Url);
94 | }
95 |
96 | ///
97 | /// Writes the Latest Version Json
98 | ///
99 | /// CLRVersion Struct
100 | ///
101 | public static string WriteLatestVersion(CLRVersion version)
102 | {
103 | return String.Format(@"SmallestDotNet.latestVersion = {0};", version != null ? WriteVersion(version) : "null");
104 | }
105 |
106 | ///
107 | /// Writes the latest .NET CLR Version found in the provided UserAgent String
108 | ///
109 | /// A User Agent String
110 | /// A Json string containing the latest .NET CLR Version
111 | public static string WriteLatestVersions(string userAgent)
112 | {
113 | var latestVersion = (new CLRVersions(userAgent)).GetLatestVersion();
114 |
115 | return WriteLatestVersion(latestVersion);
116 | }
117 |
118 | ///
119 | /// Writes all .NET CLR VErsions found in the User Agent String
120 | ///
121 | /// A User Agent String
122 | /// A Json string containing all the CLR Versions found in the User Agent String
123 | public static string WriteAllVersions(string userAgent)
124 | {
125 | var versions = new List();
126 | var detectedVersions = (new CLRVersions(userAgent)).GetInstalledVersions();
127 |
128 | foreach (var version in detectedVersions)
129 | {
130 | versions.Add(WriteVersion(version.Value));
131 | }
132 |
133 | return String.Format(@"SmallestDotNet.allVersions = [{0}];", String.Join(",", versions.ToArray()));
134 |
135 | }
136 |
137 |
138 | private static string _downloadString = "";
139 |
140 | ///
141 | /// Writes a Json String Containing Download Information for all of the .NET CLR Versions
142 | ///
143 | /// A Json String
144 | public static string WriteDownloads()
145 | {
146 | if (_downloadString == "")
147 | {
148 | var DownloadableVersions = CLRVersions.GetDownloadableVersions().Select(p => JsonVersions.WriteVersionWithDownload(p.Value)).ToList();
149 |
150 | _downloadString = String.Format(@"SmallestDotNet.downloadableVersions = [{0}];", String.Join(",", DownloadableVersions.ToArray()));
151 | }
152 |
153 | return _downloadString;
154 | }
155 |
156 | }
157 |
158 | }
159 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/OperatingSystemSupport.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestDotNetLib
2 | {
3 | using System.Collections.Generic;
4 | using System.Linq;
5 |
6 | public class OperatingSystem
7 | {
8 | public string UserAgentVersion { get; set; }
9 | public string PrettyVersion { get; set; }
10 | public CLRVersion LatestCLRVersion { get; set; }
11 | }
12 |
13 | public class OperatingSystems
14 | {
15 | public static OperatingSystem Windows81 = new OperatingSystem() { UserAgentVersion = "Windows NT 6.3", PrettyVersion = "Windows 8.1", LatestCLRVersion = CLRVersions.NET45Full };
16 | public static OperatingSystem Windows8 = new OperatingSystem() { UserAgentVersion = "Windows NT 6.2", PrettyVersion = "Windows 8", LatestCLRVersion = CLRVersions.NET45Full };
17 | public static OperatingSystem Windows7 = new OperatingSystem() { UserAgentVersion = "Windows NT 6.1", PrettyVersion = "Windows 7", LatestCLRVersion = CLRVersions.NET45Full };
18 | public static OperatingSystem WindowsVista = new OperatingSystem() { UserAgentVersion = "Windows NT 6.0", PrettyVersion = "Windows Vista", LatestCLRVersion = CLRVersions.NET45Full };
19 | public static OperatingSystem WindowsXP64ORServer2003 = new OperatingSystem { UserAgentVersion = "Windows NT 5.2", PrettyVersion = "Windows XP x64, Windows Server 2003", LatestCLRVersion = CLRVersions.NET40Full };
20 | public static OperatingSystem WindowsXP = new OperatingSystem() { UserAgentVersion = "Windows NT 5.1", PrettyVersion = "Windows XP", LatestCLRVersion = CLRVersions.NET40Full };
21 | public static OperatingSystem Windows2000SP1 = new OperatingSystem() { UserAgentVersion = "Windows NT 5.01", PrettyVersion = "Windows 2000 SP1", LatestCLRVersion = CLRVersions.NET20Full };
22 | public static OperatingSystem Windows2000 = new OperatingSystem() { UserAgentVersion = "Windows NT 5.0", PrettyVersion = "Windows 2000", LatestCLRVersion = CLRVersions.NET20Full };
23 | public static OperatingSystem Windows98 = new OperatingSystem() { UserAgentVersion = "Windows 98", PrettyVersion = "Windows 98", LatestCLRVersion = CLRVersions.NET20Full };
24 | public static OperatingSystem Macintosh = new OperatingSystem() { UserAgentVersion = "Mac", PrettyVersion = "Macintosh", LatestCLRVersion = null };
25 | public static OperatingSystem UnixBased = new OperatingSystem() { UserAgentVersion = "nix", PrettyVersion = "Unix/Linux", LatestCLRVersion = null };
26 | public static OperatingSystem Android = new OperatingSystem() { UserAgentVersion = "Android", PrettyVersion = "Android", LatestCLRVersion = null };
27 |
28 | public static List OSVersions = new List
29 | {
30 | Windows81,
31 | Windows8,
32 | Windows7,
33 | WindowsVista,
34 | WindowsXP64ORServer2003,
35 | WindowsXP,
36 | Windows2000SP1,
37 | Windows2000,
38 | Windows98,
39 | Macintosh,
40 | UnixBased
41 | };
42 |
43 | public static OperatingSystem GetOperatingSystem(string UserAgent)
44 | {
45 | return OSVersions.FirstOrDefault(o => UserAgent.Contains(o.UserAgentVersion));
46 | }
47 |
48 | }
49 | }
50 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Reflection;
2 | using System.Runtime.InteropServices;
3 |
4 | // General Information about an assembly is controlled through the following
5 | // set of attributes. Change these attribute values to modify the information
6 | // associated with an assembly.
7 | [assembly: AssemblyTitle("SmallestDotNetLib")]
8 | [assembly: AssemblyDescription("")]
9 | [assembly: AssemblyConfiguration("")]
10 | [assembly: AssemblyCompany("")]
11 | [assembly: AssemblyProduct("SmallestDotNetLib")]
12 | [assembly: AssemblyCopyright("Copyright © 2012")]
13 | [assembly: AssemblyTrademark("")]
14 | [assembly: AssemblyCulture("")]
15 |
16 | // Setting ComVisible to false makes the types in this assembly not visible
17 | // to COM components. If you need to access a type in this assembly from
18 | // COM, set the ComVisible attribute to true on that type.
19 | [assembly: ComVisible(false)]
20 |
21 | // The following GUID is for the ID of the typelib if this project is exposed to COM
22 | [assembly: Guid("f4a45b35-6b84-4b47-a463-52e2843c7e17")]
23 |
24 | // Version information for an assembly consists of the following four values:
25 | //
26 | // Major Version
27 | // Minor Version
28 | // Build Number
29 | // Revision
30 | //
31 | // You can specify all the values or you can default the Build and Revision Numbers
32 | // by using the '*' as shown below:
33 | // [assembly: AssemblyVersion("1.0.*")]
34 | [assembly: AssemblyVersion("1.0.0.0")]
35 | [assembly: AssemblyFileVersion("1.0.0.0")]
36 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/SmallestDotNetLib.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | Debug
6 | AnyCPU
7 | {3ECC85DC-EBC0-4A2E-930D-711ABC481388}
8 | Library
9 | Properties
10 | SmallestDotNetLib
11 | SmallestDotNetLib
12 | v4.5
13 | 512
14 | ..\
15 | true
16 |
17 |
18 | true
19 | full
20 | false
21 | bin\Debug\
22 | DEBUG;TRACE
23 | prompt
24 | 4
25 | false
26 |
27 |
28 | pdbonly
29 | true
30 | bin\Release\
31 | TRACE
32 | prompt
33 | 4
34 |
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
64 |
--------------------------------------------------------------------------------
/SmallestDotNetLib/UpdateInformationResponse.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestDotNetLib
2 | {
3 | ///
4 | /// Encapsulates the results from the parsing of user agent / version
5 | ///
6 | public class UpdateInformationResponse
7 | {
8 | #region Properties
9 |
10 | ///
11 | /// Gets or sets a value indicating whether the current OS can run the checker application.
12 | ///
13 | public bool CanRunCheckApp { get; set; }
14 |
15 | ///
16 | /// Gets or sets the text to be displayed to the user.
17 | ///
18 | public string Text { get; set; }
19 |
20 | ///
21 | /// Gets or sets a value indicating whether the CLR version was able to be detected.
22 | ///
23 | public bool VersionCanBeDetermined { get; set; }
24 |
25 | ///
26 | /// Gets or sets a value indicating whether the current dot net version is latest.
27 | ///
28 | public bool VersionIsLatest { get; set; }
29 |
30 | #endregion Properties
31 | }
32 | }
--------------------------------------------------------------------------------
/SmallestTest/CLRVersionDictionaryTests.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestTest
2 | {
3 | using System.Collections;
4 | using System.Collections.Generic;
5 | using Microsoft.VisualStudio.TestTools.UnitTesting;
6 | using SmallestDotNetLib;
7 |
8 | [TestClass]
9 | public class CLRVersionDictionaryTests
10 | {
11 | [TestMethod]
12 | public void ParseVersionsProperlyTest()
13 | {
14 | var UserAgent = @"Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.1; WOW64; Trident/5.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; .NET4.0C; .NET4.0E; InfoPath.3; MS-RTC LM 8)";
15 |
16 | var expected = new Dictionary();
17 |
18 | expected.Add(Constants.Version20Full, CLRVersions.Versions[Constants.Version20Full]);
19 | expected.Add(Constants.Version30Full, CLRVersions.Versions[Constants.Version30Full]);
20 | expected.Add(Constants.Version35SP1Full, CLRVersions.Versions[Constants.Version35SP1Full]);
21 | expected.Add(Constants.Version40Client, CLRVersions.Versions[Constants.Version40Client]);
22 | expected.Add(Constants.Version40Full, CLRVersions.Versions[Constants.Version40Full]);
23 |
24 | var CLRVersionFac = new CLRVersions(UserAgent);
25 | var actual = CLRVersionFac.GetInstalledVersions();
26 |
27 |
28 | CollectionAssert.AreEquivalent((ICollection)expected, (ICollection)actual);
29 |
30 | var expectedLatestVersion = CLRVersions.Versions[Constants.Version40Full];
31 | var actualLatestVersion = CLRVersionFac.GetLatestVersion();
32 | Assert.IsTrue(actualLatestVersion != null, "Version is not null");
33 |
34 | Assert.AreEqual(expectedLatestVersion.Major, actualLatestVersion.Major, "Major Versions Are the Same");
35 | Assert.AreEqual(expectedLatestVersion.Minor, actualLatestVersion.Minor, "Minor Versions Are the Same");
36 | Assert.AreEqual(expectedLatestVersion.Profile, actualLatestVersion.Profile, "Profile is the Same");
37 | Assert.AreEqual(expectedLatestVersion.ServicePack, actualLatestVersion.ServicePack, "Service Pack is the Same");
38 |
39 | }
40 | }
41 | }
42 |
--------------------------------------------------------------------------------
/SmallestTest/JavascriptDomTests.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestTest
2 | {
3 | using System;
4 | using System.Linq;
5 | using Microsoft.VisualStudio.TestTools.UnitTesting;
6 | using SmallestDotNetLib;
7 |
8 | [TestClass]
9 | public class JavascriptDomTests
10 | {
11 | private string generateLatestVersionString(int major, int minor, string profile, int? sp)
12 | {
13 | return String.Format(@"SmallestDotNet.latestVersion = {{
14 | major: {0},
15 | minor: {1},
16 | profile: ""{2}"",
17 | servicePack: {3}
18 | }};", major, minor, profile, sp.HasValue ? sp.ToString() : "null");
19 | }
20 |
21 | [TestMethod]
22 | public void WriteOnlyVersionsThatHaveLinksForDownload()
23 | {
24 | var downloadableVersions = CLRVersions.GetDownloadableVersions();
25 |
26 | Assert.IsTrue(downloadableVersions.All(pair => pair.Value.Url != ""));
27 |
28 | }
29 |
30 |
31 | [TestMethod]
32 | public void Write40AsLatestVersion()
33 | {
34 | var userAgent = ".NET4.0E; .NET4.0C";
35 |
36 | var expectedVersion = generateLatestVersionString(4, 0, "full", null);
37 |
38 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
39 |
40 | Assert.AreEqual(expectedVersion, actualVersion);
41 |
42 | }
43 |
44 | [TestMethod]
45 | public void Write40ClientAsLatestVersion()
46 | {
47 | var userAgent = ".NET4.0C; .NET CLR 2.0";
48 |
49 | var expectedVersion = generateLatestVersionString(4, 0, "client", null);
50 |
51 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
52 |
53 | Assert.AreEqual(expectedVersion, actualVersion);
54 | }
55 |
56 | [TestMethod]
57 | public void Write35SP1AsLatestVersion()
58 | {
59 | var userAgent = ".NET CLR 3.5.30729";
60 |
61 | var expectedVersion = generateLatestVersionString(3, 5, "full", 1);
62 |
63 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
64 |
65 | Assert.AreEqual(expectedVersion, actualVersion);
66 | }
67 |
68 | [TestMethod]
69 | public void Write35SP1ClientAsLatestVersion()
70 | {
71 | var userAgent = ".NET Client 3.5";
72 |
73 | var expectedVersion = generateLatestVersionString(3, 5, "client", 1);
74 |
75 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
76 |
77 | Assert.AreEqual(expectedVersion, actualVersion);
78 | }
79 |
80 | [TestMethod]
81 | public void Write35AsLatestVersion()
82 | {
83 | var userAgent = ".NET CLR 3.5.21022";
84 |
85 | var expectedVersion = generateLatestVersionString(3, 5, "full", null);
86 |
87 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
88 |
89 | Assert.AreEqual(expectedVersion, actualVersion);
90 | }
91 |
92 | [TestMethod]
93 | public void Write20AsLatestVersion()
94 | {
95 | var userAgent = ".NET CLR 2.0";
96 |
97 | var expectedVersion = generateLatestVersionString(2, 0, "full", null);
98 |
99 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
100 |
101 | Assert.AreEqual(expectedVersion, actualVersion);
102 | }
103 |
104 | [TestMethod]
105 | public void Write11AsLatestVersion()
106 | {
107 | var userAgent = ".NET CLR 1.1";
108 |
109 | var expectedVersion = generateLatestVersionString(1, 1, "full", null);
110 |
111 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
112 |
113 | Assert.AreEqual(expectedVersion, actualVersion);
114 | }
115 |
116 | [TestMethod]
117 | public void Write10AsLatestVersion()
118 | {
119 | var userAgent = ".NET CLR 1.0";
120 |
121 | var expectedVersion = generateLatestVersionString(1, 0, "full", null);
122 |
123 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
124 |
125 | Assert.AreEqual(expectedVersion, actualVersion);
126 | }
127 |
128 | [TestMethod]
129 | public void WriteNullAsLatestVersion()
130 | {
131 | var userAgent = "";
132 |
133 | var expectedVersion = "SmallestDotNet.latestVersion = null;";
134 |
135 | var actualVersion = JsonVersions.WriteLatestVersions(userAgent);
136 |
137 | Assert.AreEqual(expectedVersion, actualVersion);
138 | }
139 |
140 | }
141 | }
142 |
--------------------------------------------------------------------------------
/SmallestTest/OperatingSystemVersionTests.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestTest
2 | {
3 | using Microsoft.VisualStudio.TestTools.UnitTesting;
4 | using SmallestDotNetLib;
5 |
6 | [TestClass]
7 | public class OperatingSystemVersionTests
8 | {
9 | [TestMethod]
10 | public void CheckNoMatch()
11 | {
12 | var UserAgent = "Apeture";
13 |
14 | var actualOS = OperatingSystems.GetOperatingSystem(UserAgent);
15 |
16 | Assert.IsNull(actualOS);
17 |
18 | }
19 |
20 |
21 | [TestMethod]
22 | public void CheckWindows8()
23 | {
24 | var UserAgent = "Windows NT 6.2";
25 | var Windows8OperatingSystem = OperatingSystems.Windows8;
26 |
27 | var actualOS = OperatingSystems.GetOperatingSystem(UserAgent);
28 |
29 | Assert.AreEqual(Windows8OperatingSystem, actualOS);
30 | }
31 |
32 | [TestMethod]
33 | public void CheckWindows81()
34 | {
35 | var UserAgent = "Windows NT 6.3";
36 | var Windows8OperatingSystem = OperatingSystems.Windows81;
37 |
38 | var actualOS = OperatingSystems.GetOperatingSystem(UserAgent);
39 |
40 | Assert.AreEqual(Windows8OperatingSystem, actualOS);
41 | }
42 |
43 | [TestMethod]
44 | public void CheckWindows7()
45 | {
46 | var UserAgent = "Windows NT 6.1";
47 | var Windows7OperatingSystem = OperatingSystems.Windows7;
48 |
49 | var actualOS = OperatingSystems.GetOperatingSystem(UserAgent);
50 |
51 | Assert.AreEqual(Windows7OperatingSystem, actualOS);
52 | }
53 |
54 | [TestMethod]
55 | public void CheckWindowsVista()
56 | {
57 | var UserAgent = "Windows NT 6.0";
58 | var WinodwsVistaOperatingSytem = OperatingSystems.WindowsVista;
59 |
60 | var actualOS = OperatingSystems.GetOperatingSystem(UserAgent);
61 |
62 | Assert.AreEqual(WinodwsVistaOperatingSytem, actualOS);
63 | }
64 |
65 | [TestMethod]
66 | public void CheckoutWindowsServer2003()
67 | {
68 | var UserAgent = "Windows NT 5.2";
69 | var WindowsServer2003OperatingSystem = OperatingSystems.WindowsXP64ORServer2003;
70 |
71 | var actualOS = OperatingSystems.GetOperatingSystem(UserAgent);
72 |
73 | Assert.AreEqual(WindowsServer2003OperatingSystem, actualOS);
74 | }
75 |
76 |
77 | }
78 | }
79 |
--------------------------------------------------------------------------------
/SmallestTest/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Reflection;
2 | using System.Runtime.InteropServices;
3 |
4 | // General Information about an assembly is controlled through the following
5 | // set of attributes. Change these attribute values to modify the information
6 | // associated with an assembly.
7 | [assembly: AssemblyTitle("SmallestTest")]
8 | [assembly: AssemblyDescription("")]
9 | [assembly: AssemblyConfiguration("")]
10 | [assembly: AssemblyCompany("")]
11 | [assembly: AssemblyProduct("SmallestTest")]
12 | [assembly: AssemblyCopyright("Copyright © 2012")]
13 | [assembly: AssemblyTrademark("")]
14 | [assembly: AssemblyCulture("")]
15 |
16 | // Setting ComVisible to false makes the types in this assembly not visible
17 | // to COM components. If you need to access a type in this assembly from
18 | // COM, set the ComVisible attribute to true on that type.
19 | [assembly: ComVisible(false)]
20 |
21 | // The following GUID is for the ID of the typelib if this project is exposed to COM
22 | [assembly: Guid("1e471b2b-9007-4d89-8772-ad09899dd728")]
23 |
24 | // Version information for an assembly consists of the following four values:
25 | //
26 | // Major Version
27 | // Minor Version
28 | // Build Number
29 | // Revision
30 | //
31 | // You can specify all the values or you can default the Build and Revision Numbers
32 | // by using the '*' as shown below:
33 | // [assembly: AssemblyVersion("1.0.*")]
34 | [assembly: AssemblyVersion("1.0.0.0")]
35 | [assembly: AssemblyFileVersion("1.0.0.0")]
36 |
--------------------------------------------------------------------------------
/SmallestTest/SmallestTest.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Debug
5 | AnyCPU
6 | {21BD13C9-725E-447D-8CF9-07E8CBE797B1}
7 | Library
8 | Properties
9 | SmallestTest
10 | SmallestTest
11 | v4.5
12 | 512
13 | {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}
14 | 10.0
15 | $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)
16 | $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages
17 | False
18 | UnitTest
19 |
20 |
21 | true
22 | full
23 | false
24 | bin\Debug\
25 | DEBUG;TRACE
26 | prompt
27 | 4
28 |
29 |
30 | pdbonly
31 | true
32 | bin\Release\
33 | TRACE
34 | prompt
35 | 4
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
60 |
61 |
62 | {3ecc85dc-ebc0-4a2e-930d-711abc481388}
63 | SmallestDotNetLib
64 |
65 |
66 |
67 |
68 |
69 |
70 | False
71 |
72 |
73 | False
74 |
75 |
76 | False
77 |
78 |
79 | False
80 |
81 |
82 |
83 |
84 |
85 |
86 |
93 |
--------------------------------------------------------------------------------
/SmallestTest/VersionCheckTest.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestTest
2 | {
3 |
4 | using System;
5 | using System.Collections.Generic;
6 | using Microsoft.VisualStudio.TestTools.UnitTesting;
7 |
8 | [TestClass]
9 | public class VersionCheckTest
10 | {
11 | private static List CLRVersionStrings()
12 | {
13 | return new List
14 | {
15 | ".NET4.0E"
16 | , ".NET4.0C"
17 | , ".NET CLR 3.5.30729"
18 | , ".NET Client 3.5"
19 | , ".NET CLR 3.5.21022"
20 | , ".NET CLR 2.0"
21 | , ".NET CLR 1.1"
22 | , ".NET CLR 1.0"
23 | };
24 | }
25 |
26 | [TestMethod]
27 | public void CheckAllCLRInUserAgentDetectionStrings()
28 | {
29 | var userAgentCLRString = String.Join(" ", CLRVersionStrings().ToArray());
30 |
31 | Assert.IsTrue(Helpers.Has10(userAgentCLRString), ".NET Version 1.0");
32 | Assert.IsTrue(Helpers.Has11(userAgentCLRString), ".NET Version 1.1");
33 | Assert.IsTrue(Helpers.Has20(userAgentCLRString), ".NET Version 2.0");
34 | Assert.IsTrue(Helpers.Has35(userAgentCLRString), ".NET Version 3.5");
35 | Assert.IsTrue(Helpers.Has35SP1C(userAgentCLRString), ".NET Version 3.5 SP1 Client Profile");
36 | Assert.IsTrue(Helpers.Has35SP1E(userAgentCLRString), ".NET Version 3.5 SP1 Full");
37 | Assert.IsTrue(Helpers.Has40C(userAgentCLRString), ".NET Version 4.0 Client Profile");
38 | Assert.IsTrue(Helpers.Has40E(userAgentCLRString), ".NET Version 4.0 Full");
39 | }
40 |
41 | [TestMethod]
42 | public void CheckWindows8Detection()
43 | {
44 | var userAgent = "Windows NT 6.2";
45 |
46 | Assert.IsTrue(Helpers.HasWindows8(userAgent), "Windows 8");
47 | userAgent = "Windows NT 6.3";
48 |
49 | Assert.IsTrue(Helpers.HasWindows8(userAgent), "Windows 8.1");
50 | }
51 |
52 | ///
53 | /// Checks that the helper detects Windows 10 correctly.
54 | ///
55 | [TestMethod]
56 | public void CheckWindows10Detection()
57 | {
58 | // User agent from Edge (Windows 10 build 10074)
59 | var userAgent = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/39.0.2171.71 Safari/537.36 Edge/12.0";
60 |
61 | Assert.IsTrue(Helpers.HasWindows10(userAgent), "Windows 10 detection failed");
62 |
63 | // User agent from IE11 (Windows 10 build 10074)
64 | userAgent = "Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; Touch; MALCJS; rv:11.0) like Gecko";
65 |
66 | Assert.IsTrue(Helpers.HasWindows10(userAgent), "Windows 10 detection failed");
67 | Assert.IsFalse(Helpers.HasWindows8(userAgent), "Windows 8 incorrectly detected");
68 | }
69 |
70 | ///
71 | /// Checks that the helper shows 4.6 when Windows 10 detected.
72 | ///
73 | [TestMethod]
74 | public void CheckWindows10Shows46()
75 | {
76 | // Arrange
77 | const string UserAgent = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/39.0.2171.71 Safari/537.36 Edge/12.0";
78 |
79 |
80 | // Act
81 | string message = Helpers.GetUpdateInformation(UserAgent).Text;
82 |
83 | // Assert
84 | Assert.IsTrue(Helpers.HasWindows10(UserAgent), "Windows 10 detection failed");
85 | StringAssert.Contains(message, "4.6", "Windows 10 must have at least 4.6");
86 | }
87 |
88 | [TestMethod]
89 | public void CheckRealVersion()
90 | {
91 | // Arrange
92 | const string UserAgent = ".NET Version 1.0";
93 | const string RealVersion = "4.5.1";
94 | const string CheckerApplicationText = "The .Net Checker application determined that you have";
95 | const string UnableToDetermineText = "The application was not able to determine the exact version you have.";
96 | var releaseKey = 0;
97 |
98 | // Act
99 | string message = Helpers.GetUpdateInformation(UserAgent, RealVersion, releaseKey).Text;
100 |
101 | // Assert
102 | StringAssert.StartsWith(message, CheckerApplicationText);
103 | StringAssert.Contains(message, RealVersion);
104 | Assert.IsFalse(message.Contains(UnableToDetermineText), "The '...not able to determine the exact version...' message should NOT appear if realVersion is present and releaseKey=0");
105 |
106 | foreach (var releaseVersion in Constants.ReleaseVersions)
107 | {
108 | // Arrange
109 | releaseKey = releaseVersion.Key;
110 |
111 | // Act
112 | message = Helpers.GetUpdateInformation(UserAgent, null, releaseKey).Text;
113 |
114 | // Assert
115 | StringAssert.StartsWith(message, CheckerApplicationText);
116 | StringAssert.Contains(message, releaseVersion.Value);
117 | Assert.IsFalse(message.Contains(UnableToDetermineText), "The '...not able to determine the exact version...' message should NOT appear if releaseKey is contained in Constants.ReleaseVersions");
118 |
119 | // Arrange
120 | releaseKey = releaseVersion.Key + 1;
121 |
122 | // Act
123 | message = Helpers.GetUpdateInformation(UserAgent, null, releaseKey).Text;
124 |
125 | // Assert
126 | StringAssert.StartsWith(message, CheckerApplicationText);
127 | StringAssert.Contains(message, releaseVersion.Value + " or greater");
128 | StringAssert.Contains(message, UnableToDetermineText, "The '...not able to determine the exact version...' message SHOULD appear if releaseKey is not contained in Constants.ReleaseVersions");
129 | }
130 | }
131 | }
132 | }
133 |
--------------------------------------------------------------------------------
/SmallestTest/VersionWriterTests.cs:
--------------------------------------------------------------------------------
1 | namespace SmallestTest
2 | {
3 | using Microsoft.VisualStudio.TestTools.UnitTesting;
4 |
5 | [TestClass]
6 | public class VersionWriterTests
7 | {
8 | [TestMethod]
9 | public void Test10Version()
10 | {
11 | var expected = @"{
12 | major: 1,
13 | minor: 0,
14 | profile: ""full"",
15 | servicePack: null
16 | }";
17 |
18 | int? servicePack = null;
19 |
20 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(1, 0, "full", servicePack);
21 |
22 | Assert.AreEqual(expected, actual);
23 | }
24 |
25 | [TestMethod]
26 | public void Test11Json()
27 | {
28 | var expected = @"{
29 | major: 1,
30 | minor: 1,
31 | profile: ""full"",
32 | servicePack: null
33 | }";
34 |
35 | int? servicePack = null;
36 |
37 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(1, 1, "full", servicePack);
38 |
39 | Assert.AreEqual(expected, actual);
40 | }
41 |
42 | [TestMethod]
43 | public void Test20Json()
44 | {
45 | var expected = @"{
46 | major: 2,
47 | minor: 0,
48 | profile: ""full"",
49 | servicePack: null
50 | }";
51 |
52 | int? servicePack = null;
53 |
54 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(2, 0, "full", servicePack);
55 |
56 | Assert.AreEqual(expected, actual);
57 | }
58 |
59 |
60 | [TestMethod]
61 | public void Test35Json()
62 | {
63 | var expected = @"{
64 | major: 3,
65 | minor: 5,
66 | profile: ""full"",
67 | servicePack: null
68 | }";
69 |
70 | int? servicePack = null;
71 |
72 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(3, 5, "full", servicePack);
73 |
74 | Assert.AreEqual(expected, actual);
75 | }
76 |
77 |
78 |
79 | [TestMethod]
80 | public void Test35ServicePackOneJson()
81 | {
82 | var expected = @"{
83 | major: 3,
84 | minor: 5,
85 | profile: ""full"",
86 | servicePack: 1
87 | }";
88 |
89 | int? servicePack = 1;
90 |
91 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(3, 5, "full", servicePack);
92 |
93 | Assert.AreEqual(expected, actual);
94 | }
95 |
96 | [TestMethod]
97 | public void Test35ClientServicePackOneJson()
98 | {
99 | var expected = @"{
100 | major: 3,
101 | minor: 5,
102 | profile: ""client"",
103 | servicePack: 1
104 | }";
105 |
106 | int? servicePack = 1;
107 |
108 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(3, 5, "client", servicePack);
109 |
110 | Assert.AreEqual(expected, actual);
111 | }
112 | [TestMethod]
113 | public void Test40Json()
114 | {
115 | var expected = @"{
116 | major: 4,
117 | minor: 0,
118 | profile: ""full"",
119 | servicePack: null
120 | }";
121 |
122 | int? servicePack = null;
123 |
124 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(4, 0, "full", servicePack);
125 |
126 | Assert.AreEqual(expected, actual);
127 | }
128 |
129 | [TestMethod]
130 | public void Test40ClientProfileJson()
131 | {
132 | var expected = @"{
133 | major: 4,
134 | minor: 0,
135 | profile: ""client"",
136 | servicePack: null
137 | }";
138 |
139 | int? servicePack = null;
140 |
141 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(4, 0, "client", servicePack);
142 |
143 | Assert.AreEqual(expected, actual);
144 | }
145 |
146 | [TestMethod]
147 | public void Test45Json()
148 | {
149 | var expected = @"{
150 | major: 4,
151 | minor: 5,
152 | profile: ""full"",
153 | servicePack: null
154 | }";
155 |
156 | int? servicePack = null;
157 |
158 | var actual = SmallestDotNetLib.JsonVersions.WriteVersion(4, 5, "full", servicePack);
159 |
160 | Assert.AreEqual(expected, actual);
161 | }
162 | }
163 | }
164 |
--------------------------------------------------------------------------------
/license.txt:
--------------------------------------------------------------------------------
1 | The MIT License (MIT)
2 |
3 | Copyright (c) 2013 scott Hanselman
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in
13 | all copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21 | THE SOFTWARE.
--------------------------------------------------------------------------------