spring ResourceHolderSynchronization 源码

  • 2022-08-08
  • 浏览 (370)

spring ResourceHolderSynchronization 代码

文件路径:/spring-tx/src/main/java/org/springframework/transaction/support/ResourceHolderSynchronization.java

/*
 * Copyright 2002-2018 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.transaction.support;

/**
 * {@link TransactionSynchronization} implementation that manages a
 * {@link ResourceHolder} bound through {@link TransactionSynchronizationManager}.
 *
 * @author Juergen Hoeller
 * @since 2.5.5
 * @param <H> the resource holder type
 * @param <K> the resource key type
 */
public abstract class ResourceHolderSynchronization<H extends ResourceHolder, K>
		implements TransactionSynchronization {

	private final H resourceHolder;

	private final K resourceKey;

	private volatile boolean holderActive = true;


	/**
	 * Create a new ResourceHolderSynchronization for the given holder.
	 * @param resourceHolder the ResourceHolder to manage
	 * @param resourceKey the key to bind the ResourceHolder for
	 * @see TransactionSynchronizationManager#bindResource
	 */
	public ResourceHolderSynchronization(H resourceHolder, K resourceKey) {
		this.resourceHolder = resourceHolder;
		this.resourceKey = resourceKey;
	}


	@Override
	public void suspend() {
		if (this.holderActive) {
			TransactionSynchronizationManager.unbindResource(this.resourceKey);
		}
	}

	@Override
	public void resume() {
		if (this.holderActive) {
			TransactionSynchronizationManager.bindResource(this.resourceKey, this.resourceHolder);
		}
	}

	@Override
	public void flush() {
		flushResource(this.resourceHolder);
	}

	@Override
	public void beforeCommit(boolean readOnly) {
	}

	@Override
	public void beforeCompletion() {
		if (shouldUnbindAtCompletion()) {
			TransactionSynchronizationManager.unbindResource(this.resourceKey);
			this.holderActive = false;
			if (shouldReleaseBeforeCompletion()) {
				releaseResource(this.resourceHolder, this.resourceKey);
			}
		}
	}

	@Override
	public void afterCommit() {
		if (!shouldReleaseBeforeCompletion()) {
			processResourceAfterCommit(this.resourceHolder);
		}
	}

	@Override
	public void afterCompletion(int status) {
		if (shouldUnbindAtCompletion()) {
			boolean releaseNecessary = false;
			if (this.holderActive) {
				// The thread-bound resource holder might not be available anymore,
				// since afterCompletion might get called from a different thread.
				this.holderActive = false;
				TransactionSynchronizationManager.unbindResourceIfPossible(this.resourceKey);
				this.resourceHolder.unbound();
				releaseNecessary = true;
			}
			else {
				releaseNecessary = shouldReleaseAfterCompletion(this.resourceHolder);
			}
			if (releaseNecessary) {
				releaseResource(this.resourceHolder, this.resourceKey);
			}
		}
		else {
			// Probably a pre-bound resource...
			cleanupResource(this.resourceHolder, this.resourceKey, (status == STATUS_COMMITTED));
		}
		this.resourceHolder.reset();
	}


	/**
	 * Return whether this holder should be unbound at completion
	 * (or should rather be left bound to the thread after the transaction).
	 * <p>The default implementation returns {@code true}.
	 */
	protected boolean shouldUnbindAtCompletion() {
		return true;
	}

	/**
	 * Return whether this holder's resource should be released before
	 * transaction completion ({@code true}) or rather after
	 * transaction completion ({@code false}).
	 * <p>Note that resources will only be released when they are
	 * unbound from the thread ({@link #shouldUnbindAtCompletion()}).
	 * <p>The default implementation returns {@code true}.
	 * @see #releaseResource
	 */
	protected boolean shouldReleaseBeforeCompletion() {
		return true;
	}

	/**
	 * Return whether this holder's resource should be released after
	 * transaction completion ({@code true}).
	 * <p>The default implementation returns {@code !shouldReleaseBeforeCompletion()},
	 * releasing after completion if no attempt was made before completion.
	 * @see #releaseResource
	 */
	protected boolean shouldReleaseAfterCompletion(H resourceHolder) {
		return !shouldReleaseBeforeCompletion();
	}

	/**
	 * Flush callback for the given resource holder.
	 * @param resourceHolder the resource holder to flush
	 */
	protected void flushResource(H resourceHolder) {
	}

	/**
	 * After-commit callback for the given resource holder.
	 * Only called when the resource hasn't been released yet
	 * ({@link #shouldReleaseBeforeCompletion()}).
	 * @param resourceHolder the resource holder to process
	 */
	protected void processResourceAfterCommit(H resourceHolder) {
	}

	/**
	 * Release the given resource (after it has been unbound from the thread).
	 * @param resourceHolder the resource holder to process
	 * @param resourceKey the key that the ResourceHolder was bound for
	 */
	protected void releaseResource(H resourceHolder, K resourceKey) {
	}

	/**
	 * Perform a cleanup on the given resource (which is left bound to the thread).
	 * @param resourceHolder the resource holder to process
	 * @param resourceKey the key that the ResourceHolder was bound for
	 * @param committed whether the transaction has committed ({@code true})
	 * or rolled back ({@code false})
	 */
	protected void cleanupResource(H resourceHolder, K resourceKey, boolean committed) {
	}

}

相关信息

spring 源码目录

相关文章

spring AbstractPlatformTransactionManager 源码

spring AbstractTransactionStatus 源码

spring CallbackPreferringPlatformTransactionManager 源码

spring DefaultTransactionDefinition 源码

spring DefaultTransactionStatus 源码

spring DelegatingTransactionDefinition 源码

spring ResourceHolder 源码

spring ResourceHolderSupport 源码

spring ResourceTransactionDefinition 源码

spring ResourceTransactionManager 源码

0  赞