Search in sources :

Example 6 with Holder

use of org.apache.tapestry5.internal.util.Holder in project tapestry-5 by apache.

the class AjaxComponentEventRequestHandler method handle.

public void handle(ComponentEventRequestParameters parameters) throws IOException {
    Page activePage = cache.get(parameters.getActivePageName());
    final Holder<Boolean> resultProcessorInvoked = Holder.create();
    resultProcessorInvoked.put(false);
    ComponentEventResultProcessor interceptor = new ComponentEventResultProcessor() {

        public void processResultValue(Object value) throws IOException {
            resultProcessorInvoked.put(true);
            resultProcessor.processResultValue(value);
        }
    };
    // If we end up doing a partial render, the page render queue service needs to know the
    // page that will be rendered (for logging purposes, if nothing else).
    queue.setRenderingPage(activePage);
    request.setAttribute(InternalConstants.PAGE_NAME_ATTRIBUTE_NAME, parameters.getActivePageName());
    if (pageActivator.activatePage(activePage.getRootElement().getComponentResources(), parameters.getPageActivationContext(), interceptor))
        return;
    Page containerPage = cache.get(parameters.getContainingPageName());
    ComponentPageElement element = containerPage.getComponentElementByNestedId(parameters.getNestedComponentId());
    // In many cases, the triggered element is a Form that needs to be able to
    // pass its event handler return values to the correct result processor.
    // This is certainly the case for forms.
    TrackableComponentEventCallback callback = new ComponentResultProcessorWrapper(interceptor);
    environment.push(ComponentEventResultProcessor.class, interceptor);
    environment.push(TrackableComponentEventCallback.class, callback);
    boolean handled = element.triggerContextEvent(parameters.getEventType(), parameters.getEventContext(), callback);
    if (!handled)
        throw new TapestryException(String.format("Request event '%s' (on component %s) was not handled; you must provide a matching event handler method in the component or in one of its containers.", parameters.getEventType(), element.getCompleteId()), element, null);
    environment.pop(TrackableComponentEventCallback.class);
    environment.pop(ComponentEventResultProcessor.class);
    // If the result processor was passed a value, then it will already have rendered. Otherwise it was not passed a value,
    // but it's still possible that we still want to do a partial page render ... if filters were added to the render queue.
    // In that event, run the partial page render now and return.
    boolean wasInvoked = resultProcessorInvoked.get();
    if ((!wasInvoked) && queue.isPartialRenderInitialized()) {
        partialRenderer.renderPartialPageMarkup();
        return;
    }
    if (wasInvoked) {
        return;
    }
    // Send an empty JSON reply if no value was returned from the component event handler method.
    // This is the typical behavior when an Ajax component event handler returns null. It still
    // will go through a pipeline that will add information related to partial page rendering.
    resultProcessor.processResultValue(new JSONObject());
}
Also used : ComponentPageElement(org.apache.tapestry5.internal.structure.ComponentPageElement) ComponentEventResultProcessor(org.apache.tapestry5.services.ComponentEventResultProcessor) JSONObject(org.apache.tapestry5.json.JSONObject) TrackableComponentEventCallback(org.apache.tapestry5.TrackableComponentEventCallback) Page(org.apache.tapestry5.internal.structure.Page) JSONObject(org.apache.tapestry5.json.JSONObject) TapestryException(org.apache.tapestry5.commons.internal.util.TapestryException)

Example 7 with Holder

use of org.apache.tapestry5.internal.util.Holder in project tapestry-5 by apache.

the class PageActivationContextCollectorImpl method collectPageActivationContext.

public Object[] collectPageActivationContext(String pageName) {
    Boolean hasHandler = cache.get(pageName);
    if (hasHandler == null) {
        ComponentModel model = modelSource.getPageModel(pageName);
        hasHandler = model.handlesEvent(EventConstants.PASSIVATE);
        cache.put(pageName, hasHandler);
    }
    if (!hasHandler)
        return EMPTY;
    // Get or create a page instance and trigger the event.
    Page page = requestPageCache.get(pageName);
    ComponentPageElement element = page.getRootElement();
    final Holder<Object[]> holder = Holder.create();
    ComponentEventCallback callback = new ComponentEventCallback() {

        public boolean handleResult(Object result) {
            holder.put(typeCoercer.coerce(result, Object[].class));
            return true;
        }
    };
    element.triggerEvent(EventConstants.PASSIVATE, null, callback);
    if (!holder.hasValue())
        return EMPTY;
    return holder.get();
}
Also used : ComponentPageElement(org.apache.tapestry5.internal.structure.ComponentPageElement) ComponentModel(org.apache.tapestry5.model.ComponentModel) Page(org.apache.tapestry5.internal.structure.Page) ComponentEventCallback(org.apache.tapestry5.ComponentEventCallback)

Example 8 with Holder

use of org.apache.tapestry5.internal.util.Holder in project tapestry-5 by apache.

the class Autocomplete method onAutocomplete.

Object onAutocomplete(final EventContext context, @RequestParameter("t:input") final String input) {
    final Holder<List> matchesHolder = Holder.create();
    // Default it to an empty list.
    matchesHolder.put(Collections.emptyList());
    ComponentEventCallback callback = new ComponentEventCallback() {

        public boolean handleResult(Object result) {
            List matches = coercer.coerce(result, List.class);
            matchesHolder.put(matches);
            return true;
        }
    };
    EventContext newContext = new AbstractEventContext() {

        @Override
        public int getCount() {
            return context.getCount() + 1;
        }

        @Override
        public <T> T get(Class<T> desiredType, int index) {
            if (index == 0) {
                return coercer.coerce(input, desiredType);
            }
            return context.get(desiredType, index - 1);
        }
    };
    resources.triggerContextEvent(EventConstants.PROVIDE_COMPLETIONS, newContext, callback);
    JSONObject reply = new JSONObject();
    reply.put("matches", JSONArray.from(matchesHolder.get()));
    // A JSONObject response is always preferred, as that triggers the whole partial page render pipeline.
    return reply;
}
Also used : AbstractEventContext(org.apache.tapestry5.internal.AbstractEventContext) AbstractEventContext(org.apache.tapestry5.internal.AbstractEventContext) JSONObject(org.apache.tapestry5.json.JSONObject) List(java.util.List) JSONObject(org.apache.tapestry5.json.JSONObject)

Example 9 with Holder

use of org.apache.tapestry5.internal.util.Holder in project tapestry-5 by apache.

the class ApplicationStateManagerImplTest method get_from_unconfigured_aso.

@SuppressWarnings("unchecked")
@Test
public void get_from_unconfigured_aso() {
    ApplicationStatePersistenceStrategy strategy = mockApplicationStatePersistenceStrategy();
    ApplicationStatePersistenceStrategySource source = mockApplicationStatePersistenceStrategySource();
    Class asoClass = ReadOnlyBean.class;
    final Holder holder = new Holder();
    ObjectLocator locator = mockObjectLocator();
    train_get(source, ApplicationStateManagerImpl.DEFAULT_STRATEGY, strategy);
    IAnswer answer = new IAnswer() {

        public Object answer() throws Throwable {
            ApplicationStateCreator creator = (ApplicationStateCreator) EasyMock.getCurrentArguments()[1];
            Object aso = creator.create();
            holder.put(aso);
            return aso;
        }
    };
    expect(strategy.get(eq(asoClass), isA(ApplicationStateCreator.class))).andAnswer(answer);
    expect(locator.autobuild(EasyMock.isA(String.class), EasyMock.eq(asoClass))).andReturn(new ReadOnlyBean());
    replay();
    Map<Class, ApplicationStateContribution> configuration = Collections.emptyMap();
    ApplicationStateManager manager = new ApplicationStateManagerImpl(configuration, source, locator);
    Object actual = manager.get(asoClass);
    assertSame(actual, holder.get());
    verify();
}
Also used : ApplicationStatePersistenceStrategy(org.apache.tapestry5.services.ApplicationStatePersistenceStrategy) Holder(org.apache.tapestry5.internal.util.Holder) ApplicationStateManager(org.apache.tapestry5.services.ApplicationStateManager) ObjectLocator(org.apache.tapestry5.commons.ObjectLocator) ApplicationStatePersistenceStrategySource(org.apache.tapestry5.services.ApplicationStatePersistenceStrategySource) IAnswer(org.easymock.IAnswer) ApplicationStateContribution(org.apache.tapestry5.services.ApplicationStateContribution) ApplicationStateCreator(org.apache.tapestry5.services.ApplicationStateCreator) ReadOnlyBean(org.apache.tapestry5.internal.transform.pages.ReadOnlyBean) Test(org.testng.annotations.Test)

Example 10 with Holder

use of org.apache.tapestry5.internal.util.Holder in project tapestry-5 by apache.

the class ClientPersistentFieldStorageImplTest method modified_mutable_objects_are_reserialized.

// So if an object is stored in a persistent field and is mutable, then the field should not have to be modified
// to force a change, instead the value should be checked to see if it is dirty (assuming true), and reserialized.
@Test
public void modified_mutable_objects_are_reserialized() {
    Request request = mockRequest(null);
    Link link = mockLink();
    MutableObject mo = new MutableObject();
    mo.mutableValue = "initial state";
    String pageName = "Foo";
    String componentId = "bar.baz";
    String fieldName = "biff";
    final Holder<String> holder1 = captureLinkModification(link);
    final Holder<String> holder2 = captureLinkModification(link);
    replay();
    ClientPersistentFieldStorage storage = new ClientPersistentFieldStorageImpl(request, clientDataEncoder, analyzer);
    storage.postChange(pageName, componentId, fieldName, mo);
    storage.updateLink(link);
    mo.mutableValue = "modified state";
    storage.updateLink(link);
    verify();
    System.out.printf("holder1=%s%nholder2=%s%n", holder1.get(), holder2.get());
    assertNotEquals(holder1.get(), holder2.get(), "encoded client data should be different");
    // Now check that it de-serializes to the correct data.
    request = mockRequest(holder2.get());
    replay();
    storage = new ClientPersistentFieldStorageImpl(request, clientDataEncoder, analyzer);
    Collection<PersistentFieldChange> changes = storage.gatherFieldChanges(pageName);
    assertEquals(changes.size(), 1);
    PersistentFieldChange change = new ArrayList<PersistentFieldChange>(changes).get(0);
    MutableObject mo2 = (MutableObject) change.getValue();
    assertEquals(mo2.mutableValue, "modified state");
    verify();
}
Also used : Request(org.apache.tapestry5.http.services.Request) PersistentFieldChange(org.apache.tapestry5.services.PersistentFieldChange) Link(org.apache.tapestry5.http.Link) Test(org.testng.annotations.Test)

Aggregations

Test (org.testng.annotations.Test)7 Request (org.apache.tapestry5.http.services.Request)4 PropertyConduit (org.apache.tapestry5.beanmodel.PropertyConduit)3 InternalPropertyConduit (org.apache.tapestry5.beanmodel.internal.InternalPropertyConduit)3 PropBindingFactoryTest (org.apache.tapestry5.internal.bindings.PropBindingFactoryTest)3 Messages (org.apache.tapestry5.commons.Messages)2 TypeCoercer (org.apache.tapestry5.commons.services.TypeCoercer)2 Link (org.apache.tapestry5.http.Link)2 IntegerHolder (org.apache.tapestry5.integration.app1.data.IntegerHolder)2 InternalComponentResources (org.apache.tapestry5.internal.InternalComponentResources)2 ComponentPageElement (org.apache.tapestry5.internal.structure.ComponentPageElement)2 Page (org.apache.tapestry5.internal.structure.Page)2 Holder (org.apache.tapestry5.internal.util.Holder)2 JSONObject (org.apache.tapestry5.json.JSONObject)2 PersistentFieldChange (org.apache.tapestry5.services.PersistentFieldChange)2 ValueEncoderSource (org.apache.tapestry5.services.ValueEncoderSource)2 EnumSelectModel (org.apache.tapestry5.util.EnumSelectModel)2 List (java.util.List)1 ComponentEventCallback (org.apache.tapestry5.ComponentEventCallback)1 TrackableComponentEventCallback (org.apache.tapestry5.TrackableComponentEventCallback)1