Skript1 - Udo Munz

Werbung
Udo Matthias Munz
Datenbanken
und SQL
mit
Einführung
Informationstechnik
Zugriff auf eine Datenbank................................................................................................................ 2
ODBC...................................................................................................................................... 2
Eine DSN einrichten................................................................................................................ 3
Verbindung zu einer Datenbank ........................................................................................................ 4
Datenbank .......................................................................................................................................... 4
Metadaten der Datenbank holen.............................................................................................. 4
Namen der Tabellen und deren Eigenschaften holen .............................................................. 6
Tabelle ............................................................................................................................................... 9
Metadaten einer Tabelle ausgeben .......................................................................................... 9
Senden eines SQL-Strings an eine Tabelle.............................................................................. 9
Tabellenwerte lesen ................................................................................................................. 9
Zugriff auf eine Datenbank
ODBC
Um Datenbanken von Java aus anzusprechen, muss der ODBC-Treiber installiert und konfiguriert werden.
Java greift nämlich mittels der JDBC-ODBC-Bridge über den ODBC-Treiber auf die Datenbank zu.
Man muss also zunächst den ODBC-Zugriff auf die Datenbank einrichten. Das geschieht mit Hilfe des
ODBC-Administrators. Mit diesem können Sie nicht nur die Verbindung zu bestehenden Datenbanken aufnehmen, sondern auch Datenbanken neu erzeugen.
Rufen Sie den ODBC-Administrator auf. Sie Erreichen den ODBC-Administrator über Start - Einstellungen
- Systemsteuerung - Verwaltung - Datenquellen (ODBC). Wem dieser Weg zu lang ist, kann sich auch die
Datei C:\WINNT\System32\ODBCAD32.exe in ein beliebiges Verzeichnis kopieren und/oder eine Verknüpfung darauf anlegen.
2
Zugriff auf eine Datenbank
Eine DSN einrichten
Eine DSN einrichten
Sie müssen mit dem ODBC Administrator eine System-DSN einrichten um auf ihre Datenbank zugreifen zu
können. Das müssen Sie tun, wenn Sie die Datenbank mit dem ODBC Administrator erstellen oder auf eine
zuvor mit ACCESS erstellte Datenbank zugreifen wollen.
Mittels dem Button Hinzufügen erstellen Sie einen neuen Aliasnamen für die Datenbank. Wenn Sie auf eine
bereits bestehende (ACCESS-)Datenbank zugreifen wollen, dann klicken Sie den Button Konfigurieren und
wählen die gewünschte ACCESS-Datenbank aus:
3
Verbindung zu einer Datenbank
Metadaten der Datenbank holen
In diesem Beispiel ist die unter ACCESS erstellte Datenbank ITC-2000.mdb, die sich im Ordner
C:\Programme\Adam\SeQueL\ITC befindet unter dem Alias-Namen ITC ansprechbar. Die Vergabe Aliasnamen bringt den Vorteil, dass im Anwendungsprogramm nur die Alias-Namen erscheinen, und dieses daher
nicht angepasst werden muss, wenn man den Pfad zur Datenbank ändert oder das System auf einen anderen
Rechner überträgt.
Verbindung zu einer Datenbank
Es muss das Paket java.sql in den Programmcode importiert werden.
import java.sql.*;
Als erstes ist der Treiber zu laden. Wir wollen ODBC-konforme Datenbanken abfragen und müssen daher
die JDBC-ODBC-Bridge laden:
Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
Danach muss die Verbindung zur Datenbank (mit dem Aliasnamen ITC) aufgebaut werden. Dazu ist ein
Objekt der Klasse Connection zu erstellen. Dieses Objekt wird mit der Klassenmethode getConnection() der
Klasse DriverManager erzeugt. Vom DriverManager braucht man kein Objekt zu erstellen! Dieses Connection-Objekt stellt die notwendigen Methoden zum Datentransport bereit.
Connection con = DriverManager.getConnection ("jdbc:odbc:ITC");
Datenbank
Metadaten der Datenbank holen
Um die Daten aufnehmen zu können, muss in Java ein Objekt erstellt werden, welches den Speicherplatz für
die zu übertragenden Daten bereitstellt. Zunächst wollen wir die Metadaten der Datenbank erfragen. Das zu
4
Datenbank
Metadaten der Datenbank holen
erstellen wir ein Objekt der Klasse DatabaseMetaData. mit der Methode getMetaData() des eben erstellten
Objekts con:
DatabaseMetaData dbmd = con.getMetaData();
Metadaten kann man nun direkt mit den entsprechenden Methoden auslesen und beispielsweise in einem
TextArea ausgeben:
text = "";
text += "Datenbank:
text += "Version:
area.setText(text);
" + dbmd.getDatabaseProductName() + "\n";
" + dbmd.getDatabaseProductVersion() + "\n";
Weitere Methoden können Sie der Java-Hilfe entnehmen.
Unser Programm ist so aber noch nicht ganz fertig. Beim Datenbankzugriff kann es zu vielerlei Fehlern
kommen: Datenbank ist nicht (mehr) vorhanden, Zugriff verweigert wegen fehlender Rechte usw. Deshalb
wird die Datenbankabfrage in ein try - catch Konstrukt eingepackt, welches Systemfehler abfängt.
try{
// hier stehen die Zugriffsbefehle
}
catch (Exception e){
area.setText(e.toString());
}
Hier nun ein vollständiges Programm, welches
dieses Fenster erzeugt:
import java.awt.*;
import java.awt.event.*;
import java.sql.*;
class JavaDB extends Frame implements ActionListener{
Label lbdb = new Label("URL = jdbc:odbc:");
TextField url= new TextField("MS Datenbank",20);
Button execute = new Button("
Ausführen
");
TextArea area = new TextArea(10, 50);
Font courier = new Font("Courier",Font.PLAIN,12);
public JavaDB(){
addWindowListener(new WindowAdapter(){
public void windowClosing(WindowEvent e){
dispose();
System.exit(0);
}
});
setLayout(new FlowLayout());
add(lbdb);
add(url);
add(execute);
execute.addActionListener(this);
add(area);
area.setFont(courier);
}
public void actionPerformed(ActionEvent e){
if (e.getSource() == execute){
5
Datenbank
Namen der Tabellen und deren Eigenschaften holen
accessDatabase();
}
}
public void accessDatabase(){
try {
Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
Connection con = DriverManager.getConnection ("jdbc:odbc:"+url.getText());
DatabaseMetaData dbmd = con.getMetaData();
display(dbmd);
}
catch (Exception e){
area.setText(e.toString());
}
}
public void display(DatabaseMetaData result){
String text = "Metadaten der Datenbank"+"\n\n";
area.setText(text);
try{
text = "";
text += "Katalog:
" + result.getCatalogTerm() + "\n";
text += "Datenbank:
" + result.getDatabaseProductName() + "\n";
text += "Version:
" + result.getDatabaseProductVersion() + "\n";
text += "Treibername: " + result.getDriverName() + "\n";
text += "Version:
" + result.getDriverVersion() + "\n";
text += "URL:
" + result.getURL() + "\n";
text += "User:
" + result.getUserName() ;
area.append(text);
}
catch (Exception e){
area.setText(e.toString());
}
}
public static void main(String args[]){
System.out.println("Starting JavaDB...");
JavaDB mainFrame = new JavaDB();
mainFrame.setSize(400, 250);
mainFrame.setTitle("JavaDB");
mainFrame.setVisible(true);
}
}
Namen der Tabellen und deren Eigenschaften holen
Das vorige Beispiel gibt nicht so sehr interessante Daten preis. Um die beispielsweise die Namen der in der
Datenbank enthaltenen Tabellen zu erfahren muss man mit einem weiteren Zwischenschritt diese aus den
Metadaten extrahieren. Es ist deshalb so kompliziert, weil man nicht von vornherein sagen kann, wie viele
Tabellen vorkommen, und welche Felder diese enthalten.
Das Auslesen geschieht mit Hilfe einer weiteren Klasse: ResultSet. Nach dem Erzeugen eines Objektes dieser Klasse mit der Methode getTables() aus dem DatabaseMetaData-Objekt sind die Tabellennamen mittels
Methoden des ResultSet-Objekts verfügbar. Rufen Sie die Online-Hilfe des Java-JDK auf um weitere Informationen über die folgenden ResultSet-Klasse und deren Methoden zu erhalten!
text = "";
String[] tableType = {"TABLE"};
//nur Benutzertabellen
ResultSet rsTab = result.getTables(null,null,"%",tableType);
Der wiederholte Aufruf der Methode rsTab.getString("TABLE_NAME") gibt je Aufruf einen weiteren Tabellennamen aus.
table = rsTab.getString("TABLE_NAME");
Die Namen der Felder die in dieser Tabelle enthalten sind erhält man nach dem Erzeugen eines weiteren
ResultSet:
6
Datenbank
Namen der Tabellen und deren Eigenschaften holen
rsCol = result.getColumns(null,null,table,"%");
Aus diesem ResultSet erhalten Sie nacheinander die einzelnen Feldnamen durch wiederholten Aufruf der
Methode rsCol.getString("COLUMN_NAME")
text += rsCol.getString("COLUMN_NAME");
Die Aufrufe der einzelnen Tabellen und deren Feldnamen werden in ineinander geschachtelten Wiederholungsschleifen untergebracht. Die Methode next() gibt true zurück, solange noch weitere Elemente im ResultSet vorhanden sind. next() kann man daher als Wiederholungskriterium in einer while-Schleife verwenden.
while (rsTab.next()){
table = rsTab.getString("TABLE_NAME");
text = table + "\n";
area.append(text);
text = "";
rsCol = result.getColumns(null,null,table,"%");
while (rsCol.next()){
text += rsCol.getString("COLUMN_NAME") + " | ";
text += rsCol.getString("TYPE_NAME")
+ " | ";
text += rsCol.getString("DATA_TYPE")
+ " | ";
text += rsCol.getString("REMARKS")
+ "\n";
}
area.append(text);
}
Ein vollständiges Programm kann mit einiger kosmetischer Korrektur bei der Ausgabe das folgende Bild
liefern. Sie sehen die Ausgabe der Tabellennamen und darunter in jeweils einer Zeile ein Datenfeld samt
Datentyp und Bemerkung.
Hier folgt noch der komplette Code des Programms:
import java.awt.*;
import java.awt.event.*;
import java.sql.*;
class JavaDBTabellen extends Frame implements ActionListener{
Label lbdb = new Label("URL = jdbc:odbc:");
TextField url= new TextField("MS Datenbank",20);
7
Datenbank
Button execute = new Button("
Ausführen
TextArea area = new TextArea(20, 70);
Namen der Tabellen und deren Eigenschaften holen
");
Font courier = new Font("Courier",Font.PLAIN,12);
public JavaDBTabellen(){
addWindowListener(new WindowAdapter(){
public void windowClosing(WindowEvent e){
dispose();
System.exit(0);
}
});
setLayout(new FlowLayout());
add(lbdb);
add(url);
add(execute);
execute.addActionListener(this);
add(area);
area.setFont(courier);
}
public void actionPerformed(ActionEvent e){
if (e.getSource() == execute){
accessDatabase();
}
}
public void accessDatabase(){
try {
Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
Connection con = DriverManager.getConnection("jdbc:odbc:"+url.getText());
DatabaseMetaData dbmd = con.getMetaData();
display(dbmd);
}
catch (Exception e){
area.setText(e.toString());
}
}
public void display(DatabaseMetaData result){
String text = "";
try{
text = "Tabellen der Datenbank: " + result.getURL() + "\n";
area.setText(text);
text = "";
String[] tableType = {"TABLE"}; //nur Benutzertabellen
ResultSet rsTab = result.getTables(null,null,"%",tableType);
//
ResultSet rsTab = result.getTables(null,null,"%",null); //ALLE Tabellen
ResultSet rsCol;
String table, l20 = "
";
while (rsTab.next()){
table = rsTab.getString("TABLE_NAME");
text = rsTab.getString("TABLE_TYPE")+":\t"+table + "\n";
area.append("\n"+text);
text = "";
rsCol = result.getColumns(null,null,table,"%");
while (rsCol.next()){
text += "\t"+(rsCol.getString("COLUMN_NAME")+l20).substring(0,19);
text += "\t"+(rsCol.getString("TYPE_NAME") +l20).substring(0,10) ;
text += "\t"+(rsCol.getString("DATA_TYPE") +l20).substring(0,4) ;
text += "\t"+ rsCol.getString("REMARKS")
+"\n";
}
area.append(text);
}
}
catch (Exception e){
area.setText(e.toString());
}
}
public static void main(String args[]){
System.out.println("Starting JavaDBTabellen...");
8
Tabelle
Metadaten einer Tabelle ausgeben
JavaDBTabellen mainFrame = new JavaDBTabellen();
mainFrame.setSize(550, 400);
mainFrame.setTitle("JavaDBTabellen");
mainFrame.setVisible(true);
}
}
Tabelle
Metadaten einer Tabelle ausgeben
Die Metadaten der Tabelle enthalten die Inhalte der Felder, also die „Tabelle“ selbst. Nach Absetzen der
SQL-Anweisung SELECT * FROM <Tabelle> sind die entsprechenden Werte als Metadaten vorhanden.
Senden eines SQL-Strings an eine Tabelle
Erst muss ein Objekt der Klasse Statement erzeugt werden. Darin ist die Methode execute() enthalten, die als
Parameter den SQL-String an die Tabelle übergibt.
Statement statement = con.createStatement();
boolean control = statement.execute("SELECT * FROM Artikel");
Tabellenwerte lesen
Die Daten sind mittels ResultSet der Tabelle zu entnehmen:
ResultSet result = statement.getResultSet();
Aus diesem ResultSet kann zunächst die MetaDaten der Tabelle, also die Feldnamen, auslesen:
ResultSetMetaData meta = result.getMetaData();
int columns = meta.getColumnCount();
for (int i = 1; i <= columns; i++){
text += meta.getColumnName(i) + " | ";
}
Und weiter erhält man durch wiederholte Aufrufe in einer Schleife die Tabellendaten Zeile für Zeile die
Feldwerte durch Aufrufe der Methode getString(). Beachten Sie, dass Sie dieser Methode entweder die
Nummer oder den Bezeichner der Spalte übergeben können!
text = "";
while (result.next()){
for (int i = 1; i <= columns; i++){
text += result.getString(i) + " | ";
}
text += "\n";
}
area.append(text);
Mit einigen kosmetischen Korrekturen und einem Textfeld zur Eingabe des SQL-Strings während der Laufzeit kann man dieses Ergebnis erzielen:
9
Tabelle
Tabellenwerte lesen
Und nun auch hierzu der komplette Quellcode:
import java.awt.*;
import java.awt.event.*;
import java.sql.*;
class JavaSQL extends Frame implements ActionListener{
Label lbdb = new Label("URL = jdbc:odbc:");
TextField url= new TextField("MS Datenbank",40);
Label lbsql = new Label("SQL =");
TextField sql= new TextField("SELECT * FROM ",40);
Button execute = new Button("
Ausführen
");
TextArea area = new TextArea(20, 100);
Font courier = new Font("Courier",Font.PLAIN,12);
public JavaSQL(){
addWindowListener(new WindowAdapter(){
public void windowClosing(WindowEvent e){
dispose();
System.exit(0);
}
});
setLayout(new FlowLayout());
add(lbdb);
add(url);
add(lbsql);
add(sql);
add(execute);
execute.addActionListener(this);
add(area);
area.setFont(courier);
}
public void actionPerformed(ActionEvent e){
if (e.getSource() == execute)
{
accessDatabase();
}
}
public void accessDatabase(){
try {
Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
Connection con = DriverManager.getConnection("jdbc:odbc:"+url.getText());
//Name in ODBC-Manager festlegen
// muss _nicht_ gleich DB-Name sein!!
Statement statement = con.createStatement();
10
Tabelle
Tabellenwerte lesen
boolean control = statement.execute(sql.getText());
if (control)
{
ResultSet result = statement.getResultSet();
if (result != null)
{
display(result);
}
else{
area.setText("");
con.close();
}
}
}
catch (Exception e){
area.setText(e.toString());
}
}
public void display(ResultSet result){
try {
ResultSetMetaData meta = result.getMetaData();
int columns = meta.getColumnCount();
String text = "| ";
for (int i = 1; i <= columns; i++){
text += meta.getColumnName(i) + "\t | ";
}
text += "\n";
area.setText(text);
text = "";
while (result.next()){
text += "| ";
for (int i = 1; i <= columns; i++){
text += result.getString(i) + "\t | ";
// Feldname ODER Spaltennummer 1..n
}
text += "\n";
}
area.append(text);
}
catch (SQLException e){
area.setText(e.toString());
}
}
public static void main(String args[]){
System.out.println("Starting JavaSQL...");
JavaSQL mainFrame = new JavaSQL();
mainFrame.setSize(800, 450);
mainFrame.setTitle("JavaSQL");
mainFrame.setVisible(true);
}
}
11
Herunterladen