Pomoc - Szukaj - Użytkownicy - Kalendarz
Pełna wersja: MSSQL + PHP + francuskie znaki
Forum PHP.pl > Forum > PHP
kr27
Witam

Czy orientuje się ktoś z Was jak poprawnie wyświetlać i zapisywać francuskie znaki w PHP w MSSQL ?
W Enterprise Manager do tabeli wpisuję np:
àâçéèêëîïôûùüÿœæÀÂÇÉÈÊËÎÏÔÛÙÜŸŒÆ

Następnie wykonuję kod:
echo iconv("Windows-1250", "UTF-8//TRANSLIT//IGNORE", $pole);

W rezultacie mam:
aâçéeeëîiôuuüyoaAÂÇÉEEËÎIÔUUÜYOA

Wiem, że znaku "à" nie ma w kodowaniu 1250 i w tym problem - więc jakie to kodowanie powinno być skoro w tej samej kolumnie mam też zapisane dane w języku polskim, niemieckim oraz czeskim (z nimi nie ma żadnego problemu)

Z góry dziękuję
Pozdrawiam






Noidea
Jeśli masz typ kolumny char/varchar/text, to stronę kodową masz zapisaną w 'collation' kolumny, np.: SQL_Polish_CP1250_CI_AS = CodePage 1250 (PS: CP1 to to samo co CP1252)
No i oczywiście przy próbie wstawienia do takiej kolumny tekstu "àâçéèêëîïôûùüÿœæÀÂÇÉÈÊËÎÏÔÛÙÜŸŒÆ" SQL Server zamieni ci niewystępujące w tym kodowaniu znaki na ich odpowiedniki.

Jeśli chcesz przechowywać dane w wielu językach, to zamień typ kolumny na nchar/nvarchar. Kodowanie w tych kolumnach to zawsze UCS-2 i wszystkie europejskie litery są w nim zawarte.
kr27
Typ mojej kolumny to właśnie nvarchar.
Czy możesz mnie nakierować jak dokładnie powinien wyglądać zapis i odczyt danych w PHP?

Pozdrawiam
Noidea
podaj wersję php, system operacyjny i sposób, w jaki wykonujesz operacje na bazie (a najlepiej phpinfo)
kr27
http://www.speedyshare.com/files/26569465/phpInfo.html - tutaj moja konfiguracja PHP

Windows 2000 + MSSQL 2000

Dane zapisuje i odczytuje przez PDO.
Noidea
Poleciłbym ci nowy sterownik do PDO ( http://blogs.iis.net/sqlphp/archive/2010/0...-milestone.aspx ), który radzi sobie z UTF-8. Problem w tym, że z tego co widzę po wymaganiach, to potrzebuje on przynajmniej MSSQL 2005.

Znalazłem też rozwiązanie dla PHP na Linuksie + MSSQL, które też cie nie zainteresuje i kilka rodzajów obejść, typu:
  1. $stmt = $dbh->query( "SELECT CONVERT( varbinary( MAX ), kolumna_nvarchar ) AS kolumna_nvarchar FROM tabela" );
  2. while( $row = $stmt->fetch( PDO::FETCH_ASSOC ) )
  3. {
  4. echo iconv( "UCS-2LE", "UTF-8", $row['kolumna_nvarchar'] );
  5. }
kr27
50% problemu rozwiązane!

SELECT CONVERT( varbinary( MAX ), kolumna_nvarchar ) AS kolumna_nvarchar FROM tabela
powyższe pomaga przy odczycie danych. Nawet poprawnie wyświetlają mi się rosyjskie czcionki.


Problem natomiast mam cały czas z zapisem.
Stosuję odwrotność w postaci:

UPDATE tabela SET pole=CONVERT(varbinary(300), :pole ) WHERE id=4

":pole" przekazuje w PDO przez parametr po konwersji: iconv("UTF-8","UCS-2LE", $zmienna);

Wszystko jest ok ale tylko jeśli pod $zmienna przekazuje jeden znak np. "à" - jeśli przekaże kilka znaków np "àà" to wywala mi błąd:
Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[HY000]: General error: 10007 Line 1: Incorrect syntax near '�'. [10007] (severity 5) [(null)]'

Czy masz jakiś pomysł?
Bardzo dziękuję za dotychczasową pomoc.



Noidea
Musisz zrobić to tak:
1. Konwersja kodowania UTF-8 => UCS-2
2. Zapis danych w postaci hexadecymalnej
3. Wstawienie do zapytania, które te binarne dane skonwertuje na typ kolumny nvarchar


$utf8Str = "zażółć gęślą jaźń àà àààà àà ZAŻÓŁĆ GĘŚLĄ JAŹŃ";
  1. $ucs2Str = iconv( "UTF-8", "UCS-2LE", $utf8Str );
  2.  
  3. $hex = unpack( "H*", $ucs2Str );
  4. $hexStr = "0x" . $hex[1];
  5.  
  6. $dbh->exec( "INSERT INTO tabela ( kolumna_nvarchar ) VALUES ( CONVERT( nvarchar( MAX ), " . $hexStr . " ) )" );


Nie wiem tylko jak wstawić dane binarne w postaci 0x0123abcd jako parametr 'prepared statement' - musisz sobie poszukać na google.

Dodatkowo zapytania tworzone w ten sposób będą długie (chodzi o ilość znaków, nie czas wykonywania) - to też może powodować problemy, ale nie jestem pewien.
kr27
Bardzo dziękuję za pomoc. Sam na to bym nie wpadł. Zaoszczędziłeś mi mnóstwo czasu.
Wiszę skrzynkę piwa.

Pozdrawiam
To jest wersja lo-fi głównej zawartości. Aby zobaczyć pełną wersję z większą zawartością, obrazkami i formatowaniem proszę kliknij tutaj.
Invision Power Board © 2001-2025 Invision Power Services, Inc.