Пример #1
0
def _ProcessManifest(manifest_path, min_sdk_version, target_sdk_version,
                     max_sdk_version, manifest_package):
    """Patches an Android manifest's package and performs assertions to ensure
  correctness for the manifest.
  """
    doc, manifest, _ = manifest_utils.ParseManifest(manifest_path)
    manifest_utils.AssertUsesSdk(manifest, min_sdk_version, target_sdk_version,
                                 max_sdk_version)
    assert manifest_utils.GetPackage(manifest) or manifest_package, \
              'Must set manifest package in GN or in AndroidManifest.xml'
    manifest_utils.AssertPackage(manifest, manifest_package)
    if manifest_package:
        manifest.set('package', manifest_package)
    tmp_prefix = os.path.basename(manifest_path)
    with tempfile.NamedTemporaryFile(prefix=tmp_prefix) as patched_manifest:
        manifest_utils.SaveManifest(doc, patched_manifest.name)
        yield patched_manifest.name, manifest_utils.GetPackage(manifest)
Пример #2
0
def _OnStaleMd5(options):
    with resource_utils.BuildContext() as build:
        if options.sources:
            _CheckAllFilesListed(options.sources, options.resource_dirs)
        if options.r_text_in:
            r_txt_path = options.r_text_in
        else:
            # Extract dependencies to resolve @foo/type references into
            # dependent packages.
            dep_subdirs = resource_utils.ExtractDeps(
                options.dependencies_res_zips, build.deps_dir)

            _GenerateRTxt(options, dep_subdirs, build.gen_dir)
            r_txt_path = build.r_txt_path

            # 'aapt' doesn't generate any R.txt file if res/ was empty.
            if not os.path.exists(r_txt_path):
                build_utils.Touch(r_txt_path)

        if options.r_text_out:
            shutil.copyfile(r_txt_path, options.r_text_out)

        if options.srcjar_out:
            package = options.custom_package
            if not package and options.android_manifest:
                _, manifest_node, _ = manifest_utils.ParseManifest(
                    options.android_manifest)
                package = manifest_utils.GetPackage(manifest_node)

            # Don't create a .java file for the current resource target when no
            # package name was provided (either by manifest or build rules).
            if package:
                # All resource IDs should be non-final here, but the
                # onResourcesLoaded() method should only be generated if
                # --shared-resources is used.
                rjava_build_options = resource_utils.RJavaBuildOptions()
                rjava_build_options.ExportAllResources()
                rjava_build_options.ExportAllStyleables()
                if options.shared_resources:
                    rjava_build_options.GenerateOnResourcesLoaded()

                # Not passing in custom_root_package_name or parent to keep
                # file names unique.
                resource_utils.CreateRJavaFiles(build.srcjar_dir, package,
                                                r_txt_path,
                                                options.extra_res_packages,
                                                options.extra_r_text_files,
                                                rjava_build_options,
                                                options.srcjar_out)

            build_utils.ZipDir(options.srcjar_out, build.srcjar_dir)

        if options.resource_zip_out:
            ignore_pattern = resource_utils.AAPT_IGNORE_PATTERN
            if options.strip_drawables:
                ignore_pattern += ':*drawable*'
            _ZipResources(options.resource_dirs, options.resource_zip_out,
                          ignore_pattern)
Пример #3
0
def _ProcessManifest(manifest_path, min_sdk_version, target_sdk_version,
                     manifest_package):
  """Patches an Android manifest to always include the 'tools' namespace
  declaration, as it is not propagated by the manifest merger from the SDK.

  See https://issuetracker.google.com/issues/63411481
  """
  doc, manifest, _ = manifest_utils.ParseManifest(manifest_path)
  manifest_utils.AssertUsesSdk(manifest, min_sdk_version, target_sdk_version)
  assert manifest_utils.GetPackage(manifest) or manifest_package, \
            'Must set manifest package in GN or in AndroidManifest.xml'
  manifest_utils.AssertPackage(manifest, manifest_package)
  if manifest_package:
    manifest.set('package', manifest_package)
  tmp_prefix = os.path.basename(manifest_path)
  with tempfile.NamedTemporaryFile(prefix=tmp_prefix) as patched_manifest:
    manifest_utils.SaveManifest(doc, patched_manifest.name)
    yield patched_manifest.name, manifest_utils.GetPackage(manifest)
Пример #4
0
def _ProcessManifest(manifest_path, allow_uses_sdk):
    """Patches an Android manifest to always include the 'tools' namespace
  declaration, as it is not propagated by the manifest merger from the SDK.

  See https://issuetracker.google.com/issues/63411481
  """
    doc, manifest, _ = manifest_utils.ParseManifest(manifest_path)
    package = manifest_utils.GetPackage(manifest)
    if not allow_uses_sdk:
        manifest_utils.AssertNoUsesSdk(manifest)
    tmp_prefix = os.path.basename(manifest_path)
    with tempfile.NamedTemporaryFile(prefix=tmp_prefix) as patched_manifest:
        manifest_utils.SaveManifest(doc, patched_manifest.name)
        yield patched_manifest.name, package
Пример #5
0
def _MaybeCheckServicesPresentInBase(bundle_path, module_zips):
    """Checks bundles with isolated splits define all services in the base module.

  Due to b/169196314, service classes are not found if they are not present in
  the base module.
  """
    base_manifest = _GetManifestForModule(bundle_path, 'base')
    isolated_splits = base_manifest.get('{%s}isolatedSplits' %
                                        manifest_utils.ANDROID_NAMESPACE)
    if isolated_splits != 'true':
        return

    # Collect service names from all split manifests.
    base_zip = None
    service_names = _GetServiceNames(base_manifest)
    for module_zip in module_zips:
        name = os.path.basename(module_zip)[:-len('.zip')]
        if name == 'base':
            base_zip = module_zip
        else:
            service_names.extend(
                _GetServiceNames(_GetManifestForModule(bundle_path, name)))

    # Extract classes from the base module's dex.
    classes = set()
    base_package_name = manifest_utils.GetPackage(base_manifest)
    for package in dexdump.Dump(base_zip):
        for name, package_dict in package.items():
            if not name:
                name = base_package_name
            classes.update('%s.%s' % (name, c)
                           for c in package_dict['classes'].keys())

    # Ensure all services are present in base module.
    for service_name in service_names:
        if service_name not in classes:
            raise Exception(
                "Service %s should be present in the base module's dex."
                " See b/169196314 for more details." % service_name)
Пример #6
0
def _MaybeCheckServicesAndProvidersPresentInBase(bundle_path, module_zips):
    """Checks bundles with isolated splits define all services in the base module.

  Due to b/169196314, service classes are not found if they are not present in
  the base module. Providers are also checked because they are loaded early in
  startup, and keeping them in the base module gives more time for the chrome
  split to load.
  """
    base_manifest = _GetManifestForModule(bundle_path, 'base')
    isolated_splits = base_manifest.get('{%s}isolatedSplits' %
                                        manifest_utils.ANDROID_NAMESPACE)
    if isolated_splits != 'true':
        return

    # Collect service names from all split manifests.
    base_zip = None
    service_names = _GetComponentNames(base_manifest, 'service')
    provider_names = _GetComponentNames(base_manifest, 'provider')
    for module_zip in module_zips:
        name = os.path.basename(module_zip)[:-len('.zip')]
        if name == 'base':
            base_zip = module_zip
        else:
            service_names.extend(
                _GetComponentNames(_GetManifestForModule(bundle_path, name),
                                   'service'))
            module_providers = _GetComponentNames(
                _GetManifestForModule(bundle_path, name), 'provider')
            if module_providers:
                raise Exception(
                    "Providers should all be declared in the base manifest."
                    " '%s' module declared: %s" % (name, module_providers))

    # Extract classes from the base module's dex.
    classes = set()
    base_package_name = manifest_utils.GetPackage(base_manifest)
    for package in dexdump.Dump(base_zip):
        for name, package_dict in package.items():
            if not name:
                name = base_package_name
            classes.update('%s.%s' % (name, c)
                           for c in package_dict['classes'].keys())

    ignored_service_names = {
        # Defined in the chime DFM manifest, but unused.
        # org.chromium.chrome.browser.chime.ScheduledTaskService is used instead.
        ("com.google.android.libraries.notifications.entrypoints.scheduled."
         "ScheduledTaskService"),

        # Defined in the chime DFM manifest, only used pre-O (where isolated
        # splits are not supported).
        ("com.google.android.libraries.notifications.executor.impl.basic."
         "ChimeExecutorApiService"),
    }

    # Ensure all services are present in base module.
    for service_name in service_names:
        if service_name not in classes:
            if service_name in ignored_service_names:
                continue
            raise Exception(
                "Service %s should be present in the base module's dex."
                " See b/169196314 for more details." % service_name)

    # Ensure all providers are present in base module.
    for provider_name in provider_names:
        if provider_name not in classes:
            raise Exception(
                "Provider %s should be present in the base module's dex." %
                provider_name)