Skip to content

Commit

Permalink
Integrating GWC Configuration changes
Browse files Browse the repository at this point in the history
  • Loading branch information
smithkm committed Feb 17, 2018
1 parent 9b851c1 commit 50b7d5f
Show file tree
Hide file tree
Showing 11 changed files with 115 additions and 120 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,14 @@
import org.apache.wicket.model.ResourceModel;
import org.geoserver.web.data.store.panel.DirectoryParamPanel;
import org.geoserver.web.wicket.ParamResourceModel;
import org.geowebcache.sqlite.MbtilesConfiguration;
import org.geowebcache.sqlite.MbtilesInfo;

/**
* Panel that contains the properties required to configure a MBTiles blob store.
*/
public class MbtilesBlobStorePanel extends SqliteBlobStorePanel<MbtilesConfiguration> {
public class MbtilesBlobStorePanel extends SqliteBlobStorePanel<MbtilesInfo> {

public MbtilesBlobStorePanel(String id, IModel<MbtilesConfiguration> configurationModel) {
public MbtilesBlobStorePanel(String id, IModel<MbtilesInfo> configurationModel) {
super(id, configurationModel);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,27 +6,27 @@

import org.apache.wicket.markup.html.panel.Panel;
import org.apache.wicket.model.IModel;
import org.geowebcache.sqlite.MbtilesConfiguration;
import org.geowebcache.sqlite.MbtilesInfo;

/**
* Defines the MBTiles blob store.
*/
public class MbtilesBlobStoreType implements BlobStoreType<MbtilesConfiguration> {
public class MbtilesBlobStoreType implements BlobStoreType<MbtilesInfo> {

@Override
public Class<MbtilesConfiguration> getConfigClass() {
return MbtilesConfiguration.class;
public Class<MbtilesInfo> getConfigClass() {
return MbtilesInfo.class;
}

@Override
public MbtilesConfiguration newConfigObject() {
MbtilesConfiguration configuration = new MbtilesConfiguration();
public MbtilesInfo newConfigObject() {
MbtilesInfo configuration = new MbtilesInfo();
configuration.setEnabled(true);
return configuration;
}

@Override
public Panel createPanel(String id, IModel<MbtilesConfiguration> model) {
public Panel createPanel(String id, IModel<MbtilesInfo> model) {
return new MbtilesBlobStorePanel(id, model);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,12 +15,12 @@
import org.apache.wicket.model.ResourceModel;
import org.geoserver.web.data.store.panel.DirectoryParamPanel;
import org.geoserver.web.wicket.ParamResourceModel;
import org.geowebcache.sqlite.SqliteConfiguration;
import org.geowebcache.sqlite.SqliteInfo;

/**
* Properties that will be common to all SQLite based blob stores.
*/
abstract class SqliteBlobStorePanel<T extends SqliteConfiguration> extends Panel {
abstract class SqliteBlobStorePanel<T extends SqliteInfo> extends Panel {

public SqliteBlobStorePanel(String id, final IModel<T> configurationModel) {
super(id, configurationModel);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
import org.geowebcache.config.BlobStoreInfo;
import org.geowebcache.config.ConfigurationException;
import org.geowebcache.layer.TileLayer;
import org.geowebcache.sqlite.MbtilesConfiguration;
import org.geowebcache.sqlite.MbtilesInfo;
import org.junit.Test;

import java.lang.reflect.Field;
Expand Down Expand Up @@ -94,7 +94,7 @@ public void testCreatingNewBlobStore() throws ConfigurationException {
tester.executeAjaxEvent("blobConfigContainer:blobStoreForm:save", "click");

// checking if a store with the correct options was instantiated
MbtilesConfiguration configuration = findStore(storeId);
MbtilesInfo configuration = findStore(storeId);
assertThat(configuration, notNullValue());
assertThat(configuration.getRootDirectory(), is("/tmp/gwc"));
assertThat(configuration.getTemplatePath(), is("{grid}/{layer}/{params}/tiles-{z}.sqlite"));
Expand All @@ -114,7 +114,7 @@ public void testCreatingNewBlobStore() throws ConfigurationException {
public void testModifyingAnExistingStore() throws Exception {

// creating an mbtiles store (with the default values)
MbtilesConfiguration originalConfiguration = new MbtilesConfiguration();
MbtilesInfo originalConfiguration = new MbtilesInfo();
originalConfiguration.setRootDirectory("/tmp/gwc");
String storeId = UUID.randomUUID().toString();
// the setId method has package only visibility, so we set the value by reflection
Expand Down Expand Up @@ -144,7 +144,7 @@ public void testModifyingAnExistingStore() throws Exception {

// checking if the store was correctly updated
assertThat(findStore(storeId), nullValue());
MbtilesConfiguration configuration = findStore(updatedStoreId);
MbtilesInfo configuration = findStore(updatedStoreId);
assertThat(configuration, notNullValue());
assertThat(configuration.getTemplatePath(), is("{grid}/{layer}/{params}/{style}/tiles-{z}.sqlite"));

Expand All @@ -159,11 +159,11 @@ public void testModifyingAnExistingStore() throws Exception {
/**
* Helper method that finds a GWC store by is id.
*/
private MbtilesConfiguration findStore(String storeId) {
private MbtilesInfo findStore(String storeId) {
List<BlobStoreInfo> configurations = GWC.get().getBlobStores();
for (BlobStoreInfo candidateConfiguration : configurations) {
if (candidateConfiguration instanceof MbtilesConfiguration && candidateConfiguration.getId().equals(storeId)) {
return (MbtilesConfiguration) candidateConfiguration;
if (candidateConfiguration instanceof MbtilesInfo && candidateConfiguration.getId().equals(storeId)) {
return (MbtilesInfo) candidateConfiguration;
}
}
return null;
Expand Down
129 changes: 58 additions & 71 deletions src/gwc/src/main/java/org/geoserver/gwc/GWC.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Properties;
Expand Down Expand Up @@ -124,6 +125,7 @@
import org.geowebcache.seed.TruncateBboxRequest;
import org.geowebcache.service.Service;
import org.geowebcache.storage.BlobStore;
import org.geowebcache.storage.BlobStoreAggregator;
import org.geowebcache.storage.CompositeBlobStore;
import org.geowebcache.storage.DefaultStorageFinder;
import org.geowebcache.storage.StorageBroker;
Expand Down Expand Up @@ -1541,9 +1543,6 @@ public synchronized void modifyGridSet(final String oldGridSetName, final GridSe
saveConfigurations.add(config);
}

for (BaseConfiguration config : saveConfigurations) {
config.save();
}
} finally {
if(lock != null) {
lock.release();
Expand All @@ -1555,6 +1554,11 @@ XMLConfiguration getXmlConfiguration() {
XMLConfiguration mainConfig = GeoWebCacheExtensions.bean(XMLConfiguration.class);
return mainConfig;
}

private BlobStoreAggregator getBlobStoreAggregator() {
// TODO set this during init instead.
return GeoWebCacheExtensions.bean(BlobStoreAggregator.class);
}

@SuppressWarnings("unchecked")
public Response getResponseEncoder(MimeType responseFormat, RenderedImageMap metaTileMap) {
Expand Down Expand Up @@ -2329,19 +2333,27 @@ static Set<String> getAdvertisedCachedFormats(final PublishedType type, final It
* @return the list of configured blobstores
*/
public List<BlobStoreInfo> getBlobStores() {
BlobStoreConfiguration xmlConfig = getXmlConfiguration();

return new ArrayList<BlobStoreInfo>(xmlConfig.getBlobStores());
BlobStoreAggregator agg = getBlobStoreAggregator();
Iterable<BlobStoreInfo> blobStores = agg.getBlobStores();
if(blobStores instanceof List) {
return (List<BlobStoreInfo>) blobStores;
} else {
ArrayList<BlobStoreInfo> storeInfos = new ArrayList<BlobStoreInfo>(agg.getBlobStoreCount());
blobStores.forEach(storeInfos::add);
return storeInfos;
}
}

/**
* @return the {@link BlobStoreInfo#isDefault() default} blobstore, or {@code null} if there's
* no default
*/
public BlobStoreInfo getDefaultBlobStore() {
BlobStoreConfiguration xmlConfig = getXmlConfiguration();

for (BlobStoreInfo config : xmlConfig.getBlobStores()) {
BlobStoreAggregator agg = getBlobStoreAggregator();

// TODO We should be doing this on the aggregator upstream in GWC

for (BlobStoreInfo config : agg.getBlobStores()) {
if (config.isDefault()) {
return config;
}
Expand All @@ -2353,18 +2365,9 @@ public BlobStoreInfo getDefaultBlobStore() {
* Convenience method to add a new blob store, calling {@link #setBlobStores} the extra
* {@code config}
*/
public void addBlobStore(BlobStoreInfo config) throws ConfigurationException {
checkNotNull(config);

List<BlobStoreInfo> stores = new ArrayList<>(getXmlConfiguration().getBlobStores());
if (config.isDefault()) {
for (BlobStoreInfo c : stores) {
c.setDefault(false);
}
}
stores.add(config);

setBlobStores(stores);
public void addBlobStore(BlobStoreInfo info) throws ConfigurationException {
checkNotNull(info);
getBlobStoreAggregator().addBlobStore(info);
}

/**
Expand All @@ -2374,20 +2377,16 @@ public void addBlobStore(BlobStoreInfo config) throws ConfigurationException {
public void modifyBlobStore(String oldId, BlobStoreInfo config) throws ConfigurationException {
checkNotNull(oldId);
checkNotNull(config);

List<BlobStoreInfo> stores = new ArrayList<>(getXmlConfiguration().getBlobStores());
int index = -1;
for (int i = 0; i < stores.size(); i++) {
BlobStoreInfo c = stores.get(i);
if (oldId.equals(c.getId())) {
index = i;
break;
BlobStoreAggregator agg = getBlobStoreAggregator();

if(config.getName().equals(oldId)) {
agg.modifyBlobStore(config);
} else {
synchronized (agg) {
agg.renameBlobStore(oldId, config.getName());
agg.modifyBlobStore(config);
}
}
if (index > -1) {
stores.set(index, config);
setBlobStores(stores);
}
}

/**
Expand All @@ -2401,19 +2400,20 @@ public void modifyBlobStore(String oldId, BlobStoreInfo config) throws Configura
*/
public void removeBlobStores(Iterable<String> blobStoreIds) throws ConfigurationException {
checkNotNull(blobStoreIds);

Map<String, BlobStoreInfo> stores = Maps.uniqueIndex(new ArrayList<>(
getXmlConfiguration().getBlobStores()), new Function<BlobStoreInfo, String>() {
@Override
public String apply(BlobStoreInfo c) {
return c.getId();

BlobStoreAggregator agg = getBlobStoreAggregator();

LinkedList<Exception> exceptions = new LinkedList<>();
for(String bsName: blobStoreIds) {
try {
agg.removeBlobStore(bsName);
} catch (Exception ex) {
exceptions.add(ex);
}
});
Map<String, BlobStoreInfo> filtered = Maps.filterKeys(stores,
Predicates.not(Predicates.in(ImmutableList.copyOf(blobStoreIds))));

if (!filtered.equals(stores)) {
setBlobStores(new ArrayList<>(filtered.values()));
}
if(!exceptions.isEmpty()) {
Exception ex = exceptions.pop();
exceptions.forEach(ex::addSuppressed);
}
}

Expand All @@ -2434,33 +2434,20 @@ public String apply(BlobStoreInfo c) {
void setBlobStores(List<BlobStoreInfo> stores) throws ConfigurationException {
Preconditions.checkNotNull(stores, "stores is null");

XMLConfiguration xmlConfig = getXmlConfiguration();

CompositeBlobStore compositeBlobStore = getCompositeBlobStore();
BlobStoreAggregator agg = getBlobStoreAggregator();

List<BlobStoreInfo> oldStores = new ArrayList<BlobStoreInfo>(xmlConfig.getBlobStores());

try {
compositeBlobStore.setBlobStores(stores);
} catch (ConfigurationException ce) {
throw ce;
} catch (StorageException se) {
throw new ConfigurationException("Error connecting to BlobStore: " + se.getMessage(),
se);
}
xmlConfig.getBlobStores().clear();
xmlConfig.getBlobStores().addAll(stores);
try {
xmlConfig.save();
} catch (IOException e) {
//undo changes
xmlConfig.getBlobStores().clear();
xmlConfig.getBlobStores().addAll(oldStores);
try {
compositeBlobStore.setBlobStores(oldStores);
} catch (StorageException e1) {}

throw new ConfigurationException("Error saving configuration", e);
Collection<String> existingStoreNames = agg.getBlobStoreNames();
Set<String> toDelete = new TreeSet<>(existingStoreNames);
for(BlobStoreInfo info : stores) {
toDelete.remove(info.getName());
if(existingStoreNames.contains(info.getName())) {
agg.modifyBlobStore(info);
} else {
agg.addBlobStore(info);
}
}
for(String name: toDelete) {
agg.removeBlobStore(name);
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@
import org.geowebcache.grid.GridSetBroker;
import org.geowebcache.layer.TileLayer;
import org.geowebcache.layer.TileLayerDispatcher;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;

import java.util.*;
import java.util.concurrent.CopyOnWriteArraySet;
Expand Down Expand Up @@ -433,21 +435,16 @@ public int getTileLayerCount() {
return getLayerCount();
}

/**
* @see TileLayerConfiguration#initialize(GridSetBroker)
*/
@Override
public int initialize(GridSetBroker gridSetBroker) {
public void afterPropertiesSet() {
lock.acquireWriteLock();
try {
LOGGER.info("Initializing GWC configuration based on GeoServer's Catalog");
this.gridSetBroker = gridSetBroker;
this.layerCache.invalidateAll();
this.tileLayerCatalog.initialize();
} finally {
lock.releaseWriteLock();
}
return getLayerCount();
}

/**
Expand Down Expand Up @@ -597,16 +594,7 @@ public void removeLayer(final String layerName) throws NoSuchElementException {
save();
}

/**
* @see GWC#layerAdded(String)
* @see GWC#layerRemoved(String)
* @see GWC#layerRenamed(String, String)
* @see GWC#truncateByLayerAndStyle(String, String)
* @see GWC#truncate(String, String, String, BoundingBox, String)
* @see TileLayerConfiguration#save()
*/
@Override
public synchronized void save() {
private synchronized void save() {

final GWC mediator = GWC.get();

Expand Down Expand Up @@ -768,4 +756,16 @@ public static String removeWorkspacePrefix(String layerName, Catalog catalog) {
public String getLocation() {
return this.tileLayerCatalog.getPersistenceLocation();
}

@Override
public void deinitialize() throws Exception {
// TODO Auto-generated method stub

}

@Autowired
@Override
public void setGridSetBroker(@Qualifier("gwcGridSetBroker") GridSetBroker broker) {
this.gridSetBroker=broker;
}
}

0 comments on commit 50b7d5f

Please sign in to comment.