2012-03-04 12 views
5

AI staram się zrobić nowy wpis użytkownika DSN, w Administrator źródła danych ODBC z następującego kodu:tworzenia nowego użytkownika DSN ODBC z Delphi

procedure TForm1.FormCreate(Sender: TObject); 
var strAttributes: string; 
    wideChars : array[0..1000] of WideChar; 
    pfErrorCode: DWORD; 
    errMsg: PChar; 

begin 
strAttributes := 'DSN=' + 'example_DSN' + Chr(0); 
    strAttributes := strAttributes + 'DESCRIPTION=' + 'description' + Chr(0); 
    strAttributes := strAttributes + 'SERVER=' + 'testserver' + Chr(0); 
    strAttributes := strAttributes + 'DATABASE=' + 'somedatabase' + Chr(0); 

    StringToWideChar(strAttributes, wideChars, 12); 
    if not SqlConfigDataSource(0, ODBC_ADD_DSN, 'SQL Server', wideChars) then 
    begin 
    errMsg := AllocMem(SQL_MAX_MESSAGE_LENGTH); 
    SQLInstallerError(1, @pfErrorCode, errMsg, SQL_MAX_MESSAGE_LENGTH, nil); 
    MessageBox(0, errMsg, PChar('Add System DSN Error #' + IntToStr(pfErrorCode)), 0); 
    FreeMem(errMsg); 
    end; 
end; 

ale część SqlConfigDataSource nie wykonać zadanie, a także zwracany błąd nie jest wcale nie do odróżnienia. Nie jest to liczba ani opis błędu. Czy ktoś może mi pomóc, gdzie popełniam błąd? Dzięki

Odpowiedz

7

Prawdopodobnie Twój błąd, a nawet zestaw błędów, jest nieprawidłowym tłumaczeniem nagłówków ODBC, które mogą być następnie użyte dla wersji Unicode lub Unicode Delphi. Na przykład:

  • dla Delphi Unicode raczej trzeba użyć XxxW funkcje (UTF16) od ODBCCP32.DLL, niż Xxx funkcji (ANSI);
  • dla funkcji innych niż Unicode Delphi, a raczej Xxx. A następnie wideChars należy zdefiniować jako array[..] of Char;
  • SqlConfigDataSource może być zdefiniowany jako XxxW z PAnsiChar;
  • itp

Chciałem pokazać wam ten pomysł, ponieważ bez pełnych źródeł Mogę tylko spekulować. Wtedy masz podejrzaną rozmowę StringToWideChar(strAttributes, wideChars, 12);. Wartość strAttributes jest dłuższa niż 12 znaków.

Poniższy kod działa dobrze w Delphi XE2:

type 
    SQLHWnd = LongWord; 
    SQLChar = Char; 
    PSQLChar = ^SQLChar; 
    SQLBOOL = WordBool; 
    UDword = LongInt; 
    PUDword = ^UDword; 
    SQLSmallint = Smallint; 
    SQLReturn = SQLSmallint; 

const 
    SQL_MAX_MESSAGE_LENGTH = 4096; 

    ODBC_ADD_DSN  = 1;   // Add data source 
    ODBC_CONFIG_DSN = 2;   // Configure (edit) data source 
    ODBC_REMOVE_DSN = 3;   // Remove data source 

    ODBC_ADD_SYS_DSN = 4;   // add a system DSN 
    ODBC_CONFIG_SYS_DSN = 5;  // Configure a system DSN 
    ODBC_REMOVE_SYS_DSN = 6;  // remove a system DSN 
    ODBC_REMOVE_DEFAULT_DSN = 7; // remove the default DSN 

function SQLConfigDataSource (
    hwndParent:  SQLHWnd; 
    fRequest:  WORD; 
    lpszDriver:  PChar; 
    lpszAttributes: PChar 
): SQLBOOL; {$IFDEF MSWINDOWS} stdcall {$ELSE} cdecl {$ENDIF}; 
    external 'odbccp32.dll' name 'SQLConfigDataSourceW'; 

function SQLInstallerError (
    iError:   WORD; 
    pfErrorCode:  PUDword; 
    lpszErrorMsg:  PChar; 
    cbErrorMsgMax: WORD; 
    pcbErrorMsg:  PWORD 
): SQLReturn; {$IFDEF MSWINDOWS} stdcall {$ELSE} cdecl {$ENDIF}; 
    external 'odbccp32.dll' name 'SQLInstallerErrorW'; 

procedure TForm616.Button1Click(Sender: TObject); 
var 
    strAttributes: string; 
    pfErrorCode: UDword; 
    errMsg: PChar; 
begin 
    strAttributes := 'DSN=' + 'example_DSN' + Chr(0); 
    strAttributes := strAttributes + 'DESCRIPTION=' + 'description' + Chr(0); 
    strAttributes := strAttributes + 'SERVER=' + 'testserver' + Chr(0); 
    strAttributes := strAttributes + 'DATABASE=' + 'somedatabase' + Chr(0); 
    if not SqlConfigDataSource(0, ODBC_ADD_DSN, 'SQL Server', PChar(strAttributes)) then begin 
    errMsg := AllocMem(SQL_MAX_MESSAGE_LENGTH); 
    SQLInstallerError(1, @pfErrorCode, errMsg, SQL_MAX_MESSAGE_LENGTH, nil); 
    MessageBox(0, errMsg, PChar('Add System DSN Error #' + IntToStr(pfErrorCode)), 0); 
    FreeMem(errMsg); 
    end; 
end; 
+0

dziękuję, to wystarczyło – dzibul

-1

Odpowiedź jest w porządku, ale muszę sporządzić notatkę.

Jeśli nie ustawić testserver z portem, znaki okna „Sterownik ODBC serwera SQL równa DBNETLIB«Nieprawidłowy Connection»” Tworzy kierowcę iw Łéczy ale za każdym razem wysyła ten błąd, jeśli nie ustawiona serwer testowy jak:

'testserver, port'

strAttributes := strAttributes + 'SERVER=' + 'testserver,port' + Chr(0); 

to by lepszą odpowiedź bo to uniknąć sendidng tego błędu.