{
AbstractStorageItem item = null;
AbstractStorageItem remoteItem = null;
// proxyMode and request.localOnly decides 1st
ItemNotFoundException noRemoteAccessReason = null;
try {
shouldTryRemote(request);
}
catch (ItemNotFoundException e) {
noRemoteAccessReason = e;
}
if (noRemoteAccessReason == null) {
for (RequestStrategy strategy : getRegisteredStrategies().values()) {
try {
strategy.onRemoteAccess(this, request, localItem);
}
catch (ItemNotFoundException e) {
noRemoteAccessReason = e;
// escape
break;
}
}
}
if (noRemoteAccessReason == null) {
// we are able to go remote
if (localItem == null || request.isRequestAsExpired() || isOld(localItem)) {
// we should go remote coz we have no local copy or it is old
try {
boolean shouldGetRemote = false;
if (localItem != null) {
if (log.isDebugEnabled()) {
log.debug(
"Item " + request.toString()
+ " is old, checking for newer file on remote then local: "
+ new Date(localItem.getModified()));
}
// check is the remote newer than the local one
try {
shouldGetRemote = doCheckRemoteItemExistence(localItem, request);
if (!shouldGetRemote) {
markItemRemotelyChecked(localItem);
if (log.isDebugEnabled()) {
log.debug(
"No newer version of item " + request.toString() + " found on remote storage.");
}
}
else {
if (log.isDebugEnabled()) {
log.debug(
"Newer version of item " + request.toString() + " is found on remote storage.");
}
}
}
catch (RemoteStorageException ex) {
// NEXUS-4593 HTTP status 403 should not lead to autoblock
if (!(ex instanceof RemoteAccessDeniedException)
&& !(ex instanceof RemoteStorageTransportException)) {
autoBlockProxying(ex);
}
if (ex instanceof RemoteStorageTransportException) {
throw ex;
}
// do not go remote, but we did not mark it as "remote checked" also.
// let the user do proper setup and probably it will try again
shouldGetRemote = false;
}
catch (IOException ex) {
// do not go remote, but we did not mark it as "remote checked" also.
// let the user do proper setup and probably it will try again
shouldGetRemote = false;
}
}
else {
// we have no local copy of it, try to get it unconditionally
shouldGetRemote = true;
}
if (shouldGetRemote) {
// this will GET it unconditionally
try {
remoteItem = doRetrieveRemoteItem(request);
if (log.isDebugEnabled()) {
log.debug("Item " + request.toString() + " found in remote storage.");
}
}
catch (StorageException ex) {
if (ex instanceof RemoteStorageException
// NEXUS-4593 HTTP status 403 should not lead to autoblock
&& !(ex instanceof RemoteAccessDeniedException)
&& !(ex instanceof RemoteStorageTransportException)) {
autoBlockProxying(ex);
}
if (ex instanceof RemoteStorageTransportException
|| ex instanceof LocalStorageEOFException) {
throw ex;
}
if (ex instanceof RemoteAccessDeniedException) {
log.debug("Error code 403 {} obtaining {} from remote storage.", ex.getMessage(), request);
request.getRequestContext().put("remote.accessDeniedException", ex);
}
remoteItem = null;
// cleanup if any remnant is here
try {
if (localItem == null) {
deleteItem(false, request);
}
}
catch (ItemNotFoundException ex1) {
// ignore
}
catch (UnsupportedStorageOperationException ex2) {
// will not happen
}
}
}
else {
remoteItem = null;
}
}
catch (ItemNotFoundException ex) {
if (log.isDebugEnabled()) {
log.debug("Item " + request.toString() + " not found in remote storage.");
}
remoteItem = null;
}
}
if (localItem == null && remoteItem == null) {
// we dont have neither one, NotFoundException
if (log.isDebugEnabled()) {
log.debug(
"Item " + request.toString()
+ " does not exist in local or remote storage, throwing ItemNotFoundException.");
}
throw new ItemNotFoundException(reasonFor(request, this,
"Path %s not found in local nor in remote storage of %s", request.getRequestPath(),
this));
}
else if (localItem != null && remoteItem == null) {
// simple: we have local but not remote (coz we are offline or coz it is not newer)
if (log.isDebugEnabled()) {
log.debug(
"Item " + request.toString()
+ " does exist in local storage and is fresh, returning local one.");
}
item = localItem;
}
else {
// the fact that remoteItem != null means we _have_ to return that one
// OR: we had no local copy
// OR: remoteItem is for sure newer (look above)
item = remoteItem;
}
}
else {
// we cannot go remote
if (localItem != null) {
if (log.isDebugEnabled()) {
log.debug(
"Item " + request.toString() + " does exist locally and cannot go remote, returning local one.");
}
item = localItem;
}
else {
if (log.isDebugEnabled()) {
log.debug(
"Item " + request.toString()
+ " does not exist locally and cannot go remote, throwing ItemNotFoundException.");
}
throw new ItemNotFoundException(ItemNotFoundException.reasonFor(request, this,
noRemoteAccessReason.getMessage()), noRemoteAccessReason);
}
}
return item;
}