Apache Ant™ タスク設計ガイドライン

このドキュメントでは、Antディストリビューションに組み込むために必要な標準に準拠したApache Antタスクの記述方法について説明します。個人的な使用のためのタスクを記述する場合でも、ここで取り上げる問題は同様であるため、役立つでしょう。

既存のビルドを壊さないでください

たとえAntに非常に深刻な問題が見つかり、簡単に修正できるとしても、その修正によって既存のビルドファイルが壊れてしまうと問題が発生します。すべてのビルドファイルが引き続き動作することを保証することは、すべての変更の目標の1つです。例として、Ant 1.5は単一のドル記号「$」を文字列でそのまま渡しますが、Ant 1.4以前はそれを削除していました。この修正を行うために、まず現在の動作を明らかにするテストスイートを作成し、次に単一の「$」がそのまま渡されるように変更を加えましたが、下位互換性のために二重の「$$」は「$」にマップされるようにしました。

Java APIを壊さないでください

Antのタスクは、サードパーティのプログラムやタスクで使用できます。APIを壊すような変更はできません。これには以下が含まれます。
  1. 下位互換性のあるファサードを残さずにクラスを移動すること。
  2. クラスを削除すること。
  3. メソッドまたはフィールドを削除すること、またはそれらのアクセス可能性を低下させること。
  4. 以下のシグネチャを変更することsetAttribute(Type)メソッド。制限的な型を追加する必要がある場合は、新しい属性を追加し、元の属性の*上*のソースに配置します。XMLマッパーは制限された型を取得し、古いプログラムは引き続き古い型を使用できます。
  5. セマンティクスを変更しないでください。少なくとも、大幅に変更しないでください。結局のところ、すべてのバグ修正は暗黙的なセマンティクスの変更です。

組み込みのヘルパークラスを使用してください

Antには、作業の大部分を簡素化するヘルパーツァークが含まれています。開発、保守、コードサイズの理由から、独自のヘルパーツァークを作成するよりも、これらを使用する方がはるかに優れています。

Execute

Executeは、Antがサポートするすべてのプラットフォームで個別のプログラムを生成し、プラットフォームの問題だけでなくJavaバージョンの問題も処理します。他のプログラムを呼び出すには、常にこのクラスを使用してください。

Java, ExecuteJava

これらのクラスは、別のVMで(Executeを使用)、または同じVMで(異なるクラスローダーの有無にかかわらず)Javaプログラムを生成するために使用できます。これからタスクを派生させる場合、多くの場合、クラスパスを指定できるようにし、フォークをオプションの属性にすることでユーザーにメリットがあります。

Projectと関連クラス

Project、FileUtils、JavaEnvUtilsはすべて、ファイルに触れたり、ファイルをコピーしたりするなどのヘルパー関数を提供しています。これらを自分でコーディングしたり、安定性が低く使いにくいタスクを使用したりする代わりに、これらを使用してください。

Sun/Javaスタイルガイドラインに従ってください

Antコードベースは、単一の統一されたコーディング標準を持つことを目指しており、その標準は Sun Javaコーディングガイドライン です。

それが他の選択肢よりも優れているというわけではありませんが、それは標準であり、他のタスクで一貫して使用されているものです。コードは、これらに準拠するまでデータベースに組み込まれません。

個人的または組織的な使用のためにタスクを記述する場合は、好きなスタイルを使用できます。ただし、Sun Javaスタイルを使用すると、Antソースの残りの部分に慣れるのに役立ちます。これは重要かもしれません。

重要なルールの1つは「タブなし」です。代わりに4つのスペースを使用してください。2つでも8つでもなく、4つです。エディターがタブを4つのスペースに設定していても、他の多くのエディターはそうではありません。スペースは、エディターやプラットフォーム間でより一貫性があります。一部のIDE(JEdit)は、タブを誤って挿入しないように、タブを強調表示できます。

メインのantディレクトリには、Antのソースコードに対してcheckstyleを実行するAntビルドファイルcheck.xmlがあります。

属性と要素

すべての属性をsetFoo(String)として実装し、int、boolean、またはFileへのマッピングを自分で行うのではなく、属性をJavaデータ型にマッピングするAntイントロスペクションベースのマッピングを使用してください。これにより、作業が軽減され、Javaの呼び出し元がタイプセーフな方法で使用できるようになり、Xdocsドキュメントジェネレーターがパラメーターを把握できるようになります。

Ant 1.xタスクは、属性の命名に関して非常に一貫性がありません。一部のタスクはsourceを使用し、他のタスクはsrcを使用します。推奨される属性名の一覧を以下に示します。

failonerror 実行の失敗時にBuildExceptionをスローするか、エラーを出力するだけかを制御するブール値。パラメーター検証の失敗は、このフラグに関係なく、常にエラーをスローする必要があります。
destdir 出力先のディレクトリ
destfile 出力先のファイル
srcdir ソースディレクトリ
srcfile ソースファイル

はい、これは非常に短いリストです。少なくとも、コアタスクと漠漠と一貫性を保つようにしてください。

クラスパスをサポートする

外部ライブラリが必要な場合は、すべてをANT_HOME/libディレクトリに追加するのではなく、タスクにクラスパスを提供できるようにしてください。これにより、すべてのユーザーがAntシステム構成を変更することを強制するのではなく、Antベースのプロジェクトに外部ライブラリを保持できます。

制御された再利用のための設計

メンバー変数はプライベートにしてください。サブクラスによる読み取りアクセスが必要な場合は、メンバーのアクセス可能性を変更するのではなく、アクセサーメソッドを追加します。これにより、サブクラスはコンテンツにアクセスできますが、実際の実装からは切り離されたままになります。

Antにおけるもう1つの一般的な再利用メカニズムは、あるタスクが別のタスクを作成および設定することです。これはかなり簡単です。AntのAPIには、タスクを( "java"、 "exec"などの)使い慣れた名前でインスタンス化するための機能があります。ユーザーが名前を完全に別のクラスを指すようにオーバーライドする可能性が非常に高いため、このアプローチを使用*しない*ことをお勧めします。サブタスクをインスタンス化するには、直接コンストラクター呼び出し(またはリフレクション)を使用します。 Ant 1.6.3以降、 `org.apache.tools.ant.Task#bindToOwner()`を呼び出して、ヘルパーツァスクを親として「マスク」できます。

独自の依存関係チェックを実行する

makeは、統合された依存関係チェックにおいてAntよりも優れています。コマンドラインアプリmakeの呼び出しは、独自の作業を行う必要はありません。Antタスクは独自の依存関係作業を行う必要がありますが、これができるのであれば、うまく実行できます。優れた依存関係対応タスクは、ビルドファイルに明示的な依存関係情報がなくても依存関係を把握でき、ファイルの解析などを通じて実際の依存関係を把握するのに十分スマートです。dependsタスクは、この最良の例です。 zip/jarタスクの一部も非常に優れており、必要に応じてアーカイブを更新できます。ほとんどのタスクは、ソースとデスティネーションのタイムスタンプを比較して、そこから作業を行います。依存関係チェックを行わないタスクは、ユーザーにできる限りの segítséget 提供しません。なぜなら、不要な作業がビルド、テスト、デプロイの seluruh プロセスに波及する可能性があるからです。

適切なJavaバージョンをサポートする

Ant 1.5以前はJava 1.1をサポートするように設計されていました。 Ant 1.6以降は、Java 1.2をサポートするように設計されています。それをビルドし、実行するためです。 Ant 1.8にはJava 1.4が必要で、1.9には1.5( "JDK 5")が必要です。タスクの機能は、古い環境または新しい環境では低下する場合があります。通常はライブラリの制限が原因です。このような動作の変更は、ドキュメントに必ず記載する必要があります。

問題となるのは、現在のベースラインよりも新しいバージョンのJavaの機能に依存するコードです。たとえば、JDK 7のjava.nio.file.Pathなどです。古いクラスに追加されたメソッドにも注意してください。これらは古いシステムでコンパイルして実行できるようにするために、コードで直接使用することはできません。既存のクラスの新しいメソッドを使用する場合は、リフレクションを介して使用し、NoSuchMethodExceptionを何らかの方法で処理する必要があります。

古いバージョンのJavaでコードが einfach に動作しない場合はどうなりますか? それは起こり得ます。 build.xmlの変更によって、新しいJDK(以降)にコンパイルが制限されたオプションのタスクとしてタスクを持つことはおそらく問題ありません。さらに良いのは、リフレクションを使用して実行時にクラスにリンクすることです。

同様の考慮事項は、JDK 7の文字列switch文などの新しい言語機能にも適用されます。

ネストされたテキストのプロパティを明示的に展開する

歴史的な理由から、addText(String text)は、プロパティの展開が行われずに、タスクのネストされたテキストを設定するために呼び出されます。Project.replaceProperties()を呼び出して、手動でこれを実行します。忘れると、ユーザーのビルドファイルを壊さずに修正できない問題が発生します。

リファクタリング

タスクに加えられた変更によって扱いにくくなっている場合は、よりクリーンな設計に分割し、コードをリファクタリングし、機能の追加だけでなく、よりクリーンなタスクを送信してください。 Antプロセスで発生する傾向のある一般的な設計パターンは、アダプターパターンの採用です。このパターンでは、基本クラス(たとえばJavacまたはRmic)が単純に開始され、次に複数のバックエンド(javac、jikes、jvc)のサポートによって複雑になります。プログラム可能なフロントエンドとバックエンドを提供するクラスを分離するようにリファクタリングすると、設計がクリーンアップされ、新しいバックエンドの追加がはるかに容易になります。ただし、これを実行するには、フロントエンドのインターフェースと動作を同一に保ち、サブクラスがデータメンバーに直接アクセスしていないことを確認する必要があります。これらのデータメンバーは、リファクタリングされた設計には存在しない可能性があるためです。これが、プライベートデータメンバーを持つことが非常に重要である理由です。

してはいけないことの1つは、既存のタスクを移動したり削除したりすることです。 Antには、XML言語だけでなくJava APIもあることに注意してください。そのAPI、または既存のAntタスクをサブクラス化するものを壊したくありません。リファクタリングを行う場合は、元のクラスがあった場所にファサードを残す必要があります。そのため、既存のコードは壊れません。

テスト

以下をご覧くださいant/src/testcasesすると、付属のAntタスクのJUnitテストが見つかります。これにより、どのように行われるか、新しいタスクに何が期待されるかを確認できます。それらのほとんどは初歩的なものであり、間違いなくタスクを改善できます。自由にそうしてください!

適切に記述された一連のテストケースは、コードが実際に完成するまで、開発中のAntタスクを中断します。また、後で発生するすべてのバグには、問題を実証し、修正するためのテストケースを追加する必要があります。

テストケースは、開発中にタスクをテストするための優れた方法です。antソースツリーで 'build run-test' を呼び出すだけで、すべてのantテストが実行され、変更によって何も壊れていないことが確認されます。単一のタスクをテストするには、ワンショットの ant run-single-test -Dtestcase=${testname} を使用します。ここで、${testname} はテストクラスの名前です。

テストケースは、コミッターが変更やパッチが意図したとおりに動作することを確認するためにも使用されます。テストケースがあれば、信頼性が大幅に向上します。正確に言うと、テストケースのない提出物は嫌われます。なぜなら、私たち自身がテストケースを書かなければならないからです。これは、私たちがそのタスクを必要とする場合、または多くのユーザーにとって非常に重要であると認識される場合にのみ行われます。

また、Ant 1.xはJava 1.2でコンパイルおよび実行するように設計されているため、使用するJava 1.2以降のバージョンでもテストする必要があります。この目的のために、Sunから古いSDKをダウンロードできるはずです。

最後に、プロジェクトの開発を開始する前後に、完全な build test を実行して、誤って他のものを壊していないことを確認してください。

ドキュメント

ドキュメントがないと、タスクを使用できません。そのため、既存のタスクと同様のスタイルでタスクを説明する簡潔で明確なhtml(まもなくxml)ページを提供することを忘れないでください。属性と要素のリスト、およびタスクの少なくとも1つの実例を含める必要があります。多くのユーザーは、例をビルドファイルにコピーして貼り付けて開始点として使用するため、例を実用的にしてテストしてください。

proposal/xdocsにあるxdocsのものを使用して、ソースのjavadocからドキュメントページを自動生成できます。これにより、作業が楽になり、完全なxdoclet生成ドキュメントビルドプロセスへの移行が容易になります。

ライセンスと著作権

Apacheプロジェクトに提出されるコードは、Apacheライセンスと互換性がある必要があり、提出行為は、提出されたコードのApache Software Foundationへの暗黙のライセンスと見なされる必要があります。

これは重要です。

Apacheのかなり自由放任なライセンスは、現在、Free Software Foundation(Gnuプロジェクト)のGPLまたはLesser GPLのいずれとも互換性がないと見なされています。これらのライセンスには、Apacheライセンスにはない、より厳格な条項「コピーレフト」があります。これにより、個人や組織は、Apacheライブラリとソースの上に商用およびクローズドソースアプリケーションを構築できます。

Gnu GPLライセンスは、組み込まれたより大きなアプリケーション(またはLGPLの場合はライブラリ)をすぐにカバーするように拡張されるため、AntチームはGPLまたはLGPLソースに基づくタスクをAntコードベースに組み込むことができません。自由に提出することはできますが、丁寧かつ断固として拒否されます。

importまたはリフレクションによってGPLまたはLGPLライブラリにリンクする場合、タスクは同じ条件でライセンスされる必要があります。そのため、(L)GPLコードにリンクするタスクは、Apacheが管理するコードベースに含めることができません。このようなコードを呼び出すタスクは、「exec」または「java」タスクを使用してプログラムを実行できます。この時点では、プログラムにリンクするのではなく、実行しているだけです。

タスクをApacheコードベースに含めることができない場合でも、ホストされている場所を指すことはできます。タスクを指すxdocs/external.htmlへの差分を提出してください。

タスクが独自コードに直接リンクしている場合、別の問題があります。タスクを構築するのが非常に難しいことです。リフレクションを使用してください。

車輪の再発明はしないでください

私たちは皆それをしました:タスクを記述して提出したところ、それが別のタスクの小さな隅にすでに実装されていること、または他の誰かによって提出されてコミットされていないことがわかりました。最新のCVSツリーの内容を把握することで、これを回避できます。毎日のソースアップデートを取得し、手動の変更を確認し、開発メーリングリストに登録してください。

タスクの作成を検討している場合は、リストに自分の考えをメモとして投稿すると有益な場合があります。他の人の洞察や、基本的な作業を行うための半分書かれたタスクなどが得られます。すべてコードを1行も書かずに。

Antへの提出

Antタスクを提出するための基本的なメカニズムは、それを開発メーリングリストにメールで送信することです。このリストに載っていると、他の提出物や、自分の提出物に関する議論を見ることができるので便利です。

次のいずれかのアプローチを使用してパッチファイルを作成できます(コミッターは最初のアプローチを推奨しています)

パッチは、[PATCH]というタイトルのメッセージの添付ファイルとして、パッチの件名に特徴的な1行の概要を付けて送信する必要があります。通常、ファイル名/タスクと変更で十分です。変更を添付ファイルとして含めることが重要です。これは、多くのメーラーが貼り付けられたテキストの書式を再設定するため、パッチが壊れるためです。

その後、コミッターの1人がパッチをコミットするのを待ちます(適切と判断された場合)。バグ修正はすぐに適用されますが、他の変更は、(おそらく改訂された)コミットが行われる前に、少し議論を引き起こすことがよくあります。

新しい提出物は[SUBMIT]の前に付ける必要があります。メーラーデーモンは100KBを超えるメッセージを拒否するため、大きな更新はすべてzip圧縮する必要があります。提出物がそれより大きい場合は、 separate tasksに分割してください。

また、提出物をbugzillaに追加することをお勧めします。そうすれば、紛失することはありません。最初に意味のある名前でレポートを提出してから、ファイルを添付ファイルとして追加することで、提出してください。CVS diffファイルを使用してください!

数週間経っても何も聞こえない場合は、メーリングリストに通知してください。本当に良い提出物が他の問題のノイズに埋もれてしまうことがあります。これは、製品の新しいポイントリリースの直前に特に当てはまります。その時点で、バグ修正以外のものは無視される傾向があります。

チェックリスト

これらは、パッチと新しいタスクを提出する前に確認する必要があるものです。物事は完璧である必要はありません。パッチまたは提出物がコミットされるまでに数回の反復が必要になる場合があり、これらの項目はそのプロセスで対処できます。ただし、コードがコミットされるまでに、ドキュメントといくつかのテストケースを含むすべてが完了しているため、事前に邪魔にならないようにすることで時間を節約できます。コミッターは、テストケースを含むパッチと提出物をより好意的に見て、ドキュメントはタスクの理由を説明するのに役立ちます。

パッチを提出する前のチェックリスト

新しいタスクを提出する前のチェックリスト