PageRenderTime 49ms CodeModel.GetById 23ms RepoModel.GetById 0ms app.codeStats 0ms

/Experiments.Wif/Microsoft.Samples.DPE.Identity.Controls/SecurityTokenVisualizerControl.cs

https://github.com/bihter/Visual-Studio-Experiments
C# | 378 lines | 272 code | 70 blank | 36 comment | 22 complexity | 46fdc8d67f399d0d877c5af2773e45b6 MD5 | raw file
Possible License(s): GPL-2.0
  1. // ----------------------------------------------------------------------------------
  2. // Microsoft Developer & Platform Evangelism
  3. //
  4. // Copyright (c) Microsoft Corporation. All rights reserved.
  5. //
  6. // THIS CODE AND INFORMATION ARE PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
  7. // EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES
  8. // OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.
  9. // ----------------------------------------------------------------------------------
  10. // The example companies, organizations, products, domain names,
  11. // e-mail addresses, logos, people, places, and events depicted
  12. // herein are fictitious. No association with any real company,
  13. // organization, product, domain name, email address, logo, person,
  14. // places, or events is intended or should be inferred.
  15. // ----------------------------------------------------------------------------------
  16. namespace Microsoft.Samples.DPE.Identity.Controls
  17. {
  18. using System;
  19. using System.Collections.Generic;
  20. using System.ComponentModel;
  21. using System.Drawing;
  22. using System.Globalization;
  23. using System.Linq;
  24. using System.Security.Cryptography.X509Certificates;
  25. using System.Threading;
  26. using System.Web.UI;
  27. using System.Web.UI.HtmlControls;
  28. using System.Web.UI.WebControls;
  29. using Microsoft.IdentityModel.Claims;
  30. using Microsoft.Samples.DPE.Identity.Controls.Properties;
  31. using TokenVisualizers;
  32. [NonVisualControl, Bindable(false)]
  33. [ToolboxData("<{0}:SecurityTokenVisualizerControl runat=server></{0}:SecurityTokenVisualizerControl>")]
  34. [ToolboxBitmap(typeof(Microsoft.Samples.DPE.Identity.Controls.SecurityTokenVisualizerControl), "icon.bmp")]
  35. [Designer(typeof(SecurityTokenVisualizerControlDesigner))]
  36. public partial class SecurityTokenVisualizerControl : WebControl
  37. {
  38. private const int TableColumnsQuantity = 4;
  39. protected override void OnPreRender(System.EventArgs e)
  40. {
  41. this.RegisterCssLink();
  42. base.OnPreRender(e);
  43. this.Page.ClientScript.RegisterClientScriptResource(typeof(SecurityTokenVisualizerControl), "Microsoft.Samples.DPE.Identity.Controls.Content.scripts.SecurityTokenVisualizer.js");
  44. }
  45. protected override void RenderContents(HtmlTextWriter writer)
  46. {
  47. if (this.DesignMode)
  48. {
  49. return;
  50. }
  51. if (this.ProcessCertificateDownloadRequest())
  52. {
  53. return;
  54. }
  55. string divId = string.Format(CultureInfo.InvariantCulture, "{0}_div", this.ID);
  56. HtmlGenericControl container = new HtmlGenericControl("div") { ID = divId };
  57. ClientScriptManager clientScriptManager = this.Page.ClientScript;
  58. HtmlImage controlImage = new HtmlImage
  59. {
  60. ID = string.Format(CultureInfo.CurrentUICulture, "STVC{0}", Guid.NewGuid()),
  61. Src = clientScriptManager.GetWebResourceUrl(typeof(SecurityTokenVisualizerControl), "Microsoft.Samples.DPE.Identity.Controls.Content.images.icon.png"),
  62. Alt = Resources.SecurityTokenVisualizer,
  63. };
  64. controlImage.Attributes["title"] = Resources.SecurityTokenVisualizer;
  65. HtmlControl tokenVisualizerHeader = this.CreateCollapsableHeader(controlImage, container, false /* Expanded as Default */);
  66. if (this.Font == null || string.IsNullOrEmpty(this.Font.Name))
  67. {
  68. container.Style["font-family"] = "Arial, Consolas, Segoe UI";
  69. tokenVisualizerHeader.Style["font-family"] = "Arial, Consolas, Segoe UI";
  70. }
  71. if (this.Font == null || this.Font.Size.IsEmpty)
  72. {
  73. container.Style["font-size"] = "small";
  74. tokenVisualizerHeader.Style["font-size"] = "small";
  75. }
  76. var containerRounded = this.AddContainerRounded(container);
  77. if (Thread.CurrentPrincipal.Identity.IsAuthenticated && Thread.CurrentPrincipal.Identity is IClaimsIdentity)
  78. {
  79. AddClaimsTable(containerRounded);
  80. containerRounded.Controls.Add(new HtmlGenericControl() { InnerHtml = "&nbsp;" });
  81. this.AddSamlTokenTable(containerRounded);
  82. }
  83. else
  84. {
  85. AddNotAuthenticatedUserTable(containerRounded);
  86. }
  87. tokenVisualizerHeader.RenderControl(writer);
  88. container.RenderControl(writer);
  89. base.RenderContents(writer);
  90. }
  91. private static HtmlTable CreateTable(HtmlControl container)
  92. {
  93. HtmlTable table = new HtmlTable();
  94. table.Attributes["class"] = "TokenVisualizerTable";
  95. container.Controls.Add(table);
  96. return table;
  97. }
  98. private static void AddNotAuthenticatedUserTable(HtmlControl container)
  99. {
  100. HtmlTable table = CreateTable(container);
  101. HtmlTableRow row = new HtmlTableRow();
  102. row.Cells.Add(new HtmlTableCell() { InnerText = Resources.NotAuthenticatedUser });
  103. row.Attributes["class"] = "NotAuthenticatedUser";
  104. table.Rows.Add(row);
  105. }
  106. private static void AddClaimsTable(HtmlControl container)
  107. {
  108. HtmlTable table = CreateTable(container);
  109. HtmlTableRow row;
  110. AddTableSectionHeader(table, Resources.IssuedIdentity, "((IClaimsPrincipal)Thread.CurrentPrincipal).Identities[0].Claims");
  111. //AddColumnHeadersToTable(table, new[] { Resources.ClaimTypeColumnHeader, Resources.ClaimValueColumnHeader, Resources.ClaimIssuerColumnHeader, Resources.ClaimOriginalIssuerColumnHeader });
  112. AddColumnHeadersToTable(table, new[] { Resources.ClaimTypeColumnHeader, Resources.ClaimValueColumnHeader, Resources.ClaimIssuerColumnHeader });
  113. IClaimsPrincipal principal = (IClaimsPrincipal)Thread.CurrentPrincipal;
  114. foreach (Claim claim in principal.Identities[0].Claims)
  115. {
  116. row = new HtmlTableRow();
  117. row.Cells.Add(new HtmlTableCell { InnerText = claim.ClaimType });
  118. row.Cells.Add(new HtmlTableCell { InnerText = claim.Value });
  119. row.Cells.Add(new HtmlTableCell { InnerText = claim.Issuer });
  120. //row.Cells.Add(new HtmlTableCell { InnerText = claim.OriginalIssuer });
  121. table.Rows.Add(row);
  122. }
  123. //if (principal.Identities[0].Delegate != null)
  124. //{
  125. // AddTableSectionHeader(table, Resources.DelegatedIdentity, "((IClaimsPrincipal)Thread.CurrentPrincipal).Identities[0].Delegate.Claims");
  126. // AddColumnHeadersToTable(table, new[] { Resources.ClaimTypeColumnHeader, Resources.ClaimValueColumnHeader, Resources.ClaimIssuerColumnHeader, Resources.ClaimOriginalIssuerColumnHeader });
  127. // foreach (Claim delegatedClaim in principal.Identities[0].Delegate.Claims)
  128. // {
  129. // row = new HtmlTableRow();
  130. // row.Cells.Add(new HtmlTableCell { InnerText = delegatedClaim.ClaimType });
  131. // row.Cells.Add(new HtmlTableCell { InnerText = delegatedClaim.Value });
  132. // row.Cells.Add(new HtmlTableCell { InnerText = delegatedClaim.Issuer });
  133. // row.Cells.Add(new HtmlTableCell { InnerText = delegatedClaim.OriginalIssuer });
  134. // table.Rows.Add(row);
  135. // }
  136. //}
  137. }
  138. private static void AddColumnHeadersToTable(HtmlTable table, IEnumerable<string> headersText)
  139. {
  140. HtmlTableRow row = new HtmlTableRow();
  141. foreach (string headerText in headersText)
  142. {
  143. HtmlTableCell columnHeaderCell = new HtmlTableCell { InnerText = headerText };
  144. columnHeaderCell.Attributes["class"] = "TokenVisualizerColumnHeader";
  145. if (headersText.Count() < TableColumnsQuantity && headersText.Last() == headerText)
  146. {
  147. columnHeaderCell.ColSpan = 1 + (TableColumnsQuantity - headersText.Count());
  148. }
  149. row.Cells.Add(columnHeaderCell);
  150. }
  151. table.Rows.Add(row);
  152. }
  153. private static void AddTableSectionHeader(HtmlTable table, string text, string tooltip)
  154. {
  155. HtmlTableRow row = new HtmlTableRow();
  156. HtmlTableCell sectionTitleCell = new HtmlTableCell { ColSpan = TableColumnsQuantity, InnerText = text };
  157. sectionTitleCell.Attributes["class"] = "ClaimsSectionTitle";
  158. if (!string.IsNullOrEmpty(tooltip))
  159. {
  160. sectionTitleCell.Attributes["title"] = tooltip;
  161. }
  162. row.Cells.Add(sectionTitleCell);
  163. table.Rows.Add(row);
  164. }
  165. private static void AddTokenProperty(HtmlTable table, string propertyName, string propertyValue)
  166. {
  167. HtmlTableRow row = new HtmlTableRow();
  168. row.Cells.Add(new HtmlTableCell() { InnerHtml = propertyName });
  169. row.Cells.Add(new HtmlTableCell() { InnerHtml = propertyValue, ColSpan = TableColumnsQuantity - 1 });
  170. table.Rows.Add(row);
  171. }
  172. private HtmlControl AddContainerRounded(HtmlGenericControl container)
  173. {
  174. HtmlGenericControl tokenVisualizerTableContainerRounded = new HtmlGenericControl("div");
  175. WebControl cornerTopLeft = new WebControl(HtmlTextWriterTag.Div);
  176. WebControl cornerTopRight = new WebControl(HtmlTextWriterTag.Div);
  177. HtmlGenericControl lateralBorders = new HtmlGenericControl("div");
  178. HtmlGenericControl containerControl = new HtmlGenericControl("div");
  179. WebControl cornerBottomLeft = new WebControl(HtmlTextWriterTag.Div);
  180. WebControl cornerBottomRight = new WebControl(HtmlTextWriterTag.Div);
  181. tokenVisualizerTableContainerRounded.Attributes["class"] = "TokenVisualizerTableContainerRounded";
  182. cornerTopLeft.CssClass = "corner-top-left";
  183. cornerTopRight.CssClass = "corner-top-right";
  184. lateralBorders.Attributes["class"] = "lateralBorders";
  185. containerControl.Attributes["class"] = "containerControl";
  186. cornerBottomLeft.CssClass = "corner-bottom-left";
  187. cornerBottomRight.CssClass = "corner-bottom-right";
  188. cornerTopLeft.Style.Add(HtmlTextWriterStyle.BackgroundImage, this.Page.ClientScript.GetWebResourceUrl(this.GetType(), "Microsoft.Samples.DPE.Identity.Controls.Content.images.cornerroundedtransp.gif"));
  189. cornerTopRight.Style.Add(HtmlTextWriterStyle.BackgroundImage, this.Page.ClientScript.GetWebResourceUrl(this.GetType(), "Microsoft.Samples.DPE.Identity.Controls.Content.images.cornerroundedtransp.gif"));
  190. cornerBottomLeft.Style.Add(HtmlTextWriterStyle.BackgroundImage, this.Page.ClientScript.GetWebResourceUrl(this.GetType(), "Microsoft.Samples.DPE.Identity.Controls.Content.images.cornerroundedtransp.gif"));
  191. cornerBottomRight.Style.Add(HtmlTextWriterStyle.BackgroundImage, this.Page.ClientScript.GetWebResourceUrl(this.GetType(), "Microsoft.Samples.DPE.Identity.Controls.Content.images.cornerroundedtransp.gif"));
  192. tokenVisualizerTableContainerRounded.Controls.Add(cornerTopLeft);
  193. tokenVisualizerTableContainerRounded.Controls.Add(cornerTopRight);
  194. tokenVisualizerTableContainerRounded.Controls.Add(lateralBorders);
  195. lateralBorders.Controls.Add(containerControl);
  196. tokenVisualizerTableContainerRounded.Controls.Add(cornerBottomLeft);
  197. tokenVisualizerTableContainerRounded.Controls.Add(cornerBottomRight);
  198. container.Controls.Add(tokenVisualizerTableContainerRounded);
  199. return containerControl;
  200. }
  201. private bool ProcessCertificateDownloadRequest()
  202. {
  203. if (Thread.CurrentPrincipal.Identity.IsAuthenticated && Thread.CurrentPrincipal.Identity is IClaimsIdentity)
  204. {
  205. if (!string.IsNullOrEmpty(this.Page.Request.QueryString["___stvc___"]))
  206. {
  207. if (this.Page.Request.QueryString["___stvc___"] == "signcert")
  208. {
  209. var tokenVisualizer = TokenVisualizerFactory.GetTokenVisualizer(((IClaimsIdentity)Thread.CurrentPrincipal.Identity).BootstrapToken);
  210. var certificate = tokenVisualizer.RetrieveIssuerCertificate();
  211. if (certificate != null)
  212. {
  213. this.RespondCertificate(certificate);
  214. return true;
  215. }
  216. }
  217. }
  218. }
  219. return false;
  220. }
  221. private void RespondCertificate(X509Certificate2 certificate)
  222. {
  223. this.Page.Response.Clear();
  224. byte[] certInBytes = certificate.Export(X509ContentType.Cert);
  225. this.Page.Response.BinaryWrite(certInBytes);
  226. this.Page.Response.ContentType = "application/x-x509-user-cert";
  227. this.Page.Response.AddHeader("content-disposition", "attachment; filename=" + certificate.Issuer + ".cer");
  228. this.Page.Response.End();
  229. }
  230. private HtmlControl CreateCollapsableHeader(string collapsableTitle, HtmlControl collapsableElement, bool expandedAsDefault)
  231. {
  232. return this.CreateCollapsableHeader(
  233. new HtmlGenericControl("span") { InnerText = collapsableTitle },
  234. collapsableElement,
  235. expandedAsDefault);
  236. }
  237. private HtmlControl CreateCollapsableHeader(Control title, HtmlControl collapsableElement, bool expandedAsDefault)
  238. {
  239. ClientScriptManager clientScriptManager = this.Page.ClientScript;
  240. Type tokenVisualizerControlType = this.GetType();
  241. string iconImageId = string.Format(CultureInfo.InvariantCulture, "{0}_image", collapsableElement.ID);
  242. string onClickJavascriptHandler = string.Format(
  243. CultureInfo.InvariantCulture,
  244. "toggleVisualizerVisibility('{0}','{1}','{2}','{3}')",
  245. collapsableElement.ID,
  246. iconImageId,
  247. clientScriptManager.GetWebResourceUrl(tokenVisualizerControlType, "Microsoft.Samples.DPE.Identity.Controls.Content.images.CollapseIcon.bmp"),
  248. clientScriptManager.GetWebResourceUrl(tokenVisualizerControlType, "Microsoft.Samples.DPE.Identity.Controls.Content.images.ExpandIcon.bmp"));
  249. HtmlImage iconImage = new HtmlImage()
  250. {
  251. ID = iconImageId,
  252. };
  253. if (expandedAsDefault)
  254. {
  255. iconImage.Src = clientScriptManager.GetWebResourceUrl(tokenVisualizerControlType, "Microsoft.Samples.DPE.Identity.Controls.Content.images.CollapseIcon.bmp");
  256. collapsableElement.Style["display"] = "block";
  257. }
  258. else
  259. {
  260. iconImage.Src = clientScriptManager.GetWebResourceUrl(tokenVisualizerControlType, "Microsoft.Samples.DPE.Identity.Controls.Content.images.ExpandIcon.bmp");
  261. collapsableElement.Style["display"] = "none";
  262. }
  263. iconImage.Attributes["class"] = "TokenVisualizerImage";
  264. HtmlGenericControl collapsableDiv = new HtmlGenericControl("div");
  265. collapsableDiv.Controls.Add(iconImage);
  266. collapsableDiv.Controls.Add(title);
  267. collapsableDiv.Attributes["onclick"] = onClickJavascriptHandler;
  268. collapsableDiv.Attributes["class"] = "TokenVisualizerTitle";
  269. return collapsableDiv;
  270. }
  271. private void RegisterCssLink()
  272. {
  273. HtmlLink link = new HtmlLink()
  274. {
  275. Href = this.Page.ClientScript.GetWebResourceUrl(this.GetType(), "Microsoft.Samples.DPE.Identity.Controls.Content.styles.SecurityTokenVisualizerControl.css")
  276. };
  277. link.Attributes["rel"] = "stylesheet";
  278. link.Attributes["type"] = "text/css";
  279. this.Page.Header.Controls.Add(link);
  280. }
  281. private void AddSamlTokenTable(HtmlControl container)
  282. {
  283. HtmlTable table = CreateTable(container);
  284. var tokenVisualizer = TokenVisualizerFactory.GetTokenVisualizer(((IClaimsIdentity)Thread.CurrentPrincipal.Identity).BootstrapToken);
  285. AddTableSectionHeader(table, Resources.SamlToken, string.Empty);
  286. string tokenTextAreaId = string.Format(CultureInfo.InvariantCulture, "{0}_samlToken", this.ID);
  287. HtmlTextArea tokenTextArea = new HtmlTextArea()
  288. {
  289. ID = tokenTextAreaId
  290. //,InnerText = tokenVisualizer.SecurityTokenString
  291. };
  292. tokenTextArea.Attributes["class"] = "SAMLToken";
  293. tokenTextArea.Attributes["readonly"] = "true";
  294. HtmlControl samlTokenHeader = this.CreateCollapsableHeader(Resources.RawSamlToken, tokenTextArea, false /* Expanded as Default */);
  295. HtmlTableRow row = new HtmlTableRow();
  296. HtmlTableCell tokenCell = new HtmlTableCell { ColSpan = TableColumnsQuantity };
  297. tokenCell.Controls.Add(samlTokenHeader);
  298. tokenCell.Controls.Add(tokenTextArea);
  299. row.Cells.Add(tokenCell);
  300. table.Rows.Add(row);
  301. AddColumnHeadersToTable(table, new[] { Resources.TokenPropertyName, Resources.TokenPropertyValue });
  302. //foreach (var entry in tokenVisualizer.RetrieveTokenProperties())
  303. //{
  304. // AddTokenProperty(table, entry.Key, entry.Value);
  305. //}
  306. }
  307. }
  308. }