Code: Select all
; Import a previously exported or other addresses list
Procedure ImportAddresses()
Structure Contact
contacttype.s
contactdetails.s
EndStructure
Structure AddressItem
Titlename.s
Firstname.s
Middlename.s
Lastname.s
Business.s
Nickname.s
Customname.s
Pobox.s
Street.s
Suburb.s
City.s
State.s
Postcode.s
Country.s
Displayformat.s
Displayas.s
Ownername.s
Category.s
Comment.s
Picture.s
Label.s
Favourite.s
Locked.s
Deleted.s
Updated.s
Recordid.s
List ContactList.Contact()
EndStructure
Structure AddressBook
List AddressList.AddressItem()
EndStructure
Protected.i XMLImportFileHandle.i, DetectionState.i, ImportCounter.i
Protected XMLImportFilename.s, LineToProcess.s, PictureString.s
Protected AddressItem.AddressItem
XMLImportFilename.s = OpenFileRequester("Choose an export file to import", "", "XML|*.xml", 0)
ImportCounter.i = #NoItems
If XMLImportFilename.s
XMLImportFileHandle.i = ReadFile(#PB_Any, XMLImportFilename.s)
If XMLImportFileHandle.i
While Not Eof(XMLImportFileHandle.i)
LineToProcess.s = XMLToText(LTrim(ReadString(XMLImportFileHandle.i, #PB_UTF8)))
Select DetectionState.i
Case 0 ; Address book item
Select Left(LineToProcess.s, 5)
Case "<Titl" : AddressItem\Titlename = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Firs" : AddressItem\Firstname = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Midd" : AddressItem\Middlename = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Last" : AddressItem\Lastname = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Busi" : AddressItem\Business = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Nick" : AddressItem\Nickname = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Cust" : AddressItem\Customname = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Pobo" : AddressItem\Pobox = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Stre" : AddressItem\Street = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Subu" : AddressItem\Suburb = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<City" : AddressItem\City = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Stat" : AddressItem\State = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Post" : AddressItem\Postcode = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Coun" : AddressItem\Country = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Disp"
If Left(LineToProcess.s, 9) = "<Displayf"
AddressItem\Displayformat = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Else
AddressItem\Displayas = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
EndIf
Case "<Owne" : AddressItem\Ownername = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Cate" : AddressItem\Category = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Comm" : AddressItem\Comment = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Pict" : PictureString.s = "" : DetectionState.i = 1
Case "<Labe" : AddressItem\Label = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Favo" : AddressItem\Favourite = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Lock" : AddressItem\Locked = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Dele" : AddressItem\Deleted = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Upda" : AddressItem\Updated = RepQuote(GetPartBetweenBrackets(LineToProcess.s))
Case "<Cont" : ClearList(AddressItem\ContactList()) : DetectionState.i = 2
Case "</ele"
; Add to AddressBook at this point
If AddressItem\Picture <> #EmptyString
Debug "Picture data found, Processing"
ActualStringLength.i = StringByteLength(AddressItem\Picture, #PB_Ascii)
Debug "Actual picture length: " + Str(ActualStringLength.i)
; *DecodeBuffer = AllocateMemory(ActualStringLength.i)
; *DecodeBuffer = AllocateMemory(ActualStringLength.i + (ActualStringLength.i / 30))
*DecodeBuffer = AllocateMemory(ActualStringLength.i + (ActualStringLength.i / 2) + SizeOf(character))
If MemorySize(*DecodeBuffer)
Debug "Decoding buffer: " + Str(*DecodeBuffer)
*OutputBuffer = AllocateMemory(ActualStringLength.i)
If MemorySize(*OutputBuffer)
Debug "Output buffer: " + Str(*OutputBuffer)
BytesPoked.i = PokeS(*DecodeBuffer, AddressItem\Picture, ActualStringLength.i, #PB_Ascii | #PB_String_NoZero)
If BytesPoked.i <> #NoData
Debug "Bytes poked: " + Str(BytesPoked.i)
ActualBytesDecoded.i = Base64Decoder(*DecodeBuffer, ActualStringLength.i, *OutputBuffer, ActualStringLength.i)
If ActualBytesDecoded.i
Debug "Bytes decoded: " + Str(ActualBytesDecoded.i)
SetDatabaseBlob(Program\DatabaseHandle, 0, *OutputBuffer, ActualBytesDecoded.i)
Else
SetInfobarArea("Headings", "Error", "Could not decode the picture string back to picture data", "ImportAddresses")
EndIf
Else
SetInfobarArea("Headings", "Error", "Could not poke the picture string into the decode buffer", "ImportAddresses")
EndIf
; FreeMemory(*OutputBuffer)
EndIf
FreeMemory(*DecodeBuffer)
EndIf
Debug "==============================================================================================================="
AddressItem\Picture = ""
DatabaseUpdate.s = "INSERT INTO Addresses("
DatabaseUpdate.s + "Titlename, Firstname, Middlename, Lastname, Business, Nickname, "
DatabaseUpdate.s + "Customname, Pobox, Street, Suburb, City, State, Postcode, Country, "
DatabaseUpdate.s + "Displayformat, Displayas, Ownername, Category, Comment, Picture, Label, "
DatabaseUpdate.s + "Favourite, Locked, Deleted, Updated) "
DatabaseUpdate.s + "VALUES('" + AddressItem\Titlename + "', '" + AddressItem\Firstname + "', '" + AddressItem\Middlename
DatabaseUpdate.s + "', '" + AddressItem\Lastname + "', '" + AddressItem\Business + "', '" + AddressItem\Nickname
DatabaseUpdate.s + "', '" + AddressItem\Customname + "', '" + AddressItem\Pobox + "', '" + AddressItem\Street
DatabaseUpdate.s + "', '" + AddressItem\Suburb + "', '" + AddressItem\City + "', '" + AddressItem\State
DatabaseUpdate.s + "', '" + AddressItem\Postcode + "', '" + AddressItem\Country + "', '" + AddressItem\Displayformat
DatabaseUpdate.s + "', '" + AddressItem\Displayas + "', '" + AddressItem\Ownername + "', '" + AddressItem\Category
DatabaseUpdate.s + "', '" + AddressItem\Comment + "', " + "?, '" + AddressItem\Label
DatabaseUpdate.s + "', '" + AddressItem\Favourite + "', '" + AddressItem\Locked + "', '" + AddressItem\Deleted
DatabaseUpdate.s + "', '" + AddressItem\Updated + "')"
Else
DatabaseUpdate.s = "INSERT INTO Addresses("
DatabaseUpdate.s + "Titlename, Firstname, Middlename, Lastname, Business, Nickname, "
DatabaseUpdate.s + "Customname, Pobox, Street, Suburb, City, State, Postcode, Country, "
DatabaseUpdate.s + "Displayformat, Displayas, Ownername, Category, Comment, Label, "
DatabaseUpdate.s + "Favourite, Locked, Deleted, Updated) "
DatabaseUpdate.s + "VALUES('" + AddressItem\Titlename + "', '" + AddressItem\Firstname + "', '" + AddressItem\Middlename
DatabaseUpdate.s + "', '" + AddressItem\Lastname + "', '" + AddressItem\Business + "', '" + AddressItem\Nickname
DatabaseUpdate.s + "', '" + AddressItem\Customname + "', '" + AddressItem\Pobox + "', '" + AddressItem\Street
DatabaseUpdate.s + "', '" + AddressItem\Suburb + "', '" + AddressItem\City + "', '" + AddressItem\State
DatabaseUpdate.s + "', '" + AddressItem\Postcode + "', '" + AddressItem\Country + "', '" + AddressItem\Displayformat
DatabaseUpdate.s + "', '" + AddressItem\Displayas + "', '" + AddressItem\Ownername + "', '" + AddressItem\Category
DatabaseUpdate.s + "', '" + AddressItem\Comment + "',' " + AddressItem\Label
DatabaseUpdate.s + "', '" + AddressItem\Favourite + "', '" + AddressItem\Locked + "', '" + AddressItem\Deleted
DatabaseUpdate.s + "', '" + AddressItem\Updated + "')"
EndIf
Debug DatabaseUpdate.s
If DatabaseUpdate(Program\DatabaseHandle, DatabaseUpdate.s) <> #DatabaseUpdateFail
AddressItem\RecordId = DatabaseLastInsertRowId() ; This will be the linked Recordid for the contacts
If AddressItem\Recordid <> #EmptyString
SetInfobarArea("Headings", "Info", "Inserted record " + AddressItem\RecordId + " into the database" , "ImportAddresses")
ImportCounter.i + 1
ForEach AddressItem\ContactList()
DatabaseUpdate.s = "INSERT INTO Contacts(Contacttype, Contactdetails, Recordid) " ; Contactid is an autoincrement field
DatabaseUpdate.s + "VALUES("
DatabaseUpdate.s + "'" + AddressItem\ContactList()\contacttype + "', "
DatabaseUpdate.s + "'" + AddressItem\ContactList()\contactdetails + "', "
DatabaseUpdate.s + "'" + AddressItem\RecordId + "')"
If DatabaseUpdate(Program\DatabaseHandle, DatabaseUpdate.s) <> #DatabaseUpdateFail
SetInfobarArea("Headings", "Info", "Inserted contact for current record into database" , "ImportAddresses")
Else
SetInfobarArea("Headings", "Error", "Could not insert imported main contacts table: " + DatabaseError(), "ImportAddresses")
EndIf
Next
Else
SetInfobarArea("Headings", "Error", "No Recordid found so we cannot write the contact details to the database out", "ImportAddresses")
EndIf
If *OutputBuffer
FreeMemory(*OutputBuffer)
EndIf
Else
SetInfobarArea("Headings", "Error", "The database import failed " + DatabaseError(), "ImportAddresses")
EndIf
; No more processing on this line
EndSelect
; Picture item
Case 1
If LineToProcess.s = "</Picture>"
AddressItem\Picture = PictureString.s
PictureString.s = ""
DetectionState.i = 0
Else
PictureString.s + LineToProcess.s
EndIf
; Contact book item
Case 2
If LineToProcess.s = "</ContactList>"
DetectionState.i = 0
Else
If LineToProcess.s = "<element>"
AddElement(AddressItem\ContactList())
Else
Select Mid(LineToProcess.s, 9, 3)
Case "typ"
AddressItem\ContactList()\contacttype = GetPartBetweenBrackets(LineToProcess.s)
Case "det"
AddressItem\ContactList()\contactdetails = GetPartBetweenBrackets(LineToProcess.s)
EndSelect
EndIf
EndIf
; Stop processing information in the current line
EndSelect
; Process the next line of the import file
Wend
;
CloseFile(XMLImportFileHandle.i)
XMLImportFilename.s = ""
PostEvent(#PB_Event_Gadget, #Window_AddressBook, #Gadget_AddressBook_Titles, #PB_EventType_Change)
;
Else
SetInfobarArea("Headings", "Error", "Got no handle for the import file name", "ImportAddresses")
EndIf
Else
SetInfobarArea("Headings", "Error", "Filename importing was cancelled by the user", "ImportAddresses")
EndIf
EndProcedure