Microsoft SQL Server 2008 R2 – Das Entwicklerbuch

Georg Urban

Jörg Neumann

Klaus Löffelmann

Alexander Köller

Published by Microsoft Press Deutschland

Für meine Ursel, für die ich immer da sein werde!

—Georg Urban

Für Adriana, aus so vielen Gründen, die selbst dieses Buch doppelt so dick werden lassen würden ...

—Klaus Löffelmann

Für Brina, alleine schaffen wir es nicht ...

—Alexander Köller

A Note Regarding Supplemental Files

Supplemental files and examples for this book can be found at http://examples.oreilly.com/9783866455146/. Please use a standard desktop web browser to access these files, as they may not be accessible from all ereader devices.

All code files or examples referenced in the book will be available online. For physical books that ship with an accompanying disc, whenever possible, we’ve posted all CD/DVD content. Note that while we provide as much of the media content as we are able via free download, we are sometimes limited by licensing restrictions. Please direct any questions or concerns to booktech@oreilly.com.

Einleitung

Das zweite SQL Server Entwicklerbuch ist endlich fertig! Es ist noch umfangreicher geworden als das erste. Und wir sind stolz drauf! SQL Server 2008 R2 hat gegenüber der Version 2005 noch einmal einen mächtigen Sprung getan. Deswegen ist das »Entwicklerbuch« auch nicht einfach nur ein Update geworden, sondern es musste in großen Teilen neu geschrieben oder gründlich überarbeitet werden. An unser altes Buch einfach ein Kapitel »Neuigkeiten« anzuhängen, wäre dem tollen Produkt SQL Server 2008 R2 einfach nicht gerecht geworden.

Damit unsere Inhalte überhaupt noch zwischen zwei Buchdeckel passen, haben wir einige Themen ausgelagert,[1] damit wir uns vertieft um die eigentliche Entwicklung kümmern konnten. Wir stärken unsere »Kernkompetenzen«!

Was Sie hier in den fünf Buchteilen finden, ist ein großer Teil unserer Kenntnisse und Erfahrungen in der Arbeit mit dem SQL Server 2008 R2. Wenn es nach uns gegangen wäre, dann hätte dieses Buch noch mindestens 1000 Seiten mehr besitzen können, aber das wäre ja auch irgendwie unpraktisch – oder? So haben wir uns bemüht, die Inhalte zu komprimieren und die Kernpunkte knapp und präzise rüber zu bringen, aber auch nichts auszulassen, was Ihnen in der täglichen Arbeit helfen kann.

Dieses Buch gehört vermutlich nicht zu denjenigen, die Sie mit einem guten Glas Wein in der Hand vor dem offenen Kamin lesen (aber warum eigentlich nicht?). Am sinnvollsten erscheint es uns, wenn Sie unser Buch an Ihrem Arbeitsplatz nutzen. Wir würden uns wünschen, dass Sie dieses Buch neben Ihre Tastatur legen, damit Sie alle Beispiele sofort ausprobieren können und das Buch Ihnen als tägliche Referenz bei Ihrer Entwicklertätigkeit dienen kann (klar – wir ahnen, dass Sie dieses Buch nicht von vorne bis hinten lesen werden. Ist schon in Ordnung so!). Apropos Beispiele: Es sind über tausend Codebeispiele geworden! Wir finden, dass sich das sehen lassen kann.

Viele Entwickler – das wissen wir aus eigener Erfahrung – lesen Bücher zwischendurch in der S-Bahn, auf Flughäfen, abends im Hotelzimmer. Der Autor dieser Einleitung liest EDV-Bücher am liebsten in der Badewanne. Zugegeben: Dafür ist unser »Entwicklerbuch« mit seinen zweieinhalb Kilogramm nicht so gut geeignet. Aber überall sonst sollten Sie es nutzen können: Durch die Erklärung der Quellcode-Beispiele, durch Grafiken und Screenshots sollen Sie in die Lage versetzt werden, »im Kopf zu entwickeln«. Zurück vor Ihrem Rechner können Sie unsere Programmschnipsel sofort laufen lassen und kreativ abändern.

Wir haben zu unserem Buch »Microsoft SQL Server 2005 – Das Entwicklerbuch« sehr viel positive Resonanz erhalten. Wir würden uns freuen, wenn es diesmal wieder so wäre. Auf jeden Fall wünschen wir Ihnen aber sehr viel Freude beim Lesen und viel Erfolg mit Ihren SQL Server-Projekten!

Auch für dieses Buch gilt wieder: Wenn wir es nicht zufällig selbst geschrieben hätten – wir würden es uns kaufen!

[1] Beispielsweise wird es mit »Microsoft SQL Server Integration Services« ein komplettes Buch von unserem ehemaligen Autor Bernd Jungbluth zu genau diesem Thema geben.

Wer sind Sie (der Leser)?

Wenn Sie professionell mit dem SQL Server zu tun haben, dann ist das hier Ihr Buch! Natürlich geht es in erster Linie um das Entwickeln von Datenbankanwendungen, aber auch Administratoren, die sich mit den Konzepten und der Praxis der SQL Server-Programmierung beschäftigen möchten, sind hier gut aufgehoben. Viele der besprochenen Techniken und Hintergrundinformationen lassen sich auch für die Wartung von SQL Servern einsetzen und Themen wie Indizierung, Sicherheit, Abfrageoptimierung und Monitoring gehen auch »Alle« etwas an. In vielen Fällen lassen sich die Jobrollen des Entwicklers und des Administrators im Datenbankbereich auch gar nicht voneinander trennen. Das Implementieren einer »ordentlichen« SQL Server-Lösung besteht neben der Programmlogik häufig auch aus viel »Physik«.

Unser Buch ist auch sehr gut für »Umsteiger« von ORACLE oder DB2 geeignet und ebenso für Aufsteiger von »Access«, »MySQL« oder »PostgreSQL«.

Falls Sie sich als EDV-Trainer mit der Programmierung des SQL Servers beschäftigen: Hier finden Sie viele Anregungen und eine Menge fertiger Codebeispiele.

Auch als reinrassiger .NET-Programmierer, der in seinen Anwendungen den SQL Server einsetzt, ziehen Sie Nutzen aus diesem Buch. Was auf dem Server in der Transact-SQL oder .NET-Verarbeitung langsam abläuft, holen Sie mit dem schönsten C#-Client nicht mehr auf. Das Buch soll Sie inspirieren, sich mit der Funktionsweise des SQL Server und dessen nativer Programmiersprache T-SQL auseinander zu setzen. Damit können Sie Ihre Anwendungen wirklich schnell machen und Sie sparen Programmierarbeit in Ihren Komponenten oder Ihrer Client/Server-Anwendung.

Dieses Buch ist keine Einführung in die elementaren Grundlagen der Datenbankentwicklung. Sie sollten wissen, was eine relationale Datenbank ist und sich unter einer Normalform etwas vorstellen können. Es schadet auch nicht, wenn Sie schon Erfahrungen mit anderen Datenbanksystemen gesammelt haben. Andererseits setzen wir aber keinerlei Kenntnisse über SQL Server voraus. Wir beginnen bei Null. Sie können erwarten, dass Sie eine gründliche Einführung in die Entwicklung mit dem SQL Server 2008 R2 erhalten, bis hin zu fortgeschrittenen Implementierungs- und Optimierungstechniken.

Falls Sie vorhaben, sich für eine Microsoft Zertifizierung im Datenbankbereich zu qualifizieren (MCITP: Database Administrator oder Database Developer), dann bereitet Sie das Durcharbeiten dieses Buchs ergänzend auf die Prüfungen 70-432, 70-433 und 70-451 vor. Nähere Informationen zu dem Zertifizierungsangebot finden Sie unter http://www.microsoft.com/learning.

Wer sind wir (die Autoren)?

Unsere Namen sind Jörg Neumann, Klaus Löffelmann, Alexander Köller und Georg Urban. Wir alle arbeiten schon lange Jahre auf den Gebieten IT, Entwicklung und dem SQL Server.

Jörg Neumann beschäftigt sich ausführlich mit der Entwicklung von SQL Server-basierten Lösungen in .NET. Die Einführungen zu ADO.NET und dem clientseitigen Zugriff im Buchteil C stammen von ihm. Klaus Löffelmann, ein langjähriger Vorreiter auf dem Gebiet der Architekturen, hat sich intensiv mit den Themen LINQ und dem Entity Framework auseinandergesetzt und die entsprechenden Kapitel beigesteuert. Alexander Köller – als Experte für die Entwicklung mit .NET und XML-Technologien – hat sich um die exotischeren Themen „Service Broker“ und »Complex Event Processing« sowie um XML gekümmert. Georg Urban ist der »Servermann« im Team und hat die ersten beiden Buchteile und den Teil IV geschrieben. Außerdem stammen von ihm die Kapitel über die SQL Server Compact Edition sowie die Verarbeitung von Streaming-Daten und Geoinformationen.

Weitere sachdienliche Hinweise zu unseren Personen finden Sie im Anhang und auf der Website dieses Buchs.

Aufbau des Buchs

Aus der Erfahrung vieler Workshops, Trainings und anderer Buchprojekte heraus haben wir uns dazu entschlossen, dieses Buch vor dem Hintergrund eines eigenen durchgängigen und konkreten Szenarios zu schreiben. Dieser Weg ist steinig, dass können Sie uns glauben. Da unterscheidet sich der Entwurf einer Datenbank für ein Buchbeispiel, über das sich vier Leute die Köpfe heiß reden, nicht von einem »wirklichen« Projekt. Uns hat dieses Vorgehen jedenfalls geholfen, auf dem Boden zu bleiben und anstelle abstrakten Philosophierens die im Buch vorgestellten Technologien anhand konkreter Aufgabenstellungen zu demonstrieren. Wir hoffen, dass Ihnen der Hintergrund unserer Datenbankanwendung genau so dabei hilft, sich in den SQL Server 2008 R2 hinein zu denken.

Wir haben die Fülle des Materials in fünf Buchteile gegliedert, um Ihnen die Übersicht zu erleichtern. Zur besseren Orientierung folgt an dieser Stelle eine kurze Übersicht, was Sie in den einzelnen Teilen erwartet.

Teil A: SQL Server-Grundlagen

Der erste Teil des Buchs erledigt die notwendige Grundlagenarbeit für die restlichen Teile dieses Buchs. Falls Sie den SQL Server bis jetzt noch nicht gut kennen, werden Sie hier zunächst einmal mit dessen Möglichkeiten vertraut gemacht. Außerdem geht es um die SQL Server Architektur. Wenn Sie es eilig haben, dann können Sie dieses »Warming Up« zunächst einmal überschlagen und direkt die Kapitel lesen, die Sie am brennendsten interessieren. Es ist aber nicht ganz unwahrscheinlich, dass Sie hin und wieder zurückblättern werden, um das eine oder andere Konzept nachzulesen.

Ganz bewusst haben wir auf eine Einführung in den Entwurf relationaler Datenbanken verzichtet. Wir gehen davon aus, dass Sie sich damit auskennen. Es gibt Myriaden guter Bücher zu diesem Thema auf dem Markt, sodass wir an dieser Stelle Papier gespart haben. Worauf wir allerdings nicht verzichten konnten, ist eine kurze Erläuterung des Datenmodells unseres Arbeitsbeispiels – der netShop-Datenbank. Diese finden Sie in Kapitel vier, welches Sie als Referenz benutzen können, wenn Ihnen irgendetwas an den Codebeispielen der folgenden Buchteile seltsam vorkommt und Sie den Hintergrund der Beispielabfragen oder .NET-Routinen genauer verstehen möchten.

Teil B: Transact SQL & die Datenbankmaschine

Im zweiten Teil betreten Sie die klassische Welt der relationalen Datenbankprogrammierung. Dass dies der umfangreichste Teil unseres Buchs geworden ist, sollte Sie eigentlich nicht verwundern: Trotz der hervorragenden Möglichkeiten, die sich mit den XML- und .NET-Angeboten im SQL Server ergeben, bleibt der Kern des Datenzugriffs immer relational und SQL-basiert. Sicher wird es in der zukünftigen Weiterentwicklung des SQL Server so sein, dass Sie das weniger spüren – mit dem Entity Framework und LINQ stehen Ihnen Datenzugriffsebenen zur Verfügung, die eine Abstraktion von den Eigenarten eines Datenbankservers erlauben. Wenn es aber ans »Eingemachte« – um die maximale Performance – oder um die Verwendung neuer Serverfeatures geht, dann kommen Sie um die Programmierung in T-SQL nicht herum.

Wenn Sie in Ihrem »klassischen« clientseitigen Code Abfragen für den SQL Server formulieren möchten, egal ob Sie das direkt tun (zum Beispiel mittels eines Command-Objekts) oder verpackt in einem ADO.NET Data Adapter, dann ist es sowieso wichtig, T-SQL ganz genau kennen zu lernen.

Der zweite Buchteil behandelt die Sprachgrundlagen von T-SQL, geht intensiv auf einen effektiven Aufbau von Tabellen und Indizes ein, führt über die verschiedenen elementaren Programmierelemente bis hin zur Transaktionsverarbeitung und Optimierungen.

Teil C: Clients für den SQL Server entwickeln

Der dritte Teil des Buchs bietet zunächst einen schnellen Einstieg in die Entwicklung von Clients, die auf ADO.NET basieren. Es werden die verschiedenen Objekte und Verfahren vorgestellt, die Sie bei der Cliententwicklung einsetzen können. Über diese Grundlagen hinaus werden Sie mit vertiefenden Themen vertraut gemacht, wie der Transaktionsverarbeitung und der Datenzugriffsanalyse. Außerdem geht es um das naheliegende Thema der datenorientierten GUI-Programmierung.

In der zweiten Hälfte des dritten Teils geht es um die aktuellen Ansätze der Datenzugriffsprogrammierung in der .NET-Welt – natürlich immer vor dem Hintergrund der SQL Server-Plattform. Nach einer Einführung in das Thema LINQ (Language Integrated Queries) wird das Entity Framework vorgestellt. Das Entity Framework ist Microsofts objektrelationaler Layer für Cliententwickler. Der Einsatz des Entity Framework kann den Aufbau Ihrer Anwendungen deutlich vereinfachen und verbessern.

Den Abschluss des dritten Teils bildet ein Blick auf den SQL Server in der Compact Edition. Mit diesem lassen sich mobile Anwendungen und lose gekoppelte Clients bequem programmieren.

Teil D: Datenbankobjekte mit .NET entwickeln

Die Integration des .NET-Framework in den SQL Server, verbunden mit der Möglichkeit, die Datenbankobjekte, gespeicherte Prozeduren, Trigger, Funktionen, Aggregate und benutzerdefinierte Typen in einer .NET-Sprache zu programmieren, ist eine famose Erweiterung der Möglichkeiten für SQL Server-Entwickler. Im dritten Buchteil werden die Konzepte der Integration von CLR-Objekten in die relationale Programmierumgebung vorgestellt (SQLCLR) und deren Anwendung gezeigt.

Zum Abschluss gibt es einen Ausblick auf die administrative Programmierung des Servers mittels seines .NET-Objektmodells SMO (Server Management Objects).

Teil E: Beyond relational

Der SQL Server macht dem Entwickler eine Reihe von Angeboten in Form diverser Datentypen und Services, die auf den Technologien und Entwicklungsverfahren aufbauen, welche in den ersten vier Teilen des Buchs erläutert wurden.

Da bei der Entwicklung mittels dieser Angebote SQL oft eine eher untergeordnete Rolle spielt, haben wir den fünften Buchteil Teil V genannt. Dieser Begriff stammt ursprüglich aus dem Marketing Slang von Microsoft, beschreibt aber tatsächlich sehr gut, um was es geht. Es liegt uns sehr am Herzen, dass Sie als Entwickler diese erweiterten Möglichkeiten des SQL Server nicht übersehen, sondern sich damit vertraut machen, was der SQL Server für spezielle Anwendungsszenarien in petto hat.

Es geht unter anderem um die Verwaltung von großen Streaming-Daten, die in Datenbanken (eigentlich) nichts zu suchen haben; das Ablegen, Suchen und Manipulieren von Geodaten in einer SQL Server-Datenbank, sowie einen vereinfachten Ansatz für den Umgang mit hierarchischen Informationen.

Natürlich darf auch das Thema XML nicht fehlen, für das es in SQL Server einen eigenen Datentyp gibt und das Datenzugriffe mittels XPath und XQuery-Sprachkonstrukte erlaubt.

Zum Schluss des fünften Teils werden zwei sehr elaborierte Techniken vorgestellt: Der SQL Server Service Broker ist ein sehr performanter Service für die asynchrone Verarbeitung von Nachrichten. Ganz neu eingeführt wurde mit der Version 2008 R2 das Thema Complex Event Processing. Die StreamInsight-Technologie stellt eine Plattform für das Auswerten großer Ereignisströme in Echtzeit dar.

Schauen Sie sich den Teil V an, wenn Sie auf der Suche nach neuen Lösungen und Anregungen sind. Es könnte sich lohnen!

Die Begleit-CD

Die Begleit-CD enthält die Datenbanken, Projekte und Dateien, die Ihnen helfen werden, die Theorie sofort in die Praxis umzusetzen. Sicherlich ist der effektivste Weg, um mit Hilfe unseres Buchs die Entwicklung des SQL Server 2008 R2 in den Griff zu kriegen, das direkte Ausprobieren und Nachvollziehen des Quellcodes. Falls Sie dieses Buch als eBook erworben haben, können Sie die Begleitdateien unter www.microsoft-press.de/support.asp?s110=514 oder msp.oreilly.de/support/9783866455146/577 herunterladen.

Support

Wir haben selbstverständlich alles unternommen, um die Korrektheit dieses Buchs und seiner Begleit-CD zu gewährleisten. Microsoft Press bietet Kommentare und Korrekturen für seine Bücher im Web unter http://www.microsoft-press.de/support.asp an. Wenn Sie Kommentare, Fragen oder Ideen zu diesem Buch haben, senden Sie diese bitte per E-Mail an presscd@microsoft.com. Bitte beachten Sie, dass über diese Adressen kein Support für Microsoft-Produkte angeboten wird. Wenn Sie Hilfe zu Microsoft-Produkten benötigen, kontaktieren Sie bitte den Microsoft Online Support unter http://support.microsoft.com.

Über die Website zum Entwicklerbuch können Sie direkt mit uns Autoren Kontakt aufnehmen. Die URL der Website lautet: http://www.sqlentwicklerbuch.de.

Die Website zum Buch

Auf unserer Buch-Website finden Sie ebenfalls die aktuellen Updates – plus zusätzlicher Informationen rund um das »Entwicklerbuch«. Auf der Seite »Ask the Authors« gibt es ein Kontaktformular, mit dessen Hilfe Sie Fragen und Anregungen zu den einzelnen Themen des Buchs loswerden können. Wir würden uns freuen, von Ihnen zu hören!

So gerne wir auch alle Fragen zu SQL Server beantworten würden, leider reicht unsere Zeit nicht. Allgemeine Fragen werden Sie entweder direkt bei Microsoft los oder in den entsprechenden Newsgroups, Blogs und Communities. Auf der Seite »Ressourcen« bieten wir eine entsprechende Link-Sammlung an (das sind die Ressourcen, die wir bis jetzt kennen. Falls Sie einen Tipp haben: her damit!).

Danksagungen

Georg Urban dankt seinen hoch geschätzten Kollegen von ixto, LM IT AG und der Microsoft GmbH, die es ihm nachgesehen haben, dass er hin und wieder nach einer »Buchnacht« morgens noch etwas mehr Kaffee als sonst gebraucht hat. Er dankt besonders seiner Lebenspartnerin, seiner Familie und Freunden für Ihre Geduld und freut sich, dass sie ihn jetzt wieder häufiger sehen werden.

Alexander Köller dankt zunächst Georg für die Möglichkeit, wieder ein Teil des Ganzen zu sein. Außerdem meiner Familie für eure Geduld an so manchem Wochenende und Thomas Bonke für die Freiheiten, die ich bei meiner Projektplanung dafür bekommen habe.

Wir alle danken auch dieses Mal ganz herzlich unserem MS-Press-Projektleiter Thomas Braun-Wiesholler, dessen Geduld wir wieder auf eine große Probe gestellt haben: Thomas, das nächste Buch wird bestimmt pünktlich fertig! Wir haben auch schon wieder zu viele Seiten gefüllt – tut uns leid. Unsere Leser wird es aber (hoffentlich) freuen.

Zu guter Letzt gilt natürlich unser besonderer Dank unseren geduldigen und aufmerksamen Lektoren Uwe Thiemann und Thorsten Kansy für ihre Unterstützung!

Berlin, den 31.10.2010

Teil I. SQL Server-Grundlagen

In diesem Teil:

Kapitel 1

Kapitel 2

Kapitel 3

Kapitel 4

Kapitel 1. Szenarien für SQL Server-Entwickler

In diesem Kapitel:

„Klassische relationale Datenbanken“

„.NET Inside“

„Neue Programmierparadigmen in ADO.NET“

„XML in der Datenbank“

„Verteilte Daten“

„Datenanalyse und Darstellung“

„Immer Online: 24*7-Betrieb mit SQL Server“

„Desktop und mobile Anwendungen“

Dieses erste Kapitel verfolgt zwei wichtige Ziele: Es soll Ihnen einen Überblick über das »Objekt der Begierde« – SQL Server 2008 vermitteln und wir möchten Ihnen Lust darauf machen, den Server näher kennen zu lernen.

SQL Server 2008 hat mit einem klassischen Datenbankmanagementsystem (DBMS) vor allen Dingen die drei Buchstaben S, Q und L im Namen gemein. Ansonsten bietet er über das effektive Management von relationalen Datenbanken hinaus viele sinnvolle Angebote für Datenbankentwickler. Der Begriff einer Datenmanagementplattform, den Microsoft für diesen Server geprägt hat, ist daher mehr als zutreffend. Wenn Sie die Möglichkeiten kennen, dann können Sie viel eigenen Entwicklungsaufwand sparen und es bringt Sie sicher auf neue Ideen für Ihre Projekte. Anhand einiger Einsatzszenarien stellen wir einige der wichtigsten Highlights von SQL Server vor.

Klassische relationale Datenbanken

Microsofts SQL Server ging mit der Version 4.21 als reinrassiger relationaler Datenbankserver an den Start und auch heute noch bildet die relationale Datenbankmaschine den Kern von SQL Server. Als Entwickler braucht man Sie sicher nicht von den Vorteilen einer Datenbank als Datenspeicher zu überzeugen. Im Gegensatz zu einer dateibasierten Datenhaltung profitieren Sie von bequemen Zugriffsmechanismen und einer an das relationale Datenmodell angepassten Abfragesprache. Die Datenbank-Programmiersprache Transact-SQL ist die Microsoft-Implementierung der (mehr oder weniger) standardisierten Datenbanksprache SQL (Structured Query Language).

Warum Transact-SQL heute so ist, wie es ist, hat mit der Geschichte von SQL Server zu tun. Der wurde nämlich in einer Koproduktion von Microsoft, Ashton-Tate und Sybase Ende der 80er Jahre entwickelt. Sybase hatte zu diesem Zeitpunkt schon ein Datenbankmanagementsystem auf dem Markt. Sybase SQL Server 3.0 konnte unter UNIX und VMS betrieben werden. 1989 gab es dann zum ersten Mal SQL Server für OS/2 (Version 1.0). Das erste Produkt unter dem Namen »Microsoft SQL Server« kam 1992 auf den Markt – immer noch für OS/2. Mit dem Erscheinen von NT 3.1 gab es dann zeitgleich das erste SQL Server Release für ein Microsoft Betriebssystem: SQL Server 4.21. Die Codebasis war aber weiterhin die des Sybase Servers. Der Version 4.21 und auch den nachfolgenden Versionen, die von Microsoft entwickelt wurden – 6.0 und 6.5 –, merkte man die Herkunft deutlich an. Die Speicherplatzverwaltung beispielsweise kannte »Medien« fester Größe, ein Überbleibsel aus VMS-Zeiten. Vor allen Dingen aber die Programmiersprache Transact-SQL erinnert an diese Zeit. Transact-SQL wurde ursprünglich von Sybase entworfen und innerhalb von Microsoft SQL Server weiterentwickelt. Im Grunde müsste man von Sybase Transact-SQL und Microsoft Transact-SQL reden. Sybase-Entwickler kommen wunderbar mit Microsoft SQL Server zurecht. Schlüsselworte und Syntax der zentralen Sprachelemente sind immer noch identisch – allerdings hat »unser« SQL Server im Laufe der Zeit eine Menge sinnvoller Sprachelemente spendiert bekommen, während Sybase Transact-SQL noch sehr stark an die ursprüngliche Variante erinnert.[2]

Falls Sie noch nicht viel mit Microsoft SQL Server zu tun hatten, oder sich noch einmal vergewissern wollen, mit was für einem System Sie da eigentlich die ganze Zeit arbeiten, folgt hier Steckbrief des relationalen Servers:

Standardtreue. Es gibt eine Menge offizieller ANSI-Standards für die Structured Query Language. Trotzdem können sich zwei SQL-Indianer verschiedener Stämme (Datenbanksysteme) nicht miteinander verständigen, jedenfalls nicht, wenn die proprietären Hersteller-Spracherweiterungen eingesetzt werden. Beschränkt man sich bei der Server-Programmierung auf den ANSI 92 Entry-Level, dann gibt es meistens keine Probleme bei einer Portierung. Alle anderen ANSI-Level und Standards werden nur teilweise eingehalten. Auch wenn Sie vorhaben, eine Datenschicht zu implementieren, die sich auf andere Systeme migrieren lässt, müssen Sie nicht auf die bequemen und mächtigen Spracherweiterungen von T-SQL verzichten. Sie sollten dann allerdings die Geschäftslogik in Prozeduren verpacken, um saubere Schnittstellen zu definieren. Die »Innereien« der Prozeduren – Ihren Programmcode – müssen Sie natürlich konvertieren. Das ist wegen der Einfachheit der Serversprachen aber kein kompliziertes, höchstens ein langwieriges Unterfangen.

Intelligente Optimierung. Das Wunderbare an der deklarativen Datenbankabfragesprache T-SQL ist, dass Sie auf einem gut erforschten mathematischen Modell beruht: der relationalen Algebra. Ist ein Stapel (Batch) von T-SQL-Kommandos erst einmal in eine standardisierte interne Darstellung überführt (algebraisiert), dann beginnt der Optimierer in der Datenbankmaschine mit der Arbeit und findet auf der Grundlage der Datenstrukturen, Tabelleninhalte und Indizes den optimalen Plan für die Abarbeitung der Abfragen. SQL Server verfügt über einen kostenbasierten Optimierer, der sogar die Anzahl der verfügbaren Prozessoren und die Menge an verfügbarem Arbeitsspeicher in Betracht zieht.

Spracherweiterungen. Durch prozedurale Erweiterungen wird T-SQL zu einer Programmiersprache, die dafür geeignet ist, einfache serverseitige Logik zu entwickeln. Das Hauptanwendungsgebiet ist sicher das Schreiben der so genannten gespeicherten Prozeduren. Es gibt einen minimalen, aber ausreichenden Sprachumfang für die Implementierung der Geschäftslogik. Die Kargheit der Sprache – die mit nur einer Entscheidungs-, einer einzigen Schleifenstruktur und ausschließlich skalaren lokalen Variablen auskommt – wird durch die hohe Ausführungsgeschwindigkeit wettgemacht. Für komplexe serverseitige Aufgabenstellungen bietet sich in SQL Server 2008 die Verwendung von .NET-basierten Datenbankobjekten (wie benutzerdefinierte Datentypen oder gespeicherte Prozeduren) an.

Spracherweiterung gibt es aber auch im relationalen Bereich. In SQL Server 2008 ist es möglich, rekursive Abfragen durch Common Table Expressions zu programmieren. Nummerierte Ergebnismengen werden durch Ranking Functions möglich, Kreuztabellenabfragen durch das Schlüsselwort PIVOT und vieles mehr. Sie sollten sich immer erst nach solch einer T-SQL-Variante umsehen, bevor Sie eine Datenoperation selbst programmieren. So sparen Sie Entwicklungs- und Ausführungszeit.

Skalierbarkeit. Skalierbarkeit hat bei Datenbankmanagementsystemen entweder mit steigenden Benutzer- und Abfragezahlen oder wachsenden Datenmengen zu tun. Antwortzeiten und Durchsatz in einem akzeptablen Bereich zu halten, ist in einem großen Datenbanksystem eine anspruchsvolle Aufgabe. In SQL Server sind verschiedene Komponenten vorhanden, die zur Skalierbarkeit beitragen. Es gibt Caching-Mechanismen für T-SQL-Befehlsstapel, die verhindern, dass ähnliche Kommandos erneut für die Ausführung vorbereitet und kompiliert werden müssen (Plan Caching). Ein Sperren-Manager kümmert sich darum, dass die Datensatzsperren möglichst effizient gesetzt werden (Lock Manager). In Systemen mit mehreren Prozessoren können viele der aufwändigen Operationen parallelisiert werden (Query Parallelism). Die Liste der Optimierungen ist verdammt lang.

Management großer Datenmengen. Eine Anwendung, die unter Laboranwendungen in der Entwicklungsumgebung ausgezeichnet funktioniert, kann im Echtbetrieb unter der Last großer Datenmengen »einknicken«. SQL Server verfügt dabei über viele Funktionen, die den Umgang mit großen Datenmengen erleichtern. Das beginnt mit der Möglichkeit, die Objekte in einer Datenbank über Dateigruppen geschickt zu verteilen und Zugriffe parallel auszuführen, was mit cleveren Indizierungsverfahren zu tun hat. Partitionierte Tabellen, Sichten und Indizes wurden mit SQL Server 2005 eingeführt. SQL Server 2008 hat ausgesprochen mächtige Features für sehr große Datenbanken mit an Bord: Komprimierung von Tabellen und Indizes, sowie Backup-Komprimierung. Das spart nicht nur Speicherplatz, sondern auch Zeit, nämlich die Zeit, die für das Übertragen der Daten von den Festplatten in den Arbeitsspeicher des SQL Server benötigt wird.

Autotuning. Eine der wichtigsten Designvorgaben von SQL Server war von Anfang an, die Entwickler und Administratoren mit so wenig technischen Details wie möglich zu belasten. Keine Frage – andere DBMS sind auch performant, aber es werden viel tiefere Kenntnisse des Systems benötigt, um diese Performance zu erreichen. Die allermeisten Stellschrauben bei SQL Server werden von diesem selbst fein justiert (Autotuning), während andere Datenbanksysteme es beispielsweise erforderlich machen, zwischen verschiedenen Speicherstrukturen auszuwählen. Dennoch ist unbedingt notwendig, sich mit der Arbeitsweise von SQL Server vertraut zu machen. Direkt »aus der Dose« läuft jeder SQL Server zwar schon sehr ordentlich – mit der richtigen Konfiguration und Programmierung kann er aber höllisch schnell werden.

Es gibt eine große Anzahl von Erweiterungen des relationalen Kerns, die Sie natürlich auch in diesem Buch kennen lernen werden. Volltextsuche, XML in der Datenbank, die Möglichkeit, SQL Server Objekte in .NET-Programmiersprachen mithilfe des .NET Framework zu implementieren, sind nur ein paar davon. Wie man es auch dreht und wendet: An den relationalen Funktionen führt kein Weg vorbei. Ein Entwickler wird immer gute Transact-SQL-Kenntnisse benötigen, um das Optimum aus seinen SQL Server-Anwendungen herauszuholen. Auch in den Zeiten von LINQ.

[2] Wer sich davon überzeugen möchte, für den gibt es in der Link-Sammlung im Dokumentenordner der Buch-CD die Adresse der Sybase-Sprachdefinition.

.NET Inside

Die klassischen relationalen Abfragesprachen für Datenbanksysteme, wie Transact-SQL, weisen drei typische Merkmale auf: Sie sind unglaublich schnell, simpel aufgebaut und mehr oder weniger standardisiert. Die Muttersprache SQL ist hervorragend dafür geeignet, effiziente Datenbankabfragen zu liefern. Sie lässt sich besonders leicht analysieren, algebraisieren und optimieren. Die zu Grunde liegende relationale Algebra ist vollständig beschrieben und sehr gut erforscht – eine Freude für jede Datenbankmaschine. Auch die Ausführung der kleinen prozeduralen Programmiersprachenanteile in Transact-SQL geschieht mit einer atemberaubenden Geschwindigkeit. Ein kurzer Blick auf den Sprachumfang und die Syntax von T-SQL reicht vollkommen aus, um das zu erklären. Transact-SQL ähnelt mehr einer einfachen Batch- oder Assemblersprache, als einer »richtigen« Programmiersprache.

Was für die Datenbankmaschine von Vorteil ist, das ist für Menschen (hier »Entwickler genannt«) nicht immer schön. Eine große Menge der möglichen Geschäftsprobleme lassen sich zweifellos gut in einem relationalen Schema abbilden. Es gibt aber eine vermutlich fast genau so große Menge, bei der die Übersetzung etwas holprig wirkt. Da geht es um Themen wie die Abbildung hierarchischer Strukturen beliebiger Tiefe (hier bieten die T-SQL Common Table Expressions und der neue Datentyp HierarchyID aber endlich Auswege). Es geht um die Umsetzung objektorientierter Prinzipien wie Vererbung oder Polymorphie: Ein Kundendatensatz ist ein spezialisierter Adress-Datensatz. Schließlich geht es ganz schlicht und ergreifend um das Fehlen elementarer aber nützlicher Basisdatentypen wie Arrays oder Records (Arrays soll es erst in der nächsten SQL Server-Generation als Datentyp geben).

Betrachtet man das Zusammenspiel zwischen Client- und Serverprogrammierung, dann wird man feststellen, dass ein sehr gut durchdachtes objektorientiertes Design der Geschäftsobjekte einer Anwendung sich häufig nur mit einigem Aufwand in einer Datenbank umsetzen lässt. Das dazu notwendige objektrelationale Mapping kann handgemacht oder automatisiert sein. Es gibt viele gute Tools dafür, die sich sogar in Visual Studio integrieren lassen. Das Mapping besteht in der Regel aus vielen »dummen« Wrappern um die Tabellen einer Datenbank. Über diese werden die Datenzugriffsmethoden zur Verfügung gestellt. Hier klafft eine Lücke in den Ausdrucksmöglichkeiten der verschiedenen Programmiersprachen, die – entlehnt aus der Elektrotechnik – gerne als Impedanz-Fehlanpassung bezeichnet wird (so – jetzt klingt das Problem gleich viel besser). Arbeitet man in der .NET-Entwicklung mit typisierten ADO.NET-Datasets anstelle von Geschäftsobjekten, die man von Grund auf selbst implementiert hat, dann stellen sich einige der Probleme nicht mehr so dramatisch dar. Was bleibt ist, je nach Architektur der Anwendung, aber immer noch die Notwendigkeit, serverseitigen Code in T-SQL zu formulieren. Das ist für viele Applikationsentwickler eine ungeliebte Aufgabe – während es für viele Datenbankentwickler eine geliebte Aufgabe ist.

Microsoft hat nicht den Weg anderer Datenbankhersteller beschritten, welche die SQL:1999- und SQL:2003-Standards zur objektrelationalen Erweiterung von SQL umgesetzt haben, sondern einen eigenen, leistungsfähigen Weg entwickelt, die Mängel des ursprünglichen SQL auszugleichen: Es handelt sich um die Integration der Common Language Runtime in die Datenbankmaschine. Zu Beginn der Entwicklung der Vorgängerversion (SQL Server 2005) war nur die Möglichkeit vorgesehen, gespeicherte Prozeduren in Visual Basic.NET schreiben zu können. Gott sei Dank haben sich die schlauen Köpfe im Entwicklungsteam das anders überlegt und so ist etwas richtig Gutes daraus geworden. Serverseitiger Code kann seit SQL Server 2005 in Sprachen wie VB.NET oder C# geschrieben werden, die Möglichkeiten der Base Class Library stehen zur Verfügung, und es lassen sich mit .NET nicht nur gespeicherte Prozeduren implementieren, sondern insgesamt diese Datenbankobjekte:

Gespeicherte Prozeduren

Trigger

Benutzerdefinierte Funktionen

Benutzerdefinierte Datentypen

Aggregatfunktionen

Das bietet phantastische neue Möglichkeiten für Entwickler. Allerdings darf man dabei nicht übersehen, dass für den Datenzugriff weiterhin T-SQL eingesetzt wird, und zwar über einen serverseitigen, im Prozessraum der Datenbankmaschine gehosteten Datenprovider. Das Implementieren komplexer Geschäftslogik in der Datenbank selbst wird durch die .NET-Programmierung deutlich komfortabler. Die Ablösung von Prozeduren, die keinen oder nur einfachen prozeduralen Code beinhalten, lohnt sich dagegen nicht. Hier macht T-SQL weiterhin einen guten und schnellen Job. Betrachten Sie ».NET-Inside« einfach als einen zusätzlichen Weg, den Sie in Abhängigkeit von der Gesamtarchitektur Ihrer Anwendung gewinnbringend einsetzen können. Im Buchabschnitt »Serverobjekte mit .NET programmieren« erhalten Sie eine Menge Anregungen, wie Sie typische »Real Live«-Aufgabenstellungen, die Ihnen in T-SQL Bauchschmerzen bereiten würden, unter Einsatz der SQLCLR (SQL Server Common Language Runtime) mit ein paar Zeilen Code und einem Lächeln schnell lösen können.

Die Impedanz-Fehlanpassung ist damit jedoch noch nicht gelöst. Parallel zu SQL Server 2008 ist glücklicherweise das .NET Framework 3.5 erschienen, welches ausgesprochen nützliche Erweiterungen zu ADO.NET enthält, die wir Ihnen in diesem Buch selbstverständlich nicht vorenthalten möchten. Und ja: Es gibt jetzt eine Lösung für das Impedanz-Problem!

Neue Programmierparadigmen in ADO.NET

Der SQL Server 2008 ist eine moderne und stabile Datenbankmanagementplattform, die – wenn sie richtig verwendet wird – höllisch schnell die Kommandos der Datenbankprogrammiersprache T-SQL verarbeiten kann. Das reicht natürlich noch nicht aus, um gute Anwendungen zu programmieren. Dazu braucht es gute Entwickler. Und aus eigener Erfahrung (als Trainer und Consultant) kann ich sagen, dass sich die Anwendungsentwickler (manchmal despektierlich »Programmierer«[3] genannt) kategorisch in zwei große Klassen unterteilen lassen: Zum einen diejenigen, die sich gerne mit (Transact-) SQL beschäftigen und denen es Spaß macht, sich mit einem guten Datenbanklayout der Optimierung Ihrer SQL-Statements zu beschäftigen. Zum anderen diejenigen, die sich am liebsten mit der Konstruktion Ihrer Business-Objektmodelle beschäftigen (was nichts Verwerfliches ist) und für die der SQL Server einfach eine »Persistenzschicht« darstellt (diese Sichtweise ist schon ein wenig verwerflich). Für die zweite Klasse von Entwicklern stellt das gute alte SQL irgendwie ein finsteres Relikt aus dem letzten Jahrtausend dar (was zumindest, was das Jahrtausend angeht, auch stimmt), welches in der Datenzugriffsschicht immer nur für Ärger, Schreibarbeit und Abhängigkeit von bestimmten Datenbankservern sorgt. Na ja, wer sich mit (dem alten) ADO.NET auskennt, weiß, dass man sich das Schreiben der Datenzugriffe schon etwas flüssiger vorstellen könnte.

Doch die Rettung ist nahe! Und zwar in Form zweier neuer Konzepte in ADO.NET, die mit der Version 3.5 (bzw. 3.5 SP1 – Entity Framework) fest in das .NET Framework integriert wurden:

Language Integrated Queries (LINQ). Das LINQ-Konzept erlaubt die Formulierung von Datenbankabfragen mit den Mitteln der Programmiersprache selbst. In »klassischem« ADO.NET werden die Datenbankabfragen in der Programmiersprache des jeweiligen Datenbankservers formuliert und als Textstring zum Server geschickt, der – wenn alles gut geht – mit einem Dataset antwortet. Dieses Vorgehen hat ein paar Nachteile: Die Query Strings werden erst auf dem Server ausgewertet – Fehler werden also erst spät gefunden; es gibt keine Unterstützung durch IntelliSense; der Code kann etwas länglich geraten. Und so weiter. LINQ-fähige Programmiersprachen (wie Visual Basic.NET und C#) stellen Operatoren zur Verfügung, die direkte Abfragen ohne den Umweg über ADO.NET-Objekte, wie z. B. SQLCommand ermöglichen. In Kapitel 27 finden Sie Beispiele. Diese Programmiersprachen mussten zunächst einmal »LINQ-fähig« gemacht werden, wobei Konzepte wie Lambda-Ausdrücke, anonyme Typen und implizite Variablentypisierung eine gewisse Rolle spielen.[4] LINQ ermöglicht in diesen Sprachen nun nicht nur die Abfrage von Datenbankdaten – passende LINQ-Provider, wie LINQ to XML, LINQ to MAPI oder LINQ to SQL (eigentlich müsste man sagen: LINQ to SQL Server) erlauben die Abfrage unterschiedlicher Speichersysteme mit ein und derselben Abfragesprache: Eine feine Sache! Wie sich die LINQ-Performance gegenüber klassischem ADO.NET-Zugriff verhält, ist von vielen Faktoren abhängig. LINQ kann prinzipiell mit T-SQL-Querystrings mithalten (wenn Sie alle »Sicherheitsratschläge« beachten und die Datenbank »linkfreundlich« gestaltet ist).

ADO.NET Entity Framework. Das ADO.NET Entity Framework ist das objektrelationale Mapping-Framework, mit welchem Microsoft die Lücke zwischen den clientseitigen Objektmodellen und dem Datenbankserver zu schließen gedenkt – sprich: Das Impedanz-Fehlanpassungs-Problem löst. Die Datenbanktabellen werden auf Objekte der Businesslogik abgebildet. Der Entwickler muss beispielsweise nicht mehr wissen, durch welche Tabelle(n) sein Geschäftsobjekt »Kunde« in der Datenbank implementiert ist. Das können durchaus mehrere sein, während ein »Kunde« in der Programmiersprache aus einer einzelnen Klasse besteht. Nach der Erstellung eines Entity Data Models (EDM) kümmert sich das Entity Framework um die passenden Mappings. Abfragen gegen die Objekte des EDM werden in einem SQL-Derivat formuliert: Entity SQL. Oder – und hier schließt sich der Kreis – in LINQ. Der Provider LINQ to Entities macht das möglich. Alles Notwendige zur Arbeit mit dem ADO.NET-Entity Framework erfahren Sie in Kapitel 28.

[3] Heutzutage stellt das Wort »Programmier« in manchen Kreisen fast eine Beleidigung dar. Ich kann das nicht ganz nachvollziehen und wäre persönlich gerne ein guter Programmierer. Grüße gehen hiermit an die Software-Architekten und Application-Designer dieser Welt!

[4] Diese Konzepte zu erläutern, würde den Rahmen dieses Buchs definitiv sprengen. Gute Erläuterungen finden Sie in den Materialien auf der Buch-CD.

XML in der Datenbank

Die Speicherung von Daten im XML-Format und die Speicherung von Daten im Format eines relationalen Datenbankmanagementsystems könnten unterschiedlicher nicht sein. XML-Textdokumente sind selbst beschreibend, »geschwätzig« und nehmen keine Rücksicht auf den Speicherplatz. Daten in Datenbankdateien sind binär codiert, »unverständlich« und auf optimale Speicherplatzausnutzung und schnellen Zugriff hin programmiert. Dieser Vergleich soll keine Wertung darstellen! Schließlich sind die Entwicklungsziele der beiden Technologien ursprünglich sehr verschieden gewesen. Die eXtensible Markup Language wurde aus der Metasprache Standard Generalized Markup Language (SGML) heraus entwickelt, um einen allgemeinen Standard für menschen- und maschinenlesbare Dokumente zu schaffen. Man kann als Mitglied der hart arbeitenden IT-Arbeiterklasse gar nicht dankbar genug dafür sein, dass es die Entwicklung hin zu XML und den vielen davon abstammenden Technologien, wie XML-Schemata (XSD), Extensible Stylesheet Language Transformation (XSLT), XQuery, XPath, XPointer, und so weiter und so weiter und last, not least die XML-basierten Webservices gibt. XML-Technologien werden immer mehr zum Mittel der Wahl, um Interoperabilität zwischen Systemen herzustellen.

XML ist optimal für die Speicherung generischer, aber nichtsdestotrotz klar und eindeutig beschreibbarer Dokumente geeignet und für den Austausch dieser Dokumente zwischen Organisationen und deren EDV-Systemen. Das Datenformat der SQL Server-Datendateien dagegen ist optimal für das effektive Speichern »konventioneller« Geschäftsdaten geeignet. Nun ist es aber in der Praxis so, dass die in XML-Dokumenten enthaltenen Daten ebenfalls effizient gespeichert werden müssen, und dass die in SQL Server-Datendateien vergrabenen Informationen mit anderen Systemen ausgetauscht werden sollen. Mit dem Abspeichern hunderter von XML-Dokumenten in einem Verzeichnis eines Dateiservers und dem Durchsuchen jedes einzelnen Dokuments mit der entsprechenden XQuery-Abfrage wird man nicht richtig glücklich werden, was die Effizienz angeht. Und mit dem Versenden einer 20 GB großen SQL Server-Datenbankdatei einer Axapta-Installation an eine Firma, die ein SAP-System unter ORACLE betreibt, wird man nicht richtig glücklich werden, was den reibungslosen Datenaustausch und die Konvertierung der Daten angeht (ja ich weiß – auf solche Ideen wären Sie nie gekommen; das sind wirklich extreme Beispiele). Es liegt nahe, die Vorteile beider Technologien miteinander zu verknüpfen, um das Beste aus beiden Welten zu bekommen.

Es gibt auf dem Feld der reinrassigen XML-Datenbanksysteme ein paar mehr oder weniger experimentelle Systeme und es gibt den Tamino XML Server als ein sehr weit ausgereiftes Produkt. Diese Server speichern ausschließlich XML-Daten und verwenden die diversen XML-Sprachen für das Speichern, Abfragen und Manipulieren. Der Haken bei dieser Philosophie ist zweifellos, dass lupenreine XML-Applikationen in der wirklichen Welt doch eher noch die Ausnahme darstellen und die klassischen Datenbankmanagementsysteme bei typischen Geschäftsanwendungen immer noch klar die Nase vorn haben, was die Leistungsfähigkeit angeht. Hersteller wie Microsoft und andere beschreiten daher einen sehr attraktiven zweiten Weg: Sie bieten relationale Datenbankmanagementsysteme an, die XML-fähig sind. Hat man solch eine heterogene Datenbank zur Verfügung, kann man sich als Entwickler je nach Aufgabenstellung für die eine oder andere Variante entscheiden oder sogar beide Ansätze kombinieren. SQL Server 2008 stellt mit dem Datentyp xml die Möglichkeit zur Verfügung, in jeder beliebigen Tabelle neben relationalen Daten auch XML-Dokumente zu speichern.

Ein dritter Weg stellt die Abbildung von XML-Dokumenten auf relationale Tabellen und Beziehungen dar. In SQL Server besteht diese Möglichkeit schon seit der Version 7.0. Die Transact-SQL-Funktion OPENXML ist in der Lage, ein XML-Dokument zu parsen und daraus eine virtuelle Tabelle (ein Rowset) zu machen, deren Datenzeilen dann in der Datenbank gespeichert werden können. Umgekehrt existiert mit der Klausel FOR XML, die in jedem SELECT-Abfragekommando eingesetzt werden darf, ein Mechanismus, der aus Tabelleninhalten ein wohlgeformtes XML-Dokument generiert. Das kann in einfachen Szenarien schon vollkommen ausreichend sein, aber das direkte Speichern von XML-Dokumenten in der Datenbank hat diverse Vorteile:

Die Datenstrukturen sind dynamisch. : Daten, die über XML-Dokumente ausgetauscht werden, sind semistrukturiert und die Schemata unterliegen häufig Änderungen. Ein gutes Beispiel dafür sind Artikelkataloge, die von großen Herstellern im XML-Format zur Verfügung gestellt werden. Mit der Einführung neuer Produktlinien werden in der Regel neue Beschreibungsattribute fällig. Das ist für die resultierenden XML-Dokumente kein Problem – bei der Speicherung in einem relationalen System müssten jedoch die Tabellen angepasst werden. Bei Änderungen in der hierarchischen Struktur müssen möglicherweise sogar neue Tabellen und Beziehungen angelegt werden.

Die Dokumente können geprüft werden. Beim Einfügen in eine XML-Spalte überprüft SQL Server auf jeden Fall die Wohlgeformtheit des Dokuments. Sicherheitshalber sollte man gleich erwähnen, dass auch XML-Fragmente zugelassen werden. Dies sind »Teilbäume« eines XML-Dokuments, die kein Wurzel-Element besitzen, ansonsten aber den XML-Regeln genügen. Als Entwickler können Sie zusätzlich festlegen, dass auch die Validität der eingefügten Dokumente überprüft werden soll. Dazu werden ein oder mehrere XSD-Schemata in einer Schemasammlung hinterlegt. Bei Operationen auf den XML-Daten kann ein Schema aus einer Sammlung für die Validierung der Ergebnisse verwendet werden.

Die Dokumente können indiziert werden. Daten in einer Spalte vom Typ xml lassen sich mit einem Volltextindex belegen. Dadurch kann der Inhalt der Dokumente erschlossen werden, ohne dass die Namen von Elementen oder Attributen mit indiziert werden. Zur Schaffung möglichst schneller Zugriffspfade für SELECT-Abfragen lassen sich darüber hinaus spezielle XML-Indizes einrichten.

Es können XML-Methoden verwendet werden. Für das Navigieren, Abfragen und Manipulieren von XML-Daten gibt es XML-typische Methoden, wie XQuery. Sie können diese Methoden in SELECT-Abfragen einsetzen, um Daten in XML-Spalten zu durchsuchen. Dabei können Sie innerhalb einer Abfrage ohne Probleme auf XML-Daten und Nicht-XML-Daten zugleich zugreifen. Mit einem UPDATE unter Verwendung der XML-Methoden lassen sich XML-Dokumente direkt in der Datenbank ändern, ohne dass sie aus den Datenstrukturen ausgelesen, geändert und neu gespeichert werden müssten.

Wenn Sie es in Ihrer Entwicklerpraxis mit XML-Dokumenten zu tun haben, dann sollten Sie sich auf jeden Fall mit dem fünften Teil dieses Buchs (Teil V) beschäftigen. SQL Server bietet hervorragende Möglichkeiten für den Umgang mit XML-Daten.

Gekoppelte Systeme und SOA

Verlässt man mit seinen Anwendungen das Entwicklungslabor, gelangt man in die unübersichtliche Wirklichkeit der EDV-Systeme, von denen es viele gibt, mit denen die eigene Applikation reden muss und viele, die sich für die Daten in der Applikation interessieren.

Weil das alles so wichtig ist, fliegt seit einiger Zeit ein neues »Buzz Word« umher: Service Oriented Architecture. SOA kann man auf die eine oder andere Art definieren, aber im Kern geht es darum, »lose gekoppelte Systeme« interoperabel zu machen. Dabei stellen EDV-Systeme Daten und Logik auf standardisierte Weise im Netzwerk zur Verfügung. Die Implementierung von SOA ist ganz eng mit dem Thema Webservices (und einigen unterstützenden Technologien) verbunden.

Webservices

Reizvoll an Webservices ist ihre plattformunabhängige und standardisierte Form der Kommunikation. Wenn zwischen Systemen nichts anderes mehr geht, dann geht zumindest noch ein Webservice. Welche Technologie zur Implementierung verwendet wird, ist vollkommen transparent, und so kann man Java-Anwendungen unter Unix mit .NET-Anwendungen unter Windows oder mit Host-Anwendungen kommunizieren lassen. Das geht auch wunderbar im Internet oder Extranet. Das Protokoll SOAP (Simple Object Access Protocol), das sich hinter den »klassischen« Webservices verbirgt, ist nicht zwangsläufig an HTTP gebunden. SQL Server stellt Webservices allerdings ausschließlich über HTTP-Endpunkte zur Verfügung.

Wie bei so manch anderer Komponente von SQL Server 2008 gab es auch schon früher die Möglichkeit, Webservices in Form eines Features Packs zu implementieren, SQLXML genannt. Damit konnte man schon recht komfortabel aus gespeicherten Prozeduren Webdienste machen und diese veröffentlichen. Dabei spielten IIS (Internet Information Server bzw. Internet Information Services), ein ISAPI-Filter für IIS und OLE DB die entscheidenden Rollen. Mit anderen Worten: Der Weg vom Aufruf des Webservice durch einen Client bis hin zur SQL Server-Datenbankmaschine war nicht eben kurz und die Leistungsfähigkeit dadurch eingeschränkt. Bereits seit SQL Server 2005 ist SOAP zu einem First Class-Kommunikationskanal von SQL Server geworden. Externe Software ist nicht mehr notwendig, um HTTP-Webservices mit SQL Server zu implementieren. SQL Server benötigt einzig den von Windows XP SP2 und Windows 2003 bereitgestellten Kernel-Treiber http.sys und daher keinen installierten IIS. Ein Webservice ist mit dem T-SQL-Kommando CREATE ENDPOINT ... FOR HTTP schnell angelegt. Gespeicherte Prozeduren und benutzerdefinierte Funktionen können als Methoden eines Webservice vereinbart werden. Außerdem gibt es noch die bequeme – aber gefährliche – Variante, beliebige T-SQL-Batches über den Webservice ausführen zu können. Mit dem Anlegen eines HTTP-Endpunkts ist der Webservice tatsächlich schon fertig. Über den im CREATE-Kommando vereinbarten URI-Pfad kann der Service erreicht werden, und bei der Angabe des Parameters ?WSDL im http-Aufruf liefert der Server brav die Beschreibung des neuen Service in Form eines XML-WDSL-Dokuments (Web Services Description Language). Nach dem Konfigurieren der Sicherheit für den Endpunkt ist der Webservices bereit, verwendet zu werden. Das ist wirklich einfach!

Achtung

Das Kommando CREATE ENDPOINT ist in SQL Server 2008 offiziell abgekündigt worden. Damit werden die nativen SQL Server-SOAP Webservices in der nächsten SQL Server-Version höchstwahrscheinlich nicht mehr zur Verfügung stehen. Ich halte das für ausgesprochen bedauerlich, da die SQL Server-Webservices sehr schnell implementiert werden können und aus vorhandenen Prozeduren ganz einfach Webmethoden gemacht werden können. Bei neuen Entwicklungen sollten Sie abwägen, ob Sie mit CREATE ENDPOINT arbeiten wollen oder auf eine Alternative ausweichen, die außerhalb der T-SQL-Programmierung angesiedelt ist. Zum Beispiel:

ASP.NET-Webservices Diese sind Visual Studio-Entwicklern natürlich schon lange bekannt und haben sich in der Praxis gut bewährt.

ADO.NET Data Services Diesen neueren Ansatz sollten Sie sich auf jeden Fall einmal ansehen, wenn Sie auf der Suche nach einem Weg sind, Daten aus Ihrem SQL Server über das Web zu transportieren. Der innovative Ansatz besteht hier in der Verwendung eines Entity Data Models für die Abstraktion der Zugriffsschicht. Der Transport via http funktioniert hierbei nicht mit dem SOAP-Protokoll, sondern durch REST (Representional State Transfer).[5]

Service Broker

Der Service Broker ist sicherlich zugleich eine der interessantesten aber auch am wenigsten intuitiv verständlichen Komponenten von SQL Server 2008. Dass Sie die Beschreibung des Service Brokers gerade hier im Abschnitt „Gekoppelte Systeme und SOA“ finden, ist (kein) reiner Zufall, denn der Service Broker hat viel mit der Skalierbarkeit von Systemen zu tun, die miteinander kommunizieren. Das können sowohl separate Systeme sein, zum Beispiel zwei Applikationen, die über Webservices miteinander verbunden sind, als auch sehr eng gekoppelte Subkomponenten eines Systems. Innerhalb des SQL Server wird der Service Broker von der Datenbankmaschine selbst verwendet, und es kann unter Umständen sogar Sinn ergeben, in einer Benutzeranwendung den Broker innerhalb einer Datenbank einzusetzen. Doch was macht der Service Broker überhaupt?

Die Aufgabe des Service Brokers ist es, asynchrone Kommunikation sicherzustellen. Dabei werden Nachrichten über Warteschlangen gesendet und empfangen. Wenn Sie jetzt sofort an das Microsoft Message Queuing Subsystem von Windows denken (MSMQ), dann liegen Sie gedanklich vollkommen richtig. Konzeptionell geht es hier um das gleiche Thema. Die Bereitstellung dieser Technologie innerhalb des SQL Server hat aber diverse Vorteile:

Integrierte Einrichtung und Verwaltung. Sie sind als SQL-Entwickler nicht darauf angewiesen, zwei verschiedene Systeme einzusetzen. Die Service Broker-Objekte werden in der normalen Routine der Datenbank mit administriert. Die Warteschlangen (die als SQL Server-Tabellen implementiert sind) werden mit einem gewöhnlichen Backup gesichert und durch die Hochverfügbarkeitsmechanismen des Servers geschützt.

Vereinheitlichtes Programmiermodell. T-SQL wird für die Datenbankabfragen und die Nachrichtenverarbeitung eingesetzt.

Transaktionale Nachrichtenverarbeitung. Mit Service Broker-Warteschlangen können relativ leicht nachrichtenbasierte verteilte Transaktionen implementiert werden, ohne dass ein spezieller Transaktionsmonitor verwendet werden müsste.

Bleibt noch zu klären, wie denn überhaupt Anwendungen von der asynchronen Nachrichtenverarbeitung des Service Brokers profitieren können. Es folgen die möglichen Vorteile:

Verbesserte Antwortzeiten. Prozeduren müssen nicht auf den Abschluss der Bearbeitung nach einem Aufruf eines langsamen Teilprozesses warten, sondern können sofort weiterarbeiten. Bei einer Erhöhung der Last werden die Antwortzeiten nicht überproportional länger.

Lastverteilung. Eine Nachricht in einer Warteschlange kann durch einen Empfänger auf einer anderen Maschine verarbeitet werden

Verzögerte Bearbeitung. Nachrichten können in einer Warteschlange gespeichert werden, bis sie von einem Batch Job (beispielsweise zum Tagesabschluss) verarbeitet werden

Parallelisierung. Durch die Verteilung auf mehrere Warteschlangen können Nachrichten parallel verarbeitet werden

Lose Kopplung. Service Broker-Warteschlangen können genau wie Webservices der Kopplung von Anwendungen dienen. In diesem Fall werden natürlich SQL Server-basierte Anwendungen verbunden.

[5] Gute Informationen zu dem ADO.NET Data Services Framework finden Sie ebenfalls in der Materialsammlung auf der CD.

Verteilte Daten

Nachdem Sie gerade kennen gelernt haben, wie Sie verteilte Anwendungen verbinden können, wird jetzt die Perspektive ein wenig gedreht und es geht darum, wie SQL Server mit verteilten Daten arbeiten kann.

SQL Server Integration Services

Auf dem Feld des Datenmanagements gibt es den Begriff Extract-Transform-Load (ETL), der bestimmte, wiederkehrende Operationen treffend beschreibt: Das Abholen von Daten aus einer Datenquelle, wie einem Host, einer Transferdatei oder einem Datenbankmanagementsystem. Das Transformieren der Daten in ein Format, in welchem diese optimal weiterverwendet werden können. Und das Laden der Daten in ein Zielsystem, wie eine Datenbank, die Teil eines Data Warehouse-Systems ist. Die Microsoft-Variante von ELT heißt SQL Server Integration Services (SSIS) und wurde zusammen mit SQL Server 2005 entwickelt.

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!

Lesen Sie weiter in der vollständigen Ausgabe!