コンバータプラグイン
ドキュメントを24の対象フォーマットに変換
コンバータプラグインは Doconut をドキュメント変換サービスに変えます。パブリック DocumentConverter ファサードの背後にあるエンジンと、オプトインで DocImage.axd が提供するドロップインウィジェットを提供するので、C# から、ウィジェットから、または自分で作成したフロントエンドからドキュメントを変換できます。
パッケージをインストール
Install-Package Doconut.NETFramework.Converterコンバータパッケージは Doconut.NETFramework と同じバージョンに保ってください。
プラグインを登録
すべてのプラグインは同じ方法で登録されます: AddPlugin<TPlugin>() は DoconutHost.Initialize で。
Doconut.DoconutHost.Initialize(options =>
{
options.LicensePath = HostingEnvironment.MapPath("~/wwwroot/Doconut.Viewer.lic");
options.AddPlugin<Doconut.Plugins.Converter.ConverterPlugin>();
});アクティブなライセンスが
Converter機能を付与していない場合 — ライセンスがない、レガシーTRIALファイル、またはそれが含まれないライセンス —DoconutHost.InitializeはApplication_Startからスローされます。System.Web では、すべてのリクエストが空の500を返し、理由は Windows イベントログ(ソース ASP.NET)にのみ記録されます。一時的なデモ/NFR ライセンスは受け入れられます。License Setup を参照してください。
C# から変換
すべての変換は位置が 0 のシーク可能な MemoryStream を返します。DocumentConverter はステートレスです: 必要な場所で DoconutHost.Services から解決し、自由に再利用できます。
// DoconutHost.Services から DocumentConverter を解決します; コンストラクタは internal なので、決して `new` しないでください。
Stream pdf = await converter.ConvertAsync("contract.docx", ConversionTarget.Pdf, ct: ct);// sourceExtension には先頭のドットが含まれます。ドキュメントが保護されていない限り、password は null です。
Stream png = await converter.ConvertAsync(upload, ".xlsx", ConversionTarget.Png, password: null, ct: ct);Stream html = await converter.WordToHtmlAsync("report.docx", ct);Stream docx = await converter.HtmlToWordAsync(html, ConversionTarget.Docx, ct);間違えやすい2つの詳細があります: ストリームオーバーロードの sourceExtension には先頭のドット(".xlsx"、"xlsx" ではなく)を含める必要があり、含めないと解決しません。また、名前にもかかわらず、WordToHtmlAsync は Task<string> ではなく Task<Stream> を返します — HTML ドキュメント(画像は Base64 埋め込み)は他の結果と同様にストリームとして届きます。
MVC 5 コントローラ内で
アクションを非同期にし、変換を await してください:
[HttpPost]
public async Task<ActionResult> ToPdf(HttpPostedFileBase file)
{
var converter = Doconut.DoconutHost.Services.GetRequiredService<DocumentConverter>();
Stream pdf = await converter.ConvertAsync(
file.InputStream, Path.GetExtension(file.FileName), ConversionTarget.Pdf,
password: null, ct: Response.ClientDisconnectedToken);
return File(pdf, "application/pdf", Path.GetFileNameWithoutExtension(file.FileName) + ".pdf");
}Web Forms で: 変換時にブロックしないでください
Web Forms ページはシングルスレッドのリクエストコンテキスト上で実行されます。ConvertAsync は完了時にそのコンテキストで再開されるため、同期的に待機するページ(.Result、.Wait()、.GetAwaiter().GetResult())は変換が完了するために必要なスレッド自体を占有します。リクエストは決して返ってきません。 ブラウザーは回転し続け、IIS は何も記録せず、サイトの残りは動作し続けるため、デッドロックではなく遅い変換のように見えます。
ページを Async="true" にマークし、変換をページの非同期タスクとして実行します:
<%@ Page Language="C#" Async="true" CodeBehind="Convert.aspx.cs" Inherits="MyApp.Convert" %>// Web Forms: @Page ディレクティブに Async=\"true\" が必要で、変換はページの非同期タスクとして実行されます。
// 代わりにブロックすると (.Result、.Wait()、.GetAwaiter().GetResult()) がリクエストをデッドロックします:
// 決して戻らず、何もログに記録されません。
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack) return;
RegisterAsyncTask(new PageAsyncTask(async ct =>
{
var converter = Doconut.DoconutHost.Services.GetRequiredService<DocumentConverter>();
using (var pdf = await converter.ConvertAsync(
Server.MapPath("~/App_Data/contract.docx"), ConversionTarget.Pdf, ct: ct))
using (var ms = new MemoryStream())
{
if (pdf.CanSeek) pdf.Position = 0;
await pdf.CopyToAsync(ms);
Response.ContentType = "application/pdf";
Response.AddHeader("Content-Disposition", "attachment; filename=contract.pdf");
Response.BinaryWrite(ms.ToArray());
// Context を使用し、HttpContext.Current ではなく: await の後、後者は null になる可能性があります。
Context.ApplicationInstance.CompleteRequest();
}
}));
}@Page ディレクティブに Async="true" がない場合、RegisterAsyncTask は黙って無視されます。await の後、ページの Context を使用してください; HttpContext.Current はそこで null できます。
対象フォーマット
Pdf, Docx, Doc, Html, Xlsx, Pptx, Png, Jpeg, Csv, Tiff, Bmp, Gif, Svg, Xml,
Txt, Xls, Jp2, Rtf, Odt, Ods, Odp, Epub, Xps, Webpすべてのソースがすべてのターゲットに変換できるわけではありません。各ソースのフォーマットファミリー(Word、Excel、PowerPoint、PDF、CAD、Image、Email、Diagram、Project、PSD、web document)には、許可されたターゲットの独自のセットがあります。この列挙型を UI のターゲットリストとしてハードコードしないでください:?convert=open はアップロードされたファイルの allowedTargets を返し、これがピッカーの駆動源となるべきです。
ドロップインウィジェット
ウィジェットの ?convert=open|run|download エンドポイントは DocImage.axd によって提供され、デフォルトではオフです。プラグイン登録の横でそれらを有効にしてください:
Doconut.DoconutHost.Initialize(options =>
{
options.LicensePath = HostingEnvironment.MapPath("~/wwwroot/Doconut.Viewer.lic");
options.AddPlugin<Doconut.Plugins.Converter.ConverterPlugin>();
options.AddConverterWidget(widget =>
{
widget.MaxUploadMb = 25;
});
});
// System.Web は Doconut が見る前にアップロード全体を読み取ります: maxRequestLength (KB) と
// Web.config の maxAllowedContentLength (bytes) を widget の MaxUploadMb の上に設定してください。<div id="doconut-convert"></div>
<script src="/doconut-res/js/doconutConverter.js"></script>
<script>
Doconut.convert('#doconut-convert', { basePath: '/DocImage.axd', maxUploadMb: 25 });
</script>ウィジェットが期待通りに動作しないときに確認すべき2つのこと:
basePath: '/DocImage.axd'。 ウィジェットのデフォルトである/doconutは ASP.NET Core エンドポイントです。このパッケージでは、エンドポイントはWeb.configのDocImage.axdハンドラです。- スクリプトとエンドポイントは独立しています。 リソースモジュールはウィジェットが有効かどうかに関わらず
doconutConverter.jsを提供します。AddConverterWidget()がない場合、ウィジェットはロードされ、ドロップゾーンが描画され、完全に正しく見えます — そして最初のアクションは404に応答します。
アップロード制限
ASP.NET は DocImage.axd が実行される前にリクエストボディ全体を読み取ります。MaxUploadMb を超え、ホストの制限未満のアップロードはウィジェット独自の JSON 413(「File is too large.」)を取得します。ホストの制限を超えるアップロードはまず IIS によって拒否され、ウィジェットが読み取れないエラーページが返されます。Web.config に両方のホスト制限を設定し、ウィジェットの上限より上に保ちます:
<system.web>
<httpRuntime maxRequestLength="30720" /> <!-- KILOBYTES: 30 MB -->
</system.web>
<system.webServer>
<security>
<requestFiltering>
<requestLimits maxAllowedContentLength="31457280" /> <!-- BYTES: 30 MB -->
</requestFiltering>
</security>
</system.webServer>ウィジェットのカスタマイズ
Doconut.convert(selector, options) に渡されるオプション:
| オプション | 型 | デフォルト | 備考 |
|---|---|---|---|
basePath | string | /doconut | エンドポイント URL。'/DocImage.axd' をこのパッケージで設定してください |
resPath | string | /doconut-res | 他の Doconut ウィジェットとの一貫性のために受け入れられます;コンバータウィジェットはそれから URL を構築しません |
maxUploadMb | number | 25 | クライアント側の事前チェックのみ;サーバーは独自の上限を強制します |
licenseUrl | string | null | null | 結果画面の透かし通知をリンクに変換します |
labels | object | {} | ウィジェットの英語文字列の任意のサブセットを上書きします |
コールバック:
| コールバック | 発火条件 | ペイロード |
|---|---|---|
onReady() | ウィジェットがドロップ画面をレンダリングしたとき | — |
onSourceLoaded({ token, pages, sourceExt, allowedTargets }) | ?convert=open が成功したとき | ソーストークン、ページ数、ソース拡張子(先頭のドットなし)、許可されたターゲット |
onConverted({ downloadToken, resultToken, resultPages, downloadName, watermarked, target }) | ?convert=run が成功したとき | 実行レスポンスと要求された target |
onDownload({ downloadName, downloadToken }) | ユーザーがダウンロードをクリックしたとき | ブラウザ自身のダウンロードと同時に発火 |
onError({ phase, message }) | 開くまたは実行リクエストが失敗したとき | phase は 'open' または 'run' です;message はサニタイズされたサーバーエラーです |
Doconut.convert() はウィジェットインスタンスを返します:reset() はドロップ画面に戻り、loadFile(file) は File でフローを開始し、destroy() はそれを削除します。
独自のフロントエンドを構築する
このウィジェットは DocImage.axd 上のこの HTTP 契約のクライアントです:
| ルート | 目的 | 成功レスポンス |
|---|---|---|
POST /DocImage.axd?convert=open (multipart, field file) | ソースドキュメントをアップロードして開く | 200 — { token, pages, sourceExt, allowedTargets } |
POST /DocImage.axd?token=<token>&convert=run&target=<ext> | アップロードされたソースを target に変換する | 200 — { downloadToken, resultToken, resultPages, downloadName, watermarked } |
GET /DocImage.axd?convert=download&token=<downloadToken> | 変換されたファイルをストリームする | 200 — ファイル、Content-Disposition: attachment |
アップロードされたソースは30分間保持されます;それ以降、run は 404 と答え、ファイルは再度開く必要があります。downloadToken は変換が完了したときに独自の30分間のウィンドウを取得します。resultToken はビューアーセッションの有効期間に従う通常のビューアートークンです。
open レスポンス内の sourceExt には先頭のドット("docx")がありません — ConvertAsync の sourceExtension パラメータの反対です。
| ルート | ステータス | 条件 | 本文 |
|---|---|---|---|
| any | 404 | ウィジェットが有効化されていません(AddConverterWidget() が呼び出されていません) | ステータスのみ |
| any | 405 | 誤った動詞(open/run は POST が必要、download は GET が必要) | ステータスのみ |
open | 413 | アップロードが MaxUploadMb を超えています(ただし IIS の制限は超えていません) | { "error": "File is too large." } |
open | 400 | マルチパートボディがなく、ファイルもなく、または変換できないタイプです | { "error": "..." } |
open | 403 | ファイルタイプはライセンスが付与していない機能を必要とします | { "error": "..." } |
run | 400 | 不正なトークン、未知の target、または allowedTargets に含まれないターゲット | { "error": "..." } |
run | 404 | アップロードが期限切れになったか、開かれませんでした | { "error": "Upload expired — please re-open the file." } |
open, run | 500 | 処理に失敗しました | { "error": "<sanitized message>" } |
download | 400 / 404 | 不正な、未知の、または期限切れのダウンロードトークン | ステータスのみ |
リソース所有権
呼び出し元は変換が返す MemoryStream の所有権を持ち、コピーまたは返却後に破棄すべきです(MVC の File(stream, …) が自動的に破棄します)。DocumentConverter を自分で構築したり破棄したりしないでください — そのコンストラクタは内部です。
ウォーターマーキング
| ライセンス状態 | 起動時 | 変換出力 |
|---|---|---|
Converter を付与する有料ビューアライセンス | 開始 | クリーン — watermarked: false |
| 有効な一時/デモライセンス | 開始 | 変換し、評価用ウォーターマーク — watermarked: true |
ライセンスなし、レガシー TRIAL ファイル、または Converter がないライセンス | Application_Start が例外を投げます;すべてのリクエストは空の 500 で応答します | — |
| 期限切れの一時/デモライセンス | 開始 | 変換し、評価用ウォーターマーク — watermarked: true |
統合は購入前に評価ライセンスでエンドツーエンドに構築・テストできます — 出力バイトだけが変わります。
トラブルシューティング
| 症状 | 確認項目 |
|---|---|
プラグイン追加後、すべてのリクエストが空の 500 で応答します | ライセンスは Converter を付与します — Windows イベントログ、ソースは ASP.NET |
DocumentConverter の解決で例外が発生します | AddPlugin<ConverterPlugin>() は DoconutHost.Initialize にあります |
| Web Forms の変換が決して戻りません | ページが ConvertAsync でブロックされます — Async="true" と RegisterAsyncTask を使用してください |
| ストリーム変換がフォーマット未対応と表示します | sourceExtension に先頭のドットが含まれています |
ウィジェットは読み込まれますが、リクエストは 404 を返します | AddConverterWidget() が呼び出されていないか、basePath が '/DocImage.axd' ではありません |
| 大きなアップロードがウィジェットのメッセージではなく IIS エラーページを表示します | maxRequestLength / maxAllowedContentLength が MaxUploadMb 以下です |
| ターゲットが見つかりません | convert=open から allowedTargets を使用してください |
| ダウンロードの期限が切れました | convert=open / convert=run を再試行してください;トークンは意図的に一時的です |
このページは役に立ちましたか?