Avatar billede motyl Nybegynder
22. november 2004 - 22:44 Der er 22 kommentarer og
1 løsning

Java og Databaser

Hej Eksperter.

Jeg er nybegynder i Java kodning og derfor kommer disse spørgsmål. Jeg er i færd med at kode en vagtplan i Java, og er begyndt at rode lide med forbindelsen til databasen. Jeg forestiller mig at mit program skal have en enkelt DB controller bestående af en masse metoder til håndtering af connect, forespørgsler og close af databasen. Jeg har indtil videre kodet nedenstående, men der er en masse fejl. F.eks. ønsker jeg at få returneret 'res' til videre behandling i andre klasser, men hvilken datatype er 'res'?

Hvordan refererer jeg til 'res' i DBBroke fra DBClose? Kan man smede den sammen på en eller anden måde?

Hvordan kalder jeg på DBConnect fra en anden klasse?
 
Er det mon en god ide at dele DB controlleren op i disse metoder i samme klasse?

Har I ellers andre forslag til hvordan man kan gøre dette stykke arbejde?

Håber at I kan hjælpe mig med at udvide mit kendskab til dette sprog ;)
------------------------ 

import java.sql.*;
public class DBController {
        //Skal kunne kaldes fra andre klasser, hvor der er behov
        //for at etabelere en forbindelse til DB
    public void DBConn() {
        Connection conn = null;
        try {
            Class.forName("com.mysql.jdbc.Driver").newInstance();
            conn =
                DriverManager.getConnection(
                    "jdbc:mysql://ishtar.imv.au.dk/g04f010",
                    "g04f010",
                    "PASSWORD");

            if (!conn.isClosed())
                System.out.println(
                    "Successfully connected to "
                        + "MySQL server using TCP/IP...");

        } catch (Exception e) {
            System.err.println("Exception: " + e.getMessage());
        } finally {
            try {
                if (conn != null)
                    conn.close();
            } catch (SQLException e) {
            }
        }
    }

        //Skal håndtere forespørgsler til DB og returnere 'res'
        //som skal kunne benyttes i andre klasser.
    public String DBBroke(String theSql) {
        Statement statement = conn.createStatement();

        ResultSet res = statement.executeQuery(theSql);

        return res;
    }

    // Skal bruges til at lukke forbindelsen til DB
        // efter at det er foretaget en forespørgsel vha.
        // DBBroke().
    public void DBClose() {
        closeRes = DBBroke(??);
        closeRes.close();
        statement.close();
        conn.close();
        System.exit(0);
    }
}
Avatar billede arne_v Ekspert
22. november 2004 - 22:57 #1
Connection conn

skal lave som instans variabel og ikke som lokal variabel i DBConn fordi
du skal bruge den  de øvrige metoder.
Avatar billede arne_v Ekspert
22. november 2004 - 22:58 #2
Du skal ikke kalde

conn.close();

i din DBConn finally block fordi du vil holde forbindelsen åben
Avatar billede arne_v Ekspert
22. november 2004 - 22:58 #3
Jeg trorheller ikke at du vil kalde

System.exit(0);

i din DBClose
Avatar billede arne_v Ekspert
22. november 2004 - 23:00 #4
Statement og ResultSet variablene kan også laves til instans variable
så de kan lukkes i DBClose men det er ikke så vigtigt
Avatar billede arne_v Ekspert
22. november 2004 - 23:00 #5
public String DBBroke(String theSql)

skal naturligvis være:

public ResultSet DBBroke(String theSql)
Avatar billede arne_v Ekspert
22. november 2004 - 23:00 #6
Prøv de rettelser først !
Avatar billede motyl Nybegynder
22. november 2004 - 23:01 #7
Undskyld, men hvordan laver jeg Connection conn til en instans-variabel o DBConn?
Avatar billede arne_v Ekspert
22. november 2004 - 23:03 #8
public class DBController {
    private Connection conn = null;
    public void DBConn() {
        try {
            Class.forName("com.mysql.jdbc.Driver").newInstance();
            conn =
                DriverManager.getConnection(
                    "jdbc:mysql://ishtar.imv.au.dk/g04f010",
                    "g04f010",
                    "PASSWORD");
Avatar billede nephilim Nybegynder
22. november 2004 - 23:21 #9
tror jeg ville gøre det på følgende måde:
-----------
public void connect(){
    try{
        Class.forName("com.mysql.jdbc.Driver").newInstance();
    }
    catch(Exception e){
        throw new Exception("fejl ved indlaesning af driver i db.connect.")
    }
    try{
        con = DriverManager.getConnection(
                    "jdbc:mysql://ishtar.imv.au.dk/g04f010",
                    "g04f010",
                    "PASSWORD");
    }
    catch(Exception e){
        throw new Exception("fejl under kontakt til server i db.connect.")
    }
}

-----------
Ikke den store ændring, dog giver den lidt pænere fejlmeldinger.
Avatar billede arne_v Ekspert
22. november 2004 - 23:26 #10
pænere ja men også mindre brugbart - jeg lavede det også sådan
en gang, men jeg har lært at sætte pris på en e.getMessage(), så
man får al info.
Avatar billede nephilim Nybegynder
22. november 2004 - 23:28 #11
ja men jeg regner med at han laver den til nogle uden den store java experience, og så vil e.getMessage måske give lidt for indviklet fejlmeddelelse?
Avatar billede motyl Nybegynder
22. november 2004 - 23:36 #12
Hej Arne.

Ser det mere fornuftigt ud nu? Jeg får ingen fejl i programmet mere, så jeg er vel på rette vej:)
Ved du om det er den rigtige måde at bygge Controller/Persistens-laget i et OO program? Altså, er det en bedre måde at lave controller delen til DB'en på?

Mvh.

Brian

--------------------------
import java.sql.*;
public class DBController {
    //insatans variabler
    private Connection conn = null;
    private ResultSet res;
    private Statement statement;

    public void DBConn() {
        try {
            Class.forName("com.mysql.jdbc.Driver").newInstance();
            conn =
                DriverManager.getConnection(
                    "jdbc:mysql://ishtar.imv.au.dk/g04f010",
                    "g04f010",
                    "PASSWORD");
            ;

            if (!conn.isClosed())
                System.out.println(
                    "Successfully connected to "
                        + "MySQL server using TCP/IP...");

        } catch (Exception e) {
            System.err.println("Exception: " + e.getMessage());
        }
    }

    public ResultSet DBBroke(String theSql) throws SQLException {
        Statement statement = conn.createStatement();
        ResultSet res = statement.executeQuery(theSql);
        return res;
    }

    public void DBClose() throws SQLException {
        res.close();
        statement.close();
        conn.close();
    }
}
Avatar billede motyl Nybegynder
22. november 2004 - 23:40 #13
Hej nephilim.
Tak for din forslag.
Du har ret i at dem der skal benytte sig at programmet ikke er Java-nørder, men e.getMessage er ok under udviklingsprocessen, og efterfølgende kan/vil jeg bytte System.err.println("Exception: " + e.getMessage()); ud med en mailfunktion ;)

Mvh.

Brian
Avatar billede arne_v Ekspert
22. november 2004 - 23:42 #14
Det ser meget bedre ud.

DBBroke skal nok være:

    public ResultSet DBBroke(String theSql) throws SQLException {
        statement = conn.createStatement();
        res = statement.executeQuery(theSql);
        return res;
    }

for at bruge instans variablene
Avatar billede nephilim Nybegynder
22. november 2004 - 23:44 #15
designmæssigt mener jeg det pattern du er ved at bruge hedder PersistentStorageBroker, som står for kommunikation mellem programmet og databasen. Ifølge min og en hel del andre's mening er dette en god metode at lave det på eftersom denne klasse er nem at skifte ud skulle man få brug for at bruge samme program på en anden db-platform eller lokal persistens.
Altså design efter tyk klient/tynd server

client
  | GUI
  | Model

  Persistens middleware (her er vores broker)
server
  | Persistens (vores DB)
Avatar billede arne_v Ekspert
22. november 2004 - 23:44 #16
nephilim>

Det er meget fint at brugeren får en "bruger venlig" fejl besked. Men hvad så ?
Hvis ikke man kan bruge den til at fixe problemet med, så vil brugeren sikert
hellere copy paste noget "kinesisk" over i en email og så få en løsning
på problemet.

I den lidt mere proffe udgave vil man nok give brugeren en intet sigende
"bruger venlig" fejl, men logge den rigtige fejl til en log fil (log4j eller
lignende), som man så kan bede ham emaile.
Avatar billede nephilim Nybegynder
22. november 2004 - 23:47 #17
i forhold til exception emnet tror jeg at jeg må give mig og sige ja i har nok ret i at de godt kan administrere en getMessage :-)
Avatar billede arne_v Ekspert
22. november 2004 - 23:48 #18
Den form for database klasse er ihvertfald lavet en million gange før, så
helt forkert er det næppe.

Jeg ville nok ligge mere funktionalitet ned i klassen og jeg ville nok
lade metoderne sende exceptions videre fremfor at catche dem.
Avatar billede nephilim Nybegynder
22. november 2004 - 23:54 #19
en anden ide kunne også være at lade klassen stå for transaktions og anden konsistens, eftersom jeg ikke regner med at se mange brugere på systemet kunne du med fordel brugesåkaldt 'optimistisk lås' hvilket betyder at man når man opdaterer en post kun opdaterer hvis timestamp på den post man opdaterer er det samme timestamp som den man hentede.
Kan godt være at det bliver en smule for design ideer nu, men nu du alligevel har klassen her ville det være oplagt at ligge denne funktionalitet her også, det ville samtidig også sørge for at holde selve persistensen og konsistens-samtidighed kontrol på det samme sted.
Avatar billede motyl Nybegynder
23. november 2004 - 00:23 #20
I skal hver især have mange tak for hjælp og gode ideer. Jeg håber at jeg må vende tilbage til denne diskussion, når jeg er kommet et stykke videre i dokumentaionen og programmet. Jeg vil gerne fordele nogle points: 30 til Arne og 15 til nephilim

Hvordan kan jeg fordele points ud til flere?
Avatar billede nephilim Nybegynder
23. november 2004 - 00:42 #21
giv dem til arne, jeg kom ikke rigtig med noget banebrydende
Avatar billede motyl Nybegynder
23. november 2004 - 01:01 #22
Ok, det vil jeg så gøre. Arne skal bare lige skrive tilbage for at indkassere ;)
Avatar billede arne_v Ekspert
23. november 2004 - 07:42 #23
svar kommer her
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Kurser inden for grundlæggende programmering

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester