Line data Source code
1 : // Copyright (C) 2020 The Android Open Source Project 2 : // 3 : // Licensed under the Apache License, Version 2.0 (the "License"); 4 : // you may not use this file except in compliance with the License. 5 : // You may obtain a copy of the License at 6 : // 7 : // http://www.apache.org/licenses/LICENSE-2.0 8 : // 9 : // Unless required by applicable law or agreed to in writing, software 10 : // distributed under the License is distributed on an "AS IS" BASIS, 11 : // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 : // See the License for the specific language governing permissions and 13 : // limitations under the License. 14 : 15 : package com.google.gerrit.entities; 16 : 17 : import com.google.auto.value.AutoValue; 18 : import com.google.common.collect.ImmutableList; 19 : import com.google.common.collect.ImmutableMap; 20 : import com.google.common.collect.ImmutableSet; 21 : import com.google.common.collect.ImmutableSortedMap; 22 : import com.google.common.flogger.FluentLogger; 23 : import java.util.Collection; 24 : import java.util.List; 25 : import java.util.Map; 26 : import java.util.Optional; 27 : import org.eclipse.jgit.annotations.Nullable; 28 : import org.eclipse.jgit.errors.ConfigInvalidException; 29 : import org.eclipse.jgit.lib.ObjectId; 30 : 31 : /** 32 : * Cached representation of values parsed from {@link 33 : * com.google.gerrit.server.project.ProjectConfig}. 34 : * 35 : * <p>This class is immutable and thread-safe. 36 : */ 37 : @AutoValue 38 152 : public abstract class CachedProjectConfig { 39 153 : private static final FluentLogger logger = FluentLogger.forEnclosingClass(); 40 : 41 : public abstract Project getProject(); 42 : 43 : public abstract ImmutableMap<AccountGroup.UUID, GroupReference> getGroups(); 44 : 45 : /** Returns a set of all groups used by this configuration. */ 46 : public ImmutableSet<AccountGroup.UUID> getAllGroupUUIDs() { 47 1 : return getGroups().keySet(); 48 : } 49 : 50 : /** 51 : * Returns the group reference for a {@link AccountGroup.UUID}, if the group is used by at least 52 : * one rule. 53 : */ 54 : public Optional<GroupReference> getGroup(AccountGroup.UUID uuid) { 55 3 : return Optional.ofNullable(getGroups().get(uuid)); 56 : } 57 : 58 : /** 59 : * Returns the group reference for matching the given {@code name}, if the group is used by at 60 : * least one rule. 61 : */ 62 : public Optional<GroupReference> getGroupByName(@Nullable String name) { 63 1 : if (name == null) { 64 1 : return Optional.empty(); 65 : } 66 1 : return getGroups().values().stream().filter(g -> name.equals(g.getName())).findAny(); 67 : } 68 : 69 : /** Returns the account section containing visibility information about accounts. */ 70 : public abstract AccountsSection getAccountsSection(); 71 : 72 : /** Returns a map of {@link AccessSection}s keyed by their name. */ 73 : public abstract ImmutableSortedMap<String, AccessSection> getAccessSections(); 74 : 75 : /** Returns the {@link AccessSection} with to the given name. */ 76 : public Optional<AccessSection> getAccessSection(String refName) { 77 151 : return Optional.ofNullable(getAccessSections().get(refName)); 78 : } 79 : 80 : /** Returns all {@link AccessSection} names. */ 81 : public ImmutableSet<String> getAccessSectionNames() { 82 1 : return ImmutableSet.copyOf(getAccessSections().keySet()); 83 : } 84 : 85 : /** 86 : * Returns the {@link BranchOrderSection} containing the order in which branches should be shown. 87 : */ 88 : public abstract Optional<BranchOrderSection> getBranchOrderSection(); 89 : 90 : /** Returns the {@link ContributorAgreement}s keyed by their name. */ 91 : public abstract ImmutableMap<String, ContributorAgreement> getContributorAgreements(); 92 : 93 : /** Returns the {@link NotifyConfig}s keyed by their name. */ 94 : public abstract ImmutableMap<String, NotifyConfig> getNotifySections(); 95 : 96 : /** Returns the {@link LabelType}s keyed by their name. */ 97 : public abstract ImmutableMap<String, LabelType> getLabelSections(); 98 : 99 : /** Returns the {@link SubmitRequirement}s keyed by their name. */ 100 : public abstract ImmutableMap<String, SubmitRequirement> getSubmitRequirementSections(); 101 : 102 : /** Returns configured {@link ConfiguredMimeTypes}s. */ 103 : public abstract ConfiguredMimeTypes getMimeTypes(); 104 : 105 : /** Returns {@link SubscribeSection} keyed by the {@link Project.NameKey} they reference. */ 106 : public abstract ImmutableMap<Project.NameKey, SubscribeSection> getSubscribeSections(); 107 : 108 : /** Returns {@link StoredCommentLinkInfo} keyed by their name. */ 109 : public abstract ImmutableMap<String, StoredCommentLinkInfo> getCommentLinkSections(); 110 : 111 : /** Returns the blob ID of the {@code rules.pl} file, if present. */ 112 : public abstract Optional<ObjectId> getRulesId(); 113 : 114 : // TODO(hiesel): This should not have to be an Optional. 115 : /** Returns the SHA1 of the {@code refs/meta/config} branch. */ 116 : public abstract Optional<ObjectId> getRevision(); 117 : 118 : /** Returns the maximum allowed object size. */ 119 : public abstract long getMaxObjectSizeLimit(); 120 : 121 : /** Returns {@code true} if received objects should be checked for validity. */ 122 : public abstract boolean getCheckReceivedObjects(); 123 : 124 : /** Returns a list of panel sections keyed by title. */ 125 : public abstract ImmutableMap<String, ImmutableList<String>> getExtensionPanelSections(); 126 : 127 : public ImmutableList<SubscribeSection> getSubscribeSections(BranchNameKey branch) { 128 65 : return filterSubscribeSectionsByBranch(getSubscribeSections().values(), branch); 129 : } 130 : 131 : public abstract ImmutableMap<String, String> getPluginConfigs(); 132 : 133 : public abstract ImmutableMap<String, String> getProjectLevelConfigs(); 134 : 135 : public abstract ImmutableMap<String, ImmutableConfig> getParsedProjectLevelConfigs(); 136 : 137 : public static Builder builder() { 138 152 : return new AutoValue_CachedProjectConfig.Builder(); 139 : } 140 : 141 : public abstract Builder toBuilder(); 142 : 143 : @AutoValue.Builder 144 152 : public abstract static class Builder { 145 : public abstract Builder setProject(Project value); 146 : 147 : public abstract Builder setAccountsSection(AccountsSection value); 148 : 149 : public abstract Builder setBranchOrderSection(Optional<BranchOrderSection> value); 150 : 151 : public Builder addGroup(GroupReference groupReference) { 152 152 : groupsBuilder().put(groupReference.getUUID(), groupReference); 153 152 : return this; 154 : } 155 : 156 : public Builder addAccessSection(AccessSection accessSection) { 157 152 : accessSectionsBuilder().put(accessSection.getName(), accessSection); 158 152 : return this; 159 : } 160 : 161 : public Builder addContributorAgreement(ContributorAgreement contributorAgreement) { 162 1 : contributorAgreementsBuilder().put(contributorAgreement.getName(), contributorAgreement); 163 1 : return this; 164 : } 165 : 166 : public Builder addNotifySection(NotifyConfig notifyConfig) { 167 3 : notifySectionsBuilder().put(notifyConfig.getName(), notifyConfig); 168 3 : return this; 169 : } 170 : 171 : public Builder addLabelSection(LabelType labelType) { 172 152 : labelSectionsBuilder().put(labelType.getName(), labelType); 173 152 : return this; 174 : } 175 : 176 : public Builder addSubmitRequirementSection(SubmitRequirement submitRequirement) { 177 5 : submitRequirementSectionsBuilder().put(submitRequirement.name(), submitRequirement); 178 5 : return this; 179 : } 180 : 181 : public abstract Builder setMimeTypes(ConfiguredMimeTypes value); 182 : 183 : public Builder addSubscribeSection(SubscribeSection subscribeSection) { 184 3 : subscribeSectionsBuilder().put(subscribeSection.project(), subscribeSection); 185 3 : return this; 186 : } 187 : 188 : public Builder addCommentLinkSection(StoredCommentLinkInfo storedCommentLinkInfo) { 189 2 : commentLinkSectionsBuilder().put(storedCommentLinkInfo.getName(), storedCommentLinkInfo); 190 2 : return this; 191 : } 192 : 193 : public abstract Builder setRulesId(Optional<ObjectId> value); 194 : 195 : public abstract Builder setRevision(Optional<ObjectId> value); 196 : 197 : public abstract Builder setMaxObjectSizeLimit(long value); 198 : 199 : public abstract Builder setCheckReceivedObjects(boolean value); 200 : 201 : public abstract ImmutableMap.Builder<String, ImmutableList<String>> 202 : extensionPanelSectionsBuilder(); 203 : 204 : public Builder setExtensionPanelSections(Map<String, List<String>> value) { 205 152 : value 206 152 : .entrySet() 207 152 : .forEach( 208 : e -> 209 1 : extensionPanelSectionsBuilder() 210 1 : .put(e.getKey(), ImmutableList.copyOf(e.getValue()))); 211 152 : return this; 212 : } 213 : 214 : abstract ImmutableMap.Builder<String, String> pluginConfigsBuilder(); 215 : 216 : public Builder addPluginConfig(String pluginName, String pluginConfig) { 217 4 : pluginConfigsBuilder().put(pluginName, pluginConfig); 218 4 : return this; 219 : } 220 : 221 : abstract ImmutableMap.Builder<String, String> projectLevelConfigsBuilder(); 222 : 223 : abstract ImmutableMap.Builder<String, ImmutableConfig> parsedProjectLevelConfigsBuilder(); 224 : 225 : public Builder addProjectLevelConfig(String configFileName, String config) { 226 3 : projectLevelConfigsBuilder().put(configFileName, config); 227 : try { 228 3 : parsedProjectLevelConfigsBuilder().put(configFileName, ImmutableConfig.parse(config)); 229 0 : } catch (ConfigInvalidException e) { 230 0 : logger.atInfo().withCause(e).log("Config for %s not parsable", configFileName); 231 3 : } 232 3 : return this; 233 : } 234 : 235 : public abstract CachedProjectConfig build(); 236 : 237 : protected abstract ImmutableMap.Builder<AccountGroup.UUID, GroupReference> groupsBuilder(); 238 : 239 : protected abstract ImmutableSortedMap.Builder<String, AccessSection> accessSectionsBuilder(); 240 : 241 : protected abstract ImmutableMap.Builder<String, ContributorAgreement> 242 : contributorAgreementsBuilder(); 243 : 244 : protected abstract ImmutableMap.Builder<String, NotifyConfig> notifySectionsBuilder(); 245 : 246 : protected abstract ImmutableMap.Builder<String, LabelType> labelSectionsBuilder(); 247 : 248 : protected abstract ImmutableMap.Builder<String, SubmitRequirement> 249 : submitRequirementSectionsBuilder(); 250 : 251 : protected abstract ImmutableMap.Builder<Project.NameKey, SubscribeSection> 252 : subscribeSectionsBuilder(); 253 : 254 : protected abstract ImmutableMap.Builder<String, StoredCommentLinkInfo> 255 : commentLinkSectionsBuilder(); 256 : } 257 : 258 : private static ImmutableList<SubscribeSection> filterSubscribeSectionsByBranch( 259 : Collection<SubscribeSection> allSubscribeSections, BranchNameKey branch) { 260 65 : ImmutableList.Builder<SubscribeSection> ret = ImmutableList.builder(); 261 65 : for (SubscribeSection s : allSubscribeSections) { 262 2 : if (s.appliesTo(branch)) { 263 2 : ret.add(s); 264 : } 265 2 : } 266 65 : return ret.build(); 267 : } 268 : }