mirror of
https://github.com/Alfresco/alfresco-community-repo.git
synced 2025-08-07 17:49:17 +00:00
Merged HEAD-QA to HEAD (4.2) (including moving test classes into separate folders)
51903 to 54309 git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/HEAD/root@54310 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
@@ -0,0 +1,246 @@
|
||||
/*
|
||||
* Copyright (C) 2005-2010 Alfresco Software Limited.
|
||||
*
|
||||
* This file is part of Alfresco
|
||||
*
|
||||
* Alfresco is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* Alfresco is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with Alfresco. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package org.alfresco.repo.content;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
|
||||
import org.alfresco.repo.cache.DefaultSimpleCache;
|
||||
import org.alfresco.repo.cache.SimpleCache;
|
||||
import org.alfresco.repo.content.filestore.FileContentStore;
|
||||
import org.alfresco.service.cmr.repository.ContentIOException;
|
||||
import org.alfresco.service.cmr.repository.ContentReader;
|
||||
import org.alfresco.service.cmr.repository.ContentWriter;
|
||||
import org.alfresco.util.Pair;
|
||||
import org.alfresco.util.TempFileProvider;
|
||||
|
||||
/**
|
||||
* Ensures that the routing of URLs based on context is working. A combination
|
||||
* of fully featured and incompletely featured stores is used to ensure that
|
||||
* all routing scenarios are handled.
|
||||
*
|
||||
* @see AbstractRoutingContentStore
|
||||
* @since 2.1
|
||||
*
|
||||
* @author Derek Hulley
|
||||
*/
|
||||
public class RoutingContentStoreTest extends AbstractWritableContentStoreTest
|
||||
{
|
||||
private ContentStore storeA;
|
||||
private ContentStore storeB;
|
||||
private ContentStore storeC;
|
||||
private ContentStore storeD;
|
||||
private ContentStore routingStore;
|
||||
|
||||
@Override
|
||||
public void setUp() throws Exception
|
||||
{
|
||||
super.setUp();
|
||||
File tempDir = TempFileProvider.getTempDir();
|
||||
// Create a subdirectory for A
|
||||
File storeADir = new File(tempDir, "A");
|
||||
storeA = new FileContentStore(ctx, storeADir);
|
||||
// Create a subdirectory for B
|
||||
File storeBDir = new File(tempDir, "B");
|
||||
storeB = new FileContentStore(ctx, storeBDir);
|
||||
// Create a subdirectory for C
|
||||
File storeCDir = new File(tempDir, "C");
|
||||
storeC = new DumbReadOnlyFileStore(new FileContentStore(ctx, storeCDir));
|
||||
// No subdirectory for D
|
||||
storeD = new SupportsNoUrlFormatStore();
|
||||
// Create the routing store
|
||||
routingStore = new RandomRoutingContentStore(storeA, storeB, storeC, storeD);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected ContentStore getStore()
|
||||
{
|
||||
return routingStore;
|
||||
}
|
||||
|
||||
public void testSetUp() throws Exception
|
||||
{
|
||||
assertNotNull(routingStore);
|
||||
}
|
||||
|
||||
private void checkForContent(String contentUrl, String content)
|
||||
{
|
||||
for (ContentStore store : new ContentStore[] {storeA, storeB})
|
||||
{
|
||||
// Does the store have it
|
||||
if (store.exists(contentUrl))
|
||||
{
|
||||
// Check it
|
||||
ContentReader reader = store.getReader(contentUrl);
|
||||
String checkContent = reader.getContentString();
|
||||
assertEquals("Content found but is incorrect", content, checkContent);
|
||||
return;
|
||||
}
|
||||
}
|
||||
fail("Content not found in any of the stores: " + contentUrl);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks that requests for missing content URLs are served.
|
||||
*/
|
||||
public void testMissingUrl()
|
||||
{
|
||||
String missingContentUrl = FileContentStore.createNewFileStoreUrl();
|
||||
|
||||
ContentReader reader = routingStore.getReader(missingContentUrl);
|
||||
assertNotNull("Missing URL should not return null", reader);
|
||||
assertFalse("Empty reader should say content doesn't exist.", reader.exists());
|
||||
try
|
||||
{
|
||||
reader.getContentString();
|
||||
fail("Empty reader cannot return content.");
|
||||
}
|
||||
catch (Throwable e)
|
||||
{
|
||||
// Expected
|
||||
}
|
||||
}
|
||||
|
||||
public void testGeneralUse()
|
||||
{
|
||||
for (int i = 0 ; i < 20; i++)
|
||||
{
|
||||
ContentContext contentContext = new ContentContext(null, null);
|
||||
ContentWriter writer = routingStore.getWriter(contentContext);
|
||||
String content = "This was generated by " + this.getClass().getName() + "#" + getName() + " number " + i;
|
||||
writer.putContent(content);
|
||||
// Check that it exists
|
||||
String contentUrl = writer.getContentUrl();
|
||||
checkForContent(contentUrl, content);
|
||||
|
||||
// Now go direct to the routing store and check that it is able to find the appropriate URLs
|
||||
ContentReader reader = routingStore.getReader(contentUrl);
|
||||
assertNotNull("Null reader returned", reader);
|
||||
assertTrue("Reader should be onto live content", reader.exists());
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* A test routing store that directs content writes to a randomly-chosen store.
|
||||
* Matching of content URLs back to the stores is handled by the base class.
|
||||
*
|
||||
* @author Derek Hulley
|
||||
*/
|
||||
private static class RandomRoutingContentStore extends AbstractRoutingContentStore
|
||||
{
|
||||
private List<ContentStore> stores;
|
||||
|
||||
public RandomRoutingContentStore(ContentStore ... stores)
|
||||
{
|
||||
this.stores = new ArrayList<ContentStore>(5);
|
||||
for (ContentStore store : stores)
|
||||
{
|
||||
this.stores.add(store);
|
||||
}
|
||||
SimpleCache<Pair<String,String>, ContentStore> cache = new DefaultSimpleCache<Pair<String,String>, ContentStore>(11, getClass().getName());
|
||||
super.setStoresCache(cache);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<ContentStore> getAllStores()
|
||||
{
|
||||
return stores;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected ContentStore selectWriteStore(ContentContext ctx)
|
||||
{
|
||||
// Shuffle the list of writable stores
|
||||
List<ContentStore> shuffled = new ArrayList<ContentStore>(stores);
|
||||
Collections.shuffle(shuffled);
|
||||
// Pick the first writable store
|
||||
for (ContentStore store : shuffled)
|
||||
{
|
||||
if (store.isWriteSupported())
|
||||
{
|
||||
return store;
|
||||
}
|
||||
}
|
||||
// Nothing found
|
||||
fail("A request came for a writer when there is no writable store to choose from");
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The simplest possible store.
|
||||
*
|
||||
* @author Derek Hulley
|
||||
*/
|
||||
private static class DumbReadOnlyFileStore extends AbstractContentStore
|
||||
{
|
||||
FileContentStore fileStore;
|
||||
public DumbReadOnlyFileStore(FileContentStore fileStore)
|
||||
{
|
||||
this.fileStore = fileStore;
|
||||
}
|
||||
|
||||
public boolean isWriteSupported()
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public ContentReader getReader(String contentUrl)
|
||||
{
|
||||
return fileStore.getReader(contentUrl);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void getUrls(Date createdAfter, Date createdBefore, ContentUrlHandler handler) throws ContentIOException
|
||||
{
|
||||
fileStore.getUrls(createdAfter, createdBefore, handler);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This store supports nothing. It is designed to catch the routing code out.
|
||||
*
|
||||
* @author Derek Hulley
|
||||
*/
|
||||
private static class SupportsNoUrlFormatStore extends AbstractContentStore
|
||||
{
|
||||
public SupportsNoUrlFormatStore()
|
||||
{
|
||||
}
|
||||
|
||||
public boolean isWriteSupported()
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public ContentReader getReader(String contentUrl)
|
||||
{
|
||||
throw new UnsupportedContentUrlException(this, contentUrl);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void getUrls(Date createdAfter, Date createdBefore, ContentUrlHandler handler) throws ContentIOException
|
||||
{
|
||||
throw new UnsupportedOperationException("getUrls not supported");
|
||||
}
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user