6

問題!

Web ページ (http クロール) を通過する小さな python スクリプトがあります。この Web ページはイントラネット内でホストされ、NTLM 認証を使用してアクセスを収集します。

したがって、このタスク (http コンテンツの取得) は、python スクリプト全体を C# に書き直してから、タスクを完了するために SSIS の「スクリプト タスク」で使用するのではなく、python を使用して簡単にプログラムできることがわかりました。

ヒント!

SSIS ツールを詳しく調べたところ、Win32 実行可能ファイルを実行できる「プロセス タスクの実行」という名前の制御フローがあることがわかりました。

しかし、問題は実行可能ではなく、Python インタープリターによって解釈される必要があるため (繰り返しを許す場合)、私の python スクリプトを呼び出す方法にあります。そのため、Python スクリプトとインタープリターの両方を呼び出す単純な「.bat」ファイルを簡単に作成することができました。そして、そのファイルを SSIS の「Execute Process Task」で実行します。

質問!

これを実装する他の方法はありますか?(きちんとした方法)

編集#1

使用法

スクリプトから取得した情報は、その情報をデータベースのテーブルに格納するため、別の SSIS プロセスからデータベース テーブルを介して情報にアクセスできます。

Web サービスに投稿して Excel プロジェクトからアクセスできるデータベースにその情報をアーカイブするために、さまざまなソース (フラット ファイル、データベース テーブル、http 要求など) から情報を取得しています。

前もって感謝します!

4

3 に答える 3

4

少なくとも私の頭の中では、SSISの範囲からIronPythonを使用するための最も簡単なメカニズムは、外部プロセスを呼び出してファイルにダンプし、それをデータフローのソースとして使用することです。

そうは言っても、C#からIronPythonアプリをホストし、返されたデータを使用して出力バッファーにデータを入力し、パイプラインでそのデータを操作することができました。これを実行するマシンは1台しかないので、パッケージが緑色になるまで行ったことを思い出すすべてをリストします。

前提条件

この記事は、これを機能させる方法の道を私に教えてくれました。C#4.0プログラムでIronPythonをホストする SSISはすべてにレイヤーを追加するため、C#/ VB.NETコンソールアプリを作成し、そこで最初にIronPython統合を機能させることを強くお勧めします。

4.0フレームワークを必要とせずにC#内で古いバージョンのIronPythonをホストする機能があるかもしれませんが、それは私の能力の範囲をはるかに超えています。私が言えることは、4.0フレームワークを使用するには、SQL Server 2012を見ているということです。2008パッケージは、最大3.5フレームワーク(デフォルトは2.0)をターゲットにできます。

グローバルアセンブリキャッシュ、略してGAC。これは、署名されたアセンブリが存在できるWindowsの特別な場所です。SSISはGACにないアセンブリを使用できるかもしれませんが、私はそうすることができませんでした。この場合も例外ではありませんでした。コンソールアプリは正常に機能しましたが、そのコードをSSISにコピーすると、Could not load file or assembly 'Microsoft.Scripting...エラーメッセージが表示されます。幸いなことに、IronPython-2.7.2.1(およびおそらく以前のバージョン)は強力に署名されたdllです。つまり、GACに追加することができ、追加する必要があります。

Visual Studioディレクトリで、Visual Studioコマンドプロンプト(2010)を探します。IronPythonインストールフォルダーを次のようにC:\tmp\IronPython-2.7.2.1\IronPython-2.7.2.1入力すると仮定します。cd C:\tmp\IronPython-2.7.2.1\IronPython-2.7.2.1次に、次の3つのアセンブリを登録しました

C:\tmp\IronPython-2.7.2.1\IronPython-2.7.2.1>gacutil -if Microsoft.Dynamic.dll
Microsoft (R) .NET Global Assembly Cache Utility.  Version 4.0.30319.1
Copyright (c) Microsoft Corporation.  All rights reserved.

Assembly successfully added to the cache

C:\tmp\IronPython-2.7.2.1\IronPython-2.7.2.1>gacutil -if IronPython.dll
Microsoft (R) .NET Global Assembly Cache Utility.  Version 4.0.30319.1
Copyright (c) Microsoft Corporation.  All rights reserved.

Assembly successfully added to the cache

C:\tmp\IronPython-2.7.2.1\IronPython-2.7.2.1>gacutil -if Microsoft.Scripting.dll
Microsoft (R) .NET Global Assembly Cache Utility.  Version 4.0.30319.1
Copyright (c) Microsoft Corporation.  All rights reserved.

Assembly successfully added to the cache

私のSSISプロジェクトでは、Run64bitRuntimeをFalseに設定していましたが、再テストでは問題ありません。デフォルトはTrueで、これは正常に機能しているようです。

Pythonスクリプト-C#と.NETDLR言語の統合をより適切にするための十分な背景がありません。実行したいスクリプトを含む文字列などを提供できればよかったのですが、おそらくそれがスクリプトブロックの目的ですが、調査する時間がありません。したがって、このソリューションでは、ディスク上のどこかにスクリプトファイルを配置する必要があります。ホストされたスクリプトからのインポートの動作に問題がありました(X例外という名前のモジュールはありません)。間違いなく、クラスパスと、それをうまく機能させるためにホストに提供する必要のあるすべてのものには、いくつかの魔法があります。それはおそらく別のSOの質問です。

設定

C:\ ssisdata\simplePy.pyにファイルがあります

# could not get a simple import to work from hosted
# works fine from "not hosted"
#import os

def GetIPData():
    #os.listdir(r'C:\\')
    return range(0,100)

スクリプトタスクをデータフローに追加した後、出力バッファー(wstr 1000)に単一の列を持つように構成しました。次に、これをソースコードとして使用しました。

using System;
using System.Collections.Generic;
using System.Data;
using Microsoft.SqlServer.Dts.Pipeline.Wrapper;
using Microsoft.SqlServer.Dts.Runtime.Wrapper;
using IronPython.Hosting;
using Microsoft.Scripting.Hosting;

/// <summary>
/// Attempt to use IP script as a source
/// http://blogs.msdn.com/b/charlie/archive/2009/10/25/hosting-ironpython-in-a-c-4-0-program.aspx
/// </summary>
[Microsoft.SqlServer.Dts.Pipeline.SSISScriptComponentEntryPointAttribute]
public class ScriptMain : UserComponent
{

    /// <summary>
    /// Create data rows and fill those buckets
    /// </summary>
    public override void CreateNewOutputRows()
    {
        foreach (var item in this.GetData())
        {
            Output0Buffer.AddRow();
            Output0Buffer.Content = item;
        }

    }

    /// <summary>
    /// I've written plenty of code, but I'm quite certain this is some of the ugliest.
    /// There certainly must be more graceful means of 
    /// * feeding your source code to the ironpython run-time than a file
    /// * processing the output of the code the method call
    /// * sucking less at life
    /// </summary>
    /// <returns>A list of strings</returns>
    public List<string> GetData()
    {
        List<string> output = null;
        var ipy = Python.CreateRuntime();
        dynamic test = ipy.UseFile(@"C:\ssisdata\simplePy.py");
        output = new List<string>();
        var pythonData = test.GetIPData();
        foreach (var item in pythonData)
        {
            output.Add(item.ToString());
        }

        return output;
    }
}

私の参照がどのように見えるかのクイックショット

参考文献

実行ボタンをクリックして大成功

データフロー

于 2012-04-27T18:51:40.340 に答える
2

どれだけきちんとなりたいですか?私はあなたのオプションは問題ないと思います、そしてあなたはあなたの問題を解決するためのより簡単な方法を見つけることができません。あなたはファイルのリストを持っていて、それらを実行する必要があります、それだけです。

私が考えることができることの1つは、すべてのファイルパスをSQLテーブルに追加し、xp_cmdshellでそれらを実行することです。

SQLインスタンスで有効にする必要があります(SSISの使用を検討しているので、SQLインスタンスがあると思います)

EXEC sp_configure 'show advanced options', 1
GO
reconfigure
go

EXEC sp_configure 'xp_cmdshell', 1
GO

reconfigure
go

テーブル上でループし、行ごとに実行できるよりも:

exec master.dbo.xp_cmdshell 'your_script'
于 2012-04-27T15:18:18.627 に答える
2

簡単な解決策(.batなし)はどうですか:

「プロセス実行タスク」のエディターで、実行可能ファイルを Python INTERPRETER に設定ます。

C:\...\Python34\python.exe

引数には、最初にスクリプト パスを設定し、その後にスクリプトの引数を設定します

H:\...\test\helloworld.py -a 1 -b 2

WorkingDirectoryを忘れないでください

H:\...\test
于 2015-03-06T10:23:55.840 に答える