blob: f7a883e2a9720b8f8343a5abf19c9f69103e2433 [file] [log] [blame]
// Copyright (C) 2021 The Android Open Source Project
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package com.google.gerrit.entities;
import com.google.auto.value.AutoValue;
import com.google.common.collect.ImmutableList;
import java.util.Optional;
/** Result of evaluating a submit requirement expression on a given Change. */
@AutoValue
public abstract class SubmitRequirementExpressionResult {
/**
* Entity detailing the result of evaluating a Submit requirement expression. Contains an empty
* {@link Optional} if {@link #status()} is equal to {@link Status#ERROR}.
*/
public abstract Optional<PredicateResult> predicateResult();
public abstract Optional<String> errorMessage();
public Status status() {
if (predicateResult().isPresent()) {
return predicateResult().get().status() ? Status.PASS : Status.FAIL;
}
return Status.ERROR;
}
public static SubmitRequirementExpressionResult create(PredicateResult predicateResult) {
return new AutoValue_SubmitRequirementExpressionResult(
Optional.of(predicateResult), Optional.empty());
}
public static SubmitRequirementExpressionResult error(String errorMessage) {
return new AutoValue_SubmitRequirementExpressionResult(
Optional.empty(), Optional.of(errorMessage));
}
/**
* Returns a list of leaf predicate results whose {@link PredicateResult#status()} is true. If
* {@link #status()} is equal to {@link Status#ERROR}, an empty list is returned.
*/
public ImmutableList<PredicateResult> getPassingAtoms() {
if (predicateResult().isPresent()) {
return predicateResult().get().getAtoms(/* status= */ true);
}
return ImmutableList.of();
}
/**
* Returns a list of leaf predicate results whose {@link PredicateResult#status()} is false. If
* {@link #status()} is equal to {@link Status#ERROR}, an empty list is returned.
*/
public ImmutableList<PredicateResult> getFailingAtoms() {
if (predicateResult().isPresent()) {
return predicateResult().get().getAtoms(/* status= */ false);
}
return ImmutableList.of();
}
public enum Status {
/** Submit requirement expression is fulfilled for a given change. */
PASS,
/** Submit requirement expression is failing for a given change. */
FAIL,
/** Submit requirement expression contains invalid syntax and is not parsable. */
ERROR
}
/**
* Entity detailing the result of evaluating a predicate.
*
* <p>Example - branch:refs/heads/foo and has:unresolved
*
* <p>The above predicate is an "And" predicate having two child predicates:
*
* <ul>
* <li>branch:refs/heads/foo
* <li>has:unresolved
* </ul>
*
* <p>Each child predicate as well as the parent contains the result of its evaluation.
*/
@AutoValue
public abstract static class PredicateResult {
abstract ImmutableList<PredicateResult> childPredicateResults();
public abstract String predicateString();
/** true if the predicate is passing for a given change. */
abstract boolean status();
/**
* Returns the list of leaf {@link PredicateResult} whose {@link #status()} is equal to the
* {@code status} parameter.
*/
ImmutableList<PredicateResult> getAtoms(boolean status) {
ImmutableList.Builder<PredicateResult> atomsList = ImmutableList.builder();
getAtomsRecursively(atomsList, status);
return atomsList.build();
}
private void getAtomsRecursively(ImmutableList.Builder<PredicateResult> list, boolean status) {
if (childPredicateResults().isEmpty() && status() == status) {
list.add(this);
return;
}
childPredicateResults().forEach(c -> c.getAtomsRecursively(list, status));
}
public static Builder builder() {
return new AutoValue_SubmitRequirementExpressionResult_PredicateResult.Builder();
}
@AutoValue.Builder
public abstract static class Builder {
public abstract Builder childPredicateResults(ImmutableList<PredicateResult> value);
protected abstract ImmutableList.Builder<PredicateResult> childPredicateResultsBuilder();
public abstract Builder predicateString(String value);
public abstract Builder status(boolean value);
public Builder addChildPredicateResult(PredicateResult result) {
childPredicateResultsBuilder().add(result);
return this;
}
public abstract PredicateResult build();
}
}
}