B4A Library New Net library - Android FTP, SMTP and POP3

Discussion in 'Additional libraries, classes and official updates' started by Erel, Aug 17, 2011.

Thread Status:
Not open for further replies.
  1. Harris

    Harris Well-Known Member Licensed User

    Here is a copy of my code - whenever one has a chance to review. The MessageSent event has been moved to an activity module to capture event.
    SMTP params were derived from a Map file (created in my setup)


    Sub Process_Globals
    'These global variables will be declared once when the application starts.
    'These variables can be accessed from all modules.

    Dim SMTP1 As SMTP

    Dim myserver, myadd, mypass, myto1, myto2, myto3 As String
    Dim myport As Int
    Dim myssl,wassent As Boolean

    End Sub

    Sub QueMail
    Dim C1 As Cursor
    Dim i As Int

    ' que up out going mail

    C1 = DefCM.SQL1.ExecQuery2( "SELECT * FROM Inspections WHERE Sent = ?", Array As String(0) )
    If C1.RowCount > 0 Then

    SendSetup ' setup the SMTP object for sending
    For i = 0 To c1.RowCount - 1
    c1.Position = i
    wassent = False
    ' open send session
    Dim Recno As Long
    Dim Name, From As String
    Dim buf() As Byte

    Buf = C1.GetBlob("Inspect")
    Recno = c1.GetLong("ID_Date")
    Name = c1.GetString("Name")
    From = " "
    From = From &c1.GetString("Trip")&" For: "
    From = From &c1.GetString("Driver")&" Truck: "
    From = From &c1.GetString("Truck")&" Trailer: "
    From = From &c1.GetString("Trailer")

    Dim out As OutputStream
    out = File.OpenOutput( File.DirDefaultExternal&"/InspForms/",Name, False)
    out.WriteBytes(buf,0,buf.Length )
    Log(" Write pdf to disk for sending: "&Name)

    If SendFile(Name, From) = True Then
    If wassent Then
    Log(" Mail WAS Sent: "&Name)
    Log(" Mail WAS NOT Sent: "&Name)
    End If
    End If

    ToastMessageShow(" No Reports to Send Were Found",True)
    End If

    End Sub

    Sub SendFile(Name As String, From As String) As Boolean

    If myto2.Length > 0 Then
    End If
    If myto3.Length > 0 Then
    End If
    ' SMTP1.HtmlBody = False
    SMTP1.Subject = "MySite.com: "&Name

    Log("Attempted to Send May Have Failed: ")

    Return True
    End Sub

    'Sub SMTP1_MessageSent(Success As Boolean)
    'Log (" Message Sent: "&Success)
    'If Success Then
    ' wassent = True
    ' wassent = False
    ' Log("Send Error: "&LastException.Message)
    'End If
    'End Sub

    Sub UpDateSent(rec As Long)

    Defcm.SQL1.ExecNonQuery2("UPDATE Inspections SET Sent = ? WHERE ID_Date = ?", Array As String(DateTime.Now,rec))

    End Sub

    Sub SendSetup
    ' setup the SMTP object
    Dim mp As Map

    If File.Exists(File.DirDefaultExternal,"smtp.map") Then
    mp = File.ReadMap(File.DirDefaultExternal,"smtp.map")
    ToastMessageShow(" SMTP Setup File Not Found",False)
    End If

    myServer = mp.Get("smtpserver")
    myadd = mp.Get("smptname")
    mypass = mp.Get("smtppass")
    myport = mp.Get("smtpport")
    myssl = mp.Get("cbsmtpssl")

    myto1 = mp.Get("to1")
    myto2 = mp.Get("to2")
    myto3 = mp.Get("to3")


    Msgbox(" SMTP: "&myServer&" "&myadd&" "&mypass&" "&myport&" "&myssl&" Send To: "&myto1," SMTP ")

    End Sub
  2. vb1992

    vb1992 Well-Known Member Licensed User

    you didn't include

    Sub globals

    End Sub
    is Dim DefCM in Globals?
  3. Harris

    Harris Well-Known Member Licensed User

    Sorry vb, DefCM is my default code module - where SQL1 is inited.

    The globals contain SMTP1 and user password for priming SMTP1.Intialize.

    Funny, I had it all working - sending my pdfs like clockwork then - server responds with Authentication Required....

    I setup outlook with the same user and password and get the same result. Must be something with my username and password for that test account.
    My tester set my app up with a different account and gets the same return result - no sending

    I created a little stub, based on code above and can't seem to get passed it. Time to install 1.8 and then work beyond this.

    I will setup a new google email account and see how that flies.

  4. vb1992

    vb1992 Well-Known Member Licensed User

    Sometimes the SMTP servers want the full username/email address for authentication:

    myserver = mp.Get("abc.com")
    myadd = mp.Get("harris")


    myserver = mp.Get("abc.com")
    myadd = mp.Get("harris@abc.com")

    Last edited: Jan 14, 2012
  5. Harris

    Harris Well-Known Member Licensed User

    I have it working with my own personal account such as: myaccount@gmail.com.

    However, I ask my friend who was having issue with the same test app to use my account. He didn't get anywhere... The MessageSent event error he gets on his Galaxy S2 is:
    java.net.ConnectionException: localhost/::1:465 - Connection refused.

    LocalHost??? wtf?

    This is the same he will get using any of his valid email accounts with gmail.

    When i try to use another valid gmail account (which worked when I first tried SMTP), I get:
    Send Error: java.lang.RuntimeException: Empty writer returned: 530-5.5.1 Authentication Required. Learn more at mail.google.....

    I will post my complete test app code to see if anyone else sees the same.

  6. Harris

    Harris Well-Known Member Licensed User

    Attached is a simple sample of the test smtp.

    My primary account works, were as many other accounts produce erros in the connection.


    Attached Files:

  7. vb1992

    vb1992 Well-Known Member Licensed User

    what happens when you test the basics out?

    Sub Process_Globals
    Dim SMTP As SMTP
    End Sub
    Sub Globals

    End Sub

    Sub Activity_Create(FirstTime As Boolean)
    If FirstTime Then
    SMTP.UseSSL = True 'Gmail requires SSL.
        End If
    SMTP.Subject = "This is the subject"
    SMTP.Body = "This is the message body."
    'SMTP.AddAttachment(File.DirRootExternal, "somefile")
    End Sub
    Sub SMTP_MessageSent(Success As Boolean)
    If Success Then
    ToastMessageShow("Message sent successfully"True)
    ToastMessageShow("Error sending message"True)
    End If
    End Sub

    Have you read up on the PORTS?

    Last edited: Jan 16, 2012
  8. Harris

    Harris Well-Known Member Licensed User

    Local host issue solved:
    Seems the hint color is very close to a valid input color on some devices - and possibly the age of ones eyes plays a role. My tester did not supply a server value because the hint said: smpt.gmail.com My bad.. never supply valid values as hints.... :sign0013:

    As for my other valid address to the same gmail server, I will try your basic code above. You saw my test app is not far from your code above?

    Also, it would be nice to associate a send request with an ID. That way, I could determine which mail actually "made it" and which ones failed. With the ID, I could then update my tables record with the Sent flag and delete the file I extracted from my blob. Testing with the S2 this am, the mail was received long before (about 2 minutes) the ack came back from the server (Success) saying it was sent. This was due to low signal strength (I assume). When the same test was tried with phone in the signal booster, Success was received right away.

    Any suggestions on how to handle this would be most welcome. I have even tried waiting for the event directly after a send. I don't see the event until I exit the loop however long I wait..

    do while MsgEvent = False
    cnt = cnt + 1
    if cnt > 2000 then Exit

    In the event, I set MsgEvent to True when it fires, however it never does....

    Thanks everyone
  9. vb1992

    vb1992 Well-Known Member Licensed User

    I just know that code above works, with my gmail,
    so I figured if you can test that other gmail
    account with it, we are comparing apples to apples
  10. Harris

    Harris Well-Known Member Licensed User

    My other account now works!
    GMail was wanting me to authenticate this account. I only used it for testing on my device so I wasn't aware that it needed me to do this since this account was not listed in my gmail. Now that I have done this, it works fine - no error requesting authenication - as posted above.

    Yes, the sample code functions fine. Any suggestions about handling multiple mail send and confirmations?
  11. Harris

    Harris Well-Known Member Licensed User

    So, if I understand this correctly:
    I have 10 mails to send, create a list of these mails - que up and send the first one. Wait for response in MessageSent event (update list of pass or fail). In MessageSent, check if more mails need to be sent in list. Repeat... to end of list. When entire list has been processed, update my db table with results from list (mark sent field accordingly) and clean up files on disk (attachments).

    Sounds recursive but I think I can handle it.

  12. Smee

    Smee Well-Known Member Licensed User

    I am sending emails ok but the SMTP1_MessageSent(Success As Boolean) sub is not firing. I am using a code module for all routines

    does it have to be used in activity mod?
  13. Harris

    Harris Well-Known Member Licensed User

    YES, the event must be in activity module.... That was my problem (among others).

    I have SMTP sending multiple mails working now...

    I dont think its pretty, but it works

    I can update my db when the mail was sent and clean up left over files that were the attachments. Keep a clean house (wish I could say for my own - maid wanted...).
  14. Smee

    Smee Well-Known Member Licensed User

    I do not know what is wrong but the SMTP1_MessageSent(Success As Boolean) sub is still not firing.

    I have putting all the code in the Main Activity Module, Code Module and Service Module.
    This is how i send
    SMTP1.Initialize(server, port, emailname, Password, protocol)
    SMTP1.Subject = Subject
    SMTP1.Body = Body
    SMTP1.AddAttachment(DirName, FileName)

    Sub SMTP1_MessageSent(Success As Boolean)

    log( Success )

    end sub
    i have tried putting the dim smtp1 in process globals and globals all without success
  15. Erel

    Erel Administrator Staff Member Licensed User

    The last parameter is not "protocol". It is EventName. It should be "SMTP1" in your case.
  16. Smee

    Smee Well-Known Member Licensed User


    don' t know where i got the protocol from??? I think it was when i looked up Gmail requirements.

    Anyway i changed to "SMTP1" and it works beautifully.

    Thank you

    FWIW to any others, I changed all the code and put it into a Service Module and it runs great in the background. The program keeps running whilst all emails are being silently sent.
    lazreg likes this.
  17. Harris

    Harris Well-Known Member Licensed User

    Yes, good idea.
    I have accomplished what I wanted and have mine in a code module - "attempting" to send when I return to the main form (as would be normal in my app). However, in a service module, it could attempt always and often until all mails went out. My users have limited connection through tablets and areas not served well by cell coverage. This would ensure it would get out when it could.
    I shall convert my app pronto...

    Thanks all....
  18. cirollo

    cirollo Active Member Licensed User

    Error using the new net library

    I was using the network library
    I needed the passivemode property so I used the net 1.20 library deselecting the network library

    I'm getting this when compiling

    Compiling code.                         0.75
    Generating R 
    file.                      0.00
    Compiling generated Java code.          
    Convert byte code - optimized dex.      Error
    java.lang.IllegalArgumentException: already added: Lorg/apache/commons/net/DatagramSocketClient;
       at com.android.dx.dex.file.ClassDefsSection.add(ClassDefsSection.java:
       at com.android.dx.dex.file.DexFile.add(DexFile.java:
       at com.android.dx.command.dexer.Main.processClass(Main.java:
       at com.android.dx.command.dexer.Main.processFileBytes(Main.java:
       at com.android.dx.command.dexer.Main.access$
       at com.android.dx.command.dexer.Main$
       at com.android.dx.cf.direct.ClassPathOpener.processArchive(ClassPathOpener.java:
       at com.android.dx.cf.direct.ClassPathOpener.processOne(ClassPathOpener.java:
       at com.android.dx.cf.direct.ClassPathOpener.process(ClassPathOpener.java:
       at com.android.dx.command.dexer.Main.processOne(Main.java:
       at com.android.dx.command.dexer.Main.processAllFiles(Main.java:
       at com.android.dx.command.dexer.Main.run(Main.java:
       at com.android.dx.command.dexer.Main.main(Main.java:
       at com.android.dx.command.Main.main(Main.java:
    1 error; aborting
       Standard dexer.
  19. Erel

    Erel Administrator Staff Member Licensed User

    I don't see any problem with selecting both Net and Network libraries. Can you upload your project?
  20. biometrics

    biometrics Active Member Licensed User

    Is FTP Resume Supported?

    Hi Erel,

    Is FTP resume supported? Does the library do it automatically or should I send a resume command first using SendCommand before DownloadFile?
Thread Status:
Not open for further replies.
  1. This site uses cookies to help personalise content, tailor your experience and to keep you logged in if you register.
    By continuing to use this site, you are consenting to our use of cookies.
    Dismiss Notice