protected void validatePipeline()

in core/cocoon-pipeline/cocoon-pipeline-impl/src/main/java/org/apache/cocoon/components/pipeline/impl/AbstractCachingProcessingPipeline.java [548:720]


    protected void validatePipeline(Environment environment) throws ProcessingException {

        this.completeResponseIsCached = this.cacheCompleteResponse;
        this.fromCacheKey = this.toCacheKey.copy();
        this.firstProcessedTransformerIndex = this.firstNotCacheableTransformerIndex;

        boolean finished = false;
        while (this.fromCacheKey != null && !finished) {
            finished = true;

            final CachedResponse response = this.cache.get(this.fromCacheKey);

            // now test validity
            if (response != null) {
                if (getLogger().isDebugEnabled()) {
                    getLogger().debug("Found cached response for '" + environment.getURI() +
                            "' using key: " + this.fromCacheKey);
                }

                boolean responseIsValid = true;
                boolean responseIsUsable = true;

                // See if we have an explicit "expires" setting. If so,
                // and if it's still fresh, we're done.
                Long responseExpires = response.getExpires();

                if (responseExpires != null) {
                    if (getLogger().isDebugEnabled()) {
                        getLogger().debug("Expires time found for " + environment.getURI());
                    }

                    if (responseExpires.longValue() > System.currentTimeMillis()) {
                        if (getLogger().isDebugEnabled()) {
                            getLogger().debug("Expires time still fresh for " + environment.getURI() +
                                    ", ignoring all other cache settings. This entry expires on "+
                                    new Date(responseExpires.longValue()));
                        }
                        this.cachedResponse = response;
                        return;
                    } else {
                        if (getLogger().isDebugEnabled()) {
                            getLogger().debug("Expires time has expired for " + environment.getURI() +
                                    ", regenerating content.");
                        }

                        // If an expires parameter was provided, use it. If this parameter is not available
                        // it means that the sitemap was modified, and the old expires value is not valid
                        // anymore.
                        if (expires != 0) {
                            if (this.getLogger().isDebugEnabled())
                                this.getLogger().debug("Refreshing expires informations");
                            response.setExpires(new Long(expires + System.currentTimeMillis()));
                        } else {
                            if (this.getLogger().isDebugEnabled())
                                this.getLogger().debug("No expires defined anymore for this object, setting it to no expires");
                            response.setExpires(null);
                        }
                    }
                } else {
                    // The response had no expires informations. See if it needs to be set (i.e. because the configuration has changed)
                    if (expires != 0) {
                        if (this.getLogger().isDebugEnabled())
                            this.getLogger().debug("Setting a new expires object for this resource");
                        response.setExpires(new Long(expires + System.currentTimeMillis()));
                    }
                }

                SourceValidity[] fromCacheValidityObjects = response.getValidityObjects();

                int i = 0;
                while (responseIsValid && i < fromCacheValidityObjects.length) {
                    // BH Check if validities[i] is null, may happen
                    //    if exception was thrown due to malformed content
                    SourceValidity validity = fromCacheValidityObjects[i];
                    int valid = validity == null ? SourceValidity.INVALID : validity.isValid();
                    if (valid == SourceValidity.UNKNOWN) {
                        // Don't know if valid, make second test
                        validity = getValidityForInternalPipeline(i);
                        if (validity != null) {
                            valid = fromCacheValidityObjects[i].isValid(validity);
                            if (valid == SourceValidity.UNKNOWN) {
                                validity = null;
                            }
                        }
                    }

                    if (valid != SourceValidity.VALID) {
                        responseIsValid = false;
                        // update validity
                        if (validity == null) {
                            responseIsUsable = false;
                            if (getLogger().isDebugEnabled()) {
                                getLogger().debug("validatePipeline: responseIsUsable is false, valid=" +
                                                  valid + " at index " + i);
                            }
                        } else {
                            if (getLogger().isDebugEnabled()) {
                                getLogger().debug("validatePipeline: responseIsValid is false due to " +
                                                  validity);
                            }
                        }
                    } else {
                        i++;
                    }
                }

                if (responseIsValid) {
                    if (getLogger().isDebugEnabled()) {
                        getLogger().debug("validatePipeline: using valid cached content for '" +
                                          environment.getURI() + "'.");
                    }

                    // we are valid, ok that's it
                    this.cachedResponse = response;
                    this.toCacheSourceValidities = fromCacheValidityObjects;
                } else {
                    if (getLogger().isDebugEnabled()) {
                        getLogger().debug("validatePipeline: cached content is invalid for '" +
                                          environment.getURI() + "'.");
                    }
                    // we are not valid!

                    if (!responseIsUsable) {
                        // we could not compare, because we got no
                        // validity object, so shorten pipeline key
                        if (i > 0) {
                            int deleteCount = fromCacheValidityObjects.length - i;
                            if (i > 0 && i <= firstNotCacheableTransformerIndex + 1) {
                                this.firstNotCacheableTransformerIndex = i-1;
                            }
                            for(int x=0; x < deleteCount; x++) {
                                this.toCacheKey.removeLastKey();
                            }
                        } else {
                            this.toCacheKey = null;
                        }
                        this.cacheCompleteResponse = false;
                    } else {
                        // the entry is invalid, remove it
                        this.cache.remove(this.fromCacheKey);
                    }

                    // try a shorter key
                    if (i > 0) {
                        this.fromCacheKey.removeLastKey();
                        if (!this.completeResponseIsCached) {
                            this.firstProcessedTransformerIndex--;
                        }
                    } else {
                        this.fromCacheKey = null;
                    }

                    finished = false;
                    this.completeResponseIsCached = false;
                }
            } else {
                // check if there might be one being generated
                if (!waitForLock(this.fromCacheKey)) {
                    finished = false;
                    continue;
                }

                // no cached response found
                if (getLogger().isDebugEnabled()) {
                    getLogger().debug("Cached response not found for '" + environment.getURI() +
                                      "' using key: " +  this.fromCacheKey);
                }

                finished = setupFromCacheKey();
                this.completeResponseIsCached = false;
            }
        }
    }