You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@lenya.apache.org by an...@apache.org on 2005/04/01 15:30:33 UTC
svn commit: r159685 [1/2] - in lenya/trunk/src:
java/org/apache/lenya/cms/ant/ java/org/apache/lenya/cms/cocoon/acting/
java/org/apache/lenya/cms/cocoon/components/modules/input/
java/org/apache/lenya/cms/cocoon/flow/
java/org/apache/lenya/cms/metadata/dublincore/
java/org/apache/lenya/cms/publication/ java/org/apache/lenya/cms/rc/
java/org/apache/lenya/cms/site/tree/ java/org/apache/lenya/cms/usecase/
java/org/apache/lenya/cms/workflow/ java/org/apache/lenya/transaction/
webapp/lenya/pubs/default/java/src/org/apache/lenya/defaultpub/cms/usecases/
Author: andreas
Date: Fri Apr 1 05:30:25 2005
New Revision: 159685
URL: http://svn.apache.org/viewcvs?view=rev&rev=159685
Log:
added version number to revision control, implemented locking for Transactionables
Added:
lenya/trunk/src/java/org/apache/lenya/transaction/Lock.java
Modified:
lenya/trunk/src/java/org/apache/lenya/cms/ant/InitRCTask.java
lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/ReservedCheckinAction.java
lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/UploadAction.java
lenya/trunk/src/java/org/apache/lenya/cms/cocoon/components/modules/input/OperationModule.java
lenya/trunk/src/java/org/apache/lenya/cms/cocoon/flow/FlowHelperImpl.java
lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreImpl.java
lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreProxy.java
lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultDocument.java
lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultResourcesManager.java
lenya/trunk/src/java/org/apache/lenya/cms/publication/DocumentManagerImpl.java
lenya/trunk/src/java/org/apache/lenya/cms/rc/CheckInEntry.java
lenya/trunk/src/java/org/apache/lenya/cms/rc/RCML.java
lenya/trunk/src/java/org/apache/lenya/cms/rc/RCMLEntry.java
lenya/trunk/src/java/org/apache/lenya/cms/rc/RevisionController.java
lenya/trunk/src/java/org/apache/lenya/cms/site/tree/DefaultSiteTree.java
lenya/trunk/src/java/org/apache/lenya/cms/site/tree/SiteTreeFactory.java
lenya/trunk/src/java/org/apache/lenya/cms/site/tree/TreeSiteManager.java
lenya/trunk/src/java/org/apache/lenya/cms/usecase/AbstractUsecase.java
lenya/trunk/src/java/org/apache/lenya/cms/workflow/History.java
lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMap.java
lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMapImpl.java
lenya/trunk/src/java/org/apache/lenya/transaction/Transactionable.java
lenya/trunk/src/java/org/apache/lenya/transaction/UnitOfWork.java
lenya/trunk/src/java/org/apache/lenya/transaction/UnitOfWorkImpl.java
lenya/trunk/src/webapp/lenya/pubs/default/java/src/org/apache/lenya/defaultpub/cms/usecases/Publish.java
Modified: lenya/trunk/src/java/org/apache/lenya/cms/ant/InitRCTask.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/ant/InitRCTask.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/ant/InitRCTask.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/ant/InitRCTask.java Fri Apr 1 05:30:25 2005
@@ -94,7 +94,7 @@
language);
String filename = destDoc.getFile().getCanonicalPath();
filename = filename.substring(publicationPath.length());
- this.rc.reservedCheckIn(filename, getUserId(), true);
+ this.rc.reservedCheckIn(filename, getUserId(), true, true);
}
} catch (Exception e) {
throw new BuildException(e);
Modified: lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/ReservedCheckinAction.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/ReservedCheckinAction.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/ReservedCheckinAction.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/ReservedCheckinAction.java Fri Apr 1 05:30:25 2005
@@ -50,7 +50,7 @@
getLogger().debug("Backup: " + backup);
try {
- getRc().reservedCheckIn(getFilename(), getUsername(), backup);
+ getRc().reservedCheckIn(getFilename(), getUsername(), backup, true);
} catch (FileReservedCheckInException e) {
actionMap.put("exception", "fileReservedCheckInException");
actionMap.put("filename", getFilename());
Modified: lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/UploadAction.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/UploadAction.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/UploadAction.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/cocoon/acting/UploadAction.java Fri Apr 1 05:30:25 2005
@@ -154,7 +154,7 @@
dublinCoreParams.put("extent", Integer.toString(fileSize));
if (uploadType.equals("asset")) {
- ResourcesManager resourcesMgr = new DefaultResourcesManager(this.document);
+ ResourcesManager resourcesMgr = new DefaultResourcesManager(this.document, this.manager);
assetFile = new File(resourcesMgr.getPath(), fileName);
if (!resourcesMgr.getPath().exists()) {
Modified: lenya/trunk/src/java/org/apache/lenya/cms/cocoon/components/modules/input/OperationModule.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/cocoon/components/modules/input/OperationModule.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/cocoon/components/modules/input/OperationModule.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/cocoon/components/modules/input/OperationModule.java Fri Apr 1 05:30:25 2005
@@ -65,7 +65,7 @@
getLogger().debug("OperationModule.getUnitOfWork() does not yet have instance, looking up role [" + UnitOfWork.ROLE + "]");
this.unitOfWork = (UnitOfWork) this.manager.lookup(UnitOfWork.ROLE);
- this.unitOfWork.addIdentityMap(getDocumentIdentityMap());
+ this.unitOfWork.setIdentityMap(getDocumentIdentityMap());
}
return this.unitOfWork;
Modified: lenya/trunk/src/java/org/apache/lenya/cms/cocoon/flow/FlowHelperImpl.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/cocoon/flow/FlowHelperImpl.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/cocoon/flow/FlowHelperImpl.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/cocoon/flow/FlowHelperImpl.java Fri Apr 1 05:30:25 2005
@@ -198,7 +198,10 @@
final Publication publication = getPageEnvelope(cocoon).getPublication();
final String filename = pageEnvelope.getDocument().getFile().getCanonicalPath()
.substring(publication.getDirectory().getCanonicalPath().length());
- getRevisionController(cocoon).reservedCheckIn(filename, identity.getUser().getId(), backup);
+ getRevisionController(cocoon).reservedCheckIn(filename,
+ identity.getUser().getId(),
+ backup,
+ true);
}
private ServiceManager manager;
Modified: lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreImpl.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreImpl.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreImpl.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreImpl.java Fri Apr 1 05:30:25 2005
@@ -19,18 +19,20 @@
package org.apache.lenya.cms.metadata.dublincore;
-import java.io.File;
-import java.io.IOException;
+import java.io.OutputStream;
+import java.io.OutputStreamWriter;
+import java.io.Writer;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
-import javax.xml.parsers.ParserConfigurationException;
-import javax.xml.transform.TransformerConfigurationException;
-import javax.xml.transform.TransformerException;
-
+import org.apache.avalon.framework.service.ServiceManager;
+import org.apache.cocoon.ProcessingException;
+import org.apache.excalibur.source.ModifiableSource;
+import org.apache.excalibur.source.Source;
+import org.apache.excalibur.source.SourceResolver;
import org.apache.lenya.cms.publication.Document;
import org.apache.lenya.cms.publication.DocumentException;
import org.apache.lenya.cms.publication.PageEnvelope;
@@ -38,15 +40,13 @@
import org.apache.lenya.xml.NamespaceHelper;
import org.w3c.dom.DOMException;
import org.w3c.dom.Element;
-import org.xml.sax.SAXException;
/**
* Access dublin core meta data in documents. This class uses the dublin core specification from
* 2003-03-04.
*/
public class DublinCoreImpl {
- private Document cmsdocument;
- private File infofile;
+ private String sourceUri;
private Map elements = new HashMap();
private Map terms = new HashMap();
@@ -87,28 +87,29 @@
DublinCore.TERM_EDUCATIONLEVEL, DublinCore.TERM_ACCESSRIGHTS,
DublinCore.TERM_BIBLIOGRAPHICCITATION };
+ private ServiceManager manager;
+
/**
* Creates a new instance of Dublin Core
* @param aDocument the document for which the Dublin Core instance is created.
+ * @param manager The service manager.
* @throws DocumentException if an error occurs
*/
- protected DublinCoreImpl(Document aDocument) throws DocumentException {
- this.cmsdocument = aDocument;
- this.infofile = this.cmsdocument.getPublication().getPathMapper().getFile(
- this.cmsdocument.getPublication(), this.cmsdocument.getArea(), this.cmsdocument.getId(),
- this.cmsdocument.getLanguage());
+ protected DublinCoreImpl(Document aDocument, ServiceManager manager) throws DocumentException {
+ this.manager = manager;
+ this.sourceUri = aDocument.getSourceURI();
loadValues();
}
/**
- * Creates a new instance of Dublin Core
- * @param file the File for which the Dublin Core instance is created.
- * TODO This is a hack until resources are treated as documents, and .meta files
- * can be accessed through the Document interface.
+ * Creates a new instance of Dublin Core
+ * @param sourceUri The source URI.
+ * @param manager The service manager.
* @throws DocumentException if an error occurs
*/
- public DublinCoreImpl(File file) throws DocumentException {
- this.infofile = file;
+ public DublinCoreImpl(String sourceUri, ServiceManager manager) throws DocumentException {
+ this.sourceUri = sourceUri;
+ this.manager = manager;
loadValues();
}
@@ -118,16 +119,65 @@
*/
protected void loadValues() throws DocumentException {
- if (this.infofile.exists()) {
- org.w3c.dom.Document doc = null;
- try {
- doc = DocumentHelper.readDocument(this.infofile);
- } catch (Exception e) {
- throw new DocumentException("Parsing file [" + this.infofile + "] failed: ", e);
+ SourceResolver resolver = null;
+ Source source = null;
+ try {
+ resolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
+ source = resolver.resolveURI(this.sourceUri);
+ if (source.exists()) {
+ org.w3c.dom.Document doc = DocumentHelper.readDocument(source.getInputStream());
+
+ // FIXME: what if "lenya:meta" element doesn't exist yet?
+ // Currently the element is inserted.
+ Element metaElement = getMetaElement(doc);
+
+ String[] namespaces = { DC_NAMESPACE, DCTERMS_NAMESPACE };
+ String[] prefixes = { DC_PREFIX, DCTERMS_PREFIX };
+ String[][] arrays = { ELEMENTS, TERMS };
+ Map[] maps = { this.elements, this.terms };
+
+ for (int type = 0; type < 2; type++) {
+ NamespaceHelper helper = new NamespaceHelper(namespaces[type], prefixes[type],
+ doc);
+ String[] elementNames = arrays[type];
+ for (int i = 0; i < elementNames.length; i++) {
+ Element[] children = helper.getChildren(metaElement, elementNames[i]);
+ String[] values = new String[children.length];
+ for (int valueIndex = 0; valueIndex < children.length; valueIndex++) {
+ values[valueIndex] = DocumentHelper
+ .getSimpleElementText(children[valueIndex]);
+ }
+ maps[type].put(elementNames[i], values);
+ }
+ }
}
+ } catch (Exception e) {
+ throw new DocumentException(e);
+ } finally {
+ if (resolver != null) {
+ if (source != null) {
+ resolver.release(source);
+ }
+ this.manager.release(resolver);
+ }
+ }
+ }
+
+ /**
+ * Save the meta data.
+ * @throws DocumentException if the meta data could not be made persistent.
+ */
+ public void save() throws DocumentException {
+
+ SourceResolver resolver = null;
+ ModifiableSource source = null;
+ try {
+
+ resolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
+ source = (ModifiableSource) resolver.resolveURI(this.sourceUri);
+
+ org.w3c.dom.Document doc = DocumentHelper.readDocument(source.getInputStream());
- // FIXME: what if "lenya:meta" element doesn't exist yet?
- // Currently the element is inserted.
Element metaElement = getMetaElement(doc);
String[] namespaces = { DC_NAMESPACE, DCTERMS_NAMESPACE };
@@ -140,66 +190,38 @@
String[] elementNames = arrays[type];
for (int i = 0; i < elementNames.length; i++) {
Element[] children = helper.getChildren(metaElement, elementNames[i]);
- String[] values = new String[children.length];
for (int valueIndex = 0; valueIndex < children.length; valueIndex++) {
- values[valueIndex] = DocumentHelper
- .getSimpleElementText(children[valueIndex]);
+ metaElement.removeChild(children[valueIndex]);
+ }
+ String[] values = (String[]) maps[type].get(elementNames[i]);
+ for (int valueIndex = 0; valueIndex < values.length; valueIndex++) {
+ Element valueElement = helper.createElement(elementNames[i],
+ values[valueIndex]);
+ metaElement.appendChild(valueElement);
}
- maps[type].put(elementNames[i], values);
}
}
- }
- }
-
- /**
- * Save the meta data.
- * @throws DocumentException if the meta data could not be made persistent.
- */
- public void save() throws DocumentException {
- org.w3c.dom.Document doc = null;
- try {
- doc = DocumentHelper.readDocument(this.infofile);
- } catch (final ParserConfigurationException e) {
- throw new DocumentException(e);
- } catch (final SAXException e) {
- throw new DocumentException(e);
- } catch (final IOException e) {
- throw new DocumentException(e);
- }
-
- Element metaElement = getMetaElement(doc);
-
- String[] namespaces = { DC_NAMESPACE, DCTERMS_NAMESPACE };
- String[] prefixes = { DC_PREFIX, DCTERMS_PREFIX };
- String[][] arrays = { ELEMENTS, TERMS };
- Map[] maps = { this.elements, this.terms };
-
- for (int type = 0; type < 2; type++) {
- NamespaceHelper helper = new NamespaceHelper(namespaces[type], prefixes[type], doc);
- String[] elementNames = arrays[type];
- for (int i = 0; i < elementNames.length; i++) {
- Element[] children = helper.getChildren(metaElement, elementNames[i]);
- for (int valueIndex = 0; valueIndex < children.length; valueIndex++) {
- metaElement.removeChild(children[valueIndex]);
- }
- String[] values = (String[]) maps[type].get(elementNames[i]);
- for (int valueIndex = 0; valueIndex < values.length; valueIndex++) {
- Element valueElement = helper
- .createElement(elementNames[i], values[valueIndex]);
- metaElement.appendChild(valueElement);
+ OutputStream oStream = source.getOutputStream();
+ Writer writer = new OutputStreamWriter(oStream);
+ DocumentHelper.writeDocument(doc, writer);
+ if (oStream != null) {
+ oStream.flush();
+ try {
+ oStream.close();
+ } catch (Throwable t) {
+ throw new ProcessingException("Could not write document: ", t);
}
}
- }
-
- try {
- DocumentHelper.writeDocument(doc, this.infofile);
- } catch (TransformerConfigurationException e) {
- throw new DocumentException(e);
- } catch (TransformerException e) {
- throw new DocumentException(e);
- } catch (IOException e) {
+ } catch (Exception e) {
throw new DocumentException(e);
+ } finally {
+ if (resolver != null) {
+ if (source != null) {
+ resolver.release(source);
+ }
+ this.manager.release(resolver);
+ }
}
}
Modified: lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreProxy.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreProxy.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreProxy.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/metadata/dublincore/DublinCoreProxy.java Fri Apr 1 05:30:25 2005
@@ -19,6 +19,7 @@
package org.apache.lenya.cms.metadata.dublincore;
+import org.apache.avalon.framework.service.ServiceManager;
import org.apache.lenya.cms.publication.Document;
import org.apache.lenya.cms.publication.DocumentException;
@@ -30,15 +31,17 @@
private DublinCoreImpl dcCore;
private Document cmsDocument;
-
+ private ServiceManager manager;
/**
* Creates a new instance of Dublin Core
*
* @param aDocument the document for which the Dublin Core instance is created.
+ * @param manager The service manager.
*/
- public DublinCoreProxy(Document aDocument) {
+ public DublinCoreProxy(Document aDocument, ServiceManager manager) {
this.cmsDocument = aDocument;
+ this.manager = manager;
}
/**
@@ -49,7 +52,7 @@
*/
protected DublinCoreImpl instance() throws DocumentException {
if (this.dcCore == null) {
- this.dcCore = new DublinCoreImpl(this.cmsDocument);
+ this.dcCore = new DublinCoreImpl(this.cmsDocument, this.manager);
}
return this.dcCore;
}
Modified: lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultDocument.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultDocument.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultDocument.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultDocument.java Fri Apr 1 05:30:25 2005
@@ -33,6 +33,7 @@
import org.apache.excalibur.source.Source;
import org.apache.excalibur.source.SourceResolver;
import org.apache.lenya.ac.User;
+import org.apache.lenya.cms.cocoon.source.SourceUtil;
import org.apache.lenya.cms.metadata.dublincore.DublinCore;
import org.apache.lenya.cms.metadata.dublincore.DublinCoreProxy;
import org.apache.lenya.cms.publication.util.DocumentVisitor;
@@ -41,6 +42,7 @@
import org.apache.lenya.cms.site.SiteManager;
import org.apache.lenya.cms.workflow.CMSHistory;
import org.apache.lenya.cms.workflow.History;
+import org.apache.lenya.transaction.Lock;
import org.apache.lenya.transaction.TransactionException;
import org.apache.lenya.workflow.Situation;
import org.apache.lenya.workflow.Version;
@@ -84,7 +86,7 @@
setArea(_area);
setLanguage(getPublication().getDefaultLanguage());
- this.dublincore = new DublinCoreProxy(this);
+ this.dublincore = new DublinCoreProxy(this, this.manager);
}
/**
@@ -112,7 +114,7 @@
this.language = _language;
setArea(_area);
- this.dublincore = new DublinCoreProxy(this);
+ this.dublincore = new DublinCoreProxy(this, this.manager);
}
/**
@@ -381,7 +383,7 @@
*/
public ResourcesManager getResourcesManager() {
if (this.resourcesManager == null) {
- this.resourcesManager = new DefaultResourcesManager(this);
+ this.resourcesManager = new DefaultResourcesManager(this, this.manager);
ContainerUtil.enableLogging(this.resourcesManager, getLogger());
}
return this.resourcesManager;
@@ -402,9 +404,50 @@
}
/**
+ * If the document is involved in a unit of work, a temporary source is created to be used in
+ * the transaction.
* @see org.apache.lenya.cms.publication.Document#getSourceURI()
*/
public String getSourceURI() {
+ String uri = getRealSourceURI();
+
+ if (getIdentityMap().getUnitOfWork() != null) {
+ String workUri = getWorkSourceURI();
+
+ SourceResolver resolver = null;
+ ModifiableSource realSource = null;
+ ModifiableSource workSource = null;
+ try {
+ resolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
+ realSource = (ModifiableSource) resolver.resolveURI(uri);
+ workSource = (ModifiableSource) resolver.resolveURI(workUri);
+ if (realSource.exists() && !workSource.exists()) {
+ SourceUtil.copy(realSource, workSource, true);
+ }
+ } catch (Exception e) {
+ throw new RuntimeException(e);
+ } finally {
+ if (resolver != null) {
+ if (realSource != null) {
+ resolver.release(realSource);
+ }
+ if (workSource != null) {
+ resolver.release(workSource);
+ }
+ this.manager.release(resolver);
+ }
+ }
+
+ uri = workUri;
+ }
+
+ return uri;
+ }
+
+ /**
+ * @return The real source URI.
+ */
+ protected String getRealSourceURI() {
try {
return "file:/" + getFile().getCanonicalPath();
} catch (IOException e) {
@@ -413,6 +456,19 @@
}
/**
+ * @return A source URI to be used in a transaction.
+ */
+ protected String getWorkSourceURI() {
+ String workUri = "file:/" + getPublication().getDirectory().getAbsolutePath() + "/work/";
+ workUri += getUserId();
+
+ String path = getPublication().getPathMapper().getPath(getId(), getLanguage());
+ workUri += "/" + getArea() + "/" + path;
+
+ return workUri;
+ }
+
+ /**
* @see org.apache.lenya.cms.publication.Document#accept(org.apache.lenya.cms.publication.util.DocumentVisitor)
*/
public void accept(DocumentVisitor visitor) throws PublicationException {
@@ -492,12 +548,36 @@
* @see org.apache.lenya.transaction.Transactionable#save()
*/
public void save() throws TransactionException {
+
+ SourceResolver sourceResolver = null;
+ ModifiableSource realSource = null;
+ ModifiableSource workSource = null;
try {
getDublinCore().save();
- } catch (DocumentException e) {
+ getHistory().save();
+
+ sourceResolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
+ realSource = (ModifiableSource) sourceResolver.resolveURI(getRealSourceURI());
+ workSource = (ModifiableSource) sourceResolver.resolveURI(getWorkSourceURI());
+ if (workSource.exists()) {
+ SourceUtil.copy(workSource, realSource, true);
+ workSource.delete();
+ }
+
+ } catch (Exception e) {
throw new TransactionException(e);
+ } finally {
+ if (sourceResolver != null) {
+ if (realSource != null) {
+ sourceResolver.release(realSource);
+ }
+ if (workSource != null) {
+ sourceResolver.release(workSource);
+ }
+ this.manager.release(sourceResolver);
+ }
}
- getHistory().save();
+
}
/**
@@ -506,12 +586,12 @@
public void checkin() throws TransactionException {
checkin(true);
}
-
+
protected void checkin(boolean backup) throws TransactionException {
try {
- String fileName = getFile().getCanonicalPath();
- String userName = getUserName();
- getRevisionController().reservedCheckIn(fileName, userName, backup);
+ String userName = getUserId();
+ boolean newVersion = getIdentityMap().getUnitOfWork().isDirty(this);
+ getRevisionController().reservedCheckIn(getRCPath(), userName, backup, newVersion);
} catch (Exception e) {
throw new TransactionException(e);
}
@@ -520,11 +600,11 @@
/**
* @return The username of the unit of work's identity.
*/
- protected String getUserName() {
+ protected String getUserId() {
String userName = null;
User user = getIdentityMap().getUnitOfWork().getIdentity().getUser();
if (user != null) {
- userName = user.getName();
+ userName = user.getId();
}
return userName;
}
@@ -534,9 +614,8 @@
*/
public void checkout() throws TransactionException {
try {
- String fileName = getFile().getCanonicalPath();
- String userName = getUserName();
- getRevisionController().reservedCheckOut(fileName, userName);
+ String userName = getUserId();
+ getRevisionController().reservedCheckOut(getRCPath(), userName);
} catch (Exception e) {
throw new TransactionException(e);
}
@@ -547,9 +626,8 @@
*/
public boolean isCheckedOut() throws TransactionException {
try {
- String fileName = getFile().getCanonicalPath();
- String userName = getUserName();
- return !getRevisionController().canCheckOut(fileName, userName);
+ String userName = getUserId();
+ return !getRevisionController().canCheckOut(getRCPath(), userName);
} catch (Exception e) {
throw new TransactionException(e);
}
@@ -559,22 +637,21 @@
* @see org.apache.lenya.transaction.Transactionable#lock()
*/
public void lock() throws TransactionException {
- checkout();
+ this.lock = new Lock(getVersion());
}
/**
* @see org.apache.lenya.transaction.Transactionable#unlock()
*/
public void unlock() throws TransactionException {
- checkin(false);
+ this.lock = null;
}
/**
* @see org.apache.lenya.transaction.Transactionable#isLocked()
*/
public boolean isLocked() throws TransactionException {
- // TODO Auto-generated method stub
- return false;
+ return this.lock != null;
}
/**
@@ -589,17 +666,27 @@
*/
public void delete() throws TransactionException {
SourceResolver sourceResolver = null;
- Source source = null;
+ Source realSource = null;
+ Source workSource = null;
try {
sourceResolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
- source = sourceResolver.resolveURI(getSourceURI());
- ((ModifiableSource) source).delete();
+ realSource = sourceResolver.resolveURI(getSourceURI());
+ if (realSource.exists()) {
+ ((ModifiableSource) realSource).delete();
+ }
+ workSource = sourceResolver.resolveURI(getWorkSourceURI());
+ if (workSource.exists()) {
+ ((ModifiableSource) workSource).delete();
+ }
} catch (Exception e) {
throw new TransactionException(e);
} finally {
if (sourceResolver != null) {
- if (source != null) {
- sourceResolver.release(source);
+ if (realSource != null) {
+ sourceResolver.release(realSource);
+ }
+ if (workSource != null) {
+ sourceResolver.release(workSource);
}
this.manager.release(sourceResolver);
}
@@ -632,6 +719,35 @@
}
}
return this.revisionController;
+ }
+
+ private Lock lock;
+
+ /**
+ * @see org.apache.lenya.transaction.Transactionable#getLock()
+ */
+ public Lock getLock() {
+ return this.lock;
+ }
+
+ /**
+ * @see org.apache.lenya.transaction.Transactionable#getVersion()
+ */
+ public int getVersion() throws TransactionException {
+ try {
+ String fileName = getRCPath();
+ return getRevisionController().getLatestVersion(fileName);
+ } catch (Exception e) {
+ throw new TransactionException(e);
+ }
+ }
+
+ /**
+ * @return The path to use for the revision controller.
+ * @throws IOException if an error occurs.
+ */
+ protected String getRCPath() throws IOException {
+ return getArea() + "/" + getPublication().getPathMapper().getPath(getId(), getLanguage());
}
}
Modified: lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultResourcesManager.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultResourcesManager.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultResourcesManager.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/publication/DefaultResourcesManager.java Fri Apr 1 05:30:25 2005
@@ -33,6 +33,7 @@
import java.util.Map;
import org.apache.avalon.framework.logger.AbstractLogEnabled;
+import org.apache.avalon.framework.service.ServiceManager;
import org.apache.avalon.excalibur.io.FileUtil;
@@ -41,7 +42,6 @@
import org.apache.lenya.xml.DocumentHelper;
import org.apache.lenya.xml.NamespaceHelper;
-
/**
* Manager for resources of a CMS document.
*/
@@ -95,15 +95,17 @@
}
private Document document = null;
-
+ private ServiceManager manager;
+
protected static final String NAMESPACE_META = "http://lenya.apache.org/meta/1.0";
/**
* Create a new instance of Resources.
* @param _document the document for which the resources are managed
*/
- public DefaultResourcesManager(Document _document) {
+ public DefaultResourcesManager(Document _document, ServiceManager manager) {
this.document = _document;
+ this.manager = manager;
}
/**
@@ -145,15 +147,15 @@
/*
* } // must be a content upload then else { resourceFile = new
- * File(document.getFile().getParent(), fileName);
- * getLogger().debug("resourceFile: " + resourceFile); }
+ * File(document.getFile().getParent(), fileName); getLogger().debug("resourceFile: " +
+ * resourceFile); }
*/
saveResource(resourceFile, part);
} catch (final DocumentException e) {
- getLogger().error("Document exception " +e.toString());
+ getLogger().error("Document exception " + e.toString());
throw new RuntimeException(e);
} catch (final IOException e) {
- getLogger().error("IO Error " +e.toString());
+ getLogger().error("IO Error " + e.toString());
throw e;
}
}
@@ -167,7 +169,7 @@
protected void saveResource(File resourceFile, Part part) throws IOException {
FileOutputStream out = null;
InputStream in = null;
-
+
if (!resourceFile.exists()) {
boolean created = resourceFile.createNewFile();
if (!created) {
@@ -175,7 +177,7 @@
}
}
- try {
+ try {
byte[] buf = new byte[4096];
out = new FileOutputStream(resourceFile);
in = part.getInputStream();
@@ -186,13 +188,13 @@
read = in.read(buf);
}
} catch (final FileNotFoundException e) {
- getLogger().error("file not found" +e.toString());
+ getLogger().error("file not found" + e.toString());
throw new IOException(e.toString());
} catch (IOException e) {
- getLogger().error("IO error " +e.toString());
+ getLogger().error("IO error " + e.toString());
throw new IOException(e.toString());
} catch (Exception e) {
- getLogger().error("Exception" +e.toString());
+ getLogger().error("Exception" + e.toString());
throw new IOException(e.toString());
} finally {
if (in != null)
@@ -208,27 +210,27 @@
* @param metadata a <code>Map</code> containing the dublin core values
* @throws DocumentException if an error occurs
*/
- protected void createMetaData(File metaDataFile, Map metadata)
- throws DocumentException {
+ protected void createMetaData(File metaDataFile, Map metadata) throws DocumentException {
assert (metaDataFile.getParentFile().exists());
- try {
-
+ try {
+
if (!metaDataFile.exists()) {
metaDataFile.createNewFile();
NamespaceHelper helper = new NamespaceHelper(NAMESPACE_META, "", "meta");
DocumentHelper.writeDocument(helper.getDocument(), metaDataFile);
}
- String key;
- String value;
- Map.Entry entry;
- DublinCoreImpl dc = new DublinCoreImpl(metaDataFile);
+ String key;
+ String value;
+ Map.Entry entry;
+ String sourceUrl = "file:/" + metaDataFile.getAbsolutePath();
+ DublinCoreImpl dc = new DublinCoreImpl(sourceUrl, this.manager);
Iterator iter = metadata.entrySet().iterator();
while (iter.hasNext()) {
- entry = (Map.Entry)iter.next();
- key = (String)entry.getKey();
- value = (String)entry.getValue();
+ entry = (Map.Entry) iter.next();
+ key = (String) entry.getKey();
+ value = (String) entry.getValue();
dc.setValue(key, value);
}
dc.save();
@@ -303,8 +305,7 @@
/**
* Get the meta data for all resources for the associated document.
- * @return all meta data files for the resources for the associated
- * document.
+ * @return all meta data files for the resources for the associated document.
*/
public File[] getMetaFiles() {
FileFilter filter = new MetaSuffixFileFilter();
@@ -314,8 +315,8 @@
/**
* Returns a meta file for a given resource.
* @param resource A resource the meta file should be returned for.
- * @return A file containing meta information about a resource. Returns null
- * if no meta file was found.
+ * @return A file containing meta information about a resource. Returns null if no meta file was
+ * found.
* @throws IllegalArgumentException If resource is a meta file itself.
*/
public File getMetaFile(final File resource) throws IllegalArgumentException {
Modified: lenya/trunk/src/java/org/apache/lenya/cms/publication/DocumentManagerImpl.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/publication/DocumentManagerImpl.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/publication/DocumentManagerImpl.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/publication/DocumentManagerImpl.java Fri Apr 1 05:30:25 2005
@@ -38,6 +38,7 @@
import org.apache.lenya.cms.site.tree.SiteTreeNode;
import org.apache.lenya.cms.site.tree.TreeSiteManager;
import org.apache.lenya.cms.workflow.WorkflowManager;
+import org.apache.lenya.transaction.UnitOfWork;
/**
* Abstract DocumentManager implementation.
@@ -138,7 +139,9 @@
selector = (ServiceSelector) this.manager.lookup(SiteManager.ROLE + "Selector");
siteManager = (SiteManager) selector.select(publication.getSiteManagerHint());
siteManager.delete(document);
- document.delete();
+
+ UnitOfWork unit = document.getIdentityMap().getUnitOfWork();
+ unit.registerRemoved(document);
} catch (Exception e) {
throw new PublicationException(e);
} finally {
@@ -431,6 +434,7 @@
destination = sourceResolver.resolveURI(destinationDocument.getSourceURI());
SourceUtil.copy(source, (ModifiableSource) destination, true);
destinationDocument.getDublinCore().replaceBy(sourceDocument.getDublinCore());
+ destinationDocument.getIdentityMap().getUnitOfWork().registerDirty(destinationDocument);
} catch (Exception e) {
throw new PublicationException(e);
} finally {
Modified: lenya/trunk/src/java/org/apache/lenya/cms/rc/CheckInEntry.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/rc/CheckInEntry.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/rc/CheckInEntry.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/rc/CheckInEntry.java Fri Apr 1 05:30:25 2005
@@ -28,9 +28,21 @@
* Creates a new CheckInEntry object.
* @param identity The identity to use
* @param time The time
+ * @param version The version number.
*/
- public CheckInEntry(String identity, long time) {
+ public CheckInEntry(String identity, long time, int version) {
super(identity, time);
setType(RCML.ci);
+ this.version = version;
}
+
+ /**
+ * @return The version number.
+ */
+ public int getVersion() {
+ return this.version;
+ }
+
+ private int version = 0;
+
}
Modified: lenya/trunk/src/java/org/apache/lenya/cms/rc/RCML.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/rc/RCML.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/rc/RCML.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/rc/RCML.java Fri Apr 1 05:30:25 2005
@@ -78,9 +78,9 @@
/**
* create a RCML-File if no one exists already
* @param rcmlDirectory The rcml directory.
- * @param filename The path of the file from the publication (e.g. for file with
- * absolute path home/...//lenya/pubs/{publication id}/content/authoring/foo/bar.xml
- * the filename is content/authoring/foo/bar.xml)
+ * @param filename The path of the file from the publication (e.g. for file with absolute path
+ * home/...//lenya/pubs/{publication id}/content/authoring/foo/bar.xml the filename
+ * is content/authoring/foo/bar.xml)
* @param rootDirectory The publication directory
* @throws Exception if an error occurs
*/
@@ -104,7 +104,7 @@
// system checked the document in. We use the filesystem
// modification date as checkin time.
//
- checkOutIn(RCML.ci, RevisionController.systemUsername, lastModified, false);
+ checkOutIn(RCML.ci, RevisionController.systemUsername, lastModified, false, false);
File parent = new File(this.rcmlFile.getParent());
parent.mkdirs();
@@ -125,7 +125,7 @@
/**
* Call the methode write, if the document is dirty
- *
+ *
* @throws IOException if an error occurs
* @throws Exception if an error occurs
*/
@@ -135,8 +135,9 @@
write();
}
}
+
/**
- * Write the xml RCML-document in the RCML-file.
+ * Write the xml RCML-document in the RCML-file.
* @throws IOException if an error occurs
* @throws Exception if an error occurs
*/
@@ -152,15 +153,16 @@
* @param identity The identity of the user
* @param time Time at which the check in/out is made
* @param backup Create backup element
+ * @param newVersion If true, a new version will be created.
* @throws IOException if an error occurs
* @throws Exception if an error occurs
*/
- public void checkOutIn(short type, String identity, long time, boolean backup)
- throws IOException, Exception {
+ public void checkOutIn(short type, String identity, long time, boolean backup,
+ boolean newVersion) throws IOException, Exception {
if (type != co && type != ci) {
- throw new IllegalArgumentException(
- "ERROR: " + this.getClass().getName() + ".checkOutIn(): No such type");
+ throw new IllegalArgumentException("ERROR: " + this.getClass().getName()
+ + ".checkOutIn(): No such type");
}
NamespaceHelper helper = new NamespaceHelper(null, "", this.document);
@@ -174,6 +176,19 @@
checkOutElement.appendChild(identityElement);
checkOutElement.appendChild(timeElement);
+ if (type == ci) {
+ int version = 0;
+ CheckInEntry latestEntry = getLatestCheckInEntry();
+ if (latestEntry != null) {
+ version = latestEntry.getVersion();
+ }
+ if (newVersion) {
+ version++;
+ }
+ Element versionElement = helper.createElement("Version", "" + version);
+ checkOutElement.appendChild(versionElement);
+ }
+
if (backup) {
Element backupElement = helper.createElement(ELEMENT_BACKUP);
checkOutElement.appendChild(backupElement);
@@ -215,8 +230,9 @@
Node time = null;
String rcIdentity = null;
- identity = XPathAPI.selectSingleNode(parent,"/XPSRevisionControl/CheckOut[1]/Identity/text()");
- time = XPathAPI.selectSingleNode(parent,"/XPSRevisionControl/CheckOut[1]/Time/text()");
+ identity = XPathAPI.selectSingleNode(parent,
+ "/XPSRevisionControl/CheckOut[1]/Identity/text()");
+ time = XPathAPI.selectSingleNode(parent, "/XPSRevisionControl/CheckOut[1]/Time/text()");
if (identity == null && time == null) {
// No checkout at all
@@ -235,21 +251,25 @@
*/
public CheckInEntry getLatestCheckInEntry() throws Exception {
Element parent = this.document.getDocumentElement();
- Node identity = null;
- Node time = null;
- String rcIdentity = null;
- identity = XPathAPI.selectSingleNode(parent,"/XPSRevisionControl/CheckIn[1]/Identity/text()");
- time = XPathAPI.selectSingleNode(parent,"/XPSRevisionControl/CheckIn[1]/Time/text()");
+ Node identity = XPathAPI.selectSingleNode(parent,
+ "/XPSRevisionControl/CheckIn[1]/Identity/text()");
+ Node time = XPathAPI.selectSingleNode(parent, "/XPSRevisionControl/CheckIn[1]/Time/text()");
+ Node versionNode = XPathAPI.selectSingleNode(parent,
+ "/XPSRevisionControl/CheckOut[1]/Version/text()");
if (identity == null && time == null) {
// No checkout at all
return null;
}
- rcIdentity = identity.getNodeValue();
+ String rcIdentity = identity.getNodeValue();
long rcTime = new Long(time.getNodeValue()).longValue();
+ int version = 0;
+ if (versionNode != null) {
+ version = new Integer(versionNode.getNodeValue()).intValue();
+ }
- return new CheckInEntry(rcIdentity, rcTime);
+ return new CheckInEntry(rcIdentity, rcTime, version);
}
/**
@@ -280,21 +300,28 @@
* @throws Exception if an error occurs
*/
public Vector getEntries() throws Exception {
- Element parent = this.document.getDocumentElement();
- NodeList entries =
- XPathAPI.selectNodeList(parent, "/XPSRevisionControl/CheckOut|/XPSRevisionControl/CheckIn");
+ Element parent = this.document.getDocumentElement();
+ NodeList entries = XPathAPI.selectNodeList(parent,
+ "/XPSRevisionControl/CheckOut|/XPSRevisionControl/CheckIn");
Vector RCMLEntries = new Vector();
for (int i = 0; i < entries.getLength(); i++) {
Element elem = (Element) entries.item(i);
String time = elem.getElementsByTagName("Time").item(0).getFirstChild().getNodeValue();
- String identity =
- elem.getElementsByTagName("Identity").item(0).getFirstChild().getNodeValue();
+ String identity = elem.getElementsByTagName("Identity").item(0).getFirstChild()
+ .getNodeValue();
if (elem.getTagName().equals("CheckOut")) {
RCMLEntries.add(new CheckOutEntry(identity, new Long(time).longValue()));
} else {
- RCMLEntries.add(new CheckInEntry(identity, new Long(time).longValue()));
+ NodeList versionElements = elem.getElementsByTagName("Version");
+ int version = 0;
+ if (versionElements.getLength() > 0) {
+ String versionString = elem.getFirstChild().getNodeValue();
+ version = new Integer(versionString).intValue();
+ }
+
+ RCMLEntries.add(new CheckInEntry(identity, new Long(time).longValue(), version));
}
}
@@ -302,22 +329,22 @@
}
/**
- * Prune the list of entries and delete the corresponding backups. Limit the number of entries to the value
- * maximalNumberOfEntries (2maxNumberOfRollbacks(configured)+1)
+ * Prune the list of entries and delete the corresponding backups. Limit the number of entries
+ * to the value maximalNumberOfEntries (2maxNumberOfRollbacks(configured)+1)
* @param backupDir The backup directory
* @throws Exception if an error occurs
*/
public void pruneEntries(String backupDir) throws Exception {
- Element parent = this.document.getDocumentElement();
- NodeList entries =
- XPathAPI.selectNodeList(parent, "/XPSRevisionControl/CheckOut|/XPSRevisionControl/CheckIn");
+ Element parent = this.document.getDocumentElement();
+ NodeList entries = XPathAPI.selectNodeList(parent,
+ "/XPSRevisionControl/CheckOut|/XPSRevisionControl/CheckIn");
for (int i = this.maximalNumberOfEntries; i < entries.getLength(); i++) {
Element current = (Element) entries.item(i);
// remove the backup file associated with this entry
- String time =
- current.getElementsByTagName("Time").item(0).getFirstChild().getNodeValue();
+ String time = current.getElementsByTagName("Time").item(0).getFirstChild()
+ .getNodeValue();
File backupFile = new File(backupDir + "/" + time + ".bak");
backupFile.delete();
// remove the entry from the list
@@ -326,21 +353,22 @@
}
/**
- * Get a clone document
+ * Get a clone document
* @return org.w3c.dom.Document The clone document
* @throws Exception if an error occurs
*/
public org.w3c.dom.Document getDOMDocumentClone() throws Exception {
Document documentClone = DocumentHelper.createDocument(null, "dummy", null);
documentClone.removeChild(documentClone.getDocumentElement());
- documentClone.appendChild(documentClone.importNode(this.document.getDocumentElement(), true));
+ documentClone.appendChild(documentClone
+ .importNode(this.document.getDocumentElement(), true));
return documentClone;
}
/**
* Check if the document is dirty
- * @return boolean dirty
+ * @return boolean dirty
*/
public boolean isDirty() {
return this.dirty;
@@ -387,7 +415,7 @@
Element elem = (Element) entries.item(i);
String time = elem.getElementsByTagName("Time").item(0).getFirstChild().getNodeValue();
NodeList backupNodes = elem.getElementsByTagName(ELEMENT_BACKUP);
- if (backupNodes != null && backupNodes.getLength()>0) {
+ if (backupNodes != null && backupNodes.getLength() > 0) {
times.add(time);
}
}
@@ -402,11 +430,9 @@
public boolean delete() {
File directory = this.rcmlFile.getParentFile();
boolean deleted = this.rcmlFile.delete();
- if (directory.exists()
- && directory.isDirectory()
- && directory.listFiles().length == 0) {
+ if (directory.exists() && directory.isDirectory() && directory.listFiles().length == 0) {
directory.delete();
}
return deleted;
}
-}
+}
\ No newline at end of file
Modified: lenya/trunk/src/java/org/apache/lenya/cms/rc/RCMLEntry.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/rc/RCMLEntry.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/rc/RCMLEntry.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/rc/RCMLEntry.java Fri Apr 1 05:30:25 2005
@@ -61,7 +61,7 @@
public short getType() {
return this.type;
}
-
+
/**
* Set the type.
* @param s the type
Modified: lenya/trunk/src/java/org/apache/lenya/cms/rc/RevisionController.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/rc/RevisionController.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/rc/RevisionController.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/rc/RevisionController.java Fri Apr 1 05:30:25 2005
@@ -29,18 +29,16 @@
import org.apache.log4j.Logger;
/**
- * Controller for the reserved check-in, check-out, the backup versions and the rollback
+ * Controller for the reserved check-in, check-out, the backup versions and the rollback
*/
public class RevisionController {
private static Logger log = Logger.getLogger(RevisionController.class);
/**
- * <code>systemUsername</code> The system user name. This is used for
- * - creating dummy checkin events in a new RCML file
- * when it is created on-the-fly
- * - system override on checkin, i.e. you can force
- * a checkin into the repository if you use this
- * username as identity parameter to reservedCheckIn()
+ * <code>systemUsername</code> The system user name. This is used for - creating dummy checkin
+ * events in a new RCML file when it is created on-the-fly - system override on checkin, i.e.
+ * you can force a checkin into the repository if you use this username as identity parameter to
+ * reservedCheckIn()
*/
public static final String systemUsername = "System";
@@ -50,7 +48,7 @@
/**
* Creates a new RevisionController object.
- *
+ *
* @param rcmlDirectory The directory for the RCML files
* @param backupDirectory The directory for the backup versions
* @param rootDirectory The publication directory
@@ -66,7 +64,8 @@
* @return String The rcml directory, the backup directory, the publication directory
*/
public String toString() {
- return "rcmlDir=" + this.rcmlDir + " , rcbakDir=" + this.backupDir + " , rootDir=" + this.rootDir;
+ return "rcmlDir=" + this.rcmlDir + " , rcbakDir=" + this.backupDir + " , rootDir="
+ + this.rootDir;
}
/**
@@ -82,21 +81,35 @@
}
/**
+ * Returns the latest version of a source.
+ * @param source The path of the file from the publication.
+ * @return A version number.
+ * @throws Exception if an error occurs.
+ */
+ public int getLatestVersion(String source) throws Exception {
+ RCML rcml = new RCML(this.rcmlDir, source, this.rootDir);
+ CheckInEntry entry = rcml.getLatestCheckInEntry();
+ int version = 0;
+ if (entry != null) {
+ version = entry.getVersion();
+ }
+ return version;
+ }
+
+ /**
* Try to make a reserved check out of the file source for a user with identity
- *
+ *
* @param source The filename of the file to check out
* @param identity The identity of the user
* @return File File to check out
* @throws Exception if an error occurs
*/
public File reservedCheckOut(String source, String identity) throws Exception {
-
+
File file = new File(this.rootDir + source);
/*
- if (!file.isFile()) {
- throw new FileNotFoundException(file.getAbsolutePath());
- }
- */
+ * if (!file.isFile()) { throw new FileNotFoundException(file.getAbsolutePath()); }
+ */
RCML rcml = new RCML(this.rcmlDir, source, this.rootDir);
@@ -111,13 +124,12 @@
log.debug("entry.identity" + entry.getIdentity());
}
- if ((entry != null)
- && (entry.getType() != RCML.ci)
- && !entry.getIdentity().equals(identity)) {
+ if ((entry != null) && (entry.getType() != RCML.ci)
+ && !entry.getIdentity().equals(identity)) {
throw new FileReservedCheckOutException(this.rootDir + source, rcml);
}
- rcml.checkOutIn(RCML.co, identity, new Date().getTime(), false);
+ rcml.checkOutIn(RCML.co, identity, new Date().getTime(), false, false);
return file;
}
@@ -143,8 +155,8 @@
log.debug("entry.identity" + entry.getIdentity());
}
- boolean checkedOutByOther =
- entry != null && entry.getType() != RCML.ci && !entry.getIdentity().equals(identity);
+ boolean checkedOutByOther = entry != null && entry.getType() != RCML.ci
+ && !entry.getIdentity().equals(identity);
return !checkedOutByOther;
}
@@ -152,19 +164,20 @@
/**
* Try to make a reserved check in of the file destination for a user with identity. A backup
* copy can be made.
- *
+ *
* @param destination The file we want to check in
* @param identity The identity of the user
* @param backup if true, a backup will be created, else no backup will be made.
- *
+ * @param newVersion If true, a new version will be created.
+ *
* @return long The time.
- *
+ *
* @exception FileReservedCheckInException if the document couldn't be checked in (for instance
- * because it is already checked out by someone other ...)
+ * because it is already checked out by someone other ...)
* @exception Exception if other problems occur
*/
- public long reservedCheckIn(String destination, String identity, boolean backup)
- throws FileReservedCheckInException, Exception {
+ public long reservedCheckIn(String destination, String identity, boolean backup,
+ boolean newVersion) throws FileReservedCheckInException, Exception {
FileInputStream in = null;
FileOutputStream out = null;
@@ -187,23 +200,19 @@
if (!((coe == null) || identity.equals(RevisionController.systemUsername))) {
/*
* Possible cases and rules:
- *
+ *
* 1.) we were able to read the latest checkin and it is later than latest checkout
- * (i.e. there is no open checkout to match this checkin, an unusual case)
- * 1.1.) identity of latest checkin is equal to current user
- * -> checkin allowed, same user may check in repeatedly
- * 1.2.) identity of latest checkin is not equal to current user
- * -> checkin rejected, may not overwrite the revision which
- * another user checked in previously
- * 2.) there was no checkin or the latest checkout is later than latest checkin
- * (i.e. there is an open checkout)
- * 2.1.) identity of latest checkout is equal to current user
- * -> checkin allowed, user checked out and may check in again
- * (the most common case)
- * 2.2.) identity of latest checkout is not equal to current user
- * -> checkin rejected, may not check in while another
- * user is working on this document
- *
+ * (i.e. there is no open checkout to match this checkin, an unusual case) 1.1.)
+ * identity of latest checkin is equal to current user -> checkin allowed, same user
+ * may check in repeatedly 1.2.) identity of latest checkin is not equal to current
+ * user -> checkin rejected, may not overwrite the revision which another user
+ * checked in previously 2.) there was no checkin or the latest checkout is later
+ * than latest checkin (i.e. there is an open checkout) 2.1.) identity of latest
+ * checkout is equal to current user -> checkin allowed, user checked out and may
+ * check in again (the most common case) 2.2.) identity of latest checkout is not
+ * equal to current user -> checkin rejected, may not check in while another user is
+ * working on this document
+ *
*/
if ((cie != null) && (cie.getTime() > coe.getTime())) {
// We have case 1
@@ -223,7 +232,7 @@
}
File originalFile = new File(this.rootDir, destination);
-
+
if (backup && originalFile.isFile()) {
File backupFile = new File(this.backupDir, destination + ".bak." + time);
File parent = new File(backupFile.getParent());
@@ -232,10 +241,7 @@
parent.mkdirs();
}
- log.debug(
- "Backup: copy "
- + originalFile.getAbsolutePath()
- + " to "
+ log.debug("Backup: copy " + originalFile.getAbsolutePath() + " to "
+ backupFile.getAbsolutePath());
in = new FileInputStream(originalFile.getAbsolutePath());
@@ -248,26 +254,26 @@
}
}
- rcml.checkOutIn(RCML.ci, identity, time, backup);
+ rcml.checkOutIn(RCML.ci, identity, time, backup, newVersion);
rcml.pruneEntries(this.backupDir);
rcml.write();
} catch (final FileNotFoundException e) {
- log.error("File not found" +e.toString());
+ log.error("File not found" + e.toString());
} catch (final IOException e) {
- log.error("IO error " +e.toString());
+ log.error("IO error " + e.toString());
} finally {
- if (in != null)
- in.close();
- if (out != null)
- out.close();
+ if (in != null)
+ in.close();
+ if (out != null)
+ out.close();
}
return time;
}
/**
- * Get the absolute path of a backup version
- * @param time The time of the backup
+ * Get the absolute path of a backup version
+ * @param time The time of the backup
* @param filename The path of the file from the {publication}
* @return String The absolute path of the backup version
*/
@@ -277,8 +283,8 @@
}
/**
- * Get the file of a backup version
- * @param time The time of the backup
+ * Get the file of a backup version
+ * @param time The time of the backup
* @param filename The path of the file from the {publication}
* @return File The file of the backup version
*/
@@ -288,7 +294,7 @@
}
/**
- * Rolls back to the given point in time.
+ * Rolls back to the given point in time.
* @param destination File which will be rolled back
* @param identity The identity of the user
* @param backupFlag If true, a backup of the current version will be made before the rollback
@@ -300,12 +306,9 @@
* @exception Exception if another problem occurs
*/
public long rollback(String destination, String identity, boolean backupFlag, long time)
- throws
- FileReservedCheckInException,
- FileReservedCheckOutException,
- FileNotFoundException,
- Exception {
-
+ throws FileReservedCheckInException, FileReservedCheckOutException,
+ FileNotFoundException, Exception {
+
FileInputStream in = null;
FileOutputStream out = null;
@@ -335,22 +338,22 @@
out.write(buffer, 0, length);
}
} catch (FileNotFoundException e) {
- log.error("File not found " +e.toString());
+ log.error("File not found " + e.toString());
} catch (IOException e) {
- log.error("IO error " +e.toString());
+ log.error("IO error " + e.toString());
} catch (Exception e) {
- log.error("Exception " +e.toString());
+ log.error("Exception " + e.toString());
} finally {
- if (in != null)
- in.close();
- if (out != null)
- out.close();
+ if (in != null)
+ in.close();
+ if (out != null)
+ out.close();
}
// Try to check back in, this might cause
// a backup of the current version to be created if
// desired by the user.
- long newtime = reservedCheckIn(destination, identity, backupFlag);
+ long newtime = reservedCheckIn(destination, identity, backupFlag, false);
return newtime;
}
@@ -359,8 +362,8 @@
* Delete the check in and roll back the file to the backup at time
* @param time The time point of the back version we want to retrieve
* @param destination The File for which we want undo the check in
- * @exception Exception FileNotFoundException if the back version or the current version
- * couldn't be found
+ * @exception Exception FileNotFoundException if the back version or the current version
+ * couldn't be found
*/
public void undoCheckIn(long time, String destination) throws Exception {
FileInputStream in = null;
@@ -392,55 +395,54 @@
rcml.deleteFirstCheckIn();
} catch (FileNotFoundException e) {
- log.error("File not found " +e.toString());
+ log.error("File not found " + e.toString());
} catch (IOException e) {
- log.error("IO error " +e.toString());
+ log.error("IO error " + e.toString());
} catch (Exception e) {
- log.error("Exception " +e.toString());
+ log.error("Exception " + e.toString());
} finally {
- if (in != null)
- in.close();
- if (out != null)
- out.close();
+ if (in != null)
+ in.close();
+ if (out != null)
+ out.close();
}
}
/**
* delete the revisions
- * @param filename of the document
- * @throws RevisionControlException when somthing went wrong
- */
- public void deleteRevisions(String filename) throws RevisionControlException{
+ * @param filename of the document
+ * @throws RevisionControlException when somthing went wrong
+ */
+ public void deleteRevisions(String filename) throws RevisionControlException {
try {
- RCML rcml = this.getRCML(filename);
+ RCML rcml = this.getRCML(filename);
String[] times = rcml.getBackupsTime();
- for (int i=0; i < times.length; i++) {
+ for (int i = 0; i < times.length; i++) {
long time = new Long(times[i]).longValue();
File backup = this.getBackupFile(time, filename);
- File parentDirectory = null;
- parentDirectory = backup.getParentFile();
+ File parentDirectory = null;
+ parentDirectory = backup.getParentFile();
boolean deleted = backup.delete();
if (!deleted) {
- throw new RevisionControlException("The backup file, "+backup.getCanonicalPath()+" could not be deleted!");
+ throw new RevisionControlException("The backup file, "
+ + backup.getCanonicalPath() + " could not be deleted!");
}
- if (parentDirectory != null
- && parentDirectory.exists()
- && parentDirectory.isDirectory()
- && parentDirectory.listFiles().length == 0) {
- parentDirectory.delete();
+ if (parentDirectory != null && parentDirectory.exists()
+ && parentDirectory.isDirectory() && parentDirectory.listFiles().length == 0) {
+ parentDirectory.delete();
}
}
- } catch (Exception e) {
+ } catch (Exception e) {
throw new RevisionControlException(e);
- }
+ }
}
-
+
/**
* delete the rcml file
- * @param filename of the document
- * @throws RevisionControlException if something went wrong
- */
- public void deleteRCML(String filename) throws RevisionControlException{
+ * @param filename of the document
+ * @throws RevisionControlException if something went wrong
+ */
+ public void deleteRCML(String filename) throws RevisionControlException {
try {
RCML rcml = this.getRCML(filename);
boolean deleted = rcml.delete();
@@ -451,5 +453,5 @@
throw new RevisionControlException(e);
}
}
-
-}
+
+}
\ No newline at end of file
Modified: lenya/trunk/src/java/org/apache/lenya/cms/site/tree/DefaultSiteTree.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/site/tree/DefaultSiteTree.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/site/tree/DefaultSiteTree.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/site/tree/DefaultSiteTree.java Fri Apr 1 05:30:25 2005
@@ -28,10 +28,17 @@
import org.apache.avalon.framework.container.ContainerUtil;
import org.apache.avalon.framework.logger.AbstractLogEnabled;
+import org.apache.lenya.ac.Identity;
+import org.apache.lenya.ac.User;
import org.apache.lenya.cms.publication.Publication;
+import org.apache.lenya.cms.rc.RCEnvironment;
+import org.apache.lenya.cms.rc.RevisionController;
import org.apache.lenya.cms.site.Label;
import org.apache.lenya.cms.site.SiteException;
+import org.apache.lenya.transaction.IdentityMap;
+import org.apache.lenya.transaction.Lock;
import org.apache.lenya.transaction.TransactionException;
+import org.apache.lenya.transaction.UnitOfWork;
import org.apache.lenya.xml.DocumentHelper;
import org.apache.lenya.xml.NamespaceHelper;
import org.apache.xpath.XPathAPI;
@@ -64,6 +71,13 @@
// the area is only retained to provide some more info when raising an
// exception.
private String area = "";
+ private IdentityMap identityMap;
+ private Publication publication;
+
+ protected void setup(IdentityMap map, Publication publication) {
+ this.identityMap = map;
+ this.publication = publication;
+ }
/**
* Create a DefaultSiteTree
@@ -549,48 +563,82 @@
* @see org.apache.lenya.transaction.Transactionable#checkin()
*/
public void checkin() throws TransactionException {
- // TODO Auto-generated method stub
+ checkin(true);
+ }
+ protected void checkin(boolean backup) throws TransactionException {
+ try {
+ String userName = getUserID();
+ boolean newVersion = this.identityMap.getUnitOfWork().isDirty(this);
+ getRevisionController().reservedCheckIn(getRCPath(), userName, backup, newVersion);
+ } catch (Exception e) {
+ throw new TransactionException(e);
+ }
+ }
+
+ /**
+ * @return The username of the unit of work's identity.
+ */
+ protected String getUserID() {
+ String userName = null;
+ UnitOfWork unit = this.identityMap.getUnitOfWork();
+ Identity identity = unit.getIdentity();
+ User user = identity.getUser();
+ if (user != null) {
+ userName = user.getId();
+ }
+ return userName;
}
/**
* @see org.apache.lenya.transaction.Transactionable#checkout()
*/
public void checkout() throws TransactionException {
- // TODO Auto-generated method stub
-
+ try {
+ String userName = getUserID();
+ getRevisionController().reservedCheckOut(getRCPath(), userName);
+ } catch (Exception e) {
+ throw new TransactionException(e);
+ }
+ }
+
+ protected String getRCPath() {
+ return this.area + "/" + SITE_TREE_FILENAME;
}
/**
* @see org.apache.lenya.transaction.Transactionable#isCheckedOut()
*/
public boolean isCheckedOut() throws TransactionException {
- // TODO Auto-generated method stub
- return false;
+ try {
+ String userName = getUserID();
+ return !getRevisionController().canCheckOut(getRCPath(), userName);
+ } catch (Exception e) {
+ throw new TransactionException(e);
+ }
}
+ private Lock lock;
+
/**
* @see org.apache.lenya.transaction.Transactionable#lock()
*/
public void lock() throws TransactionException {
- // TODO Auto-generated method stub
-
+ this.lock = new Lock(getVersion());
}
/**
* @see org.apache.lenya.transaction.Transactionable#unlock()
*/
public void unlock() throws TransactionException {
- // TODO Auto-generated method stub
-
+ this.lock = null;
}
/**
* @see org.apache.lenya.transaction.Transactionable#isLocked()
*/
public boolean isLocked() throws TransactionException {
- // TODO Auto-generated method stub
- return false;
+ return this.lock != null;
}
/**
@@ -612,4 +660,44 @@
public void create() throws TransactionException {
}
+ private RevisionController revisionController;
+
+ protected RevisionController getRevisionController() throws TransactionException {
+ if (this.revisionController == null) {
+ try {
+ String publicationPath = this.publication.getDirectory().getCanonicalPath();
+ RCEnvironment rcEnvironment = RCEnvironment.getInstance(this.publication
+ .getServletContext().getCanonicalPath());
+ String rcmlDirectory = publicationPath + File.separator
+ + rcEnvironment.getRCMLDirectory();
+ String backupDirectory = publicationPath + File.separator
+ + rcEnvironment.getBackupDirectory();
+
+ this.revisionController = new RevisionController(rcmlDirectory, backupDirectory,
+ publicationPath);
+ } catch (IOException e) {
+ throw new TransactionException(e);
+ }
+ }
+ return this.revisionController;
+ }
+
+ /**
+ * @see org.apache.lenya.transaction.Transactionable#getLock()
+ */
+ public Lock getLock() {
+ return this.lock;
+ }
+
+ /**
+ * @see org.apache.lenya.transaction.Transactionable#getVersion()
+ */
+ public int getVersion() throws TransactionException {
+ try {
+ String fileName = this.treefile.getCanonicalPath();
+ return getRevisionController().getLatestVersion(fileName);
+ } catch (Exception e) {
+ throw new TransactionException(e);
+ }
+ }
}
Modified: lenya/trunk/src/java/org/apache/lenya/cms/site/tree/SiteTreeFactory.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/site/tree/SiteTreeFactory.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/site/tree/SiteTreeFactory.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/site/tree/SiteTreeFactory.java Fri Apr 1 05:30:25 2005
@@ -58,7 +58,7 @@
SourceResolver resolver = null;
Source source = null;
- SiteTree tree;
+ DefaultSiteTree tree;
try {
resolver = (SourceResolver) this.manager.lookup(SourceResolver.ROLE);
source = resolver.resolveURI("context://");
@@ -69,6 +69,7 @@
.getAbsolutePath());
tree = new DefaultSiteTree(publication.getDirectory(), area);
+ tree.setup(map, publication);
ContainerUtil.enableLogging(tree, getLogger());
} finally {
Modified: lenya/trunk/src/java/org/apache/lenya/cms/site/tree/TreeSiteManager.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/site/tree/TreeSiteManager.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/site/tree/TreeSiteManager.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/site/tree/TreeSiteManager.java Fri Apr 1 05:30:25 2005
@@ -32,6 +32,7 @@
import org.apache.lenya.cms.site.AbstractSiteManager;
import org.apache.lenya.cms.site.Label;
import org.apache.lenya.cms.site.SiteException;
+import org.apache.lenya.transaction.TransactionException;
import org.apache.lenya.transaction.TransactionableFactory;
/**
@@ -60,15 +61,16 @@
public SiteTree getTree(DocumentIdentityMap map, Publication publication, String area)
throws SiteException {
+ String key = getKey(publication, area);
+ DefaultSiteTree sitetree;
TransactionableFactory factory = map.getFactory(SiteTree.TRANSACTIONABLE_TYPE);
if (factory == null) {
factory = new SiteTreeFactory(this.manager);
ContainerUtil.enableLogging(factory, getLogger());
map.setFactory(SiteTree.TRANSACTIONABLE_TYPE, factory);
}
+ sitetree = (DefaultSiteTree) map.get(SiteTree.TRANSACTIONABLE_TYPE, key);
- String key = getKey(publication, area);
- DefaultSiteTree sitetree = (DefaultSiteTree) map.get(SiteTree.TRANSACTIONABLE_TYPE, key);
return sitetree;
}
@@ -240,7 +242,11 @@
destinationTree.setLabel(destinationDocument.getId(), label);
}
- sourceDocument.getIdentityMap().getUnitOfWork().registerDirty(destinationTree);
+ try {
+ sourceDocument.getIdentityMap().getUnitOfWork().registerDirty(destinationTree);
+ } catch (TransactionException e) {
+ throw new SiteException(e);
+ }
}
/**
@@ -273,8 +279,11 @@
if (node.getLabels().length == 0) {
tree.removeNode(document.getId());
}
-
- document.getIdentityMap().getUnitOfWork().registerDirty(tree);
+ try {
+ document.getIdentityMap().getUnitOfWork().registerDirty(tree);
+ } catch (TransactionException e) {
+ throw new SiteException(e);
+ }
}
/**
@@ -295,7 +304,11 @@
SiteTree tree = getTree(document);
tree.setLabel(document.getId(), labelObject);
- document.getIdentityMap().getUnitOfWork().registerDirty(tree);
+ try {
+ document.getIdentityMap().getUnitOfWork().registerDirty(tree);
+ } catch (TransactionException e) {
+ throw new SiteException(e);
+ }
}
/**
@@ -357,7 +370,11 @@
if (node == null) {
Label[] labels = { label };
tree.addNode(document.getId(), labels, null, null, false);
- document.getIdentityMap().getUnitOfWork().registerDirty(tree);
+ try {
+ document.getIdentityMap().getUnitOfWork().registerDirty(tree);
+ } catch (TransactionException e) {
+ throw new SiteException(e);
+ }
} else {
tree.addLabel(document.getId(), label);
}
Modified: lenya/trunk/src/java/org/apache/lenya/cms/usecase/AbstractUsecase.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/usecase/AbstractUsecase.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/usecase/AbstractUsecase.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/usecase/AbstractUsecase.java Fri Apr 1 05:30:25 2005
@@ -29,6 +29,7 @@
import org.apache.avalon.framework.context.Context;
import org.apache.avalon.framework.context.ContextException;
import org.apache.avalon.framework.context.Contextualizable;
+import org.apache.avalon.framework.service.ServiceException;
import org.apache.cocoon.components.ContextHelper;
import org.apache.cocoon.environment.Request;
import org.apache.cocoon.environment.Session;
@@ -201,11 +202,11 @@
clearInfoMessages();
doExecute();
dumpErrorMessages();
-
+
if (getErrorMessages().size() == 0) {
getUnitOfWork().commit();
}
-
+
} catch (Exception e) {
getLogger().error(e.getMessage(), e);
addErrorMessage(e.getMessage() + " - Please consult the logfiles.");
@@ -405,19 +406,21 @@
this.context = _context;
}
- private DocumentIdentityMap documentIdentityMap;
-
protected DocumentIdentityMap getDocumentIdentityMap() {
- return this.documentIdentityMap;
+ try {
+ return (DocumentIdentityMap) getUnitOfWork().getIdentityMap();
+ } catch (ServiceException e) {
+ throw new RuntimeException(e);
+ }
}
-
+
/**
* @see org.apache.avalon.framework.activity.Initializable#initialize()
*/
public final void initialize() throws Exception {
super.initialize();
- this.documentIdentityMap = new DocumentIdentityMap(this.manager, getLogger());
- getUnitOfWork().addIdentityMap(this.documentIdentityMap);
+ DocumentIdentityMap map = new DocumentIdentityMap(this.manager, getLogger());
+ getUnitOfWork().setIdentityMap(map);
Request request = ContextHelper.getRequest(this.context);
Session session = request.getSession(true);
Identity identity = (Identity) session.getAttribute(Identity.class.getName());
Modified: lenya/trunk/src/java/org/apache/lenya/cms/workflow/History.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/cms/workflow/History.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/cms/workflow/History.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/cms/workflow/History.java Fri Apr 1 05:30:25 2005
@@ -226,7 +226,6 @@
Element versionElement = versions[i].getVersionElement(helper);
documentElement.appendChild(versionElement);
}
-System.out.println("Saving file [" + getHistoryFile().getAbsolutePath() + "]");
DocumentHelper.writeDocument(helper.getDocument(), getHistoryFile());
} catch (final Exception e) {
throw new RuntimeException(e);
Modified: lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMap.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMap.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMap.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMap.java Fri Apr 1 05:30:25 2005
@@ -54,5 +54,10 @@
* @param unit The unit of work to use.
*/
void setUnitOfWork(UnitOfWork unit);
+
+ /**
+ * @return All objects in this map.
+ */
+ Transactionable[] getObjects();
}
Modified: lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMapImpl.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMapImpl.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMapImpl.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/transaction/IdentityMapImpl.java Fri Apr 1 05:30:25 2005
@@ -17,7 +17,10 @@
package org.apache.lenya.transaction;
import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
import java.util.Map;
+import java.util.Set;
import org.apache.avalon.framework.logger.AbstractLogEnabled;
@@ -43,6 +46,7 @@
if (transactionable == null) {
try {
transactionable = getFactory(type).build(this, key);
+ transactionable.lock();
} catch (Exception e) {
throw new RuntimeException(e);
}
@@ -82,6 +86,20 @@
*/
public void setUnitOfWork(UnitOfWork unit) {
this.unitOfWork = unit;
+ }
+
+ /**
+ * @see org.apache.lenya.transaction.IdentityMap#getObjects()
+ */
+ public Transactionable[] getObjects() {
+ Set objects = new HashSet();
+ for (Iterator i = this.maps.values().iterator(); i.hasNext(); ) {
+ Map map = (Map) i.next();
+ for (Iterator j = map.values().iterator(); j.hasNext(); ) {
+ objects.add(j.next());
+ }
+ }
+ return (Transactionable[]) objects.toArray(new Transactionable[objects.size()]);
}
}
Added: lenya/trunk/src/java/org/apache/lenya/transaction/Lock.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/transaction/Lock.java?view=auto&rev=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/transaction/Lock.java (added)
+++ lenya/trunk/src/java/org/apache/lenya/transaction/Lock.java Fri Apr 1 05:30:25 2005
@@ -0,0 +1,43 @@
+/*
+ * Copyright 1999-2004 The Apache Software Foundation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+package org.apache.lenya.transaction;
+
+/**
+ * A lock on a transactionable.
+ *
+ * @version $Id:$
+ */
+public class Lock {
+
+ /**
+ * Ctor.
+ * @param version The version of the transactionable when it was locked.
+ */
+ public Lock(int version) {
+ this.version = version;
+ }
+
+ private int version;
+
+ /**
+ * @return The version number.
+ */
+ public int getVersion() {
+ return this.version;
+ }
+
+}
Modified: lenya/trunk/src/java/org/apache/lenya/transaction/Transactionable.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/transaction/Transactionable.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/transaction/Transactionable.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/transaction/Transactionable.java Fri Apr 1 05:30:25 2005
@@ -66,6 +66,11 @@
void lock() throws TransactionException;
/**
+ * @return The lock which is held by this object.
+ */
+ Lock getLock();
+
+ /**
* Unlocks this object.
* @throws TransactionException if an error occurs.
*/
@@ -81,5 +86,11 @@
* @return The type of the transactionable.
*/
String getTransactionableType();
+
+ /**
+ * @return The latest version.
+ * @throws TransactionException if an error occurs.
+ */
+ int getVersion() throws TransactionException;
}
Modified: lenya/trunk/src/java/org/apache/lenya/transaction/UnitOfWork.java
URL: http://svn.apache.org/viewcvs/lenya/trunk/src/java/org/apache/lenya/transaction/UnitOfWork.java?view=diff&r1=159684&r2=159685
==============================================================================
--- lenya/trunk/src/java/org/apache/lenya/transaction/UnitOfWork.java (original)
+++ lenya/trunk/src/java/org/apache/lenya/transaction/UnitOfWork.java Fri Apr 1 05:30:25 2005
@@ -38,34 +38,36 @@
String ROLE = UnitOfWork.class.getName();
/**
- * Returns the identity maps.
- * @return An array of identity maps.
+ * Returns the identity map.
+ * @return An identity map.
*/
- IdentityMap[] getIdentityMaps();
+ IdentityMap getIdentityMap();
/**
- * Adds an identity map.
- * @param map The map to add.
+ * @param map The identity map to use.
*/
- void addIdentityMap(IdentityMap map);
-
+ void setIdentityMap(IdentityMap map);
+
/**
* Registers an object as new.
* @param object The object.
+ * @throws TransactionException if an error occurs.
*/
- void registerNew(Transactionable object);
+ void registerNew(Transactionable object) throws TransactionException;
/**
* Registers an object as modified.
* @param object The object.
+ * @throws TransactionException if an error occurs.
*/
- void registerDirty(Transactionable object);
+ void registerDirty(Transactionable object) throws TransactionException;
/**
* Registers an object as removed.
* @param object The object.
+ * @throws TransactionException if an error occurs.
*/
- void registerRemoved(Transactionable object);
+ void registerRemoved(Transactionable object) throws TransactionException;
/**
* Commits the transaction.
@@ -82,4 +84,10 @@
* @param identity The identity.
*/
void setIdentity(Identity identity);
+
+ /**
+ * @param transactionable A transactionable.
+ * @return If the transactionable is registered as dirty.
+ */
+ boolean isDirty(Transactionable transactionable);
}
---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@lenya.apache.org
For additional commands, e-mail: commits-help@lenya.apache.org