Microsofts Ajax (Atlas) steht als RC zum Download bereit

Auch wenn ich bis jetzt das Thema Ajax hier wohl mehr stiefmütterlich behandelt habe, habe ich dieses immer im Fokus. Das von Microsoft entwickelte Ajax-Framework steht nun als RC zur Verfügung und kann hier runtergeladen weden. Jetzt kann man also über einen ernsthaften Einsatz nachdenken und ich werde das Thema nun endlich angehen.

DotNetNuke und entfernen von Profilproperties

Für einen Bekannten habe ich eine DotNetNukeinstallation (4.3.6) aufgesetzt und ihn ein wenig damit spielen lassen. Dabei hat er sich auch ein wenig mit den Profileigenschaften eines Users beschäftigt und diese Modifiziert. Das finde ich doch schon sehr gut und hätte ich mir eigentlich von Anfang an gewünscht .. Da sein Portal lediglich den deutschsprachigen Raum anspricht hat er einfach die Eigenschaft TimeZone gelöscht. Leider findet das DotNetNuke gar nicht witzig und normale Anwender konnten sich ab diesem Zeitpunkt nicht mehr anmelden. Einige Komponenten benötigen diese Profileigenschaft und es kracht ganz schön böse, falls diese nicht im Profil enthalten ist. Also: Vorsicht beim Löschen von Profileigenschaften - lieber ausblenden:)

Visual Studio 2003 und Windows Vista / Mein Tag

Schon länger wollte ich mein Notebook mal mit Windows Vista ausstatten doch irgendwie fehlte mir die Zeit. Nachdem dann letzte Nacht mein Notebook softwaretechnisch zu Bode ging, habe ich mich direkt entschlossen Windows Vista zu installieren. Im guten Glauben gesagt, getan und dachte alles wäre gut! Doch weit gefehlt... der erste Eindruck ist echt gut (ein wenig gewöhnungsbedürftig aber ich würde sagen: nicht schlecht).... Dann habe ich meine Visual Studio 2003 installiert,  was kein Problem war, nur das Starten war mir nicht vergönnt. Was soll das denn ????  Eigentlich bin ich davon ausgegangen, dass Microsoft die meist verwendeten Anwendungen (Visual Studio 2003 / MS-SQL Server 2000, usw) unterstützt ... diese Hoffnung ist aber gerade wie eine Seifenblase geplatzt! Normalerweise bin ich nicht contra-microsoft aber das ist ja wohl komplett am Thema vorbei! Sogar Visual Studio 2005 läuft nur nach einem ServicePack - und selbst dann gibt es wohl noch ein paar Probleme (mehr als unter XP). Super, toller Start in ein neues Betriebssystemzeitalter.... jetzt geht es wieder zum good, old Windowx XP - bis all meine Anwendung und Tools unter .NET 2.0 (3.0) laufen. An dieser Stelle sage ich : Vielen Dank für nichts! P.S.: Vielleicht hätten wir alle bei VB 6 bleiben sollen, denn das wird unter Vista supportet *mahlzeit*

DotNetNuke 3.3.6 / 4.3.6 steht zum Download bereit

Seit gestern gibt es die aktuelle Version von DotNetNuke auf der offiziellen Downloadseite zur Verfügung. Neben einigen Fehlern, Sicherheitslücken und Peformanceoptimierung wurde auch mal die Datensyncronisation verbessert. Genaue Informationen gibt es wie immer hier. Die Deutsche Übersetzung findet man bei http://www.deutschnetnuke.de/

MenuPilot: Open source context menu ASP.NET

Ein sehr schönes Context-Menü für ASP.net 2.0 habe ich soeben hier entdeckt. Dabei wird die Smart-Tag-Technologie (bekannt z.B. aus dem VS.NET 2005) verwendet. Ebenso gibt es unter http://www.daypilot.org/ einen Klasse ASP.NET Kalender im Look & Feel von Outlook 2003  .. 

Generierung von Barcode on the fly

Hier ein paar Blogbeträge zum Thema Barcodes und wie man diese unter DotNet erzeugen kann ohne 3rd-party Komponenten:Code 39 barcodes in C#ISBN to EAN-13 (C#)An ASP.NET .ashx HTTP handler for Code 39 barcode generation

HTML-Mails mit Bildern unter .Net erzeugen und versenden

Wer schon mal HTML-E-Mails verschickt hat kommt wohl kaum um das Problem herum, dass man auch Bilder dieser E-Mail hinzufügen möchte. Der erste und einfachste Weg ist, diese einfach auf einem Server abzulegen und dann auf diesen zu verweisen. Was ist aber wenn der Anwender keine Internetverbindung hat, der Server bzw. das Bild nicht mehr erreichbar ist? Dann sehen diese E-Mails meist sehr unschön aus. Gerade habe ich einen netten Artikel gefunden, der Beschreibt, wie man ein Bild als E-Mailanhang mitschickt und wie man die Verbindung zwischen Bild und Anhang herstellen kann. Hier einmal die Kurzfassung: <IMG height=68 src="cid:015024716@24012006-255A" width=140 align=top border=0> Die Sourceanweisung mit dem Wert "cid:015024716@24012006-255A" ist hier das interessante. Die RFC-Spezi. besagt das jeder E-Mailanhang eine eindeutige Id bekommt. Der benötigte Sourcecode zum Versand der E-Mail: 'Zu erst mal die Imports die benötigt werdenImports System.Net.MailImports System.Net.MimePublic Sub SendMail()Dim objMail As New MailMessageDim objSender As New MailAddress("absender@server.de")Dim objSmtpClient As New SmtpClient("smtp.server.de:8881")Dim objEmpfaenger As New MailAddress("empfaenger@server.de")objMail.To.Add(objEmpfaenger)objMail.From = objSenderobjMail.Subject = "Betreff der Mail"'Damit das ganze auch funktioniert muss man angeben,'das man die Mail im HTML-Format verschicken möchteobjMail.IsBodyHtml = True'So jetzt zum spannenden Teil, das Bild als Attachment anfügenDim objFootImage As New Attachment(Server.MapPath("LOGO.gif"), _MediaTypeNames.Image.Gif)objFootImage.ContentId = "01"objFootImage.ContentDisposition.Inline = TrueobjFootImage.TransferEncoding = TransferEncoding.Base64objMail.Attachments.Add(objFootImage)'Und so wird es anschließend verwendetobjMail.Body = "<img src=""cid:01"" border=0 height=68 width=140>"'Jetzt nurnoch die Mail verschicken und fertigobjSmtpClient.Send(objMail)End Sub Eine ausführliche Erklärung des ganzen gibt es auf dieser Seite

Bitte warten Sie in ASP.NET oder eine BusyBoxDotNet

Soeben habe ich eine sehr coole Komponente entdeckt, die es einem relativ einfach ermöglicht bei einer ASP.NET WebForm einen "Bitte warte Sie"-Dialog / BusyBox einzubelnden. Dieses ASP.NET Komponenten ist sehr anpassbar und scheint auf dem ersten Blick sogar schon in der Version 0.2.1 sehr brauchen zu sein. Das Opensource Projekt heißt "BusyBoxDotNet" und ist hier zu finden. Mal schauen wie sich die Komponente unter DotNetNuke verhält und ob man diese für eine Modulentwicklung einsetzen kann. Die Komponente ist nur für ASP.NET 2.0 verfügbar ...

XML-Editor

Mittlerweile gibt es viele XML-Editoren jetzt gibt es einen XML-Notepad :) Das XML Team von Microsoft hat eine .NET 2.0 Anwendung released mit der man XML Documents bearbeiten kann, XSL supported, XML Schema Validierung und sogar ein XML Diff Tool... zu guter letzt gibt es sogar intellisense. Auch bei großen Dokumente ist die Performance der Anwendung gut und im Vergleich zu vielen anderen Editoren wirklich mal zu gebrauchen. Den Download gibt es hier. Voraussetzung für das 2XML-Notepad" ist das .NET Framework 2.0. Der erste Eindruck sieht echt gut aus, werde das jetzt mal in der Praxis vermehrt einsetzen.

Cool (und kostenlos) Threading .NET 2.0 E-Book

Ich habe gerade eine coole Seite über Threading in .NET 2.0 gefunden, die auch viele Beispiele in C# bietet. http://www.albahari.com/threading/ Zudem gibt es (derzeit links unten) einen PDF, das nun auf meinem "muss ich unbedingt mal komplett Lesen" Stappel liegt ;-)

Phalanger 2.0 oder wie aus php msil code erzeugt....

Auf CodePlex wird von Microsoft ein Projekt mit dem Namen Phalanger gehostet. Phalager soll einen PHP-Compiler anzubieten, der es ermöglicht, PHP-Skripts ohne Modifikation auf .NET zu kompilieren. Dabei erzeugt der Compilier aus PHP-Skipts MSIL (Microsoft Intermediate Language). Ausprobiert habe ich es selber noch nicht, allerdings finde ich den Ansatz sehr interessant! Hier der direkte Link zum Projekt auf CodePlex

Mal wieder eine coole Komponente: Outlook 2003 Style Sidebar

Gerade habe ich auf GotDotNet mal wieder eine wirklich coole Komponente gefunden, mit der man die Sidebar von Outlook 2003 abbilden kann. Zu finden gibt es dieses .NET Komponenten - die übrigens in C# implementiert wurde - inkl. dem kompletten Sourcecode und einer Beispielanwendung, wie man die Komponente einsetzt, genau hier (klickst Du).

Windows Form Textbox und Strg-A bzw. Ctrl-A

Eigentlich bin ich von den Controls des .NET Frameworks 2.0 sehr zufrieden und der Umfang der enthaltenen Controls ist durchaus brauchbar. Aber gerade bin ich doch ein wenig entäuscht, da es die Jungs wohl nicht geschafft, übersehen bzw. nicht an eine sehr simple doch oft gebraucht Funktionalität zu denken. Ich habe eine Windowsforms-Anwendung auf der sich ein Multiline-Textfeld befindet. Jeder (oder sagen wir lieber viele) Benutzer sind es gewohnt den gesamte Inhalt eines solchen Textfeldes mit Strg-A zu markieren... doch was ist das? Nichts rührt sich, nichts wird markiert :( Nach einer recherche im Web musste ich wohl feststellen, dass ich nicht zu blöd bin, sondern dieses Problem wohl auch bei anderen existiert. Also beleibt einem nichts übrig als diese Enterprise-Funktionalität selber zu implementieren... das würde dann so aussehen: if ( (e.Control) && (e.KeyCode==Keys.A)){this.myTextbox.SelectAll();} Mahlzeit!

Nur eine Instanz einer Anwendung starten / zulassen

Manchmal ist erwünscht, dass der Benutzer nur eine Instanze der Anwendung starten kann. Hier ein Code-Beispiel wie man dieses Verhalten über ein Mutex erreichen kann: [STAThread]static void Main() {Application.EnableVisualStyles();Application.DoEvents();// ensure one instance runningif(!MainForm.InstanceExists) {Application.Run(new MainForm());}}static Mutex mutex;static string AppGuid = "4B3DF7C2-1BD3-7d54-AFF0-A3D4656C5EDH";static bool InstanceExists {get {bool notExists;mutex = new Mutex( false, "Local\\" + AppGuid, out notExists ); return !notExists;}} Durch die Verwendung einer Guid wird hier die "Einmaligkeit" gewährleistet. Sollte die Anwendung auf einem Terminalserver laufen dann muss "Local\\" gegen "Global\\" ersetzt werden....  

In einem BackgroundWorker einen Treeview aufbauen / populate

In .NET 2.0 ist das Arbeiten mit Threads dank des Backgroundworkers deutlich einfacher geworden. Heute Abend habe ich mich mal damit beschäftigt in einem Backgroundworker einen Treeview zu füllen. Der Zugriff auf ein Control in der Methode DoWork() ist nämlich nicht möglich, aber es gibt einen Trick, dieses zu lösen. Zunächst einmal die Basics um einen Backgroundworker bereitzustellen: this.backgroundworker = new BackgroundWorker();this.backgroundworker.WorkerReportsProgress = true;this.backgroundworker.DoWork += new DoWorkEventHandler(backgroundworker_DoWork);this.backgroundworker.ProgressChanged += new ProgressChangedEventHandler(backgroundworker_ProgressChanged);this.backgroundworker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(backgroundworker_RunWorkerCompleted); Wichtig dabei ist lediglich das Event ProgressChanged zu implementieren und die Property WorkerReportsProgress auf "true" zu setzen. Bis hier noch nicht wirklich aufregend....auch der Auruf mit this.backgroundworker.RunWorkerAsync(); ist wie gewohnt. In der Methode DoWork() kommt dann aber der Trick... void backgroundworker_DoWork(object sender, DoWorkEventArgs e){   TreeNode treenode= new TreeNode();    treenode.Text = 'name';   this.backgroundworker.ReportProgress(0, treenode);} Hier jetzt einfach mal so viel Vorstellungskraft aufbringen als würde DoWork() eine Schleife, Datenbankabfrage oder ähnliches durchführen, die viel Zeit in Anspruch nimmt. Die Möglichkeit eine Fortschritt zu Reporten kann man nun nutzen um ein Object an eine Form weiterzugeben. Die Implementierung der Methode/Event ProgessChanged könnte dann so aussehen: void backgroundworker_ProgressChanged(object sender, ProgressChangedEventArgs e){this.tvNavigator.BeginUpdate();this.tvNavigator.Nodes.Clear();this.tvNavigator.Nodes.Add((TreeNode)e.UserState);this.tvNavigator.EndUpdate();} Mit diesem Trick ist es nun möglich einen TreeView asyncron zu füllen....

Christian Weyer erklärt WCF

Eine wirklich sehr coole Vorstellung der WCF (Windows Communication Foundation) gibt es derzeit als Folge von dotnetPro-TV. Zusammen mit Ralf Westphal gibt Christian Weyer einen super Überblick für Einsteiger und Neulinge in diesem Bereich. Derzeit gibt es das Video sogar für die Öffentlichkeit zugänglich auf der Seite von DotNetPro, der Link zum Video ist in der orangefarbenen Kästchen. Viel Spaß :)

testing regular expressions online

Wer mal "eben" ein Regex-Pattern erstellen möchte und dieses auch direkt testen will, kann ein kleines Online-Tool dafür nutzen. Hier der Link

Timezones in DotNet: GMT in PST (Pacific Standard Time) konvertieren

Ich kann es ja kaum glauben aber bei dem mächtigen Framework von .Net wird es echt kompliziert eine DateTime Wert von GMT in PST zu konvertieren. Habe gerade ein paar lustige Stunden damit verbraucht eine dieses einigermaßen sauber zu implementieren und hier meine Lösung: Basis für meine Lösung ist eine Klasse von Clemens Vasters und seiner Blogengine dasblog.net. Dort gibt es im Projekt "newtelligence.DasBlog.Util.csproj" die Klasse "TimeZones.cs". Die nötigen Informationen für eine Konvertierung wird hier allerdings in einer XML Datei gespeichert. Da ich derzeit allerdings nur eine konvertierung nach PST brauch habe ich die XML Datei ignoriert und setze die Daten manuell in einer Klasse.     /// <summary>    /// Liefert verschiedne Zeiten auf der Welt zurücl    /// </summary>    public class TimeZoneConverter    {        /// <summary>        /// (GMT-08:00) Pacific Time (US &amp; Canada); Tijuana        /// Pacific Daylight Time        /// </summary>        /// <returns>DateTime of Pacific Daylight Time</returns>        public static DateTime GetCurrentPST()        {            return DateTime2PST(DateTime.Now) ;        }        /// <summary>        /// (GMT-08:00) Pacific Time (US &amp; Canada); Tijuana        /// Pacific Daylight Time        /// </summary>        /// <returns>DateTime of Pacific Daylight Time</returns>        public static DateTime DateTime2PST(DateTime dtDate)        {            WindowsTZI pstTZI = new WindowsTZI();            pstTZI.bias = 480;            pstTZI.daylightBias = -60;            pstTZI.standardBias = 0;                        WindowsSystemTime standardDate = new WindowsSystemTime();            standardDate.year = 0;            standardDate.month = 10;            standardDate.day = 5;            standardDate.dayOfWeek = 0;            standardDate.hour = 2;            standardDate.minute = 0;            standardDate.second = 0;            standardDate.milliseconds = 0;            WindowsSystemTime daylightDate = new WindowsSystemTime();            daylightDate.year = 0;            daylightDate.month = 4;            daylightDate.day = 1;            daylightDate.dayOfWeek = 0;            daylightDate.hour = 2;            daylightDate.minute = 0;            daylightDate.second = 0;            daylightDate.milliseconds = 0;            pstTZI.standardDate = standardDate;            pstTZI.daylightDate = daylightDate;                                    WindowsTimeZone tz = new WindowsTimeZone();            tz.WinTZI = pstTZI;                        return tz.ToLocalTime ( dtDate.ToUniversalTime() ) ;        }        } Wer das ganze etwas dynamischer haben möchte schaut sich am beste die Klasse vom Clemens an ... Ich brauchte diese Funktion für die Google-Adwords-API, diese erwatet nämlich das Datum im PST Format.

Parameter aus einem Querystring entfernen.

Gerade habe ich einen interessanten Artikel gefunden der zeigt, wie man einen Parameter aus der Querystringauflistung entfernen kann. Public Sub RemoveQueryString(ByVal Req As HttpRequest, ByVal strKeyToDel As String, ByVal http_Context As HttpContext)Dim nvc As System.Collections.Specialized.NameValueCollection = New System.Collections.Specialized.NameValueCollection(Req.QueryString)Dim sPage As String = Req.ServerVariables("SERVER_NAME") & Req.ServerVariables("SCRIPT_NAME")nvc.Remove(strKeyToDel)Dim strNewURL As String = Req.PathDim sSeparator As String = "?"Dim sKey As StringFor Each sKey In nvcIf sKey <> Nothing ThenDim sValues As String() = nvc.GetValues(sKey)Dim sValue As StringFor Each sValue In sValuesIf sValue <> Nothing ThenstrNewURL &= sSeparatorstrNewURL &= sKey & "=" & sValuesSeparator = "&"End IfNextEnd IfNextIf nvc.Keys.Count < 1 ThenstrNewURL &= "?"End Ifhttp_Context.Current.RewritePath(strNewURL)End Sub Gefunden habe ich den Code unter http://www.codeproject.com

DNN (DotNetNuke) und Transaktionen

Eines meiner größten Probleme - oder sagen wir lieber Sorgen - war bisher, dass DNN keine Transaktionen unterstützt. Es gibt doch immer wieder mal Business-Cases wo man transaktionsicher Daten verarbeiten möchte. Ein typischens Beispiel wäre z.B. eine Online-Shop, wenn es um die Bestellung und gleichzeitige Zahlungsabwicklung geht. Da DotNetNuke in vermutlich in vielen Fällen auf einem Windows 2003 Server betrieben wird, ist die komplette Umgebung schon vorhanden um die Abläufe transaktionssicher zu gestalten. Das Stichwort ist hier "Services without Components". Der Begriff "Services without Components" steht für die Nutzung von COM+-Dienste in .NET-Anwendung ohne Registrierung als Serviced Component (COM+-Anwendung).Klassen: .ServiceConfig and System.EnterpriseServices.ServiceDomain Das folgende Beispiel zeigt eine ganz einfache Implementierung innerhalb einer Methode:                  //Hier wird mit einem Transaktionskontext gearbeitet,                //damit das Handling einfacher wird                ServiceConfig sc = new ServiceConfig();                sc.Transaction = TransactionOption.RequiresNew ;                ServiceDomain.Enter ( sc ) ;                try                {                    //mach was ....                    ContextUtil.SetComplete() ;                }                catch (Exception exc)                 {                    ContextUtil.SetAbort() ;                    throw exc ;                }                finally                {                    ServiceDomain.Leave();                }  

Architects Connection

Seit einigen Tagen existiert ein eigenes Informations-Portal für IT-Architekten (www.architectsconnection.de). Dort stehen sehr viele  architekturrelevanten Ressourcen – Fachartikel, Kommentare, Web- und PodCasts, Vorträge, Event-Termine u.v.m  zur Verfügung und soll bei den täglichen Aufgaben helfen und unterstützen. Der Gedanke des Portals ist "Service von Architekten für Architekten". Schauen wir mal wie sich dieses Microsoft Portal entwickelt. 

Einstellungen einer Windows Anwendung speichern unter .NET 2.0

Die ersten Erfahrungen mit dem .NET Framework 2.0 waren sehr erfreulich. Als eines der ersten Features habe ich mir die "Anwendungseinstellungen" vorgenommen und war total begeistert. Endlich wird einem diese lästige Aufgabe komplett abgenommen auch das Binden von Einstellunge auf Eigenschaften eines Controls finde ich super! Nur noch ein Load() und Save() in den Code einbauen und fertig. So dachte ich zumindest aber der Frust kam relativ schnell: Das Speichern von benutzerabhängigen Einstellungen wird unter c:\Dokumente und Einstellungen\benutzername\.... vorgenommen. So weit kein Problem nur das die Versionsnummer mit im Pfad stehen muss finde ich richtig übel. So bald sich die Versionnummer ändert ist es mit den alten Einstellungen essig ... es gibt zwar eine Upgrade() Methode aber bei der Verwendung von SettingKey funktioniert das nicht mehr :( Also habe ich versucht den Pfad anzupassen und habe gegoogelt .. siehe da: Es geht nicht .... super gemacht, toll durchdacht aber dann trotzdem leider auf den letzten Metern versaut. Immerhin hat man die Möglichkeit einen eigenenen Provider zu schreiben, um die Einstellungen abzuspeichern. Das wiederum ist klasse gelöst und mehr als sinnvoll! Nun hier ist eine Provider, der die Einstellungen im XML-Format unter dem Anwendungsverzeichnis speichert: using System;using System.Collections;using System.Collections.Generic;using System.Text;using System.Configuration;using System.Windows.Forms;using System.Xml;using System.Collections.Specialized;using Microsoft.Win32;namespace GaliNeo.Framework.GaliNeoSettings{class GaliNeoSettingsProvider : SettingsProvider{XmlDocument doc = null;XmlNode root = null;XmlNode userSettings = null;XmlNode appSettings = null;public GaliNeoSettingsProvider(){doc = new XmlDocument();LoadSettings();}public override string ApplicationName{get { return Application.ProductName; }set { }}public override void Initialize(string name, NameValueCollection col){base.Initialize(this.ApplicationName, col);}public override void SetPropertyValues(SettingsContext context, SettingsPropertyValueCollection propvals){foreach (SettingsPropertyValue propval in propvals){SettingsProperty prop = propval.Property;setValue(prop, propval, context);}this.WriteSettings();}public override SettingsPropertyValueCollection GetPropertyValues(SettingsContext context, SettingsPropertyCollection props){// Create new collection of valuesSettingsPropertyValueCollection values = new SettingsPropertyValueCollection();string sectionName = this.GetSectionName(context);string settingKey = (string)context["SettingsKey"];// Iterate through the settings to be retrievedforeach (SettingsProperty setting in props){SettingsPropertyValue value = new SettingsPropertyValue(setting);value.IsDirty = false;value.SerializedValue = getValue(setting, context );values.Add(value);}return values;}private XmlNode SerializeToXmlElement(SettingsProperty setting, SettingsPropertyValue value){XmlElement element = doc.CreateElement("value");string text1 = value.SerializedValue as string;if ((text1 == null) && (setting.SerializeAs == SettingsSerializeAs.Binary)){byte[] buffer1 = value.SerializedValue as byte[];if (buffer1 != null){text1 = Convert.ToBase64String(buffer1);}}if (text1 == null){text1 = string.Empty;}if (setting.SerializeAs == SettingsSerializeAs.String){//text1 = this.Escaper.Escape(text1);}element.InnerXml = text1;XmlNode node1 = null;foreach (XmlNode node2 in element.ChildNodes){if (node2.NodeType == XmlNodeType.XmlDeclaration){node1 = node2;break;}}if (node1 != null){element.RemoveChild(node1);}return element;}private string GetSectionName(SettingsContext context){string groupName = (string)context["GroupName"];string settingKey = (string)context["SettingsKey"];string section = groupName;if (!string.IsNullOrEmpty(settingKey)){object[] arrName = new object[] { section, settingKey };section = string.Format("{0}.{1}", arrName);}return XmlConvert.EncodeLocalName(section);}#region DANprivate string getXPathQueryProperty(SettingsProperty setting, SettingsContext context){string xPathQuery = getXPathQuerySection(setting, context);if (setting.Name != ""){xPathQuery += "/" + setting.Name;} //if (propName != "")return xPathQuery;}private string getXPathQuerySection(SettingsProperty setting, SettingsContext context){string xPathQueryGroup = doc.DocumentElement.LocalName ;if (this.IsUserScoped(setting)){xPathQueryGroup += "/userSettings";}else{xPathQueryGroup += "/appSettings";}xPathQueryGroup += "/" + GetSectionName(context);return xPathQueryGroup;}private void CreatePropNode(SettingsProperty setting, SettingsPropertyValue value, SettingsContext context){string xPathQuery = getXPathQuerySection(setting, context);XmlNode groupNode = doc.SelectSingleNode(xPathQuery);if (groupNode == null){groupNode = doc.CreateElement(GetSectionName(context));if (this.IsUserScoped(setting)){userSettings.AppendChild(groupNode);}else{appSettings.AppendChild(groupNode);}} //if (node == null)XmlNode nodeProp = doc.CreateElement(setting.Name);nodeProp.AppendChild (this.SerializeToXmlElement(setting,value) );groupNode.AppendChild(nodeProp);}private void setValue(SettingsProperty setting, SettingsPropertyValue value, SettingsContext context) //string propName, string groupName, object value, object defaultvalue){string xPathQuery = getXPathQueryProperty(setting,context);XmlNode node = doc.SelectSingleNode(xPathQuery);if (node != null){XmlNode valueNode = SerializeToXmlElement(setting, value);node.RemoveAll();node.AppendChild(valueNode);}else{CreatePropNode(setting, value, context);} //if (node != null)}private object getValue(SettingsProperty setting, SettingsContext context){string xPathQuery = getXPathQueryProperty(setting, context);XmlNode node = doc.SelectSingleNode(xPathQuery + "/value");if (node != null){return node.InnerXml;}else if (setting.DefaultValue != null){return setting.DefaultValue;}else{return null;}}// Helper method: walks the "attribute bag" for a given property// to determine if it is user-scoped or not.// Note that this provider does not enforce other rules, such as // - unknown attributes// - improper attribute combinations (e.g. both user and app - this implementation// would say true for user-scoped regardless of existence of app-scoped)private bool IsUserScoped(SettingsProperty prop){foreach (DictionaryEntry d in prop.Attributes){Attribute a = (Attribute)d.Value;if (a.GetType() == typeof(UserScopedSettingAttribute))return true;}return false;}#endregionprivate void LoadSettings(){string configFile = getPath() + "user.config";if (System.IO.File.Exists(configFile) ){doc.Load(configFile);root = doc.DocumentElement;userSettings = doc.DocumentElement.SelectSingleNode("./userSettings");appSettings = doc.DocumentElement.SelectSingleNode("./appSettings"); ;}else{try{root = doc.CreateElement("configuration");userSettings = doc.CreateElement("userSettings");root.AppendChild(userSettings);appSettings = doc.CreateElement("appSettings");root.AppendChild(appSettings);doc.AppendChild(root);}catch {}}}private string getPath(){return Application.StartupPath + @"\App_Data\" ;}private void WriteSettings(){if (!( System.IO.Directory.Exists(getPath()))){System.IO.Directory.CreateDirectory(getPath());}string configFile = getPath() + "user.config";doc.Save(configFile);}}} Nun das ist noch nicht 100% best practice Entwicklung (musste schnell gehen) aber es funktioniert ....:)    

Neue Themen .NET 2.0, Winform und Google-API

Ab Heute wird die Thematik dieses Blogs ein wenig erweitert. Nun ist es endlich so weit und di Entwicklung mit .NET 2.0 geht bei mir endlich los. In der nächsten Zeit wird der Schwerpunkt mehr auf .NET Winforms und der Google-API liegen. Aber keine Angst ich werde DotNetNuke nicht wirklich vernachlässigen.