MSBuild-Eigenschaften

Eigenschaften sind Name/Wert-Paare, die zur Konfiguration von Builds verwendet werden können. Sie sind hilfreich, um Werte an Aufgaben zu übergeben, Bedingungen auszuwerten und Werte zu speichern, auf die in der gesamten Projektdatei verwiesen wird.

Definieren von Eigenschaften und Verweisen auf Eigenschaften in einer Projektdatei

Eigenschaften werden deklariert, indem ein Element mit dem Namen der jeweiligen Eigenschaft als untergeordnetes Element eines PropertyGroup-Elements erstellt wird. Durch das folgende XML wird beispielsweise die Eigenschaft BuildDir mit dem Wert Build erstellt.

<PropertyGroup>
    <BuildDir>Build</BuildDir>
</PropertyGroup>

Gültige Eigenschaftsnamen beginnen mit einem Groß- oder Kleinbuchstaben oder Unterstrich (_). Gültige nachfolgende Zeichen umfassen alphanumerische Zeichen (Buchstaben oder Ziffern), Unterstrich und Bindestrich (-).

In der gesamten Projektdatei wird mit der Syntax $(<PropertyName>) auf Eigenschaften verwiesen. Beispielsweise wird mit $(BuildDir) auf die Eigenschaft im vorangehenden Beispiel verwiesen.

Eigenschaftswerte können durch Neudefinieren der Eigenschaft geändert werden. Der Wert der Eigenschaft BuildDir kann mit folgendem XML geändert werden:

<PropertyGroup>
    <BuildDir>Alternate</BuildDir>
</PropertyGroup>

Eigenschaften werden in der Reihenfolge ausgewertet, in der sie in der Projektdatei angezeigt werden. Der neue Wert für BuildDir muss deklariert werden, nachdem der alte Wert zugewiesen wurde.

Reservierte Eigenschaften

Einige Eigenschaftennamen werden von MSBuild reserviert, um Informationen zur Projektdatei und zu den Binärdateien von MSBuild zu speichern. Auf diese Eigenschaften wird wie auf jede andere Eigenschaft mit der $-Notation verwiesen. Beispielsweise gibt $(MSBuildProjectFile) den vollständigen Namen der Projektdatei einschließlich der Dateierweiterung zurück.

Weitere Informationen finden Sie unter Vorgehensweise: Verweisen auf den Namen oder Speicherort der Projektdatei und Reservierte und bekannte Eigenschaften für MSBuild.

Interne MSBuild-Eigenschaften

Eigenschaften, die in Standardimportdateien definiert sind und mit einem Unterstrich (_) beginnen, sind für MSBuild privat und dürfen im Benutzercode nicht gelesen, zurückgesetzt oder überschrieben werden.

Umgebungseigenschaften

Auf Umgebungsvariablen in Projektdateien kann auf die gleiche Weise verwiesen werden wie auf reservierte Eigenschaften. Um die PATH-Umgebungsvariable in der Projektdatei zu verwenden, verwenden Sie beispielsweise $(Path). Wenn das Projekt eine Eigenschaftendefinition enthält, die denselben Namen wie eine Umgebungseigenschaft hat, wird der Wert der Umgebungsvariablen von der Eigenschaft im Projekt überschrieben.

Jedes MSBuild-Projekt hat einen isolierten Umgebungsblock: Es sieht nur Lese- und Schreibvorgänge im eigenen Block. MSBuild liest Umgebungsvariablen nur, wenn die Eigenschaftenauflistung vor der Auswertung oder Erstellung der Projektdatei initialisiert wird. Danach sind Umgebungseigenschaften statisch, d. h jedes generierte Tool beginnt mit denselben Namen und Werten.

Verwenden Sie die Eigenschaftenfunktionen „System.Environment.GetEnvironmentVariable“, um den aktuellen Wert von Umgebungsvariablen aus einem generierten Tool abzurufen. Die bevorzugte Methode ist jedoch, den Aufgabenparameter EnvironmentVariables zu verwenden. Die Umgebungseigenschaften, die in diesem Zeichenfolgenarray festgelegt sind, können an das generierte Tool übergeben werden, ohne die Systemumgebungsvariablen zu beeinflussen.

Tipp

Nicht alle Umgebungsvariablen werden gelesen, um sie zu anfänglichen Eigenschaften zu machen. Jede Umgebungsvariable, deren Name kein gültiger MSBuild-Eigenschaftenname ist (z.B. "386"), wird ignoriert.

Weitere Informationen finden Sie unter Vorgehensweise: Verwenden von Umgebungsvariablen in einem Build.

Registrierungseigenschaften

Systemregistrierungswerte können mit der nachfolgend angegebenen Syntax gelesen werden. Dabei steht Hive für den Registrierungshive (z.B. HKEY_LOCAL_MACHINE), MyKey steht für den Schlüsselnamen, MySubKey für den Unterschlüsselnamen, und Value ist der Wert des Unterschlüssels.

$(registry:Hive\MyKey\MySubKey@Value)

Lassen Sie Value weg, um den Standardunterschlüsselwert abzurufen.

$(registry:Hive\MyKey\MySubKey)

Mit diesem Registrierungswert kann eine Buildeigenschaft initialisiert werden. Beispielsweise können Sie mit dem folgenden Code eine Buildeigenschaft erstellen, die die Webbrowser-Homepage für Visual Studio darstellt:

<PropertyGroup>
  <VisualStudioWebBrowserHomePage>
    $(registry:HKEY_CURRENT_USER\Software\Microsoft\VisualStudio\14.0\WebBrowser@HomePage)
  </VisualStudioWebBrowserHomePage>
<PropertyGroup>

Warnung

In der .NET SDK-Version von MSBuild (dotnet build) werden Registrierungseigenschaften nicht unterstützt.

Erstellen von Eigenschaften während der Ausführung

Eigenschaften außerhalb von Target-Elementen werden die Werte im Rahmen der Auswertungsphase eines Builds zugewiesen. Während der anschließenden Ausführungsphase können die Eigenschaften erstellt oder geändert werden, wie nachfolgend veranschaulicht:

  • Eigenschaften können von einer beliebigen Aufgabe ausgegeben werden. Das Task-Element muss über ein untergeordnetes Output-Element mit einem PropertyName-Attribut verfügen, um eine Eigenschaft auszugeben.

  • Eigenschaften lassen sich mithilfe der CreateProperty-Aufgabe ausgeben. Diese Verwendung ist veraltet.

  • In Target-Elementen können PropertyGroup-Elemente enthalten sein, die Eigenschaftendeklarationen enthalten können.

Globale Eigenschaften

Mit MSBuild können Sie die Eigenschaften in der Befehlszeile mithilfe des Schalters -property (oder -p) festlegen. Diese globalen Eigenschaftswerte überschreiben Eigenschaftswerte, die in der Projektdatei festgelegt werden. Dies betrifft auch Umgebungseigenschaften, nicht jedoch reservierte Eigenschaften ein, die nicht geändert werden können.

Im folgenden Beispiel wird die globale Configuration-Eigenschaft auf DEBUG festgelegt.

msbuild.exe MyProj.proj -p:Configuration=DEBUG

Globale Eigenschaften können auch für untergeordnete Projekte in einem Build mit mehreren Projekten festgelegt oder geändert werden, indem das Properties-Attribut der MSBuild-Aufgabe verwendet wird. Globale Eigenschaften werden auch an untergeordnete Projekte weitergeleitet, es sei denn, das RemoveProperties-Attribut des MSBuild-Tasks wird dafür verwendet, eine Liste von Eigenschaften anzugeben, die nicht weitergeleitet werden sollen. Weitere Informationen finden Sie unter MSBuild-Aufgabe.

Lokale Eigenschaften

Lokale Eigenschaften können in einem Projekt zurückgesetzt werden, globale Eigenschaften hingegen nicht. Wenn eine lokale Eigenschaft über die Befehlszeile mit der Option -p festgelegt wird, hat die Einstellung in der Projektdatei Vorrang vor der Befehlszeile.

Sie geben eine lokale Eigenschaft an, indem Sie das TreatAsLocalProperty-Attribut in einem Projekttag verwenden.

Der folgende Code gibt an, dass zwei Eigenschaften lokal sind:

<Project Sdk="Microsoft.Net.Sdk" TreatAsLocalProperty="Prop1;Prop2">

Lokale Eigenschaften werden in einem Build mit mehreren Projekten nicht an untergeordnete Projekte übergeben. Wenn Sie an der Befehlszeile einen Wert mit der Option -p angeben, erhalten untergeordnete Projekte den Wert der globalen Eigenschaft anstelle des lokalen Werts, der im übergeordneten Projekt geändert wurde. Untergeordnete Projekt (oder Importe) können ihn aber mit einer eigenen TreatAsLocalPropertyändern.

Beispiel mit lokalen Eigenschaften

Das folgende Codebeispiel veranschaulicht die Auswirkungen von TreatAsLocalProperty:

<!-- test1.proj -->
<Project TreatAsLocalProperty="TreatedAsLocalProp">
    <PropertyGroup>
        <TreatedAsLocalProp>LocalOverrideValue</TreatedAsLocalProp>
    </PropertyGroup>

    <Target Name="Go">
        <MSBuild Projects="$(MSBuildThisFileDirectory)\test2.proj" Targets="Go2" Properties="Inner=true" />
    </Target>

    <Target Name="Go2" BeforeTargets="Go">
        <Warning Text="TreatedAsLocalProp($(MSBuildThisFileName)): $(TreatedAsLocalProp)" />
    </Target>
</Project>
<!-- test2.proj -->
<Project TreatAsLocalProperty="TreatedAsLocalProp">
    <Target Name="Go2">
        <Warning Text="TreatedAsLocalProp($(MSBuildThisFileName)): $(TreatedAsLocalProp)" />
    </Target>
</Project>

Angenommen, Sie erstellen test1.proj an der Befehlszeile und weisen TreatedAsLocalProperty den globalen Wert GlobalOverrideValue zu:

dotnet msbuild .\test1.proj -p:TreatedAsLocalProp=GlobalOverrideValue

Die Ausgabe lautet wie folgt:

test1.proj(11,9): warning : TreatedAsLocalProp(test): LocalOverrideValue
test2.proj(3,9): warning : TreatedAsLocalProp(test2): GlobalOverrideValue

Das untergeordnete Projekt erbt den globalen Wert, aber das übergeordnete Projekt verwendet die lokal festgelegte Eigenschaft.

Lokale Eigenschaften und Importe

Wenn das TreatAsLocalProperty-Attribut für ein importiertes Projekt verwendet wird, legt die Reihenfolge fest, welchen Wert die Eigenschaft erhält.

Das folgende Codebeispiel zeigt die Auswirkungen von TreatAsLocalProperty auf ein importiertes Projekt:

<!-- importer.proj -->
<Project>
    <PropertyGroup>
        <TreatedAsLocalProp>FirstOverrideValue</TreatedAsLocalProp>
    </PropertyGroup>

    <Import Project="import.props" />

    <PropertyGroup>
        <TreatedAsLocalProp Condition=" '$(TrySecondOverride)' == 'true' ">SecondOverrideValue</TreatedAsLocalProp>
    </PropertyGroup>

    <Target Name="Go">
        <Warning Text="TreatedAsLocalProp($(MSBuildThisFileName)): $(TreatedAsLocalProp)" />
    </Target>
</Project>
<!-- import.proj -->
<Project TreatAsLocalProperty="TreatedAsLocalProp">
    <PropertyGroup>
        <TreatedAsLocalProp>ImportOverrideValue</TreatedAsLocalProp>
    </PropertyGroup>

    <!-- Here, TreatedAsLocalProp has the value "ImportOverrideValue"-->
</Project>

Angenommen, Sie erstellen importer.proj und legen für TreatedAsLocalProp wie folgt einen globalen Wert fest:

dotnet msbuild .\importer.proj -p:TreatedAsLocalProp=GlobalOverrideValue

Die Ausgabe lautet:

importer.proj(9,9): warning : TreatedAsLocalProp(importer.proj): GlobalOverrideValue

Angenommen, Sie erstellen einen Build, bei dem die Eigenschaft TrySecondOverride auf true festgelegt ist:

dotnet msbuild .\importer.proj -p:TreatedAsLocalProp=GlobalOverrideValue -p:TrySecondOverride=true

Die Ausgabe lautet:

importer.proj(13,9): warning : TreatedAsLocalProp(importer.proj): SecondOverrideValue

Das Beispiel zeigt, dass die Eigenschaft nach dem importierten Projekt, in dem das TreatAsLocalProperty-Attribut verwendet wurde, als lokal behandelt wird und nicht nur innerhalb der importierten Datei. Der Wert der Eigenschaft wird durch den global außer Kraft gesetzten Wert beeinflusst, aber nur vor dem importierten Projekt, in dem TreatAsLocalProperty verwendet wird.

Weitere Informationen finden Sie unter Project-Element (MSBuild) und Vorgehensweise: Erstellen identischer Quelldateien mit unterschiedlichen Optionen.

Eigenschaftenfunktionen

Ab .NET Framework Version 4 können Sie Eigenschaftenfunktionen verwenden, um MSBuild-Skripts auszuwerten. Sie können die Systemzeit lesen, Zeichenfolgen vergleichen, reguläre Ausdrücke abgleichen und viele weitere Aktionen ohne MSBuild-Aufgaben im Buildskript ausführen.

Sie können Zeichenfolgen-(Instanz-)Methoden für beliebige Eigenschaftswerte verwenden, und Sie können die statischen Methoden für zahlreiche Systemklassen aufrufen. Beispielsweise können Sie so eine Buildeigenschaft auf das heutige Datum festlegen:

<Today>$([System.DateTime]::Now.ToString("yyyy.MM.dd"))</Today>

Weitere Informationen sowie eine Liste der verfügbaren Eigenschaftenfunktionen finden Sie unter Eigenschaftenfunktionen.

Speichern von XML in Eigenschaften

Eigenschaften können beliebigen XML-Code enthalten, um die Übergabe von Werten an Aufgaben oder das Anzeigen von Protokollierungsinformationen zu unterstützen. Im folgenden Beispiel wird die ConfigTemplate-Eigenschaft veranschaulicht, die über einen Wert verfügt, der XML- und andere Eigenschaftenverweise enthält. MSBuild ersetzt die Eigenschaftenverweise durch ihre jeweiligen Eigenschaftswerte. Eigenschaftswerte werden in der Reihenfolge zugewiesen, in der sie angezeigt werden. $(MySupportedVersion), $(MyRequiredVersion) und $(MySafeMode) sollten in diesem Beispiel daher bereits definiert worden sein.

<PropertyGroup>
    <ConfigTemplate>
        <Configuration>
            <Startup>
                <SupportedRuntime
                    ImageVersion="$(MySupportedVersion)"
                    Version="$(MySupportedVersion)"/>
                <RequiredRuntime
                    ImageVersion="$(MyRequiredVersion)"
                    Version="$(MyRequiredVersion)"
                    SafeMode="$(MySafeMode)"/>
            </Startup>
        </Configuration>
    </ConfigTemplate>
</PropertyGroup>