/* Copyright (c) 2001 - 2011 TOPP - www.openplans.org. All rights reserved.
* This code is licensed under the GPL 2.0 license, available at the root
* application directory.
*/
package org.geoserver.gwc.layer;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
import org.apache.commons.lang.builder.EqualsBuilder;
import org.apache.commons.lang.builder.HashCodeBuilder;
import org.geoserver.catalog.CoverageInfo;
import org.geoserver.catalog.FeatureTypeInfo;
import org.geoserver.catalog.LayerGroupInfo;
import org.geoserver.catalog.LayerInfo;
import org.geoserver.catalog.MetadataMap;
import org.geoserver.catalog.ResourceInfo;
import org.geoserver.catalog.StyleInfo;
import org.geoserver.gwc.config.GWCConfig;
import org.springframework.util.Assert;
public class GeoServerTileLayerInfo {
private static final String CONFIG_KEY_ENABLED = "GWC.enabled";
private static final String CONFIG_KEY_GUTTER = "GWC.gutter";
private static final String CONFIG_KEY_GRIDSETS = "GWC.gridSets";
private static final String CONFIG_KEY_METATILING_X = "GWC.metaTilingX";
private static final String CONFIG_KEY_METATILING_Y = "GWC.metaTilingY";
private static final String CONFIG_KEY_FORMATS = "GWC.cacheFormats";
private static final String CONFIG_KEY_AUTO_CACHE_STYLES = "GWC.autoCacheStyles";
private static final String CONFIG_KEY_CACHED_STYLES = "GWC.cachedNonDefaultStyles";
private int gutter;
private boolean enabled;
private Set<String> cachedGridSetIds;
private int metaTilingX;
private int metaTilingY;
private Set<String> mimeFormats;
private boolean autoCacheStyles;
private Set<String> cachedStyles;
private boolean dirty;
private static Set<String> unmarshalSet(final String listStr) {
Set<String> unmarshalled = new HashSet<String>(Arrays.asList(listStr.split(",")));
return unmarshalled;
}
private static String marshalList(final Collection<String> list) {
StringBuilder sb = new StringBuilder();
for (Iterator<String> i = list.iterator(); i.hasNext();) {
sb.append(i.next());
if (i.hasNext()) {
sb.append(",");
}
}
return sb.toString();
}
@SuppressWarnings("unchecked")
public static GeoServerTileLayerInfo create(final LayerInfo layerInfo, final GWCConfig defaults) {
ResourceInfo resourceInfo = layerInfo.getResource();
MetadataMap metadataMap = layerInfo.getMetadata();
GeoServerTileLayerInfo info = create(metadataMap, defaults);
if (metadataMap.containsKey(CONFIG_KEY_FORMATS)) {
String mimeFormatsStr = metadataMap.get(CONFIG_KEY_FORMATS, String.class);
Set<String> mimeFormats = unmarshalSet(mimeFormatsStr);
info.setMimeFormats(mimeFormats);
} else if (resourceInfo instanceof FeatureTypeInfo) {
info.setMimeFormats(defaults.getDefaultVectorCacheFormats());
info.setDirty(true);
} else if (resourceInfo instanceof CoverageInfo) {
info.setMimeFormats(defaults.getDefaultCoverageCacheFormats());
info.setDirty(true);
} else {
info.setMimeFormats(defaults.getDefaultOtherCacheFormats());
info.setDirty(true);
}
boolean autoCacheStyles = defaults.isCacheNonDefaultStyles();
if (metadataMap.containsKey(CONFIG_KEY_AUTO_CACHE_STYLES)) {
autoCacheStyles = metadataMap.get(CONFIG_KEY_AUTO_CACHE_STYLES, Boolean.class)
.booleanValue();
} else {
info.setDirty(true);
}
info.setAutoCacheStyles(autoCacheStyles);
info.setCachedStyles(Collections.EMPTY_SET);
if (metadataMap.containsKey(CONFIG_KEY_CACHED_STYLES)) {
String cachedStylesStr = metadataMap.get(CONFIG_KEY_CACHED_STYLES, String.class);
Set<String> cachedStyles = unmarshalSet(cachedStylesStr);
info.setCachedStyles(cachedStyles);
} else {
if (autoCacheStyles) {
Set<StyleInfo> alternateStyles = layerInfo.getStyles();
if (alternateStyles != null && alternateStyles.size() > 0) {
Set<String> cachedStyles = new HashSet<String>();
for (StyleInfo si : alternateStyles) {
if (si != null) {
cachedStyles.add(si.getName());
}
}
info.setCachedStyles(cachedStyles);
info.setDirty(true);
}
}
}
return info;
}
@SuppressWarnings("unchecked")
public static GeoServerTileLayerInfo create(final LayerGroupInfo layerInfo,
final GWCConfig defaults) {
MetadataMap metadataMap = layerInfo.getMetadata();
GeoServerTileLayerInfo info = create(metadataMap, defaults);
if (metadataMap.containsKey(CONFIG_KEY_FORMATS)) {
String mimeFormatsStr = metadataMap.get(CONFIG_KEY_FORMATS, String.class);
Set<String> mimeFormats = unmarshalSet(mimeFormatsStr);
info.setMimeFormats(mimeFormats);
} else {
info.setMimeFormats(defaults.getDefaultOtherCacheFormats());
info.setDirty(true);
}
info.setCachedStyles(Collections.EMPTY_SET);
return info;
}
/**
* Factory method based on a {@link LayerInfo}'s or {@link LayerGroupInfo}'s metadata map
*
* @param resourceInfo
*
* @param metadataMap
* @return
*/
private static GeoServerTileLayerInfo create(final MetadataMap metadataMap,
final GWCConfig defaults) {
GeoServerTileLayerInfo info = new GeoServerTileLayerInfo();
// whether the config needs to be saved
boolean dirty = false;
boolean enabled = defaults.isCacheLayersByDefault();
if (metadataMap.containsKey(CONFIG_KEY_ENABLED)) {
enabled = metadataMap.get(CONFIG_KEY_ENABLED, Boolean.class).booleanValue();
} else {
dirty = true;
}
info.setEnabled(enabled);
info.setGutter(defaults.getGutter());
if (metadataMap.containsKey(CONFIG_KEY_GUTTER)) {
int gutter = metadataMap.get(CONFIG_KEY_GUTTER, Integer.class).intValue();
info.setGutter(gutter);
} else {
dirty = true;
}
info.setCachedGridSetIds(defaults.getDefaultCachingGridSetIds());
if (metadataMap.containsKey(CONFIG_KEY_GRIDSETS)) {
String gridsets = metadataMap.get(CONFIG_KEY_GRIDSETS, String.class);
Set<String> gridSetIds = unmarshalSet(gridsets);
info.setCachedGridSetIds(gridSetIds);
} else {
dirty = true;
}
info.setMetaTilingX(defaults.getMetaTilingX());
info.setMetaTilingY(defaults.getMetaTilingY());
if (metadataMap.containsKey(CONFIG_KEY_METATILING_X)) {
info.setMetaTilingX(metadataMap.get(CONFIG_KEY_METATILING_X, Integer.class).intValue());
} else {
dirty = true;
}
if (metadataMap.containsKey(CONFIG_KEY_METATILING_Y)) {
info.setMetaTilingY(metadataMap.get(CONFIG_KEY_METATILING_Y, Integer.class).intValue());
} else {
dirty = true;
}
info.setDirty(dirty);
return info;
}
public void setDirty(boolean dirty) {
this.dirty = dirty;
}
/**
* @return whether the config needs to be saved because it's out of sync with the
* layer(group)info metadatamap
*/
public boolean isDirty() {
return dirty;
}
public void saveTo(MetadataMap metadata) {
final boolean enabled = this.isEnabled();
final int gutter = this.getGutter();
final Set<String> cachedGridSetIds = this.getCachedGridSetIds();
final int metaTilingX = this.getMetaTilingX();
final int metaTilingY = this.getMetaTilingY();
final Set<String> mimeFormats = this.getMimeFormats();
final Set<String> cachedStyles = this.getCachedStyles();
metadata.put(CONFIG_KEY_ENABLED, Boolean.valueOf(enabled));
metadata.put(CONFIG_KEY_GUTTER, Integer.valueOf(gutter));
metadata.put(CONFIG_KEY_GRIDSETS, marshalList(cachedGridSetIds));
metadata.put(CONFIG_KEY_METATILING_X, Integer.valueOf(metaTilingX));
metadata.put(CONFIG_KEY_METATILING_Y, Integer.valueOf(metaTilingY));
metadata.put(CONFIG_KEY_FORMATS, marshalList(mimeFormats));
metadata.put(CONFIG_KEY_AUTO_CACHE_STYLES, autoCacheStyles);
if (cachedStyles.size() > 0) {
metadata.put(CONFIG_KEY_CACHED_STYLES, marshalList(cachedStyles));
}
}
public Set<String> getCachedStyles() {
return cachedStyles;
}
public void setCachedStyles(Set<String> cachedStyles) {
this.cachedStyles = new HashSet<String>(cachedStyles);
}
public Set<String> getMimeFormats() {
return mimeFormats;
}
public void setMimeFormats(Set<String> mimeFormats) {
this.mimeFormats = new HashSet<String>(mimeFormats);
}
public int getMetaTilingX() {
return metaTilingX;
}
public int getMetaTilingY() {
return metaTilingY;
}
public void setMetaTilingY(int metaTilingY) {
Assert.isTrue(metaTilingY > 0);
this.metaTilingY = metaTilingY;
}
public void setMetaTilingX(int metaTilingX) {
Assert.isTrue(metaTilingX > 0);
this.metaTilingX = metaTilingX;
}
public void setCachedGridSetIds(Set<String> cachedGridSetIds) {
this.cachedGridSetIds = cachedGridSetIds;
}
@SuppressWarnings("unchecked")
public Set<String> getCachedGridSetIds() {
return cachedGridSetIds == null ? Collections.EMPTY_SET : cachedGridSetIds;
}
public void setEnabled(boolean enabled) {
this.enabled = enabled;
}
public boolean isEnabled() {
return enabled;
}
public void setGutter(int gutter) {
this.gutter = gutter;
}
public int getGutter() {
return gutter;
}
@Override
public boolean equals(Object other) {
return EqualsBuilder.reflectionEquals(this, other);
}
@Override
public int hashCode() {
return HashCodeBuilder.reflectionHashCode(this);
}
public boolean isAutoCacheStyles() {
return autoCacheStyles;
}
public void setAutoCacheStyles(boolean autoCacheStyles) {
this.autoCacheStyles = autoCacheStyles;
}
}