diff options
author | Andrew Arnott <andrewarnott@gmail.com> | 2009-02-01 13:18:33 -0800 |
---|---|---|
committer | Andrew <andrewarnott@gmail.com> | 2009-02-01 13:18:33 -0800 |
commit | e6512c223cb078b5f2fd4ea4abb28810ecca8c47 (patch) | |
tree | bb9dbea5e485a9a2c6aca44308659577333fba26 /samples/OpenIdProviderWebForms/Code | |
parent | e865ec7da293496d6c2e67039b86c4ef9ded5a6c (diff) | |
download | DotNetOpenAuth-e6512c223cb078b5f2fd4ea4abb28810ecca8c47.zip DotNetOpenAuth-e6512c223cb078b5f2fd4ea4abb28810ecca8c47.tar.gz DotNetOpenAuth-e6512c223cb078b5f2fd4ea4abb28810ecca8c47.tar.bz2 |
Renamed OpenID Provider sample directory to match project name.
Diffstat (limited to 'samples/OpenIdProviderWebForms/Code')
9 files changed, 1164 insertions, 0 deletions
diff --git a/samples/OpenIdProviderWebForms/Code/CustomStore.cs b/samples/OpenIdProviderWebForms/Code/CustomStore.cs new file mode 100644 index 0000000..8031a59 --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/CustomStore.cs @@ -0,0 +1,89 @@ +//----------------------------------------------------------------------- +// <copyright file="CustomStore.cs" company="Andrew Arnott"> +// Copyright (c) Andrew Arnott. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace OpenIdProviderWebForms.Code { + using System; + using System.Data; + using System.Globalization; + using System.Security.Cryptography; + using DotNetOpenAuth.OpenId; + using IProviderAssociationStore = DotNetOpenAuth.OpenId.IAssociationStore<DotNetOpenAuth.OpenId.AssociationRelyingPartyType>; + + /// <summary> + /// This custom store serializes all elements to demonstrate peristent and/or shared storage. + /// This is common in a web farm, for example. + /// </summary> + /// <remarks> + /// This doesn't actually serialize anything to a persistent store, so restarting the web server + /// will still clear everything this store is supposed to remember. + /// But we "persist" all associations and nonces into a DataTable to demonstrate + /// that using a database is possible. + /// </remarks> + public class CustomStore : IProviderAssociationStore { + private static CustomStoreDataSet dataSet = new CustomStoreDataSet(); + + #region IAssociationStore<AssociationRelyingPartyType> Members + + public void StoreAssociation(AssociationRelyingPartyType distinguishingFactor, Association assoc) { + var assocRow = dataSet.Association.NewAssociationRow(); + assocRow.DistinguishingFactor = distinguishingFactor.ToString(); + assocRow.Handle = assoc.Handle; + assocRow.Expires = assoc.Expires.ToLocalTime(); + assocRow.PrivateData = assoc.SerializePrivateData(); + dataSet.Association.AddAssociationRow(assocRow); + } + + public Association GetAssociation(AssociationRelyingPartyType distinguishingFactor) { + // properly escape the URL to prevent injection attacks. + string value = distinguishingFactor.ToString(); + string filter = string.Format( + CultureInfo.InvariantCulture, + "{0} = '{1}'", + dataSet.Association.DistinguishingFactorColumn.ColumnName, + value); + string sort = dataSet.Association.ExpiresColumn.ColumnName + " DESC"; + DataView view = new DataView(dataSet.Association, filter, sort, DataViewRowState.CurrentRows); + if (view.Count == 0) { + return null; + } + var row = (CustomStoreDataSet.AssociationRow)view[0].Row; + return Association.Deserialize(row.Handle, row.Expires.ToUniversalTime(), row.PrivateData); + } + + public Association GetAssociation(AssociationRelyingPartyType distinguishingFactor, string handle) { + var assocRow = dataSet.Association.FindByDistinguishingFactorHandle(distinguishingFactor.ToString(), handle); + return Association.Deserialize(assocRow.Handle, assocRow.Expires, assocRow.PrivateData); + } + + public bool RemoveAssociation(AssociationRelyingPartyType distinguishingFactor, string handle) { + var row = dataSet.Association.FindByDistinguishingFactorHandle(distinguishingFactor.ToString(), handle); + if (row != null) { + dataSet.Association.RemoveAssociationRow(row); + return true; + } else { + return false; + } + } + + public void ClearExpiredAssociations() { + this.removeExpiredRows(dataSet.Association, dataSet.Association.ExpiresColumn.ColumnName); + } + + #endregion + + private void removeExpiredRows(DataTable table, string expiredColumnName) { + string filter = string.Format( + CultureInfo.InvariantCulture, + "{0} < #{1}#", + expiredColumnName, + DateTime.Now); + DataView view = new DataView(table, filter, null, DataViewRowState.CurrentRows); + for (int i = view.Count - 1; i >= 0; i--) { + view.Delete(i); + } + } + } +} diff --git a/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.Designer.cs b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.Designer.cs new file mode 100644 index 0000000..58c20a9 --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.Designer.cs @@ -0,0 +1,621 @@ +//------------------------------------------------------------------------------ +// <auto-generated> +// This code was generated by a tool. +// Runtime Version:2.0.50727.3521 +// +// Changes to this file may cause incorrect behavior and will be lost if +// the code is regenerated. +// </auto-generated> +//------------------------------------------------------------------------------ + +#pragma warning disable 1591 + +namespace OpenIdProviderWebForms.Code { + + + /// <summary> + ///Represents a strongly typed in-memory cache of data. + ///</summary> + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Data.Design.TypedDataSetGenerator", "2.0.0.0")] + [global::System.Serializable()] + [global::System.ComponentModel.DesignerCategoryAttribute("code")] + [global::System.ComponentModel.ToolboxItem(true)] + [global::System.Xml.Serialization.XmlSchemaProviderAttribute("GetTypedDataSetSchema")] + [global::System.Xml.Serialization.XmlRootAttribute("CustomStoreDataSet")] + [global::System.ComponentModel.Design.HelpKeywordAttribute("vs.data.DataSet")] + public partial class CustomStoreDataSet : global::System.Data.DataSet { + + private AssociationDataTable tableAssociation; + + private global::System.Data.SchemaSerializationMode _schemaSerializationMode = global::System.Data.SchemaSerializationMode.IncludeSchema; + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public CustomStoreDataSet() { + this.BeginInit(); + this.InitClass(); + global::System.ComponentModel.CollectionChangeEventHandler schemaChangedHandler = new global::System.ComponentModel.CollectionChangeEventHandler(this.SchemaChanged); + base.Tables.CollectionChanged += schemaChangedHandler; + base.Relations.CollectionChanged += schemaChangedHandler; + this.EndInit(); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected CustomStoreDataSet(global::System.Runtime.Serialization.SerializationInfo info, global::System.Runtime.Serialization.StreamingContext context) : + base(info, context, false) { + if ((this.IsBinarySerialized(info, context) == true)) { + this.InitVars(false); + global::System.ComponentModel.CollectionChangeEventHandler schemaChangedHandler1 = new global::System.ComponentModel.CollectionChangeEventHandler(this.SchemaChanged); + this.Tables.CollectionChanged += schemaChangedHandler1; + this.Relations.CollectionChanged += schemaChangedHandler1; + return; + } + string strSchema = ((string)(info.GetValue("XmlSchema", typeof(string)))); + if ((this.DetermineSchemaSerializationMode(info, context) == global::System.Data.SchemaSerializationMode.IncludeSchema)) { + global::System.Data.DataSet ds = new global::System.Data.DataSet(); + ds.ReadXmlSchema(new global::System.Xml.XmlTextReader(new global::System.IO.StringReader(strSchema))); + if ((ds.Tables["Association"] != null)) { + base.Tables.Add(new AssociationDataTable(ds.Tables["Association"])); + } + this.DataSetName = ds.DataSetName; + this.Prefix = ds.Prefix; + this.Namespace = ds.Namespace; + this.Locale = ds.Locale; + this.CaseSensitive = ds.CaseSensitive; + this.EnforceConstraints = ds.EnforceConstraints; + this.Merge(ds, false, global::System.Data.MissingSchemaAction.Add); + this.InitVars(); + } + else { + this.ReadXmlSchema(new global::System.Xml.XmlTextReader(new global::System.IO.StringReader(strSchema))); + } + this.GetSerializationData(info, context); + global::System.ComponentModel.CollectionChangeEventHandler schemaChangedHandler = new global::System.ComponentModel.CollectionChangeEventHandler(this.SchemaChanged); + base.Tables.CollectionChanged += schemaChangedHandler; + this.Relations.CollectionChanged += schemaChangedHandler; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.ComponentModel.Browsable(false)] + [global::System.ComponentModel.DesignerSerializationVisibility(global::System.ComponentModel.DesignerSerializationVisibility.Content)] + public AssociationDataTable Association { + get { + return this.tableAssociation; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.ComponentModel.BrowsableAttribute(true)] + [global::System.ComponentModel.DesignerSerializationVisibilityAttribute(global::System.ComponentModel.DesignerSerializationVisibility.Visible)] + public override global::System.Data.SchemaSerializationMode SchemaSerializationMode { + get { + return this._schemaSerializationMode; + } + set { + this._schemaSerializationMode = value; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.ComponentModel.DesignerSerializationVisibilityAttribute(global::System.ComponentModel.DesignerSerializationVisibility.Hidden)] + public new global::System.Data.DataTableCollection Tables { + get { + return base.Tables; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.ComponentModel.DesignerSerializationVisibilityAttribute(global::System.ComponentModel.DesignerSerializationVisibility.Hidden)] + public new global::System.Data.DataRelationCollection Relations { + get { + return base.Relations; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override void InitializeDerivedDataSet() { + this.BeginInit(); + this.InitClass(); + this.EndInit(); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public override global::System.Data.DataSet Clone() { + CustomStoreDataSet cln = ((CustomStoreDataSet)(base.Clone())); + cln.InitVars(); + cln.SchemaSerializationMode = this.SchemaSerializationMode; + return cln; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override bool ShouldSerializeTables() { + return false; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override bool ShouldSerializeRelations() { + return false; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override void ReadXmlSerializable(global::System.Xml.XmlReader reader) { + if ((this.DetermineSchemaSerializationMode(reader) == global::System.Data.SchemaSerializationMode.IncludeSchema)) { + this.Reset(); + global::System.Data.DataSet ds = new global::System.Data.DataSet(); + ds.ReadXml(reader); + if ((ds.Tables["Association"] != null)) { + base.Tables.Add(new AssociationDataTable(ds.Tables["Association"])); + } + this.DataSetName = ds.DataSetName; + this.Prefix = ds.Prefix; + this.Namespace = ds.Namespace; + this.Locale = ds.Locale; + this.CaseSensitive = ds.CaseSensitive; + this.EnforceConstraints = ds.EnforceConstraints; + this.Merge(ds, false, global::System.Data.MissingSchemaAction.Add); + this.InitVars(); + } + else { + this.ReadXml(reader); + this.InitVars(); + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override global::System.Xml.Schema.XmlSchema GetSchemaSerializable() { + global::System.IO.MemoryStream stream = new global::System.IO.MemoryStream(); + this.WriteXmlSchema(new global::System.Xml.XmlTextWriter(stream, null)); + stream.Position = 0; + return global::System.Xml.Schema.XmlSchema.Read(new global::System.Xml.XmlTextReader(stream), null); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + internal void InitVars() { + this.InitVars(true); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + internal void InitVars(bool initTable) { + this.tableAssociation = ((AssociationDataTable)(base.Tables["Association"])); + if ((initTable == true)) { + if ((this.tableAssociation != null)) { + this.tableAssociation.InitVars(); + } + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + private void InitClass() { + this.DataSetName = "CustomStoreDataSet"; + this.Prefix = ""; + this.Namespace = "http://tempuri.org/CustomStoreDataSet.xsd"; + this.EnforceConstraints = true; + this.SchemaSerializationMode = global::System.Data.SchemaSerializationMode.IncludeSchema; + this.tableAssociation = new AssociationDataTable(); + base.Tables.Add(this.tableAssociation); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + private bool ShouldSerializeAssociation() { + return false; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + private void SchemaChanged(object sender, global::System.ComponentModel.CollectionChangeEventArgs e) { + if ((e.Action == global::System.ComponentModel.CollectionChangeAction.Remove)) { + this.InitVars(); + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public static global::System.Xml.Schema.XmlSchemaComplexType GetTypedDataSetSchema(global::System.Xml.Schema.XmlSchemaSet xs) { + CustomStoreDataSet ds = new CustomStoreDataSet(); + global::System.Xml.Schema.XmlSchemaComplexType type = new global::System.Xml.Schema.XmlSchemaComplexType(); + global::System.Xml.Schema.XmlSchemaSequence sequence = new global::System.Xml.Schema.XmlSchemaSequence(); + global::System.Xml.Schema.XmlSchemaAny any = new global::System.Xml.Schema.XmlSchemaAny(); + any.Namespace = ds.Namespace; + sequence.Items.Add(any); + type.Particle = sequence; + global::System.Xml.Schema.XmlSchema dsSchema = ds.GetSchemaSerializable(); + if (xs.Contains(dsSchema.TargetNamespace)) { + global::System.IO.MemoryStream s1 = new global::System.IO.MemoryStream(); + global::System.IO.MemoryStream s2 = new global::System.IO.MemoryStream(); + try { + global::System.Xml.Schema.XmlSchema schema = null; + dsSchema.Write(s1); + for (global::System.Collections.IEnumerator schemas = xs.Schemas(dsSchema.TargetNamespace).GetEnumerator(); schemas.MoveNext(); ) { + schema = ((global::System.Xml.Schema.XmlSchema)(schemas.Current)); + s2.SetLength(0); + schema.Write(s2); + if ((s1.Length == s2.Length)) { + s1.Position = 0; + s2.Position = 0; + for (; ((s1.Position != s1.Length) + && (s1.ReadByte() == s2.ReadByte())); ) { + ; + } + if ((s1.Position == s1.Length)) { + return type; + } + } + } + } + finally { + if ((s1 != null)) { + s1.Close(); + } + if ((s2 != null)) { + s2.Close(); + } + } + } + xs.Add(dsSchema); + return type; + } + + public delegate void AssociationRowChangeEventHandler(object sender, AssociationRowChangeEvent e); + + /// <summary> + ///Represents the strongly named DataTable class. + ///</summary> + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Data.Design.TypedDataSetGenerator", "2.0.0.0")] + [global::System.Serializable()] + [global::System.Xml.Serialization.XmlSchemaProviderAttribute("GetTypedTableSchema")] + public partial class AssociationDataTable : global::System.Data.TypedTableBase<AssociationRow> { + + private global::System.Data.DataColumn columnDistinguishingFactor; + + private global::System.Data.DataColumn columnHandle; + + private global::System.Data.DataColumn columnExpires; + + private global::System.Data.DataColumn columnPrivateData; + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public AssociationDataTable() { + this.TableName = "Association"; + this.BeginInit(); + this.InitClass(); + this.EndInit(); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + internal AssociationDataTable(global::System.Data.DataTable table) { + this.TableName = table.TableName; + if ((table.CaseSensitive != table.DataSet.CaseSensitive)) { + this.CaseSensitive = table.CaseSensitive; + } + if ((table.Locale.ToString() != table.DataSet.Locale.ToString())) { + this.Locale = table.Locale; + } + if ((table.Namespace != table.DataSet.Namespace)) { + this.Namespace = table.Namespace; + } + this.Prefix = table.Prefix; + this.MinimumCapacity = table.MinimumCapacity; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected AssociationDataTable(global::System.Runtime.Serialization.SerializationInfo info, global::System.Runtime.Serialization.StreamingContext context) : + base(info, context) { + this.InitVars(); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public global::System.Data.DataColumn DistinguishingFactorColumn { + get { + return this.columnDistinguishingFactor; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public global::System.Data.DataColumn HandleColumn { + get { + return this.columnHandle; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public global::System.Data.DataColumn ExpiresColumn { + get { + return this.columnExpires; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public global::System.Data.DataColumn PrivateDataColumn { + get { + return this.columnPrivateData; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + [global::System.ComponentModel.Browsable(false)] + public int Count { + get { + return this.Rows.Count; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public AssociationRow this[int index] { + get { + return ((AssociationRow)(this.Rows[index])); + } + } + + public event AssociationRowChangeEventHandler AssociationRowChanging; + + public event AssociationRowChangeEventHandler AssociationRowChanged; + + public event AssociationRowChangeEventHandler AssociationRowDeleting; + + public event AssociationRowChangeEventHandler AssociationRowDeleted; + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public void AddAssociationRow(AssociationRow row) { + this.Rows.Add(row); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public AssociationRow AddAssociationRow(string DistinguishingFactor, string Handle, System.DateTime Expires, byte[] PrivateData) { + AssociationRow rowAssociationRow = ((AssociationRow)(this.NewRow())); + object[] columnValuesArray = new object[] { + DistinguishingFactor, + Handle, + Expires, + PrivateData}; + rowAssociationRow.ItemArray = columnValuesArray; + this.Rows.Add(rowAssociationRow); + return rowAssociationRow; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public AssociationRow FindByDistinguishingFactorHandle(string DistinguishingFactor, string Handle) { + return ((AssociationRow)(this.Rows.Find(new object[] { + DistinguishingFactor, + Handle}))); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public override global::System.Data.DataTable Clone() { + AssociationDataTable cln = ((AssociationDataTable)(base.Clone())); + cln.InitVars(); + return cln; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override global::System.Data.DataTable CreateInstance() { + return new AssociationDataTable(); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + internal void InitVars() { + this.columnDistinguishingFactor = base.Columns["DistinguishingFactor"]; + this.columnHandle = base.Columns["Handle"]; + this.columnExpires = base.Columns["Expires"]; + this.columnPrivateData = base.Columns["PrivateData"]; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + private void InitClass() { + this.columnDistinguishingFactor = new global::System.Data.DataColumn("DistinguishingFactor", typeof(string), null, global::System.Data.MappingType.Element); + base.Columns.Add(this.columnDistinguishingFactor); + this.columnHandle = new global::System.Data.DataColumn("Handle", typeof(string), null, global::System.Data.MappingType.Element); + base.Columns.Add(this.columnHandle); + this.columnExpires = new global::System.Data.DataColumn("Expires", typeof(global::System.DateTime), null, global::System.Data.MappingType.Element); + base.Columns.Add(this.columnExpires); + this.columnPrivateData = new global::System.Data.DataColumn("PrivateData", typeof(byte[]), null, global::System.Data.MappingType.Element); + base.Columns.Add(this.columnPrivateData); + this.Constraints.Add(new global::System.Data.UniqueConstraint("PrimaryKey", new global::System.Data.DataColumn[] { + this.columnDistinguishingFactor, + this.columnHandle}, true)); + this.columnDistinguishingFactor.AllowDBNull = false; + this.columnHandle.AllowDBNull = false; + this.columnExpires.AllowDBNull = false; + this.columnPrivateData.AllowDBNull = false; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public AssociationRow NewAssociationRow() { + return ((AssociationRow)(this.NewRow())); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override global::System.Data.DataRow NewRowFromBuilder(global::System.Data.DataRowBuilder builder) { + return new AssociationRow(builder); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override global::System.Type GetRowType() { + return typeof(AssociationRow); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override void OnRowChanged(global::System.Data.DataRowChangeEventArgs e) { + base.OnRowChanged(e); + if ((this.AssociationRowChanged != null)) { + this.AssociationRowChanged(this, new AssociationRowChangeEvent(((AssociationRow)(e.Row)), e.Action)); + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override void OnRowChanging(global::System.Data.DataRowChangeEventArgs e) { + base.OnRowChanging(e); + if ((this.AssociationRowChanging != null)) { + this.AssociationRowChanging(this, new AssociationRowChangeEvent(((AssociationRow)(e.Row)), e.Action)); + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override void OnRowDeleted(global::System.Data.DataRowChangeEventArgs e) { + base.OnRowDeleted(e); + if ((this.AssociationRowDeleted != null)) { + this.AssociationRowDeleted(this, new AssociationRowChangeEvent(((AssociationRow)(e.Row)), e.Action)); + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + protected override void OnRowDeleting(global::System.Data.DataRowChangeEventArgs e) { + base.OnRowDeleting(e); + if ((this.AssociationRowDeleting != null)) { + this.AssociationRowDeleting(this, new AssociationRowChangeEvent(((AssociationRow)(e.Row)), e.Action)); + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public void RemoveAssociationRow(AssociationRow row) { + this.Rows.Remove(row); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public static global::System.Xml.Schema.XmlSchemaComplexType GetTypedTableSchema(global::System.Xml.Schema.XmlSchemaSet xs) { + global::System.Xml.Schema.XmlSchemaComplexType type = new global::System.Xml.Schema.XmlSchemaComplexType(); + global::System.Xml.Schema.XmlSchemaSequence sequence = new global::System.Xml.Schema.XmlSchemaSequence(); + CustomStoreDataSet ds = new CustomStoreDataSet(); + global::System.Xml.Schema.XmlSchemaAny any1 = new global::System.Xml.Schema.XmlSchemaAny(); + any1.Namespace = "http://www.w3.org/2001/XMLSchema"; + any1.MinOccurs = new decimal(0); + any1.MaxOccurs = decimal.MaxValue; + any1.ProcessContents = global::System.Xml.Schema.XmlSchemaContentProcessing.Lax; + sequence.Items.Add(any1); + global::System.Xml.Schema.XmlSchemaAny any2 = new global::System.Xml.Schema.XmlSchemaAny(); + any2.Namespace = "urn:schemas-microsoft-com:xml-diffgram-v1"; + any2.MinOccurs = new decimal(1); + any2.ProcessContents = global::System.Xml.Schema.XmlSchemaContentProcessing.Lax; + sequence.Items.Add(any2); + global::System.Xml.Schema.XmlSchemaAttribute attribute1 = new global::System.Xml.Schema.XmlSchemaAttribute(); + attribute1.Name = "namespace"; + attribute1.FixedValue = ds.Namespace; + type.Attributes.Add(attribute1); + global::System.Xml.Schema.XmlSchemaAttribute attribute2 = new global::System.Xml.Schema.XmlSchemaAttribute(); + attribute2.Name = "tableTypeName"; + attribute2.FixedValue = "AssociationDataTable"; + type.Attributes.Add(attribute2); + type.Particle = sequence; + global::System.Xml.Schema.XmlSchema dsSchema = ds.GetSchemaSerializable(); + if (xs.Contains(dsSchema.TargetNamespace)) { + global::System.IO.MemoryStream s1 = new global::System.IO.MemoryStream(); + global::System.IO.MemoryStream s2 = new global::System.IO.MemoryStream(); + try { + global::System.Xml.Schema.XmlSchema schema = null; + dsSchema.Write(s1); + for (global::System.Collections.IEnumerator schemas = xs.Schemas(dsSchema.TargetNamespace).GetEnumerator(); schemas.MoveNext(); ) { + schema = ((global::System.Xml.Schema.XmlSchema)(schemas.Current)); + s2.SetLength(0); + schema.Write(s2); + if ((s1.Length == s2.Length)) { + s1.Position = 0; + s2.Position = 0; + for (; ((s1.Position != s1.Length) + && (s1.ReadByte() == s2.ReadByte())); ) { + ; + } + if ((s1.Position == s1.Length)) { + return type; + } + } + } + } + finally { + if ((s1 != null)) { + s1.Close(); + } + if ((s2 != null)) { + s2.Close(); + } + } + } + xs.Add(dsSchema); + return type; + } + } + + /// <summary> + ///Represents strongly named DataRow class. + ///</summary> + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Data.Design.TypedDataSetGenerator", "2.0.0.0")] + public partial class AssociationRow : global::System.Data.DataRow { + + private AssociationDataTable tableAssociation; + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + internal AssociationRow(global::System.Data.DataRowBuilder rb) : + base(rb) { + this.tableAssociation = ((AssociationDataTable)(this.Table)); + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public string DistinguishingFactor { + get { + return ((string)(this[this.tableAssociation.DistinguishingFactorColumn])); + } + set { + this[this.tableAssociation.DistinguishingFactorColumn] = value; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public string Handle { + get { + return ((string)(this[this.tableAssociation.HandleColumn])); + } + set { + this[this.tableAssociation.HandleColumn] = value; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public System.DateTime Expires { + get { + return ((global::System.DateTime)(this[this.tableAssociation.ExpiresColumn])); + } + set { + this[this.tableAssociation.ExpiresColumn] = value; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public byte[] PrivateData { + get { + return ((byte[])(this[this.tableAssociation.PrivateDataColumn])); + } + set { + this[this.tableAssociation.PrivateDataColumn] = value; + } + } + } + + /// <summary> + ///Row event argument class + ///</summary> + [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Data.Design.TypedDataSetGenerator", "2.0.0.0")] + public class AssociationRowChangeEvent : global::System.EventArgs { + + private AssociationRow eventRow; + + private global::System.Data.DataRowAction eventAction; + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public AssociationRowChangeEvent(AssociationRow row, global::System.Data.DataRowAction action) { + this.eventRow = row; + this.eventAction = action; + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public AssociationRow Row { + get { + return this.eventRow; + } + } + + [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] + public global::System.Data.DataRowAction Action { + get { + return this.eventAction; + } + } + } + } +} + +#pragma warning restore 1591
\ No newline at end of file diff --git a/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xsc b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xsc new file mode 100644 index 0000000..05b0199 --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xsc @@ -0,0 +1,9 @@ +<?xml version="1.0" encoding="utf-8"?> +<!--<autogenerated> + This code was generated by a tool. + Changes to this file may cause incorrect behavior and will be lost if + the code is regenerated. +</autogenerated>--> +<DataSetUISetting Version="1.00" xmlns="urn:schemas-microsoft-com:xml-msdatasource"> + <TableUISettings /> +</DataSetUISetting>
\ No newline at end of file diff --git a/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xsd b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xsd new file mode 100644 index 0000000..63226bd --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xsd @@ -0,0 +1,33 @@ +<?xml version="1.0" encoding="utf-8"?> +<xs:schema id="CustomStoreDataSet" targetNamespace="http://tempuri.org/CustomStoreDataSet.xsd" xmlns:mstns="http://tempuri.org/CustomStoreDataSet.xsd" xmlns="http://tempuri.org/CustomStoreDataSet.xsd" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata" xmlns:msprop="urn:schemas-microsoft-com:xml-msprop" attributeFormDefault="qualified" elementFormDefault="qualified"> + <xs:annotation> + <xs:appinfo source="urn:schemas-microsoft-com:xml-msdatasource"> + <DataSource DefaultConnectionIndex="0" FunctionsComponentName="QueriesTableAdapter" Modifier="AutoLayout, AnsiClass, Class, Public" SchemaSerializationMode="IncludeSchema" xmlns="urn:schemas-microsoft-com:xml-msdatasource"> + <Connections /> + <Tables /> + <Sources /> + </DataSource> + </xs:appinfo> + </xs:annotation> + <xs:element name="CustomStoreDataSet" msdata:IsDataSet="true" msdata:UseCurrentLocale="true" msprop:Generator_UserDSName="CustomStoreDataSet" msprop:Generator_DataSetName="CustomStoreDataSet" msprop:EnableTableAdapterManager="true"> + <xs:complexType> + <xs:choice minOccurs="0" maxOccurs="unbounded"> + <xs:element name="Association" msprop:Generator_UserTableName="Association" msprop:Generator_RowDeletedName="AssociationRowDeleted" msprop:Generator_RowChangedName="AssociationRowChanged" msprop:Generator_RowClassName="AssociationRow" msprop:Generator_RowChangingName="AssociationRowChanging" msprop:Generator_RowEvArgName="AssociationRowChangeEvent" msprop:Generator_RowEvHandlerName="AssociationRowChangeEventHandler" msprop:Generator_TableClassName="AssociationDataTable" msprop:Generator_TableVarName="tableAssociation" msprop:Generator_RowDeletingName="AssociationRowDeleting" msprop:Generator_TablePropName="Association"> + <xs:complexType> + <xs:sequence> + <xs:element name="DistinguishingFactor" msprop:Generator_UserColumnName="DistinguishingFactor" msprop:Generator_ColumnPropNameInRow="DistinguishingFactor" msprop:Generator_ColumnVarNameInTable="columnDistinguishingFactor" msprop:Generator_ColumnPropNameInTable="DistinguishingFactorColumn" type="xs:string" /> + <xs:element name="Handle" msprop:Generator_UserColumnName="Handle" msprop:Generator_ColumnPropNameInRow="Handle" msprop:Generator_ColumnVarNameInTable="columnHandle" msprop:Generator_ColumnPropNameInTable="HandleColumn" type="xs:string" /> + <xs:element name="Expires" msprop:Generator_UserColumnName="Expires" msprop:Generator_ColumnPropNameInRow="Expires" msprop:Generator_ColumnVarNameInTable="columnExpires" msprop:Generator_ColumnPropNameInTable="ExpiresColumn" type="xs:dateTime" /> + <xs:element name="PrivateData" msprop:Generator_UserColumnName="PrivateData" msprop:Generator_ColumnPropNameInRow="PrivateData" msprop:Generator_ColumnVarNameInTable="columnPrivateData" msprop:Generator_ColumnPropNameInTable="PrivateDataColumn" type="xs:base64Binary" /> + </xs:sequence> + </xs:complexType> + </xs:element> + </xs:choice> + </xs:complexType> + <xs:unique name="PrimaryKey" msdata:PrimaryKey="true"> + <xs:selector xpath=".//mstns:Association" /> + <xs:field xpath="mstns:DistinguishingFactor" /> + <xs:field xpath="mstns:Handle" /> + </xs:unique> + </xs:element> +</xs:schema>
\ No newline at end of file diff --git a/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xss b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xss new file mode 100644 index 0000000..0b3972e --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/CustomStoreDataSet.xss @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="utf-8"?> +<!--<autogenerated> + This code was generated by a tool to store the dataset designer's layout information. + Changes to this file may cause incorrect behavior and will be lost if + the code is regenerated. +</autogenerated>--> +<DiagramLayout xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" ex:showrelationlabel="False" ViewPortX="0" ViewPortY="0" xmlns:ex="urn:schemas-microsoft-com:xml-msdatasource-layout-extended" xmlns="urn:schemas-microsoft-com:xml-msdatasource-layout"> + <Shapes> + <Shape ID="DesignTable:Association" ZOrder="1" X="349" Y="83" Height="105" Width="154" AdapterExpanded="true" DataTableExpanded="true" OldAdapterHeight="0" OldDataTableHeight="0" SplitterPosition="101" /> + </Shapes> + <Connectors /> +</DiagramLayout>
\ No newline at end of file diff --git a/samples/OpenIdProviderWebForms/Code/ReadOnlyXmlMembershipProvider.cs b/samples/OpenIdProviderWebForms/Code/ReadOnlyXmlMembershipProvider.cs new file mode 100644 index 0000000..54db5c0 --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/ReadOnlyXmlMembershipProvider.cs @@ -0,0 +1,270 @@ +namespace OpenIdProviderWebForms.Code { + using System; + using System.Collections.Generic; + using System.Collections.Specialized; + using System.Configuration.Provider; + using System.Security.Permissions; + using System.Web; + using System.Web.Hosting; + using System.Web.Security; + using System.Xml; + + public class ReadOnlyXmlMembershipProvider : MembershipProvider { + private Dictionary<string, MembershipUser> users; + private string xmlFileName; + + // MembershipProvider Properties + public override string ApplicationName { + get { throw new NotSupportedException(); } + set { throw new NotSupportedException(); } + } + + public override bool EnablePasswordRetrieval { + get { return false; } + } + + public override bool EnablePasswordReset { + get { return false; } + } + + public override int MaxInvalidPasswordAttempts { + get { throw new NotSupportedException(); } + } + + public override int MinRequiredNonAlphanumericCharacters { + get { throw new NotSupportedException(); } + } + + public override int MinRequiredPasswordLength { + get { throw new NotSupportedException(); } + } + + public override int PasswordAttemptWindow { + get { throw new NotSupportedException(); } + } + + public override MembershipPasswordFormat PasswordFormat { + get { throw new NotSupportedException(); } + } + + public override string PasswordStrengthRegularExpression { + get { throw new NotSupportedException(); } + } + + public override bool RequiresQuestionAndAnswer { + get { throw new NotSupportedException(); } + } + + public override bool RequiresUniqueEmail { + get { throw new NotSupportedException(); } + } + + // MembershipProvider Methods + public override void Initialize(string name, NameValueCollection config) { + // Verify that config isn't null + if (config == null) { + throw new ArgumentNullException("config"); + } + + // Assign the provider a default name if it doesn't have one + if (string.IsNullOrEmpty(name)) { + name = "ReadOnlyXmlMembershipProvider"; + } + + // Add a default "description" attribute to config if the + // attribute doesn't exist or is empty + if (string.IsNullOrEmpty(config["description"])) { + config.Remove("description"); + config.Add("description", "Read-only XML membership provider"); + } + + // Call the base class's Initialize method + base.Initialize(name, config); + + // Initialize _XmlFileName and make sure the path + // is app-relative + string path = config["xmlFileName"]; + + if (string.IsNullOrEmpty(path)) { + path = "~/App_Data/Users.xml"; + } + + if (!VirtualPathUtility.IsAppRelative(path)) { + throw new ArgumentException("xmlFileName must be app-relative"); + } + + string fullyQualifiedPath = VirtualPathUtility.Combine( + VirtualPathUtility.AppendTrailingSlash(HttpRuntime.AppDomainAppVirtualPath), + path); + + this.xmlFileName = HostingEnvironment.MapPath(fullyQualifiedPath); + config.Remove("xmlFileName"); + + // Make sure we have permission to read the XML data source and + // throw an exception if we don't + FileIOPermission permission = new FileIOPermission(FileIOPermissionAccess.Read, this.xmlFileName); + permission.Demand(); + + // Throw an exception if unrecognized attributes remain + if (config.Count > 0) { + string attr = config.GetKey(0); + if (!string.IsNullOrEmpty(attr)) { + throw new ProviderException("Unrecognized attribute: " + attr); + } + } + } + + public override bool ValidateUser(string username, string password) { + // Validate input parameters + if (string.IsNullOrEmpty(username) || + string.IsNullOrEmpty(password)) { + return false; + } + + try { + // Make sure the data source has been loaded + this.ReadMembershipDataStore(); + + // Validate the user name and password + MembershipUser user; + if (this.users.TryGetValue(username, out user)) { + if (user.Comment == password) { // Case-sensitive + // NOTE: A read/write membership provider + // would update the user's LastLoginDate here. + // A fully featured provider would also fire + // an AuditMembershipAuthenticationSuccess + // Web event + return true; + } + } + + // NOTE: A fully featured membership provider would + // fire an AuditMembershipAuthenticationFailure + // Web event here + return false; + } catch (Exception) { + return false; + } + } + + public override MembershipUser GetUser(string username, bool userIsOnline) { + // Note: This implementation ignores userIsOnline + + // Validate input parameters + if (string.IsNullOrEmpty(username)) { + return null; + } + + // Make sure the data source has been loaded + this.ReadMembershipDataStore(); + + // Retrieve the user from the data source + MembershipUser user; + if (this.users.TryGetValue(username, out user)) { + return user; + } + + return null; + } + + public override MembershipUserCollection GetAllUsers(int pageIndex, int pageSize, out int totalRecords) { + // Note: This implementation ignores pageIndex and pageSize, + // and it doesn't sort the MembershipUser objects returned + + // Make sure the data source has been loaded + this.ReadMembershipDataStore(); + + MembershipUserCollection users = new MembershipUserCollection(); + + foreach (KeyValuePair<string, MembershipUser> pair in this.users) { + users.Add(pair.Value); + } + + totalRecords = users.Count; + return users; + } + + public override int GetNumberOfUsersOnline() { + throw new NotSupportedException(); + } + + public override bool ChangePassword(string username, string oldPassword, string newPassword) { + throw new NotSupportedException(); + } + + public override bool ChangePasswordQuestionAndAnswer(string username, string password, string newPasswordQuestion, string newPasswordAnswer) { + throw new NotSupportedException(); + } + + public override MembershipUser CreateUser(string username, string password, string email, string passwordQuestion, string passwordAnswer, bool isApproved, object providerUserKey, out MembershipCreateStatus status) { + throw new NotSupportedException(); + } + + public override bool DeleteUser(string username, bool deleteAllRelatedData) { + throw new NotSupportedException(); + } + + public override MembershipUserCollection FindUsersByEmail(string emailToMatch, int pageIndex, int pageSize, out int totalRecords) { + throw new NotSupportedException(); + } + + public override MembershipUserCollection FindUsersByName(string usernameToMatch, int pageIndex, int pageSize, out int totalRecords) { + throw new NotSupportedException(); + } + + public override string GetPassword(string username, string answer) { + throw new NotSupportedException(); + } + + public override MembershipUser GetUser(object providerUserKey, bool userIsOnline) { + throw new NotSupportedException(); + } + + public override string GetUserNameByEmail(string email) { + throw new NotSupportedException(); + } + + public override string ResetPassword(string username, string answer) { + throw new NotSupportedException(); + } + + public override bool UnlockUser(string userName) { + throw new NotSupportedException(); + } + + public override void UpdateUser(MembershipUser user) { + throw new NotSupportedException(); + } + + // Helper method + private void ReadMembershipDataStore() { + lock (this) { + if (this.users == null) { + this.users = new Dictionary<string, MembershipUser>(16, StringComparer.InvariantCultureIgnoreCase); + XmlDocument doc = new XmlDocument(); + doc.Load(this.xmlFileName); + XmlNodeList nodes = doc.GetElementsByTagName("User"); + + foreach (XmlNode node in nodes) { + MembershipUser user = new MembershipUser( + Name, // Provider name + node["UserName"].InnerText, // Username + null, // providerUserKey + null, // Email + string.Empty, // passwordQuestion + node["Password"].InnerText, // Comment + true, // isApproved + false, // isLockedOut + DateTime.Now, // creationDate + DateTime.Now, // lastLoginDate + DateTime.Now, // lastActivityDate + DateTime.Now, // lastPasswordChangedDate + new DateTime(1980, 1, 1)); // lastLockoutDate + + this.users.Add(user.UserName, user); + } + } + } + } + } +}
\ No newline at end of file diff --git a/samples/OpenIdProviderWebForms/Code/TracePageAppender.cs b/samples/OpenIdProviderWebForms/Code/TracePageAppender.cs new file mode 100644 index 0000000..1bb7a34 --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/TracePageAppender.cs @@ -0,0 +1,13 @@ +namespace OpenIdProviderWebForms.Code { + using System; + using System.Collections.Generic; + using System.IO; + using System.Web; + + public class TracePageAppender : log4net.Appender.AppenderSkeleton { + protected override void Append(log4net.Core.LoggingEvent loggingEvent) { + StringWriter sw = new StringWriter(Global.LogMessages); + Layout.Format(sw, loggingEvent); + } + } +} diff --git a/samples/OpenIdProviderWebForms/Code/URLRewriter.cs b/samples/OpenIdProviderWebForms/Code/URLRewriter.cs new file mode 100644 index 0000000..daa4dea --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/URLRewriter.cs @@ -0,0 +1,61 @@ +namespace OpenIdProviderWebForms.Code { + using System.Configuration; + using System.Diagnostics; + using System.Text.RegularExpressions; + using System.Web; + using System.Xml; + + // nicked from http://www.codeproject.com/aspnet/URLRewriter.asp + public class URLRewriter : IConfigurationSectionHandler { + public static log4net.ILog Logger = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); + + protected XmlNode rules = null; + + protected URLRewriter() { + } + + public static void Process() { + URLRewriter rewriter = (URLRewriter)ConfigurationManager.GetSection("urlrewrites"); + + string subst = rewriter.GetSubstitution(HttpContext.Current.Request.Path); + + if (!string.IsNullOrEmpty(subst)) { + Logger.InfoFormat("Rewriting url '{0}' to '{1}' ", HttpContext.Current.Request.Path, subst); + HttpContext.Current.RewritePath(subst); + } + } + + public string GetSubstitution(string path) { + foreach (XmlNode node in this.rules.SelectNodes("rule")) { + // get the url and rewrite nodes + XmlNode urlNode = node.SelectSingleNode("url"); + XmlNode rewriteNode = node.SelectSingleNode("rewrite"); + + // check validity of the values + if (urlNode == null || string.IsNullOrEmpty(urlNode.InnerText) + || rewriteNode == null || string.IsNullOrEmpty(rewriteNode.InnerText)) { + Logger.Warn("Invalid urlrewrites rule discovered in web.config file."); + continue; + } + + Regex reg = new Regex(urlNode.InnerText, RegexOptions.IgnoreCase); + + // if match, return the substitution + Match match = reg.Match(path); + if (match.Success) { + return reg.Replace(path, rewriteNode.InnerText); + } + } + + return null; // no rewrite + } + + #region Implementation of IConfigurationSectionHandler + public object Create(object parent, object configContext, XmlNode section) { + this.rules = section; + + return this; + } + #endregion + } +}
\ No newline at end of file diff --git a/samples/OpenIdProviderWebForms/Code/Util.cs b/samples/OpenIdProviderWebForms/Code/Util.cs new file mode 100644 index 0000000..5cec951 --- /dev/null +++ b/samples/OpenIdProviderWebForms/Code/Util.cs @@ -0,0 +1,56 @@ +//----------------------------------------------------------------------- +// <copyright file="Util.cs" company="Andrew Arnott"> +// Copyright (c) Andrew Arnott. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace OpenIdProviderWebForms.Code { + using System; + using System.Collections.Generic; + using System.Diagnostics; + using System.Net; + using System.Text; + using System.Web; + using DotNetOpenAuth.OpenId; + using DotNetOpenAuth.OpenId.Provider; + + public class Util { + public static string ExtractUserName(Uri url) { + return url.Segments[url.Segments.Length - 1]; + } + + public static string ExtractUserName(Identifier identifier) { + return ExtractUserName(new Uri(identifier.ToString())); + } + + public static Identifier BuildIdentityUrl() { + string username = HttpContext.Current.User.Identity.Name; + + // be sure to normalize case the way the user's identity page does. + username = username.Substring(0, 1).ToUpperInvariant() + username.Substring(1).ToLowerInvariant(); + return new Uri(HttpContext.Current.Request.Url, "/user/" + username); + } + + internal static void ProcessAuthenticationChallenge(IAuthenticationRequest idrequest) { + if (idrequest.Immediate) { + if (idrequest.IsDirectedIdentity) { + if (HttpContext.Current.User.Identity.IsAuthenticated) { + idrequest.LocalIdentifier = Util.BuildIdentityUrl(); + idrequest.IsAuthenticated = true; + } else { + idrequest.IsAuthenticated = false; + } + } else { + string userOwningOpenIdUrl = Util.ExtractUserName(idrequest.LocalIdentifier); + + // NOTE: in a production provider site, you may want to only + // respond affirmatively if the user has already authorized this consumer + // to know the answer. + idrequest.IsAuthenticated = userOwningOpenIdUrl == HttpContext.Current.User.Identity.Name; + } + } else { + HttpContext.Current.Response.Redirect("~/decide.aspx", true); + } + } + } +}
\ No newline at end of file |