package de.nplusc.izc.tools.IOtools;


import de.nplusc.izc.tools.baseTools.Tools;
import java.sql.*;
import java.util.LinkedList;

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

/**
 *
 * @author LH
 */
public class DBWriter
{
Connection cn = null;
ResultSet rs=null;


    /**
     * Datenbankverbindung aufbauen
     * @param host Server der DB mit port(standard=3306
     * @param db Datenbnak auf server
     * @param user Username
     * @param pw Passy
     */
    public DBWriter(String host,String db,String user,String pw)
    {
        
        try {
        // Select fitting database driver and connect:
        Class.forName("com.mysql.jdbc.Driver");
        cn = DriverManager.getConnection( "jdbc:mysql://"+host+"/"+db+"",user,pw);
        }
        catch(ClassNotFoundException | SQLException e)
        {
            e.printStackTrace();
        }
    }
    
    /**
     * Führt Spaltenweise Abfrage aus
     * @param Query
     * @return Array des Ergebnisses (eine zeile pro feld)
     */
    public String[] querySIngleColumn(String Query)
    {
        rs=null;
        LinkedList<String> masterList = new LinkedList<>();
       // masterList.
        Tools.DebugHelperPrint(Query, true, "Toolkit.enableCoreDebug");
        try{
        Statement st = cn.createStatement();
        rs = st.executeQuery(Query);
        if(rs!=null)
        {
            while(rs.next())
            {
                try
                {
                masterList.add(rs.getString(1));
            
                }
                catch(Exception e)
                {
                    return null;
                }
            }
            rs.close();
            return masterList.toArray(new String[0]);
            
        }
        }
        catch (Exception e)
        {
            return null;
        }
        return null;
    }
    
    
    /**
     * Führt einzelwertabfrage aus
     * @param Query Abfrage
     * @return der Wert
     */
    public String querySingleCell(String Query)
    {
        rs=null;
        Tools.DebugHelperPrint(Query, true, "Toolkit.enableCoreDebug");
        try{
        Statement st = cn.createStatement();
        rs = st.executeQuery(Query);
        if(rs!=null)
        {
            while(rs.next())
            {
                try
                {
                return rs.getString(1);
            
                }
                catch(Exception e)
                {
                    return null;
                }
            }
            rs.close();
        }
        }
        catch (Exception e)
        {
            return null;
        }
        return null;
    }
    
     
    /**
     * Führt Zeilenweise Abfrage aus
     * @param Query
     * @return Array des Ergebnisses (eine Spalte pro feld)
     */
    public String[] querySingleRow(String Query)
    {
        rs=null;
        try
        {
            
            Statement st = cn.createStatement();
            rs = st.executeQuery(Query);
            return querySingleRow(Query, rs.getMetaData().getColumnCount(), true);
        }
        catch (SQLException ex)
        {
            ex.printStackTrace();
            return null;
        }
        
        
    }
    
    /**
     * Abfrage auf eine reihe mit erwarteter SPaltenzahl
     * @param Query Abfrage
     * @param cols Spaltenzahl
     * @return Eregebnis
     */
    
    public String[] querySingleRow(String Query,int cols)
    {
        return querySingleRow(Query, cols, false);
    }
    
    
    
    private String[] querySingleRow(String Query,int cols,boolean delivRS)
    {
        if(delivRS=false)
            rs=null;
        LinkedList<String> masterList = new LinkedList<>();
       // masterList.
        Tools.DebugHelperPrint(Query, true, "Toolkit.enableCoreDebug");
        try
        {
            Statement st =null;
            if(!delivRS)
                st = cn.createStatement();
                rs = st.executeQuery(Query);
            if(rs!=null)
            {
                while(rs.next())
                {
                    try
                    {
                        for (int i = 1; i <= cols; i++)
                        {
                            masterList.add(rs.getString(i));
                        }
                    }
                    catch(Exception e)
                    {
                        return null;
                    }
                }
                rs.close();
                return masterList.toArray(new String[0]);

            }
        }
        catch (Exception e)
        {
            return null;
        }
        return null;
    }
    
    
    
       /**
     * Abfrage auf tabelle
     * @param Query Abfrage
     * @return Eregebnis ZEile,dann spalte in arrray
     */
    public String[][] queryTable(String Query)
    {
        rs=null;
        try
        {
            
            Statement st = cn.createStatement();
            rs = st.executeQuery(Query);
            return queryTable(Query, rs.getMetaData().getColumnCount(), true);
        }
        catch (SQLException ex)
        {
            ex.printStackTrace();
            return null;
        }
        
        
    }
    
       /**
     * Abfrage auf Tabelle mit aerwarteter Spaltenzahl
     * @param Query Abfrage
     * @param cols Spaltenzahl
     * @return Eregebnis ZEile,dann spalte in arrray
     */
    public String[][] queryTable(String Query,int cols)
    {
        return queryTable(Query, cols, false);
    }
    
    
    
    
    
    private String[][] queryTable(String Query,int cols,boolean delivRS)
    {
        if(delivRS=false)
            rs=null;
        LinkedList<String> RowList = new LinkedList<>();
        LinkedList<String[]> masterList = new LinkedList<>();
       // masterList.
        Tools.DebugHelperPrint(Query, true, "Toolkit.enableCoreDebug");
        try
        {
            Statement st =null;
            if(!delivRS)
                st = cn.createStatement();
                rs = st.executeQuery(Query);
            if(rs!=null)
            {
                while(rs.next())
                {
                    try
                    {
                        for (int i = 1; i <= cols; i++)
                        {
                            RowList.add(rs.getString(i));
                        }
                    }
                    catch(Exception e)
                    {
                        return null;
                    }
                }
                rs.close();
                masterList.add(RowList.toArray(new String[0]));
            }
        }
        catch (Exception e)
        {
            return null;
        }
        String[] retvaltmp =  masterList.toArray(new String[0][0])[0];//hatmit nem ekligen Bug zu tun
        int sizetmp = retvaltmp.length;
        int sizet = sizetmp/cols;
        String[][]retvals = new String[sizet][cols];
        for (int i = 0; i < sizet; i++)
        {
            for (int j = 0; j < cols; j++)
            {
                retvals[i][j] = retvaltmp[i*cols+j];
                
            }
        }
        return retvals;
        
    }
    
    
    /**
     * Schreibende abfrage (unterdrückt exception
     * @param query Abfrage
     * @return erfolgsstatus
     */
    
    public boolean write(String query)
    {
        try{
        return write(query,false);
        }
        catch(Exception e)
        {
            return false;
        }
    }
    /**
     * Schreibt in DB
     * @param query abfrage
     * @param passthroughException ob exception unterdrückt werden soll
     * @return Erfolgsfall
     * @throws Exception bei Error in Query
     */
    
    public boolean write(String query,boolean passthroughException) throws Exception
    {
        return write(query,passthroughException,false);
    }
    
        /**
     * Schreibt in DB
     * @param query abfrage
     * @param passthroughException ob exception unterdrückt werden soll
     * @param erroutwhenzeroedited ob except wenn kein datensatz bearbeitet
     * @return Erfolgsfall
     * @throws Exception bei Error in Query
     */
    
    @SuppressWarnings("CallToThreadDumpStack")
    public boolean write(String query,boolean passthroughException,boolean erroutwhenzeroedited) throws Exception
    {
        boolean ret = true;
        Tools.DebugHelperPrint(query, true, "Toolkit.enableCoreDebug");
        try 
        {
            Statement st = cn.createStatement();
            int rs = st.executeUpdate(query);
            if(rs==0)
                ret=false;
      
        }
        catch(Exception e)
        {
            e.getMessage();
            e.printStackTrace();
            //System.err.println("FF");
            Tools.DebugHelperPrint("FF", true, "Toolkit.enableFinerDebug");
            ret= false;
        }
        if(passthroughException && !ret)
        {
            //Integer.valueOf()
            throw new Exception();
        }
        
        return ret;

    }
    /**
     * schließt connex
     */
    public void closeConn()
    {
        try
        {
            cn.close();
        }
        catch (SQLException ex)
        {
            Tools.DebugHelperPrint("DB.close()->fail", true, "Toolkit.enableCoreDebug");
        }
    }
    
    
    /**
     * rückt spaltenzahl letzter abfrage raus
     * @return spaltenzahl
     */
    public int getColCount()
    {
        try
        {
            ResultSetMetaData md = rs.getMetaData();
            return md.getColumnCount();
        }
        catch (SQLException ex)
        {
            return -1;
        }
    }
    
    /**
     * rückt kopfzeile letzter abfrage raus
     * @return kopfzeile
     */
    public String[] getHeadlines()
    {
        try
        {
            ResultSetMetaData md = rs.getMetaData();
            int mc = md.getColumnCount();
            String[] ret = new String[mc];
            for (int i=0;i<mc;i++)
            {
                ret[i] = md.getColumnName(i);
            }
            return ret;
        }
        catch (SQLException ex)
        {
            Tools.DebugHelperPrint("Fikk", true, "Toolkit.enableCoreDebug");
            return null;
        }
    }
}
