Search in sources :

Example 1 with AndroidResource

use of com.facebook.buck.android.AndroidResource in project buck by facebook.

the class Project method walkRuleAndAdd.

/**
   * Walks the dependencies of a build rule and adds the appropriate DependentModules to the
   * specified dependencies collection. All library dependencies will be added before any module
   * dependencies. See {@code ProjectTest#testThatJarsAreListedBeforeModules()} for details on why
   * this behavior is important.
   */
@SuppressWarnings("PMD.LooseCoupling")
private void walkRuleAndAdd(final BuildRule rule, final boolean isForTests, final LinkedHashSet<SerializableDependentModule> dependencies, @Nullable final BuildRule srcTarget) {
    final Path basePathForRule = rule.getBuildTarget().getBasePath();
    Set<BuildRule> targetsToWalk;
    if (rule instanceof JavaTest) {
        targetsToWalk = ((JavaTest) rule).getCompiledTestsLibrary().getDeps();
    } else {
        targetsToWalk = rule.getDeps();
    }
    new AbstractBreadthFirstTraversal<BuildRule>(targetsToWalk) {

        private final LinkedHashSet<SerializableDependentModule> librariesToAdd = Sets.newLinkedHashSet();

        private final LinkedHashSet<SerializableDependentModule> modulesToAdd = Sets.newLinkedHashSet();

        @Override
        public ImmutableSet<BuildRule> visit(BuildRule dep) {
            // Hack: we don't want uber R.java to show up in the deps that IntelliJ sees.
            if (dep.getBuildTarget().toString().endsWith("_uber_r_dot_java")) {
                return ImmutableSet.of();
            }
            ImmutableSet<BuildRule> depsToVisit;
            if (rule.getProperties().is(PACKAGING) || dep instanceof AndroidResource || dep == rule) {
                depsToVisit = dep.getDeps();
            } else if (dep.getProperties().is(LIBRARY) && dep instanceof ExportDependencies) {
                depsToVisit = ((ExportDependencies) dep).getExportedDeps();
            } else {
                depsToVisit = ImmutableSet.of();
            }
            // should contain the union of :lib and :test's deps as dependent modules.
            if (isForTests && depsToVisit.isEmpty() && dep.getBuildTarget().getBasePath().equals(basePathForRule) && !dep.equals(srcTarget)) {
                depsToVisit = dep.getDeps();
            }
            SerializableDependentModule dependentModule;
            if (androidAars.contains(dep)) {
                AndroidPrebuiltAar aar = androidAars.getParentAar(dep);
                dependentModule = SerializableDependentModule.newLibrary(aar.getBuildTarget(), getIntellijNameForAar(aar));
            } else if (dep instanceof PrebuiltJar) {
                libraryJars.add(dep);
                String libraryName = getIntellijNameForRule(dep);
                dependentModule = SerializableDependentModule.newLibrary(dep.getBuildTarget(), libraryName);
            } else if (dep instanceof AndroidPrebuiltAar) {
                androidAars.add((AndroidPrebuiltAar) dep);
                String libraryName = getIntellijNameForAar(dep);
                dependentModule = SerializableDependentModule.newLibrary(dep.getBuildTarget(), libraryName);
            } else if ((dep instanceof CxxLibrary) || (dep instanceof NdkLibrary) || (dep instanceof JavaLibrary) || (dep instanceof AndroidResource)) {
                String moduleName = getIntellijNameForRule(dep);
                dependentModule = SerializableDependentModule.newModule(dep.getBuildTarget(), moduleName);
            } else {
                return depsToVisit;
            }
            if (librariesToAdd.contains(dependentModule) || modulesToAdd.contains(dependentModule)) {
                return depsToVisit;
            }
            if (isForTests) {
                dependentModule.scope = "TEST";
            } else {
                // If the dependentModule has already been added in the "TEST" scope, then it should be
                // removed and then re-added using the current (compile) scope.
                String currentScope = dependentModule.scope;
                dependentModule.scope = "TEST";
                if (dependencies.contains(dependentModule)) {
                    dependencies.remove(dependentModule);
                }
                dependentModule.scope = currentScope;
            }
            // dependencies collection once the traversal is complete in the onComplete() method.
            if (dependentModule.isLibrary()) {
                librariesToAdd.add(dependentModule);
            } else {
                modulesToAdd.add(dependentModule);
            }
            return depsToVisit;
        }

        @Override
        protected void onComplete() {
            dependencies.addAll(librariesToAdd);
            dependencies.addAll(modulesToAdd);
        }
    }.start();
}
Also used : Path(java.nio.file.Path) PathSourcePath(com.facebook.buck.rules.PathSourcePath) SourcePath(com.facebook.buck.rules.SourcePath) CxxLibrary(com.facebook.buck.cxx.CxxLibrary) ExportDependencies(com.facebook.buck.rules.ExportDependencies) AndroidResource(com.facebook.buck.android.AndroidResource) PrebuiltJar(com.facebook.buck.jvm.java.PrebuiltJar) ImmutableSet(com.google.common.collect.ImmutableSet) JavaLibrary(com.facebook.buck.jvm.java.JavaLibrary) JavaTest(com.facebook.buck.jvm.java.JavaTest) AndroidPrebuiltAar(com.facebook.buck.android.AndroidPrebuiltAar) BuildRule(com.facebook.buck.rules.BuildRule) NdkLibrary(com.facebook.buck.android.NdkLibrary)

Example 2 with AndroidResource

use of com.facebook.buck.android.AndroidResource in project buck by facebook.

the class Project method createModuleForProjectConfig.

@SuppressWarnings("PMD.LooseCoupling")
private SerializableModule createModuleForProjectConfig(ProjectConfig projectConfig, Optional<Path> rJava) throws IOException {
    BuildRule projectRule = Preconditions.checkNotNull(projectConfig.getProjectRule());
    Preconditions.checkState(projectRule instanceof AndroidBinary || projectRule instanceof AndroidLibrary || projectRule instanceof AndroidResource || projectRule instanceof JavaBinary || projectRule instanceof JavaLibrary || projectRule instanceof JavaTest || projectRule instanceof CxxLibrary || projectRule instanceof NdkLibrary, "project_config() does not know how to process a src_target of type %s (%s).", projectRule.getType(), projectRule.getBuildTarget());
    LinkedHashSet<SerializableDependentModule> dependencies = Sets.newLinkedHashSet();
    final BuildTarget target = projectConfig.getBuildTarget();
    SerializableModule module = new SerializableModule(projectRule, target);
    module.name = getIntellijNameForRule(projectRule);
    module.isIntelliJPlugin = projectConfig.getIsIntelliJPlugin();
    Path relativePath = projectConfig.getBuildTarget().getBasePath();
    module.pathToImlFile = relativePath.resolve(module.name + ".iml");
    // List the module source as the first dependency.
    boolean includeSourceFolder = true;
    // Do the tests before the sources so they appear earlier in the classpath. When tests are run,
    // their classpath entries may be deliberately shadowing production classpath entries.
    // tests folder
    boolean hasSourceFoldersForTestRule = addSourceFolders(module, projectConfig.getTestRule(), projectConfig.getTestsSourceRoots(), true);
    // test dependencies
    BuildRule testRule = projectConfig.getTestRule();
    if (testRule != null) {
        walkRuleAndAdd(testRule, true, /* isForTests */
        dependencies, projectConfig.getSrcRule());
    }
    // src folder
    boolean hasSourceFoldersForSrcRule = addSourceFolders(module, projectConfig.getSrcRule(), projectConfig.getSourceRoots(), false);
    addRootExcludes(module, projectConfig.getSrcRule(), projectFilesystem);
    // non-library Android project with no source roots specified.
    if (!hasSourceFoldersForTestRule && !hasSourceFoldersForSrcRule) {
        includeSourceFolder = false;
    }
    // IntelliJ expects all Android projects to have a gen/ folder, even if there is no src/
    // directory specified.
    boolean isAndroidRule = projectRule.getProperties().is(ANDROID);
    if (isAndroidRule) {
        boolean hasSourceFolders = !module.sourceFolders.isEmpty();
        module.sourceFolders.add(SerializableModule.SourceFolder.GEN);
        if (!hasSourceFolders) {
            includeSourceFolder = true;
        }
    }
    // src dependencies
    // Note that isForTests is false even if projectRule is the project_config's test_target.
    walkRuleAndAdd(projectRule, false, /* isForTests */
    dependencies, projectConfig.getSrcRule());
    Path basePath = projectConfig.getBuildTarget().getBasePath();
    // Specify another path for intellij to generate gen/ for each android module,
    // so that it will not disturb our glob() rules.
    // To specify the location of gen, Intellij requires the relative path from
    // the base path of current build target.
    module.moduleGenPath = generateRelativeGenPath(projectFilesystem, basePath);
    if (turnOffAutoSourceGeneration && rJava.isPresent()) {
        module.moduleRJavaPath = basePath.relativize(Paths.get("")).resolve(rJava.get());
    }
    SerializableDependentModule jdkDependency;
    if (isAndroidRule) {
        // android details
        if (projectRule instanceof NdkLibrary) {
            NdkLibrary ndkLibrary = (NdkLibrary) projectRule;
            module.isAndroidLibraryProject = true;
            module.keystorePath = null;
            module.nativeLibs = relativePath.relativize(ndkLibrary.getLibraryPath());
        } else if (projectRule instanceof AndroidLibrary) {
            module.isAndroidLibraryProject = true;
            module.keystorePath = null;
            module.resFolder = intellijConfig.getAndroidResources().orElse(null);
            module.assetFolder = intellijConfig.getAndroidAssets().orElse(null);
        } else if (projectRule instanceof AndroidResource) {
            AndroidResource androidResource = (AndroidResource) projectRule;
            module.resFolder = createRelativeResourcesPath(Optional.ofNullable(androidResource.getRes()).map(resolver::getAbsolutePath).map(projectFilesystem::relativize).orElse(null), target);
            module.isAndroidLibraryProject = true;
            module.keystorePath = null;
        } else if (projectRule instanceof AndroidBinary) {
            AndroidBinary androidBinary = (AndroidBinary) projectRule;
            module.resFolder = intellijConfig.getAndroidResources().orElse(null);
            module.assetFolder = intellijConfig.getAndroidAssets().orElse(null);
            module.isAndroidLibraryProject = false;
            module.binaryPath = generateRelativeAPKPath(projectFilesystem, projectRule.getBuildTarget().getShortName(), basePath);
            KeystoreProperties keystoreProperties = KeystoreProperties.createFromPropertiesFile(resolver.getAbsolutePath(androidBinary.getKeystore().getPathToStore()), resolver.getRelativePath(androidBinary.getKeystore().getPathToPropertiesFile()), projectFilesystem);
            // getKeystore() returns an absolute path, but an IntelliJ module
            // expects the path to the keystore to be relative to the module root.
            // First, grab the aboslute path to the project config.
            BuildTarget projectTarget = projectConfig.getBuildTarget();
            Path modulePath = projectTarget.getCellPath().resolve(projectTarget.getBasePath());
            // Now relativize to the keystore path, which is absolute too.
            module.keystorePath = modulePath.relativize(keystoreProperties.getKeystore());
        } else {
            module.isAndroidLibraryProject = true;
            module.keystorePath = null;
        }
        module.hasAndroidFacet = true;
        module.proguardConfigPath = null;
        module.androidManifest = resolveAndroidManifestRelativePath(basePath);
        // List this last so that classes from modules can shadow classes in the JDK.
        jdkDependency = SerializableDependentModule.newInheritedJdk();
    } else {
        module.hasAndroidFacet = false;
        if (module.isIntelliJPlugin()) {
            jdkDependency = SerializableDependentModule.newIntelliJPluginJdk();
        } else {
            jdkDependency = SerializableDependentModule.newStandardJdk(intellijConfig.getJdkName(), intellijConfig.getJdkType());
        }
    }
    // Assign the dependencies.
    module.setModuleDependencies(createDependenciesInOrder(includeSourceFolder, dependencies, jdkDependency));
    // Annotation processing generates sources for IntelliJ to consume, but does so outside
    // the module directory to avoid messing up globbing.
    JavaLibrary javaLibrary = null;
    if (projectRule instanceof JavaLibrary) {
        javaLibrary = (JavaLibrary) projectRule;
    }
    if (javaLibrary != null) {
        Optional<Path> processingParams = javaLibrary.getGeneratedSourcePath();
        if (processingParams.isPresent()) {
            module.annotationGenPath = basePath.relativize(processingParams.get());
            module.annotationGenIsForTest = !hasSourceFoldersForSrcRule;
        }
    }
    return module;
}
Also used : Path(java.nio.file.Path) PathSourcePath(com.facebook.buck.rules.PathSourcePath) SourcePath(com.facebook.buck.rules.SourcePath) CxxLibrary(com.facebook.buck.cxx.CxxLibrary) AndroidBinary(com.facebook.buck.android.AndroidBinary) JavaBinary(com.facebook.buck.jvm.java.JavaBinary) AndroidResource(com.facebook.buck.android.AndroidResource) JavaLibrary(com.facebook.buck.jvm.java.JavaLibrary) AndroidLibrary(com.facebook.buck.android.AndroidLibrary) BuildTarget(com.facebook.buck.model.BuildTarget) JavaTest(com.facebook.buck.jvm.java.JavaTest) BuildRule(com.facebook.buck.rules.BuildRule) NdkLibrary(com.facebook.buck.android.NdkLibrary) KeystoreProperties(com.facebook.buck.android.KeystoreProperties)

Example 3 with AndroidResource

use of com.facebook.buck.android.AndroidResource in project buck by facebook.

the class Project method createModulesForProjectConfigs.

@VisibleForTesting
List<SerializableModule> createModulesForProjectConfigs() throws IOException {
    List<SerializableModule> modules = Lists.newArrayList();
    // Convert the project_config() targets into modules and find the union of all jars passed to
    // no_dx.
    ImmutableSet.Builder<Path> noDxJarsBuilder = ImmutableSet.builder();
    for (ProjectConfig projectConfig : rules) {
        BuildRule srcRule = projectConfig.getSrcRule();
        if (srcRule instanceof AndroidBinary) {
            AndroidBinary androidBinary = (AndroidBinary) srcRule;
            AndroidPackageableCollection packageableCollection = androidBinary.getAndroidPackageableCollection();
            ImmutableSortedSet<Path> dxAbsolutePaths = resolver.getAllAbsolutePaths(packageableCollection.getNoDxClasspathEntries());
            noDxJarsBuilder.addAll(dxAbsolutePaths.stream().map(projectFilesystem::relativize).iterator());
        }
        final Optional<Path> rJava;
        if (srcRule instanceof AndroidLibrary) {
            AndroidLibrary androidLibrary = (AndroidLibrary) srcRule;
            BuildTarget dummyRDotJavaTarget = AndroidLibraryGraphEnhancer.getDummyRDotJavaTarget(androidLibrary.getBuildTarget());
            Path src = DummyRDotJava.getRDotJavaSrcFolder(dummyRDotJavaTarget, projectFilesystem);
            rJava = Optional.of(src);
        } else if (srcRule instanceof AndroidResource) {
            AndroidResource androidResource = (AndroidResource) srcRule;
            BuildTarget dummyRDotJavaTarget = AndroidLibraryGraphEnhancer.getDummyRDotJavaTarget(androidResource.getBuildTarget());
            Path src = DummyRDotJava.getRDotJavaSrcFolder(dummyRDotJavaTarget, projectFilesystem);
            rJava = Optional.of(src);
        } else {
            rJava = Optional.empty();
        }
        SerializableModule module = createModuleForProjectConfig(projectConfig, rJava);
        modules.add(module);
    }
    ImmutableSet<Path> noDxJars = noDxJarsBuilder.build();
    // Update module dependencies to apply scope="PROVIDED", where appropriate.
    markNoDxJarsAsProvided(projectFilesystem, modules, noDxJars, resolver);
    return modules;
}
Also used : Path(java.nio.file.Path) PathSourcePath(com.facebook.buck.rules.PathSourcePath) SourcePath(com.facebook.buck.rules.SourcePath) AndroidBinary(com.facebook.buck.android.AndroidBinary) AndroidResource(com.facebook.buck.android.AndroidResource) ProjectConfig(com.facebook.buck.rules.ProjectConfig) ImmutableSet(com.google.common.collect.ImmutableSet) AndroidLibrary(com.facebook.buck.android.AndroidLibrary) BuildTarget(com.facebook.buck.model.BuildTarget) BuildRule(com.facebook.buck.rules.BuildRule) AndroidPackageableCollection(com.facebook.buck.android.AndroidPackageableCollection) VisibleForTesting(com.google.common.annotations.VisibleForTesting)

Example 4 with AndroidResource

use of com.facebook.buck.android.AndroidResource in project buck by facebook.

the class ReactNativeLibraryGraphEnhancer method enhanceForAndroid.

public AndroidReactNativeLibrary enhanceForAndroid(BuildRuleParams params, BuildRuleResolver resolver, AndroidReactNativeLibraryDescription.Args args) {
    SourcePathRuleFinder ruleFinder = new SourcePathRuleFinder(resolver);
    BuildTarget originalBuildTarget = params.getBuildTarget();
    ReactNativeBundle bundle = createReactNativeBundle(params, resolver, ruleFinder, BuildTarget.builder(originalBuildTarget).addFlavors(REACT_NATIVE_BUNDLE_FLAVOR).build(), args, ReactNativePlatform.ANDROID);
    resolver.addToIndex(bundle);
    ImmutableList.Builder<BuildRule> extraDeps = ImmutableList.builder();
    extraDeps.add(bundle);
    if (args.rDotJavaPackage.isPresent()) {
        BuildRuleParams paramsForResource = params.withAppendedFlavor(REACT_NATIVE_ANDROID_RES_FLAVOR).copyReplacingExtraDeps(Suppliers.ofInstance(ImmutableSortedSet.of(bundle)));
        SourcePath resources = new ExplicitBuildTargetSourcePath(bundle.getBuildTarget(), bundle.getResources());
        BuildRule resource = new AndroidResource(paramsForResource, ruleFinder, /* deps */
        ImmutableSortedSet.of(), resources, /* resSrcs */
        ImmutableSortedMap.of(), args.rDotJavaPackage.get(), /* assets */
        null, /* assetsSrcs */
        ImmutableSortedMap.of(), /* manifest */
        null, /* hasWhitelistedStrings */
        false);
        resolver.addToIndex(resource);
        extraDeps.add(resource);
    }
    return new AndroidReactNativeLibrary(params.copyAppendingExtraDeps(extraDeps.build()), bundle);
}
Also used : ExplicitBuildTargetSourcePath(com.facebook.buck.rules.ExplicitBuildTargetSourcePath) SourcePath(com.facebook.buck.rules.SourcePath) BuildRuleParams(com.facebook.buck.rules.BuildRuleParams) BuildTarget(com.facebook.buck.model.BuildTarget) ImmutableList(com.google.common.collect.ImmutableList) BuildRule(com.facebook.buck.rules.BuildRule) AndroidResource(com.facebook.buck.android.AndroidResource) SourcePathRuleFinder(com.facebook.buck.rules.SourcePathRuleFinder) ExplicitBuildTargetSourcePath(com.facebook.buck.rules.ExplicitBuildTargetSourcePath)

Aggregations

AndroidResource (com.facebook.buck.android.AndroidResource)4 BuildRule (com.facebook.buck.rules.BuildRule)4 SourcePath (com.facebook.buck.rules.SourcePath)4 BuildTarget (com.facebook.buck.model.BuildTarget)3 PathSourcePath (com.facebook.buck.rules.PathSourcePath)3 Path (java.nio.file.Path)3 AndroidBinary (com.facebook.buck.android.AndroidBinary)2 AndroidLibrary (com.facebook.buck.android.AndroidLibrary)2 NdkLibrary (com.facebook.buck.android.NdkLibrary)2 CxxLibrary (com.facebook.buck.cxx.CxxLibrary)2 JavaLibrary (com.facebook.buck.jvm.java.JavaLibrary)2 JavaTest (com.facebook.buck.jvm.java.JavaTest)2 ImmutableSet (com.google.common.collect.ImmutableSet)2 AndroidPackageableCollection (com.facebook.buck.android.AndroidPackageableCollection)1 AndroidPrebuiltAar (com.facebook.buck.android.AndroidPrebuiltAar)1 KeystoreProperties (com.facebook.buck.android.KeystoreProperties)1 JavaBinary (com.facebook.buck.jvm.java.JavaBinary)1 PrebuiltJar (com.facebook.buck.jvm.java.PrebuiltJar)1 BuildRuleParams (com.facebook.buck.rules.BuildRuleParams)1 ExplicitBuildTargetSourcePath (com.facebook.buck.rules.ExplicitBuildTargetSourcePath)1