diff --git a/Configuration.props b/Configuration.props index 1463c7b8184..447a8fda27f 100644 --- a/Configuration.props +++ b/Configuration.props @@ -21,14 +21,9 @@ <_StandardLibraryPath Condition=" '$(TargetFrameworkVersion)' == '' ">$([Microsoft.Build.Utilities.ToolLocationHelper]::GetPathToStandardLibraries('.NETFramework', 'v4.7.2', '')) v4.7.2 v4.7.1 - - - v4.4 - 19 26 21 - $(AndroidFirstApiLevel) 33 $(AndroidLatestStableApiLevel) diff --git a/Documentation/building/configuration.md b/Documentation/building/configuration.md index 3325276f929..630e27407d0 100644 --- a/Documentation/building/configuration.md +++ b/Documentation/building/configuration.md @@ -27,11 +27,6 @@ Overridable MSBuild properties include: This is an integer value, e.g. `15` for [API-15 (Android 4.0.3)](http://developer.android.com/about/versions/android-4.0.3.html). - * `$(AndroidFirstFrameworkVersion)`: The first `$(TargetFrameworkVersion)` - which will be built by `make jenkins` and included in the installer. - Currently `v4.4`. - This controls what is included in `build-tools/create-vsix` packages. - * `$(AndroidFrameworkVersion)`: The Xamarin.Android `$(TargetFrameworkVersion)` version which corresponds to `$(AndroidApiLevel)`. This is *usually* the Android version number with a leading `v`, e.g. `v4.0.3` for API-15. diff --git a/Documentation/guides/messages/README.md b/Documentation/guides/messages/README.md index c31c84e89dc..c32d917a755 100644 --- a/Documentation/guides/messages/README.md +++ b/Documentation/guides/messages/README.md @@ -30,6 +30,7 @@ ms.date: 01/24/2020 + APT0002: Invalid file name: It must contain only \[^a-zA-Z0-9_.-\]+. + APT0003: Invalid file name: It must contain only \[^a-zA-Z0-9_.\]+. + APT0004: Invalid file name: It must start with either A-Z or a-z or an underscore. ++ [APT2264](apt2264.md): The system cannot find the file specified. (2). ## JAVAxxxx: Java Tool diff --git a/Documentation/guides/messages/apt2264.md b/Documentation/guides/messages/apt2264.md new file mode 100644 index 00000000000..d058a29a74f --- /dev/null +++ b/Documentation/guides/messages/apt2264.md @@ -0,0 +1,58 @@ +--- +title: Xamarin.Android error APT2264 +description: APT2264 error code +ms.date: 12/16/2022 +--- +# Xamarin.Android error APT2264 + +## Issue + +The tool `aapt2` is unable to resolve one of the files it was passed. +This is generally caused by the path being longer than the Maximum Path +length allowed on windows. + +## Solution + +The best way to avoid this is to ensure that your project is not located +deep in the folder structure. For example if you create all of your +projects in folders such as + +`C:\Users\shelly\Visual Studio\Android\MyProjects\Com.SomeReallyLongCompanyName.MyBrillantApplication\MyBrilliantApplicaiton.Android\` + +you may well encounter problems with not only `aapt2` but also Ahead of Time +compilation. Keeping your project names and folder structures short and +concise will help work around these issues. For example instead of the above +you could use + +`C:\Work\Android\MyBrilliantApp` + +Which is much shorter and much less likely to encounter path issues. + +However this is no always possible. Sometimes a project or a environment requires +deep folder structures. In this case enabling long path support in Windows *might* +be enough to get your project working. Details on how to do this can be found +[here](https://learn.microsoft.com/windows/win32/fileio/maximum-file-path-limitation?tabs=registry#enable-long-paths-in-windows-10-version-1607-and-later). + + +If long path support does not work changing the location of the +`$(BaseIntermediateOutputPath)` can help solve these problems. In order for this +to work the setting MUST be changed before ANY build or restore occurs. To do this +you can make use of the MSBuild `Directory.Build.props` support. + +Creating a `Directory.Build.props` file in your solution or project directory which +redefines the `$(BaseIntermediateOutputPath)` to somewhere nearer the root of the drive +with solve these issues. Adding a file with the following contents will create the `obj` +directory in a different location of your choosing. + +``` + + + C:\Intermediate\$(ProjectName) + /tmp/Intermediate/$(ProjectName) + + Tests > WearOS timeoutInMinutes: 180 @@ -771,172 +761,6 @@ stages: - template: yaml-templates/fail-on-issue.yaml - -- stage: designer_tests - displayName: Designer Tests - dependsOn: mac_build - condition: and(succeeded(), or(eq(variables['RunAllTests'], true), contains(dependencies.mac_build.outputs['mac_build_create_installers.TestConditions.TestAreas'], 'Designer'))) - jobs: - # Check - "Xamarin.Android (macOS > Tests > Designer Integration)" - - job: designer_integration_mac - condition: false #TODO: Enable once test issues are fixed. - displayName: macOS > Tests > Designer Integration - pool: - vmImage: $(HostedMacImage) - timeoutInMinutes: 120 - cancelTimeoutInMinutes: 5 - workspace: - clean: all - variables: - EnableRegressionTest: true - steps: - - checkout: uitools - clean: true - submodules: recursive - path: s/UITools - persistCredentials: true - - - powershell: | - # Use the branch name of the source being built or the PR target branch name. Fall back to 'main' if the branch is unknown. - $branchPrefix = "/refs/heads/" - $branchName = "$(Build.SourceBranch)" -replace $branchPrefix, "" - if ("$(Build.Reason)" -eq "PullRequest") { - $branchName = "$(System.PullRequest.TargetBranch)" -replace $branchPrefix, "" - } - if (("$branchName" -ne "main") -and ("$branchName" -notlike "d1*")) { - $branchName = "main" - } - Set-Location -Path $(System.DefaultWorkingDirectory)/UITools - git checkout $branchName - git submodule update -q --init --recursive - displayName: Clone and update UITools - - - task: NuGetAuthenticate@0 - displayName: authenticate with azure artifacts - inputs: - forceReinstallCredentialProvider: true - - - task: provisionator@2 - displayName: provision designer dependencies - inputs: - github_token: $(GitHub.Token) - provisioning_script: $(System.DefaultWorkingDirectory)/UITools/src/bot-provisioning/dependencies.csx - provisioning_extra_args: -remove Xamarin.Android -vv DEVDIV_PKGS_NUGET_TOKEN=$(DevDiv.NuGet.Token) SECTOOLS_PKGS_NUGET_TOKEN=$(SecTools.NuGet.Token) - env: - PROVISIONATOR_CHANNEL: ${{ parameters.provisionatorChannel }} - - - template: yaml-templates/setup-test-environment.yaml - parameters: - xaSourcePath: $(System.DefaultWorkingDirectory)/xamarin-android - jdkTestFolder: $(JAVA_HOME_8_X64) - provisionatorChannel: ${{ parameters.provisionatorChannel }} - - - template: designer/android-designer-build-mac.yaml@yaml-templates - parameters: - designerSourcePath: $(System.DefaultWorkingDirectory)/UITools/src - - - template: designer/android-designer-tests.yaml@yaml-templates - parameters: - designerSourcePath: $(System.DefaultWorkingDirectory)/UITools/src - runAddinTests: false - - - task: CopyFiles@2 - displayName: 'Copy binlogs' - inputs: - sourceFolder: $(System.DefaultWorkingDirectory)/UITools/src/Xamarin.Designer.Android - contents: '**/*.binlog' - targetFolder: $(Build.ArtifactStagingDirectory)/designer-binlogs - overWrite: true - flattenFolders: true - condition: ne(variables['Agent.JobStatus'], 'Succeeded') - - - template: yaml-templates/publish-artifact.yaml - parameters: - displayName: upload designer binlogs - artifactName: Test Results - Designer - macOS - targetPath: $(Build.ArtifactStagingDirectory)/designer-binlogs - condition: ne(variables['Agent.JobStatus'], 'Succeeded') - - # Check - "Xamarin.Android (Windows > Tests > Designer Integration)" - - job: designer_integration_win - displayName: Windows > Tests > Designer Integration - pool: - vmImage: $(HostedWinImage) - timeoutInMinutes: 120 - cancelTimeoutInMinutes: 5 - workspace: - clean: all - variables: - EnableRegressionTest: true - RegressionTestSuiteOutputDir: C:\Git\ADesRegTestSuite - VisualStudioInstallationPath: C:\Program Files\Microsoft Visual Studio\2022\Enterprise - steps: - - checkout: uitools - clean: true - submodules: recursive - path: s\UITools - persistCredentials: true - - - powershell: | - # Use the branch name of the source being built or the PR target branch name. Fall back to 'main' if the branch is unknown. - $branchPrefix = "/refs/heads/" - $branchName = "$(Build.SourceBranch)" -replace $branchPrefix, "" - if ("$(Build.Reason)" -eq "PullRequest") { - $branchName = "$(System.PullRequest.TargetBranch)" -replace $branchPrefix, "" - } - if (("$branchName" -ne "main") -and ("$branchName" -notlike "d1*")) { - $branchName = "main" - } - Set-Location -Path $(System.DefaultWorkingDirectory)\UITools - git checkout $branchName - git submodule update -q --init --recursive - displayName: Clone and update UITools - - - task: NuGetAuthenticate@0 - displayName: authenticate with azure artifacts - inputs: - forceReinstallCredentialProvider: true - - - task: provisionator@2 - displayName: provision designer dependencies - inputs: - github_token: $(GitHub.Token) - provisioning_script: $(System.DefaultWorkingDirectory)\UITools\src\bot-provisioning\dependencies.csx - provisioning_extra_args: -vv DEVDIV_PKGS_NUGET_TOKEN=$(DevDiv.NuGet.Token) SECTOOLS_PKGS_NUGET_TOKEN=$(SecTools.NuGet.Token) - env: - PROVISIONATOR_CHANNEL: ${{ parameters.provisionatorChannel }} - - - template: yaml-templates\setup-test-environment.yaml - parameters: - xaSourcePath: $(System.DefaultWorkingDirectory)\xamarin-android - jdkTestFolder: $(JAVA_HOME_8_X64) - provisionatorChannel: ${{ parameters.provisionatorChannel }} - - - task: VSBuild@1 - displayName: Restore Xamarin.AndroidDesigner - inputs: - solution: $(System.DefaultWorkingDirectory)\UITools\src\Xamarin.Designer.Android\Xamarin.AndroidDesigner.sln - vsVersion: 17.0 - msbuildArgs: >- - /t:Restore /p:RestoreDisableParallel=true - /p:RestoreConfigFile="$(System.DefaultWorkingDirectory)\UITools\NuGet.Config" - /p:JavaSdkDirectory="$(JAVA_HOME_8_X64)" - platform: Any CPU - configuration: DebugWin32 - - - task: VSBuild@1 - displayName: Build Xamarin.AndroidDesigner - inputs: - solution: $(System.DefaultWorkingDirectory)\UITools\src\Xamarin.Designer.Android\Xamarin.AndroidDesigner.sln - vsVersion: 17.0 - msbuildArgs: /t:Build /p:GitHubToken=$(GitHub.Token) - platform: Any CPU - configuration: DebugWin32 - - - template: yaml-templates/run-designer-tests.yml - parameters: - designerSourcePath: $(System.DefaultWorkingDirectory)\UITools\src - - stage: bcl_tests displayName: BCL Emulator Tests dependsOn: mac_build diff --git a/build-tools/installers/create-installers.targets b/build-tools/installers/create-installers.targets index ada186821d7..7f8c78b577a 100644 --- a/build-tools/installers/create-installers.targets +++ b/build-tools/installers/create-installers.targets @@ -14,7 +14,6 @@ $(XAInstallPrefix)xbuild\Xamarin\Android\ $(XamarinAndroidSourcePath)src\Xamarin.Android.Build.Tasks\MSBuild\Xamarin\Android $(MSBuildThisFileDirectory)\..\create-pkg\runtime-entitlements.plist - $(AndroidFirstFrameworkVersion) $(AndroidLatestStableFrameworkVersion) v1.0 dylib diff --git a/build-tools/xaprepare/xaprepare/ConfigAndData/BuildAndroidPlatforms.cs b/build-tools/xaprepare/xaprepare/ConfigAndData/BuildAndroidPlatforms.cs index 0dbf3ca9f74..4604aea5292 100644 --- a/build-tools/xaprepare/xaprepare/ConfigAndData/BuildAndroidPlatforms.cs +++ b/build-tools/xaprepare/xaprepare/ConfigAndData/BuildAndroidPlatforms.cs @@ -29,20 +29,20 @@ class BuildAndroidPlatforms new AndroidPlatform (apiName: "Jelly Bean", apiLevel: 16, platformID: "16", include: "v4.1"), new AndroidPlatform (apiName: "Jelly Bean", apiLevel: 17, platformID: "17", include: "v4.2"), new AndroidPlatform (apiName: "Jelly Bean", apiLevel: 18, platformID: "18", include: "v4.3"), - new AndroidPlatform (apiName: "Kit Kat", apiLevel: 19, platformID: "19", include: "v4.4", framework: "v4.4"), - new AndroidPlatform (apiName: "Kit Kat + Wear support", apiLevel: 20, platformID: "20", include: "v4.4.87", framework: "v4.4.87"), - new AndroidPlatform (apiName: "Lollipop", apiLevel: 21, platformID: "21", include: "v5.0", framework: "v5.0"), - new AndroidPlatform (apiName: "Lollipop", apiLevel: 22, platformID: "22", include: "v5.1", framework: "v5.1"), - new AndroidPlatform (apiName: "Marshmallow", apiLevel: 23, platformID: "23", include: "v6.0", framework: "v6.0"), - new AndroidPlatform (apiName: "Nougat", apiLevel: 24, platformID: "24", include: "v7.0", framework: "v7.0"), - new AndroidPlatform (apiName: "Nougat", apiLevel: 25, platformID: "25", include: "v7.1", framework: "v7.1"), - new AndroidPlatform (apiName: "Oreo", apiLevel: 26, platformID: "26", include: "v8.0", framework: "v8.0"), - new AndroidPlatform (apiName: "Oreo", apiLevel: 27, platformID: "27", include: "v8.1", framework: "v8.1"), - new AndroidPlatform (apiName: "Pie", apiLevel: 28, platformID: "28", include: "v9.0", framework: "v9.0"), - new AndroidPlatform (apiName: "Q", apiLevel: 29, platformID: "29", include: "v10.0", framework: "v10.0"), - new AndroidPlatform (apiName: "R", apiLevel: 30, platformID: "30", include: "v11.0", framework: "v11.0"), - new AndroidPlatform (apiName: "S", apiLevel: 31, platformID: "31", include: "v12.0", framework: "v12.0"), - new AndroidPlatform (apiName: "Sv2", apiLevel: 32, platformID: "32", include: "v12.1", framework: "v12.1"), + new AndroidPlatform (apiName: "Kit Kat", apiLevel: 19, platformID: "19", include: "v4.4"), + new AndroidPlatform (apiName: "Kit Kat + Wear support", apiLevel: 20, platformID: "20", include: "v4.4.87"), + new AndroidPlatform (apiName: "Lollipop", apiLevel: 21, platformID: "21", include: "v5.0"), + new AndroidPlatform (apiName: "Lollipop", apiLevel: 22, platformID: "22", include: "v5.1"), + new AndroidPlatform (apiName: "Marshmallow", apiLevel: 23, platformID: "23", include: "v6.0"), + new AndroidPlatform (apiName: "Nougat", apiLevel: 24, platformID: "24", include: "v7.0"), + new AndroidPlatform (apiName: "Nougat", apiLevel: 25, platformID: "25", include: "v7.1"), + new AndroidPlatform (apiName: "Oreo", apiLevel: 26, platformID: "26", include: "v8.0"), + new AndroidPlatform (apiName: "Oreo", apiLevel: 27, platformID: "27", include: "v8.1"), + new AndroidPlatform (apiName: "Pie", apiLevel: 28, platformID: "28", include: "v9.0"), + new AndroidPlatform (apiName: "Q", apiLevel: 29, platformID: "29", include: "v10.0"), + new AndroidPlatform (apiName: "R", apiLevel: 30, platformID: "30", include: "v11.0"), + new AndroidPlatform (apiName: "S", apiLevel: 31, platformID: "31", include: "v12.0"), + new AndroidPlatform (apiName: "Sv2", apiLevel: 32, platformID: "32", include: "v12.1"), new AndroidPlatform (apiName: "Tiramisu", apiLevel: 33, platformID: "33", include: "v13.0", framework: "v13.0"), }; diff --git a/src/Xamarin.Android.Build.Tasks/Properties/Resources.Designer.cs b/src/Xamarin.Android.Build.Tasks/Properties/Resources.Designer.cs index c87254b93ce..a086eaa35f3 100644 --- a/src/Xamarin.Android.Build.Tasks/Properties/Resources.Designer.cs +++ b/src/Xamarin.Android.Build.Tasks/Properties/Resources.Designer.cs @@ -800,6 +800,15 @@ public static string XA2008 { } } + /// + /// Looks up a localized string similar to This is probably caused by the project exceeding the Max Path length. Please move your entire project closer to the Root of the drive.. + /// + public static string APT2264 { + get { + return ResourceManager.GetString("APT2264", resourceCulture); + } + } + /// /// Looks up a localized string similar to Could not AOT the assembly: {0}. /// diff --git a/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx b/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx index c36b272704b..f78a40c1314 100644 --- a/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx +++ b/src/Xamarin.Android.Build.Tasks/Properties/Resources.resx @@ -530,6 +530,10 @@ Please change the value to an assembly-qualifed type name which inherits from '{ The following are literal names and should not be translated: Java.Interop.DoNotPackageAttribute {0} - The assembly name + + This is probably caused by the project exceeding the Windows maximum path length limitation. See https://learn.microsoft.com/xamarin/android/errors-and-warnings/apt2264 for details. + The following are literal names and should not be translated: + Could not AOT the assembly: {0} The abbreviation "AOT" should not be translated. diff --git a/src/Xamarin.Android.Build.Tasks/Tasks/Aapt2.cs b/src/Xamarin.Android.Build.Tasks/Tasks/Aapt2.cs index 961005e362a..193a72e630f 100644 --- a/src/Xamarin.Android.Build.Tasks/Tasks/Aapt2.cs +++ b/src/Xamarin.Android.Build.Tasks/Tasks/Aapt2.cs @@ -188,23 +188,38 @@ protected bool LogAapt2EventsFromOutput (string singleLine, MessageImportance me message = message.Substring ("error: ".Length); if (level.Contains ("error") || (line != 0 && !string.IsNullOrEmpty (file))) { + var errorCode = GetErrorCode (message); if (manifestError) - LogCodedError (GetErrorCode (message), string.Format (Xamarin.Android.Tasks.Properties.Resources.AAPTManifestError, message.TrimEnd('.')), AndroidManifestFile.ItemSpec, 0); + LogCodedError (errorCode, string.Format (Xamarin.Android.Tasks.Properties.Resources.AAPTManifestError, message.TrimEnd('.')), AndroidManifestFile.ItemSpec, 0); else - LogCodedError (GetErrorCode (message), message, file, line); + LogCodedError (errorCode, AddAdditionalErrorText (errorCode, message), file, line); return true; } } if (!apptResult) { var message = string.Format ("{0} \"{1}\".", singleLine.Trim (), singleLine.Substring (singleLine.LastIndexOfAny (new char [] { '\\', '/' }) + 1)); - LogCodedError (GetErrorCode (message), message, ToolName); + var errorCode = GetErrorCode (message); + LogCodedError (errorCode, AddAdditionalErrorText (errorCode, message), ToolName); } else { LogCodedWarning (GetErrorCode (singleLine), singleLine); } return true; } + static string AddAdditionalErrorText (string errorCode, string message) + { + var sb = new StringBuilder (); + sb.AppendLine (message); + switch (errorCode) + { + case "APT2264": + sb.AppendLine (Xamarin.Android.Tasks.Properties.Resources.APT2264); + break; + } + return sb.ToString (); + } + static string GetErrorCode (string message) { foreach (var tuple in error_codes) @@ -478,6 +493,7 @@ static string GetErrorCode (string message) Tuple.Create ("APT2261", "file failed to compile"), Tuple.Create ("APT2262", "unexpected element found in "), Tuple.Create ("APT2263", "found in "), // unexpected element found in + Tuple.Create ("APT2264", "The system cannot find the file specified. (2).") // Windows Long Path error from aapt2 }; } } diff --git a/src/Xamarin.Android.Build.Tasks/Tasks/ReadAndroidManifest.cs b/src/Xamarin.Android.Build.Tasks/Tasks/ReadAndroidManifest.cs index 612fea6a844..c8143247d22 100644 --- a/src/Xamarin.Android.Build.Tasks/Tasks/ReadAndroidManifest.cs +++ b/src/Xamarin.Android.Build.Tasks/Tasks/ReadAndroidManifest.cs @@ -35,6 +35,9 @@ public class ReadAndroidManifest : AndroidTask [Output] public bool UseEmbeddedDex { get; set; } = false; + [Output] + public bool IsTestOnly { get; set; } = false; + public override bool RunTask () { var androidNs = AndroidAppManifest.AndroidXNamespace; @@ -52,6 +55,11 @@ public override bool RunTask () UseEmbeddedDex = value; } + text = app.Attribute (androidNs + "testOnly")?.Value; + if (bool.TryParse (text, out value)) { + IsTestOnly = value; + } + var libraries = new List (); foreach (var uses_library in app.Elements ("uses-library")) { var attribute = uses_library.Attribute (androidNs + "name"); diff --git a/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets b/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets index 8606402f9f1..060d670a696 100644 --- a/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets +++ b/src/Xamarin.Android.Build.Tasks/Xamarin.Android.Common.targets @@ -1641,6 +1641,7 @@ because xbuild doesn't support framework reference assemblies. + .so;$(AndroidStoreUncompressedFileExtensions) diff --git a/tests/MSBuildDeviceIntegration/Tests/InstallAndRunTests.cs b/tests/MSBuildDeviceIntegration/Tests/InstallAndRunTests.cs index 1b95d9469f9..c707f41a37e 100644 --- a/tests/MSBuildDeviceIntegration/Tests/InstallAndRunTests.cs +++ b/tests/MSBuildDeviceIntegration/Tests/InstallAndRunTests.cs @@ -786,12 +786,14 @@ public void ResourceDesignerWithNuGetReference ([Values ("net8.0-android33.0")] } [Test] - public void SingleProject_ApplicationId () + public void SingleProject_ApplicationId ([Values (false, true)] bool testOnly) { AssertHasDevices (); proj = new XamarinAndroidApplicationProject (); proj.SetProperty ("ApplicationId", "com.i.should.get.overridden.by.the.manifest"); + if (testOnly) + proj.AndroidManifest = proj.AndroidManifest.Replace ("