Datei in einen Binärencode umwandeln und in eine Datenbank einfügen

  • VB.NET

Es gibt 17 Antworten in diesem Thema. Der letzte Beitrag () ist von raist10.

    Datei in einen Binärencode umwandeln und in eine Datenbank einfügen

    Hallo Leute,
    bin neu angefangen mit der Sprache VB.Net und nun tritt für mich ein Problem auf das ich einfach
    nicht gelöst bekomme.

    Folgendes Programm soll eigentlich eine ausgewählte Datei auslesen, in einen binären Code umwandeln
    und dann in eine Datenbank schreiben.

    Quellcode:

    VB.NET-Quellcode

    1. Imports System.Security.Permissions
    2. Imports System
    3. Imports System.Data.SqlClient
    4. Imports System.Data
    5. Imports System.ComponentModel
    6. Imports System.IO
    7. Imports System.Drawing
    8. Imports System.DiagnosticsImports Microsoft.VisualBasic
    9.  
    10. Partial Class _Default
    11. Inherits System.Web.UI.PageProtected Sub Button1_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles Button1.Click
    12. Dim rstream As New FileStream("C:\Users\dRoZ\Desktop\Neues.txt", FileMode.Open, FileAccess.Read)
    13. Dim binreader As New BinaryReader(rstream)Using conn2 As New SqlConnection("Data Source=SVS57;Initial Catalog=Testdatenbank;Integrated Security=True;Pooling=False")
    14. Dim sqlInsert1 As String = "INSERT INTO Binary(File) VALUES ('" & binreader.ReadString & "')"
    15. Try
    16. conn2.Open()Dim sqlCom2 As New SqlCommand(sqlInsert1, conn2)
    17. sqlCom2.ExecuteNonQuery()
    18. Catch ex As Exception
    19. conn2.Close()
    20. End Try
    21. End Using
    22. End Sub
    23.  
    24. End Class




    Nach dem ausführen der Datei erscheint folgende Fehlermeldung:
    "Über das Ende des Streams hinaus kann nicht gelesen werden."

    Die Tabelle in der Datenbank habe ich als binary(8000) konvertiert, aber auch varbinary(max) und varchar(max)
    probiert.

    Ich programmiere mit Visual Studio 2010 und die Datenbank ist Sql Server Managment Stduio 2008 erstellt.

    Ich bitte um Hilfe! ;)
    Deine Datei "C:\Users\dRoZ\Desktop\Neues.txt" hat das falsche Format.
    Erzeuge Dir in Umkehrung eine für BinaryReader() verständliche Dagei und Du wirst sehen:

    VB.NET-Quellcode

    1. Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
    2. Dim rstream As New FileStream("C:\Temp\new2.txt", FileMode.OpenOrCreate, FileAccess.Write)
    3. Using binreader As New BinaryWriter(rstream)
    4. binreader.Write("hhhh1")
    5. binreader.Write("hhhh2")
    6. binreader.Write("hhhh3")
    7. End Using
    8. End Sub

    Die Zeilen erhalten alle ein 7-Bit-Zeichen, das die Länge der Zeile angibt.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Um ein File als Binary einzulesen eignet sich meiner Meinung nach die Methode

    VB.NET-Quellcode

    1. File.ReadAllBytes(strFileName)


    besser.


    Mit MySQL kenne ich mich nicht so sonderlich gut aus kann Dir daher auch nicht sagen welchen DatenTyp Du einstellen musst, aber ich würde mal nach dem Datentyp BLOB gucken ob es den gibt ... wenn ja, dann ist das der richtige. ;)

    EDIT: Habe mir mal gerade die Datentypen von MySQL angesehen da gibt es neben dem einfachen BLOB noch MEDIUMBLOB und LONGBLOB ... der Unterschied liegt nur in der Speichergröße BLOB kann maximal 64 KB aufnehmen, MEDIUMBLOB bis 16 MB und LONGBLOB bis 4 GB. Musst halt entscheiden bis zu welcher Dateigröße Du einlesen willst, reichen 16 MB nicht dann musste LONGBLOB nehmen (kannst aber mit dem Parameter M die maximale Größe in Byte einstellen wenn Du z.B. auf maximal 100 MB begrenzen willst).

    Binäre-Arrays direkt per SQL-Statement mit Insert/Update zu speichern ist selten eine gute Idee. Besser wäre es wenn Du ein Command-Object mit Parametern nutzt und das Binäre-Array als Parameter-Value übergibst.

    Hier mal ein Code-Snipet was ich für SQLite geschrieben habe und das genau das macht was Du vorhast (so in der Art müsste es auch mit MySQL funktionieren):

    VB.NET-Quellcode

    1. Public Function nInsertDokument(ByRef bteArr() As Byte, ByVal intDokID As Int64) As Boolean
    2. Dim SQLCommand As SQLite.SQLiteCommand = Nothing
    3. Dim SQLReader As SQLite.SQLiteDataReader = Nothing
    4. Dim SQLparm As New SQLite.SQLiteParameter("@blob", DbType.Binary)
    5. Dim strSQL As String = "INSERT INTO tbl2Dokumente (DokID, TimeStamp, DokDokument) VALUES (" & intDokID & ", strftime('%Y-%m-%d %H:%M:%S', 'now'), @blob)"
    6. Try
    7. SQLCommand = sLite.CreateCommand
    8. SQLCommand.CommandText = strSQL & ";"
    9. SQLparm.Value = bteArr
    10. SQLCommand.Parameters.Add(SQLparm)
    11. SQLReader = SQLCommand.ExecuteReader
    12. Catch ex As SQLite.SQLiteException
    13. '// Error-Handling
    14. Return Nothing
    15. Finally
    16. SQLparm = Nothing
    17. SQLReader.Close()
    18. SQLReader = Nothing
    19. SQLCommand.Dispose()
    20. SQLCommand = Nothing
    21. End Try
    22. Return AffectedRecords(1) '// Check if 1 row in Database was affected
    23. End Function


    Das Binäre-Array welches übergeben wird ist mit der oben erwähnten Methode File.ReadAllBytes zuvor erzeugt worden.

    Wie gesagt, nutzt jetzt die Methoden aus System.Data.SQLite aber so ähnlich muss das auch mit den Methoden für MySQL funktionieren. ;)

    Hoffe es hilft Dir weiter.

    Gruß

    Rainer

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „raist10“ ()

    RodFromGermany schrieb:

    Deine Datei "C:UsersdRoZDesktopNeues.txt" hat das falsche Format.
    Erzeuge Dir in Umkehrung eine für BinaryReader() verständliche Dagei und Du wirst sehen:

    VB.NET-Quellcode

    1. Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
    2. Dim rstream As New FileStream("C:Tempnew2.txt", FileMode.OpenOrCreate, FileAccess.Write)
    3. Using binreader As New BinaryWriter(rstream)
    4. binreader.Write("hhhh1")
    5. binreader.Write("hhhh2")
    6. binreader.Write("hhhh3")
    7. End Using
    8. End Sub

    Die Zeilen erhalten alle ein 7-Bit-Zeichen, das die Länge der Zeile angibt.


    Sorry, aber daraus werde ich nicht ganz schlau was genau du mir damit sagen/zeigen möchtest.

    Außerdem heißt die Datei nur Neues.txt, ist eigentlich eine absolute Pfad angabe, wurde wohl "verschluckt":(
    @Rainer
    Der Dateityp BLOB ist mir öfters schon im Netz begegnet, scheint aber ein Rainer Sql-Datentyp zu sein (man beachte dieses Wortspielchen), deswegen
    auch mein rumprobieren mit den verschiedenen anderen Datentypen. ;)
    Ich versteh nur nicht was in der Syntax an sich verkehrt ist das er die Datei nicht einliest

    RodFromGermany schrieb:

    VB.NET-Quellcode

    1. Dim rstream As New FileStream("C:\Temp\new2.txt", FileMode.OpenOrCreate, FileAccess.Write)
    Da steht der Pfad.
    Dieser Code hat so, wie er da steht, bei mir funktioniert.
    Bei Deiner C&P-Aktion wurde wohl etrwas verschluckt? :D
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!

    dRoZ schrieb:

    @Rainer
    Der Dateityp BLOB ist mir öfters schon im Netz begegnet, scheint aber ein Rainer Sql-Datentyp zu sein (man beachte dieses Wortspielchen), deswegen


    Es ist natürlich ein DB-Datentyp. BLOB = Binary Long Objects

    Und er ist genau dafür gedacht Binäre Objekte mit unbestimmter Länger aufzunehmen. Alle anderen Datentypen haben so ihre liebe Not mit Byte-Arrays. Daher stelle auf BLOB (oder eben Medium-/Long-Blob) ein und es klappt auch mit der Abspeicherung.

    DB-Datentypen sind immer was anderes als die Datentypen in der Programmiersprache. Sie sind zwar auch quasi dafür gedacht Speicher zu reservieren aber nicht im Stack sondern in der Datenbank.

    Aus dem Grunde der variablen Länge ist es auch nicht möglich Byte-Arrays an ein BLOB-Field per SQL-Statement zu übergeben sondern es kann wie geschrieben nur über einen Parameter erfolgen.

    Ich versteh nur nicht was in der Syntax an sich verkehrt ist das er die Datei nicht einliest


    Die Frage ist doch was willst Du erreichen? Den Inhalt einer Datei als binäres Array auslesen oder die Datei in ihrer Gesamtheit im binären Format abspeichern?

    Willst Du nur Inhalte von Text-Dateien auslesen und abspeichern dann ist die Frage wieso der Umweg über ein binäres Array? Einfach den Datei-Inhalt in einen String einlesen und in die DB als Text abspeichern (DB-Typen: TEXT (64kb), TINYTEXT(255 Byte), MEDIUMTEXT (16 MB), LONGTEXT(4GB)). Das macht auch wegen einer dann möglichen Text-Suche weitaus mehr Sinn.

    Die Abspeicherung als binäres Array würde ich nur empfehlen wenn Du die Datei als komplettes abspeichern willst ... also eher für eine Dokumentenverwaltung als für eine Textverwaltung.

    Gruß

    Rainer
    Ich glaube jetzt kommen wir der Sache näher ;)
    Ich glaub ich habe mich auch etwas missverständlich ausgedrückt.

    Letztenendes möchte ich eine Datenbank verwalten in der Daten eines beliebigen Types, ob nun .pdf, .dox, .xls oder was auch immer, binär abgelegt sind.
    Das Programm ist soweit vollständig fertig so das Daten hochgeladen werden können, benötigte Daten-Infos werden ausgelesen etc. nur das abspeichern
    einer quasi binären Sicherheitskopie funktioniert nicht.
    Als Arbeitsvorgabe wurde mir zudem erteilt ohne Pfade einen Download zu ermöglichen und genau dafür brauche ich ja den BinaryReader, bzw. BinaryWriter
    sofern mich das Internet laut google-Suche nicht belogen hat ;)
    Ich sag ja, bin erst seit 2 Wochen mit VB.net am gange und versteh noch nicht jeden Quellcode.

    Die maximale Größe ist für mich ersteinmal nicht ausschlaggebend.
    Problem ist jedoch das mir das SQL Managment Studio kein BLOB, LONGBLOB oder sonst etwas in der Richtung vorgibt.
    Deswegen bin ich ja den Weg des Vchar(Max) etc. gegangen. :(

    dRoZ schrieb:

    Letztenendes möchte ich eine Datenbank verwalten in der Daten eines beliebigen Types, ob nun .pdf, .dox, .xls oder was auch immer, binär abgelegt sind.


    Dann würde ich Dir empfehlen auf die Methoden File.ReadAllBytes/File.WriteAllBytes umzustellen. Damit funktioniert die Umwandlung jeglichen Dateiformates aus und in ein binäres Array einfach und absolut zuverlässig und zwar völlig Format unabhängig ... selbst EXE-Dateien und ganze Datenbank-Files lassen sich so problemlos in eine Datenbank übernehmen und wieder zurück schreiben.

    Als Arbeitsvorgabe wurde mir zudem erteilt ohne Pfade einen Download zu ermöglichen und genau dafür brauche ich ja den BinaryReader, bzw. BinaryWriter


    Hhhmmm ... wirklich? Die Ausgangsbasis ist doch immer eine Datei im Datei-System ... wie die ins Datei-System kommt ob jetzt dort vorhanden oder per Download hin transferiert ist doch völlig schnuppe. Also quasi Download to Disk -> "C:\Temp\MeineDownloadDatei.xxx -> File.ReadAllBytes("C:\Temp\MeineDownloadDatei.xxx") -> save to Database ... oder verstehe ich Deinen Ablauf nur gerade falsch?

    Ich habe zwar noch nicht viel mit BinaryReader/BinaryWriter rumhantiert aber da die ein Stream-Objekt benötigen das zuerst die Datei öffnet und den Inhalt ausliest dürfte diese Variante für Dich ungeeignet sein. Du brauchst ja die komplette Datei als binäres Array und das geht sauber und zuverlässig mit den oben beschriebenen Methoden der Klasse File.

    dRoZ schrieb:

    Die maximale Größe ist für mich ersteinmal nicht ausschlaggebend.
    Problem ist jedoch das mir das SQL Managment Studio kein BLOB, LONGBLOB oder sonst etwas in der Richtung vorgibt.
    Deswegen bin ich ja den Weg des Vchar(Max) etc. gegangen.


    Au verdammt ... war die ganze Zeit von einem MySQL-Server ausgegangen ... ka wieso. ^^

    In MSSQL ist der passende Datentyp für binäre Arrays mit variabler Größe: varbinary(max) ... max als Parameter da ansonsten die Größe auf 8.000 Byte beschränkt ist. < 8 KB für ein PDF ist so oder so i.d.R. zu wenig.

    Aber egal wie ... für die Übertragung des binären Arrays in die Datenbank MUSST Du mit dem Command-Objekt und einer Parameter-Abfrage arbeiten und das binäre Array als Parameter-Value übergeben ... anders bekommst Du ein binäres Array nicht in die Datenbank rein.

    Gruß

    Rainer

    raist10 schrieb:

    dRoZ schrieb:

    Letztenendes möchte ich eine Datenbank verwalten in der Daten eines beliebigen Types, ob nun .pdf, .dox, .xls oder was auch immer, binär abgelegt sind.


    Dann würde ich Dir empfehlen auf die Methoden File.ReadAllBytes/File.WriteAllBytes umzustellen. Damit funktioniert die Umwandlung jeglichen Dateiformates aus und in ein binäres Array einfach und absolut zuverlässig und zwar völlig Format unabhängig ... selbst EXE-Dateien und ganze Datenbank-Files lassen sich so problemlos in eine Datenbank übernehmen und wieder zurück schreiben.

    Als Arbeitsvorgabe wurde mir zudem erteilt ohne Pfade einen Download zu ermöglichen und genau dafür brauche ich ja den BinaryReader, bzw. BinaryWriter


    Hhhmmm ... wirklich? Die Ausgangsbasis ist doch immer eine Datei im Datei-System ... wie die ins Datei-System kommt ob jetzt dort vorhanden oder per Download hin transferiert ist doch völlig schnuppe. Also quasi Download to Disk -> "C:TempMeineDownloadDatei.xxx -> File.ReadAllBytes("C:TempMeineDownloadDatei.xxx") -> save to Database ... oder verstehe ich Deinen Ablauf nur gerade falsch?

    Ich habe zwar noch nicht viel mit BinaryReader/BinaryWriter rumhantiert aber da die ein Stream-Objekt benötigen das zuerst die Datei öffnet und den Inhalt ausliest dürfte diese Variante für Dich ungeeignet sein. Du brauchst ja die komplette Datei als binäres Array und das geht sauber und zuverlässig mit den oben beschriebenen Methoden der Klasse File.

    dRoZ schrieb:

    Die maximale Größe ist für mich ersteinmal nicht ausschlaggebend.
    Problem ist jedoch das mir das SQL Managment Studio kein BLOB, LONGBLOB oder sonst etwas in der Richtung vorgibt.
    Deswegen bin ich ja den Weg des Vchar(Max) etc. gegangen.


    Au verdammt ... war die ganze Zeit von einem MySQL-Server ausgegangen ... ka wieso. ^^

    In MSSQL ist der passende Datentyp für binäre Arrays mit variabler Größe: varbinary(max) ... max als Parameter da ansonsten die Größe auf 8.000 Byte beschränkt ist. < 8 KB für ein PDF ist so oder so i.d.R. zu wenig.

    Aber egal wie ... für die Übertragung des binären Arrays in die Datenbank MUSST Du mit dem Command-Objekt und einer Parameter-Abfrage arbeiten und das binäre Array als Parameter-Value übergeben ... anders bekommst Du ein binäres Array nicht in die Datenbank rein.

    Gruß

    Rainer


    Als erstes vielen Dank für deine ausführliche Antwort, nun wirds langsam verständlicher für mich! ;)
    Die Ausgangsbasis ist eigentlich eine freidefinierte Datei die via "FileUpload" Funktion ausgesucht wird, daher die Aktionen nach Betätigung des Buttons, hab hier nur
    eine absolute Addressierung gewählt weil der "Uploader" noch nicht implementiert wurde, wird ja wohl am ehesten keine Probleme machen.
    Dann werde ich nun erstmal bei gehen und mich um ein Tutorial, bzw. um eine Einarbeitungshilfe bemühen um das ganze nach deinem Vorschlag mal Umzusetzen! :)

    dRoZ schrieb:

    Die Ausgangsbasis ist eigentlich eine freidefinierte Datei die via "FileUpload" Funktion ausgesucht wird, daher die Aktionen nach Betätigung des Buttons, hab hier nur
    eine absolute Addressierung gewählt weil der "Uploader" noch nicht implementiert wurde, wird ja wohl am ehesten keine Probleme machen.
    Dann werde ich nun erstmal bei gehen und mich um ein Tutorial, bzw. um eine Einarbeitungshilfe bemühen um das ganze nach deinem Vorschlag mal Umzusetzen!


    Da brauchst Du kein Tutorial oder Einarbeitungshilfe ... das ist tierisch simple. ;)

    Hab Dir mal meine obige Funktion inklusive vorheriger Umwandlung der Datei in ein Byte-Array auf System.Data.SqlClient "übersetzt":

    VB.NET-Quellcode

    1. Public Function InsertFileAsByteArrayToDatabase(ByVal strFile As String, _
    2. ByVal intID As Integer) As Boolean
    3. Dim bteArr() As Byte
    4. '// read complete file as byte array
    5. bteArr = System.IO.File.ReadAllBytes(strFile)
    6. Return InsertBteArr(bteArr, intID)
    7. End Function
    8. Public Function InsertBteArr(ByVal bteArr() As Byte, _
    9. ByVal intID As Integer) As Boolean
    10. '// initialize the command-object
    11. Dim cmd As New System.Data.SqlClient.SqlCommand()
    12. '// initialize the paramter-object and sets parameter-name to @blob and datatype to VarBinary
    13. Dim param As New System.Data.SqlClient.SqlParameter("@blob", SqlDbType.VarBinary)
    14. Dim strSQL As String
    15. '// fill sqlstring with SQL-Statement use @blob as paramter-name
    16. '// Table-Field to store byte array: DokDokumente
    17. strSQL = "INSERT INTO tbl2Dokumente (DokID, TimeStamp, DokDokument) VALUES (" & intID & ", strftime('%Y-%m-%d %H:%M:%S', 'now'), @blob)"
    18. '// fill paramter-value with bteArr
    19. param.Value = bteArr
    20. With cmd
    21. '// set active connection (i.e. a private class member that
    22. '//reference the connection object) to command-object
    23. .Connection = aktive Verbindung als System.Data.SqlClient.SqlConnection-Objekt
    24. '// set SQL-Statement as command-text
    25. .CommandText = strSQL
    26. '// add paramter @blob to command-object
    27. .Parameters.Add(param)
    28. '// execute commandobject ... returns number of rows affected
    29. Return (.ExecuteNonQuery = 1)
    30. End With
    31. End Function


    Wie Du siehst absolut simple.

    Da ich nicht weiss wie Du die ID erzeugst, habe ich hier mal vorgesehen das Du als Aufruf das File als "C:\MeinVerzeichnis\MeineDatei.ext" übergibst und dazu die ID unter der der Eintrag erzeugt wird. Lässt du die ID automatisch erzeugen dann kannst Du dir den Parameter natürlich ersparen, genauso wie beim TimeStamp-Field ... SQLlite erzeugt das nicht automatisch (zumindest wenn man nicht RowID auch gleichzeitig als UniqueIdentifier nutzen will) daher sind die beiden Dinge drinnen.

    Gruß

    Rainer
    Moin nochmal, bin nun immernoch mit diesem Thema beschäftigt und es scheint kein Ende zu finden : /

    Habe folgendes Problemchen, nachdem ich die Tipps von raist10 befolgt habe dachte ich das ich fertig wäre,
    schien ja auch alles zu funktioneren, aber nachdem ich nun einen Umwandler von Binär in Ursprungsdatei
    wieder durchführen wollte stellte sich heraus das dort nicht der blob übergeben wurde, sondern
    der Wert "@blob", zu sehen nach der Umwandlung einer .ppt in der auf einmal nur der Wert "@blob"
    drinne stand und 5 Bytes groß war :D

    Hier mal der komplette Upload:

    VB.NET-Quellcode

    1. Imports System.Data.SqlClient
    2. Imports System.Data
    3. Imports System.ComponentModel
    4. Imports System.IO
    5. Imports System.Drawing
    6. Imports System.Diagnostics
    7. Imports Microsoft.VisualBasic
    8. Partial Class _Default
    9. Inherits System.Web.UI.Page
    10. Dim endung() As String
    11. Dim name As String
    12. Dim size As String
    13. Dim folder As String = "Y:Eigene DateienVisual Studio 2010WebSitesWebSite3_1Files" 'Zielordner!
    14. Dim creation As Date
    15. Dim acces As Date
    16. Dim content As String
    17. Protected Sub Button1_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles Button1.Click
    18. Label1.Visible = True
    19. If FileUpload1.HasFile Then
    20. FileUpload1.SaveAs(folder + FileUpload1.FileName)
    21. Label1.Text = FileUpload1.PostedFile.FileName + " erfolgreich hochgeladen!" & Environment.NewLine
    22. Dim strFile As String = FileUpload1.PostedFile.FileName
    23. 'InsertFileAsByteArrayToDatabase(strFile)
    24. 'zeigt den Dateinamen an!
    25. name = FileUpload1.FileName
    26. 'Datei in die Methode FileInfo einlesen!
    27. Dim info As New FileInfo(FileUpload1.PostedFile.FileName)
    28. 'Erstelldatum auslesen
    29. creation = info.CreationTime
    30. 'Letztes Zugriffsdatum auslesen
    31. acces = info.LastAccessTime
    32. 'ContentType
    33. content = FileUpload1.PostedFile.ContentType
    34. Dim sqlRead As String = "SELECT * FROM FILES, INFOS"
    35. 'sqlRead &= " WHERE FILES.ID = INFOS.ID"
    36. Using conn As New SqlConnection("Data Source=EM090;Initial Catalog=File_Datenbank;Integrated Security=True;Pooling=False")
    37. Dim sqlInsert As String = "INSERT INTO Infos(Verzeichnis, Erstelldatum, Zugriff) VALUES ('" & folder & name & "','" & creation.ToString & "','" & acces.ToString & "')"
    38. Using conn1 As New SqlConnection("Data Source=EM090;Initial Catalog=File_Datenbank;Integrated Security=True;Pooling=False")
    39. Try
    40. conn1.Open()
    41. Dim sqlCom1 As New SqlCommand(sqlInsert, conn1)
    42. sqlCom1.ExecuteNonQuery()
    43. Catch ex As Exception
    44. conn1.Close()
    45. End Try
    46. End Using
    47. End Using
    48. endung = Split(name, ".") 'Zerlegt Namen nach ".", bspw. "janna.txt" in "janna" "txt"
    49. size = FileUpload1.PostedFile.ContentLength
    50. InsertFileAsByteArrayToDatabase(strFile)
    51. End If
    52. End Sub
    53. Public Function InsertFileAsByteArrayToDatabase(ByVal strFile As String) As Boolean
    54. Dim bteArr() As Byte
    55. '// read complete file as byte array
    56. bteArr = System.IO.File.ReadAllBytes(strFile)
    57. Return InsertBteArr(bteArr)
    58. End Function
    59. Public Function InsertBteArr(ByVal bteArr() As Byte) As Boolean
    60. '// initialize the command-object
    61. Dim cmd As New System.Data.SqlClient.SqlCommand()
    62. '// initialize the paramter-object and sets parameter-name to @blob and datatype to VarBinary
    63. Dim param As New System.Data.SqlClient.SqlParameter("@blob", SqlDbType.Image)
    64. 'Dim strSQL As String
    65. '// fill sqlstring with SQL-Statement use @blob as paramter-name
    66. '// Table-Field to store byte array: DokDokumente
    67. '// fill paramter-value with bteArr
    68. param.Value = bteArr
    69. Using conn As New SqlConnection("Data Source=EM090;Initial Catalog=File_Datenbank;Integrated Security=True;Pooling=False")
    70. Dim sqlInsert1 As String = "INSERT INTO Files(FileTyp, FileName, FileLink, FileInfo, FileContent, FileObj) VALUES ('" & endung(1) & "','" & endung(0) & "','" & "Files" & name & "','" & size & "','" & content & "','" & "@blob'" & ")"
    71. 'strSQL = "INSERT INTO Files (FileObj) VALUES (" & "'@blob')"
    72. Try
    73. conn.Open()
    74. Dim sqlCom2 As New SqlCommand(sqlInsert1, conn)
    75. sqlCom2.ExecuteNonQuery()
    76. Catch ex As Exception
    77. conn.Close()
    78. End Try
    79. End Using
    80. End Function
    81. End Class


    Ich weiß das es daran liegt das @blob in ein Hochkomma verfasst wurde, jedoch funktioniert sonst die Übergabe nicht, da VB
    einen Wert erwartet :(

    also

    VB.NET-Quellcode

    1. Dim sqlInsert1 As String = "INSERT INTO Files(FileTyp, FileName, FileLink, FileInfo, FileContent, FileObj) VALUES ('" & endung(1) & "','" & endung(0) & "','" & "Files" & name & "','" & size & "','" & content & "','" & @blob & ")"


    funktioniert leider so nicht...

    Lieben Gruß und danke für die bisherige Hilfe! :)
    @ DRoz

    Du hast da auch einen entscheidenden Teil vergessen. ^^

    Nämlich dem Command-Object den erstellten Parameter zu zu weisen. Da Du nun das Command-Object ohne die Parameterzuweisung ausführst, kann der zwangsläufig auch @blob nicht als Placeholder für einen Paramter erkennen und interpretiert das eben als String-Value und verlangt deswegen die Hochkommas.

    Du brauchst noch vor der Ausführung eine Anweisung wie

    VB.NET-Quellcode

    1. sqlCom2.Parameter.Add = param


    Musst aber selber mal gucken da ich mit dem Objektmodell von System.Data.SqlClient noch nicht gearbeitet habe und daher nicht genau weiss wie die Anweisung heisst.

    UND ... NEIN, das ist kein DBType.Image, das ist und bleibt ein DBType.VarBinary ... so hast Du ja auch das Datenfeld in der DB deklariert. Oder nicht?

    Gruß

    Rainer
    Habe nun folgendes versucht:

    VB.NET-Quellcode

    1. ...
    2. Dim param As New System.Data.SqlClient.SqlParameter("@blob", SqlDbType.Image)
    3. SqlCom.Parameters.Add(New SqlParameter("@blob", SqlDbType.Image))
    4. SqlCom.Parameters("@blob").Value = param.Value
    5. ...

    Müsste ja eigentlich das sein was du meintest, hilft aber auch nicht :pinch:
    Hhhmmm ... tief einatmen, langsam bis zehn zählen, im Sessel zurück lehnen und nochmal nachdenken. ;)

    Wieso hälst Du Dich nicht an den Code-Vorschlag den ich Dir bereits im Post 10 gepostet hatte? Wenn Du immer willkürlich irgendwas anderes machst als ich Dir gepostet habe, dann kann er auch nie funktionieren.

    Und nochmal ... ein Byte-Array ist KEIN SqlDbType.Image sondern es ist und bleibt ein SqlDbType.VarBinary ... wie oft noch? ;)

    Gruß

    Rainer
    Hhhmmm ... tief einatmen, langsam bis zehn zählen, im Sessel zurück lehnen und nochmal nachdenken.

    Wieso hälst Du Dich nicht an den Code-Vorschlag den ich Dir bereits im Post 10 gepostet hatte? Wenn Du immer willkürlich irgendwas anderes machst als ich Dir gepostet habe, dann kann er auch nie funktionieren.

    Und nochmal ... ein Byte-Array ist KEIN SqlDbType.Image sondern es ist und bleibt ein SqlDbType.VarBinary ... wie oft noch?

    Gruß

    Rainer


    Also ich weiß nicht was ich falsch mache, bzw. wo ich mich nicht an deinen Vorschlag halte, ich meine klar, ich habe natürlich ein paar modifikationen vorgenommen um halt auch genau
    meine Dateien zu übertragen, aber der Aufbau und der Ablauf sind nahezu identisch.
    Außerdem ist es der Datentyp Image da dies eine maximale Größe der Dateien von ~2 Gigabyte erlaubt, varbinary lediglich ~8 Kilobyte!

    Ich habe ja gesagt das ich wirklich ein Neuling in VB.NET bin :P

    Hoffe du nimmst dir vielleicht doch nochmal Zeit und guckst dir an was falsch sein könnte ;)

    Habs auch probiert mit:

    VB.NET-Quellcode

    1. ...
    2. Dim param As New System.Data.SqlClient.SqlParameter("@blob", SqlDbType.Image)
    3. SqlCom.CommandType = CommandType.StoredProcedure
    4. SqlCom.Parameters.Add(New SqlParameter("@blob", SqlDbType.Image))
    5. SqlCom.Parameters("@blob").Value = param.Value
    6. ...


    Irgendwas möchte er einfach nicht haben :(

    dRoZ schrieb:


    ... ich meine klar, ich habe natürlich ein paar modifikationen vorgenommen um halt auch genau
    meine Dateien zu übertragen, aber der Aufbau und der Ablauf sind nahezu identisch


    Das einzige was Deine Änderungen bewirkt haben ist das der Code nicht funktioniert. Wenn Du ein Code-Snippet nutzt/bekommst dann arbeite erstmal exakt 1 zu 1 mit dem Teil solange bis Du es verstanden hast was genau passiert. Und dann erst machst Du Änderungen ... aber nur 1 auf einmal. Danach testen ob der Code immer noch funktioniert und macht was er soll, wenn ja dann kannst Du die nächste Änderung einbauen wenn nein Ursache erforschen wieso Deine erste Änderung nicht funktioniert hat und bereinigen.

    Hoffe du nimmst dir vielleicht doch nochmal Zeit und guckst dir an was falsch sein könnte ;)


    Ja, aber ehrlich ... zum letzten Mal. Wenn Du dann wieder den Code von mir frei Schnauze abänderst und Dich wunderst warum es immer noch nicht läuft, dann mag ich nicht mehr. ^^

    Ich helfe Dir hier nach erst wieder wenn Du meinen code so eingebaut hast das er funzt, also quasi bei den Änderungen danach helfe ich wieder.

    Also gut ... hier nochmal:

    VB.NET-Quellcode

    1. ...
    2. '// hier wird das Parameter-Objekt erzeugt und zwar als VARBINARY und NICHTS anderes ... wenn Du das nochmal auf Image abänderst hau ich Dich
    3. '// eh klar, dass das Field in der Datenbank auch als VarBinary(max) deklariert sein muss
    4. Dim param As New System.Data.SqlClient.SqlParameter("@blob", SqlDbType.VARBINARY)
    5. '// hier bekommt das Parameter-Objekt als Wert das Byte-Array zugewiesen
    6. param.Value = bteArr()
    7. '// nun wird das erzeugte Parameter-Objekt dem Command-Objekt zugewiesen
    8. SqlCom.Parameters.Add = param
    9. ...


    Ist doch absolut simple. ;)

    Halte Dich jetzt aber bittte einfach mal genau an das was ich Dir hier poste.

    Gruß

    Rainer
    So,
    hab nun den Fehler gefunden und es funktioniert nun einwandfrei...
    Hattest recht, ich hätte nach und nach deinen Code ausbauen sollen
    anstatt meinen vorherigen mit deinen zu mixen ;)

    Hab einfach ganz stumpf deinen Code kopiert, etwas editiert
    dann ausprobiert (mit deinem VarBinary :P ) und es funktionierte.

    Nun im "großen" Code implementiert ( mit meinem Image :whistling: ) und
    es funktioniert! ;)

    Vielen Dank für deine Hilfe :love:

    Nun im "großen" Code implementiert ( mit meinem Image :whistling: ) und
    es funktioniert!


    Das wundert mich jetzt allerdings schon. Aber gut ... wenn es funzt dann funzt es.

    Sollte es doch irgendwann mal Probleme geben, dann weisst Du ja zumindest schonmal woran es liegen könnte. *g*

    Gruß

    Rainer