Sinds de release ervan hebben ASP.NET-toepassingen en componenten gekeken naar het web.config-bestand om alle instellingen te laden die ze nodig hebben om te functioneren. Het toevoegen van aangepaste instellingen om flexibiliteit en robuustheid aan een toepassing of component toe te voegen, is echter niet zo eenvoudig als de meeste zouden willen. In dit artikel leert u hoe u de noodzakelijke klassen schrijft om XML-configuratie-elementen af te handelen en de instellingen te gebruiken die ze in uw code bevatten.
Opnieuw gepubliceerde zelfstudieOm de paar weken bekijken we enkele van onze favoriete lezers uit de geschiedenis van de site. Deze tutorial werd voor het eerst gepubliceerd in november 2012.
Het .NET Framework biedt een breed scala aan instellingen die kunnen worden geconfigureerd in web.config om het gedrag van een of meer ingebouwde componenten in de toepassing te wijzigen. Voor sommige ontwikkelaars is het volstaan om alleen de instellingen van het .NET Framework te volgen. Maar veel meer ontwikkelaars vinden dat ze een bredere verzameling instellingen moeten beheren - hetzij voor componenten (die ze zelf of een derde partij hebben geschreven), of gewoon een reeks waarden die ze tijdens hun toepassing gebruiken..
Met het bestand web.config kunt u aangepaste instellingen instellen met de
Key / Value-instellingen kunnen in veel omstandigheden zeker nuttig zijn, maar
Gelukkig stelt Microsoft ontwikkelaars in staat klassen te schrijven die programmatische toegang tot aangepaste configuratie-instellingen binnen web.config toevoegen.
Instellingen binnen web.config worden gecategoriseerd in configuratiesecties. Bijvoorbeeld de instellingen in de
sectie heeft betrekking op ASP.NET-instellingen voor uw toepassing. U kunt het authenticatieschema van uw app wijzigen en HTTP-handlers toevoegen of verwijderen om specifieke functies voor specifieke bestandstypen uit te voeren. De
Een configuratiesectie is vereist voor alle instellingen die niet zijn opgenomen in de
De configuratie die als voorbeeld wordt gebruikt in deze zelfstudie, is voor een component die RSS- of Atom-feeds ophaalt. Er wordt niet geparseerd, omdat dit buiten het bestek van deze zelfstudie valt. In plaats van het hard coderen van de lijst met feeds die moeten worden opgehaald, kijkt de component naar de configuratie ervan met de namen en URL's van de feeds die moeten worden opgehaald. Het onderdeel heet FeedRetriever en de gewenste XML-structuur van de configuratie ziet er als volgt uit:
De
Deze
De bovenstaande configuratie is eenvoudig. De
Na het ontwerpen van de XML-structuur, is de volgende stap het schrijven van een configuratiehandler voor het verwerken van de instellingen die in de XML zijn gedefinieerd. De handler is primair een klasse die overerft van System.Configuration.ConfigurationSection, maar deze bevat ook het gebruik van andere klassen - zoals klassen die zijn afgeleid van System.Configuration.ConfigurationElement en System.Configuration.ConfigurationElementCollection.
Klassen op basis van ConfigurationElement vertegenwoordigen individuele elementen; het is de bouwsteen van een configuratiesectie. Typen die afkomstig zijn van ConfigurationElementCollection vertegenwoordigen eenvoudig elementen die meer dan één type element bevatten. Uit de bovenstaande configuratie, de
ElementJe begint met de
Elk ConfigurationElement-object functioneert als een index voor de interne verzameling van eigenschapswaarden. Het is deze interne verzameling, samen met .NET-kenmerken, waarmee u de kaart kunt toewijzen
De volgende code is de volledige code voor de klasse FeedElement:
public class FeedElement: ConfigurationElement [ConfigurationProperty ("name", IsKey = true, IsRequired = true)] public string Name get return (string) this ["name"]; stel this ["name"] = waarde in; [ConfigurationProperty ("url", IsRequired = true, DefaultValue = "http: // localhost")] [RegexStringValidator (@ "https? \: // \ S +")] public string Url krijg return (string) deze [ "url"]; stel this ["url"] = waarde in; [ConfigurationProperty ("cache", IsRequired = false, DefaultValue = true)] public bool Cache get return (bool) this ["cache"]; stel this ["cache"] = waarde in;
De ConfigurationElement-klasse dient als een indexering voor een onderliggende verzameling configuratie-eigenschappen (vandaar de indexeringsnotatie van deze [keyValue]). Door dit sleutelwoord te gebruiken en toegang te krijgen tot de onderliggende eigenschap met een tekenreekscode, kunt u de waarde van de eigenschap ophalen en instellen zonder dat een privéveld die gegevens bevat. De onderliggende eigenschappenverzameling slaat gegevens op als type Object; daarom moet je de waarde uitbrengen als het juiste type als je er iets mee wilt doen.
De eigenschappen die XML-attributen vertegenwoordigen, zijn versierd met ConfigurationPropertyAttribute-kenmerken. De eerste parameter van het kenmerk ConfigurationPropertyAttribute is de naam van het XML-kenmerk dat wordt gevonden in de
De standaardwaarde van "http: // localhost" voor de eigenschap Url is geen fout. Het .NET Framework biedt u ook de mogelijkheid om de eigenschappen te verfraaien met validatorattributen, zoals het RegexStringValidatorAttribute dat de eigenschap Url verfraait. Deze validator neemt de waarde van de eigenschap Url en valideert deze met de reguliere expressie die aan het kenmerk wordt verstrekt; het valideert echter ook de eigenschap Url voordat deze de gegevens uit het XML-element bevat. De standaardwaarde van de eigenschap Url is een lege tekenreeks wanneer een FeedElement-object voor het eerst wordt gemaakt. Een lege tekenreeks valideert niet met de opgegeven reguliere expressie, dus de validator genereert een ArgumentException voordat gegevens worden geladen vanuit het XML-bestand.
Er zijn twee mogelijke oplossingen voor dit probleem. De eerste benadering wijzigt de reguliere expressie om lege tekenreeksen toe te staan. De tweede benadering wijst een standaardwaarde toe aan de eigenschap. Het maakt in dit specifieke geval niet uit. Zelfs met een standaardwaarde is het kenmerk url nog steeds een vereist kenmerk in de
Er zijn verschillende andere validatorattributen in de namespace System.Configuration om gegevens te valideren die zijn toegewezen aan eigenschappen en de XML-kenmerken waarnaar ze verwijzen. Hieronder worden alle validatorattributen weergegeven in de naamruimte System.Configuration:
Met uitzondering van het CallbackValidatorAttribute, hoeft u geen bijbehorende validatorobjecten te maken voor gebruik in combinatie met de validatorattributen. De runtime van .NET maakt de juiste validatorobjecten voor u en de kenmerken bevatten de benodigde parameters om de validatorobjecten te configureren.
Dit kleine stukje code is alles wat nodig is om een individu programmatisch te vertegenwoordigen
De XML-weergave van de
De klasse ConfigurationElementCollection bevat verschillende leden, maar slechts twee zijn gemarkeerd als abstract. De eenvoudigste implementatie ConfigurationElementCollection heeft dus twee methoden:
Bekijk met dat in gedachten de volledige code voor de klasse FeedElementCollection hieronder:
[ConfigurationCollection (typeof (FeedElement))] public class FeedElementCollection: ConfigurationElementCollection protected override ConfigurationElement CreateNewElement () return new FeedElement (); beveiligd override-object GetElementKey (element ConfigurationElement) return ((FeedElement) -element) .Name;
Een ConfigurationCollectionAttribute siert deze collectieklasse. De eerste parameter voor het kenmerk is een Type-object - het type items dat de verzameling bevat. In dit geval is dit het FeedElement-type. Nadat de parameter type verschillende parameters heeft gekregen, kunt u deze doorgeven aan het kenmerk. Deze staan hieronder vermeld:
Als je deze parameters wit laat, worden ze standaard ingesteld
De laatste klasse, genaamd FeedRetrieverSection, is afgeleid van ConfigurationSection en vertegenwoordigt de
public class FeedRetrieverSection: ConfigurationSection [ConfigurationProperty ("feeds", IsDefaultCollection = true)] public FeedElementCollection Feeds krijg return (FeedElementCollection) this ["feeds"]; stel this ["feeds"] = waarde in;
Het is één eigenschap, van het type FeedElementCollection en genaamd Feeds, is versierd met een ConfigurationPropertyAttribute - het toewijzen aan de
Als de configuratiehandler is voltooid, kunt u de juiste elementen toevoegen aan web.config. De
De volgende stap is het toevoegen van een onderliggende element
Het volgende element is wat u toevoegt aan een web.config-bestand, onder
Uw toepassing is nu correct geconfigureerd om de klassen FeedRetrieverSection, FeedElementCollection en FeedElement te gebruiken om u programmatische toegang te verlenen tot de aangepaste instellingen in de
De namespace System.Configuration bevat een statische klasse met de naam ConfigurationManager. Als u de
FeedRetrieverSection config = ConfigurationManager.GetSection ("feedRetriever") als FeedRetrieverSection;
De methode GetSection () retourneert een waarde van het type Object, dus deze moet worden gegoten in het type van de handler voor die sectie. Deze code haalt de sectie genaamd feedRetriever op en cast het resultaat als FeedRetrieverSection. Zodra u het object hebt, kunt u programmatisch toegang krijgen tot configuratiegegevens.
Om u een idee te geven van hoe configuratie-instellingen binnen uw component of applicatie kunnen worden gebruikt, is de volgende code een zeer eenvoudige implementatie van de FeedRetriever-component.
public class FeedRetriever public static FeedRetrieverSection _Config = ConfigurationManager.GetSection ("feedRetriever") als FeedRetrieverSection;
public static void GetFeeds () foreach (FeedElement feedEl in _Config.Feeds) // aanvraag HttpWebRequest request = (HttpWebRequest) WebRequest.Create (feedEl.Url); HttpWebResponse response = (HttpWebResponse) request.GetResponse (); if (response.StatusCode == HttpStatusCode.OK) string feedData = String.Empty; using (StreamReader reader = new StreamReader (response.GetResponseStream ())) feedData = reader.ReadToEnd (); if (feedEl.Cache) // bestandsnaam van cachebestandstring bestandsnaam = String.Format ("0 _ 1 .xml", feedEl.Name, DateTime.Now.Ticks); // cachebestand met (StreamWriter writer = new StreamWriter (@ "C: \" + bestandsnaam)) writer.Write (feedData);
Eerst wordt een statische variabele genaamd _Config, van het type FeedRetreiverSection, gedeclareerd en een waarde toegekend door ConfigurationManager.GetSection () aan te roepen. De variabele statisch maken is een ontwerpkeuze. Door dit te doen, zouden alle leden van de klasse, ofwel instantie of statisch, toegang hebben tot de configuratie-instellingen zonder meerdere aanroepen te hoeven doen naar GetSection ().
Nadat u de sectie-afhandelaar met GetSection () hebt opgehaald, hebt u volledige toegang tot objecten die zijn gemaakt met uw handlerklassen. De eerste regel GetFeeds () is een voor elke lus die alle FeedElement-objecten doorzoekt die zich bevinden in het FeedElementCollection-object dat wordt geretourneerd door de eigenschap Feeds. Dit geeft u directe toegang tot die FeedElement-objecten - waardoor u eenvoudig toegang hebt tot de naam, URL en cache-instellingen van elke feed.
Tijdens elke iteratie van de lus maakt de methode een aanvraag met de URL-eigenschap van het FeedElement-object. Als het verzoek tot een succes leidt, worden de gegevens van de feed opgehaald en opgeslagen in de feedData-variabele. Vervolgens controleert de code de eigenschap Cache van het FeedElement-object om te bepalen of de feed wel of niet in de cache wordt geplaatst. Bij het cachen van de feed wordt een bestandsnaam geconstrueerd met behulp van de eigenschap Name van het FeedElement-object en de huidige datum en tijd. Vervolgens maakt een StreamWriter-object het bestand en schrijft de feedgegevens ernaar toe.
Zoals je kunt zien, is het gebruik van de handlersklassen in de configuratiesectie de sleutel om aangepaste instellingen op te halen en te gebruiken die zich bevinden in web.config. Het vereist zeker meer tijd en moeite van je, maar het maakt je applicatie of component zeker gemakkelijker om te configureren voor jezelf en andere ontwikkelaars.
Wist u dat we een .NET-categorie hebben op CodeCanyon. Als u een bekwame .NET-ontwikkelaar bent, waarom verkoopt u uw scripts / componenten / besturingselementen dan niet als auteur en verdient u 40-70% van elke verkoop?