BITTE helfen Sie uns HEUTE mit einer SPENDE
Helfen Sie das LibreOffice Forum zu erhalten!

❤️ DANKE >><< DANKE ❤️

> KEINE WERBUNG FÜR REGISTRIERTE BENUTZER!<
Ihre Spende wird für die Deckung der laufenden Kosten sowie den Erhalt und Ausbau 🌱 des LibreOffice Forums verwendet.
🤗 Als Dankeschön werden Sie im Forum als LO-SUPPORTER gekennzeichnet. 🤗

(gelöst) Daten einer Calc/Exel-Tabelle per Makro importieren

Base ermöglicht es Ihnen, Ihre Daten in einer Datenbank direkt mit LibreOffice zu bearbeiten.
Stegull
Beiträge: 37
Registriert: Di 6. Dez 2022, 13:36

Re: (gelöst) Daten einer Calc/Exel-Tabelle per Makro importieren

Beitrag von Stegull » Di 17. Jan 2023, 21:47

Da erscheint diese Fehlermeldung:
Dateianhänge
2.JPG
2.JPG (25.01 KiB) 662 mal betrachtet

Wanderer
Beiträge: 895
Registriert: Di 11. Feb 2014, 20:03
Wohnort: Berlin

Re: (gelöst) Daten einer Calc/Exel-Tabelle per Makro importieren

Beitrag von Wanderer » Mi 18. Jan 2023, 08:15

Stegull hat geschrieben:
Di 17. Jan 2023, 21:47
Da erscheint diese Fehlermeldung:
Das ist leider nicht die Fehlermeldung, sondern die Stelle an der der Fehler auftritt.

Da es wahrscheinlich um das Sql-Kommando ist, würde ich direkt davor stSql per MsgBox anzeigen lassen um herauszufinden was da falsch läuft.

Mfg, Jörn
LO 6.0.7 (32Bit) Win8.1 Pro 32 Bit/ LO 6.3.2 Win10 64Bit / LO 6.0.7 Win7 Pro 64 Bit

RobertG
Beiträge: 2732
Registriert: Sa 19. Mai 2012, 17:37
Kontaktdaten:

Re: (gelöst) Daten einer Calc/Exel-Tabelle per Makro importieren

Beitrag von RobertG » Mi 18. Jan 2023, 11:29

Die Fehler jetzt kommt daher, dass die Abfrage so
SELECT MAX("ID") FROM "Sheet"
lautet, weil die beiden Parameter für die Tabelle in der Tabellenkalkulation und der Datenbank vertauscht sind. Die Tabelle "Sheet" hast Du mit Sicherheit nicht in der Datenbank. Also Parameter 2 und 3 in Import1_Start vertauschen, damit die Tabellenbezeichnungen stimmen.
https://de.libreoffice.org/get-help/documentation/
https://www.familiegrosskopf.de/robert/index.php?&Inhalt=base_handbuch
https://www.familiegrosskopf.de/robert/index.php?&Inhalt=xml_formulare

Stegull
Beiträge: 37
Registriert: Di 6. Dez 2022, 13:36

Re: (gelöst) Daten einer Calc/Exel-Tabelle per Makro importieren

Beitrag von Stegull » Mi 18. Jan 2023, 13:59

Erstmal Danke für Eure Mühe,

Robert, die importierten Tabellen beinhalten keine "ID". Kann das daran liegen?

Mit den von Dir korrigierten/vertauschten Parametern:

Code: Alles auswählen

SUB Import1_Start(oEvent AS OBJECT)
        CalcDataImport(oEvent, "tbl_Auf_Dat",  "Sheet", "Auftragliste.xlsx")
        CalcDataImport(oEvent, "Daten", "Sheet", "Auftragdetailliste.xlsx")
END SUB


Sub CalcDataImport(oEvent AS OBJECT, stBaseTab AS STRING, stCalcTab AS STRING, stCalc AS STRING)
	DIM oDatasource AS OBJECT
	DIM oConnection AS OBJECT
	DIM oSQL_Command AS OBJECT
	DIM oResult AS OBJECT
	DIM oDB AS OBJECT
	DIM oDoc AS OBJECT
	DIM oDocView AS OBJECT
	DIM oRange AS OBJECT
	DIM Arg()
	DIM aColumn()
	DIM aColumns()
	DIM aType()
	DIM stSql AS STRING
	DIM stRow AS STRING
	DIM stDir AS STRING
	DIM stColumns AS STRING
	DIM stStartCol AS STRING
	DIM stEndCol AS STRING
	DIM stStartRow AS STRING
	DIM stEndRow AS STRING
	DIM stRange AS STRING
	DIM inCounter AS INTEGER
	DIM loColumns AS LONG
	DIM loRows AS LONG
	DIM loID AS LONG
	oDatasource = ThisComponent.Parent.CurrentController
	If NOT (oDatasource.isConnected()) THEN
		oDatasource.connect()
	END IF
	oConnection = oDatasource.ActiveConnection()
	oSQL_Command = oConnection.createStatement()
	' Spaltennamen und Spaltentypen aus der Tabelle der Datenbank auslesen. "ID" ist als Primärschlüssel vorgesehen.
	stSql = "SELECT COLUMN_NAME, TYPE_NAME FROM INFORMATION_SCHEMA.SYSTEM_COLUMNS WHERE TABLE_NAME = '"+stBaseTab+"' AND NOT COLUMN_NAME = 'ID'"
	oResult = oSQL_Command.executeQuery(stSql)
	inCounter = 0
	stColumns = ""
	' Spaltennamen und Spaltentypen in getrennten Arrays speichern. Ginge auch in einem zweidimensionalen Array
	WHILE oResult.next
		ReDim Preserve aColumn(inCounter)
		ReDim Preserve aType(inCounter)
		aColumn(inCounter) = oResult.getString(1)
		aType(inCounter) = oResult.getString(2)
		inCounter = inCounter+1
	WEND
	stSql = "SELECT MAX(""ID"") FROM """+stBaseTab+""""
	oResult = oSQL_Command.executeQuery(stSql)
	WHILE oResult.next
		loID = oResult.getInt(1) + 1
	WEND
	' Pfad zur Calc-Datei ermitteln. Liegt hier im gleichen Verzeichnis wie die Datenbankdatei
	oDB = ThisComponent.Parent
	stDir = Left(oDB.Location,Len(oDB.Location)-Len(oDB.Title))
	stDir = ConvertToUrl(stDir & stCalc)
	' Calcdatei laden und auf unsichtbar schalten
	oDoc = StarDesktop.loadComponentFromURL(stDir,"_blank", 0, Arg() )
	oDocView = oDoc.CurrentController.Frame.ContainerWindow
	oDocView.Visible = False
	' Position des beschrifteten Bereichs im Tabellenblatt ermitteln
	loColumns = uBound(oDoc.Sheets(0).ColumnDescriptions)	' Anzahl der Spalten
	stStartCol = split(oDoc.Sheets(0).ColumnDescriptions(0))(1)
	stEndCol = split(oDoc.Sheets(0).ColumnDescriptions(loColumns))(1)
	loRows = uBound(oDoc.Sheets(0).RowDescriptions)	' Anzahl der Zeilen
	stStartRow = split(oDoc.Sheets(0)).RowDescriptions(0)(1)
	stEndRow = split(oDoc.Sheets(0)).RowDescriptions(loRows)(1)
	stRange = stStartCol & stStartRow & ":" & stEndCol & StEndRow
	' Beschrifteten Bereich als Datenquelle nutzen. Dabei wird davon ausgegangen, dass in der ersten beschrifteten Zeile die Spaltennamen stehen
	oRange = oDoc.Sheets(0).getCellRangeByName(stRange)
	aDat = oRange.getDataArray()
	' Spaltennamen stehen in der ersten Zeile und können eine andere Reihenfolge haben als in der Tabelle der Datenbank.
	aColumns = aDat(0)
	FOR i = 1 TO uBound(aDat)	'0 wären die Spaltenüberschriften
		aRow = aDat(i)
		stColumns = """ID"""
		stRow = loID
		FOR k = 0 TO loColumns
			FOR n = 0 TO uBound(aColumn)
				IF aColumns(k) = aColumn(n) THEN	' Nur Spalten, die in der Datenbank mit gleichem Namen vorhanden sind, werden auch eingelesen.
					IF aType(n) = "DECIMAL" THEN
						IF aRow(k) <> "" THEN
							aRow(k) = Str(CDbl(aRow(k)))
						END IF
					END IF
					IF aType(n) = "DATE" THEN 'Datumsfeld
						IF isDate(CDate(aRow(k))) AND aRow(k) <> "" THEN
							aRow(k) = Year(CDate(aRow(k))) & "-" & Right("0" & Month(CDate(aRow(k))), 2) & "-" & Right("0" & Day(CDate(aRow(k))), 2)
						ELSE
							aRow(k) = ""
						END IF
					END IF
					IF aType(n) = "TIME" THEN 'Zeitfeld
						IF isDate(CDate(aRow(k))) AND aRow(k) <> "" THEN
							aRow(k) = Right("0" & Hour(CDate(aRow(k))), 2) & ":" & Right("0" & Minute(CDate(aRow(k))), 2) & ":" & Right("0" & Second(CDate(aRow(k))), 2)
						ELSE						
							aRow(k) = ""
						END IF
					END IF
					IF aType(n) = "TIMESTAMP" THEN 'Datum und Zeit
						IF isDate(CDate(aRow(k))) AND aRow(k) <> "" THEN
							aRow(k) = Year(CDate(aRow(k))) & "-" & Right("0" & Month(CDate(aRow(k))), 2) & "-" & Right("0" & Day(CDate(aRow(k))), 2) & " " & Right("0" & Hour(CDate(aRow(k))), 2) & ":" & Right("0" & Minute(CDate(aRow(k))), 2) & ":" & Right("0" & Second(CDate(aRow(k))), 2)
						ELSE						
							aRow(k) = ""
						END IF
					END IF
					IF aRow(k) = "" THEN
						aRow(k) = "NULL"
					ELSE
						aRow(k) = "'" & aRow(k) & "'"
					END IF
					stRow = stRow & "," & aRow(k)
					stColumns = stColumns & ",""" & aColumns(k) & """"
				END IF
			NEXT
		NEXT
		stSql = "INSERT INTO """+stBaseTab+""" ("& stColumns &") VALUES ("& stRow &")"
		oSQL_Command.executeUpdate(stSql)
		loID = loID + 1
	NEXT
	oDoc.close(True)	' Schließen des Calc-Documentes
	oEvent.Source.Model.parent.reload()	' Neuladen des Formulars
End Sub
wird dieser Fehler gemeldet:
Dateianhänge
11.JPG
11.JPG (26.51 KiB) 641 mal betrachtet

RobertG
Beiträge: 2732
Registriert: Sa 19. Mai 2012, 17:37
Kontaktdaten:

Re: (gelöst) Daten einer Calc/Exel-Tabelle per Makro importieren

Beitrag von RobertG » Mi 18. Jan 2023, 17:35

Wenn Du bereits dabei stehen bleibst, dass die Datenquelle nicht erkannt wird, dann hast Du das Makro nicht von der Base-Datei aus ausgelöst. Das Makro ist aber so gedacht, dass es aus einem Formular heraus durch eine Schaltfläche ausgelöst wird.
Startest Du das Makro z.B. aus dem Makroeditor, so ist "thisComponent" der Makroeditor. Und der kann die Datenbankverbindung so nicht auslesen.

Das Feld "ID" muss lediglich in den Datenbanktabellen vorhanden sein. Das Feld beinhaltet (auch in der Beispieldatenbank) den Primärschlüssel. Bei den Tabellen aus Calc heraus wird so ein Feld nicht erwartet.
https://de.libreoffice.org/get-help/documentation/
https://www.familiegrosskopf.de/robert/index.php?&Inhalt=base_handbuch
https://www.familiegrosskopf.de/robert/index.php?&Inhalt=xml_formulare

An alle, die das LibreOffice-Forum nutzen:


Bitte beteiligen Sie sich mit 7 Euro pro Monat und helfen uns bei unserem Budget für das Jahr 2024.
Einfach per Kreditkarte oder PayPal.
Als Dankeschön werden Sie im Forum als LO-SUPPORTER gekennzeichnet.

❤️ Vielen lieben Dank für Ihre Unterstützung ❤️

Antworten