Zugriff auf FTP-Server per WinInet

Unter AX auf einen FTP-Server zuzugreifen und dort mit Dateien zu jonglieren ist meines Wissens nach standardmässig nicht möglich. Glücklicherweise stellt Windows aber eine API namens WinInet zur Verfügung, deren Funktionen man auch unter AX ansprechen kann.

 

Im folgenden findest Du einen einfachen Job, der anhand einger FTP-Befehle aufzeigt, wie die WinInet eingebunden werden kann. Selbstverständlich kann man mit ein paar Handgriffen auch auf andere Funktionen dieser API zugreifen. Der eigenen Fantasie bzw. auch den Wünschen der Kunden sind kaum Grenzen gesetzt ;-)

static void HandleFTP(Args _args)
{
    // Variablen-Definition
    DLL                     winInet;
    DLLFunction             internetConnect;
    DLLFunction             internetOpen;
    DLLFunction             internetCloseHandle;
    DLLFunction             ftpPutFile;
    DLLFunction             ftpRenameFile;
    DLLFunction             ftpDeleteFile;
    DLLFunction             ftpCreateDirectory;
    DLLFunction             ftpRemoveDirectory;

    int                     connectionHandle;
    int                     FileHandle;
    int                     handle;

    // Submethoden
    int internetOpen(str 255 _agent, int _accessType, str 255 _proxyName, str 255 _proxyByPass, int _flags)
    {
        return internetOpen.call(_agent, _accessType, _proxyName, _proxyByPass, _flags);
    }

    int internetConnect(str 60 _server, str 99 _userName, str 99 _password )
    {
        return internetConnect.call(handle, _server, 0, _userName, _password, 1, 0, 0);
    }

    boolean internetCloseHandle(int _handle)
    {
        return internetCloseHandle.call(_handle);
    }

    int FtpPutFile(int _hdl, str 255 _localFile, str 255 _remoteFile)
    {
        return FtpPutFile.call(_hdl, _localFile, _remoteFile, 2, 0);
    }

    int FtpRenameFile(int _hdl, str 255 _localFile, str 255 _remoteFile)
    {
        return FtpRenameFile.call(_hdl, _localFile, _remoteFile);
    }

    int FtpDeleteFile(int _hdl, str 255 _localFile)
    {
        return FtpDeleteFile.call(_hdl, _localFile);
    }

    int FtpCreateDirectory(int _hdl, str 255 _directory)
    {
        return FtpCreateDirectory.call(_hdl, _directory);
    }

    int FtpRemoveDirectory(int _hdl, str 255 _directory)
    {
        return FtpRemoveDirectory.call(_hdl, _directory);
    }

    ;

    // Objekte erstellen
    winInet = new DLL('WinInet');

    internetConnect = new DLLFunction(winInet, "InternetConnectA");
    internetConnect.returns(ExtTypes::DWORD);
    internetConnect.arg(ExtTypes::DWORD);
    internetConnect.arg(ExtTypes::STRING);
    internetConnect.arg(ExtTypes::DWORD);
    internetConnect.arg(ExtTypes::STRING);
    internetConnect.arg(ExtTypes::STRING);
    internetConnect.arg(ExtTypes::DWORD);
    internetConnect.arg(ExtTypes::DWORD);
    internetConnect.arg(ExtTypes::DWORD);

    internetOpen = new DLLFunction(winInet, 'InternetOpenA');
    internetOpen.returns(ExtTypes::DWORD);
    internetOpen.arg(ExtTypes::STRING);
    internetOpen.arg(ExtTypes::DWORD);
    internetOpen.arg(ExtTypes::STRING);
    internetOpen.arg(ExtTypes::STRING);
    internetOpen.arg(ExtTypes::DWORD);

    internetCloseHandle = new DLLFunction(winInet, 'InternetCloseHandle');
    internetCloseHandle.returns(ExtTypes::DWORD);
    internetCloseHandle.arg(ExtTypes::DWORD);

    ftpPutFile  = new DLLFunction(winInet, "FtpPutFileA");
    ftpPutFile.returns(ExtTypes::DWORD);
    ftpPutFile.arg(ExtTypes::DWORD);
    ftpPutFile.arg(ExtTypes::STRING);
    ftpPutFile.arg(ExtTypes::STRING);
    ftpPutFile.arg(ExtTypes::DWORD);
    ftpPutFile.arg(ExtTypes::DWORD);

    ftpRenameFile  = new DLLFunction(winInet, "FtpRenameFileA");
    ftpRenameFile.returns(ExtTypes::DWORD);
    ftpRenameFile.arg(ExtTypes::DWORD);
    ftpRenameFile.arg(ExtTypes::STRING);
    ftpRenameFile.arg(ExtTypes::STRING);

    ftpDeleteFile  = new DLLFunction(winInet, "FtpDeleteFileA");
    ftpDeleteFile.returns(ExtTypes::DWORD);
    ftpDeleteFile.arg(ExtTypes::DWORD);
    ftpDeleteFile.arg(ExtTypes::STRING);

    ftpCreateDirectory  = new DLLFunction(winInet, "FtpCreateDirectoryA");
    ftpCreateDirectory.returns(ExtTypes::DWORD);
    ftpCreateDirectory.arg(ExtTypes::DWORD);
    ftpCreateDirectory.arg(ExtTypes::STRING);

    ftpRemoveDirectory  = new DLLFunction(winInet, "FtpRemoveDirectoryA");
    ftpRemoveDirectory.returns(ExtTypes::DWORD);
    ftpRemoveDirectory.arg(ExtTypes::DWORD);
    ftpRemoveDirectory.arg(ExtTypes::STRING);


    // Verbindung aufbauen
    handle = internetOpen('Axapta', 0, '', '', 0);

    connectionHandle = internetConnect('someftp.com', 'domain/username', 'password');
    if(connectionHandle == 0)
    {
        throw error('Could not connect');
    }

    // Datei übertragen
    FileHandle = FtpPutFile(connectionHandle, 'c:\\filename.ext', 'dir1/subdir1/subdir2/uploadfilename.ext');
    if (FileHandle == 0)
    {
        error('Error');
    }
    else
    {
        info('Success');
    }

    // Datei am FTP-Server umbenennen
    FileHandle = FtpRenameFile(connectionHandle, 'dir1/subdir1/subdir2/uploadfilename.ext', 'dir1/subdir1/subdir2/renamed_filename.ext');
    if (FileHandle == 0)
    {
        error('Error');
    }
    else
    {
        info('Success');
    }

    // Datei am FTP-Server löschen
    FileHandle = FtpDeleteFile(connectionHandle, 'dir1/subdir1/subdir2/renamed_filename.ext');
    if (FileHandle == 0)
    {
        error('Error');
    }
    else
    {
        info('Success');
    }

    // Verzeichnis am FTP-Server erstellen
    FileHandle = FtpCreateDirectory(connectionHandle, 'dir1/subdir1/subdir2/new_dir');
    if (FileHandle == 0)
    {
        error('Error');
    }
    else
    {
        info('Success');
    }

    // Verzeichnis am FTP-Server löschen
    FileHandle = FtpRemoveDirectory(connectionHandle, 'dir1/subdir1/subdir2/new_dir');
    if (FileHandle == 0)
    {
        error('Error');
    }
    else
    {
        info('Success');
    }

    // Verbindung trennen
    internetCloseHandle(connectionHandle);
 
}

Übrigens, den Code habe ich bislang nur in AX 4.0 getestet, er sollte aber auch problemlos in anderen, älteren AX-Versionen laufen.

Wer mehr über die WinInet wissen möchte, im Microsoft Developer Network findet man so ziemlich alles dazu.

Dieser Beitrag bezieht sich auf die Version:
Dynamics AX 4.0

 
 

 

 
 
 
Beiträge des aktuellen Monats
November 2024
MoDiMiDoFrSaSo
 123
45678910
11121314151617
18192021222324
252627282930 
 
© 2006-2024 Heinz Schweda | Impressum | Kontakt | English version | Mobile Version
Diese Webseite verwendet Cookies, um Benutzern einen besseren Service anzubieten. Wenn Sie weiterhin auf der Seite bleiben, stimmen Sie der Verwendung von Cookies zu.  Mehr dazu