code it

Martins Tech Blog

Fehlermeldung beim Öffnen von Word- und Excel-Dokumenten aus Outlook

Gelegentlich bekommt man ja auch mal Office-Dokumente per Mail geschickt. Und früher funktionierte es mal, dass man diese Dokumente auch direkt aus der Mail in Outlook per Doppelklick öffnen konnte - wie gesagt früher. Aktuell ist es bei mir so, dass ich dann von den Zielanwendungen - also Word 2010 oder Excel 2010 mit diversen Fehlermeldungen beglückt werde.

Excel meldet: "Die Datei ist beschädigt und kann nicht geöffnet werden.".

Word meint: "Fehler beim Öffnen der Datei in Word."

Und PowerPoint meldet gleich: "Die Anwendung konnte nicht korrekt gestartet werden (0x000022)." und bietet mir an, die Präsentation zu reparieren.

Ursache dafür ist das Sicherheitscenter (englisch Trust Center). Dieses findet man unter Datei -> Sicherheitscenter im jeweiligen Programm. Unter dem Menüpunkt "Geschützte Ansicht" gibt es die Option "Geschützte Ansicht für Outlook Anlagen aktivieren".

Deaktiviert man diese Option, so kann man die Dateien auch wieder aus Outlook heraus öffnen.

Verwirrendes NotFound

Das Szenario ist recht schnell umrissen: Abstrakt gesehen gibt es einen Webservice: Unter einer Url ist ein Endpunkt registriert, über den per Get-Parameter gesteuert die Daten gefiltert abgerufen werden können. Auf der Client-Seite gibt es eine Windows Phone 7 Anwendung, die mit Hilfe eines asynchronen WebRequest diese Url abfragt und die in der Response enthaltenen Daten deserialisiert und der Anwendung bereitstellt - also alles recht trivial.

Etwas überrascht war ich, als ich bei der Ausführung im Callback beim Aufruf von EndGetResponse dann eine WebException mit der Meldung "NotFound" bekam. Auch die Details der WebException waren nicht aussagekräftiger.

 

Beim Zugriff auf entfernte Inhalte bedeutet NotFound ja eigentlich, dass die angeforderte Ressource nicht da ist - eine Datei, ein Endpunkt oder was auch immer. Meist lässt sich dann auch mit einer Überwachung der http(s)-Anforderungen überprüfen, ob der Server irgendwo einen Statuscode 404 geliefert hat.

Genau das war aber bei mir nicht der Fall. Im Browser war die Url problemlos aufrufbar und lieferte Daten und die von mir an den WebRequest übergebenen Credentials waren auch die gleichen wie die, die ich im Browser eingegeben hatte. Auch die Überwachung des Traffics (wenn ich die Seite im Browser aufrief) zeigte nie einen Http-Statuscode im 400er oder 500er Bereich an.

Was war nun eigentlich das Problem? Ganz einfach: Ein selbst ausgestelltes Zertifikat. Was man im Browser bei bekannten Seiten recht schnell wegklickt, machte hier nun ein so großes Problem, dass der Zugriff ganz unterbunden wurde.

 

Da das Windows Phone 7 auch über keinen Certificate Store verfügt, im man mal eben Zertifikate ablegen kann und so Vertrauensstellungen definiert, war in diesem Fall der einfachere Weg, wieder auf http umzustellen.

Gewünscht hätte ich mir von der API eine aussagekräftigere Fehlermeldung, damit man gleich in der richtigen Richtung suchen kann. Jetzt weiß ich, dass NotFound bedeutet, dass irgend etwas schief gegangen ist.

.NET Open Space - ein Rückblick

#netos - wer an diesem Wochenende die Tweets in der Leipziger Twitterszene verfolgt hat, der wird häufiger über diesen Hashtag gestolpert sein. Grund dafür war ein Event, der mittlerweile seinen festen Platz in der deutschen .NET-Community gefunden hat: der .NET Open Space. Jedes Jahr pilgern knapp 150 .NET-Entwickler und -Interessierte nach Leipzig, um sich hier mit Gleichgesinnten auszutauschen. Auch ich war dabei und möchte meine Eindrücke zum Besten geben. Ich war schon im letzten Jahr mit dabei und natürlich ist man dann versucht, auch immer einen Vergleich zu ziehen.

Im letzen Jahr fand der .NET Open Space in der Villa Ida statt. Und da der frühe Vogel ja bekanntlich den Wurm fängt, buchte ich mir auch ein Hotelzimmer in der Nähe. Etwas überrascht wurde ich dann, als bekannt wurde, dass es in diesem Jahr einen anderen Veranstaltungsort geben würde. Da wir ja alle agil sind, ist auch das natürlich kein Problem - schnell umgebucht und alles in Butter - einzig der Hotelbetreiber wird sich etwas gewundert haben, denn wie ich erfahren habe, war ich mit meiner Stornierung nicht allein.

Beginn der Veranstaltung war dann Samstag um 10:00 Uhr. Einige der Teilnehmer reisten schon am Freitag an, um an der Kennenlern-Party teilzunehmen oder erholt am Samstag starten zu können. Bei der Party war ich leider nicht dabei, da ich einer derjenigen war, die erst am Samstag dazustießen.

Nach und nach trafen alle ein und schnell sah man auch bekannte Gesichter und der Smalltak begann, den nur ein Pfiff unterbrechen konnte: Es war an der Zeit, die Agenda zu füllen. Jeder, der wollte konnte ein Thema vorschlagen und viele haben auch diese Gelegenheit genutzt, das zu tun. Gefühlt war die Themenfindung in diesem Jahr etwas träger und unorganisierter als im letzten Jahr, aber es ist halt schließlich eine Unkonferenz und warum nicht auch das kreative Chaos nutzen.

Was für Themen kamen da zusammen? Natürlich durften aktuelle Buzzwords wie Agilität, *DD und Windows Phone 7 nicht fehlen und so kam es zu einer bunten Themen-Mischung über Methodik, Architektur und Softskills. Auch wenn letzteres auf den ersten Blick für einige nicht zu einer Entwicklerkonferenz gehören mag, so ist es eben auch wichtig Fragen zu klären wie "Wie bringe ich eigentlich meinen Kollegen bei, die Werte die ich habe auch zu vertreten." - und das ist eben nicht nur Methodik sondern auch der menschliche Faktor. Zusammengefasst waren die eher technisch geprägten Themen aber in der Überzahl: Was sind eigentlich Monaden? Wozu sind EBCs gut? Wann lohnt es sich, eine funktionale Programmiersprache wie F# zu verwenden? Wie mach ich sinnvollerweise Logging? Welche AddIns sind empfehlenswert? ... und so weiter und so fort. Auch ein Coding Dojo war wieder dabei, das aber nach meinem Empfinden in diesem Jahr besser lief, da gleich mehrere Gruppen gebildet wurden und so in einem kleineren Kreis intensiver gearbeitet werden konnte. Aber genug vom Fachlichen: Wer es selbst erleben möchte, der möge selbst an einem .NET Open Space teilnehmen und seine eigenen Erfahrungen sammeln - es lohnt sich.

Abseits der Diskussionen gab es aber auch noch das Abendessen am Samstag in der Schaubühne Lindenfels und dem Joseph Pub - mit klarer Präferenz für zweiteres meinerseits und ich glaube der ein oder andere sieht das ähnlich. Und auch die Mittagessen, die dieses Mal im Vergleich zum Vorjahr eher mit bekannte Gerichte aufwarteten, boten genug Raum dafür, sich auszutauschen und neue Leute kennenzulernen oder über andere Ansichten und Erfahrungen zu diskutieren.

Alles in allem ist mein Resümee ein postives. Ich habe es in keinem Fall bereut, dieses Wochenende in Leipzig verbracht zu haben. Egal ob Freak oder Quatschaffe - es hat Spaß gemacht mit euch zu diskutieren und dabei gewesen zu sein und man sieht sich beim nächsten Mal.

Build Messages in CodeActivities in Teambuild 2010

Wer in TFS 2008 eigene Build-Tasks geschrieben hat und dabei von der abstrakten Basisklasse Task abgeleitet hat, wird wissen,dass es recht einfach war, Meldungen ins Log zu schreiben. Die Klasse stellte ein Objekt Log zur Verfügung, das über die passenden Methoden verfügte.

In TFS 2010 ist die Workflow-Engine Grundlage des Teambuilds. Dieser ist auch weiterhin erweiterbar - nur wird nun nicht mehr von der Klasse Task, sondern von der Klasse CodeActivity geerbt. Nur leider bietet diese Klasse eben kein solches Log-Objekt mehr.

Abhilfe schafft hier der Microsoft.TeamFoundation.Build.Workflow.Activities-Namespace. Ist dieser über eine using-Direktive eingebunden, so stehen auf dem context-Objekt drei Extension-Methods zur Verfügung, die das Logging übernehmen können.

using System.Activities;
using Microsoft.TeamFoundation.Build.Workflow.Activities;

namespace CustomActivityLibrary
{
    public sealed class CodeActivity1 : CodeActivity
    {
        protected override void Execute(CodeActivityContext context)
        {
            context.TrackBuildMessage("this is a message");
            context.TrackBuildWarning("this is a warning");
            context.TrackBuildError("this is an error");
        }
    }
}

Mails versenden mit Outlook und Dynamics

Ein altbekanntes Problem, aber eines, das auch in Foren immer wieder gestellt wird ist "Wie kann ich Mails mit Outlook versenden?" - nach Möglichkeit unabhängig von der Outlook-Version des Anwenders.

Ein Weg unter vielen ist die Verwendung der Dynamic Language Runtime. Diese gibt es seit dem .NET Framework 4.0 und sie erlaubt einen Zugriff auf Typen, die in ihrer wirklichen Ausprägung erst zur Laufzeit fest stehen. Einen Überblick über die Grundzüge und die Möglichkeiten der DLR gibt es in der MSDN.

In der Praxis sieht das Ganze dann in etwa so aus:

private void ComposeEmail(string receipient, string subject, string body)
{
   const int olMailItem = 0;

   dynamic outlookApp = GetOutlookApplication();
   if (outlookApp == null)
   {
       MessageBox.Show("Outlook konnte nicht initialisiert werden.");
       return;
   }

   dynamic mailItem = outlookApp.CreateItem(olMailItem);
   mailItem.To = receipient;
   mailItem.Body = body;
   mailItem.Subject = subject;
   mailItem.Display();
   //mailItem.Send();
}

private dynamic GetOutlookApplication()
{
   // try to get an existing outlook instance
   try
   {
       dynamic outlookApp = System.Runtime.InteropServices.Marshal.GetActiveObject("Outlook.Application");
       return outlookApp;
   }
   catch (System.Runtime.InteropServices.COMException)
   {
   }

   // try to get an existing outlook instance
   try
   {
       dynamic outlookApp = System.Activator.CreateInstance(
          System.Type.GetTypeFromProgID("Outlook.Application"));
       return outlookApp;
   }
   catch
   {
       return null;
   }
}

Die Funktion GetOutlookApplication versucht zunächst eine laufende Outlook-Instanz zu ermitteln. Schlägt das fehl wird eine neue Instanz geöffnet. Dabei wird das Objekt über den Registry-Eintrag "Outlook.Application" referenziert. Dies ist ein Verweis auf die jeweils aktuelle Outlook-Installation.

Die ermittelte Outlook-Instanz wird dann verwendet, um ein neues MailItem zu erzeugen. Im Beispiel wird das Item nur angezeigt, damit der Kunde es noch bearbeiten kann. Durch die Verwendung von Late Binding mit dem dynamic Schlüsselwort ist zur Entwicklungszeit irrelevant, welche Version der Kunde installiert hat. Die Überprüfung erfolgt erst zur Laufzeit. Wird dann auf eine Eigenschaft oder Methode zugegriffen, die es bei dem real vorliegenden Objekt nicht gibt, so wird ein RuntimeException geworfen, die es zu behandeln gilt.

PDC Public Viewing bei der .NET Usergroup Dresden am 28.10.2010

Am 28. und 29. Oktober veranstaltet Microsoft in Redmond die Professional Developers Converence. Zur Eröffnung gibt es deutschlandweit in vielen Usergroups ein Public Viewing der Keynote. Auch wir sind mit dabei und möchten gemeinsam mit euch die Gelegenheit nutzen und diesen Event in das Oktober-Treffen der Usergroup einbetten. In lockerer Runde können wir so fachsimpeln, ein paar interessante Anregungen mitnehmen, Ankündigungen diskutieren und neue Kontakte knüpfen.

Nach der Keynote gibt es auch noch eine Verlosung. Zu gewinnen gibt es die folgenden Produkte:
  • 1x Visual Studio 2010 Professional (NFR)
  • 1x Windows 7 Ultimate (NFR)
  • 1x Competition Pro C64 USB-Joystick und eine umfangreiche Spielesammlung
Alle angemeldeten Teilnehmer, erhalten noch einen USB-Lanyard.

Die Keynote beginnt um 18:00 Uhr. Deshalb treffen wir uns dieses Mal schon um 17:45 Uhr bei der T-Systems MMS. Die Teilnehmerliste befindet sich wie gewohnt im Xing.

Ich freue mich schon auf euer Erscheinen und vielleicht können wir ja auch das ein oder andere neue Gesicht in unserer Runde begrüßen.