Matt
Matt

Reputation: 141

How to fix 'Setting the namespace via the package attribute in the source AndroidManifest.xml is no longer supported.' with React Native Android

Error

Execution failed for task ':appcenter-analytics:processDebugManifest'.
> A failure occurred while executing com.android.build.gradle.tasks.ProcessLibraryManifest$ProcessLibWorkAction
   > Incorrect package="com.microsoft.appcenter.reactnative.analytics" found in source AndroidManifest.xml.
     Setting the namespace via the package attribute in the source AndroidManifest.xml is no longer supported.
     Recommendation: remove package="com.microsoft.appcenter.reactnative.analytics" from the source AndroidManifest.xml.

I am getting this error when trying to run an android React Native application, after upgrading the AGP with the AGP upgrade assistant (in Android Studio) from 7.4.2 to 8.2.1 (& Gradle version 8.2).

I have already specified a namespace it my own build.gradle (app) file:

android {
    ndkVersion rootProject.ext.ndkVersion
    compileSdkVersion 34
    namespace "com.example"
...

But as seen from the error, the issue is from a subproject dependency. There seems to be many (>10) of these dependencies with this issue. Which I think stems from them not specifying a namespace.

I have followed the advice from this answer https://stackoverflow.com/a/77738936/23282142 on a similar post, which attempts to add a namespace to all the subprojects if they don't already have one. But it has not fixed the problem. Here is my top-level build.gradle file:

// Top-level build file where you can add configuration options common to all sub-projects/modules.

buildscript {
    ext.kotlin_version = '1.8.22'
    ext {
        buildToolsVersion = "33.0.0"
        minSdkVersion = 21
        compileSdkVersion = 34
        targetSdkVersion = 33

        // We use NDK 23 which has both M1 support and is the side-by-side NDK version from AGP.
        ndkVersion = "23.1.7779620"
        playServicesLocationVersion = "21.0.1"
    }
    
    repositories {
        google()
        mavenCentral()
    }

    dependencies {
        classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
        classpath('com.android.tools.build:gradle:8.2.1')
        classpath("com.google.gms:google-services:4.4.0")
        classpath("com.facebook.react:react-native-gradle-plugin")
    }
}

// From https://stackoverflow.com/questions/76108428/how-do-i-fix-namespace-not-specified-error-in-android-studio
allprojects {
    // This code is where all the magic happens and fixes the error.
    subprojects {
        afterEvaluate { project ->
            if (project.hasProperty('android')) {
                project.android {
                    if (namespace == null) {
                        namespace project.group
                    }
                }
            }
        }
    }
    // This code is where all the magic happens and fixes the error.
}

Upvotes: 14

Views: 4652

Answers (1)

Vishnubly
Vishnubly

Reputation: 739

To anyone still facing this issue, can refer this: https://github.com/proyecto26/react-native-inappbrowser/issues/451#issuecomment-2275538714

Basically, add the following subproject script in your android build.gradle.

allprojects {
    repositories {

        maven {
            // https://wix.github.io/Detox/docs/introduction/project-setup
            url("$rootDir/../node_modules/detox/Detox-android")
        }

    }
  subprojects {
    afterEvaluate { project ->
      if (project.hasProperty('android')) {
        project.android {
          if (namespace == null || namespace.isEmpty()) {
            def defaultNamespace = project.group.toString().replace('.', '_')
            namespace = defaultNamespace
          }

          buildFeatures {
            buildConfig = true
          }
        }

        // Task to ensure namespace and remove package attribute
        project.tasks.register("fixManifestsAndNamespace") {
          doLast {
            // Ensure namespace in build.gradle
            def buildGradleFile = file("${project.projectDir}/build.gradle")
            if (buildGradleFile.exists()) {
              def buildGradleContent = buildGradleFile.getText('UTF-8')
              def manifestFile = file("${project.projectDir}/src/main/AndroidManifest.xml")
              if (manifestFile.exists()) {
                def manifestContent = manifestFile.getText('UTF-8')
                def packageName = manifestContent.find(/package="([^"]+)"/) { match, p -> p }
                if (packageName && !buildGradleContent.contains("namespace")) {
                  println "Setting namespace in ${buildGradleFile}"
                  buildGradleContent = buildGradleContent.replaceFirst(
                    /android\s*\{/, "android {\n    namespace '${packageName}'"
                  )
                  buildGradleFile.write(buildGradleContent, 'UTF-8')
                }
              }
            }

            // Remove package attribute from AndroidManifest.xml
            def manifests = fileTree(dir: project.projectDir, includes: ['**/AndroidManifest.xml'])
            manifests.each { File manifestFile ->
              def manifestContent = manifestFile.getText('UTF-8')
              if (manifestContent.contains('package=')) {
                println "Removing package attribute from ${manifestFile}"
                manifestContent = manifestContent.replaceAll(/package="[^"]*"/, '')
                manifestFile.write(manifestContent, 'UTF-8')
              }
            }
          }
        }

        // Ensure the task runs before the build process
        project.tasks.matching { it.name.startsWith("preBuild") }.all {
          dependsOn project.tasks.named("fixManifestsAndNamespace")
        }
      }
    }
  }

}

Upvotes: 1

Related Questions