-
Notifications
You must be signed in to change notification settings - Fork 32
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[macios] Add
@(XcodeProjectReference)
Introduces a new `@(XcodeProjectReference)` item to help simplify the content that needs to be added to the binding .csproj file. This item will translate relevant metadata to the `@(NativeReference)` item that is automatically added to the project after the xcode project is built. Build task wrappers for `xcodebuild` and `sharpie` have been added to improve msbuild output and error logging when a tool invocation fails.
- Loading branch information
Showing
11 changed files
with
309 additions
and
170 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -403,6 +403,7 @@ FodyWeavers.xsd | |
|
||
xcuserdata/ | ||
|
||
build/ | ||
.build/ | ||
*.xcframework | ||
Pods/ | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,94 +1,118 @@ | ||
<Project> | ||
|
||
<PropertyGroup> | ||
<Configuration Condition=" '$(Configuration)' == '' ">Release</Configuration> | ||
|
||
<XcodeDefaultBuildDir>.build</XcodeDefaultBuildDir> | ||
<XcodeBuildDirName Condition=" '$(XcodeBuildDirName)' == '' ">$(XcodeDefaultBuildDir)</XcodeBuildDirName> | ||
|
||
<_XcodeProjectFullPath>$([System.IO.Path]::GetFullPath($(XcodeProject)))</_XcodeProjectFullPath> | ||
|
||
<XcodeScheme Condition=" '$(XcodeScheme)' == '' ">$([System.IO.Path]::GetFilenameWithoutExtension($(XcodeProject)))</XcodeScheme> | ||
|
||
<XcodeProjectDir Condition=" '$(XcodeProjectDir)' == '' ">$([System.IO.Path]::GetDirectoryName($(_XcodeProjectFullPath)))</XcodeProjectDir> | ||
<XcodeBuildDir Condition=" '$(XcodeBuildDir)' == '' ">$([System.IO.Path]::Combine($(XcodeProjectDir), $(XcodeBuildDirName)))</XcodeBuildDir> | ||
|
||
<XcodeBuildXCFramework Condition=" '$(XcodeBuildXCFramework)' == '' ">True</XcodeBuildXCFramework> | ||
|
||
<XcodeBuildiOS Condition=" '$(XcodeBuildiOS)' == '' ">True</XcodeBuildiOS> | ||
<XcodeBuildiOSSimulator Condition=" '$(XcodeBuildiOSSimulator)' == '' ">True</XcodeBuildiOSSimulator> | ||
<XcodeBuildMacCatalyst Condition=" '$(XcodeBuildMacCatalyst)' == '' ">True</XcodeBuildMacCatalyst> | ||
|
||
<_XcodeBuildDirFullPath>$([System.IO.Path]::GetFullPath($(XcodeBuildDir)))</_XcodeBuildDirFullPath> | ||
<_XcodeProjectDirFullPath>$([System.IO.Path]::GetFullPath($(XcodeProjectDir)))</_XcodeProjectDirFullPath> | ||
|
||
<_XcArchiveiOSFullPath>$([System.IO.Path]::Combine($(_XcodeBuildDirFullPath), $(XcodeScheme)-ios.xcarchive))</_XcArchiveiOSFullPath> | ||
<_XcArchiveiOSSimulatorFullPath>$([System.IO.Path]::Combine($(_XcodeBuildDirFullPath), $(XcodeScheme)-iossimulator.xcarchive))</_XcArchiveiOSSimulatorFullPath> | ||
<_XcArchiveMacCatalystFullPath>$([System.IO.Path]::Combine($(_XcodeBuildDirFullPath), $(XcodeScheme)-maccatalyst.xcarchive))</_XcArchiveMacCatalystFullPath> | ||
<_XcArchiveExtraArgs>ENABLE_BITCODE=NO SKIP_INSTALL=NO SWIFT_INSTALL_OBJC_HEADER=YES BUILD_LIBRARY_FOR_DISTRIBUTION=YES OTHER_LDFLAGS='-ObjC' OTHER_SWIFT_FLAGS='-no-verify-emitted-module-interface' OBJC_CFLAGS='-fno-objc-msgsend-selector-stubs -ObjC'</_XcArchiveExtraArgs> | ||
|
||
<_XcFrameworkFullPath>$([System.IO.Path]::Combine($(_XcodeBuildDirFullPath), $(XcodeScheme).xcframework))</_XcFrameworkFullPath> | ||
</PropertyGroup> | ||
|
||
<ItemGroup> | ||
<_XcodeProjectInputs Include="$(_XcodeProjectDirFullPath)/**/*.swift" Exclude="$(_XcodeBuildDirFullPath)/**" /> | ||
<_XcodeProjectInputs Include="$(_XcodeProjectDirFullPath)/**/*.h" Exclude="$(_XcodeBuildDirFullPath)/**" /> | ||
<_XcodeProjectInputs Include="$(_XcodeProjectFullPath)/*.pbxproj" /> | ||
<_XcodeProjectInputs Include="$(_XcodeProjectFullPath)/*.xcworkspace" /> | ||
</ItemGroup> | ||
|
||
<PropertyGroup Condition="$(TargetFramework.Contains('ios')) Or $(TargetFramework.Contains('maccatalyst'))"> | ||
<_GenerateBindingsDependsOn> | ||
BuildXCFramework; | ||
ObjSharpieBind; | ||
$(_GenerateBindingsDependsOn); | ||
</_GenerateBindingsDependsOn> | ||
</PropertyGroup> | ||
|
||
<Target Name="BuildXCFramework" | ||
Condition=" '$(XcodeBuildXCFramework)' == 'true' " | ||
DependsOnTargets="$(BuildXCFrameworkDependsOnTargets)" | ||
Inputs="@(_XcodeProjectInputs)" | ||
Outputs="$(_XcFrameworkFullPath)/Info.plist"> | ||
<Error Condition=" !Exists('$(_XcodeProjectFullPath)') " Text="Xcode project '$(_XcodeProjectFullPath)' not found." /> | ||
|
||
<Exec Condition=" '$(XcodeBuildiOS)' == 'True' " Command="xcodebuild -project $(_XcodeProjectFullPath) archive -scheme $(XcodeScheme) -configuration $(Configuration) -archivePath $(_XcArchiveiOSFullPath) -destination 'generic/platform=iOS' $(_XcArchiveExtraArgs)" /> | ||
<Exec Condition=" '$(XcodeBuildiOSSimulator)' == 'True' " Command="xcodebuild -project $(_XcodeProjectFullPath) archive -scheme $(XcodeScheme) -configuration $(Configuration) -archivePath $(_XcArchiveiOSSimulatorFullPath) -destination 'generic/platform=iOS Simulator' $(_XcArchiveExtraArgs)" /> | ||
<Exec Condition=" '$(XcodeBuildMacCatalyst)' == 'True' " Command="xcodebuild -project $(_XcodeProjectFullPath) archive -scheme $(XcodeScheme) -configuration $(Configuration) -archivePath $(_XcArchiveMacCatalystFullPath) -destination 'generic/platform=macOS,variant=Mac Catalyst' $(_XcArchiveExtraArgs)" /> | ||
|
||
<ItemGroup> | ||
<_CreateXcFxArgs Include="-create-xcframework" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildiOS)' == 'True' " Include="-archive $(_XcArchiveiOSFullPath) -framework $(XcodeScheme).framework" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildiOSSimulator)' == 'True' " Include="-archive $(_XcArchiveiOSSimulatorFullPath) -framework $(XcodeScheme).framework" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildMacCatalyst)' == 'True' " Include="-archive $(_XcArchiveMacCatalystFullPath) -framework $(XcodeScheme).framework" /> | ||
<_CreateXcFxArgs Include="-output $(_XcFrameworkFullPath)" /> | ||
</ItemGroup> | ||
|
||
<RemoveDir Directories="$(_XcFrameworkFullPath)" /> | ||
<Exec Command="xcodebuild @(_CreateXcFxArgs, ' ')" /> | ||
</Target> | ||
|
||
<PropertyGroup> | ||
<ObjSharpieBind Condition=" '$(ObjSharpieBind)' == '' ">True</ObjSharpieBind> | ||
<ObjSharpieBindOutputDir Condition=" '$(ObjSharpieBindOutputDir)' == '' ">$(_XcodeBuildDirFullPath)/Binding</ObjSharpieBindOutputDir> | ||
<ObjSharpieSourceHeader>$(_XcArchiveiOSFullPath)/Products/Library/Frameworks/$(XcodeScheme).framework/Headers/$(XcodeScheme)-Swift.h</ObjSharpieSourceHeader> | ||
</PropertyGroup> | ||
|
||
<ItemGroup> | ||
<ObjcBindingApiDefinitionFiles Include="$(ObjSharpieBindOutputDir)/ApiDefinitions.cs" /> | ||
<_ObjSharpieInputs Include="$(ObjSharpieSourceHeader)" /> | ||
</ItemGroup> | ||
|
||
<Target Name="ObjSharpieBind" | ||
Condition="'$(ObjSharpieBind)' == 'true'" | ||
Inputs="@(_ObjSharpieInputs)" | ||
Outputs="@(ObjcBindingApiDefinitionFiles)"> | ||
<ItemGroup> | ||
<_ObjSharpieArgs Include="--output=$(ObjSharpieBindOutputDir)" /> | ||
<_ObjSharpieArgs Include="--namespace=$(ObjSharpieBindNamespace)" /> | ||
<_ObjSharpieArgs Include="--framework $(_XcArchiveiOSFullPath)/Products/Library/Frameworks/$(XcodeScheme).framework" /> | ||
</ItemGroup> | ||
<Exec Command="sharpie bind @(_ObjSharpieArgs, ' ')" /> | ||
</Target> | ||
<Import Project="$(MSBuildThisFileDirectory)Common.targets" Condition=" '$(CommonTargetsImported)' != 'true' " /> | ||
|
||
<UsingTask TaskName="Sharpie" AssemblyFile="$(BindingExtBuildTasksAssembly)"/> | ||
<UsingTask TaskName="XcodeBuild" AssemblyFile="$(BindingExtBuildTasksAssembly)"/> | ||
|
||
<PropertyGroup> | ||
<XcodeProjectConfiguration Condition=" '$(XcodeProjectConfiguration)' == '' ">Release</XcodeProjectConfiguration> | ||
<XcodeBuildiOS Condition=" '$(XcodeBuildiOS)' == '' ">true</XcodeBuildiOS> | ||
<XcodeBuildiOSSimulator Condition=" '$(XcodeBuildiOSSimulator)' == '' ">true</XcodeBuildiOSSimulator> | ||
<XcodeBuildMacCatalyst Condition=" '$(XcodeBuildMacCatalyst)' == '' ">true</XcodeBuildMacCatalyst> | ||
<EnableDefaultSharpieiOSItems Condition=" '$(EnableDefaultSharpieiOSItems)' == '' ">false</EnableDefaultSharpieiOSItems> | ||
|
||
<_XcArchiveExtraArgs>$(_XcArchiveExtraArgs) ENABLE_BITCODE=NO SKIP_INSTALL=NO SWIFT_INSTALL_OBJC_HEADER=YES BUILD_LIBRARY_FOR_DISTRIBUTION=YES</_XcArchiveExtraArgs> | ||
<_XcArchiveExtraArgs>$(_XcArchiveExtraArgs) OTHER_LDFLAGS="-ObjC" OTHER_SWIFT_FLAGS="-no-verify-emitted-module-interface" OBJC_CFLAGS="-fno-objc-msgsend-selector-stubs -ObjC"</_XcArchiveExtraArgs> | ||
</PropertyGroup> | ||
|
||
<PropertyGroup Condition="$(TargetFramework.Contains('ios')) Or $(TargetFramework.Contains('maccatalyst'))"> | ||
<_GenerateBindingsDependsOn> | ||
_BuildXcodeProjects; | ||
_SharpieBindXcodeProjects; | ||
$(_GenerateBindingsDependsOn); | ||
</_GenerateBindingsDependsOn> | ||
</PropertyGroup> | ||
|
||
<ItemDefinitionGroup> | ||
<XcodeProjectReference> | ||
<Kind>Framework</Kind> | ||
<SmartLink>true</SmartLink> | ||
</XcodeProjectReference> | ||
</ItemDefinitionGroup> | ||
|
||
<!-- TODO Fix incremental builds --> | ||
<Target Name="_GetBuildXcodeProjectsInputs"> | ||
<ItemGroup> | ||
<_XcbInputs Include="@(XcodeProjectReference->'%(RootDir)%(Directory)**/*.swift')" /> | ||
<_XcbInputs Include="@(XcodeProjectReference->'%(RootDir)%(Directory)**/*.h')" /> | ||
<_XcbInputs Include="@(XcodeProjectReference->'%(RootDir)%(Directory)**/*.pbxproj')" /> | ||
<_XcbInputs Include="@(XcodeProjectReference->'%(RootDir)%(Directory)**/*.xcworkspace')"/> | ||
<_XcbInputs Remove="@(XcodeProjectReference->'%(RootDir)%(Directory)build/**/*')" /> | ||
</ItemGroup> | ||
</Target> | ||
|
||
<Target Name="_BuildXcodeProjects" | ||
Condition=" '@(XcodeProjectReference->Count())' != '0' " | ||
DependsOnTargets="_EnsureBuildTasksAssembly;_GetBuildXcodeProjectsInputs;$(BuildXcodeProjectsDependsOnTargets)" | ||
Inputs="@(_XcbInputs)" | ||
Outputs="@(XcodeProjectReference->'%(RootDir)%(Directory)build/%(SchemeName).xcframework/Info.plist')" > | ||
|
||
<!-- Create xcarchive files for configured platforms --> | ||
<XcodeBuild Condition=" '$(XcodeBuildiOS)' == 'true' " | ||
Arguments="-project "%(XcodeProjectReference.FullPath)" archive -scheme %(SchemeName) -configuration $(XcodeProjectConfiguration) -archivePath "@(XcodeProjectReference->'%(RootDir)%(Directory)build/%(SchemeName)-ios.xcarchive')" -destination "generic/platform=iOS" $(_XcArchiveExtraArgs)" | ||
WorkingDirectory="%(XcodeProjectReference.RootDir)%(XcodeProjectReference.Directory)" > | ||
</XcodeBuild> | ||
|
||
<XcodeBuild Condition=" '$(XcodeBuildiOSSimulator)' == 'true' " | ||
Arguments="-project "%(XcodeProjectReference.FullPath)" archive -scheme %(SchemeName) -configuration $(XcodeProjectConfiguration) -archivePath "@(XcodeProjectReference->'%(RootDir)%(Directory)build/%(SchemeName)-iossimulator.xcarchive')" -destination "generic/platform=iOS Simulator" $(_XcArchiveExtraArgs)" | ||
WorkingDirectory="%(XcodeProjectReference.RootDir)%(XcodeProjectReference.Directory)" > | ||
</XcodeBuild> | ||
|
||
<XcodeBuild Condition=" '$(XcodeBuildMacCatalyst)' == 'true' " | ||
Arguments="-project "%(XcodeProjectReference.FullPath)" archive -scheme %(SchemeName) -configuration $(XcodeProjectConfiguration) -archivePath "@(XcodeProjectReference->'%(RootDir)%(Directory)build/%(SchemeName)-maccatalyst.xcarchive')" -destination "generic/platform=macOS,variant=Mac Catalyst" $(_XcArchiveExtraArgs)" | ||
WorkingDirectory="%(XcodeProjectReference.RootDir)%(XcodeProjectReference.Directory)" > | ||
</XcodeBuild> | ||
|
||
<!-- Create xcframework file from xcarchive files --> | ||
<ItemGroup> | ||
<_CreateXcFxArgs Include="-create-xcframework" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildiOS)' == 'true' " Include="@(XcodeProjectReference->'-archive %(RootDir)%(Directory)build/%(SchemeName)-ios.xcarchive')" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildiOS)' == 'true' " Include="-framework %(XcodeProjectReference.SchemeName).framework" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildiOSSimulator)' == 'true' " Include="@(XcodeProjectReference->'-archive %(RootDir)%(Directory)build/%(SchemeName)-iossimulator.xcarchive')" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildiOSSimulator)' == 'true' " Include="-framework %(XcodeProjectReference.SchemeName).framework" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildMacCatalyst)' == 'true' " Include="@(XcodeProjectReference->'-archive %(RootDir)%(Directory)build/%(SchemeName)-maccatalyst.xcarchive')" /> | ||
<_CreateXcFxArgs Condition=" '$(XcodeBuildMacCatalyst)' == 'true' " Include="-framework %(XcodeProjectReference.SchemeName).framework" /> | ||
<_CreateXcFxArgs Include="@(XcodeProjectReference->'-output %(RootDir)%(Directory)build/%(SchemeName).xcframework')" /> | ||
</ItemGroup> | ||
|
||
<RemoveDir Directories="@(XcodeProjectReference->'%(RootDir)%(Directory)build/%(SchemeName).xcframework')" /> | ||
|
||
<XcodeBuild Arguments="@(_CreateXcFxArgs, ' ')" | ||
WorkingDirectory="%(XcodeProjectReference.RootDir)%(XcodeProjectReference.Directory)" > | ||
</XcodeBuild> | ||
|
||
<ItemGroup> | ||
<NativeReference Include="@(XcodeProjectReference->'%(RootDir)%(Directory)build/%(SchemeName).xcframework')"> | ||
<Kind>%(XcodeProjectReference.Kind)</Kind> | ||
<SmartLink>%(XcodeProjectReference.SmartLink)</SmartLink> | ||
</NativeReference> | ||
</ItemGroup> | ||
|
||
<Error Condition=" !Exists('@(NativeReference)') " Text="Xcode project built successfully but did not produce expected output file: '@(NativeReference)'" /> | ||
<Message Text="Adding reference to Xcode project output: @(NativeReference)" /> | ||
</Target> | ||
|
||
|
||
<Target Name="_GetSharpieBindInputs"> | ||
<ItemGroup> | ||
<_SharpieInputs Include="@(XcodeProjectReference->'%(RootDir)%(Directory)build/%(SchemeName)-ios.xcarchive/Products/Library/Frameworks/%(SchemeName).framework')" /> | ||
</ItemGroup> | ||
</Target> | ||
|
||
<Target Name="_SharpieBindXcodeProjects" | ||
Condition=" '@(XcodeProjectReference->Count())' != '0' and '@(XcodeProjectReference->'%(SharpieBind)')' == 'true' " | ||
DependsOnTargets="_GetSharpieBindInputs" | ||
Inputs="@(_SharpieInputs)" | ||
Outputs="@(XcodeProjectReference->'%(RootDir)%(Directory)build/sharpie/ApiDefinitions.cs')"> | ||
|
||
<ItemGroup> | ||
<_ObjSharpieArgs Include="@(XcodeProjectReference->'--output=%(RootDir)%(Directory)build/sharpie')" /> | ||
<_ObjSharpieArgs Include="--namespace=%(XcodeProjectReference.SharpieNamespace)" /> | ||
<_ObjSharpieArgs Include="@(XcodeProjectReference->'--framework %(RootDir)%(Directory)build/%(SchemeName)-ios.xcarchive/Products/Library/Frameworks/%(SchemeName).framework')" /> | ||
</ItemGroup> | ||
|
||
<Sharpie Arguments="bind @(_ObjSharpieArgs, ' ')" /> | ||
</Target> | ||
|
||
</Project> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
7 changes: 4 additions & 3 deletions
7
eng/src/Microsoft.Maui.BindingExtensions.Build.Tasks/Tasks/Gradle.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
48 changes: 48 additions & 0 deletions
48
eng/src/Microsoft.Maui.BindingExtensions.Build.Tasks/Tasks/Sharpie.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
using System; | ||
using System.Runtime.InteropServices; | ||
|
||
using Microsoft.Build.Framework; | ||
|
||
namespace Microsoft.Maui.BindingExtensions.Build.Tasks | ||
{ | ||
public class Sharpie : BindingToolTask | ||
{ | ||
public override string TaskPrefix => "SHRP"; | ||
|
||
protected override string ToolName => "sharpie"; | ||
|
||
|
||
public string Arguments { get; set; } = string.Empty; | ||
|
||
|
||
public Sharpie() | ||
{ | ||
} | ||
|
||
protected override string GenerateFullPathToTool() | ||
{ | ||
return Path.Combine("/usr", "local", "bin", ToolExe); | ||
} | ||
|
||
protected override string GenerateCommandLineCommands() => Arguments; | ||
|
||
public override bool RunTask() | ||
{ | ||
if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX)) | ||
{ | ||
if (!File.Exists (GenerateFullPathToTool ())) { | ||
Log.LogCodedWarning($"{TaskPrefix}1000", "Unable to locate `sharpie`, please install https://aka.ms/objective-sharpie."); | ||
return false; | ||
} | ||
|
||
return base.RunTask(); | ||
} | ||
else | ||
{ | ||
Log.LogCodedWarning($"{TaskPrefix}1000", "sharpie is not currently supported on this platform. Please build this project on a macOS machine."); | ||
return false; | ||
} | ||
} | ||
|
||
} | ||
} |
43 changes: 43 additions & 0 deletions
43
eng/src/Microsoft.Maui.BindingExtensions.Build.Tasks/Tasks/XcodeBuild.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
using System; | ||
using System.Runtime.InteropServices; | ||
|
||
using Microsoft.Build.Framework; | ||
|
||
namespace Microsoft.Maui.BindingExtensions.Build.Tasks | ||
{ | ||
public class XcodeBuild : BindingToolTask | ||
{ | ||
public override string TaskPrefix => "XCBD"; | ||
|
||
protected override string ToolName => "xcodebuild"; | ||
|
||
|
||
public string Arguments { get; set; } = string.Empty; | ||
|
||
|
||
public XcodeBuild() | ||
{ | ||
} | ||
|
||
protected override string GenerateFullPathToTool() | ||
{ | ||
return Path.Combine("/usr", "bin", ToolExe); | ||
} | ||
|
||
protected override string GenerateCommandLineCommands() => Arguments; | ||
|
||
public override bool RunTask() | ||
{ | ||
if (RuntimeInformation.IsOSPlatform(OSPlatform.OSX)) | ||
{ | ||
return base.RunTask(); | ||
} | ||
else | ||
{ | ||
Log.LogCodedWarning($"{TaskPrefix}1000", "xcodebuild is not currently supported on this platform. Please build this project on a macOS machine."); | ||
return false; | ||
} | ||
} | ||
|
||
} | ||
} |
Oops, something went wrong.