diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/AndroidUpdateResourcesTest.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/AndroidUpdateResourcesTest.cs index fd082a697a0..b101a9f3895 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/AndroidUpdateResourcesTest.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/AndroidUpdateResourcesTest.cs @@ -383,7 +383,7 @@ public void CheckResourceDesignerIsUpdatedWhenReadOnly (bool isRelease, ProjectL }; using (var b = CreateApkBuilder ("temp/CheckResourceDesignerIsUpdatedWhenReadOnly")) { Assert.IsTrue (b.Build (proj), "Build should have succeeded."); - var designerPath = Path.Combine (Root, b.ProjectDirectory, "Resources", "Resource.designer" + language.DefaultExtension); + var designerPath = Path.Combine (Root, b.ProjectDirectory, "Resources", "Resource.designer" + language.DefaultDesignerExtension); var attr = File.GetAttributes (designerPath); File.SetAttributes (designerPath, FileAttributes.ReadOnly); Assert.IsTrue ((File.GetAttributes (designerPath) & FileAttributes.ReadOnly) == FileAttributes.ReadOnly, @@ -400,25 +400,28 @@ public void CheckResourceDesignerIsUpdatedWhenReadOnly (bool isRelease, ProjectL [TestCaseSource("ReleaseLanguage")] public void CheckOldResourceDesignerIsNotUsed (bool isRelease, ProjectLanguage language) { + if (language == XamarinAndroidProjectLanguage.FSharp) + Assert.Ignore ("Skipping CheckOldResourceDesignerIsNotUsed for FSharp until Xamarin.Android.FSharp.ResourceProvider supports it."); var proj = new XamarinAndroidApplicationProject () { Language = language, IsRelease = isRelease, }; proj.SetProperty ("AndroidUseIntermediateDesignerFile", "True"); using (var b = CreateApkBuilder ("temp/CheckOldResourceDesignerIsNotUsed")) { - var designer = proj.Sources.First (x => x.Include() == "Resources\\Resource.designer" + proj.Language.DefaultExtension); - designer.Deleted = true; + var designer = Path.Combine ("Resources", "Resource.designer" + proj.Language.DefaultDesignerExtension); + if (File.Exists (designer)) + File.Delete (Path.Combine (Root, b.ProjectDirectory, designer)); Assert.IsTrue (b.Build (proj), "Build should have succeeded."); Assert.IsFalse (File.Exists (Path.Combine (b.ProjectDirectory, "Resources", - "Resource.designer" + proj.Language.DefaultExtension)), - "{0} should not exists", designer.Include ()); + "Resource.designer" + proj.Language.DefaultDesignerExtension)), + "{0} should not exists", designer); var outputFile = Path.Combine (Root, b.ProjectDirectory, proj.IntermediateOutputPath, - "Resource.Designer" + proj.Language.DefaultExtension); + "Resource.Designer" + proj.Language.DefaultDesignerExtension); Assert.IsTrue (File.Exists (outputFile), "Resource.Designer{1} should have been created in {0}", - proj.IntermediateOutputPath, proj.Language.DefaultExtension); + proj.IntermediateOutputPath, proj.Language.DefaultDesignerExtension); Assert.IsTrue (b.Clean (proj), "Clean should have succeeded."); Assert.IsFalse (File.Exists (outputFile), "Resource.Designer{1} should have been cleaned in {0}", - proj.IntermediateOutputPath, proj.Language.DefaultExtension); + proj.IntermediateOutputPath, proj.Language.DefaultDesignerExtension); } } @@ -427,6 +430,8 @@ public void CheckOldResourceDesignerIsNotUsed (bool isRelease, ProjectLanguage l [TestCaseSource("ReleaseLanguage")] public void CheckOldResourceDesignerWithWrongCasingIsRemoved (bool isRelease, ProjectLanguage language) { + if (language == XamarinAndroidProjectLanguage.FSharp) + Assert.Ignore ("Skipping CheckOldResourceDesignerIsNotUsed for FSharp until Xamarin.Android.FSharp.ResourceProvider supports it."); var proj = new XamarinAndroidApplicationProject () { Language = language, IsRelease = isRelease, @@ -434,19 +439,21 @@ public void CheckOldResourceDesignerWithWrongCasingIsRemoved (bool isRelease, Pr proj.SetProperty ("AndroidUseIntermediateDesignerFile", "True"); proj.SetProperty ("AndroidResgenFile", "Resources\\Resource.Designer" + proj.Language.DefaultExtension); using (var b = CreateApkBuilder ("temp/CheckOldResourceDesignerWithWrongCasingIsRemoved")) { - var designer = proj.Sources.First (x => x.Include() == "Resources\\Resource.designer" + proj.Language.DefaultExtension); + var designer = proj.Sources.FirstOrDefault (x => x.Include() == "Resources\\Resource.designer" + proj.Language.DefaultDesignerExtension); + designer = designer ?? proj.OtherBuildItems.FirstOrDefault (x => x.Include () == "Resources\\Resource.designer" + proj.Language.DefaultDesignerExtension); + Assert.IsNotNull (designer, $"Failed to retrieve the Resource.designer.{proj.Language.DefaultDesignerExtension}"); designer.Deleted = true; Assert.IsTrue (b.Build (proj), "Build should have succeeded."); Assert.IsFalse (File.Exists (Path.Combine (b.ProjectDirectory, "Resources", - "Resource.designer" + proj.Language.DefaultExtension)), + "Resource.designer" + proj.Language.DefaultDesignerExtension)), "{0} should not exists", designer.Include ()); var outputFile = Path.Combine (Root, b.ProjectDirectory, proj.IntermediateOutputPath, - "Resource.Designer" + proj.Language.DefaultExtension); + "Resource.Designer" + proj.Language.DefaultDesignerExtension); Assert.IsTrue (File.Exists (outputFile), "Resource.Designer{1} should have been created in {0}", - proj.IntermediateOutputPath, proj.Language.DefaultExtension); + proj.IntermediateOutputPath, proj.Language.DefaultDesignerExtension); Assert.IsTrue (b.Clean (proj), "Clean should have succeeded."); Assert.IsFalse (File.Exists (outputFile), "Resource.Designer{1} should have been cleaned in {0}", - proj.IntermediateOutputPath, proj.Language.DefaultExtension); + proj.IntermediateOutputPath, proj.Language.DefaultDesignerExtension); } } diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs index c1311c161ac..fb579980427 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.Android.Build.Tests/BuildTest.cs @@ -735,7 +735,7 @@ public void CheckJavaError () using (var b = CreateApkBuilder ("temp/CheckJavaError")) { b.ThrowOnBuildFailure = false; Assert.IsFalse (b.Build (proj), "Build should have failed."); - if (b.RunXBuild) { + if (b.IsUnix) { var text = "TestMe.java(1,8): javacerror : error: class, interface, or enum expected"; if (b.RunningMSBuild) text = "TestMe.java(1,8): javac error : error: class, interface, or enum expected"; diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/KnownPackages.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/KnownPackages.cs index 1c7272784e7..faf08a0be00 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/KnownPackages.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/KnownPackages.cs @@ -238,6 +238,27 @@ public static class KnownPackages }, } }; + public static Package FSharp_Core_Latest = new Package { + Id = "FSharp.Core", + Version = "4.0.0.1", + TargetFramework = "monoandroid71", + References = { + new BuildItem.Reference ("mscorlib"), + new BuildItem.Reference ("FSharp.Core") { + MetadataValues = "HintPath=..\\packages\\FSharp.Core.4.0.0.1\\lib\\portable-net45+monoandroid10+monotouch10+xamarinios10\\FSharp.Core.dll" + }, + } + }; + public static Package Xamarin_Android_FSharp_ResourceProvider_Runtime = new Package { + Id = "Xamarin.Android.FSharp.ResourceProvider", + Version = "1.0.0.13", + TargetFramework = "monoandroid71", + References = { + new BuildItem.Reference ("FSharp.Core") { + MetadataValues = "HintPath=..\\packages\\Xamarin.Android.FSharp.ResourceProvider.1.0.0.13\\lib\\Xamarin.Android.FSharp.ResourceProvider.Runtime.dll" + }, + } + }; } } diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidApplicationProject.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidApplicationProject.cs index a7aac09e2f6..98ce1aa683e 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidApplicationProject.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidApplicationProject.cs @@ -39,10 +39,12 @@ public XamarinAndroidApplicationProject (string debugConfigurationName = "Debug" SetProperty ("AndroidApplication", "True"); SetProperty ("AndroidResgenClass", "Resource"); - SetProperty ("AndroidResgenFile", () => "Resources\\Resource.designer" + Language.DefaultExtension); + SetProperty ("AndroidResgenFile", () => "Resources\\Resource.designer" + Language.DefaultDesignerExtension); SetProperty ("AndroidManifest", "Properties\\AndroidManifest.xml"); SetProperty (DebugProperties, "AndroidLinkMode", "None"); SetProperty (ReleaseProperties, "AndroidLinkMode", "SdkOnly"); + SetProperty (DebugProperties, "EmbedAssembliesIntoApk", "False"); + SetProperty (ReleaseProperties, "EmbedAssembliesIntoApk", "True"); AndroidManifest = default_android_manifest; LayoutMain = default_layout_main; diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidCommonProject.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidCommonProject.cs index c6e44e4d71e..f41121de83f 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidCommonProject.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidCommonProject.cs @@ -17,6 +17,8 @@ public abstract class XamarinAndroidCommonProject : XamarinAndroidProject public static readonly byte[] icon_binary_xxhdpi; public static readonly byte[] icon_binary_xxxhdpi; + BuildItem.Source resourceDesigner; + static byte[] ScaleIcon (Image image, int width, int height) { float scale = Math.Min (width / image.Width, height / image.Height); @@ -56,8 +58,8 @@ protected XamarinAndroidCommonProject (string debugConfigurationName = "Debug", { AndroidResources = new List (); ItemGroupList.Add (AndroidResources); - - Sources.Add (new BuildItem.Source (() => "Resources\\Resource.designer" + Language.DefaultExtension) { TextContent = () => string.Empty }); + resourceDesigner = new BuildItem.Source (() => "Resources\\Resource.designer" + Language.DefaultDesignerExtension) { TextContent = () => string.Empty }; + Sources.Add (resourceDesigner); AndroidResources.Add (new AndroidItem.AndroidResource ("Resources\\drawable-mdpi\\Icon.png") { BinaryContent = () => icon_binary_mdpi }); AndroidResources.Add (new AndroidItem.AndroidResource ("Resources\\drawable-hdpi\\Icon.png") { BinaryContent = () => icon_binary_hdpi }); AndroidResources.Add (new AndroidItem.AndroidResource ("Resources\\drawable-xhdpi\\Icon.png") { BinaryContent = () => icon_binary_xhdpi }); @@ -78,5 +80,21 @@ public override ProjectRootElement Construct () root.AddImport (import.Project ()); return root; } + + public override ProjectLanguage Language { + get { + return base.Language; + } + set { + base.Language = value; + if (value == XamarinAndroidProjectLanguage.FSharp) { + // add the stuff needed for FSharp + Packages.Add (KnownPackages.FSharp_Core_Latest); + Packages.Add (KnownPackages.Xamarin_Android_FSharp_ResourceProvider_Runtime); + Sources.Remove (resourceDesigner); + OtherBuildItems.Add (new BuildItem.NoActionResource (() => "Resources\\Resource.designer" + Language.DefaultDesignerExtension) { TextContent = () => string.Empty }); + } + } + } } } diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidProjectLanguage.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidProjectLanguage.cs index 8d76eaa04da..d0058cde7a6 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidProjectLanguage.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Android/XamarinAndroidProjectLanguage.cs @@ -33,6 +33,9 @@ public override string ProjectTypeGuid { public override string DefaultExtension { get { return ".fs"; } } + public override string DefaultDesignerExtension { + get { return ".cs"; } + } public override string DefaultProjectExtension { get { return ".fsproj"; } } @@ -55,6 +58,9 @@ public override string ProjectTypeGuid { public override string DefaultExtension { get { return ".cs"; } } + public override string DefaultDesignerExtension { + get { return ".cs"; } + } public override string DefaultProjectExtension { get { return ".csproj"; } } diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/BuildOutput.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/BuildOutput.cs index 71c179538c5..3e00da5bdc7 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/BuildOutput.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/BuildOutput.cs @@ -49,7 +49,8 @@ public bool IsTargetSkipped (string target) if (!Builder.LastBuildOutput.Contains (target)) throw new ArgumentException (string.Format ("Target '{0}' is not even in the build output.", target)); return Builder.LastBuildOutput.Contains (string.Format ("Target {0} skipped due to ", target)) - || Builder.LastBuildOutput.Contains (string.Format ("Skipping target \"{0}\" because its outputs are up-to-date", target)); + || Builder.LastBuildOutput.Contains (string.Format ("Skipping target \"{0}\" because its outputs are up-to-date", target)) + || Builder.LastBuildOutput.Contains ($"Skipping target \"{target}\" because all output files are up-to-date"); } public bool IsApkInstalled { diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/Builder.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/Builder.cs index 16152a322ba..353387d456a 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/Builder.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/Builder.cs @@ -14,7 +14,7 @@ public class Builder : IDisposable const string msbuildapp = "msbuild"; string msbuildExe; - public bool RunXBuild { get; set; } + public bool IsUnix { get; set; } public bool RunningMSBuild { get; set; } public LoggerVerbosity Verbosity { get; set; } public string LastBuildOutput { get; set; } @@ -22,27 +22,28 @@ public class Builder : IDisposable public string BuildLogFile { get; set; } public bool ThrowOnBuildFailure { get; set; } - string GetXbuildPath () + string GetUnixBuildExe () { + RunningMSBuild = false; string path = Path.Combine (fixed_osx_xbuild_path, xbuildapp); if (!string.IsNullOrEmpty (Environment.GetEnvironmentVariable ("USE_MSBUILD"))) { path = Path.Combine (fixed_osx_xbuild_path, msbuildapp); RunningMSBuild = true; } - return File.Exists (path) ? path : xbuildapp; + return File.Exists (path) ? path : msbuildapp; } public string MSBuildExe { get { - return RunXBuild - ? File.Exists (fixed_osx_xbuild_path) ? fixed_osx_xbuild_path : "xbuild" + return IsUnix + ? GetUnixBuildExe () : msbuildExe; } } public string FrameworkLibDirectory { get { - if (RunXBuild) { + if (IsUnix) { var outdir = Environment.GetEnvironmentVariable ("XA_BUILD_OUTPUT_PATH"); if (String.IsNullOrEmpty(outdir)) outdir = Path.GetFullPath (Path.Combine (Root, "..", "..", "..", "..", "..", "..", "..", "out")); @@ -69,7 +70,7 @@ public string Root { public Builder () { - RunXBuild = Environment.OSVersion.Platform != PlatformID.Win32NT; + IsUnix = Environment.OSVersion.Platform != PlatformID.Win32NT; BuildLogFile = "build.log"; // Allow the override of the location of MSBuild and try a couple of backup paths for // MSBuild 14.0 and 4.0 @@ -124,7 +125,7 @@ protected bool BuildInternal (string projectOrSolution, string target, string [] ndkPath = Path.GetFullPath (Path.Combine (androidSdkToolPath, "ndk")); StringBuilder args = new StringBuilder (); var psi = new ProcessStartInfo (MSBuildExe); - if (RunXBuild) { + if (IsUnix) { if (Directory.Exists (sdkPath)) { args.AppendFormat ("/p:AndroidSdkDirectory=\"{0}\" ", sdkPath); } @@ -140,9 +141,12 @@ protected bool BuildInternal (string projectOrSolution, string target, string [] psi.EnvironmentVariables ["MSBuildExtensionsPath"] = targetsdir; } if (Directory.Exists (outdir)) { + var frameworksPath = Path.Combine (outdir, "lib", "xamarin.android", "xbuild-frameworks"); psi.EnvironmentVariables ["MONO_ANDROID_PATH"] = outdir; - psi.EnvironmentVariables ["XBUILD_FRAMEWORK_FOLDERS_PATH"] = Path.Combine (outdir, "lib", "xamarin.android", "xbuild-frameworks"); + psi.EnvironmentVariables ["XBUILD_FRAMEWORK_FOLDERS_PATH"] = frameworksPath; args.AppendFormat ("/p:MonoDroidInstallDirectory=\"{0}\" ", outdir); + if (RunningMSBuild) + args.AppendFormat ($"/p:TargetFrameworkRootPath={frameworksPath} "); } args.AppendFormat ("/t:{0} {1} /p:UseHostCompilerIfAvailable=false /p:BuildingInsideVisualStudio=true", target, QuoteFileName (Path.Combine (Root, projectOrSolution))); } diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectBuilder.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectBuilder.cs index 8354b9bca94..20cd257f7d5 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectBuilder.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectBuilder.cs @@ -119,8 +119,8 @@ public struct RuntimeInfo public RuntimeInfo [] GetSupportedRuntimes () { var runtimeInfo = new List (); - string outdir = FrameworkLibDirectory; - string path = Path.Combine (outdir, RunXBuild ? Path.Combine ("xbuild", "Xamarin", "Android", "lib") : ""); + var outdir = FrameworkLibDirectory; + var path = Path.Combine (outdir, IsUnix ? Path.Combine ("xbuild", "Xamarin", "Android", "lib") : ""); foreach (var file in Directory.EnumerateFiles (path, "libmono-android.*.*.so", SearchOption.AllDirectories)) { string fullFilePath = Path.GetFullPath (file); DirectoryInfo parentDir = Directory.GetParent (fullFilePath); diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectLanguage.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectLanguage.cs index e8df5133ca3..1bcff4b9e97 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectLanguage.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/ProjectLanguage.cs @@ -11,6 +11,7 @@ public abstract class ProjectLanguage { public abstract string DefaultAssemblyInfo { get; } public abstract string DefaultExtension { get; } + public abstract string DefaultDesignerExtension { get; } public abstract string DefaultProjectExtension { get; } public abstract string ProjectTypeGuid { get; } } diff --git a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/XamarinProject.cs b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/XamarinProject.cs index efab92cf46c..d2305281ab1 100644 --- a/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/XamarinProject.cs +++ b/src/Xamarin.Android.Build.Tasks/Tests/Xamarin.ProjectTools/Common/XamarinProject.cs @@ -17,7 +17,7 @@ public abstract class XamarinProject public string ProjectGuid { get; set; } public string AssemblyName { get; set; } - public ProjectLanguage Language { get; set; } + public virtual ProjectLanguage Language { get; set; } string debugConfigurationName; string releaseConfigurationName; @@ -62,6 +62,7 @@ protected XamarinProject (string debugConfigurationName = "Debug", string releas SetProperty ("RootNamespace", () => RootNamespace ?? ProjectName); SetProperty ("AssemblyName", () => AssemblyName ?? ProjectName); SetProperty ("BuildingInsideVisualStudio", "True"); + SetProperty ("BaseIntermediateOutputPath", "obj\\", " '$(BaseIntermediateOutputPath)' == '' "); SetProperty (DebugProperties, "DebugSymbols", "true"); SetProperty (DebugProperties, "DebugType", "full");