2017-02-25 3 views
1

현재 데이터베이스에서 데이터를 수집하고이를 쉼표로 구분 된 단일 플랫 파일로 출력하는 SSIS를 만듭니다. 파일에는 주문 세부 정보가 포함됩니다. 파일 형식은SSIS - 플랫 파일로 출력 할 여러 열 수

Order#1 details (51 columns) 
Order#1 header (62 columns) 
Order#2 details (51 columns) 
Order#2 header (62 columns) 
etc... 

입니다. 주문 헤더에는 62 개의 열이 있고 주문 세부 사항에는 51 개의 열이 있습니다. 이 파일을 플랫 파일로 출력해야하며 SSIS가 다양한 열을 처리하지 않기 때문에 문제가 발생합니다. 누군가 내게 도움을 주실 수 있고 내 소스가 쿼리를 사용하여 OLEDB 소스 인 경우 파일로 출력 할 스크립트 구성 요소를 어떻게 만듭니 까?

현재 패키지는 다음과 같습니다

  1. 모든 순서의 목록을 가져옵니다. orderid를 변수로 전달하십시오.
  2. for 루프 컨테이너는 각 orderid를 거치며 데이터 태스크 플로우를 실행하여 주.에 대한 주. 세부 사항을 확보합니다. 데이터 태스크를 실행하여 주문 헤더를 가져옵니다. 각 줄을 플랫 파일로 출력하는 데 문제가 있습니다.

누구든지 도움을받을 수 있다면 대단히 감사하겠습니다. 저는 일주일 동안이 문제에 고심하고 있습니다. 누구든지 스크립트 구성 요소 코드가 어떤 모습으로 시작되어야하는지 알려 주시면 대단히 감사하겠습니다. 나는 지금까지 무엇을 추가 한

: http://imgur.com/a/yTxfH

이 내 스크립트 모습입니다 같은 :

public void Main() 
    { 
     // TODO: Add your code here 
     DataTable RecordType300 = new DataTable(); 
     DataTable RecordType210 = new DataTable(); 
     DataTable RecordType220 = new DataTable(); 
     DataTable RecordType200 = new DataTable(); 

     OleDbDataAdapter adapter = new OleDbDataAdapter(); 
     adapter.Fill(RecordType300, Dts.Variables["User:rec_type300"].Value); 
     adapter.Fill(RecordType210, Dts.Variables["User::rec_type_210"].Value); 
     adapter.Fill(RecordType220, Dts.Variables["User::rec_type_220"].Value); 
     adapter.Fill(RecordType200, Dts.Variables["User::rec_type200"].Value); 
     using (StreamWriter outfile = new StreamWriter("C:\\myoutput.csv")) 
     { 
      for (var i = 0; i < RecordType300.Rows.Count; i++) 
      { 
       var detailFields = RecordType300.Rows[i].ItemArray.Select(field => field.ToString()).ToArray(); 
       // var poBillFields = RecordType210.Rows[i].ItemArray.Select(field => field.ToString()).ToArray(); 
       // var poShipFields = RecordType220.Rows[i].ItemArray.Select(field => field.ToString()).ToArray(); 
      // var poHeaderFields = RecordType200.Rows[i].ItemArray.Select(field => field.ToString()).ToArray(); 
       outfile.WriteLine(String.Join(",", detailFields)); 
       // outfile.WriteLine(string.Join(",", poBillFields)); 
       // outfile.WriteLine(string.Join(",", poShipFields)); 
       // outfile.WriteLine(string.Join(",", poHeaderFields)); 
      } 
     } 

     Dts.TaskResult = (int)ScriptResults.Success; 

    } 

하지만, 그것은 오류가 밖으로 그것을 실행할 때마다. 내가 여기서 뭔가를 놓치고 있니? 또한 처음에 파일을 한 번만 만들려면 어떻게해야합니까? 이 패키지가 실행될 때마다 datestamp가있는 파일이 만들어지고 매번 추가됩니다. 다음 번에 패키지를 실행하면 새 날짜 스탬프가있는 새 파일이 만들어지고 주문 번호를 기반으로 각 주문 세부 정보가 추가됩니다.

+0

스크립트 아이디어로 올바른 길을 가고 있다고 생각합니다. 머리글과 세부 정보의 결과를 두 개의 별도 DataTable에 저장하십시오. 이 링크를 채우고 반복하는 방법의 예로서이 링크를 참조하십시오. http://stackoverflow.com/a/14103080 – sorrell

+0

@Sorrell. 현재 두 개의 별도 데이터 표가 있습니다. 내가 겪고있는 문제는 실제로 스크립트를 만드는 것입니다. – a415

+1

비정형 파일의 일반적인 해결 방법은 쉼표로 구분 된 데이터 묶음이 포함 된 _one_ 열로 데이터를 내보내는 것입니다. 이 쿼리를 생성하고 내보내는 단일 쿼리를 작성할 수 있지만 T-SQL 또는 C#에 익숙한 지 여부에 따라 달라집니다. IMHO는 C#/Lookup 방식이 복잡하고 연결이 끊어져 있습니다. 나는 모든 작업 (효율적으로)을 수행하고 그것을 수출하는 하나의 SQL 쿼리를 작성하는 것을 선호한다. –

답변

1

이 코드/테스트 방법은 테스트하지 않았으므로 어떻게해야 할 지 알려 주어야합니다.

  1. 두 개의 SSIS 변수 (헤더 및 세부 정보 용)를 만듭니다., 머리글에 머리글하지만지도 결과에 대한 유사한 Overview
  2. 설치 프로그램이 작업이 사진과 같은 전체 결과 집합을 처리하기 위해 (상세 버전이 표시됩니다 않습니다 : Variables
  3. 2 Execute SQL 작업과 여기에 설명 등 1 Script Task 만들기 객체와 헤더 테이블에 지점에 쿼리를 변경) : 읽기 전용으로 ExecSqlExecSql2
  4. 편집 스크립트 작업 및 DetailHeader을 할 수는 바르 : ReadOnlyVars
  5. 편집 실제 스크립트를 지금이 라인을 따라 (이것은 당신이 가정됩니다 정확하게 1 헤더 행 1 개 세부 행) :

using System.IO; 
using System.Linq; 
using System.Data.OleDb; 

// following to be inserted into Main() function 
DataTable detailData = new DataTable(); 
DataTable headerData = new DataTable(); 
OleDbDataAdapter adapter = new OleDbDataAdapter(); 
adapter.Fill(detailData, Dts.Variables["User::Detail"].Value); 
adapter.Fill(headerData, Dts.Variables["User::Header"].Value); 

using (StreamWriter outfile = new StreamWriter("myoutput.csv")) 
{ 
    // we are making the assumption that 
    for (var i = 0; i < detailData.Rows.Count; i++) 
    { 
     var detailFields = detailData.Rows[i].ItemArray.Select(field => field.ToString()).ToArray(); 
     var headerFields = headerData.Rows[i].ItemArray.Select(field => field.ToString()).ToArray(); 
     outfile.WriteLine(string.Join(",", detailFields)); 
     outfile.WriteLine(string.Join(",", headerFields)); 
    } 
} 
+0

감사합니다. 이것은 정말 대단합니다. 그러나 추가 조회를 수행해야하므로 스크립트에서 데이터를 가져 오지 않았습니다. 예를 들어,이 출력되기 전에 회사 이름 조회를 수행해야합니다. – a415

+0

SQL 작업 스크립트를 실행하면 해당 열을 변경할 수 없습니다. – a415

+1

데이터 흐름에서 수행 할 수있는 모든 작업은 SQL 및 C#을 사용하여 수행 할 수 있습니다. 예를 들어, 조회 대신 회사 테이블에 조인하도록 구조를 재구성하여 이름을 가져올 수 있습니까? 그렇다면 해당 열은 결과 집합의 일부입니다. 파생 및 계산은 SQL 및/또는 C#을 사용하여 수행 할 수도 있습니다. – sorrell

1

아니 완전한 답변, 뭔가는 다른 방법

SELECT Type, OrderBy, Col 
FROM 
(
    SELECT 'D' As Type, Ord as OrderBy, 
    Col1 + ',' + CAST(Col2 AS VARCHAR(50)) + ',' + Col3 As Col 
    FROM Details 
    UNION ALL 
    SELECT 'H' As Type, Ord as OrderBy, 
    Col1 + ',' + CAST(Col2 AS VARCHAR(50)) + ',' + Col3 As Col + ',' + Col4 
    FROM Header 
) S 
ORDER BY OrderBy, Type 

의 트랙에 당신을 넣어 그것의 추한하지만 varchar 모든 데이터 형식을 캐스팅만큼 작동합니다

뷰 또는 저장 프로 시저에서이를 랩핑하고 SSIS 파트에 도달하기 전에 데이터베이스에서 테스트 할 수 있습니다. 지속적으로 한 열

메타 데이터의 관점에서

A,B,C 
D,E,F,G 

가 :

당신이 여기에있는 것은 이러한 종류의 데이터를 포함 할 일이 하나 개의 컬럼입니다

당신은 오히려 SSIS보다 사용하여이있는 Bcp.exe를 내보낼 수 있습니다

CSV 관점에서 변수 열이 있습니다