001    package org.jetbrains.jet.lang.resolve;
002    
003    import com.google.common.collect.Maps;
004    import com.intellij.util.containers.ContainerUtil;
005    import com.intellij.util.containers.MultiMap;
006    import org.jetbrains.annotations.NotNull;
007    import org.jetbrains.jet.lang.descriptors.ModuleDescriptor;
008    import org.jetbrains.jet.lang.descriptors.PackageFragmentDescriptor;
009    import org.jetbrains.jet.lang.descriptors.PackageFragmentProvider;
010    import org.jetbrains.jet.lang.descriptors.impl.MutablePackageFragmentDescriptor;
011    import org.jetbrains.jet.lang.resolve.name.FqName;
012    
013    import java.util.Collection;
014    import java.util.List;
015    import java.util.Map;
016    
017    public class MutablePackageFragmentProvider implements PackageFragmentProvider {
018        private final ModuleDescriptor module;
019    
020        private final Map<FqName, MutablePackageFragmentDescriptor> fqNameToPackage = Maps.newHashMap();
021        private final MultiMap<FqName, FqName> subPackages = MultiMap.create();
022    
023        public MutablePackageFragmentProvider(@NotNull ModuleDescriptor module) {
024            this.module = module;
025            fqNameToPackage.put(FqName.ROOT, new MutablePackageFragmentDescriptor(module, FqName.ROOT));
026        }
027    
028        @NotNull
029        @Override
030        public List<PackageFragmentDescriptor> getPackageFragments(@NotNull FqName fqName) {
031            return ContainerUtil.<PackageFragmentDescriptor>createMaybeSingletonList(fqNameToPackage.get(fqName));
032        }
033    
034        @NotNull
035        @Override
036        public Collection<FqName> getSubPackagesOf(@NotNull FqName fqName) {
037            return subPackages.get(fqName);
038        }
039    
040        @NotNull
041        public MutablePackageFragmentDescriptor getOrCreateFragment(@NotNull FqName fqName) {
042            if (!fqNameToPackage.containsKey(fqName)) {
043                FqName parent = fqName.parent();
044                getOrCreateFragment(parent); // assure that parent exists
045    
046                fqNameToPackage.put(fqName, new MutablePackageFragmentDescriptor(module, fqName));
047                subPackages.putValue(parent, fqName);
048            }
049    
050            return fqNameToPackage.get(fqName);
051        }
052    
053        @NotNull
054        public ModuleDescriptor getModule() {
055            return module;
056        }
057    
058        @NotNull
059        public Collection<MutablePackageFragmentDescriptor> getAllFragments() {
060            return fqNameToPackage.values();
061        }
062    }