Hinweise zum neuen Forum
Zur Homepage des Deutschsprachige Xbase-Entwickler e. V.
Xbase++-Wiki des Deutschsprachige Xbase-Entwickler e. V.

Outlook 2015 und Mail Massenversand

Einbindung von Office-Komponenten wie Word, Excel usw.

Moderator: Moderatoren

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Outlook 2015 und Mail Massenversand

Beitrag von MichaMB » Mo, 03. Aug 2015 21:08

Hallo Liebe Spezialisten,

das nachfolgende Programm um personifizierte E-Mails mit Anhang zu versenden, funktioniert.
Nun würde ich gerne mehrere E-Mails (Newsletter) versenden die jedoch automatisch im Outlook-Ordner Ausgänge gespeichert werden sollen, ohne dass für jede E-Mail ein Popup-Fenster für Outlook geöffnet wird.

Ist das überhaupt möglich bzw. was muss ich genau ändern?

Code: Alles auswählen

   #pragma library( "ascom10.lib" )
   #include "Appevent.ch"
   #include "Dmlb.ch"
   #include "outlook.ch"
   #include "dll.ch"
   #include "common.ch"

//--error codes from MAPI.H
#define SUCCESS_SUCCESS                     0
#define MAPI_USER_ABORT                     1
#define MAPI_E_FAILURE                      2
#define MAPI_E_LOGIN_FAILURE                3
#define MAPI_E_DISK_FULL                    4
#define MAPI_E_INSUFFICIENT_MEMORY          5
#define MAPI_E_ACCESS_DENIED                6
#define MAPI_E_TOO_MANY_SESSIONS            8
#define MAPI_E_TOO_MANY_FILES               9
#define MAPI_E_TOO_MANY_RECIPIENTS          10
#define MAPI_E_ATTACHMENT_NOT_FOUND         11
#define MAPI_E_ATTACHMENT_OPEN_FAILURE      12
#define MAPI_E_ATTACHMENT_WRITE_FAILURE     13
#define MAPI_E_UNKNOWN_RECIPIENT            14
#define MAPI_E_BAD_RECIPTYPE                15
#define MAPI_E_NO_MESSAGES                  16
#define MAPI_E_INVALID_MESSAGE              17
#define MAPI_E_TEXT_TOO_LARGE               18
#define MAPI_E_INVALID_SESSION              19
#define MAPI_E_TYPE_NOT_SUPPORTED           20
#define MAPI_E_AMBIGUOUS_RECIPIENT          21
#define MAPI_E_MESSAGE_IN_USE               22
#define MAPI_E_NETWORK_FAILURE              23
#define MAPI_E_INVALID_EDITFIELDS           24
#define MAPI_E_INVALID_RECIPS               25
#define MAPI_E_NOT_SUPPORTED                26

//--ID´s for Message items
#define ID_SUBJECT                0
#define ID_MESSAGE                1
#define ID_MESSAGE_TYPE           2
#define ID_DATE                   3
#define ID_ORIGINATOR_NAME        4
#define ID_ORIGINATOR_ADRESS      5
#define ID_RECIPIENT_NAME         6
#define ID_RECIPIENT_ADRESS       7
#define ID_ATTACHMENT_PATHNAME    8
#define ID_ATTACHMENT_FILENAME    9
#define ID_CONVERSATION_ID        10

//--Message Flags
#define NOFLAG                    0
#define FLAG_UNREAD               1
#define FLAG_RECEIPT_REQUESTED    2
#define FLAG_SENT                 4

//--SKIP Flags
#define SKIP_ONLY                 0
#define DELETE_THEN_SKIP          1

//--Function Handles
STATIC snDllHandle    := 0
STATIC scDLLSocMapiIsInit    := ""    //Determines if MAPI is already initialized
STATIC scDLLSocMapiInit      := ""    //Initializes MAPI
STATIC scDLLSocMapiDeInit    := ""    //DeInitializes MAPI

STATIC scDLLSocMapiIsLoggedOn:= ""    //Dertermines if already logged onto a MAPI session.
STATIC scDLLSocMapiLogon     := ""    //Loggs onto a MAPI session
STATIC scDLLSocMapiLogoff    := ""    //Loggs off from a MAPI session

STATIC scDLLSocMapiSendMail  := ""    //Opens the mail editor with some preset Data.
STATIC scDLLSocMapiPostMail  := ""    //Directly puts a mail in the outbox (without a Dialog)

STATIC scDLLInboxOpen        := ""    //Initializes for further actions with the Inbox
STATIC scDLLInboxClose       := ""    //Frees memory that has been allocated with the inbox functions
STATIC scDLLInboxGoTop       := ""    //Positions the "Record pointer" to the first message in the inbox and reads it.
STATIC scDLLInboxSkip        := ""    //Skips to the next message in the inbox and reads it.

STATIC scDLLAskFlag          := ""    //Determines the Flags of a message (unread, Receipt requested, sent)
STATIC scDLLAskBufferSize    := ""    //Determines, how much buffer must be allocated for the following "StuffBuffer" call.
STATIC scDLLStuffBuffer      := ""    //Stuffs the buffer with a string for the desired message-element.

STATIC scDLLCountRecipients  := ""    //Counts the number of recipients for the current message.
STATIC scDLLCountAttachments := ""    //counts the number of attachments for the current message.
STATIC scDLLSaveAttachments  := ""    //Stores all attachments of a message to temporary files.
STATIC scDLLMarkAsRead       := ""    //Marks current message as read

// PRG VZerstna fr gleichzeitige Emailausudrucke

Procedure emailout

//if not already logged on, Logon to new MAPI session
  if  DllExecuteCall( scDLLSocMapiIsLoggedOn  ) == 0
      if (nErr := DllExecuteCall(scDLLSocMapiLogon)) != SUCCESS_SUCCESS
         NotifyError( nErr )
          return
      endif
  endif

  set default to (substr(FESTWO,1,1) + ":")
  set path to (substr(FESTWO,1,1) + ":")
  // set default to (verzword)
  // SET PATH to (verzword)
  set default to (verzexe)
  SET PATH to (verzexe)

// Grundeinstellungen erfolgen in Global*.PRG (MAIN)  laut Programm-Anmeldung User
// Emailadresse Empf„nger =  cAdresses  eventuell ändern

// public betrmail = cSubject   eventuell ändern

// public Anlage1 = cAttachments  eventuell ändern


// z.B. cAttachments cAttachments := (verzword)+ "/BUEPLogo.PDF"

// w„hlt die Anzahl der Anh„nge aus, je nach Emailart mit 1 2 oder 3 Anhängen

// Public AnzAnhaenge   ANzahl in VZerstna vorgegeben

// ist die Variable die die Anhänge für

// Public Anhangx

      // wenn Nutzer geprüft und ok Variablen belegen
      // public Emilwer   Emailadresse Empf„nger =  cAdresses
      // Vorbelegung für Anrede und Grüße in Email
      // public PERSWER
      // public betrmail = cSubject
      // public Anlage = cAttachments
      // public Anlage = cAttachments
      // Public infmess0      Text in mail = cMessage   Sehr geehrte Damen und Herren oder Hallo
      //  Public infmess1   Text um was es geht
      //  Public infmess2  Grußformel   Mit freundlichen Grüßen   bzw.   Viele Grüße
      //  Public infmess3    Geschäftsführer
      //  Public infmess3b   Unterzeichner
      //  Public infmess3c   Abteilung
      //  Public infmess4    Name Firma
      //  Public infmess5    Firmensitz
      // Public infmess6    Web und EMail
      // Public infmess7    bei GMBH Registergericht und Nummer
      // Public infmess8    Registrierungsstelle des Vermittlers
      // Public infmess9    www.vermittlerregister.info
      //  Public infmess10  Art der Tätigkeit  und   Nummer
      //  Public infmess11  Anschrift Gewerbeamt
      // Public infmess12   Versicherung und Nummer

  SendMail()

  //  Diese Programmausfhrung kann deaktiviert werden, wenn alles läuft
  ProcessInbox()

  //Logoff from MAPI session
  DllExecuteCall(scDLLSocMapiLogoff)

  // Rückstellung Anrede auf Standard
  store "S" to perswer

return

// EMail-Senden durch Outlook

// Init PROCEDURE //

INIT PROCEDURE SocMapiI()

    //Load DLL
    snDllHandle       := DllLoad( "SocMapi.Dll" )
    if snDllHandle == 0
        MsgBox("SOCMAPI.DLL not found!")
        ?
        ?
        ? "SOCMAPI.DLL nicht gefunden"
        ?
        wait
        QUIT
    endif

    //Get Function handles from DLL.
    scDLLSocMapiIsInit    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiIsInit"     )
    scDLLSocMapiInit      := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiInit"       )
    scDLLSocMapiDeInit    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiDeInit"     )

    scDLLSocMapiIsLoggedOn:= DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiIsLoggedOn" )
    scDLLSocMapiLogon     := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiLogon"      )
    scDLLSocMapiLogoff    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiLogoff"     )

    scDLLSocMapiSendMail  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiSendMail"   )
    scDLLSocMapiPostMail  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiPostMail"   )

    scDLLInboxOpen        := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxOpen"         )
    scDLLInboxClose       := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxClose"        )
    scDLLInboxGoTop       := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxGoTop"        )
    scDLLInboxSkip        := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxSkip"         )

    scDLLAskFlag          := DllPrepareCall( snDllHandle, DLL_STDCALL, "AskFlag"           )
    scDLLAskBufferSize    := DllPrepareCall( snDllHandle, DLL_STDCALL, "AskBufferSize"     )
    scDLLStuffBuffer      := DllPrepareCall( snDllHandle, DLL_STDCALL, "StuffBuffer"       )

    scDLLCountRecipients  := DllPrepareCall( snDllHandle, DLL_STDCALL, "CountRecipients"   )
    scDLLCountAttachments := DllPrepareCall( snDllHandle, DLL_STDCALL, "CountAttachments"  )
    scDLLSaveAttachments  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SaveAttachments"   )
    scDLLMarkAsRead       := DllPrepareCall( snDllHandle, DLL_STDCALL, "MarkAsRead"        )

    //initialize MAPI
    if DllExecuteCall( scDLLSocMapiIsInit ) == 0
        nErr := DllExecuteCall( scDLLSocMapiInit )
        if nErr != 0
            MsgBox("MAPI could not be initialized!  Errorcode: " + ALLTRIM(str(nErr)) )
            QUIT
        endif
    endif

return
//*************************************************************************** Init Procedure


//*************************************************************************** DemoSendMail
// SendMail //
//////////////////
// remarks:
// If no Flags are desired, use NOFLAG (don´t leave that uninitialised)
// Combine flags with "+" e.g.:
// nFlag := FLAG_RECEIPT_REQUESTED + FLAG_UNREAD + FLAG_SENT
// However for sending mails, actually only FLAG_RECEIPT_REQUESTED is useful.

PROCEDURE SendMail()

  // "Mxxxx@T-Online.de;" + "info@Mxxxxx.de;" + "CC:Mxxxx@T-Online.de;" + "BCC:info@Sxxxx.de"


  Local cAdresses    := (Emilwer)
  local cSubject     := (Betrmail)
  local cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
  //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
  Local cAttachments :=  &Anhangx
  local nFlag        :=  NOFLAG
  local nErr

    BEGIN SEQUENCE

    // set default to (verzword)
    // SET PATH to (verzword)

    set default to (verzexe)
    SET PATH to (verzexe)

        //-- Pop up maileditor
        MsgBox("mail will be send with Maileditor popping up")
        nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject  ,    cMessage,  cAttachments , nFlag)
        if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
            break nErr
        endif


        //-- Store mail directly to outbox
        MsgBox("mail will be stored directly to outbox")
        nErr := DllExecuteCall( scDLLSocMapiPostMail , cAdresses , cSubject  ,   cMessage  ,  cAttachments , nFlag)
        if nErr != SUCCESS_SUCCESS
            break nErr
        endif
//      MsgBox("mail successfully stored to outbox")

    RECOVER USING nErr
        NotifyError (nErr)
    END SEQUENCE

return
//*************************************************************************** DemoSendMail

//*************************************************************************** DemoProcessInbox
// DemoProcessInbox //
//////////////////////
PROCEDURE ProcessInbox()
local nErr
local nMsg := 0
local i
local cSubject, cMessage , cMessageType, cDate
local cOriginatorName    , cOriginatorAdress
local cConversationID
local nRead, nRecipRequest, nSent
local nRecipients, nAttachments
local aRecipName , aRecipAdress
local aAttachPath, aAttachFile



    BEGIN SEQUENCE

//        MsgBox("mails from the inbox folder will be processed!")

        //Open (i.e. initialize) Inbox folder, goto Top message
        if (nErr := DllExecuteCall( scDLLInboxOpen  )) != SUCCESS_SUCCESS
            break nErr
        endif
        if (nErr := DllExecuteCall( scDLLInboxGoTop )) != SUCCESS_SUCCESS
            break nErr
        endif

        //--loop for every message in the inbox
        do while .T.

            //--Get Flags from Message
            nRead               := DllExecuteCall( scDLLAskFlag , FLAG_UNREAD            )
            nRecipRequest       := DllExecuteCall( scDLLAskFlag , FLAG_RECEIPT_REQUESTED )
            nSent               := DllExecuteCall( scDLLAskFlag , FLAG_SENT              )

            //--Get all Message items for current message
            cSubject            := GetMessageItem ( ID_SUBJECT          , nil )
            cMessage            := GetMessageItem ( ID_MESSAGE          , nil )
            cMessageType        := GetMessageItem ( ID_MESSAGE_TYPE     , nil )
            cDate               := GetMessageItem ( ID_DATE             , nil )
            cOriginatorName     := GetMessageItem ( ID_ORIGINATOR_NAME  , nil )
            cOriginatorAdress   := GetMessageItem ( ID_ORIGINATOR_ADRESS, nil )
            cConversationID     := GetMessageItem ( ID_CONVERSATION_ID  , nil )

            //--Get all Recipients names/adresses to Array
            nRecipients         := DllExecuteCall  ( scDLLCountRecipients )
            aRecipName   := {}
            aRecipAdress := {}
            for i=1 to nRecipients
                AADD( aRecipName  , GetMessageItem ( ID_RECIPIENT_NAME   , i   ))
                AADD( aRecipAdress, GetMessageItem ( ID_RECIPIENT_ADRESS , i   ))
            next

            //--In case there are Attachments, store them to Temp files, get all Filenames/pathnames to Array
            nAttachments        := DllExecuteCall  ( scDLLCountAttachments )
            aAttachFile  := {}
            aAttachPath  := {}
            if nAttachments > 0
                if (nErr := DllExecuteCall( scDllSaveAttachments)) != SUCCESS_SUCCESS
                    break nErr
                endif
                for i=1 to nAttachments
                    AADD( aAttachFile , GetMessageItem ( ID_ATTACHMENT_FILENAME  , i ))
                    AADD( aAttachPath , GetMessageItem ( ID_ATTACHMENT_PATHNAME  , i ))
                next
            endif

            //-- Display on the screen
            nMsg++
            ? ""
            ? "Mailnr.: " + ALLTRIM(STR(nMsg))
            ?      "--------Flags--------"
            ? LEFT("Msg unread        : " + ALLTRIM(STR(nRead        ))  , 78)
            ? LEFT("Receipt requested : " + ALLTRIM(STR(nRecipRequest))  , 78)
            ? LEFT("Msg sent          : " + ALLTRIM(STR(nSent        ))  , 78)
            ?      "---------------------"
            ? LEFT("Subject  : " + cSubject         , 78)
            ? LEFT("Message  : " + cMessage         , 78)
            ? LEFT("Mess.Type: " + cMessageType     , 78)
            ? LEFT("Rec.Date : " + cDate            , 78)
            ? LEFT("Orig.Name: " + cOriginatorName  , 78)
            ? LEFT("Orig.Adr : " + cOriginatorAdress, 78)
            ? LEFT("Conv-ID  : " + cConversationID  , 78)
            for i=1 to nRecipients
                ? LEFT("Recip-Name-" + ALLTRIM(STR(i)) + ": " + aRecipName[i]   , 78)
                ? LEFT("Recip-Adr -" + ALLTRIM(STR(i)) + ": " + aRecipAdress[i] , 78)
            next
            for i=1 to nAttachments
                ? LEFT("Att.File  -" + ALLTRIM(STR(i)) + ": " + aAttachFile [i] , 78)
                ? LEFT("Att.Path  -" + ALLTRIM(STR(i)) + ": " + aAttachPath [i] , 78)
            next
            ? REPL("-",78)
//            MsgBox("Message " + ALLTRIM(STR(nMsg)))


            //--Mark message as read.
            if (nErr := DllExecuteCall( scDLLMarkAsRead )) != SUCCESS_SUCCESS
                break nErr
            endif

            //-- Skip to next message without deleting, Set DELETE_THEN_SKIP flag if current message
            //-- should be deleted before skipping
            nErr := DllExecuteCall (scDLLInboxSkip , SKIP_ONLY )
            if nErr == SUCCESS_SUCCESS
                loop
            elseif nErr == MAPI_E_NO_MESSAGES
                exit
            else
                break nErr
            endif
        enddo

//        MsgBox("All Messages processed")


    RECOVER USING nErr
        NotifyError(nErr)
    END SEQUENCE

    //--Finally close inbox, i.e free memory.
    DllExecuteCall(scDLLInboxClose)

return
//*************************************************************************** DemoProcessInbox

//*************************************************************************** GetMessageItem
// GetMessageItem  //
/////////////////////
FUNCTION GetMessageItem ( nID , nItemPos )
local nBufSize
local cBuffer
local nErr

    nBufSize := DllExecuteCall( scDLLAskBufferSize , nID  , nItemPos )
    cBuffer  := SPACE(nBufSize)
    nErr     := DllExecuteCall( scDLLStuffBuffer   , nID  , nItemPos , @cBuffer , nBufSize)

    if nErr != SUCCESS_SUCCESS
        break nErr
    endif

return cBuffer
//*************************************************************************** GetMessageItem

//*************************************************************************** NotifyError
// NotifyError //
/////////////////
PROCEDURE NotifyError( nErr )
local cErr
    do case
        case nErr==SUCCESS_SUCCESS                ; cErr := "Successful!"
        case nErr==MAPI_USER_ABORT                ; cErr := "USER_ABORT              "
        case nErr==MAPI_E_FAILURE                 ; cErr := "FAILURE                 "
        case nErr==MAPI_E_LOGIN_FAILURE           ; cErr := "LOGIN_FAILURE           "
        case nErr==MAPI_E_DISK_FULL               ; cErr := "DISK_FULL               "
        case nErr==MAPI_E_INSUFFICIENT_MEMORY     ; cErr := "INSUFFICIENT_MEMORY     "
        case nErr==MAPI_E_ACCESS_DENIED           ; cErr := "ACCESS_DENIED           "
        case nErr==MAPI_E_TOO_MANY_SESSIONS       ; cErr := "TOO_MANY_SESSIONS       "
        case nErr==MAPI_E_TOO_MANY_FILES          ; cErr := "TOO_MANY_FILES          "
        case nErr==MAPI_E_TOO_MANY_RECIPIENTS     ; cErr := "TOO_MANY_RECIPIENTS     "
        case nErr==MAPI_E_ATTACHMENT_NOT_FOUND    ; cErr := "ATTACHMENT_NOT_FOUND    "
        case nErr==MAPI_E_ATTACHMENT_OPEN_FAILURE ; cErr := "ATTACHMENT_OPEN_FAILURE "
        case nErr==MAPI_E_ATTACHMENT_WRITE_FAILURE; cErr := "ATTACHMENT_WRITE_FAILURE"
        case nErr==MAPI_E_UNKNOWN_RECIPIENT       ; cErr := "UNKNOWN_RECIPIENT       "
        case nErr==MAPI_E_BAD_RECIPTYPE           ; cErr := "BAD_RECIPTYPE           "
        case nErr==MAPI_E_NO_MESSAGES             ; cErr := "NO_MESSAGES             "
        case nErr==MAPI_E_INVALID_MESSAGE         ; cErr := "INVALID_MESSAGE         "
        case nErr==MAPI_E_TEXT_TOO_LARGE          ; cErr := "TEXT_TOO_LARGE          "
        case nErr==MAPI_E_INVALID_SESSION         ; cErr := "INVALID_SESSION         "
        case nErr==MAPI_E_TYPE_NOT_SUPPORTED      ; cErr := "TYPE_NOT_SUPPORTED      "
        case nErr==MAPI_E_AMBIGUOUS_RECIPIENT     ; cErr := "AMBIGUOUS_RECIPIENT     "
        case nErr==MAPI_E_MESSAGE_IN_USE          ; cErr := "MESSAGE_IN_USE          "
        case nErr==MAPI_E_NETWORK_FAILURE         ; cErr := "NETWORK_FAILURE         "
        case nErr==MAPI_E_INVALID_EDITFIELDS      ; cErr := "INVALID_EDITFIELDS      "
        case nErr==MAPI_E_INVALID_RECIPS          ; cErr := "INVALID_RECIPS          "
        case nErr==MAPI_E_NOT_SUPPORTED           ; cErr := "NOT_SUPPORTED           "
        otherwise                                 ; cErr := "Unknown Mapi Error"

    endcase
    // Zeile kann deaktiviert werden
    // MsgBox(cErr)

return
Zuletzt geändert von MichaMB am Di, 11. Aug 2015 22:06, insgesamt 1-mal geändert.
lG
Micha

Benutzeravatar
AUGE_OHR
Marvin
Marvin
Beiträge: 10381
Registriert: Do, 16. Mär 2006 8:55
Wohnort: Hamburg

Re: Outlook 2007 display()-Fehler

Beitrag von AUGE_OHR » Mo, 03. Aug 2015 21:54

MichaMB hat geschrieben:das nachfolgende Programm um personifizierte E-Mails mit Anhang zu versenden, funktioniert.
Nun würde ich gerne mehrere E-Mails (Newsletter) versenden die jedoch automatisch im Outlook-Ordner Ausgänge gespeichert werden sollen, ohne dass für jede E-Mail ein Popup-Fenster für Outlook geöffnet wird.

Ist das überhaupt möglich bzw. was muss ich genau ändern?
meinst du das Pop-Up wegen dem Zugriffsrecht von Outlook ?
gruss by OHR
Jimmy

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2015 display()-Fehler

Beitrag von MichaMB » Di, 04. Aug 2015 8:10

ja genau das PopUp von Outlook

Unterdrücke ich die Meldung passiert gar nichts mehr und das Programm läuft ohne E-Mail-Erstellung durch, danach...
startet übrigens hinterher Outlook nicht.. endlos, erst Neustart des Rechners behebt das Problem

Code: Alles auswählen

//-- Pop up maileditor
 MsgBox("mail will be send with Maileditor popping up")
 nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject ,cMessage , cAttachments , nFlag )
 if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
 break nErr
 endif
LG
Micha
Zuletzt geändert von MichaMB am Di, 11. Aug 2015 22:06, insgesamt 1-mal geändert.
lG
Micha

Benutzeravatar
AUGE_OHR
Marvin
Marvin
Beiträge: 10381
Registriert: Do, 16. Mär 2006 8:55
Wohnort: Hamburg

Re: Outlook 2007 display()-Fehler

Beitrag von AUGE_OHR » Di, 04. Aug 2015 21:32

MichaMB hat geschrieben:ja genau das PopUp von Outlook
Unterdrücke ich die Meldung passiert gar nichts mehr und das Programm läuft ohne E-Mail-Erstellung durch, danach...
startet übrigens hinterher Outlook nicht.. endlos, erst Neustart des Rechners behebt das Problem
hm ... den Code den du da zeigst "ist" zum auf-poppen des Outlook Mail Editor für die du ein "Recht" benötigst wobei die Zeitspanne festgelegt werden kann.

nun hast du aber geschieben
Nun würde ich gerne mehrere E-Mails (Newsletter) versenden die jedoch automatisch im Outlook-Ordner Ausgänge gespeichert werden sollen, ohne dass für jede E-Mail ein Popup-Fenster für Outlook geöffnet wird.
also frage ich dich warum steht dann BEIDES in deinem Code ???

Code: Alles auswählen

        //-- Pop up maileditor
        MsgBox("mail will be send with Maileditor popping up")
        nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject  ,    cMessage,  cAttachments , nFlag)
        if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
            break nErr
        endif

        //-- Store mail directly to outbox
        MsgBox("mail will be stored directly to outbox")
        nErr := DllExecuteCall( scDLLSocMapiPostMail , cAdresses , cSubject  ,   cMessage  ,  cAttachments , nFlag)
        if nErr != SUCCESS_SUCCESS
            break nErr
        endif
//      MsgBox("mail successfully stored to outbox")
wenn du mehrere Email verschicken willst solltest du das alles in "einer MAPI Session" machen und nicht jedes mal auf/zu.

für SocMAPI gilt die Empfehlung es im Thread laufen zu lassen. die Daten aus einer DBF sollte man vorher in ein Array schaufeln und das Array an den Thread übergeben.
gruss by OHR
Jimmy

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2015 display()-Fehler

Beitrag von MichaMB » Di, 04. Aug 2015 22:26

Hallo Jimmy,
mit dem nachfolgenden Code wird die Email geöffnet in das Outlook Ausgangspostfach gelegt, schön wäre es, wenn die offene E-Mail auch noch geschlossen wird. Versenden möchte ich dann selbst. Alle POPUP-Fenster sind deaktiviert, das Xbase++ Programm schließt den Vorgang ganz normal ab und wartet auf den nächsten Programm-Befehl

lässt man nur die Zeile (aus den 2 angesprochenen Codes)
// nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject , cMessage, cAttachments , nFlag)
weg, passiert gar nichts mehr

Code: Alles auswählen

// EMail-Senden durch Outlook

   #pragma library( "ascom10.lib" )
   #include "Appevent.ch"
   #include "Dmlb.ch"
   #include "outlook.ch"
   #include "dll.ch"
   #include "common.ch"

//--error codes from MAPI.H
#define SUCCESS_SUCCESS                     0
#define MAPI_USER_ABORT                     1
#define MAPI_E_FAILURE                      2
#define MAPI_E_LOGIN_FAILURE                3
#define MAPI_E_DISK_FULL                    4
#define MAPI_E_INSUFFICIENT_MEMORY          5
#define MAPI_E_ACCESS_DENIED                6
#define MAPI_E_TOO_MANY_SESSIONS            8
#define MAPI_E_TOO_MANY_FILES               9
#define MAPI_E_TOO_MANY_RECIPIENTS          10
#define MAPI_E_ATTACHMENT_NOT_FOUND         11
#define MAPI_E_ATTACHMENT_OPEN_FAILURE      12
#define MAPI_E_ATTACHMENT_WRITE_FAILURE     13
#define MAPI_E_UNKNOWN_RECIPIENT            14
#define MAPI_E_BAD_RECIPTYPE                15
#define MAPI_E_NO_MESSAGES                  16
#define MAPI_E_INVALID_MESSAGE              17
#define MAPI_E_TEXT_TOO_LARGE               18
#define MAPI_E_INVALID_SESSION              19
#define MAPI_E_TYPE_NOT_SUPPORTED           20
#define MAPI_E_AMBIGUOUS_RECIPIENT          21
#define MAPI_E_MESSAGE_IN_USE               22
#define MAPI_E_NETWORK_FAILURE              23
#define MAPI_E_INVALID_EDITFIELDS           24
#define MAPI_E_INVALID_RECIPS               25
#define MAPI_E_NOT_SUPPORTED                26

//--ID´s for Message items
#define ID_SUBJECT                0
#define ID_MESSAGE                1
#define ID_MESSAGE_TYPE           2
#define ID_DATE                   3
#define ID_ORIGINATOR_NAME        4
#define ID_ORIGINATOR_ADRESS      5
#define ID_RECIPIENT_NAME         6
#define ID_RECIPIENT_ADRESS       7
#define ID_ATTACHMENT_PATHNAME    8
#define ID_ATTACHMENT_FILENAME    9
#define ID_CONVERSATION_ID        10

//--Message Flags
#define NOFLAG                    0
#define FLAG_UNREAD               1
#define FLAG_RECEIPT_REQUESTED    2
#define FLAG_SENT                 4

//--SKIP Flags
#define SKIP_ONLY                 0
#define DELETE_THEN_SKIP          1


//--Function Handles
STATIC snDllHandle    := 0
STATIC scDLLSocMapiIsInit    := ""    //Determines if MAPI is already initialized
STATIC scDLLSocMapiInit      := ""    //Initializes MAPI
STATIC scDLLSocMapiDeInit    := ""    //DeInitializes MAPI

STATIC scDLLSocMapiIsLoggedOn:= ""    //Dertermines if already logged onto a MAPI session.
STATIC scDLLSocMapiLogon     := ""    //Loggs onto a MAPI session
STATIC scDLLSocMapiLogoff    := ""    //Loggs off from a MAPI session

STATIC scDLLSocMapiSendMail  := ""    //Opens the mail editor with some preset Data.
STATIC scDLLSocMapiPostMail  := ""    //Directly puts a mail in the outbox (without a Dialog)

STATIC scDLLInboxOpen        := ""    //Initializes for further actions with the Inbox
STATIC scDLLInboxClose       := ""    //Frees memory that has been allocated with the inbox functions
STATIC scDLLInboxGoTop       := ""    //Positions the "Record pointer" to the first message in the inbox and reads it.
STATIC scDLLInboxSkip        := ""    //Skips to the next message in the inbox and reads it.

STATIC scDLLAskFlag          := ""    //Determines the Flags of a message (unread, Receipt requested, sent)
STATIC scDLLAskBufferSize    := ""    //Determines, how much buffer must be allocated for the following "StuffBuffer" call.
STATIC scDLLStuffBuffer      := ""    //Stuffs the buffer with a string for the desired message-element.

STATIC scDLLCountRecipients  := ""    //Counts the number of recipients for the current message.
STATIC scDLLCountAttachments := ""    //counts the number of attachments for the current message.
STATIC scDLLSaveAttachments  := ""    //Stores all attachments of a message to temporary files.
STATIC scDLLMarkAsRead       := ""    //Marks current message as read


// PRG VZerstna.prg  wird fr gleichzeitige Ausdrucke  ohne E-Mailversand verwendet

Procedure emailout

  //if not already logged on, Logon to new MAPI session
  if  DllExecuteCall( scDLLSocMapiIsLoggedOn  ) == 0
      if (nErr := DllExecuteCall(scDLLSocMapiLogon)) != SUCCESS_SUCCESS
         NotifyError( nErr )
          return
      endif
  endif

  set default to (substr(FESTWO,1,1) + ":")
  set path to (substr(FESTWO,1,1) + ":")
  // set default to (verzword)
  // SET PATH to (verzword)
  set default to (verzexe)
  SET PATH to (verzexe)

  // Grundeinstellungen erfolgen in Global*.PRG (MAIN)  laut Programm-Anmeldung User
  // Emailadresse Empf„nger =  cAdresses  eventuell „ndern
  // public betrmail = cSubject   eventuell „ndern
  // public Anlage1 = cAttachments  eventuell „ndern
  // z.B. cAttachments cAttachments := (verzword)+ "/BUEPLogo.PDF"
  // w„hlt die Anzahl der Anh„nge aus, je nach Emailart mit 1 2 oder 3 Anh„ngen
  // Public AnzAnhaenge   ANzahl in VZerstna vorgegeben
  // ist die Variable die die Anh„nge fr
  // Public Anhangx
  // wenn Nutzer geprft und ok Variablen belegen
  // public Emilwer   Emailadresse Empf„nger =  cAdresses
  // Vorbelegung fr Anrede und Gráe in Email
  // public PERSWER
  // public betrmail = cSubject
  // public Anlage = cAttachments
  // public Anlage = cAttachments
  // Public infmess0      Text in mail = cMessage   Sehr geehrte Damen und Herren oder Hallo
  // Public infmess1   Text um was es geht
  // Public infmess2  Gruáformel   Mit freundlichen Gráen   bzw.   Viele Gráe
  // Public infmess3    Gesch„ftsfhrer
  // Public infmess3b   Unterzeichner
  // Public infmess3c   Abteilung
  // Public infmess4    Name Firma
  // Public infmess5    Firmensitz
  // Public infmess6    Web und EMail
  // Public infmess7    bei GMBH Registergericht und Nummer
  // Public infmess8    Registrierungsstelle des Vermittlers
  // Public infmess9    www.vermittlerregister.info
  // Public infmess10  Art der T„tigkeit  und   Nummer
  // Public infmess11  Anschrift Gewerbeamt
  // Public infmess12   Versicherung und Nummer

  SendMail()

  //  Diese Programmausfhrung kann deaktiviert werden, wenn alles l„uft
  ProcessInbox()

  //Logoff from MAPI session
  DllExecuteCall(scDLLSocMapiLogoff)

  // Rckstellung Anrede auf Standard
  store "S" to perswer

return

// EMail-Senden durch Outlook


INIT PROCEDURE SocMapiI()

    //Load DLL
    snDllHandle       := DllLoad( "SocMapi.Dll" )
    if snDllHandle == 0
        MsgBox("SOCMAPI.DLL not found!")
    endif

    //Get Function handles from DLL.
    scDLLSocMapiIsInit    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiIsInit"     )
    scDLLSocMapiInit      := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiInit"       )
    scDLLSocMapiDeInit    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiDeInit"     )

    scDLLSocMapiIsLoggedOn:= DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiIsLoggedOn" )
    scDLLSocMapiLogon     := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiLogon"      )
    scDLLSocMapiLogoff    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiLogoff"     )

    scDLLSocMapiSendMail  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiSendMail"   )
    scDLLSocMapiPostMail  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiPostMail"   )

    scDLLInboxOpen        := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxOpen"         )
    scDLLInboxClose       := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxClose"        )
    scDLLInboxGoTop       := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxGoTop"        )
    scDLLInboxSkip        := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxSkip"         )

    scDLLAskFlag          := DllPrepareCall( snDllHandle, DLL_STDCALL, "AskFlag"           )
    scDLLAskBufferSize    := DllPrepareCall( snDllHandle, DLL_STDCALL, "AskBufferSize"     )
    scDLLStuffBuffer      := DllPrepareCall( snDllHandle, DLL_STDCALL, "StuffBuffer"       )

    scDLLCountRecipients  := DllPrepareCall( snDllHandle, DLL_STDCALL, "CountRecipients"   )
    scDLLCountAttachments := DllPrepareCall( snDllHandle, DLL_STDCALL, "CountAttachments"  )
    scDLLSaveAttachments  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SaveAttachments"   )
    scDLLMarkAsRead       := DllPrepareCall( snDllHandle, DLL_STDCALL, "MarkAsRead"        )

    //initialize MAPI
    if DllExecuteCall( scDLLSocMapiIsInit ) == 0
        nErr := DllExecuteCall( scDLLSocMapiInit )
        if nErr != 0
            MsgBox("MAPI could not be initialized!  Errorcode: " + ALLTRIM(str(nErr)) )
            QUIT
        endif
    endif

return
//*************************************************************************** Init Procedure



//*************************************************************************** DemoSendMail
// SendMail //
//////////////////
// remarks:
// If no Flags are desired, use NOFLAG (don´t leave that uninitialised)
// Combine flags with "+" e.g.:
// nFlag := FLAG_RECEIPT_REQUESTED + FLAG_UNREAD + FLAG_SENT
// However for sending mails, actually only FLAG_RECEIPT_REQUESTED is useful.

PROCEDURE SendMail()

  // "Mxxxxxx@T-Online.de;" + "info@Mxxxxxxxxxxxxxxxx;" + "CC:Mxxxxxxx@T-Online.de;" + "BCC:info@Sxxxxxxxxxxxxxxxx.de"


  Local cAdresses    := (Emilwer)
  local cSubject     := (Betrmail)
  local cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
  //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
  Local cAttachments :=  &Anhangx
  local nFlag        :=  NOFLAG
  local nErr

    BEGIN SEQUENCE

      // set default to (verzword)
      // SET PATH to (verzword)

      set default to (verzexe)
      SET PATH to (verzexe)

      //-- Pop up maileditor
  //  MsgBox("mail will be send with Maileditor popping up")
      nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject  ,    cMessage,  cAttachments , nFlag)
      if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
        break nErr
      endif
      //-- Store mail directly to outbox
  //  MsgBox("mail will be stored directly to outbox")
      nErr := DllExecuteCall( scDLLSocMapiPostMail , cAdresses , cSubject  ,   cMessage  ,  cAttachments , nFlag)
      if nErr != SUCCESS_SUCCESS
        break nErr
      endif
  //  MsgBox("mail successfully stored to outbox")

      RECOVER USING nErr
        NotifyError (nErr)
    END SEQUENCE

return
//*************************************************************************** DemoSendMail

//*************************************************************************** DemoProcessInbox
// DemoProcessInbox //
//////////////////////
PROCEDURE ProcessInbox()
local nErr
local nMsg := 0
local i
local cSubject, cMessage , cMessageType, cDate
local cOriginatorName    , cOriginatorAdress
local cConversationID
local nRead, nRecipRequest, nSent
local nRecipients, nAttachments
local aRecipName , aRecipAdress
local aAttachPath, aAttachFile

    BEGIN SEQUENCE

//      MsgBox("mails from the inbox folder will be processed!")

        //Open (i.e. initialize) Inbox folder, goto Top message
        if (nErr := DllExecuteCall( scDLLInboxOpen  )) != SUCCESS_SUCCESS
            break nErr
        endif
        if (nErr := DllExecuteCall( scDLLInboxGoTop )) != SUCCESS_SUCCESS
            break nErr
        endif

        //--loop for every message in the inbox
        do while .T.

            //--Get Flags from Message
            nRead               := DllExecuteCall( scDLLAskFlag , FLAG_UNREAD            )
            nRecipRequest       := DllExecuteCall( scDLLAskFlag , FLAG_RECEIPT_REQUESTED )
            nSent               := DllExecuteCall( scDLLAskFlag , FLAG_SENT              )

            //--Get all Message items for current message
            cSubject            := GetMessageItem ( ID_SUBJECT          , nil )
            cMessage            := GetMessageItem ( ID_MESSAGE          , nil )
            cMessageType        := GetMessageItem ( ID_MESSAGE_TYPE     , nil )
            cDate               := GetMessageItem ( ID_DATE             , nil )
            cOriginatorName     := GetMessageItem ( ID_ORIGINATOR_NAME  , nil )
            cOriginatorAdress   := GetMessageItem ( ID_ORIGINATOR_ADRESS, nil )
            cConversationID     := GetMessageItem ( ID_CONVERSATION_ID  , nil )

            //--Get all Recipients names/adresses to Array
            nRecipients         := DllExecuteCall  ( scDLLCountRecipients )
            aRecipName   := {}
            aRecipAdress := {}
            for i=1 to nRecipients
                AADD( aRecipName  , GetMessageItem ( ID_RECIPIENT_NAME   , i   ))
                AADD( aRecipAdress, GetMessageItem ( ID_RECIPIENT_ADRESS , i   ))
            next

            //--In case there are Attachments, store them to Temp files, get all Filenames/pathnames to Array
            nAttachments        := DllExecuteCall  ( scDLLCountAttachments )
            aAttachFile  := {}
            aAttachPath  := {}
            if nAttachments > 0
                if (nErr := DllExecuteCall( scDllSaveAttachments)) != SUCCESS_SUCCESS
                    break nErr
                endif
                for i=1 to nAttachments
                    AADD( aAttachFile , GetMessageItem ( ID_ATTACHMENT_FILENAME  , i ))
                    AADD( aAttachPath , GetMessageItem ( ID_ATTACHMENT_PATHNAME  , i ))
                next
            endif

            //-- Display on the screen
            nMsg++
            ? ""
            ? "Mailnr.: " + ALLTRIM(STR(nMsg))
            ?      "--------Flags--------"
            ? LEFT("Msg unread        : " + ALLTRIM(STR(nRead        ))  , 78)
            ? LEFT("Receipt requested : " + ALLTRIM(STR(nRecipRequest))  , 78)
            ? LEFT("Msg sent          : " + ALLTRIM(STR(nSent        ))  , 78)
            ?      "---------------------"
            ? LEFT("Subject  : " + cSubject         , 78)
            ? LEFT("Message  : " + cMessage         , 78)
            ? LEFT("Mess.Type: " + cMessageType     , 78)
            ? LEFT("Rec.Date : " + cDate            , 78)
            ? LEFT("Orig.Name: " + cOriginatorName  , 78)
            ? LEFT("Orig.Adr : " + cOriginatorAdress, 78)
            ? LEFT("Conv-ID  : " + cConversationID  , 78)
            for i=1 to nRecipients
                ? LEFT("Recip-Name-" + ALLTRIM(STR(i)) + ": " + aRecipName[i]   , 78)
                ? LEFT("Recip-Adr -" + ALLTRIM(STR(i)) + ": " + aRecipAdress[i] , 78)
            next
            for i=1 to nAttachments
                ? LEFT("Att.File  -" + ALLTRIM(STR(i)) + ": " + aAttachFile [i] , 78)
                ? LEFT("Att.Path  -" + ALLTRIM(STR(i)) + ": " + aAttachPath [i] , 78)
            next
            ? REPL("-",78)
//          MsgBox("Message " + ALLTRIM(STR(nMsg)))

            //--Mark message as read.
            if (nErr := DllExecuteCall( scDLLMarkAsRead )) != SUCCESS_SUCCESS
                break nErr
            endif

            //-- Skip to next message without deleting, Set DELETE_THEN_SKIP flag if current message
            //-- should be deleted before skipping
            nErr := DllExecuteCall (scDLLInboxSkip , SKIP_ONLY )
            if nErr == SUCCESS_SUCCESS
                loop
            elseif nErr == MAPI_E_NO_MESSAGES
                exit
            else
                break nErr
            endif
        enddo

//      MsgBox("All Messages processed")


    RECOVER USING nErr
        NotifyError(nErr)
    END SEQUENCE

    //--Finally close inbox, i.e free memory.
    DllExecuteCall(scDLLInboxClose)

return



// GetMessageItem  //
FUNCTION GetMessageItem ( nID , nItemPos )
local nBufSize
local cBuffer
local nErr

    nBufSize := DllExecuteCall( scDLLAskBufferSize , nID  , nItemPos )
    cBuffer  := SPACE(nBufSize)
    nErr     := DllExecuteCall( scDLLStuffBuffer   , nID  , nItemPos , @cBuffer , nBufSize)

    if nErr != SUCCESS_SUCCESS
        break nErr
    endif

return cBuffer
//*************************************************************************** GetMessageItem

// NotifyError //
PROCEDURE NotifyError( nErr )
local cErr
    do case
        case nErr==SUCCESS_SUCCESS                ; cErr := "Successful!"
        case nErr==MAPI_USER_ABORT                ; cErr := "USER_ABORT              "
        case nErr==MAPI_E_FAILURE                 ; cErr := "FAILURE                 "
        case nErr==MAPI_E_LOGIN_FAILURE           ; cErr := "LOGIN_FAILURE           "
        case nErr==MAPI_E_DISK_FULL               ; cErr := "DISK_FULL               "
        case nErr==MAPI_E_INSUFFICIENT_MEMORY     ; cErr := "INSUFFICIENT_MEMORY     "
        case nErr==MAPI_E_ACCESS_DENIED           ; cErr := "ACCESS_DENIED           "
        case nErr==MAPI_E_TOO_MANY_SESSIONS       ; cErr := "TOO_MANY_SESSIONS       "
        case nErr==MAPI_E_TOO_MANY_FILES          ; cErr := "TOO_MANY_FILES          "
        case nErr==MAPI_E_TOO_MANY_RECIPIENTS     ; cErr := "TOO_MANY_RECIPIENTS     "
        case nErr==MAPI_E_ATTACHMENT_NOT_FOUND    ; cErr := "ATTACHMENT_NOT_FOUND    "
        case nErr==MAPI_E_ATTACHMENT_OPEN_FAILURE ; cErr := "ATTACHMENT_OPEN_FAILURE "
        case nErr==MAPI_E_ATTACHMENT_WRITE_FAILURE; cErr := "ATTACHMENT_WRITE_FAILURE"
        case nErr==MAPI_E_UNKNOWN_RECIPIENT       ; cErr := "UNKNOWN_RECIPIENT       "
        case nErr==MAPI_E_BAD_RECIPTYPE           ; cErr := "BAD_RECIPTYPE           "
        case nErr==MAPI_E_NO_MESSAGES             ; cErr := "NO_MESSAGES             "
        case nErr==MAPI_E_INVALID_MESSAGE         ; cErr := "INVALID_MESSAGE         "
        case nErr==MAPI_E_TEXT_TOO_LARGE          ; cErr := "TEXT_TOO_LARGE          "
        case nErr==MAPI_E_INVALID_SESSION         ; cErr := "INVALID_SESSION         "
        case nErr==MAPI_E_TYPE_NOT_SUPPORTED      ; cErr := "TYPE_NOT_SUPPORTED      "
        case nErr==MAPI_E_AMBIGUOUS_RECIPIENT     ; cErr := "AMBIGUOUS_RECIPIENT     "
        case nErr==MAPI_E_MESSAGE_IN_USE          ; cErr := "MESSAGE_IN_USE          "
        case nErr==MAPI_E_NETWORK_FAILURE         ; cErr := "NETWORK_FAILURE         "
        case nErr==MAPI_E_INVALID_EDITFIELDS      ; cErr := "INVALID_EDITFIELDS      "
        case nErr==MAPI_E_INVALID_RECIPS          ; cErr := "INVALID_RECIPS          "
        case nErr==MAPI_E_NOT_SUPPORTED           ; cErr := "NOT_SUPPORTED           "
        otherwise                                 ; cErr := "Unknown Mapi Error"

    endcase
    // Zeile kann deaktiviert werden
    // MsgBox(cErr)

return
Zuletzt geändert von MichaMB am Di, 11. Aug 2015 22:07, insgesamt 2-mal geändert.
lG
Micha

Benutzeravatar
AUGE_OHR
Marvin
Marvin
Beiträge: 10381
Registriert: Do, 16. Mär 2006 8:55
Wohnort: Hamburg

Re: Outlook 2007 display()-Fehler

Beitrag von AUGE_OHR » Mi, 05. Aug 2015 4:05

MichaMB hat geschrieben:

Code: Alles auswählen

PROCEDURE SendMail()
      ...
      //-- Pop up maileditor
  //  MsgBox("mail will be send with Maileditor popping up")
      nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject  ,    cMessage,  cAttachments , nFlag)
      if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
        break nErr
      endif
      //-- Store mail directly to outbox
  //  MsgBox("mail will be stored directly to outbox")
      nErr := DllExecuteCall( scDLLSocMapiPostMail , cAdresses , cSubject  ,   cMessage  ,  cAttachments , nFlag)
      if nErr != SUCCESS_SUCCESS
        break nErr
      endif
  //  MsgBox("mail successfully stored to outbox")
ich kann mich nur wiederholen [-o<
also frage ich dich warum steht dann BEIDES in deinem Code ???
du hast sowohl "//-- Pop up maileditor", was den Outlook Mail Client Editor öffnet, UND AUCH "//-- Store mail directly to outbox" dort stehen.
Entscheide dich ENTWEDER ODER aber NICHT BEIDES :boxing:

p.s. Das ganze hat nichts mit dem oOutlook:Display() Problem zu tun ausser dem Rechte Problem.
gruss by OHR
Jimmy

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2015 display()-Fehler

Beitrag von MichaMB » Mi, 05. Aug 2015 13:49

Hallo Jimmy,
das habe ich auch verstanden, aber es funktioniert nur der MAPI- Sendmail -Befehl
für die andere Variante rufe ich im Main Postmail auf, dann passiert gar nichts mehr, nicht mal mein vorheriger Ausdruck der Word.-Dateien per makro funtioniert, das Programm beendet aber ordnungsgemäß
Da habe ich irgendwo etwas übersehen, da für die Newsletter Versendung nur die Postmail Procedur aus dem Main-Programm in Frage kommt, oder ?
hast du mir bitte ein Beispiel mit 3 Datensätzen von DBF auf Array und z.B. 3 Felder Name, Anrede, emailadresse

Code: Alles auswählen

// EMail-Senden durch Outlook

   #pragma library( "ascom10.lib" )
   #include "Appevent.ch"
   #include "Dmlb.ch"
   #include "outlook.ch"
   #include "dll.ch"
   #include "common.ch"

//--error codes from MAPI.H
#define SUCCESS_SUCCESS                     0
#define MAPI_USER_ABORT                     1
#define MAPI_E_FAILURE                      2
#define MAPI_E_LOGIN_FAILURE                3
#define MAPI_E_DISK_FULL                    4
#define MAPI_E_INSUFFICIENT_MEMORY          5
#define MAPI_E_ACCESS_DENIED                6
#define MAPI_E_TOO_MANY_SESSIONS            8
#define MAPI_E_TOO_MANY_FILES               9
#define MAPI_E_TOO_MANY_RECIPIENTS          10
#define MAPI_E_ATTACHMENT_NOT_FOUND         11
#define MAPI_E_ATTACHMENT_OPEN_FAILURE      12
#define MAPI_E_ATTACHMENT_WRITE_FAILURE     13
#define MAPI_E_UNKNOWN_RECIPIENT            14
#define MAPI_E_BAD_RECIPTYPE                15
#define MAPI_E_NO_MESSAGES                  16
#define MAPI_E_INVALID_MESSAGE              17
#define MAPI_E_TEXT_TOO_LARGE               18
#define MAPI_E_INVALID_SESSION              19
#define MAPI_E_TYPE_NOT_SUPPORTED           20
#define MAPI_E_AMBIGUOUS_RECIPIENT          21
#define MAPI_E_MESSAGE_IN_USE               22
#define MAPI_E_NETWORK_FAILURE              23
#define MAPI_E_INVALID_EDITFIELDS           24
#define MAPI_E_INVALID_RECIPS               25
#define MAPI_E_NOT_SUPPORTED                26

//--ID´s for Message items
#define ID_SUBJECT                0
#define ID_MESSAGE                1
#define ID_MESSAGE_TYPE           2
#define ID_DATE                   3
#define ID_ORIGINATOR_NAME        4
#define ID_ORIGINATOR_ADRESS      5
#define ID_RECIPIENT_NAME         6
#define ID_RECIPIENT_ADRESS       7
#define ID_ATTACHMENT_PATHNAME    8
#define ID_ATTACHMENT_FILENAME    9
#define ID_CONVERSATION_ID        10

//--Message Flags
#define NOFLAG                    0
#define FLAG_UNREAD               1
#define FLAG_RECEIPT_REQUESTED    2
#define FLAG_SENT                 4

//--SKIP Flags
#define SKIP_ONLY                 0
#define DELETE_THEN_SKIP          1


//--Function Handles
STATIC snDllHandle    := 0
STATIC scDLLSocMapiIsInit    := ""    //Determines if MAPI is already initialized
STATIC scDLLSocMapiInit      := ""    //Initializes MAPI
STATIC scDLLSocMapiDeInit    := ""    //DeInitializes MAPI

STATIC scDLLSocMapiIsLoggedOn:= ""    //Dertermines if already logged onto a MAPI session.
STATIC scDLLSocMapiLogon     := ""    //Loggs onto a MAPI session
STATIC scDLLSocMapiLogoff    := ""    //Loggs off from a MAPI session

STATIC scDLLSocMapiSendMail  := ""    //Opens the mail editor with some preset Data.
STATIC scDLLSocMapiPostMail  := ""    //Directly puts a mail in the outbox (without a Dialog)

STATIC scDLLInboxOpen        := ""    //Initializes for further actions with the Inbox
STATIC scDLLInboxClose       := ""    //Frees memory that has been allocated with the inbox functions
STATIC scDLLInboxGoTop       := ""    //Positions the "Record pointer" to the first message in the inbox and reads it.
STATIC scDLLInboxSkip        := ""    //Skips to the next message in the inbox and reads it.

STATIC scDLLAskFlag          := ""    //Determines the Flags of a message (unread, Receipt requested, sent)
STATIC scDLLAskBufferSize    := ""    //Determines, how much buffer must be allocated for the following "StuffBuffer" call.
STATIC scDLLStuffBuffer      := ""    //Stuffs the buffer with a string for the desired message-element.

STATIC scDLLCountRecipients  := ""    //Counts the number of recipients for the current message.
STATIC scDLLCountAttachments := ""    //counts the number of attachments for the current message.
STATIC scDLLSaveAttachments  := ""    //Stores all attachments of a message to temporary files.
STATIC scDLLMarkAsRead       := ""    //Marks current message as read


// PRG VZerstna.prg  wird fr gleichzeitige Ausdrucke  ohne E-Mailversand verwendet

Procedure emailout

  //if not already logged on, Logon to new MAPI session
  if  DllExecuteCall( scDLLSocMapiIsLoggedOn  ) == 0
      if (nErr := DllExecuteCall(scDLLSocMapiLogon)) != SUCCESS_SUCCESS
         NotifyError( nErr )
          return
      endif
  endif

  set default to (substr(FESTWO,1,1) + ":")
  set path to (substr(FESTWO,1,1) + ":")
  // set default to (verzword)
  // SET PATH to (verzword)
  set default to (verzexe)
  SET PATH to (verzexe)

  // Grundeinstellungen erfolgen in Global*.PRG (MAIN)  laut Programm-Anmeldung User
  // Emailadresse Empf„nger =  cAdresses  eventuell „ndern
  // public betrmail = cSubject   eventuell „ndern
  // public Anlage1 = cAttachments  eventuell „ndern
  // z.B. cAttachments cAttachments := (verzword)+ "/BUEPLogo.PDF"
  // w„hlt die Anzahl der Anh„nge aus, je nach Emailart mit 1 2 oder 3 Anh„ngen
  // Public AnzAnhaenge   ANzahl in VZerstna vorgegeben
  // ist die Variable die die Anh„nge fr
  // Public Anhangx
  // wenn Nutzer geprft und ok Variablen belegen
  // public Emilwer   Emailadresse Empf„nger =  cAdresses
  // Vorbelegung fr Anrede und Gráe in Email
  // public PERSWER
  // public betrmail = cSubject
  // public Anlage = cAttachments
  // public Anlage = cAttachments
  // Public infmess0      Text in mail = cMessage   Sehr geehrte Damen und Herren oder Hallo
  // Public infmess1   Text um was es geht
  // Public infmess2  Gruáformel   Mit freundlichen Gráen   bzw.   Viele Gráe
  // Public infmess3    Gesch„ftsfhrer
  // Public infmess3b   Unterzeichner
  // Public infmess3c   Abteilung
  // Public infmess4    Name Firma
  // Public infmess5    Firmensitz
  // Public infmess6    Web und EMail
  // Public infmess7    bei GMBH Registergericht und Nummer
  // Public infmess8    Registrierungsstelle des Vermittlers
  // Public infmess9    www.vermittlerregister.info
  // Public infmess10  Art der T„tigkeit  und   Nummer
  // Public infmess11  Anschrift Gewerbeamt
  // Public infmess12   Versicherung und Nummer

   SendMail()
  // PostMail()

  //  Diese Programmausfhrung kann deaktiviert werden, wenn alles l„uft
  ProcessInbox()

  //Logoff from MAPI session
  DllExecuteCall(scDLLSocMapiLogoff)

  // Rckstellung Anrede auf Standard
  store "S" to perswer

return

// EMail-Senden durch Outlook


INIT PROCEDURE SocMapiI()

    //Load DLL
    snDllHandle       := DllLoad( "SocMapi.Dll" )
    if snDllHandle == 0
        MsgBox("SOCMAPI.DLL not found!")
    endif

    //Get Function handles from DLL.
    scDLLSocMapiIsInit    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiIsInit"     )
    scDLLSocMapiInit      := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiInit"       )
    scDLLSocMapiDeInit    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiDeInit"     )

    scDLLSocMapiIsLoggedOn:= DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiIsLoggedOn" )
    scDLLSocMapiLogon     := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiLogon"      )
    scDLLSocMapiLogoff    := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiLogoff"     )

    scDLLSocMapiSendMail  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiSendMail"   )
    scDLLSocMapiPostMail  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SocMapiPostMail"   )

    scDLLInboxOpen        := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxOpen"         )
    scDLLInboxClose       := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxClose"        )
    scDLLInboxGoTop       := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxGoTop"        )
    scDLLInboxSkip        := DllPrepareCall( snDllHandle, DLL_STDCALL, "InboxSkip"         )

    scDLLAskFlag          := DllPrepareCall( snDllHandle, DLL_STDCALL, "AskFlag"           )
    scDLLAskBufferSize    := DllPrepareCall( snDllHandle, DLL_STDCALL, "AskBufferSize"     )
    scDLLStuffBuffer      := DllPrepareCall( snDllHandle, DLL_STDCALL, "StuffBuffer"       )

    scDLLCountRecipients  := DllPrepareCall( snDllHandle, DLL_STDCALL, "CountRecipients"   )
    scDLLCountAttachments := DllPrepareCall( snDllHandle, DLL_STDCALL, "CountAttachments"  )
    scDLLSaveAttachments  := DllPrepareCall( snDllHandle, DLL_STDCALL, "SaveAttachments"   )
    scDLLMarkAsRead       := DllPrepareCall( snDllHandle, DLL_STDCALL, "MarkAsRead"        )

    //initialize MAPI
    if DllExecuteCall( scDLLSocMapiIsInit ) == 0
        nErr := DllExecuteCall( scDLLSocMapiInit )
        if nErr != 0
            MsgBox("MAPI could not be initialized!  Errorcode: " + ALLTRIM(str(nErr)) )
            QUIT
        endif
    endif

return
//*************************************************************************** Init Procedure



//*************************************************************************** DemoSendMail
// SendMail //
//////////////////
// remarks:
// If no Flags are desired, use NOFLAG (don´t leave that uninitialised)
// Combine flags with "+" e.g.:
// nFlag := FLAG_RECEIPT_REQUESTED + FLAG_UNREAD + FLAG_SENT
// However for sending mails, actually only FLAG_RECEIPT_REQUESTED is useful.

PROCEDURE postMail()

  // "Mxxxxxxxxxxxx@T-Online.de;" + "info@Mxxxxxxxxxxxxxxxxxx.de;" + "CC:Mxxxxx@T-Online.de;" + "BCC:info@Sxxxxxxxxxxxxxxxx.de"


  Local cAdresses    := (Emilwer)
  local cSubject     := (Betrmail)
  local cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
  //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
  Local cAttachments :=  &Anhangx
  local nFlag        :=  NOFLAG
  local nErr

    BEGIN SEQUENCE

      // set default to (verzword)
      // SET PATH to (verzword)

      set default to (verzexe)
      SET PATH to (verzexe)

      //-- Pop up maileditor
 //  MsgBox("mail will be send with Maileditor popping up")
 //     nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject  ,    cMessage,  cAttachments , nFlag)
 //     if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
 //      break nErr
 //   endif
      //-- Store mail directly to outbox
      MsgBox("mail will be stored directly to outbox")
      nErr := DllExecuteCall( scDLLSocMapiPostMail , cAdresses , cSubject  ,   cMessage  ,  cAttachments , nFlag)
      if nErr != SUCCESS_SUCCESS
        break nErr
      endif
      MsgBox("mail successfully stored to outbox")

      RECOVER USING nErr
        NotifyError (nErr)
    END SEQUENCE

return

PROCEDURE SendMail()

  // "Mxxxxxxxxxxxx@T-Online.de;" + "info@Mxxxxxxxxxxxxxxxxxx.de;" + "CC:Mxxxxx@T-Online.de;" + "BCC:info@Sxxxxxxxxxxxxxxxx.de"


  Local cAdresses    := (Emilwer)
  local cSubject     := (Betrmail)
  local cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
  //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
  Local cAttachments :=  &Anhangx
  local nFlag        :=  NOFLAG
  local nErr

    BEGIN SEQUENCE

      // set default to (verzword)
      // SET PATH to (verzword)

      set default to (verzexe)
      SET PATH to (verzexe)

      //-- Pop up maileditor
     MsgBox("mail will be send with Maileditor popping up")
     nErr := DllExecuteCall( scDLLSocMapiSendMail , cAdresses , cSubject  ,    cMessage,  cAttachments , nFlag)
     if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
       break nErr
     endif
      //-- Store mail directly to outbox
//      MsgBox("mail will be stored directly to outbox")
//      nErr := DllExecuteCall( scDLLSocMapiPostMail , cAdresses , cSubject  ,   cMessage  ,  cAttachments , nFlag)
//      if nErr != SUCCESS_SUCCESS
//        break nErr
//      endif
//      MsgBox("mail successfully stored to outbox")

      RECOVER USING nErr
        NotifyError (nErr)
    END SEQUENCE

return
//*************************************************************************** SendMail

//*************************************************************************** DemoProcessInbox
// ProcessInbox //
//////////////////////
PROCEDURE ProcessInbox()
local nErr
local nMsg := 0
local i
local cSubject, cMessage , cMessageType, cDate
local cOriginatorName    , cOriginatorAdress
local cConversationID
local nRead, nRecipRequest, nSent
local nRecipients, nAttachments
local aRecipName , aRecipAdress
local aAttachPath, aAttachFile

    BEGIN SEQUENCE

//      MsgBox("mails from the inbox folder will be processed!")

        //Open (i.e. initialize) Inbox folder, goto Top message
        if (nErr := DllExecuteCall( scDLLInboxOpen  )) != SUCCESS_SUCCESS
            break nErr
        endif
        if (nErr := DllExecuteCall( scDLLInboxGoTop )) != SUCCESS_SUCCESS
            break nErr
        endif

        //--loop for every message in the inbox
        do while .T.

            //--Get Flags from Message
            nRead               := DllExecuteCall( scDLLAskFlag , FLAG_UNREAD            )
            nRecipRequest       := DllExecuteCall( scDLLAskFlag , FLAG_RECEIPT_REQUESTED )
            nSent               := DllExecuteCall( scDLLAskFlag , FLAG_SENT              )

            //--Get all Message items for current message
            cSubject            := GetMessageItem ( ID_SUBJECT          , nil )
            cMessage            := GetMessageItem ( ID_MESSAGE          , nil )
            cMessageType        := GetMessageItem ( ID_MESSAGE_TYPE     , nil )
            cDate               := GetMessageItem ( ID_DATE             , nil )
            cOriginatorName     := GetMessageItem ( ID_ORIGINATOR_NAME  , nil )
            cOriginatorAdress   := GetMessageItem ( ID_ORIGINATOR_ADRESS, nil )
            cConversationID     := GetMessageItem ( ID_CONVERSATION_ID  , nil )

            //--Get all Recipients names/adresses to Array
            nRecipients         := DllExecuteCall  ( scDLLCountRecipients )
            aRecipName   := {}
            aRecipAdress := {}
            for i=1 to nRecipients
                AADD( aRecipName  , GetMessageItem ( ID_RECIPIENT_NAME   , i   ))
                AADD( aRecipAdress, GetMessageItem ( ID_RECIPIENT_ADRESS , i   ))
            next

            //--In case there are Attachments, store them to Temp files, get all Filenames/pathnames to Array
            nAttachments        := DllExecuteCall  ( scDLLCountAttachments )
            aAttachFile  := {}
            aAttachPath  := {}
            if nAttachments > 0
                if (nErr := DllExecuteCall( scDllSaveAttachments)) != SUCCESS_SUCCESS
                    break nErr
                endif
                for i=1 to nAttachments
                    AADD( aAttachFile , GetMessageItem ( ID_ATTACHMENT_FILENAME  , i ))
                    AADD( aAttachPath , GetMessageItem ( ID_ATTACHMENT_PATHNAME  , i ))
                next
            endif

            //-- Display on the screen
            nMsg++
            ? ""
            ? "Mailnr.: " + ALLTRIM(STR(nMsg))
            ?      "--------Flags--------"
            ? LEFT("Msg unread        : " + ALLTRIM(STR(nRead        ))  , 78)
            ? LEFT("Receipt requested : " + ALLTRIM(STR(nRecipRequest))  , 78)
            ? LEFT("Msg sent          : " + ALLTRIM(STR(nSent        ))  , 78)
            ?      "---------------------"
            ? LEFT("Subject  : " + cSubject         , 78)
            ? LEFT("Message  : " + cMessage         , 78)
            ? LEFT("Mess.Type: " + cMessageType     , 78)
            ? LEFT("Rec.Date : " + cDate            , 78)
            ? LEFT("Orig.Name: " + cOriginatorName  , 78)
            ? LEFT("Orig.Adr : " + cOriginatorAdress, 78)
            ? LEFT("Conv-ID  : " + cConversationID  , 78)
            for i=1 to nRecipients
                ? LEFT("Recip-Name-" + ALLTRIM(STR(i)) + ": " + aRecipName[i]   , 78)
                ? LEFT("Recip-Adr -" + ALLTRIM(STR(i)) + ": " + aRecipAdress[i] , 78)
            next
            for i=1 to nAttachments
                ? LEFT("Att.File  -" + ALLTRIM(STR(i)) + ": " + aAttachFile [i] , 78)
                ? LEFT("Att.Path  -" + ALLTRIM(STR(i)) + ": " + aAttachPath [i] , 78)
            next
            ? REPL("-",78)
//          MsgBox("Message " + ALLTRIM(STR(nMsg)))

            //--Mark message as read.
            if (nErr := DllExecuteCall( scDLLMarkAsRead )) != SUCCESS_SUCCESS
                break nErr
            endif

            //-- Skip to next message without deleting, Set DELETE_THEN_SKIP flag if current message
            //-- should be deleted before skipping
            nErr := DllExecuteCall (scDLLInboxSkip , SKIP_ONLY )
            if nErr == SUCCESS_SUCCESS
                loop
            elseif nErr == MAPI_E_NO_MESSAGES
                exit
            else
                break nErr
            endif
        enddo

//      MsgBox("All Messages processed")


    RECOVER USING nErr
        NotifyError(nErr)
    END SEQUENCE

    //--Finally close inbox, i.e free memory.
    DllExecuteCall(scDLLInboxClose)

return



// GetMessageItem  //
FUNCTION GetMessageItem ( nID , nItemPos )
local nBufSize
local cBuffer
local nErr

    nBufSize := DllExecuteCall( scDLLAskBufferSize , nID  , nItemPos )
    cBuffer  := SPACE(nBufSize)
    nErr     := DllExecuteCall( scDLLStuffBuffer   , nID  , nItemPos , @cBuffer , nBufSize)

    if nErr != SUCCESS_SUCCESS
        break nErr
    endif

return cBuffer
//*************************************************************************** GetMessageItem

// NotifyError //
PROCEDURE NotifyError( nErr )
local cErr
    do case
        case nErr==SUCCESS_SUCCESS                ; cErr := "Successful!"
        case nErr==MAPI_USER_ABORT                ; cErr := "USER_ABORT              "
        case nErr==MAPI_E_FAILURE                 ; cErr := "FAILURE                 "
        case nErr==MAPI_E_LOGIN_FAILURE           ; cErr := "LOGIN_FAILURE           "
        case nErr==MAPI_E_DISK_FULL               ; cErr := "DISK_FULL               "
        case nErr==MAPI_E_INSUFFICIENT_MEMORY     ; cErr := "INSUFFICIENT_MEMORY     "
        case nErr==MAPI_E_ACCESS_DENIED           ; cErr := "ACCESS_DENIED           "
        case nErr==MAPI_E_TOO_MANY_SESSIONS       ; cErr := "TOO_MANY_SESSIONS       "
        case nErr==MAPI_E_TOO_MANY_FILES          ; cErr := "TOO_MANY_FILES          "
        case nErr==MAPI_E_TOO_MANY_RECIPIENTS     ; cErr := "TOO_MANY_RECIPIENTS     "
        case nErr==MAPI_E_ATTACHMENT_NOT_FOUND    ; cErr := "ATTACHMENT_NOT_FOUND    "
        case nErr==MAPI_E_ATTACHMENT_OPEN_FAILURE ; cErr := "ATTACHMENT_OPEN_FAILURE "
        case nErr==MAPI_E_ATTACHMENT_WRITE_FAILURE; cErr := "ATTACHMENT_WRITE_FAILURE"
        case nErr==MAPI_E_UNKNOWN_RECIPIENT       ; cErr := "UNKNOWN_RECIPIENT       "
        case nErr==MAPI_E_BAD_RECIPTYPE           ; cErr := "BAD_RECIPTYPE           "
        case nErr==MAPI_E_NO_MESSAGES             ; cErr := "NO_MESSAGES             "
        case nErr==MAPI_E_INVALID_MESSAGE         ; cErr := "INVALID_MESSAGE         "
        case nErr==MAPI_E_TEXT_TOO_LARGE          ; cErr := "TEXT_TOO_LARGE          "
        case nErr==MAPI_E_INVALID_SESSION         ; cErr := "INVALID_SESSION         "
        case nErr==MAPI_E_TYPE_NOT_SUPPORTED      ; cErr := "TYPE_NOT_SUPPORTED      "
        case nErr==MAPI_E_AMBIGUOUS_RECIPIENT     ; cErr := "AMBIGUOUS_RECIPIENT     "
        case nErr==MAPI_E_MESSAGE_IN_USE          ; cErr := "MESSAGE_IN_USE          "
        case nErr==MAPI_E_NETWORK_FAILURE         ; cErr := "NETWORK_FAILURE         "
        case nErr==MAPI_E_INVALID_EDITFIELDS      ; cErr := "INVALID_EDITFIELDS      "
        case nErr==MAPI_E_INVALID_RECIPS          ; cErr := "INVALID_RECIPS          "
        case nErr==MAPI_E_NOT_SUPPORTED           ; cErr := "NOT_SUPPORTED           "
        otherwise                                 ; cErr := "Unknown Mapi Error"

    endcase
    // Zeile kann deaktiviert werden
    // MsgBox(cErr)

return
Zuletzt geändert von MichaMB am Di, 11. Aug 2015 22:07, insgesamt 1-mal geändert.
lG
Micha

Benutzeravatar
AUGE_OHR
Marvin
Marvin
Beiträge: 10381
Registriert: Do, 16. Mär 2006 8:55
Wohnort: Hamburg

Re: Outlook 2007 display()-Fehler

Beitrag von AUGE_OHR » Mi, 05. Aug 2015 18:00

wie ich schon sagte solltes du es im Thread laufen lassen und den Code "anhalten" während der Thread läuft.

Code: Alles auswählen

// im ganzen PRG "sichtbar"
STATIC lisRunning := .F.

PROCEDURE SENDONBRITHDAY(cAdresses,cSubject,cMessage)
   LOCAL cAttachments := ""
   LOCAL nFlag        := NOFLAG
   LOCAL oMAPI
   LOCAL Homepath := LEFT( APPNAME( .T. ), LEN( APPNAME( .T. ) ) - LEN( APPNAME( .F. ) ) )

   //
   // so und nun einen Thread starten, dann funktioniert es
   //
   oMAPI := Thread() :new()
   oMAPI:start( "SENDNOW", cAdresses, cSubject, cMessage, cAttachments, nFlag )
   SLEEP( 100 )
   DO WHILE lisRunning = .T.
      SLEEP( 10 )
   ENDDO
   SLEEP( 100 )

   CurDrive( SUBSTR( Homepath, 1, 1 ) )
   CURDIR( Homepath )
RETURN


PROCEDURE SENDNOW( cAdresses, cSubject, cMessage, cAttachments, nFlag )
...
   // Flag setzten
   lisRunning := .T.

   BEGIN SEQUENCE
      // hier dein Code
   RECOVER USING nErr
   END SEQUENCE

   // Flag ausschalten
   lisRunning := .F.
RETURN
gruss by OHR
Jimmy

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2007 display()-Fehler

Beitrag von MichaMB » Di, 11. Aug 2015 11:50

Hallo Jimmy,

leider komme ich mit deinem Beispiel ueberhaupt nicht weiter. Alle Suchen im Forum ergeben wieder andere Ansaetze mit komplett anderer Programmierung.
(Einzelversenden ueber Outlook mit Popup funktioniert einwandfrei, ich moechte aber alle Emails der Datenbankadressen auf einmal versenden)
Habe meinen Code entsprechend umprogrammiert und als Beispiel nur 5 Datensaetze der Datenbank "KUMAIL.DBF" zum abarbeiten in das Proc. Sendnowl eingefuegt.
Nun sollen diese Datensaetze vor jedem Skip versendet werden. Dazu bedarf es noch des Sendbefehles vor dem skip ?
habe leider keine Ahnung wie diese Befehlszeile(n) lautet(n)
hier das Programm:

Code: Alles auswählen

#pragma library( "ascom10.lib" )
#include "Appevent.ch"
#include "Dmlb.ch"
#include "outlook.ch"
#include "dll.ch"
#include "common.ch"

//--error codes from MAPI.H
#define SUCCESS_SUCCESS                     0
#define MAPI_USER_ABORT                     1
#define MAPI_E_FAILURE                      2
#define MAPI_E_LOGIN_FAILURE                3
#define MAPI_E_DISK_FULL                    4
#define MAPI_E_INSUFFICIENT_MEMORY          5
#define MAPI_E_ACCESS_DENIED                6
#define MAPI_E_TOO_MANY_SESSIONS            8
#define MAPI_E_TOO_MANY_FILES               9
#define MAPI_E_TOO_MANY_RECIPIENTS          10
#define MAPI_E_ATTACHMENT_NOT_FOUND         11
#define MAPI_E_ATTACHMENT_OPEN_FAILURE      12
#define MAPI_E_ATTACHMENT_WRITE_FAILURE     13
#define MAPI_E_UNKNOWN_RECIPIENT            14
#define MAPI_E_BAD_RECIPTYPE                15
#define MAPI_E_NO_MESSAGES                  16
#define MAPI_E_INVALID_MESSAGE              17
#define MAPI_E_TEXT_TOO_LARGE               18
#define MAPI_E_INVALID_SESSION              19
#define MAPI_E_TYPE_NOT_SUPPORTED           20
#define MAPI_E_AMBIGUOUS_RECIPIENT          21
#define MAPI_E_MESSAGE_IN_USE               22
#define MAPI_E_NETWORK_FAILURE              23
#define MAPI_E_INVALID_EDITFIELDS           24
#define MAPI_E_INVALID_RECIPS               25
#define MAPI_E_NOT_SUPPORTED                26

//--ID´s for Message items
#define ID_SUBJECT                0
#define ID_MESSAGE                1
#define ID_MESSAGE_TYPE           2
#define ID_DATE                   3
#define ID_ORIGINATOR_NAME        4
#define ID_ORIGINATOR_ADRESS      5
#define ID_RECIPIENT_NAME         6
#define ID_RECIPIENT_ADRESS       7
#define ID_ATTACHMENT_PATHNAME    8
#define ID_ATTACHMENT_FILENAME    9
#define ID_CONVERSATION_ID        10

//--Message Flags
#define NOFLAG                    0
#define FLAG_UNREAD               1
#define FLAG_RECEIPT_REQUESTED    2
#define FLAG_SENT                 4

//--SKIP Flags
#define SKIP_ONLY                 0
#define DELETE_THEN_SKIP          1

STATIC lisRunning := .F.

Procedure emmailou


 // "MBasche@T-Online.de;" + "info@MichaelBasche.de;" + "CC:MBSkat@T-Online.de;" + "BCC:info@Skat-Pforzheim.de"
    //
   Public cAdresses    := (Emilwer)
   Public cSubject     := (Betrmail)

//   local cMessage     := (infmess0) + (Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
   Public cMessage     := (infmess0)
   //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
   // Local cAttachments :=  &Anhangx
   Public cAttachments :=  (Anhangx)
   Public nFlag        :=  NOFLAG
   Public nErr

  //   LOCAL Homepath := LEFT( APPNAME( .T. ), LEN( APPNAME( .T. ) ) - LEN( APPNAME( .F. ) ) )
  //  Local cAdresses    := (Emilwer)
  //  local cSubject     := (Betrmail)
  //  local cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
  //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
  //  Local cAttachments :=  &Anhangx
  //  local nFlag        :=  NOFLAG


  // Grundeinstellungen erfolgen in Global*.PRG (MAIN)  laut Programm-Anmeldung User
  // Emailadresse Empf„nger =  cAdresses  eventuell „ndern
  // public betrmail = cSubject   eventuell „ndern
  // public Anlage1 = cAttachments  eventuell „ndern
  // z.B. cAttachments cAttachments := (verzword)+ "/BUEPLogo.PDF"
  // w„hlt die Anzahl der Anh„nge aus, je nach Emailart mit 1 2 oder 3 Anh„ngen
  // Public AnzAnhaenge   ANzahl in VZerstna vorgegeben
  // ist die Variable die die Anh„nge fr
  // Public Anhangx
  // wenn Nutzer geprft und ok Variablen belegen
  // public Emilwer   Emailadresse Empf„nger =  cAdresses
  // Vorbelegung fr Anrede und Gráe in Email
  // public PERSWER
  // public betrmail = cSubject
  // public Anlage = cAttachments
  // Public infmess0      Text in mail = cMessage   Sehr geehrte Damen und Herren oder Hallo
  // Public infmess1   Text um was es geht
  // Public infmess2  Gruáformel   Mit freundlichen Gráen   bzw.   Viele Gráe
  // Public infmess3    Gesch„ftsfhrer
  // Public infmess3b   Unterzeichner
  // Public infmess3c   Abteilung
  // Public infmess4    Name Firma
  // Public infmess5    Firmensitz
  // Public infmess6    Web und EMail
  // Public infmess7    bei GMBH Registergericht und Nummer
  // Public infmess8    Registrierungsstelle des Vermittlers
  // Public infmess9    www.vermittlerregister.info
  // Public infmess10  Art der T„tigkeit  und   Nummer
  // Public infmess11  Anschrift Gewerbeamt
  // Public infmess12   Versicherung und Nummer

   set default to (substr(FESTWO,1,1) + ":")
   set path to (substr(FESTWO,1,1) + ":")
   set default to (verzword)
   SET PATH to (verzword)

   if firmist = .t.
     store ConvToAnsiCP("Newsletter") to ersit400
     store (ersit400) to betrmail
     store '"' + (verzword) + '\' + ConvToAnsiCP('NEWSG.PDF') + '"' to ersitz17b
     store (ersitz17b) to Anhangx
   else
     store ConvToAnsiCP("Newsletter") to ersit400
     store (ersit400) to betrmail
     store '"' + (verzword) + '\' + ConvToAnsiCP('NEWSP.PDF') + '"' to ersitz17b
     store (ersitz17b) to Anhangx
   endif

   cSubject     := (Betrmail)
   cAttachments :=  &Anhangx


   set default to (substr(FESTWO,1,1) + ":")
   set path to (substr(FESTWO,1,1) + ":")
   set default to (verzexe)
   SET PATH to (verzexe)

  do sendnews


return



PROCEDURE SENDNEWS( cAdresses, cSubject, cMessage, cAttachments, nFlag )

   //

   LOCAL oMAPI
   Local Homepath := (verzexe)
   // so und nun einen Thread starten, dann funktioniert es
   //
   oMAPI := Thread() :new()
   oMAPI:start( "SENDNOW", cAdresses, cSubject, cMessage, cAttachments, nFlag )
   SLEEP( 100 )
   DO WHILE lisRunning = .T.
      SLEEP( 10 )
   ENDDO
   SLEEP( 100 )

   CurDrive( SUBSTR( Homepath, 1, 1 ) )
   CURDIR( Homepath )
RETURN


PROCEDURE SENDNOW( cAdresses, cSubject, cMessage, cAttachments, nFlag )

   // Flag setzen


   lisRunning := .T.

   BEGIN SEQUENCE

   // hier dein Code

   Public MerkeX
   store "  " to infmess1
   store 1 to AnzAnhaenge
   set default to (substr(FESTWO,1,1) + ":")
   set path to (substr(FESTWO,1,1) + ":")
   set default to (verzdat)
   SET PATH to (verzdat)


   use
   sele j
   use KUMAIL.dbf
   go top


   // Anrede in der Email
   do while .not. eof()
      IF upper(KUMAIL->Persdu) = "D"
        if upper(KOMO) = 'BUE' .or. upper(KOMO) = 'KUE' .or. upper(KOMO) = 'WF' .or. upper(KOMO) = 'WV' .or. upper(KOMO) = 'AK'
          store "Sehr geehrte Damen und Herren," to infmess0
        else
          if firmist = .t.
            if ZEICHINH = 1
              store "Hallo " + rtrim(KUMAIL->Vorname) + "," to infmess0
            else
              store "Hallo " + rtrim(KUMAIL->PPname) + "," to infmess0
            endif
          else
            store "Hallo " + rtrim(KUMAIL->Vorname) + "," to infmess0
          endif
        endif
      else
        if upper(KOMO) = 'BUE' .or. upper(KOMO) = 'KUE' .or. upper(KOMO) = 'WF' .or. upper(KOMO) = 'WV' .or. upper(KOMO) = 'AK'
          store "Sehr geehrte Damen und Herren," to infmess0
        else
          if firmist = .t.
            if ZEICHINH = 1
              DO CASE
                CASE KUMAIL->ANR = "Praxis "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Firma  "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "WEG    "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Z-Prax."
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Verein "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "GBR    "
                  if upper(j->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(j->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Bro   "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Herrn  "
                  store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                CASE KUMAIL->ANR = "Frau   "
                  store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
              ENDCASE
            else
              if ZEICHINH = 2
                DO CASE
                  CASE j->ANR = "Praxis "
                    if upper(j->PG) = "W"
                      store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                    else
                      if upper(j->PG) = "M"
                        store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                      else
                        store "Sehr geehrt"+ rtrim(j->Floskel) +"," to infmess0
                      endif
                    endif
                  CASE j->ANR = "Firma  "
                    if upper(j->PG) = "W"
                      store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                    else
                      if upper(j->PG) = "M"
                        store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                      else
                        store "Sehr geehrt"+ rtrim(j->Floskel) +"," to infmess0
                      endif
                    endif
                  CASE j->ANR = "WEG    "
                    if upper(j->PG) = "W"
                      store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                    else
                      if upper(j->PG) = "M"
                        store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                      else
                        store "Sehr geehrt"+ rtrim(j->Floskel) +"," to infmess0
                      endif
                    endif
                  CASE j->ANR = "Z-Prax."
                    if upper(j->PG) = "W"
                      store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                    else
                      if upper(j->PG) = "M"
                        store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                      else
                        store "Sehr geehrt"+ rtrim(j->Floskel) +"," to infmess0
                      endif
                    endif
                  CASE j->ANR = "Verein "
                    if upper(j->PG) = "W"
                      store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                    else
                      if upper(j->PG) = "M"
                        store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                      else
                        store "Sehr geehrt"+ rtrim(j->Floskel) +"," to infmess0
                      endif
                    endif
                  CASE j->ANR = "GBR    "
                    if upper(j->PG) = "W"
                      store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                    else
                      if upper(j->PG) = "M"
                        store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                      else
                        store "Sehr geehrt"+ rtrim(j->Floskel) +"," to infmess0
                      endif
                    endif
                  CASE j->ANR = "Bro   "
                    if upper(j->PG) = "W"
                      store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                    else
                      if upper(j->PG) = "M"
                        store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                      else
                        store "Sehr geehrt"+ rtrim(j->Floskel) +"," to infmess0
                      endif
                    endif
                  CASE j->ANR = "Herrn  "
                    store "Sehr geehrter Herr"+ " " + rtrim(j->PaName) +"," to infmess0
                  CASE j->ANR = "Frau   "
                    store "Sehr geehrte Frau"+ " " + rtrim(j->PaName) +"," to infmess0
                ENDCASE
              else
                if upper(j->PG) = "W"
                  store "Sehr geehrte Frau"+ " " + rtrim(j->Name) +"," to infmess0
                else
                  store "Sehr geehrter Herr"+ " " + rtrim(j->Name) +"," to infmess0
                endif
              endif
            endif
          else
            if KUMAIL->Floskel = "e Damen und Herren"
              store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
            else
              if upper(KUMAIL->KG) = "W"
                store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
              else
                store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
              endif
            endif
          endif
        endif
      endif
      *store "sehr geehrte Damen und Herren" to infmess0

      store ConvToAnsiCP(infmess0) to infmess0

      // Grussformel in der Email

      IF upper(KUMAIL->Persdu) = "D"
        if upper(KOMO) = 'BUE' .or. upper(KOMO) = 'KUE' .or. upper(KOMO) = 'WF' .or. upper(KOMO) = 'WV' .or. upper(KOMO) = 'AK'
          store "Mit freundlichen Gráen" to infmesss
        else
          store "Viele Gráe" to infmesss
        endif
      else
        store "Mit freundlichen Gráen" to infmesss
      endif
      store ConvToAnsiCP(infmesss) to infmesss

      // Email Text 2-Zeilig    infmess1 und infmess2
      // "MXXXXXXXXX@T-Online.de;" + "info@MXXXXXXXXXXXXXXX.de;" + "CC:MXXXXXXXXXXXX@T-Online.de;" + "BCC:info@SXXXXXXXXXXXXXXXXX.de"

      if firmist = .t.
        if ZEICHINH = 1
          store alltrim(KUMAIL->EMAIL) to Emilwer
          if len(Emilwer) < 2
            store alltrim(KUMAIL->EAMAIL) to Emilwer
          else
            if len(Emilwer) < 2
              store '"Keine E-Mail von Kunde, Arbeitgeber gespeichert"' to EMILWER
            endif
          endif
        else
          store alltrim(KUMAIL->EPMAIL) to Emilwer
          if len(Emilwer) < 2
            store alltrim(KUMAIL->EAMAIL) to Emilwer
          else
            if len(Emilwer) < 2
              store '"Keine E-Mail von Partner, Arbeitgeber gespeichert"' to EMILWER
            endif
          endif
        endif
      else
        store alltrim(KUMAIL->EMAIL) to Emilwer
        if len(Emilwer) < 2
          store alltrim(KUMAIL->EPMAIL) to Emilwer
          if len(Emilwer) < 2
            store alltrim(KUMAIL->EAMAIL) to Emilwer
          else
            if len(Emilwer) < 2
              store '"Keine E-Mail von Kunde, Partner, Arbeitgeber gespeichert"' to EMILWER
            endif
          endif
        endif
      endif
      IF upper(KUMAIL->Persdu) = "D"
        store "in der Anlage erh„ltst Du unseren Newsletter mit aktuellen Informationen." to infmess1
        store "Viel Spaá beim lesen des Newsletters, gerne stehen wir Dir fr weitere Fragen zur Verfgung." to infmess2
      else
        store "in der Anlage erhalten Sie unseren Newsletter mit aktuellen Informationen." to infmess1
        store "Viel Spaá beim lesen des Newsletters, gerne stehen wir Ihnen fr weitere Fragen zur Verfgung." to infmess2
      endif

      store ConvToAnsiCP(infmess1) to infmess1
      store ConvToAnsiCP(infmess2) to infmess2
      store ConvToAnsiCP(EMILWER) to EMILWER
      cAdresses    := (Emilwer)
      cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)

      skip
    enddo

    set default to (substr(FESTWO,1,1) + ":")
    set path to (substr(FESTWO,1,1) + ":")
    set default to (verzexe)
    SET PATH to (verzexe)

    // Ende hier mein Code

    RECOVER USING nErr

   END SEQUENCE


   // Flag ausschalten
   lisRunning := .F.

RETURN
lG
Micha

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2007 display()-Fehler

Beitrag von brandelh » Di, 11. Aug 2015 12:57

Ich habe mal versucht oben durchzusteigen, mein erster Rat ist, die unterschiedlichen DO CASE ... Blöcke in Funktionen auszulagern,
bei der länge des Codes, kann man nur verzweifeln ;-)

VORTEIL:

1. besser lesbar
2. eine Funktion steuert alles und kann leicht geändert werden
3. Die Funktion kann auch in anderen PRG verwendet werden.

Beispiel, wer soll diese Listings lesen ?

So wie ich das sehe wird hier die Variable infmess0 mit der Anrede versehen ...

Code: Alles auswählen


     IF upper(KUMAIL->Persdu) = "D"
        if upper(KOMO) = 'BUE' .or. upper(KOMO) = 'KUE' .or. upper(KOMO) = 'WF' .or. upper(KOMO) = 'WV' .or. upper(KOMO) = 'AK'
          store "Sehr geehrte Damen und Herren," to infmess0
        else
          if firmist = .t.
            if ZEICHINH = 1
              store "Hallo " + rtrim(KUMAIL->Vorname) + "," to infmess0
            else
              store "Hallo " + rtrim(KUMAIL->PPname) + "," to infmess0
            endif
          else
            store "Hallo " + rtrim(KUMAIL->Vorname) + "," to infmess0
          endif
        endif
      else
        if upper(KOMO) = 'BUE' .or. upper(KOMO) = 'KUE' .or. upper(KOMO) = 'WF' .or. upper(KOMO) = 'WV' .or. upper(KOMO) = 'AK'
          store "Sehr geehrte Damen und Herren," to infmess0
        else
          if firmist = .t.
            if ZEICHINH = 1
              DO CASE
                CASE KUMAIL->ANR = "Praxis "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Firma  "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "WEG    "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Z-Prax."
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Verein "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "GBR    "
                  if upper(j->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(j->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Bro   "
                  if upper(KUMAIL->KG) = "W"
                    store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                  else
                    if upper(KUMAIL->KG) = "M"
                      store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                    else
                      store "Sehr geehrt"+ rtrim(KUMAIL->Floskel) +"," to infmess0
                    endif
                  endif
                CASE KUMAIL->ANR = "Herrn  "
                  store "Sehr geehrter Herr"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
                CASE KUMAIL->ANR = "Frau   "
                  store "Sehr geehrte Frau"+ " " + rtrim(KUMAIL->Name) +"," to infmess0
              ENDCASE
            e
So wie ich das sehe wird hier die Variable infmess0 mit der Anrede versehen ...
im Anwendungsprogramm bei der Senderoutine ...

Code: Alles auswählen

    // Anrede speichern, alle abhängigen Infos übergeben ...
    infmess0 := GetAnredeBrief1( KUMAIL->Persdu, KOMO, firmist, nZEICHINH, KUMAIL->Vorname, KUMAIL->Name, KUMAIL->PPname, KUMAIL->ANR, ... )
Bei dieser Zeile erkennt JEDER SOFORT, dass dort nichts relevantes steht und liest weiter um das Problem zu finden !

In einer anderen PRG mit Funktionen steht dann der ganze Do Case Zweig, OHNE BEZUG zu Dateien oder externen Variablen:

Code: Alles auswählen

// Anrede erzeugen, die Variablen (lokal) ersetzten die früheren Feldzugriffe. Funktionsname möglich sprechend wählen !
function GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, cZEICHINH, cVorname, cName, cPPname, cANR, ... )
     local cAnrede := ""
     // Parameter richten wie man sie unten braucht 
     cPersdu    := upper(cPersdu)
     cKOMO     := upper(cKOMO)
     cVorname := alltrim(cVorname)
     cName    := alltrim(cName)
     ...
     IF cPersdu = "D"
        if cKOMO = 'BUE' .or. cKOMO = 'KUE' .or. cKOMO = 'WF' .or. cKOMO = 'WV' .or. cKOMO = 'AK'
           // store "Sehr geehrte Damen und Herren," to infmess0    ---- das geht heute schneller
           cAnrede := "Sehr geehrte Damen und Herren,"
        else
          if Isfirmist   //  = .t. kann man weglassen
            if nZEICHINH = 1
               cAnrede := "Hallo " + cVorname + ","
            else
     ...
return cAnrede
nun zu deinem Problem. Wenn ich Jimmy richtig verstehe ruft SEND den direkten Versand auf (inkl. Nachbearbeitung) während POST im Postfach ablegt.
Falls es das POSTAUSGANGS-Fach ist, müsste man noch SENDEN in outlook wählen damit was gesendet wird.

Da ich outlook nicht nutze, kann ich das leider nicht prüfen, aber für den Massenversand solcher Sachen nutzt man eigentlich den Weg über SMTP Server (also den Mailserver des Providers wie auch outlook) nur hat man das dann nicht im Protokoll von outlook.

Sollen die Newsletter in Oulook protokolliert abgelegt werden ?

Aus der Erinnerung heraus weiß ich, dass Microsoft das Versenden im Hintergrund wegen der SPAM und Rechteproblematik stark eingeschränkt hat.
Gruß
Hubert

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2013 und Mail Massenversand

Beitrag von brandelh » Di, 11. Aug 2015 13:21

Ich habe dieses Thema hier hin verschoben, da es mit dem ursprünglichen nicht viel zu tun hatte:

http://www.xbaseforum.de/viewtopic.php?f=50&t=6041
Gruß
Hubert

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2013 und Mail Massenversand

Beitrag von MichaMB » Di, 11. Aug 2015 14:30

lieber Hubert,

herzlichen Dank für Deine Mühe das PRG zu ordnen, ich schaue das mal durch und versuche das nachzuvollziehen und zu verinnerlichen =D>
zu Deiner Frage Outlook oder SMTP ?
Es wäre schön, wenn man zum Testen sieht wer alles die E-Mail (Name, Anrede E-Mal-Adresse alles richtig ??) bekommen hat, wenn es funktioniert ist es nicht mehr wichtig, da ja die Datenbank selektiert wurde und jeder das gleiche Schreiben bekommen hat, Rückläufer falsche E-Mail wäre noch ganz gut
Da ich mir ja selbst 2 - 3 E-Mails auf verschiedene E-Mail-Adressen senden kann, sehe ich dort ja auch ob es klappt. (Eingang dann mit Outlook)
Ein Zähler zum Vergleich mit der Anzahl der Datenbankadressen würde auch schon helfen
Also kann die Massenmail ausserhalb von Outlook gesendet werden sofern das eine dauerhafte Lösung ist
(habe da einiges, noch nicht Verstandenes, wegen den künftigen Verschlüsselungen im Forum gelesen)
lG
Micha

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2013 und Mail Massenversand

Beitrag von brandelh » Di, 11. Aug 2015 14:43

MichaMB hat geschrieben:(habe da einiges, noch nicht Verstandenes, wegen den künftigen Verschlüsselungen im Forum gelesen)
das verstehe ich jetzt nicht, aber um zu sehen wer alles etwas bekommen hat, kann man ein Protokoll beim SMTP Versand führen.
Als Absender wird ja (normalerweise) die eigene Adresse benutzt, dann bekommt man auf jeden Fall die Rückantwort oder Zustellfehler.

Möglich ist auch sich oder eine Kontrolladresse als BCC anzugeben, dann sieht es der andere nicht.

Für den automatischen Versand mit ASINET (SMTP) habe ich Beispiele, mal sehen ob ich daraus was einfaches bauen kann...

Habt Ihr die ASINET (also Profsub) ?

Wenn nicht, kann man auch andere nutzen ...
Gruß
Hubert

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2013 und Mail Massenversand

Beitrag von MichaMB » Di, 11. Aug 2015 15:09

Hallo Hubert,
schon ist die erste Frage aufgetaucht

Code: Alles auswählen

function GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, cZEICHINH, cVorname, cName, cPPname, cANR, ... )
     local cAnrede := ""
     // Parameter richten wie man sie unten braucht 
     cPersdu    := upper(cPersdu)
     cKOMO     := upper(cKOMO)
     cVorname := alltrim(cVorname)
     cName    := alltrim(cName)

wäre das mit der Datenbank KUMAIL.dbf wie nachstehend?
     cPersdu    := upper(KUMAIL->Persdu)
     cKOMO      := upper(cKOMO) // die Original-Variable heisSt KOMO, muss trotzdem das c für die Art der Variable davor?
     cVorname  := alltrim(KUMAIL->Vorname)
     cName      := alltrim(KUMAIL->Name)
     cPPname   := alltrim(KUMAIL->PPname)
     cPAName   := alltrim(KUMAIL->PAName)
     cANR         := alltrim(KUMAIL->ANR)
     cFLOSKEL  := alltrim(KUMAIL->Floskel)
     ...
     IF cPersdu = "D"
        if cKOMO = 'BUE' .or. cKOMO = 'KUE' .or. cKOMO = 'WF' .or. cKOMO = 'WV' .or. cKOMO = 'AK'
           // store "Sehr geehrte Damen und Herren," to infmess0    ---- das geht heute schneller
           cAnrede := "Sehr geehrte Damen und Herren,"
        else
          if Isfirmist   //  = .t. kann man weglassen
            if nZEICHINH = 1
               cAnrede := "Hallo " + cVorname + ","
            else
     ...
return cAnrede
um die Parameter zu richten...
wie ist es dann mit Numerischen Variablen wie " nZEICHINH = 1 "
muss diese
a) nZEICHINH := (nZEICHINH) // dann in Variable richten

oder
cZEICHINH := str(nZEICHINH,10)
oder
gar nichts ?

B) function GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, cZEICHINH, cVorname, cName, cPPname, cANR, ... )

müste dann
function GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, nZEICHINH, cVorname, cName, cPPname, cANR, ... )
heißen?

c) logische Variablen // bei Variablen richten z.B. die Variable " FIRMIST "
du hast diese dann umbenannt in " ISFIRMIST " // soll bedeuten es ist eine Firma, steht IS.. für ist wahr?

liebe Grüße

Micha
Zuletzt geändert von MichaMB am Di, 11. Aug 2015 15:52, insgesamt 1-mal geändert.
lG
Micha

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2013 und Mail Massenversand

Beitrag von brandelh » Di, 11. Aug 2015 15:12

Das ist die Funktion, die ich für ALLE eMail-Versandaufträge eines Programmes nutze.
Idealerweise funktionieren solche Funktionen unabhängig von anderen Programmteilen sodass man sie einfach austauschen kann.

Code: Alles auswählen

*----------------------------------------------------------------------------------------
// das haben viele schon definiert, nicht doppelt setzen 
#define CRLF chr(13)+chr(10)   // lange Texte durch Kürzel ersetzten CRLF kennt man 

#pragma library("ASINET10.LIB")
*----------------------------------------------------------------------------------------
function GetSmtpServer(cNewSmtpServer)
   static cSmtpServer := "mein.SMTPServer.xyz"
   if ! empty(cNewSmtpServer)
      cSmtpServer := cNewSmtpServer
   endif
return cSmtpServer
*----------------------------------------------------------------------------------------
Function SendAsinet(aEmpfaenger,cBetreff,cText,cProgPfad,aAttachFile,cAntwortAdresse) 
   local lOK        := .f.
   LOCAL oLog       := LogWriter():new() // das ist ein Beispiel von Alaska, die log landet in einer Datei auf der Festplatte
   LOCAL oSmtp      := SMTPClient():new( GetSmtpServer(),,, oLog, 2 ) // über Funktion oder direkt den Namen eingeben, z.B. mail.gmx.de
   LOCAL oSender    := MailAddress():new( "Newsletter von Infotek <Info.Infotek@gmx.de>" )  // das ist die Adresse die der Empfänger als Sender SIEHT !
   LOCAL oMail      := MIMEMessage():new()

   DEFAULT aEmpfaenger TO  { "Hans.Testmann@web.de" } // eigene eMailadresse und man bekommt alle eMails OHNE Empfänger
   DEFAULT cBetreff    TO    "SendAsinet - Betreff fehlte"
   DEFAULT cText       TO  ( "SendAsinet - Text von eMail fehlte" + CRLF )

   set alternate to AsinetLog.txt
   set alternate on 
   set console off // für GUI nötig

   ? ProcName()+" - ENDE mit lOK=",lOK // für eventuellen Debugger

   oMail:setFrom     ( oSender     )
   oMail:setSubject  ( cBetreff    )
   oMail:setMessage  ( cText       )
   aeval(aEmpfaenger, {|cEmp| oMail:addRecipient(MailAddress():new(cEmp) ) }) // kann man auch mit for next machen
   // Verbessert einen AsiNet Fehler !
   oMail:addHeader( "Date", TimeStampSMTP() )
   // Man kann eine andere eMail-Adresse als die Sendeadresse für den Empfang von Antworten einstellen
   if ! empty(cAntwortAdresse)
      oMail:addHeader( "Reply-To", cAntwortAdresse )
   endif

   if ! aAttachFile = NIL
      aeval(aAttachFile, {|cFile| oMail:attachFile( cFile ) })
   endif

   IF oSmtp:connect(  cSMTPUSER, cSMTPPW )
      IF oSmtp:send( oMail )
         lOK := .t.
         ? "Message sent"
      ELSE
         ? "Unable to deliver message"
      ENDIF

      oSmtp:disconnect()
   ELSE
      ? "Unable to connect to mail server"
   ENDIF

   set alternate to


RETURN lOK


   /*
    * User-defined class for log-data processing
    */
   CLASS LogWriter
      EXPORTED:

      INLINE METHOD write( cLogData )
         ? cLogData
      RETURN

   ENDCLASS

// diese Funktion ist wegen einem Fehler in Asinet nötig um den Zeitstempel richtig zu übergeben

*----------------------------------------------------------------------------------------
#include "Dll.ch"
#define TIME_ZONE_ID_INVALID   0xFFFFFFFF
#define TIME_ZONE_ID_UNKNOWN   0
#define TIME_ZONE_ID_STANDARD  1
#define TIME_ZONE_ID_DAYLIGHT  2

function TimeStampSMTP() // aus der Wissensbasis

   local cST  := replicate(W2bin(0),8)  // TimeStamp 8x Word = SYSTEMTIME Struktur     16 End
   local cTZI := l2bin(0)+;             // LONG   Bias;             TZI _TimeZoneInfo   4   1-  4
                 space(64)+;            // WCHAR  StandardName[32];                    64   5- 68
                 replicate(W2bin(0),8)+;// SYSTEMTIME StandardDate;                    16  69- 84
                 l2bin(0)+;             // LONG   StandardBias;                         4  85- 88
                 space(64)+;            // WCHAR  DaylightName[ 32 ];                  64  89-152
                 replicate(W2bin(0),8)+;// SYSTEMTIME DaylightDate;                    16 153-168
                 l2bin(0)               // LONG       DaylightBias;                     4 169-172
                                        // wir brauchen hiervon nur die 3 Bias !
   local nTZI_Return, cTimeZoneInfo := ""
   local cTimeStamp, nH, x
   local nYear,nMonth,nDayOfWeek,nDay,nHour,nMinute,nSecond,nMilliseconds
   local nHourOffsetUTC, nMinuteOffsetUTC
   local nBias, nStandardBias, nDaylightBias
   local aDay   := { "Sun","Mon","Tue","Wed","Thu","Fri","Sat"}
   local aMonth := { "Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec" }


   nH := DllLoad("KERNEL32.DLL")

   DllCall(nH,DLL_STDCALL,"GetLocalTime",@cST)

   nTZI_Return := DllCall(nH,DLL_STDCALL,"GetTimeZoneInformation",@cTZI)
   if nTZI_Return = TIME_ZONE_ID_INVALID .or. nTZI_Return = TIME_ZONE_ID_UNKNOWN
      // bei ungültiger Zeitzonen Information UTC liefern
      // if TZI is invalid or unknown, use UTC.
      DllCall(nH,DLL_STDCALL,"GetSystemTime",@cST)
      cTimeZoneInfo := "???("+alltrim(str(nTZI_Return))+")"
      nBias         := 0
      nStandardBias := 0
      nDaylightBias := 0
   else
      nBias         := bin2l(substr(cTZI,  1,4))
      nStandardBias := bin2l(substr(cTZI, 85,4))
      nDaylightBias := bin2l(substr(cTZI,169,4))
   endif

   do case
      case nTZI_Return = TIME_ZONE_ID_STANDARD
           nBias := nBias + nStandardBias
      case nTZI_Return = TIME_ZONE_ID_DAYLIGHT
           nBias := nBias + nStandardBias + nDaylightBias
      otherwise
           nBias := 0
   endcase

   // SYSTEMTIME structure, the right sequence is important.
   // Reihenfolge ist wichtig, je 2 Byte, bei Stunde wird auch die SystemTime (UTC) ermittelt.
   x := 1
   nYear            := Bin2w( substr(cST,x,2)) ; x += 2
   nMonth           := Bin2w( substr(cST,x,2)) ; x += 2
   nDayOfWeek       := Bin2w( substr(cST,x,2)) ; x += 2
   nDay             := Bin2w( substr(cST,x,2)) ; x += 2
   nHour            := Bin2w( substr(cST,x,2)) ; x += 2
   nMinute          := Bin2w( substr(cST,x,2)) ; x += 2
   nSecond          := Bin2w( substr(cST,x,2)) ; x += 2
   nMilliseconds    := Bin2w( substr(cST,x,2)) // ENDE

   cTZI := cST := ""

   // ISO 8601 - wikipedia
   //
   // die BIAS Angaben beziehen sich immer auf  UTC = LOCAL + BIAS + ...
   // wir brauchen hier aber die Angabe       LOCAL = UTC - BIAS
   // denn     ...232010+0100 => LOKALEZEIT+UTC_Offset
   // The BIAS values have to be added on LOCAL time:   UTC = LOCAL + BIAS + ...
   // but we need it like                             LOCAL = UTC - BIAS
   // because  ...232010+0100 => LOCALTIME+UTC_Offset

   do case
      case nBias > 0
           cTZI := "-"
      case nBias < 0
           cTZI := "+"
           nBias := abs(nBias)
      otherwise
           cTZI := "Z"
   endcase

   if cTZI # "Z"
      nHourOffsetUTC   := int(nBias/60)
      nMinuteOffsetUTC := int(nBias - int(nHourOffsetUTC*60))
      cTZI += strZero(nHourOffsetUTC,2)+strZero(nMinuteOffsetUTC,2)
   endif

   // Windows nDayOfWeek geht von 0 bis 6, wir brauchen aber wie dow() 1 bis 7
   nDayOfWeek++ // 0 bis 6 -> 1 bis 7

   cTimeStamp := aDay[nDayOfWeek]+", "+StrZero(nDay,2,0)+" "+aMonth[nMonth]+" "+StrZero(nYear,4,0)+" "+time()+" "+cTZI

   // "Date: Mon, 24 Jan 2011 17:22:22 +0100"
   //       "Mon, 24 Jan 2011 17:22:22 +0100"

return cTimeStamp

Gruß
Hubert

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2013 und Mail Massenversand

Beitrag von brandelh » Di, 11. Aug 2015 15:41

Vorweg, grundsätzlich kann man Variablen benennen wie man will, aber ich halte mich an die ungarische Notation (wie ich sie zu URZEITEN mal gelernt habe) ...

cVar => String oder Char in Xbase++ ist das identisch
nVar => Numerisch
dVar => Datumstyp
l wäre dann für logisch, aber das ist mir zu schlecht lesbar, daher setze ich Is (nein keine gefährliche Gruppe ...) nach dem IST ES ... IS IT a logical ...
IsVar => logischer Datentyp

sVar => wird in anderen Sprachen häufig für Strings verwendet, da diese auch noch reine char Typen haben ... ähnlich wie iVar für Integer oder lVar für LONG Integer ...

nun zu den Fragen
MichaMB hat geschrieben:schon ist die erste Frage aufgetaucht

Code: Alles auswählen

function GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, cZEICHINH, cVorname, cName, cPPname, cANR, ... )
     local cAnrede := ""
     // Parameter richten wie man sie unten braucht 
hier habe ich die Variablen nach deinen Feldern benannt und den TYP vorangestellt, das kann man halten wie man will, aber es erleichtert mir die Übersicht.

MichaMB hat geschrieben: um die Parameter zu richten...
damit meine ich hier z.B. die Länge zu begrenzen, wenn man nur mit einem Buchstaben weiter vergleichen will, oder upper etc.
einmalig hier die Bedingungen schaffen (left(x,1), upper() etc.) statt danach immer wieder das gleiche im Vergleich zu schreiben.
Genauso kann es sein, dass der Datentyp verändert werden soll oder muss, aber nur wenn es Sinn macht.
MichaMB hat geschrieben: wie ist es dann mit Numerischen Variablen wie " nZEICHINH = 1 "
muss diese
a) nZEICHINH := (nZEICHINH) // dann in Variable richten
oder
b) cZEICHINH := str(nZEICHINH,10)
oder
c) gar nichts ?
Das kommt darauf an, wie ich die Variable später brauche !
Wenn ich z.b. Zahlenwerte benötige, übergebe ich Zahlenwerte und wandle NICHT um (c)

Deine Antwort a) macht nichts anderes als den Inhalt von (nZEICHINH) auszuwerten und an nZEICHINH zu übergeben.
Das Ergebnis wird hier nicht geändert, in dem Beispiel eine Zeitverschwendung ... es gibt Fälle wo es nötig sein kann, aber das ist exotisch.

Deine Antwort b) wäre richtig, wenn man in der Funktion nicht die Zahl, sondern einen Text mit dieser benötigt.
Beispiel in Funktion wird häufig das aufgerufen:

Code: Alles auswählen

function xyz(nID) 
..."Text "+alltrim(str(nID)) ... // "Text 341" nID bleibt gleich
dann macht es Sinn, nID umzusetzen und womöglich gleich auf Fehler zu prüfen !

Code: Alles auswählen

function xyz(nID) 
   local cID, cReturn
   if empty(nID) // NIL ODER 0 => Rückgabe ""
      cReturn := ""
   else
      cID := alltrim(str(cID))
      cReturn := "Text "+cID ... // "Text 341" nID bleibt gleich
return cReturn
Ich nutze Groß-/Kleinschreibung um besser lesen zu können was da steht, auch bei VariablenNamen ( <= )
c) logische Variablen // bei Variablen richten z.B. die Variable " FIRMIST "
du hast diese dann umbenannt in " ISFIRMIST " // soll bedeuten es ist eine Firma, steht IS.. für ist wahr?
IsFirmist ... erkenne ICH als logische Variable, die wahr oder falsch sein kann.
Wahr ist Standard, daher kann ich einfach schreiben...

Code: Alles auswählen

IF IsKeinKunde
   SchreibeInfo()
else
   ...
oder und das ist jedem selbst überlassen ob er ! oder .not. oder ... = .f. oder <> .t. schreibt

Code: Alles auswählen

IF ! IsKeinKunde
   SchreibeAblehnung()
else
   SchreibePreisInfo()
   ...
Gruß
Hubert

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2013 und Mail Massenversand

Beitrag von MichaMB » Di, 11. Aug 2015 15:59

Ok, damit komme ich weiter

Ich habe meine Frage noch bezüglich der Variablen die aus Datenbanken eingelesen werden genauer formuliert, so wie ich dich verstanden habe, ist das dann auch richtig den Datenbanknamen (oder Alias) anzugeben, oder?

lg
Micha
lG
Micha

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2013 und Mail Massenversand

Beitrag von brandelh » Di, 11. Aug 2015 16:11

Es ist wie zu dbase Zeiten erlaubt sich darauf zu verlassen, dass der richtige Selectbereich eingestellt ist.
Für kurze Sachen geht das ja OK, aber viel eleganter, sicherer und auch flexibler ist es so vorzugehen, wobei ICH nicht den Alias sondern eine Variable mit Select-Bereich nutze:

Code: Alles auswählen

cDatei := "Kunden"
use (cDatei) shared NEW  // (cDatei) so kann man eine Variable nach dem Inhalt auswerten und Kunden öffnen ohne Macro !
if neterr()
   ... Fehler abbruch oder ELSE nötig
endif
nKunde := select()   // ich nutze eine sprechenden Namen für den Selectbereich der Kunden-DBF, dieser wird dynamisch ausgelesen, auch in 1000 Fenstern !
// wenn index nötig ... eventuell auf existens prüfen und neu aufbauen
set index to (cDatei) // ich nutze CDX, Index und Dbf haben gleichen Namen, sonst ..

(nKunde)->(dbGoTop()) // hier ist es völlig egal in welchem Select-Bereich wir mittlerweile sind !
do while ! (nKunde)->(eof())
   ... und alle anderen sind zugreifbar
   (nRechnung)->(dblocate(...))
   ...
   (nKunde)->(dbSkip())
enddo
die Klammern sind nötig, weil der Selectbereich in einer Variablen steht, das ginge auch mit dem Alias in einer Variablen,
aber wenn man einen Alias verwendet den es nicht gibt, erhält man einen Laufzeitfehler !
Wenn man einen unbenutztern Selectbereich abfragt ist der nur EOF() !

MichGibtEsNicht->(used()) :arrow: Laufzeitfehler
(nMichGibtEsNicht->(used()) :arrow: .f.
Gruß
Hubert

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2013 und Mail Massenversand

Beitrag von MichaMB » Di, 11. Aug 2015 17:58

Hallo Hubert
vielen vielen Dank!
Mein Fleisch ist willig aber ob der Geist mithält?
Habe mal versucht den Programmcode mit Deinem Vorschlag umzusetzen.
Bitte schaue doch mal drüber ob es so ok ist, oder wo ich etwas falsch verstanden habe, auch gerade in Bezug auf die Datenbanken und select

Index ist bei mir *.TXT, habe ich in dem Beispiel nur wegen der "Programmier-Vollständigkeit" hinzugefügt, wird hier sonst nicht benötigt.
Die Funktion im Main.prg abspeichern?
oder in einem "Funktio.PRG" mit allen Funktionen welches als erstes PRG im Main aufgerufen wird?

Wenn soweit alles ok ist, kommt der nächste Schritt mit SMTP
Danke fürs drüber schauen

Code: Alles auswählen

   ConvToAnsiCP(infmess0) := GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, NZEICHINH, cVorname, cName, cPPname, cFloskel, cPG, cANR )            

// Anrede erzeugen, die Variablen (lokal) ersetzen die früheren Feldzugriffe. Funktionsname möglichst sprechend wählen !

function GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, NZEICHINH, cVorname, cName, cPPname, cFloskel, cPG, cANR )

     local cAnrede := ""                      // Public cAnrede :=""  falls in anderen Programmen gebraucht

     // Datenbank auswählen
     cDatei    := "KUMAIL"                   // die DBF ( Namen sprechend) um die es geht
     use (cDatei) shared new                 // DBF in neuem Arbeitsbereich öffnen
     nKumail   := select()                   // Arbeitsbereich (mit sprechendem Namen) benennen
     if .not. File("Kunamxy.NTX")              // Abfragen ob Index bereits existiert, andernfalls neu erzeugen
       Index on name to kunamxy.ntx          // Field-Name reicht, da die KuMail.DBF aus dem select-Bereich gewählt wurde und es da nur eine DBF gibt
     endif
     if .not. File("Kunrxy.NTX")             // Abfragen ob Index bereits existiert, andernfalls neu erzeugen
       Index on name to kunrxy.ntx           // Field-Name reicht, da die KuMail.DBF aus dem select-Bereich gewählt wurde und es da nur eine DBF gibt
     endif
     set index to Kunamxy,KUNRXY             // Der Datei in dem Select-Bereich  beide Index zufügen

     // Parameter richten wie man sie für die Do Case -Anwendungen benötigt

     cPersdu   := upper(Persdu)              // Datenbankfeld "D" = Kunde per Du
     cKOMO     := upper(cKOMO)               // Achtung Public Variable "KOMO" aus dem Vorprogramm vergeben
     cVorname  := alltrim(Vorname)
     cName     := alltrim(Name)
     cPPname   := alltrim(PPname)            // Partner Vorname
     cPAName   := alltrim(PAName)            // Partner Nachname
     cANR      := alltrim(ANR)               // Herrn, Frau, Firma, Praxis, WEG usw.
     cFLOSKEL  := alltrim(Floskel)           // Ergänzung nach sehr geehrt "e  Damen und Herren"  bzw. "er Herr"   bzw. "e Frau"
     cPG       := upper(PG)                  // M = Männlich W = weiblich
     ...

     // Do Case und IF- abfragen  zur Ermittlng des Inhalts der Variable cAnrede
     IF cPersdu = "D"
        if cKOMO = 'BUE' .or. cKOMO = 'KUE' .or. cKOMO = 'WF' .or. cKOMO = 'WV' .or. cKOMO = 'AK'
           cAnrede := "Sehr geehrte Damen und Herren,"
        else
          if Isfirmist   //  = .t. kann man weglassen
            if nZEICHINH = 1    // bei Firmen = 1 erster Inhaber  /   2 = 2. Inhaber
              cAnrede := "Hallo " + cVorname + ","
            else
              cAnrede := "Hallo " + cPPname + ","
            endif
          else
            cAnrede := "Hallo " + cVorname + ","
          endif
        endif
      else
        if cKOMO = 'BUE' .or. cKOMO = 'KUE' .or. cKOMO = 'WF' .or. cKOMO = 'WV' .or. cKOMO = 'AK'
          cAnrede := "Sehr geehrte Damen und Herren,"
        else
          if Isfirmist
            if nZEICHINH = 1
              DO CASE
                CASE cANR = "Praxis"
                  if cKG = "W"
                    cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                  else
                    if cKG = "M"
                      cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                    else
                      cAnrede := "Sehr geehrt"+ cFloskel +","
                    endif
                  endif
                CASE cANR = "Firma"
                  if cKG = "W"
                    cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                  else
                    if cKG = "M"
                      cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                    else
                      cAnrede := "Sehr geehrt"+ cFloskel +","
                    endif
                  endif
                CASE cANR = "WEG"
                  if cKG = "W"
                    cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                  else
                    if cKG = "M"
                      cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                    else
                      cAnrede := "Sehr geehrt"+ cFloskel +","
                    endif
                  endif
                CASE cANR = "Z-Prax."
                  if cKG = "W"
                    cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                  else
                    if cKG = "M"
                      cAnrede := "Sehr geehrter Herr"+ " " + cNamec +","
                    else
                      cAnrede := "Sehr geehrt"+ cFloskel +","
                    endif
                  endif
                CASE cANR = "Verein"
                  if cKG = "W"
                    cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                  else
                    if cKG = "M"
                      cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                    else
                      cAnrede := "Sehr geehrt"+ cFloskel +","
                    endif
                  endif
                CASE cANR = "GBR"
                  if cKG = "W"
                    cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                  else
                    if cKG = "M"
                      cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                    else
                      cAnrede := "Sehr geehrt"+ cFloskel +","
                    endif
                  endif
                CASE cANR = "Bro"
                  if cKG = "W"
                    cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                  else
                    if cKG = "M"
                      cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                    else
                      cAnrede := "Sehr geehrt"+ cFloskel +","
                    endif
                  endif
                CASE cANR = "Herrn"
                  cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                CASE cANR = "Frau"
                  cAnrede := "Sehr geehrte Frau"+ " " + cName +","
              ENDCASE
            else
              if nZEICHINH = 2
                DO CASE
                  CASE cANR = "Praxis"
                    if cPG = "W"
                      cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                    else
                      if cPG = "M"
                        cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                      else
                        cAnrede := "Sehr geehrt"+ cFloskel +","
                      endif
                    endif
                  CASE cANR = "Firma"
                    if cPG = "W"
                      cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                    else
                      if cPG) = "M"
                        cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                      else
                        cAnrede := "Sehr geehrt"+ cFloskel +","
                      endif
                    endif
                  CASE cANR = "WEG"
                    if cPG = "W"
                      cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                    else
                      if cPG = "M"
                        cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                      else
                        cAnrede := "Sehr geehrt"+ cFloskel +","
                      endif
                    endif
                  CASE cANR = "Z-Prax."
                    if cPG = "W"
                      cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                    else
                      if cPG = "M"
                        cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                      else
                        cAnrede := "Sehr geehrt"+ cFloskel +","
                      endif
                    endif
                  CASE cANR = "Verein"
                    if cPG = "W"
                      cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                    else
                      if cPG = "M"
                        cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                      else
                        cAnrede := "Sehr geehrt"+ cFloskel +","
                      endif
                    endif
                  CASE cANR = "GBR"
                    if cPG = "W"
                      cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                    else
                      if cPG = "M"
                        cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                      else
                        cAnrede := "Sehr geehrt"+ cFloskel +","
                      endif
                    endif
                  CASE cANR = "Bro"
                    if cPG = "W"
                      cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                    else
                      if cPG = "M"
                        cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                      else
                        cAnrede := "Sehr geehrt"+ cFloskel +","
                      endif
                    endif
                  CASE cANR = "Herrn"
                    cAnrede := "Sehr geehrter Herr"+ " " + cPaName +","
                  CASE cANR = "Frau   "
                    cAnrede := "Sehr geehrte Frau"+ " " + cPaName +","
                ENDCASE
              else
                if cPG = "W"
                  cAnrede := "Sehr geehrte Frau"+ " " + cName +","
                else
                  cAnrede := "Sehr geehrter Herr"+ " " + cName +","
                endif
              endif
            endif
          else
            if cFloskel = "e Damen und Herren"
              cAnrede := "Sehr geehrt"+ cFloskel +","
            else
              if cKG = "W"
                cAnrede := "Sehr geehrte Frau"+ " " + cName +","
              else
                cAnrede := "Sehr geehrter Herr"+ " " + cName +","
              endif
            endif
          endif
        endif
      endif


return cAnrede
lg
Micha
lG
Micha

Benutzeravatar
AUGE_OHR
Marvin
Marvin
Beiträge: 10381
Registriert: Do, 16. Mär 2006 8:55
Wohnort: Hamburg

Re: Outlook 2007 display()-Fehler

Beitrag von AUGE_OHR » Di, 11. Aug 2015 18:04

MichaMB hat geschrieben:Hallo Jimmy,
leider komme ich mit deinem Beispiel ueberhaupt nicht weiter. Alle Suchen im Forum ergeben wieder andere Ansaetze mit komplett anderer Programmierung.
(Einzelversenden ueber Outlook mit Popup funktioniert einwandfrei, ich moechte aber alle Emails der Datenbankadressen auf einmal versenden)
wie Hubert schon sagte ist sehr schwer wenn du diese Mengen an (ungeordneten) Code postest ...

ich bin mir nicht sicher wohl nun dein eigentliches Problem liegt ... im Zusammenstellen der Strings und/oder dem senden ?

was das senden und DBF angeht meine ich zu erinnern das es damit Probleme gab und ich deshalb einen Thread benutzt habe.
Ich übergebe an den Thread die zuvor aus der DBF gefüllten Variablen :

Code: Alles auswählen

   oMAPI := Thread() :new()
   oMAPI:start( "SENDNOW", cAdresses, cSubject, cMessage, cAttachments, nFlag )
   SLEEP( 100 )
   DO WHILE lisRunning = .T.
danach "warte" ich bis der Thread abgearbeitet ist und kann dann den nächsten Datensatz nehmen und die Aktion wiederholen.

wenn du die alle in den Postausgang legst werden die ja noch nicht gesendet.
die letzte Massen Email sollte also dann direkt gesendet werden dann gehen auch die aus dem Postausgang raus.
gruss by OHR
Jimmy

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2013 und Mail Massenversand

Beitrag von brandelh » Di, 11. Aug 2015 19:10

Die Funktion ist soweit ich das sehen kann sauber umgesetzt und wird hier bei dem Thema nicht mehr benötigt.

Nur eines ... das geht so nicht:

Code: Alles auswählen

 ConvToAnsiCP(infmess0) := GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, NZEICHINH, cVorname, cName, cPPname, cFloskel, cPG, cANR )      
richtig ist es so:

Code: Alles auswählen

 
infmess0 := GetAnredeBrief1( cPersdu, cKOMO, IsFirmist, NZEICHINH, cVorname, cName, cPPname, cFloskel, cPG, cANR ) 
infmess0 := ConvToAnsiCP(infmess0)     
Immer daran denken, lieber 2 Zeilen und besser lesbar (auch bei Fehlermeldung in Zeile ..) als zu viel hintereinander packen.
Die Funktion im Main.prg abspeichern?
oder in einem "Funktio.PRG" mit allen Funktionen welches als erstes PRG im Main aufgerufen wird?
Du solltest unbedingt die Grundlagen von Xbase++ in der Hilfe lesen.
dBase musste als Interpreter alles stark beschränken, Clipper war etwas besser drann, aber Xbase hat weder die Beschränkungen noch ist es so umständlich ;-)

1. Ich habe eine PRG für das Hauptprogramm, dort rufe ich Funktionen AUF, aber es steht nichts weiter drinn als die nötigen Routinen um den Programmfluß zu starten.
2. Eine PRG für allgemeine Routinen für alle Programme, die pflege ich zentral und kopiere immer die neueste Version zu den Programmen
3. Eine PRG für jedes Fenster des Programmes, d.h. eigentlich je 2 weil ich Classcode nutze
4. Für alle gesonderten Aufgaben jeweils ein eigenes
...
20 bis 40 PRG nach sinnvoller Namensnennung sind gut zu handeln und übersichtlich.

So vermeide ich wo es nur geht Monster mit einigen hundert Zeilen (es geht nicht immer, weil eine Klasse in eine PRG muss, eine davon hat 7000 Zeilen) ...
Alles was irgendwie eine Einheit ist getrennt in eine Funktion (später Methode / Classe) stecken, sorgfälltig testen und vergessen ...

Nun hast du also in einem Verzeichnis (ein Programm, ein Verzeichnis) also 10 PRG Dateien nun kommt das Beste PBUILD und DIR ;-)

Code: Alles auswählen

CMD Box im Verzeichnis öffnen

DIR *.PRG /B > MeinProgramm.txt

MeinProgramm.txt eventuell verbessern (überflüssige PRG raus) ...

PBUILD @MeinProgramm.txt

Hierbei wird eine projekt.prj Datei erzeugt, in der müssen wir noch DEBUG und GUI prüfen
dann der große Hammer

PBUILD /G

nun ist alles fertig was man zum Entwickeln braucht.

PBUILD ... allein erstellt eine EXE

PBUILD /A ... erzwingt eine komplette Neuerstellung (ich lösche einfach EXE und OBJ, das geht auch)
Wir rufen keine PRG in einer PRG oder sonstigen alten Clipper Kram !

Bei GUI kommen noch ein paar Sachen dazu, aber das später.
Gruß
Hubert

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2013 und Mail Massenversand

Beitrag von MichaMB » Di, 11. Aug 2015 19:31

Hallo Hubert und Jimmy und wer sich angesprochen fühlt...

so sieht nun mein "verkürztes" Programm aus:
Variablen sind aus dem Datensatz ausgelesen, nächster Datensatz dann mit DBSKIP

1. was benötigt man von den Zeilen 1 bis 58 ?

2. was muss nun als Programmcode in die Procedure Sendnow?
bzw. was wird von meinem Code Zeile 62 bis 217 dorthin verschoben?

Code: Alles auswählen

 /// Procedure emmailou.prg   Aufruf vom Kmenue2 Zeile  5460

#pragma library( "ascom10.lib" )
#include "Appevent.ch"
#include "Dmlb.ch"
#include "outlook.ch"
#include "dll.ch"
#include "common.ch"

//--error codes from MAPI.H
#define SUCCESS_SUCCESS                     0
#define MAPI_USER_ABORT                     1
#define MAPI_E_FAILURE                      2
#define MAPI_E_LOGIN_FAILURE                3
#define MAPI_E_DISK_FULL                    4
#define MAPI_E_INSUFFICIENT_MEMORY          5
#define MAPI_E_ACCESS_DENIED                6
#define MAPI_E_TOO_MANY_SESSIONS            8
#define MAPI_E_TOO_MANY_FILES               9
#define MAPI_E_TOO_MANY_RECIPIENTS          10
#define MAPI_E_ATTACHMENT_NOT_FOUND         11
#define MAPI_E_ATTACHMENT_OPEN_FAILURE      12
#define MAPI_E_ATTACHMENT_WRITE_FAILURE     13
#define MAPI_E_UNKNOWN_RECIPIENT            14
#define MAPI_E_BAD_RECIPTYPE                15
#define MAPI_E_NO_MESSAGES                  16
#define MAPI_E_INVALID_MESSAGE              17
#define MAPI_E_TEXT_TOO_LARGE               18
#define MAPI_E_INVALID_SESSION              19
#define MAPI_E_TYPE_NOT_SUPPORTED           20
#define MAPI_E_AMBIGUOUS_RECIPIENT          21
#define MAPI_E_MESSAGE_IN_USE               22
#define MAPI_E_NETWORK_FAILURE              23
#define MAPI_E_INVALID_EDITFIELDS           24
#define MAPI_E_INVALID_RECIPS               25
#define MAPI_E_NOT_SUPPORTED                26

//--ID´s for Message items
#define ID_SUBJECT                0
#define ID_MESSAGE                1
#define ID_MESSAGE_TYPE           2
#define ID_DATE                   3
#define ID_ORIGINATOR_NAME        4
#define ID_ORIGINATOR_ADRESS      5
#define ID_RECIPIENT_NAME         6
#define ID_RECIPIENT_ADRESS       7
#define ID_ATTACHMENT_PATHNAME    8
#define ID_ATTACHMENT_FILENAME    9
#define ID_CONVERSATION_ID        10

//--Message Flags
#define NOFLAG                    0
#define FLAG_UNREAD               1
#define FLAG_RECEIPT_REQUESTED    2
#define FLAG_SENT                 4

//--SKIP Flags
#define SKIP_ONLY                 0
#define DELETE_THEN_SKIP          1

STATIC lisRunning := .F.

Procedure emmailou

   local cAnrede := ""                      // Public cAnrede :=""  falls in anderen Programmen gebraucht
   local cGruss  := ""
 // "MBasche@T-Online.de;" + "info@MichaelBasche.de;" + "CC:MBSkat@T-Online.de;" + "BCC:info@Skat-Pforzheim.de"
    //
   Local cAdresses    := (Emilwer)
   Local cSubject     := (Betrmail)

//   local cMessage     := (infmess0) + (Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
   Local cMessage     := (infmess0)
   //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
   // Local cAttachments :=  &Anhangx
   Local cAttachments :=  (Anhangx)
   Local nFlag        :=  NOFLAG
   Local nErr

  //   LOCAL Homepath := LEFT( APPNAME( .T. ), LEN( APPNAME( .T. ) ) - LEN( APPNAME( .F. ) ) )
  //  Local cAdresses    := (Emilwer)
  //  local cSubject     := (Betrmail)
  //  local cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)
  //  das ist das Muster => wichtig in Anfhrungszeichen Local cAttachments :=  "C:\MBNETZ\MAB\DRUWORD\BUEPOB.PDF;C:\MBNETZ\MAB\DRUWORD\BUEPLogo.PDF"
  //  Local cAttachments :=  &Anhangx
  //  local nFlag        :=  NOFLAG


  // Grundeinstellungen erfolgen in Global*.PRG (MAIN)  laut Programm-Anmeldung User
  // Emailadresse Empf„nger =  cAdresses  eventuell „ndern
  // public betrmail = cSubject   eventuell „ndern
  // public Anlage1 = cAttachments  eventuell „ndern
  // z.B. cAttachments cAttachments := (verzword)+ "/BUEPLogo.PDF"
  // w„hlt die Anzahl der Anh„nge aus, je nach Emailart mit 1 2 oder 3 Anh„ngen
  // Public AnzAnhaenge   ANzahl in VZerstna vorgegeben
  // ist die Variable die die Anh„nge fr
  // Public Anhangx
  // wenn Nutzer geprft und ok Variablen belegen
  // public Emilwer   Emailadresse Empf„nger =  cAdresses
  // Vorbelegung fr Anrede und Gráe in Email
  // public PERSWER
  // public betrmail = cSubject
  // public Anlage = cAttachments
  // Public infmess0      Text in mail = cMessage   Sehr geehrte Damen und Herren oder Hallo
  // Public infmess1   Text um was es geht
  // Public infmess2  Gruáformel   Mit freundlichen Gráen   bzw.   Viele Gráe
  // Public infmess3    Gesch„ftsfhrer
  // Public infmess3b   Unterzeichner
  // Public infmess3c   Abteilung
  // Public infmess4    Name Firma
  // Public infmess5    Firmensitz
  // Public infmess6    Web und EMail
  // Public infmess7    bei GMBH Registergericht und Nummer
  // Public infmess8    Registrierungsstelle des Vermittlers
  // Public infmess9    www.vermittlerregister.info
  // Public infmess10  Art der T„tigkeit  und Nummer
  // Public infmess11  Anschrift Gewerbeamt
  // Public infmess12   Versicherung und Nummer

   set default to (substr(FESTWO,1,1) + ":")
   set path to (substr(FESTWO,1,1) + ":")
   set default to (verzword)
   SET PATH to (verzword)

   ersit400  := ConvToAnsiCP("Newsletter")
   betrmail  := (ersit400)

   if Isfirmist
     ersitz17b := '"' + (verzword) + '\' + ConvToAnsiCP('NEWSG.PDF') + '"'
   else
     ersitz17b := '"' + (verzword) + '\' + ConvToAnsiCP('NEWSP.PDF') + '"'
   endif
   anhangx   := (ersitz17b)

   cAttachments :=  &Anhangx


   Public MerkeX
   store "  " to infmess1
   store 1 to AnzAnhaenge
   set default to (substr(FESTWO,1,1) + ":")
   set path to (substr(FESTWO,1,1) + ":")
   set default to (verzdat)
   SET PATH to (verzdat)

   sele j
   use
   // Anrede
// nach oben versetzt    local cAnrede := ""                      // Public cAnrede :=""  falls in anderen Programmen gebraucht
   // Datenbank ausw„hlen
   cDatei    := "KUMAIL"                   // die DBF ( Namen sprechend) um die es geht
   use (cDatei) shared new                 // DBF in neuem Arbeitsbeeich ”ffnen
   nKumail   := select()                   // Arbeitsbereich (mit sprechendem Namen) benennen
   // Anrede speichern, alle abh„ngigen Infos bergeben ...
   infmess0 := GetAnrede( cPersdu, cKOMO, IsFirmist, NZEICHINH, cVorname, cName, cPPname, cFloskel, cPG, cANR )


   // Grussformel in der Email
// nach oben versetzt    local cGruss := ""
   infmess := GetGruss( cPersdu, cKOMO, IsFirmist, NZEICHINH, cVorname, cName, cPPname, cFloskel, cPG, cANR )

   // Email Text 2-Zeilig    infmess1 und infmess2
   // "MXXXXXXXXX@T-Online.de;" + "info@MXXXXXXXXXXXXXXX.de;" + "CC:MXXXXXXXXXXXX@T-Online.de;" + "BCC:info@SXXXXXXXXXXXXXXXXX.de"

      if Isfirmist
        if nZEICHINH = 1
          emilwer := alltrim((nKumail)->EMAIL)
          if len(Emilwer) < 2
            emilwer := alltrim((nKumail)->EAMAIL)
          else
            if len(Emilwer) < 2
              emilwer :=  '"Keine E-Mail von Kunde, Arbeitgeber gespeichert"'
            endif
          endif
        else
          emilwer := alltrim((nKumail)->EPMAIL)
          if len(Emilwer) < 2
            emilwer := alltrim((nKumail)->EAMAIL)
          else
            if len(Emilwer) < 2
              emilwer := '"Keine E-Mail von Partner, Arbeitgeber gespeichert"'
            endif
          endif
        endif
      else
        emilwer := alltrim((nKumail)->EMAIL)
        if len(Emilwer) < 2
          emilwer := alltrim((nKumail)->EPMAIL)
          if len(Emilwer) < 2
            emilwer := alltrim((nKumail)->EAMAIL)
          else
            if len(Emilwer) < 2
              emilwer := '"Keine E-Mail von Kunde, Partner, Arbeitgeber gespeichert"'
            endif
          endif
        endif
      endif
      IF cPersdu = "D"
        store "in der Anlage erh„ltst Du unseren Newsletter mit aktuellen Informationen." to infmess1
        store "Viel Spaá beim lesen des Newsletters, gerne stehen wir Dir fr weitere Fragen zur Verfgung." to infmess2
      else
        store "in der Anlage erhalten Sie unseren Newsletter mit aktuellen Informationen." to infmess1
        store "Viel Spaá beim lesen des Newsletters, gerne stehen wir Ihnen fr weitere Fragen zur Verfgung." to infmess2
      endif
      store ConvToAnsiCP(infmess) to infmess
      store ConvToAnsiCP(infmess0) to infmess0
      store ConvToAnsiCP(infmess1) to infmess1
      store ConvToAnsiCP(infmess2) to infmess2
      store ConvToAnsiCP(EMILWER) to EMILWER
      cAdresses    := (Emilwer)
      cMessage     := (infmess0)+(Chr(13))+(Chr(13))+(infmess1)+(Chr(13))+(infmess2)+(Chr(13))+(Chr(13))+(infmesss)+(Chr(13))+(Chr(13))+(infmess3b)+(Chr(13))+(infmess3c)+(Chr(13))+(Chr(13))+(infmess4)+(Chr(13))+(infmess3)+(Chr(13))+(infmess5)+(Chr(13))+(Chr(13))+(infmess6)+(Chr(13))+(Chr(13))+(infmess7)+(Chr(13))+(Chr(13))+(infmess8a)+(Chr(13))+(infmess8)+(Chr(13))+(infmess9)+(Chr(13))+(Chr(13))+(infmess10)+(Chr(13))+(Chr(13))+(infmess11)+(Chr(13))+(Chr(13))+(infmess12)



   set default to (substr(FESTWO,1,1) + ":")
   set path to (substr(FESTWO,1,1) + ":")
   set default to (verzexe)
   SET PATH to (verzexe)

  do sendnews


return
PROCEDURE SENDNEWS( cAdresses, cSubject, cMessage, cAttachments, nFlag )

   //

   LOCAL oMAPI
   Local Homepath := (verzexe)
   // so und nun einen Thread starten, dann funktioniert es
   //
   oMAPI := Thread() :new()
   oMAPI:start( "SENDNOW", cAdresses, cSubject, cMessage, cAttachments, nFlag )
   SLEEP( 100 )
   DO WHILE lisRunning = .T.
      SLEEP( 10 )
   ENDDO
   SLEEP( 100 )

   CurDrive( SUBSTR( Homepath, 1, 1 ) )
   CURDIR( Homepath )
RETURN


PROCEDURE SENDNOW( cAdresses, cSubject, cMessage, cAttachments, nFlag )

   // Flag setzen


   lisRunning := .T.

   BEGIN SEQUENCE

    // hier dein Code


    // Ende hier mein Code

   RECOVER USING nErr

   END SEQUENCE


   // Flag ausschalten
   lisRunning := .F.

RETURN
lg

Micha
lG
Micha

Benutzeravatar
MichaMB
UDF-Programmierer
UDF-Programmierer
Beiträge: 57
Registriert: Fr, 26. Jul 2013 12:03

Re: Outlook 2013 und Mail Massenversand

Beitrag von MichaMB » Di, 11. Aug 2015 20:20

Das kleine Problem bei der Sache...

never change a running System :)
ich habe so viele alte PRG's mit sehr vielen Datenbanken zusammengefasst in einer Global.EXE zum laufen gebracht, das funktioniert auch super schnell
Jetzt habe ich sehr viele Verbesserungen und Erweiterungen mit einer Mischung aus altem Wissen und neuer Programm-Technik vereint. Wenn nun das Programm mit der Massenmail läuft, werde ich Schritt für Schritt die PRG's straffen und dann auf Netzwerk-Programmierung umstellen.
Doch da steht mir noch einiges bevor wie ihr in der Project-Datei unschwer erkennen könnt

Code: Alles auswählen

[PROJECT]
    DEBUG         = yes
    PBUILD        = @project
    MAKE          =
    VERSION       = 2.0
    OPENFILES     = 
    PROJECT.XPJ

[PROJECT.XPJ]
    Global.EXE



[Global.EXE]
    COMPILE       = xpp
    COMPILE_FLAGS = /wi /wl /wu /q /P /w /d_GUI /dGRAPHICS_PRINTER
    DEBUG_SAVE    = yes
    GUI           = yes
    LINKER        = alink
    LINK_FLAGS    = 
    RC_COMPILE    = arc
    RC_FLAGS      = /v

// $START-AUTODEPEND

    STD.CH
    SET.CH
    NATMSG.CH
    GET.CH
    PROMPT.CH
    MEMVAR.CH
    COLLAT.CH
    GETEXIT.CH
    APPEVENT.CH
    SETCURS.CH
    XBP.CH
    PDF_LES.OBJ

    EMAILOUT.obj
    EMMAILOU.obj
    VZMEmail.OBJ
    VZEmail.OBJ
    abb.obj
    accviol.obj
    adrlidru.obj
    adrlist.obj
    ae2kenn.obj
    AELIEINT.obj
    allku.obj
    apmeintr.obj
    appsys.obj
    apstat.obj
    art.obj
    beglabzu.obj
    begleitc.obj
    beglvnr.obj
    beitrb.obj
    bemenue.obj
    Berech.obj
    Besuchli.obj
    bewert.obj
    Bild.obj
    buvrech.obj
    change_P.obj
    dataus.obj
    delete_U.obj
    dirfset.obj
    dpmenue.obj
    drinit.obj
    druwaehl.obj
    dynamik.obj
    dynapber.obj
    dyninmpl.obj
    dynliein.obj
    dynlistn.obj
    DYNlverg.obj
    Dynmerke.obj
    dynneuve.obj
    dynsto.obj
    dynvertr.obj
    DYVETEAE.obj
    einli.obj
    einlidr.obj
    Empeintr.obj
    empfzeig.obj
    endechec.obj
    ergcheck.obj
    Ergdaten.obj
    errork.obj
    Fenster1.obj
    Fenster2.obj
    Fenster3.obj
    FABTEST.obj
    faellche.obj
    findkom.obj
    fmaske.obj
    folgepmi.obj
    folgepro.obj
    folgesto.obj
    fpstat.obj
    Fremdruc.obj
    fremlisc.obj
    fverab.obj
    fverae.obj
    Fverlo.obj
    Fverneu.obj
    Fversu.obj
    FVertrag.obj
    gebdr.obj
    gesbneu.obj
    gebneuKP.obj
    getgk.obj
    getmj.obj
    getret.obj
    gettmj.obj
    glaserho.obj
    Global.obj
    infoabk.obj
    initdr.obj
    inst_rvv.obj
    infolist.obj
    javor.obj
    JZVeintr.obj
    Kennchec.obj
    KFZerhoe.obj
    KFZneu.obj
    KFZPROVs.obj
    KFZumste.obj
    Kimask2.obj
    kindein.obj
    kkind2.obj
    KLING.obj
    Klingel.obj
    Kmaske1.obj
    kmenue2.obj
    Ksuch2.obj
    Kuli.obj
    kulidr.obj
    kuliein.obj
    kulioh.obj
    kuliohdr.obj
    kuliwo.obj
    Kunam.obj
    Kunbet.obj
    Kunddr2.obj
    KUNDDRUC.obj
    Kverae.obj
    Kveraeal.obj
    KVerer.obj
    KVerlo.obj
    Kverneu.obj
    KVertrag.obj
    Kverze.obj
    Leerergd.obj
    Lieintra.obj
    Liindex.obj
    limask.obj
    line.obj
    listkon.obj
    loeschb.obj
    loeschre.obj
    LVbeitra.obj
    LVbeivor.obj
    LVeintra.obj
    LVjavor.obj
    LVvplzei.obj
    LVzwizei.obj
//    MIGRATE.obj
    mili.obj
    mitae.obj
    mitarbli.obj
    Mitnutes.obj
    MMaske.obj
    Mmenue.obj
    mplaende.obj
    mpldruck.obj
    MPLeintr.obj
    Mplloesc.obj
    mpllvfp.obj
    mplmenue.obj
    mplneuze.obj
    mplprifu.obj
    mplprima.obj
    mplprint.obj
    mplprite.obj
    mplsoort.obj
    mplunter.obj
    mplvnrlo.obj
    mplzeig.obj
    mptmodi.obj
    mquittun.obj
    msuch.obj
    nachrech.obj
    neinvor.obj
    neuseite.obj
    neuver.obj
    new_user.obj
    newpage.obj
    not_fert.obj
    pamenue.obj
    Pause.obj
    plmaske.obj
    plmenue.obj
    plsuch.obj
    pritest.obj
    pritest.obj
    prodanf.obj
    prodeint.obj
    prodkont.obj
    prodliko.obj
    prodpriz.obj
    prodscko.obj
    prodscze.obj
    produges.obj
    produkon.obj
    prodvorh.obj
    prodwelc.obj
    proerg.obj
    protab.obj
    PROVB.obj
    provili.obj
    provilo.obj
    provilr.obj
    PROZWAHP.obj
    PROZWAVK.obj
    PROZWTSB.obj
    PROZWVSB.obj
    quartal.obj
    quartlis.obj
    Restbetr.obj
    restlo.obj
    RSerhoe.obj
    rueck.obj
    readpdf.obj
    saaen.obj
    sachstil.obj
    scheminf.obj
    schemmas.obj
    schemmen.obj
    schemsuc.obj
    schutzbr.obj
    sdabl.obj
    sdlis.obj
    sdloe.obj
    sdneu1.obj
    sdneu2.obj
    sdneuV1.obj
    sdohne.obj
    serdatne.obj
    servaend.obj
    sfraende.obj
    sicher.obj
    SICHMIT.obj
    soalarm.obj
    somenue.obj
    sortaTR2.obj
    sortauAR.obj
    sortauFA.obj
    sortauLA.obj
    sortauPA.obj
    sortaPPA.obj
    sortausg.obj
    sortauSP.obj
    sortauST.obj
    sortauTI.obj
    sortauTR.obj
    sortauWg.obj
    SORTSCHE.obj
    spmenue.obj
    Stillgut.obj
    stobewer.obj
    stolvmpl.obj
    stolvvpl.obj
    stornein.obj
    stornlv.obj
    stornsac.obj
    stosampl.obj
    stosavpl.obj
    stovsuch.obj
    stube.obj
    suchg2.obj
    sysmenue.obj
    tabelle.obj
    Tagcheck.obj
    Tagsu1.obj
    Tagsu2.obj
    Tagsu3.obj
    Tagsu4.obj
    Tagsu5.obj
    Tagsu6.obj
    Tagsu7.obj
    tariferh.obj
    tatproz.obj
    teilmpl.obj
    teilsto.obj
    teilvpl.obj
    textinfo.obj
    Textsuch.obj
    textuebe.obj
    ujfhol.obj
    update.obj
    user_lis.obj
    vaeinfo.obj
    vaender.obj
    vdrukopf.obj
    vdruzeil.obj
    vekont.obj
    vemabip.obj
    veraende.obj
    vergleic.obj
    verhoeh.obj
    verhqlis.obj
    verhqmpl.obj
    vermasae.obj
    vermasn.obj
    vermasin.obj 
    vermasvv.obj
    verneu.obj
    versuch.obj
    vertdr2.obj
    vertdruc.obj
    vertrmas.obj
    verschad.obj
    vesuch.obj
    veteae.obj
    vkenninf.obj
    vkorrig.obj
    vliste.obj
    vnrberec.obj
    voraend.obj
    vpldruck.obj
    vpldruma.obj
    vpleinl.obj
    vplloesc.obj
    vpllvfp.obj
    vplmenue.obj
    vplsum.obj
    vplzeig.obj
    vplzeile.obj
    vrntrenn.obj
    vsuch.obj
    vucheck.obj
    W_Euro.obj
    welch.obj
    welcher.obj
    welcome.obj
    wetbewe.obj
    wettliko.obj
    wettlilv.obj
    wettlv.obj
    wettlv2.obj
    wettlvze.obj
    wettzeil.obj
    word_Td.obj
    zaehler.obj
    ZGmenue.obj
    zlistkon.obj
    zmplzeig.obj
    Zufall.obj
    zwfaktor.obj
    zwizeig.obj
    VZerstel.obj
    VZerstna.obj

// $STOP-AUTODEPEND

    EMAILOUT.prg
    VZEmail.prg
    EMMAILOU.PRG
    VZMEmail.PRG

    PDF_LES.PRG
    abb.PRG
    accviol.prg
    adrlidru.PRG
    adrlist.prg
    ae2kenn.PRG
    AELIEINT.PRG
    allku.prg
    apmeintr.PRG
    appsys.prg
    apstat.PRG
    art.PRG
    beglabzu.PRG
    begleitc.PRG
    beglvnr.PRG
    beitrb.PRG
    bemenue.PRG
    Berech.PRG
    Besuchli.PRG
    bewert.PRG
    Bild.PRG
    buvrech.PRG
    change_P.PRG
    dataus.PRG
    delete_U.PRG
    dirfset.PRG
    dpmenue.PRG
    drinit.PRG
    druwaehl.PRG
    dynamik.PRG
    dynapber.PRG
    dyninmpl.PRG
    dynliein.PRG
    dynlistn.PRG
    DYNlverg.PRG
    Dynmerke.PRG
    dynneuve.PRG
    dynsto.PRG
    dynvertr.PRG
    DYVETEAE.PRG
    einli.PRG
    einlidr.PRG
    Empeintr.PRG
    empfzeig.PRG
    endechec.PRG
    ergcheck.PRG
    Ergdaten.PRG
    errork.PRG
    Fenster1.PRG
    Fenster2.PRG
    Fenster3.PRG
    FABTEST.prg
    faellche.PRG
    findkom.PRG
    fmaske.PRG
    folgepmi.PRG
    folgepro.PRG
    folgesto.PRG
    fpstat.PRG
    Fremdruc.PRG
    fremlisc.PRG
    fverab.PRG
    fverae.PRG
    Fverlo.PRG
    Fverneu.PRG
    Fversu.PRG
    FVertrag.PRG
    gebdr.PRG
    gesbneu.PRG
    getgk.PRG
    gebneuKP.PRG
    getmj.prg
    getret.PRG
    gettmj.PRG
    glaserho.PRG
    Global.prg
    infoabk.PRG
    initdr.PRG
    inst_rvv.PRG
    infolist.prg
    javor.PRG
    JZVeintr.PRG
    Kennchec.PRG
    KFZerhoe.PRG
    KFZneu.PRG
    KFZPROVs.PRG
    KFZumste.PRG
    Kimask2.PRG
    kindein.PRG
    kkind2.PRG
    KLING.PRG
    Klingel.PRG
    Kmaske1.PRG
    kmenue2.PRG
    Ksuch2.PRG
    Kuli.PRG
    kulidr.PRG
    kuliein.PRG
    kulioh.PRG
    kuliohdr.PRG
    kuliwo.PRG
    Kunam.PRG
    Kunbet.PRG
    Kunddr2.PRG
    KUNDDRUC.PRG
    Kverae.PRG
    Kveraeal.PRG
    KVerer.PRG
    KVerlo.PRG
    Kverneu.PRG
    KVertrag.PRG
    Kverze.PRG
    Leerergd.PRG
    Lieintra.PRG
    Liindex.PRG
    limask.PRG
    line.PRG
    listkon.PRG
    loeschb.PRG
    loeschre.PRG
    LVbeitra.PRG
    LVbeivor.PRG
    LVeintra.PRG
    LVjavor.PRG
    LVvplzei.PRG
    LVzwizei.PRG
//    MIGRATE.prg
    mili.PRG
    mitae.PRG
    mitarbli.PRG
    Mitnutes.PRG
    MMaske.PRG
    Mmenue.PRG
    mplaende.PRG
    mpldruck.PRG
    MPLeintr.PRG
    Mplloesc.PRG
    mpllvfp.PRG
    mplmenue.PRG
    mplneuze.PRG
    mplprifu.PRG
    mplprima.PRG
    mplprint.prg
    mplprite.prg
    mplsoort.prg
    mplunter.PRG
    mplvnrlo.prg
    mplzeig.prg
    mptmodi.PRG
    mquittun.PRG
    msuch.PRG
    nachrech.PRG
    neinvor.PRG
    neuseite.PRG
    neuver.PRG
    new_user.PRG
    newpage.PRG
    not_fert.PRG
    pamenue.PRG
    Pause.PRG
    plmaske.PRG
    plmenue.PRG
    plsuch.PRG
    pritest.PRG
    pritest.PRG
    prodanf.PRG
    prodeint.PRG
    prodkont.PRG
    prodliko.PRG
    prodpriz.PRG
    prodscko.PRG
    prodscze.PRG
    produges.PRG
    produkon.PRG
    prodvorh.PRG
    prodwelc.PRG
    proerg.PRG
    protab.PRG
    PROVB.PRG
    provili.PRG
    provilo.PRG
    provilr.PRG
    PROZWAHP.PRG
    PROZWAVK.PRG
    PROZWTSB.PRG
    PROZWVSB.PRG
    quartal.PRG
    quartlis.PRG
    Restbetr.PRG
    restlo.PRG
    RSerhoe.PRG
    rueck.PRG
    readpdf.prg
    saaen.PRG
    sachstil.PRG
    scheminf.PRG
    schemmas.PRG
    schemmen.PRG
    schemsuc.PRG
    schutzbr.PRG
    sdabl.PRG
    sdlis.PRG
    sdloe.PRG
    sdneu1.PRG
    sdneu2.prg
    sdneuV1.prg
    sdohne.PRG
    serdatne.PRG
    servaend.PRG
    sfraende.PRG
    sicher.prg
    sichmit.prg
    soalarm.prg
    somenue.PRG
    sortaTR2.PRG
    sortauAR.PRG
    sortauFA.PRG
    sortauLA.PRG
    sortauPA.PRG
    sortaPPA.PRG
    sortausg.PRG
    sortauSP.PRG
    sortauST.PRG
    sortauTI.PRG
    sortauTR.PRG
    sortauWg.PRG
    SORTSCHE.PRG
    spmenue.PRG
    Stillgut.PRG
    stobewer.PRG
    stolvmpl.PRG
    stolvvpl.PRG
    stornein.PRG
    stornlv.PRG
    stornsac.PRG
    stosampl.PRG
    stosavpl.PRG
    stovsuch.PRG
    stube.PRG
    suchg2.PRG
    sysmenue.PRG
    tabelle.PRG
    Tagcheck.PRG
    Tagsu1.PRG
    Tagsu2.PRG
    Tagsu3.PRG
    Tagsu4.PRG
    Tagsu5.PRG
    Tagsu6.PRG
    Tagsu7.PRG
    tariferh.PRG
    tatproz.PRG
    teilmpl.PRG
    teilsto.PRG
    teilvpl.PRG
    textinfo.PRG
    Textsuch.PRG
    textuebe.PRG
    ujfhol.PRG
    update.PRG
    user_lis.PRG
    vaeinfo.PRG
    vaender.PRG
    vdrukopf.PRG
    vdruzeil.PRG
    vekont.PRG
    vemabip.prg
    veraende.PRG
    vergleic.PRG
    verhoeh.PRG
    verhqlis.PRG
    verhqmpl.PRG
    vermasae.PRG
    vermasn.PRG
    vermasin.PRG 
    vermasvv.PRG
    verneu.PRG
    versuch.PRG
    vertdr2.PRG
    vertdruc.PRG
    vertrmas.PRG
    verschad.PRG
    vesuch.PRG
    veteae.PRG
    vkenninf.PRG
    vkorrig.PRG
    vliste.PRG
    vnrberec.PRG
    voraend.PRG
    vpldruck.PRG
    vpldruma.PRG
    vpleinl.PRG
    vplloesc.PRG
    vpllvfp.PRG
    vplmenue.PRG
    vplsum.PRG
    vplzeig.PRG
    vplzeile.PRG
    vrntrenn.PRG
    vsuch.PRG
    vucheck.PRG
    W_Euro.prg
    welch.PRG
    welcher.PRG
    welcome.PRG
    wetbewe.PRG
    wettliko.PRG
    wettlilv.PRG
    wettlv.PRG
    wettlv2.PRG
    wettlvze.PRG
    wettzeil.PRG
    word_Td.prg
    zaehler.PRG
    ZGmenue.PRG
    zlistkon.PRG
    zmplzeig.PRG
    Zufall.prg
    zwfaktor.PRG
    zwizeig.PRG
    VZerstel.PRG
    VZerstna.PRG
PS: gibt es eine Möglichkeit die Dateien wieder alphabetisch zu sortieren ?

Die fertige Global.exe hat 16.440 KB

lG
Micha
lG
Micha

Benutzeravatar
AUGE_OHR
Marvin
Marvin
Beiträge: 10381
Registriert: Do, 16. Mär 2006 8:55
Wohnort: Hamburg

Re: Outlook 2013 und Mail Massenversand

Beitrag von AUGE_OHR » Di, 11. Aug 2015 21:24

MichaMB hat geschrieben:so sieht nun mein "verkürztes" Programm aus:
naja ...
die ganzen #define sind für das Verständnis ebenso unnötig wie die "auskommentierten" Zeilen
MichaMB hat geschrieben:Variablen sind aus dem Datensatz ausgelesen, nächster Datensatz dann mit DBSKIP
fein ... aber dann ...
MichaMB hat geschrieben:

Code: Alles auswählen

  do sendnews
...
PROCEDURE SENDNEWS( cAdresses, cSubject, cMessage, cAttachments, nFlag )
ein "DO" kann ich ja noch verstehen aber "wo" sind nun deine (belegten) Variablen welche du übergeben willst ?
(bitte komme mir nicht mit PUBLIC / PRIVATE ... )
MichaMB hat geschrieben:1. was benötigt man von den Zeilen 1 bis 58 ?
hm ... von Zeile 1 - 58 stehen doch nur die #include und #define ... die musst du nicht mehrfach posten [-X
MichaMB hat geschrieben:2. was muss nun als Programmcode in die Procedure Sendnow?
bzw. was wird von meinem Code Zeile 62 bis 217 dorthin verschoben?
das was da auch vorher stand ...
MichaMB hat geschrieben:

Code: Alles auswählen

PROCEDURE SENDNOW( cAdresses, cSubject, cMessage, cAttachments, nFlag )
   // Flag setzen
   lisRunning := .T.
   BEGIN SEQUENCE
    //
    // entweder
    //
        //-- Pop up maileditor
        MsgBox("mail will be send with Maileditor popping up")
        nErr := DllExecuteCall( scDLLSocMapiSendMail,cAdresses,cSubject,cMessage,cAttachments,nFlag)
        if nErr != SUCCESS_SUCCESS .and. nErr != MAPI_USER_ABORT
            break nErr
        endif
     //
     // ODER ( aber NICHT UND !!! ) 
     //
        //-- Store mail directly to outbox
        MsgBox("mail will be stored directly to outbox")
        nErr := DllExecuteCall( scDLLSocMapiPostMail,cAdresses,cSubject,cMessage,cAttachments,nFlag)
        if nErr != SUCCESS_SUCCESS
            break nErr
        endif
//      MsgBox("mail successfully stored to outbox")
   RECOVER USING nErr
   // Fehlerbehandlung
   END SEQUENCE
   // Flag ausschalten
   lisRunning := .F.

RETURN
wie schon gesagt übergibst du die Variablen als Parameter des Threads.
ansonsten sollte in dem Thread kein weiterer Code ausgeführt werden.
gruss by OHR
Jimmy

Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 13601
Registriert: Mo, 23. Jan 2006 21:54
Wohnort: Germersheim
Kontaktdaten:

Re: Outlook 2013 und Mail Massenversand

Beitrag von brandelh » Di, 11. Aug 2015 21:49

Zeilennummern sind ja keine da, vermutlich meinst du das ...

Code: Alles auswählen

//--error codes from MAPI.H
#define SUCCESS_SUCCESS                     0
#define MAPI_USER_ABORT                     1
#define MAPI_E_FAILURE                      2
#define MAPI_E_LOGIN_FAILURE                3
#define MAPI_E_DISK_FULL                    4
Das sind defines die immer gleich sind und in jedem Mapi Programm benötigt werden.
Ein Musterbeispiel für eine EIGENE CH Datei, z.B. MAPI.CH !

Im Programm selbst dann

#include "mapi.ch"

Ein Programm das alles macht hat Vorteile, aber ist auch sehr unflexibel bei Änderungen ...
Gruß
Hubert

Antworten

Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 1 Gast