spring CompositeRequestCondition 源码
spring CompositeRequestCondition 代码
文件路径:/spring-webmvc/src/main/java/org/springframework/web/servlet/mvc/condition/CompositeRequestCondition.java
/*
* Copyright 2002-2021 the original author or authors.
*
* 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
*
* https://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 org.springframework.web.servlet.mvc.condition;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import jakarta.servlet.http.HttpServletRequest;
import org.springframework.lang.Nullable;
import org.springframework.util.Assert;
import org.springframework.util.ObjectUtils;
/**
* Implements the {@link RequestCondition} contract by delegating to multiple
* {@code RequestCondition} types and using a logical conjunction ({@code ' && '}) to
* ensure all conditions match a given request.
*
* <p>When {@code CompositeRequestCondition} instances are combined or compared
* they are expected to (a) contain the same number of conditions and (b) that
* conditions in the respective index are of the same type. It is acceptable to
* provide {@code null} conditions or no conditions at all to the constructor.
*
* @author Rossen Stoyanchev
* @since 3.2
*/
public class CompositeRequestCondition extends AbstractRequestCondition<CompositeRequestCondition> {
private final RequestConditionHolder[] requestConditions;
/**
* Create an instance with 0 or more {@code RequestCondition} types. It is
* important to create {@code CompositeRequestCondition} instances with the
* same number of conditions so they may be compared and combined.
* It is acceptable to provide {@code null} conditions.
*/
public CompositeRequestCondition(RequestCondition<?>... requestConditions) {
this.requestConditions = wrap(requestConditions);
}
private CompositeRequestCondition(RequestConditionHolder[] requestConditions) {
this.requestConditions = requestConditions;
}
private RequestConditionHolder[] wrap(RequestCondition<?>... rawConditions) {
RequestConditionHolder[] wrappedConditions = new RequestConditionHolder[rawConditions.length];
for (int i = 0; i < rawConditions.length; i++) {
wrappedConditions[i] = new RequestConditionHolder(rawConditions[i]);
}
return wrappedConditions;
}
/**
* Whether this instance contains 0 conditions or not.
*/
@Override
public boolean isEmpty() {
return ObjectUtils.isEmpty(this.requestConditions);
}
/**
* Return the underlying conditions (possibly empty but never {@code null}).
*/
public List<RequestCondition<?>> getConditions() {
return unwrap();
}
private List<RequestCondition<?>> unwrap() {
List<RequestCondition<?>> result = new ArrayList<>();
for (RequestConditionHolder holder : this.requestConditions) {
result.add(holder.getCondition());
}
return result;
}
@Override
protected Collection<?> getContent() {
return (!isEmpty() ? getConditions() : Collections.emptyList());
}
@Override
protected String getToStringInfix() {
return " && ";
}
private int getLength() {
return this.requestConditions.length;
}
/**
* If one instance is empty, return the other.
* If both instances have conditions, combine the individual conditions
* after ensuring they are of the same type and number.
*/
@Override
public CompositeRequestCondition combine(CompositeRequestCondition other) {
if (isEmpty() && other.isEmpty()) {
return this;
}
else if (other.isEmpty()) {
return this;
}
else if (isEmpty()) {
return other;
}
else {
assertNumberOfConditions(other);
RequestConditionHolder[] combinedConditions = new RequestConditionHolder[getLength()];
for (int i = 0; i < getLength(); i++) {
combinedConditions[i] = this.requestConditions[i].combine(other.requestConditions[i]);
}
return new CompositeRequestCondition(combinedConditions);
}
}
private void assertNumberOfConditions(CompositeRequestCondition other) {
Assert.isTrue(getLength() == other.getLength(),
"Cannot combine CompositeRequestConditions with a different number of conditions. " +
ObjectUtils.nullSafeToString(this.requestConditions) + " and " +
ObjectUtils.nullSafeToString(other.requestConditions));
}
/**
* Delegate to <em>all</em> contained conditions to match the request and return the
* resulting "matching" condition instances.
* <p>An empty {@code CompositeRequestCondition} matches to all requests.
*/
@Override
@Nullable
public CompositeRequestCondition getMatchingCondition(HttpServletRequest request) {
if (isEmpty()) {
return this;
}
RequestConditionHolder[] matchingConditions = new RequestConditionHolder[getLength()];
for (int i = 0; i < getLength(); i++) {
matchingConditions[i] = this.requestConditions[i].getMatchingCondition(request);
if (matchingConditions[i] == null) {
return null;
}
}
return new CompositeRequestCondition(matchingConditions);
}
/**
* If one instance is empty, the other "wins". If both instances have
* conditions, compare them in the order in which they were provided.
*/
@Override
public int compareTo(CompositeRequestCondition other, HttpServletRequest request) {
if (isEmpty() && other.isEmpty()) {
return 0;
}
else if (isEmpty()) {
return 1;
}
else if (other.isEmpty()) {
return -1;
}
else {
assertNumberOfConditions(other);
for (int i = 0; i < getLength(); i++) {
int result = this.requestConditions[i].compareTo(other.requestConditions[i], request);
if (result != 0) {
return result;
}
}
return 0;
}
}
}
相关信息
相关文章
spring AbstractMediaTypeExpression 源码
spring AbstractNameValueExpression 源码
spring AbstractRequestCondition 源码
spring ConsumesRequestCondition 源码
spring HeadersRequestCondition 源码
spring ParamsRequestCondition 源码
0
赞
热门推荐
-
2、 - 优质文章
-
3、 gate.io
-
8、 golang
-
9、 openharmony
-
10、 Vue中input框自动聚焦