http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/ObjectAdapterMemento.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/ObjectAdapterMemento.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/ObjectAdapterMemento.java deleted file mode 100644 index 107bde0..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/ObjectAdapterMemento.java +++ /dev/null @@ -1,458 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.mementos; - -import java.io.Serializable; -import java.util.List; - -import com.google.common.base.Function; - -import org.apache.isis.core.commons.ensure.Ensure; -import org.apache.isis.core.metamodel.adapter.ObjectAdapter; -import org.apache.isis.core.metamodel.adapter.mgr.AdapterManager; -import org.apache.isis.core.metamodel.adapter.mgr.AdapterManager.ConcurrencyChecking; -import org.apache.isis.core.metamodel.adapter.oid.Oid; -import org.apache.isis.core.metamodel.adapter.oid.OidMarshaller; -import org.apache.isis.core.metamodel.adapter.oid.RootOid; -import org.apache.isis.core.metamodel.adapter.oid.TypedOid; -import org.apache.isis.core.metamodel.facets.object.encodeable.EncodableFacet; -import org.apache.isis.core.metamodel.spec.ObjectSpecId; -import org.apache.isis.core.metamodel.spec.ObjectSpecification; -import org.apache.isis.core.metamodel.spec.feature.ObjectAction; -import org.apache.isis.core.metamodel.spec.feature.ObjectActionParameter; -import org.apache.isis.core.metamodel.spec.feature.OneToManyAssociation; -import org.apache.isis.core.metamodel.spec.feature.OneToOneAssociation; -import org.apache.isis.core.runtime.memento.Memento; -import org.apache.isis.core.runtime.system.context.IsisContext; -import org.apache.isis.core.runtime.system.persistence.PersistenceSession; - -public class ObjectAdapterMemento implements Serializable { - - private static final long serialVersionUID = 1L; - - /** - * Factory method - */ - public static ObjectAdapterMemento createOrNull(final ObjectAdapter adapter) { - if (adapter == null) { - return null; - } - return new ObjectAdapterMemento(adapter); - } - - /** - * Factory method - */ - public static ObjectAdapterMemento createPersistent(final RootOid rootOid) { - return new ObjectAdapterMemento(rootOid); - } - - - - enum Type { - /** - * The {@link ObjectAdapter} that this is the memento for directly has - * an {@link EncodableFacet} (it is almost certainly a value), and so is - * stored directly. - */ - ENCODEABLE { - @Override - ObjectAdapter recreateAdapter(final ObjectAdapterMemento oam, ConcurrencyChecking concurrencyChecking) { - ObjectSpecId objectSpecId = oam.objectSpecId; - ObjectSpecification objectSpec = SpecUtils.getSpecificationFor(objectSpecId); - final EncodableFacet encodableFacet = objectSpec.getFacet(EncodableFacet.class); - return encodableFacet.fromEncodedString(oam.encodableValue); - } - - @Override - public boolean equals(ObjectAdapterMemento oam, ObjectAdapterMemento other) { - return other.type == ENCODEABLE && oam.encodableValue.equals(other.encodableValue); - } - - @Override - public int hashCode(ObjectAdapterMemento oam) { - return oam.encodableValue.hashCode(); - } - - @Override - public String toString(final ObjectAdapterMemento oam) { - return oam.encodableValue; - } - - @Override - public void resetVersion(ObjectAdapterMemento objectAdapterMemento) { - } - }, - /** - * The {@link ObjectAdapter} that this is for is already known by its - * (persistent) {@link Oid}. - */ - PERSISTENT { - @Override - ObjectAdapter recreateAdapter(final ObjectAdapterMemento oam, ConcurrencyChecking concurrencyChecking) { - TypedOid oid = getOidMarshaller().unmarshal(oam.persistentOidStr, TypedOid.class); - try { - final ObjectAdapter adapter = getAdapterManager().adapterFor(oid, concurrencyChecking); - return adapter; - - } finally { - // a side-effect of AdapterManager#adapterFor(...) is that it will update the oid - // with the correct version, even when there is a concurrency exception - // we copy this updated oid string into our memento so that, if we retry, - // we will succeed second time around - - oam.persistentOidStr = oid.enString(getOidMarshaller()); - } - } - - @Override - public void resetVersion(ObjectAdapterMemento oam) { - // REVIEW: this may be redundant because recreateAdapter also guarantees the version will be reset. - final ObjectAdapter adapter = recreateAdapter(oam, ConcurrencyChecking.NO_CHECK); - Oid oid = adapter.getOid(); - oam.persistentOidStr = oid.enString(getOidMarshaller()); - } - - @Override - public boolean equals(ObjectAdapterMemento oam, ObjectAdapterMemento other) { - return other.type == PERSISTENT && oam.persistentOidStr.equals(other.persistentOidStr); - } - - @Override - public int hashCode(ObjectAdapterMemento oam) { - return oam.persistentOidStr.hashCode(); - } - - @Override - public String toString(final ObjectAdapterMemento oam) { - return oam.persistentOidStr; - } - - }, - /** - * Uses Isis' own {@link Memento}, to capture the state of a transient - * object. - */ - TRANSIENT { - /** - * {@link ConcurrencyChecking} is ignored for transients. - */ - @Override - ObjectAdapter recreateAdapter(final ObjectAdapterMemento oam, ConcurrencyChecking concurrencyChecking) { - return oam.transientMemento.recreateObject(); - } - - @Override - public boolean equals(ObjectAdapterMemento oam, ObjectAdapterMemento other) { - return other.type == TRANSIENT && oam.transientMemento.equals(other.transientMemento); - } - - @Override - public int hashCode(ObjectAdapterMemento oam) { - return oam.transientMemento.hashCode(); - } - - @Override - public String toString(final ObjectAdapterMemento oam) { - return oam.transientMemento.toString(); - } - - @Override - public void resetVersion(ObjectAdapterMemento objectAdapterMemento) { - } - }; - - public synchronized ObjectAdapter getAdapter(final ObjectAdapterMemento nom, ConcurrencyChecking concurrencyChecking) { - return recreateAdapter(nom, concurrencyChecking); - } - - abstract ObjectAdapter recreateAdapter(ObjectAdapterMemento nom, ConcurrencyChecking concurrencyChecking); - - public abstract boolean equals(ObjectAdapterMemento oam, ObjectAdapterMemento other); - public abstract int hashCode(ObjectAdapterMemento objectAdapterMemento); - - public abstract String toString(ObjectAdapterMemento adapterMemento); - - public abstract void resetVersion(ObjectAdapterMemento objectAdapterMemento); - } - - private Type type; - - private final ObjectSpecId objectSpecId; - private String titleHint; - - /** - * The current value, if {@link Type#ENCODEABLE}. - * - * <p> - * Will be <tt>null</tt> otherwise. - */ - private String encodableValue; - - /** - * The current value, if {@link Type#PERSISTENT}. - * - * <p> - * Will be <tt>null</tt> otherwise. - */ - private String persistentOidStr; - - /** - * The current value, if {@link Type#TRANSIENT}. - * - * <p> - * Will be <tt>null</tt> otherwise. - */ - private Memento transientMemento; - - private ObjectAdapterMemento(final RootOid rootOid) { - Ensure.ensureThatArg(rootOid, Oid.Matchers.isPersistent()); - this.persistentOidStr = rootOid.enString(getOidMarshaller()); - this.objectSpecId = rootOid.getObjectSpecId(); - this.type = Type.PERSISTENT; - } - - private ObjectAdapterMemento(final ObjectAdapter adapter) { - if (adapter == null) { - throw new IllegalArgumentException("adapter cannot be null"); - } - final ObjectSpecification specification = adapter.getSpecification(); - objectSpecId = specification.getSpecId(); - init(adapter); - } - - private void init(final ObjectAdapter adapter) { - - final ObjectSpecification specification = adapter.getSpecification(); - - final EncodableFacet encodableFacet = specification.getFacet(EncodableFacet.class); - final boolean isEncodable = encodableFacet != null; - if (isEncodable) { - encodableValue = encodableFacet.toEncodedString(adapter); - type = Type.ENCODEABLE; - return; - } - - final RootOid oid = (RootOid) adapter.getOid(); - if (oid.isTransient()) { - transientMemento = new Memento(adapter); - type = Type.TRANSIENT; - return; - } - - persistentOidStr = oid.enString(getOidMarshaller()); - type = Type.PERSISTENT; - } - - public void resetVersion() { - type.resetVersion(this); - } - - - /** - * Lazily looks up {@link ObjectAdapter} if required. - * - * <p> - * For transient objects, be aware that calling this method more than once - * will cause the underlying {@link ObjectAdapter} to be recreated, - * overwriting any changes that may have been made. In general then it's - * best to call once and then hold onto the value thereafter. Alternatively, - * can call {@link #setAdapter(ObjectAdapter)} to keep this memento in sync. - */ - public ObjectAdapter getObjectAdapter(ConcurrencyChecking concurrencyChecking) { - return type.getAdapter(this, concurrencyChecking); - } - - /** - * Updates the memento if the adapter's state has changed. - * - * <p> - * This is a no-op for - * - * @param adapter - */ - public void setAdapter(final ObjectAdapter adapter) { - init(adapter); - } - - public ObjectSpecId getObjectSpecId() { - return objectSpecId; - } - - /** - * Analogous to {@link List#contains(Object)}, but does not perform - * {@link ConcurrencyChecking concurrency checking} of the OID. - */ - public boolean containedIn(List<ObjectAdapterMemento> list) { - // REVIEW: heavy handed, ought to be possible to just compare the OIDs - // ignoring the concurrency checking - final ObjectAdapter currAdapter = getObjectAdapter(ConcurrencyChecking.NO_CHECK); - for (ObjectAdapterMemento each : list) { - if(each == null) { - continue; - } - final ObjectAdapter otherAdapter = each.getObjectAdapter(ConcurrencyChecking.NO_CHECK); - if(currAdapter == otherAdapter) { - return true; - } - } - return false; - } - - @Override - public int hashCode() { - return type.hashCode(this); - } - - @Override - public boolean equals(Object obj) { - return (obj instanceof ObjectAdapterMemento) && type.equals(this, (ObjectAdapterMemento)obj); - } - - - @Override - public String toString() { - return asString(); - } - - public String asString() { - return type.toString(this); - } - - - ////////////////////////////////////////////////// - // Functions - ////////////////////////////////////////////////// - - - public final static class Functions { - - private Functions() { - } - - public static Function<ObjectSpecification, ObjectSpecId> fromSpec() { - return new Function<ObjectSpecification, ObjectSpecId>() { - - @Override - public ObjectSpecId apply(final ObjectSpecification from) { - return from.getSpecId(); - } - }; - } - - public static Function<OneToOneAssociation, PropertyMemento> fromProperty() { - return new Function<OneToOneAssociation, PropertyMemento>() { - @Override - public PropertyMemento apply(final OneToOneAssociation from) { - return new PropertyMemento(from); - } - }; - } - - public static Function<OneToManyAssociation, CollectionMemento> fromCollection() { - return new Function<OneToManyAssociation, CollectionMemento>() { - @Override - public CollectionMemento apply(final OneToManyAssociation from) { - return new CollectionMemento(from); - } - }; - } - - public static Function<ObjectAction, ActionMemento> fromAction() { - return new Function<ObjectAction, ActionMemento>() { - @Override - public ActionMemento apply(final ObjectAction from) { - return new ActionMemento(from); - } - }; - } - - public static Function<ObjectActionParameter, ActionParameterMemento> fromActionParameter() { - return new Function<ObjectActionParameter, ActionParameterMemento>() { - @Override - public ActionParameterMemento apply(final ObjectActionParameter from) { - return new ActionParameterMemento(from); - } - }; - } - - public static Function<Object, ObjectAdapterMemento> fromPojo(final AdapterManager adapterManager) { - return new Function<Object, ObjectAdapterMemento>() { - @Override - public ObjectAdapterMemento apply(final Object pojo) { - final ObjectAdapter adapter = adapterManager.adapterFor(pojo); - return ObjectAdapterMemento.createOrNull(adapter); - } - }; - } - - public static Function<ObjectAdapter, ObjectAdapterMemento> fromAdapter() { - return new Function<ObjectAdapter, ObjectAdapterMemento>() { - @Override - public ObjectAdapterMemento apply(final ObjectAdapter adapter) { - return ObjectAdapterMemento.createOrNull(adapter); - } - }; - } - - - public static Function<ObjectAdapterMemento, ObjectAdapter> fromMemento(final ConcurrencyChecking concurrencyChecking) { - return new Function<ObjectAdapterMemento, ObjectAdapter>() { - @Override - public ObjectAdapter apply(final ObjectAdapterMemento from) { - return from.getObjectAdapter(concurrencyChecking); - } - }; - } - - public static Function<ObjectAdapter, ObjectAdapterMemento> toMemento() { - return new Function<ObjectAdapter, ObjectAdapterMemento>() { - - @Override - public ObjectAdapterMemento apply(ObjectAdapter from) { - return ObjectAdapterMemento.createOrNull(from); - } - - }; - } - - } - - - ////////////////////////////////////////////////// - // Dependencies (from context) - ////////////////////////////////////////////////// - - private static AdapterManager getAdapterManager() { - return getPersistenceSession().getAdapterManager(); - } - - private static PersistenceSession getPersistenceSession() { - return IsisContext.getPersistenceSession(); - } - - public static OidMarshaller getOidMarshaller() { - return IsisContext.getOidMarshaller(); - } - - - - -}
http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PageParameterNames.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PageParameterNames.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PageParameterNames.java deleted file mode 100644 index 75f1a64..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PageParameterNames.java +++ /dev/null @@ -1,142 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.mementos; - -import java.util.List; - -import com.google.common.base.Function; -import com.google.common.collect.Lists; - -import org.apache.wicket.request.mapper.parameter.PageParameters; -import org.apache.wicket.util.string.StringValue; - -import org.apache.isis.core.commons.lang.StringExtensions; -import org.apache.isis.core.metamodel.adapter.oid.Oid; - -public enum PageParameterNames { - - /** - * The object's {@link Oid}. - * - * <p> - * Also encodes the object's spec, and whether the object is persistent or not. - */ - OBJECT_OID, - - /** - * Hints for the rendering of an entity. - */ - ANCHOR, - - /** - * Owning type of an action. - * - * <p> - * Whereas {@link #OBJECT_SPEC} is the concrete runtime type of the adapter, - * the owning type could be some superclass if the action has been - * inherited. - */ - ACTION_OWNING_SPEC, - - /** - * Whether user, exploration, prototype etc. - */ - ACTION_TYPE, - - /** - * The name of the action, along with its parameters. - */ - ACTION_ID, - - /** - * When a single object is returned, whether to redirect to it or simply inline it. - */ - ACTION_SINGLE_RESULTS_MODE, - - /** - * The argument acting as a context for a contributed action, if any. - * - * <p> - * In the format N=OBJECT_OID, where N is the 0-based action parameter - * index. - */ - ACTION_PARAM_CONTEXT, - - /** - * Action argument(s), if known. - */ - ACTION_ARGS; - - /** - * Returns the {@link #name()} formatted as - * {@link Strings#camelCase(String) camel case}. - * - * <p> - * For example, <tt>ACTION_TYPE</tt> becomes <tt>actionType</tt>. - */ - @Override - public String toString() { - return StringExtensions.toCamelCase(name()); - } - - public String getStringFrom(final PageParameters pageParameters) { - return getStringFrom(pageParameters, null); - } - - public String getStringFrom(PageParameters pageParameters, String defaultValue) { - if(pageParameters == null) { - return defaultValue; - } - return pageParameters.get(this.toString()).toString(defaultValue); - } - - public <T extends Enum<T>> T getEnumFrom(PageParameters pageParameters, Class<T> enumClass) { - String value = getStringFrom(pageParameters); - return value != null? Enum.valueOf(enumClass, value): null; - } - - public List<String> getListFrom(PageParameters pageParameters) { - return Lists.transform(pageParameters.getValues(this.toString()), new Function<StringValue, String>() { - @Override - public String apply(StringValue input) { - return input.toString(); - } - }); - } - - - public void addStringTo(final PageParameters pageParameters, final String value) { - pageParameters.add(this.toString(), value); - } - - public void addEnumTo(final PageParameters pageParameters, final Enum<?> someEnum) { - addStringTo(pageParameters, someEnum.name()); - } - - /** - * @param pageParameters - */ - public void removeFrom(PageParameters pageParameters) { - pageParameters.remove(this.toString()); - } - - - -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PropertyMemento.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PropertyMemento.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PropertyMemento.java deleted file mode 100644 index 6504be6..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/PropertyMemento.java +++ /dev/null @@ -1,123 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.mementos; - -import java.io.Serializable; - -import org.apache.isis.core.metamodel.spec.ObjectSpecId; -import org.apache.isis.core.metamodel.spec.ObjectSpecification; -import org.apache.isis.core.metamodel.spec.feature.OneToOneAssociation; -import org.apache.isis.core.runtime.system.context.IsisContext; -import org.apache.isis.viewer.wicket.model.models.EntityModel; - -public class PropertyMemento implements Serializable { - - private static final long serialVersionUID = 1L; - - private static ObjectSpecification owningSpecFor(final OneToOneAssociation association) { - return IsisContext.getSpecificationLoader().loadSpecification(association.getIdentifier().toClassIdentityString()); - } - - private final ObjectSpecId owningSpecId; - private final String identifier; - private final ObjectSpecId specId; - -// private transient OneToOneAssociation property; - - public PropertyMemento(final ObjectSpecId owningType, final String identifier) { - this(owningType, identifier, null); - } - - public PropertyMemento(final ObjectSpecId owningType, final String identifier, final ObjectSpecId type) { - this(owningType, identifier, type, propertyFor(owningType, identifier)); - } - - public PropertyMemento(final OneToOneAssociation property) { - this(owningSpecFor(property).getSpecId(), property.getIdentifier().toNameIdentityString(), property.getSpecification().getSpecId(), property); - } - - private PropertyMemento(final ObjectSpecId owningSpecId, final String name, final ObjectSpecId specId, final OneToOneAssociation property) { - this.owningSpecId = owningSpecId; - this.identifier = name; - this.specId = specId; -// this.property = property; - } - - public ObjectSpecId getOwningType() { - return owningSpecId; - } - - public ObjectSpecId getType() { - return specId; - } - - public String getIdentifier() { - return identifier; - } - - public OneToOneAssociation getProperty() { -// if (property == null) { -// property = propertyFor(owningSpecId, identifier); -// } -// return property; - return propertyFor(owningSpecId, identifier); - } - - private static OneToOneAssociation propertyFor(ObjectSpecId owningType, String identifier) { - return (OneToOneAssociation) SpecUtils.getSpecificationFor(owningType).getAssociation(identifier); - } - - /** - * Value semantics so can use as a key in {@link EntityModel} hash. - */ - @Override - public int hashCode() { - final int prime = 31; - int result = 1; - result = prime * result + ((identifier == null) ? 0 : identifier.hashCode()); - return result; - } - - /** - * Value semantics so can use as a key in {@link EntityModel} hash. - */ - @Override - public boolean equals(final Object obj) { - if (this == obj) { - return true; - } - if (obj == null) { - return false; - } - if (getClass() != obj.getClass()) { - return false; - } - final PropertyMemento other = (PropertyMemento) obj; - if (identifier == null) { - if (other.identifier != null) { - return false; - } - } else if (!identifier.equals(other.identifier)) { - return false; - } - return true; - } - -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/SpecUtils.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/SpecUtils.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/SpecUtils.java deleted file mode 100644 index 8e34386..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/mementos/SpecUtils.java +++ /dev/null @@ -1,44 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.mementos; - -import org.apache.isis.core.metamodel.spec.ObjectSpecId; -import org.apache.isis.core.metamodel.spec.ObjectSpecification; -import org.apache.isis.core.metamodel.spec.SpecificationLoaderSpi; -import org.apache.isis.core.runtime.system.context.IsisContext; - -public final class SpecUtils { - - private SpecUtils(){} - - public static ObjectSpecification getSpecificationFor(ObjectSpecId objectSpecId) { - ObjectSpecification objectSpec = getSpecificationLoader().lookupBySpecId(objectSpecId); - if(objectSpec != null) { - return objectSpec; - } - - // attempt to load directly. - return getSpecificationLoader().loadSpecification(objectSpecId.asString()); - } - - protected static SpecificationLoaderSpi getSpecificationLoader() { - return IsisContext.getSpecificationLoader(); - } - -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/AboutModel.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/AboutModel.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/AboutModel.java deleted file mode 100644 index 7ca84ab..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/AboutModel.java +++ /dev/null @@ -1,47 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -/** - * Model providing welcome text. - */ -public class AboutModel extends ModelAbstract<String> { - - private static final long serialVersionUID = 1L; - - public AboutModel(String message) { - super(); - setObject(message); - } - - @Override - protected String load() { - return getObject(); - } - - @Override - public void setObject(final String message) { - if(message == null) { - return; - } - super.setObject(message); - } - -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionExecutor.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionExecutor.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionExecutor.java deleted file mode 100644 index d634262..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionExecutor.java +++ /dev/null @@ -1,35 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -import java.io.Serializable; - -import org.apache.wicket.ajax.AjaxRequestTarget; -import org.apache.wicket.markup.html.form.Form; - -/** - * Decouples the {@link ActionModel}, which needs to delegate the actual - * execution of an action, from its implementor. - */ -public interface ActionExecutor extends Serializable { - - boolean executeActionAndProcessResults(AjaxRequestTarget target, Form<?> feedbackForm); - -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionModel.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionModel.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionModel.java deleted file mode 100644 index ee5e341..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionModel.java +++ /dev/null @@ -1,663 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -import java.io.ByteArrayInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Map.Entry; -import java.util.regex.Matcher; -import java.util.regex.Pattern; -import com.google.common.base.Throwables; -import com.google.common.collect.Iterables; -import com.google.common.collect.Lists; -import com.google.common.collect.Maps; -import org.apache.wicket.request.IRequestHandler; -import org.apache.wicket.request.handler.resource.ResourceStreamRequestHandler; -import org.apache.wicket.request.http.handler.RedirectRequestHandler; -import org.apache.wicket.request.mapper.parameter.PageParameters; -import org.apache.wicket.request.resource.ContentDisposition; -import org.apache.wicket.util.resource.AbstractResourceStream; -import org.apache.wicket.util.resource.IResourceStream; -import org.apache.wicket.util.resource.ResourceStreamNotFoundException; -import org.apache.wicket.util.resource.StringResourceStream; -import org.apache.isis.applib.Identifier; -import org.apache.isis.applib.RecoverableException; -import org.apache.isis.applib.annotation.ActionSemantics; -import org.apache.isis.applib.annotation.BookmarkPolicy; -import org.apache.isis.applib.annotation.Where; -import org.apache.isis.applib.value.Blob; -import org.apache.isis.applib.value.Clob; -import org.apache.isis.applib.value.NamedWithMimeType; -import org.apache.isis.core.commons.authentication.AuthenticationSession; -import org.apache.isis.core.metamodel.adapter.ObjectAdapter; -import org.apache.isis.core.metamodel.adapter.mgr.AdapterManager.ConcurrencyChecking; -import org.apache.isis.core.metamodel.adapter.oid.OidMarshaller; -import org.apache.isis.core.metamodel.adapter.oid.RootOid; -import org.apache.isis.core.metamodel.adapter.oid.RootOidDefault; -import org.apache.isis.core.metamodel.consent.Consent; -import org.apache.isis.core.metamodel.facets.object.bookmarkpolicy.BookmarkPolicyFacet; -import org.apache.isis.core.metamodel.facets.object.encodeable.EncodableFacet; -import org.apache.isis.core.metamodel.spec.ActionType; -import org.apache.isis.core.metamodel.spec.ObjectSpecId; -import org.apache.isis.core.metamodel.spec.ObjectSpecification; -import org.apache.isis.core.metamodel.spec.feature.ObjectAction; -import org.apache.isis.core.metamodel.spec.feature.ObjectActionParameter; -import org.apache.isis.core.runtime.system.context.IsisContext; -import org.apache.isis.viewer.wicket.model.common.PageParametersUtils; -import org.apache.isis.viewer.wicket.model.mementos.ActionMemento; -import org.apache.isis.viewer.wicket.model.mementos.ActionParameterMemento; -import org.apache.isis.viewer.wicket.model.mementos.ObjectAdapterMemento; -import org.apache.isis.viewer.wicket.model.mementos.PageParameterNames; - -/** - * Models an action invocation, either the gathering of arguments for the - * action's {@link Mode#PARAMETERS parameters}, or the handling of the - * {@link Mode#RESULTS results} once invoked. - */ -public class ActionModel extends BookmarkableModel<ObjectAdapter> { - - private static final long serialVersionUID = 1L; - - private static final String NULL_ARG = "$nullArg$"; - private static final Pattern KEY_VALUE_PATTERN = Pattern.compile("([^=]+)=(.+)"); - - /** - * Whether we are obtaining arguments (eg in a dialog), or displaying the - * results - */ - private enum Mode { - PARAMETERS, - RESULTS - } - - - - ////////////////////////////////////////////////// - // Factory methods - ////////////////////////////////////////////////// - - /** - * @param objectAdapter - * @param action - * @return - */ - public static ActionModel create(final ObjectAdapter objectAdapter, final ObjectAction action) { - final ObjectAdapterMemento serviceMemento = ObjectAdapterMemento.Functions.fromAdapter().apply(objectAdapter); - final ActionMemento homePageActionMemento = ObjectAdapterMemento.Functions.fromAction().apply(action); - final Mode mode = action.getParameterCount() > 0? Mode.PARAMETERS : Mode.RESULTS; - return new ActionModel(serviceMemento, homePageActionMemento, mode); - } - - public static ActionModel createForPersistent(final PageParameters pageParameters) { - return new ActionModel(pageParameters); - } - - /** - * Factory method for creating {@link PageParameters}. - * - * see {@link #ActionModel(PageParameters)} - */ - public static PageParameters createPageParameters( - final ObjectAdapter adapter, final ObjectAction objectAction, final ConcurrencyChecking concurrencyChecking) { - - final PageParameters pageParameters = PageParametersUtils.newPageParameters(); - - final String oidStr = concurrencyChecking == ConcurrencyChecking.CHECK? - adapter.getOid().enString(getOidMarshaller()): - adapter.getOid().enStringNoVersion(getOidMarshaller()); - PageParameterNames.OBJECT_OID.addStringTo(pageParameters, oidStr); - - final ActionType actionType = objectAction.getType(); - PageParameterNames.ACTION_TYPE.addEnumTo(pageParameters, actionType); - - final ObjectSpecification actionOnTypeSpec = objectAction.getOnType(); - if (actionOnTypeSpec != null) { - PageParameterNames.ACTION_OWNING_SPEC.addStringTo(pageParameters, actionOnTypeSpec.getFullIdentifier()); - } - - final String actionId = determineActionId(objectAction); - PageParameterNames.ACTION_ID.addStringTo(pageParameters, actionId); - - return pageParameters; - } - - - public static Entry<Integer, String> parse(final String paramContext) { - final Matcher matcher = KEY_VALUE_PATTERN.matcher(paramContext); - if (!matcher.matches()) { - return null; - } - - final int paramNum; - try { - paramNum = Integer.parseInt(matcher.group(1)); - } catch (final Exception e) { - // ignore - return null; - } - - final String oidStr; - try { - oidStr = matcher.group(2); - } catch (final Exception e) { - return null; - } - - return new Map.Entry<Integer, String>() { - - @Override - public Integer getKey() { - return paramNum; - } - - @Override - public String getValue() { - return oidStr; - } - - @Override - public String setValue(final String value) { - return null; - } - }; - } - - ////////////////////////////////////////////////// - // BookmarkableModel - ////////////////////////////////////////////////// - - public PageParameters getPageParameters() { - final ObjectAdapter adapter = getTargetAdapter(); - final ObjectAction objectAction = getActionMemento().getAction(); - final PageParameters pageParameters = createPageParameters( - adapter, objectAction, ConcurrencyChecking.NO_CHECK); - - // capture argument values - final ObjectAdapter[] argumentsAsArray = getArgumentsAsArray(); - for(final ObjectAdapter argumentAdapter: argumentsAsArray) { - final String encodedArg = encodeArg(argumentAdapter); - PageParameterNames.ACTION_ARGS.addStringTo(pageParameters, encodedArg); - } - - return pageParameters; - } - - @Override - public String getTitle() { - final ObjectAdapter adapter = getTargetAdapter(); - final ObjectAction objectAction = getActionMemento().getAction(); - - final StringBuilder buf = new StringBuilder(); - final ObjectAdapter[] argumentsAsArray = getArgumentsAsArray(); - for(final ObjectAdapter argumentAdapter: argumentsAsArray) { - if(buf.length() > 0) { - buf.append(","); - } - buf.append(abbreviated(titleOf(argumentAdapter), 8)); - } - - return adapter.titleString(null) + "." + objectAction.getName() + (buf.length()>0?"(" + buf.toString() + ")":""); - } - - @Override - public boolean hasAsRootPolicy() { - return true; - } - - ////////////////////////////////////////////////// - // helpers - ////////////////////////////////////////////////// - - - private static String titleOf(final ObjectAdapter argumentAdapter) { - return argumentAdapter!=null?argumentAdapter.titleString(null):""; - } - - private static String abbreviated(final String str, final int maxLength) { - return str.length() < maxLength ? str : str.substring(0, maxLength - 3) + "..."; - } - - - private static String determineActionId(final ObjectAction objectAction) { - final Identifier identifier = objectAction.getIdentifier(); - if (identifier != null) { - return identifier.toNameParmsIdentityString(); - } - // fallback (used for action sets) - return objectAction.getId(); - } - - public static Mode determineMode(final ObjectAction action) { - return action.getParameterCount() > 0 ? Mode.PARAMETERS : Mode.RESULTS; - } - - private final ObjectAdapterMemento targetAdapterMemento; - private final ActionMemento actionMemento; - private Mode actionMode; - - - /** - * Lazily populated in {@link #getArgumentModel(ActionParameterMemento)} - */ - private final Map<Integer, ScalarModel> arguments = Maps.newHashMap(); - private ActionExecutor executor; - - - private ActionModel(final PageParameters pageParameters) { - this(newObjectAdapterMementoFrom(pageParameters), newActionMementoFrom(pageParameters), actionModeFrom(pageParameters)); - - setArgumentsIfPossible(pageParameters); - setContextArgumentIfPossible(pageParameters); - } - - private static ActionMemento newActionMementoFrom(final PageParameters pageParameters) { - final ObjectSpecId owningSpec = ObjectSpecId.of(PageParameterNames.ACTION_OWNING_SPEC.getStringFrom(pageParameters)); - final ActionType actionType = PageParameterNames.ACTION_TYPE.getEnumFrom(pageParameters, ActionType.class); - final String actionNameParms = PageParameterNames.ACTION_ID.getStringFrom(pageParameters); - return new ActionMemento(owningSpec, actionType, actionNameParms); - } - - private static Mode actionModeFrom(final PageParameters pageParameters) { - final ActionMemento actionMemento = newActionMementoFrom(pageParameters); - if(actionMemento.getAction().getParameterCount() == 0) { - return Mode.RESULTS; - } - final List<String> listFrom = PageParameterNames.ACTION_ARGS.getListFrom(pageParameters); - return !listFrom.isEmpty()? Mode.RESULTS: Mode.PARAMETERS; - } - - - private static ObjectAdapterMemento newObjectAdapterMementoFrom(final PageParameters pageParameters) { - final RootOid oid = oidFor(pageParameters); - if(oid.isTransient()) { - return null; - } else { - return ObjectAdapterMemento.createPersistent(oid); - } - } - - private static RootOid oidFor(final PageParameters pageParameters) { - final String oidStr = PageParameterNames.OBJECT_OID.getStringFrom(pageParameters); - return getOidMarshaller().unmarshal(oidStr, RootOid.class); - } - - - private ActionModel(final ObjectAdapterMemento adapterMemento, final ActionMemento actionMemento, final Mode actionMode) { - this.targetAdapterMemento = adapterMemento; - this.actionMemento = actionMemento; - this.actionMode = actionMode; - } - - /** - * Copy constructor, as called by {@link #copy()}. - */ - private ActionModel(final ActionModel actionModel) { - this.targetAdapterMemento = actionModel.targetAdapterMemento; - this.actionMemento = actionModel.actionMemento; - this.actionMode = actionModel.actionMode; - //this.actionPrompt = actionModel.actionPrompt; - - primeArgumentModels(); - final Map<Integer, ScalarModel> argumentModelByIdx = actionModel.arguments; - for (final Map.Entry<Integer,ScalarModel> argumentModel : argumentModelByIdx.entrySet()) { - setArgument(argumentModel.getKey(), argumentModel.getValue().getObject()); - } - - this.executor = actionModel.executor; - } - - private void setArgumentsIfPossible(final PageParameters pageParameters) { - final List<String> args = PageParameterNames.ACTION_ARGS.getListFrom(pageParameters); - - final ObjectAction action = actionMemento.getAction(); - final List<ObjectSpecification> parameterTypes = action.getParameterTypes(); - - for (int paramNum = 0; paramNum < args.size(); paramNum++) { - final String encoded = args.get(paramNum); - setArgument(paramNum, parameterTypes.get(paramNum), encoded); - } - } - - public boolean hasParameters() { - return actionMode == ActionModel.Mode.PARAMETERS; - } - - private boolean setContextArgumentIfPossible(final PageParameters pageParameters) { - final String paramContext = PageParameterNames.ACTION_PARAM_CONTEXT.getStringFrom(pageParameters); - if (paramContext == null) { - return false; - } - - final ObjectAction action = actionMemento.getAction(); - final List<ObjectSpecification> parameterTypes = action.getParameterTypes(); - final int parameterCount = parameterTypes.size(); - - final Map.Entry<Integer, String> mapEntry = parse(paramContext); - - final int paramNum = mapEntry.getKey(); - if (paramNum >= parameterCount) { - return false; - } - - final String encoded = mapEntry.getValue(); - setArgument(paramNum, parameterTypes.get(paramNum), encoded); - - return true; - } - - private void setArgument(final int paramNum, final ObjectSpecification argSpec, final String encoded) { - final ObjectAdapter argumentAdapter = decodeArg(argSpec, encoded); - setArgument(paramNum, argumentAdapter); - } - - private String encodeArg(final ObjectAdapter adapter) { - if(adapter == null) { - return NULL_ARG; - } - - final ObjectSpecification objSpec = adapter.getSpecification(); - if(objSpec.isEncodeable()) { - final EncodableFacet encodeable = objSpec.getFacet(EncodableFacet.class); - return encodeable.toEncodedString(adapter); - } - - return adapter.getOid().enStringNoVersion(getOidMarshaller()); - } - - private ObjectAdapter decodeArg(final ObjectSpecification objSpec, final String encoded) { - if(NULL_ARG.equals(encoded)) { - return null; - } - - if(objSpec.isEncodeable()) { - final EncodableFacet encodeable = objSpec.getFacet(EncodableFacet.class); - return encodeable.fromEncodedString(encoded); - } - - try { - final RootOid oid = RootOidDefault.deStringEncoded(encoded, getOidMarshaller()); - return getAdapterManager().adapterFor(oid); - } catch (final Exception e) { - return null; - } - } - - private void setArgument(final int paramNum, final ObjectAdapter argumentAdapter) { - final ObjectAction action = actionMemento.getAction(); - final ObjectActionParameter actionParam = action.getParameters().get(paramNum); - final ActionParameterMemento apm = new ActionParameterMemento(actionParam); - final ScalarModel argumentModel = getArgumentModel(apm); - argumentModel.setObject(argumentAdapter); - } - - - public ScalarModel getArgumentModel(final ActionParameterMemento apm) { - final int i = apm.getNumber(); - ScalarModel scalarModel = arguments.get(i); - if (scalarModel == null) { - scalarModel = new ScalarModel(targetAdapterMemento, apm); - final int number = scalarModel.getParameterMemento().getNumber(); - arguments.put(number, scalarModel); - } - return scalarModel; - } - - public ObjectAdapter getTargetAdapter() { - return targetAdapterMemento.getObjectAdapter(getConcurrencyChecking()); - } - - protected ConcurrencyChecking getConcurrencyChecking() { - return actionMemento.getConcurrencyChecking(); - } - - public ActionMemento getActionMemento() { - return actionMemento; - } - - @Override - protected ObjectAdapter load() { - - // from getObject()/reExecute - detach(); // force re-execute - - // TODO: think we need another field to determine if args have been populated. - final ObjectAdapter results = executeAction(); - this.actionMode = Mode.RESULTS; - - return results; - } - - // REVIEW: should provide this rendering context, rather than hardcoding. - // the net effect currently is that class members annotated with - // @Hidden(where=Where.ANYWHERE) or @Disabled(where=Where.ANYWHERE) will indeed - // be hidden/disabled, but will be visible/enabled (perhaps incorrectly) - // for any other value for Where - public static final Where WHERE_FOR_ACTION_INVOCATION = Where.ANYWHERE; - - private ObjectAdapter executeAction() { - - final ObjectAdapter targetAdapter = getTargetAdapter(); - final ObjectAdapter[] arguments = getArgumentsAsArray(); - final ObjectAction action = getActionMemento().getAction(); - - final AuthenticationSession session = getAuthenticationSession(); - return action.executeWithRuleChecking(targetAdapter, arguments, session, WHERE_FOR_ACTION_INVOCATION); - } - - public String getReasonInvalidIfAny() { - final ObjectAdapter targetAdapter = getTargetAdapter(); - final ObjectAdapter[] proposedArguments = getArgumentsAsArray(); - final ObjectAction objectAction = getActionMemento().getAction(); - final Consent validity = objectAction.isProposedArgumentSetValid(targetAdapter, proposedArguments); - return validity.isAllowed() ? null : validity.getReason(); - } - - @Override - public void setObject(final ObjectAdapter object) { - throw new UnsupportedOperationException("target adapter for ActionModel cannot be changed"); - } - - public ObjectAdapter[] getArgumentsAsArray() { - if(this.arguments.size() < this.getActionMemento().getAction().getParameterCount()) { - primeArgumentModels(); - } - - final ObjectAction objectAction = getActionMemento().getAction(); - final ObjectAdapter[] arguments = new ObjectAdapter[objectAction.getParameterCount()]; - for (int i = 0; i < arguments.length; i++) { - final ScalarModel scalarModel = this.arguments.get(i); - arguments[i] = scalarModel.getObject(); - } - return arguments; - } - - public ActionExecutor getExecutor() { - return executor; - } - - public void setExecutor(final ActionExecutor executor) { - this.executor = executor; - } - - public void reset() { - this.actionMode = determineMode(actionMemento.getAction()); - } - - public void clearArguments() { - for (final ScalarModel argumentModel : arguments.values()) { - argumentModel.reset(); - } - this.actionMode = determineMode(actionMemento.getAction()); - } - - /** - * Bookmarkable if the {@link ObjectAction action} has a {@link BookmarkPolicyFacet bookmark} policy - * of {@link BookmarkPolicy#AS_ROOT root}, and has safe {@link ObjectAction#getSemantics() semantics}. - */ - public boolean isBookmarkable() { - final ObjectAction action = getActionMemento().getAction(); - final BookmarkPolicyFacet bookmarkPolicy = action.getFacet(BookmarkPolicyFacet.class); - final boolean safeSemantics = action.getSemantics() == ActionSemantics.Of.SAFE; - return bookmarkPolicy.value() == BookmarkPolicy.AS_ROOT && safeSemantics; - } - - // ////////////////////////////////////// - - /** - * Executes the action, handling any {@link RecoverableException}s that - * might be encountered. - * - * <p> - * If an {@link RecoverableException} is encountered, then the application error will be - * {@link org.apache.isis.core.commons.authentication.MessageBroker#setApplicationError(String) set} so that a suitable message can be - * rendered higher up the call stack. - * - * <p> - * Any other types of exception will be ignored (to be picked up higher up in the callstack) - */ - public ObjectAdapter executeHandlingApplicationExceptions() { - try { - final ObjectAdapter resultAdapter = this.getObject(); - return resultAdapter; - - } catch (final RuntimeException ex) { - - // see if is an application-defined exception - // if so, is converted to an application error, - // equivalent to calling DomainObjectContainer#raiseError(...) - final RecoverableException appEx = getApplicationExceptionIfAny(ex); - if (appEx != null) { - IsisContext.getMessageBroker().setApplicationError(appEx.getMessage()); - - // there's no need to set the abort cause on the transaction, it will have already been done - // (in IsisTransactionManager#executeWithinTransaction(...)). - - return null; - } - - // not handled, so propagate - throw ex; - } - } - - - // ////////////////////////////////////// - - public static RecoverableException getApplicationExceptionIfAny(final Exception ex) { - final Iterable<RecoverableException> appEx = Iterables.filter(Throwables.getCausalChain(ex), RecoverableException.class); - final Iterator<RecoverableException> iterator = appEx.iterator(); - return iterator.hasNext() ? iterator.next() : null; - } - - public static IRequestHandler redirectHandler(final Object value) { - if(value instanceof java.net.URL) { - final java.net.URL url = (java.net.URL) value; - return new RedirectRequestHandler(url.toString()); - } - return null; - } - - public static IRequestHandler downloadHandler(final Object value) { - if(value instanceof Clob) { - final Clob clob = (Clob)value; - return handlerFor(resourceStreamFor(clob), clob); - } - if(value instanceof Blob) { - final Blob blob = (Blob)value; - return handlerFor(resourceStreamFor(blob), blob); - } - return null; - } - - private static IResourceStream resourceStreamFor(final Blob blob) { - final IResourceStream resourceStream = new AbstractResourceStream() { - - private static final long serialVersionUID = 1L; - - @Override - public InputStream getInputStream() throws ResourceStreamNotFoundException { - return new ByteArrayInputStream(blob.getBytes()); - } - - @Override - public String getContentType() { - return blob.getMimeType().toString(); - } - - @Override - public void close() throws IOException { - } - }; - return resourceStream; - } - - private static IResourceStream resourceStreamFor(final Clob clob) { - final IResourceStream resourceStream = new StringResourceStream(clob.getChars(), clob.getMimeType().toString()); - return resourceStream; - } - - private static IRequestHandler handlerFor(final IResourceStream resourceStream, final NamedWithMimeType namedWithMimeType) { - final ResourceStreamRequestHandler handler = - new ResourceStreamRequestHandler(resourceStream, namedWithMimeType.getName()); - handler.setContentDisposition(ContentDisposition.ATTACHMENT); - return handler; - } - - // ////////////////////////////////////// - - public List<ActionParameterMemento> primeArgumentModels() { - final ObjectAction objectAction = getActionMemento().getAction(); - - final List<ObjectActionParameter> parameters = objectAction.getParameters(); - final List<ActionParameterMemento> mementos = buildParameterMementos(parameters); - for (final ActionParameterMemento apm : mementos) { - getArgumentModel(apm); - } - - return mementos; - } - - - private static List<ActionParameterMemento> buildParameterMementos(final List<ObjectActionParameter> parameters) { - final List<ActionParameterMemento> parameterMementoList = Lists.transform(parameters, ObjectAdapterMemento.Functions.fromActionParameter()); - // we copy into a new array list otherwise we get lazy evaluation = - // reference to a non-serializable object - return Lists.newArrayList(parameterMementoList); - } - - ////////////////////////////////////////////////// - // Dependencies (from context) - ////////////////////////////////////////////////// - - private static OidMarshaller getOidMarshaller() { - return IsisContext.getOidMarshaller(); - } - - public ActionModel copy() { - return new ActionModel(this); - } - - - -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPrompt.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPrompt.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPrompt.java deleted file mode 100644 index 0e2747a..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPrompt.java +++ /dev/null @@ -1,71 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -import java.io.Serializable; - -import org.apache.wicket.Component; -import org.apache.wicket.ajax.AjaxRequestTarget; - -/** - * Decouples the {@link ActionModel} from its (modal window) prompt. - */ -public interface ActionPrompt extends Serializable { - - /** - * Sets the component that should be used as a title for the modal window - * - * @param component The title component - * @param target The current Ajax request handler - */ - void setTitle(Component component, AjaxRequestTarget target); - - /** - * Sets the component that should be used as a body for the modal window - * - * @param component The body component - * @param target The current Ajax request handler - */ - void setPanel(Component component, AjaxRequestTarget target); - - /** - * Shows the modal window - * - * @param target The current Ajax request handler - */ - void showPrompt(AjaxRequestTarget target); - - /** - * @return the component id for the title component - */ - String getTitleId(); - - /** - * @return the component id for the body component - */ - String getContentId(); - - /** - * Closes the modal window - * - * @param target The current Ajax request handler - */ - void closePrompt(AjaxRequestTarget target); -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPromptProvider.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPromptProvider.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPromptProvider.java deleted file mode 100644 index 42fbda5..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/ActionPromptProvider.java +++ /dev/null @@ -1,44 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You 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.isis.viewer.wicket.model.models; - -import org.apache.wicket.Component; -import org.apache.wicket.Page; - -public interface ActionPromptProvider { - - public static class Util{ - - public static ActionPromptProvider getFrom(Component component) { - final Page page = component.getPage(); - if(page == null) { - throw new IllegalArgumentException("Programming error: component must be added to a page in order to locate the ActionPromptProvider"); - } - return getFrom(page); - } - public static ActionPromptProvider getFrom(Page page) { - if(page instanceof ActionPromptProvider) { - final ActionPromptProvider provider = (ActionPromptProvider) page; - return provider; - } - // else - throw new IllegalArgumentException("Programming error: all pages should inherit from PageAbstract, which serves as the ActionPromptProvider"); - } - } - - public ActionPrompt getActionPrompt(); -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNode.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNode.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNode.java deleted file mode 100644 index 089eb88..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNode.java +++ /dev/null @@ -1,270 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -import java.io.Serializable; -import java.util.List; - -import com.google.common.base.Function; -import com.google.common.base.Objects; -import com.google.common.collect.Lists; - -import org.apache.wicket.request.mapper.parameter.PageParameters; -import org.apache.isis.core.metamodel.adapter.ObjectAdapter; -import org.apache.isis.core.metamodel.adapter.oid.Oid; -import org.apache.isis.core.metamodel.adapter.oid.OidMarshaller; -import org.apache.isis.core.metamodel.adapter.oid.RootOid; -import org.apache.isis.core.metamodel.spec.feature.Contributed; -import org.apache.isis.core.metamodel.spec.feature.ObjectAssociation; -import org.apache.isis.core.runtime.system.context.IsisContext; -import org.apache.isis.viewer.wicket.model.mementos.PageParameterNames; - -public class BookmarkTreeNode implements Serializable { - - private static final long serialVersionUID = 1L; - - private final List<BookmarkTreeNode> children = Lists.newArrayList(); - private final int depth; - - private final RootOid oidNoVer; - private final String oidNoVerStr; - private final PageType pageType; - - private String title; - private PageParameters pageParameters; - - public static BookmarkTreeNode newRoot( - BookmarkableModel<?> bookmarkableModel) { - return new BookmarkTreeNode(bookmarkableModel, 0); - } - - private BookmarkTreeNode( - final BookmarkableModel<?> bookmarkableModel, - final int depth) { - pageParameters = bookmarkableModel.getPageParameters(); - RootOid oid = oidFrom(pageParameters); - this.oidNoVerStr = getOidMarshaller().marshalNoVersion(oid); - this.oidNoVer = getOidMarshaller().unmarshal(oidNoVerStr, RootOid.class); - - // replace oid with the noVer equivalent. - PageParameterNames.OBJECT_OID.removeFrom(pageParameters); - PageParameterNames.OBJECT_OID.addStringTo(pageParameters, getOidNoVerStr()); - - this.title = bookmarkableModel.getTitle(); - this.pageType = bookmarkableModel instanceof EntityModel ? PageType.ENTITY : PageType.ACTION_PROMPT; - this.depth = depth; - - } - - public RootOid getOidNoVer() { - return oidNoVer; - } - - public String getOidNoVerStr() { - return oidNoVerStr; - } - - public String getTitle() { - return title; - } - private void setTitle(String title) { - this.title = title; - } - - public PageType getPageType() { - return pageType; - } - - public List<BookmarkTreeNode> getChildren() { - return children; - } - public BookmarkTreeNode addChild(BookmarkableModel<?> childModel) { - final BookmarkTreeNode childNode = new BookmarkTreeNode(childModel, depth+1); - children.add(childNode); - return childNode; - } - - /** - * Whether or not the provided {@link BookmarkableModel} matches that contained - * within this node, or any of its children. - * - * <p> - * If it does, then the matched node's title is updated to that of the provided - * {@link BookmarkableModel}. - * - * <p> - * The {@link PageParameters} (used for matching) is - * {@link BookmarkableModel#getPageParameters() obtained} from the {@link BookmarkableModel}. - * - * @return - whether the provided candidate is found or was added to this node's tree. - */ - public boolean matches(BookmarkableModel<?> candidateBookmarkableModel) { - if(candidateBookmarkableModel instanceof EntityModel) { - if(this.pageType != PageType.ENTITY) { - return false; - } - return matchAndUpdateTitleFor((EntityModel) candidateBookmarkableModel); - } else if(candidateBookmarkableModel instanceof ActionModel) { - if(this.pageType != PageType.ACTION_PROMPT) { - return false; - } - return matchFor((ActionModel) candidateBookmarkableModel); - } else { - return false; - } - } - - /** - * Whether or not the provided {@link EntityModel} matches that contained - * within this node, or any of its children. - * - * <p> - * If it does match, then the matched node's title is updated to that of the provided - * {@link EntityModel}. - * - * @return - whether the provided candidate is found or was added to this node's tree. - */ - private boolean matchAndUpdateTitleFor(final EntityModel candidateEntityModel) { - - // match only on the oid string - final String candidateOidStr = oidStrFrom(candidateEntityModel); - boolean inGraph = Objects.equal(this.oidNoVerStr, candidateOidStr); - if(inGraph) { - this.setTitle(candidateEntityModel.getTitle()); - } - - // and also match recursively down to all children and grandchildren. - if(candidateEntityModel.hasAsChildPolicy()) { - for(BookmarkTreeNode childNode: this.getChildren()) { - inGraph = childNode.matches(candidateEntityModel) || inGraph; // evaluate each - } - - if(!inGraph) { - inGraph = addToGraphIfParented(candidateEntityModel); - } - } - return inGraph; - } - - /** - * Whether or not the provided {@link ActionModel} matches that contained - * within this node (taking into account the action's arguments). - * - * If it does match, then the matched node's title is updated to that of the provided - * {@link ActionModel}. - * <p> - * - * @return - whether the provided candidate is found or was added to this node's tree. - */ - private boolean matchFor(final ActionModel candidateActionModel) { - - // check if target object of the action is the same (the oid str) - final String candidateOidStr = oidStrFrom(candidateActionModel); - if(!Objects.equal(this.oidNoVerStr, candidateOidStr)) { - return false; - } - - // check if args same - List<String> thisArgs = PageParameterNames.ACTION_ARGS.getListFrom(pageParameters); - PageParameters candidatePageParameters = candidateActionModel.getPageParameters(); - List<String> candidateArgs = PageParameterNames.ACTION_ARGS.getListFrom(candidatePageParameters); - if(!Objects.equal(thisArgs, candidateArgs)) { - return false; - } - - // ok, a match - return true; - } - - private boolean addToGraphIfParented(BookmarkableModel<?> candidateBookmarkableModel) { - - boolean whetherAdded = false; - // TODO: this ought to be move into a responsibility of BookmarkableModel, perhaps, rather than downcasting - if(candidateBookmarkableModel instanceof EntityModel) { - EntityModel entityModel = (EntityModel) candidateBookmarkableModel; - final ObjectAdapter candidateAdapter = entityModel.getObject(); - final List<ObjectAssociation> properties = candidateAdapter.getSpecification().getAssociations(Contributed.EXCLUDED, ObjectAssociation.Filters.REFERENCE_PROPERTIES); - for (ObjectAssociation objectAssoc : properties) { - final ObjectAdapter possibleParentAdapter = objectAssoc.get(candidateAdapter); - if(possibleParentAdapter == null) { - continue; - } - final Oid possibleParentOid = possibleParentAdapter.getOid(); - if(possibleParentOid == null) { - continue; - } - final String possibleParentOidStr = possibleParentOid.enStringNoVersion(getOidMarshaller()); - if(Objects.equal(this.oidNoVerStr, possibleParentOidStr)) { - this.addChild(candidateBookmarkableModel); - whetherAdded = true; - } - } - } - return whetherAdded; - } - - public void appendGraphTo(List<BookmarkTreeNode> list) { - list.add(this); - for (BookmarkTreeNode childNode : children) { - childNode.appendGraphTo(list); - } - } - - public int getDepth() { - return depth; - } - - - // ////////////////////////////////////// - - public PageParameters getPageParameters() { - return pageParameters; - } - - // ////////////////////////////////////// - - public static RootOid oidFrom(final PageParameters pageParameters) { - String oidStr = PageParameterNames.OBJECT_OID.getStringFrom(pageParameters); - if(oidStr == null) { - return null; - } - try { - return getOidMarshaller().unmarshal(oidStr, RootOid.class); - } catch(Exception ex) { - return null; - } - } - - public static String oidStrFrom(BookmarkableModel<?> candidateBookmarkableModel) { - final RootOid oid = oidFrom(candidateBookmarkableModel.getPageParameters()); - return oid != null? getOidMarshaller().marshalNoVersion(oid): null; - } - - - // ////////////////////////////////////// - - protected static OidMarshaller getOidMarshaller() { - return IsisContext.getOidMarshaller(); - } - - - - -} \ No newline at end of file http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNodeComparator.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNodeComparator.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNodeComparator.java deleted file mode 100644 index 638968e..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkTreeNodeComparator.java +++ /dev/null @@ -1,86 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -import java.util.Comparator; - -import org.apache.wicket.request.mapper.parameter.PageParameters; - -import org.apache.isis.core.metamodel.adapter.oid.OidMarshaller; -import org.apache.isis.core.metamodel.adapter.oid.RootOid; -import org.apache.isis.core.metamodel.spec.ObjectSpecId; -import org.apache.isis.core.metamodel.spec.SpecificationLoader; -import org.apache.isis.core.runtime.system.context.IsisContext; -import org.apache.isis.viewer.wicket.model.mementos.PageParameterNames; - -final class BookmarkTreeNodeComparator implements Comparator<BookmarkTreeNode> { - - @Override - public int compare(BookmarkTreeNode o1, BookmarkTreeNode o2) { - - final PageType pageType1 = o1.getPageType(); - final PageType pageType2 = o2.getPageType(); - - final int pageTypeComparison = pageType1.compareTo(pageType2); - if(pageTypeComparison != 0) { - return pageTypeComparison; - } - - final RootOid oid1 = o1.getOidNoVer(); - final RootOid oid2 = o2.getOidNoVer(); - - // sort by entity type - final String className1 = classNameOf(oid1); - final String className2 = classNameOf(oid2); - - final int classNameComparison = className1.compareTo(className2); - if(classNameComparison != 0) { - return classNameComparison; - } - - final String title1 = o1.getTitle(); - final String title2 = o2.getTitle(); - - return title1.compareTo(title2); - } - - private String classNameOf(RootOid oid) { - ObjectSpecId objectSpecId = oid.getObjectSpecId(); - return getSpecificationLoader().lookupBySpecId(objectSpecId).getIdentifier().getClassName(); - } - - private RootOid oidOf(PageParameters pp) { - String oidStr = PageParameterNames.OBJECT_OID.getStringFrom(pp); - return getOidMarshaller().unmarshal(oidStr, RootOid.class); - } - - ////////////////////////////////////////////////// - // Dependencies (from context) - ////////////////////////////////////////////////// - - protected OidMarshaller getOidMarshaller() { - return IsisContext.getOidMarshaller(); - } - - protected SpecificationLoader getSpecificationLoader() { - return IsisContext.getSpecificationLoader(); - } - -} \ No newline at end of file http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkableModel.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkableModel.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkableModel.java deleted file mode 100644 index 1dfa2ec..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkableModel.java +++ /dev/null @@ -1,46 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -import org.apache.wicket.request.mapper.parameter.PageParameters; - -public abstract class BookmarkableModel<T> extends ModelAbstract<T> { - - private static final long serialVersionUID = 1L; - - public BookmarkableModel() { - super(); - } - - public BookmarkableModel(T t) { - super(t); - } - - - /** - * So can be bookmarked / added to <tt>BookmarkedPagesModel</tt>. - */ - public abstract PageParameters getPageParameters(); - - public abstract boolean hasAsRootPolicy(); - - public abstract String getTitle(); - -} http://git-wip-us.apache.org/repos/asf/isis/blob/d84c6609/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkedPagesModel.java ---------------------------------------------------------------------- diff --git a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkedPagesModel.java b/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkedPagesModel.java deleted file mode 100644 index 1a5d614..0000000 --- a/component/viewer/wicket/model/src/main/java/org/apache/isis/viewer/wicket/model/models/BookmarkedPagesModel.java +++ /dev/null @@ -1,151 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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.isis.viewer.wicket.model.models; - -import java.util.Collections; -import java.util.Iterator; -import java.util.List; -import com.google.common.base.Objects; -import com.google.common.collect.Lists; -import org.apache.wicket.request.mapper.parameter.PageParameters; -import org.apache.isis.core.commons.config.IsisConfiguration; -import org.apache.isis.core.metamodel.adapter.oid.RootOid; -import org.apache.isis.core.runtime.system.context.IsisContext; - - -public class BookmarkedPagesModel extends ModelAbstract<List<? extends BookmarkTreeNode>> { - - - private static final long serialVersionUID = 1L; - - private static final BookmarkTreeNodeComparator COMPARATOR = new BookmarkTreeNodeComparator(); - - private static final String MAX_SIZE_KEY = "isis.viewer.wicket.bookmarkedPages.maxSize"; - private static final int MAX_SIZE_DEFAULT_VALUE = 15; - - private final List<BookmarkTreeNode> rootNodes = Lists.newArrayList(); - - private transient PageParameters current; - - public void bookmarkPage(final BookmarkableModel<?> bookmarkableModel) { - - // hack: remove any garbage that might've got stored in 'rootNodes' - cleanUpGarbage(rootNodes); - - final PageParameters candidatePP = bookmarkableModel.getPageParameters(); - RootOid oid = BookmarkTreeNode.oidFrom(candidatePP); - if(oid == null) { - // ignore - return; - } - - BookmarkTreeNode rootNode = null; - for (BookmarkTreeNode eachNode : rootNodes) { - if(eachNode.matches(bookmarkableModel)) { - rootNode = eachNode; - } - } - // MRU/LRU algorithm - if(rootNode != null) { - rootNodes.remove(rootNode); - rootNodes.add(0, rootNode); - current = candidatePP; - } else { - if (bookmarkableModel.hasAsRootPolicy()) { - rootNode = BookmarkTreeNode.newRoot(bookmarkableModel); - rootNodes.add(0, rootNode); - current = candidatePP; - } - } - - trim(rootNodes, getMaxSize()); - } - - private int getMaxSize() { - return getConfiguration().getInteger(MAX_SIZE_KEY, MAX_SIZE_DEFAULT_VALUE); - } - - private static void trim(List<?> list, int requiredSize) { - int numToRetain = Math.min(list.size(), requiredSize); - list.retainAll(list.subList(0, numToRetain)); - } - - @Override - protected List<BookmarkTreeNode> load() { - List<BookmarkTreeNode> depthFirstGraph = Lists.newArrayList(); - - List<BookmarkTreeNode> sortedNodes = Lists.newArrayList(rootNodes); - Collections.sort(sortedNodes, COMPARATOR); - - for (BookmarkTreeNode rootNode : sortedNodes) { - rootNode.appendGraphTo(depthFirstGraph); - } - return depthFirstGraph; - } - - public boolean isCurrent(PageParameters pageParameters) { - return Objects.equal(current, pageParameters); - } - - private static void cleanUpGarbage(List<BookmarkTreeNode> rootNodes) { - final Iterator<BookmarkTreeNode> iter = rootNodes.iterator(); - while(iter.hasNext()) { - BookmarkTreeNode node = iter.next(); - // think this is redundant... - if(node.getOidNoVer() == null) { - iter.remove(); - } - } - } - - public void clear() { - rootNodes.clear(); - } - - public boolean isEmpty() { - return rootNodes.isEmpty(); - } - - public void remove(BookmarkTreeNode rootNode) { - this.rootNodes.remove(rootNode); - } - - public void remove(EntityModel entityModel) { - BookmarkTreeNode rootNode = null; - for (BookmarkTreeNode eachNode : rootNodes) { - if(eachNode.getOidNoVerStr().equals((entityModel).getObjectAdapterMemento().toString())) { - rootNode = eachNode; - } - } - if(rootNode != null) { - rootNodes.remove(rootNode); - } - } - - // ////////////////////////////////////// - - - protected IsisConfiguration getConfiguration() { - return IsisContext.getConfiguration(); - } - - - -}
