2011-03-16 10 views
12

mieć całkiem prosto do przodu pakietu SSIS:SSIS - Płaski plik zawsze ANSI nie UTF-8 zakodowany

  • OLE DB źródło, aby uzyskać dane poprzez widzenia, (wszystkie kolumny ciągów w tabeli db nvarchar lub nchar).
  • Kolumna pochodna do sformatowania istniejącej daty i dodania jej do zestawu danych (typ danych DT_WSTR).
  • Zadanie multiemisji do podzielenia zestawu danych między:
    • Polecenie OLE DB, aby zaktualizować wiersze jako "przetworzone".
    • Miejsce docelowe pliku płaskiego - którego menedżer połączeń ustawiony jest na kod Page 65001 UTF-8 i Unicode są odznaczone. Wszystkie kolumny ciągów mapują do DT_WSTR.

Everytime I uruchomić ten pakiet otwarty plik mieszkanie w Notepad ++ jego ANSI, nigdy UTF-8. Jeśli sprawdzę opcję Unicode, plik to UCS-2 Little Endian.

Czy robię coś złego - w jaki sposób mogę uzyskać, że płaski plik ma kodowanie UTF-8?

Dzięki

+0

OK - wydawało się, że znalazło akceptowalne podejście do pracy na [forach SQL Server] (http://social.msdn.microsoft.com/forums/sqlintegrationservices/thread/9B68C357-A5B4-47BF-8EFD -A05945210CA2). Zasadniczo musiałem utworzyć dwa pliki szablonów UTF-8, użyć zadania Plik, aby skopiować je do miejsca docelowego, a następnie upewnić się, że dodawałem dane, zamiast nadpisywać. – Neil

+1

Możesz odpowiedzieć na swoje pytanie, a następnie oznaczyć je. – Sam

Odpowiedz

0

OK - wydawało się, że znalazłem akceptowalne obejście na SQL Server Forums. Zasadniczo musiałem utworzyć dwa pliki szablonów UTF-8, użyć zadania Plik, aby skopiować je do miejsca docelowego, a następnie upewnić się, że dodawałem dane, a nie nadpisywanie.

20

W Źródło -> Advance Editor -> Właściwości Component - Kodeks> Set Default Page do 65001 AlwaysUseDefaultCodePage do Prawdziwa

Następnie source-> Advance Editor -> Wejście i wyjście Właściwości Sprawdź Każda kolumna Kolumny zewnętrzne i OutPut Columns i ustaw CodePage na 65001, jeśli to możliwe.

To wszystko.

Przy okazji program Excel nie może zdefiniować danych w pliku jako UTF - 8. Program Excel jest tylko narzędziem obsługi plików. Możesz również tworzyć pliki csv za pomocą notatnika. tak długo, jak wypełniasz plik csv z UTF-8, powinieneś być w porządku.

+2

W Source -> Advance Editor -> Właściwości komponentu -> Ustaw domyślną stronę kodową na 65001 AlwaysUseDefaultCodePage na True, ta czynność pomogła mi zaoszczędzić godziny, szukając błędu odniesienia dla podwójnej strony kodowej. – BigChief

+1

Należy zauważyć, że to nie działa z kolumnami NVARCHAR (MAX) , ale działa, jeśli zapytanie zostanie przesłane do NVARCHAR (4000). Jeśli zapytanie wymaga w polu 4000 znaków, wypróbuj komponent skryptu lub jedno z pozostałych rozwiązań. – NYCdotNet

5

Dodanie wyjaśnienia do odpowiedzi ...

ustawienie strony kodowej do 65001 (ale nie zaznacz pole Unicode na źródło pliku), należy wygenerować plik UTF-8. (tak, typy danych również wewnętrznie powinny być nvarchar, itp.).

Jednak plik wytworzony z SSIS nie ma nagłówka BOM (znacznika kolejności bajtów), więc niektóre programy przyjmą, że nadal jest to ASCII, a nie UTF-8. Widziałem to potwierdzone przez pracowników MS na MSDN, a także potwierdzone przez testowanie.

Rozwiązanie dołączane do pliku jest sposobem obejścia tego problemu - poprzez utworzenie pustego pliku Z prawidłowym zestawieniem komponentów, a następnie dołączaniem danych z SSIS, nagłówek specyfikacji materiałowej pozostaje na miejscu. Jeśli powiesz SSIS, aby nadpisał plik, również traci on LM.

Dzięki za wskazówki, pomogły mi one wymyślić powyższy szczegół.

4

Niedawno pracował na problem gdzie natknąć sytuacji takiej jak:

pracujesz nad rozwiązaniem pomocą SQL Server Integration Services (Visual Studio 2005). Wyciągasz dane z bazy danych i próbujesz umieścić wyniki w płaskim pliku (.CSV) w formacie UTF-8. Rozwiązanie eksportuje dane doskonale i zachowuje znaki specjalne w pliku, ponieważ użyłeś 65001 jako strony kodowej.

Jednak plik tekstowy po otwarciu lub próbie załadowania go do innego procesu, mówi, że plik ma ANSI zamiast UTF-8. Jeśli otworzysz plik w notatniku i zrobisz ZAPISZ JAKO i zmień kodowanie na UTF-8, a następnie twój zewnętrzny proces działa, ale jest to żmudna praca ręczna.

Co odkryłem, że po określeniu właściwości strony kodowej menedżera połączeń pliku płaskiego, generowany jest plik UTF-8. Generuje jednak wersję pliku UTF-8, który pomija coś, co nazywamy Markerem kolejności bajtów.

Więc jeśli masz plik CSV zawierający znak AA, BOM dla UTF8 będzie 0xef, 0xbb i 0xbf. Mimo że plik nie zawiera specyfikacji materiałowej, nadal jest to kodowanie UTF8.

Niestety, w niektórych starych starszych systemach aplikacje wyszukują zestawienie komponentów, aby określić typ pliku. Wygląda na to, że twój proces również robi to samo.

Aby obejść problem, można użyć następującego kodu w zadaniu skryptu, który można uruchomić po procesie eksportowania.

using System.IO; 

using System.Text; 

using System.Threading; 

using System.Globalization; 

enter code here 

static void Main(string[] args) 
     { 
      string pattern = "*.csv"; 
      string[] files = Directory.GetFiles(@".\", pattern, SearchOption.AllDirectories); 
      FileCodePageConverter converter = new FileCodePageConverter(); 
      converter.SetCulture("en-US"); 
      foreach (string file in files) 
      { 
       converter.Convert(file, file, "Windows-1252"); // Convert from code page Windows-1250 to UTF-8 
      } 
     } 

class FileCodePageConverter 
    { 
     public void Convert(string path, string path2, string codepage) 
     { 
      byte[] buffer = File.ReadAllBytes(path); 
      if (buffer[0] != 0xef && buffer[0] != 0xbb) 
      { 
       byte[] buffer2 = Encoding.Convert(Encoding.GetEncoding(codepage), Encoding.UTF8, buffer); 
       byte[] utf8 = new byte[] { 0xef, 0xbb, 0xbf }; 
       FileStream fs = File.Create(path2); 
       fs.Write(utf8, 0, utf8.Length); 
       fs.Write(buffer2, 0, buffer2.Length); 
       fs.Close(); 
      } 
     } 

     public void SetCulture(string name) 
     { 
      Thread.CurrentThread.CurrentCulture = new CultureInfo(name); 
      Thread.CurrentThread.CurrentUICulture = new CultureInfo(name); 
     } 
    } 

kiedy będzie uruchomić pakiet można zauważyć, że wszystkie pliki CSV w wyznaczonym folderze zostaną przekształcone w formacie UTF-8, który zawiera bom.

W ten sposób Twój proces zewnętrzny będzie mógł pracować z eksportowanymi plikami CSV.

jeśli szukasz tylko do określonego folderu ... wysłać tę zmienną do zadania skryptu i używać poniżej jednego ..

 string sPath; 

     sPath=Dts.Variables["User::v_ExtractPath"].Value.ToString(); 

     string pattern = "*.txt"; 

     string[] files = Directory.GetFiles(sPath); 

Mam nadzieję, że to pomoże !!

+0

Pracuję nad projektem, w którym przekazuję pliki CSV zespołowi Linux, który ostatecznie załaduje je do magazynu MySQL. Twoje podejście było jedyną, która działała dla nich. Twój kod zadziałał, dodałem tylko parametrowanie. Każda próba utworzenia pliku zakodowanego w formacie UTF-8, który został załadowany bez problemów z urządzeniami pokładowymi SSIS, zakończył się niepowodzeniem. – cdonner