001/**
002 * Copyright 2005-2016 The Kuali Foundation
003 *
004 * Licensed under the Educational Community License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 * http://www.opensource.org/licenses/ecl2.php
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016package org.kuali.rice.krad.web.bind;
017
018import org.junit.Before;
019import org.junit.Test;
020import org.kuali.rice.krad.test.TestForm;
021import org.kuali.rice.krad.uif.UifConstants;
022import org.kuali.rice.krad.uif.lifecycle.ViewPostMetadata;
023import org.kuali.rice.krad.uif.view.ViewModel;
024import org.springframework.mock.web.MockHttpServletRequest;
025import org.springframework.web.context.request.RequestContextHolder;
026import org.springframework.web.context.request.ServletWebRequest;
027
028import static org.junit.Assert.assertEquals;
029
030/**
031 * Test cases for {@link UifViewBeanWrapper}.
032 *
033 * @author Kuali Rice Team (rice.collab@kuali.org)
034 */
035public class UifViewBeanWrapperTest {
036
037    private UifViewBeanWrapper beanWrapper;
038
039    @Before
040    public void setUp() throws Exception {
041        TestForm model = new TestForm();
042        model.setMethodToCall("field7TestMethodToCall");
043
044        UifBeanPropertyBindingResult bindingResult = new UifBeanPropertyBindingResult(model, "model", true, 100);
045
046        beanWrapper = new UifViewBeanWrapper(model, bindingResult);
047
048        MockHttpServletRequest request = new MockHttpServletRequest();
049        request.setMethod("POST");
050        request.addParameter(UifConstants.CONTROLLER_METHOD_DISPATCH_PARAMETER_NAME, "field7TestMethodToCall");
051
052        RequestContextHolder.setRequestAttributes(new ServletWebRequest(request));
053    }
054
055    /**
056     * Tests binding annotations are being correctly picked up for various property paths.
057     */
058    @Test
059    public void testCheckForAnnotationInPropertyPath() {
060        assertBindingAnnotationsInPath("Annotation on simple form property not picked up", "field1", Boolean.TRUE);
061
062        assertBindingAnnotationsInPath("Annotation on simple form property not picked up", "field2", Boolean.FALSE);
063
064        assertBindingAnnotationsInPath("Annotation picked up where not present", "field3", null);
065
066        assertBindingAnnotationsInPath("Annotation on nested property not picked up", "dataObject.field5",
067                Boolean.FALSE);
068
069        assertBindingAnnotationsInPath("Annotation picked up on nested property where not present", "dataObject.field1",
070                null);
071
072        assertBindingAnnotationsInPath("Annotation on nested property not picked up", "dataObject.nestedObject.field1",
073                Boolean.TRUE);
074
075        assertBindingAnnotationsInPath("Annotation not correctly picked up for multiple annotations",
076                "dataObject.nestedObject.field5", Boolean.FALSE);
077
078        assertBindingAnnotationsInPath("Annotation on nested list property not picked up", "dataObject.list[0].field5",
079                Boolean.FALSE);
080
081        assertBindingAnnotationsInPath("Annotation on nested list property picked up where not present",
082                "dataObject.list[0].field1", null);
083
084        assertBindingAnnotationsInPath("Annotation on map property not picked up", "dataObject.map['key']",
085                Boolean.TRUE);
086
087        assertBindingAnnotationsInPath("Annotation on accessible list property not picked up",
088                "dataObject.list2[3].field7", Boolean.TRUE);
089
090        assertBindingAnnotationsInPath("Annotation picked up for wrong request method", "field4", null);
091
092        assertBindingAnnotationsInPath("Annotation picked up for wrong request method", "field7", Boolean.TRUE);
093
094        MockHttpServletRequest request = new MockHttpServletRequest();
095        request.setMethod("GET");
096
097        RequestContextHolder.setRequestAttributes(new ServletWebRequest(request));
098
099        assertBindingAnnotationsInPath("Annotation not picked up for correct request method", "field4", Boolean.TRUE);
100
101        assertBindingAnnotationsInPath("Annotation not picked up for multiple request methods", "dataObject.field8",
102                Boolean.TRUE);
103    }
104
105    /**
106     * Helper method for testing {@link UifViewBeanWrapper#checkBindingAnnotationsInPath(java.lang.String)}.
107     *
108     * @param failureMessage message to show if assert fails
109     * @param path property path to invoke method with
110     * @param result expected annotation result
111     */
112    protected void assertBindingAnnotationsInPath(String failureMessage, String path, Boolean result) {
113        Boolean bindingAnnotationAccess = beanWrapper.checkBindingAnnotationsInPath(path);
114
115        assertEquals(failureMessage, result, bindingAnnotationAccess);
116    }
117
118    /**
119     * Tests binding access is correctly being granted and prevented for various cases.
120     */
121    @Test
122    public void testCheckPropertyAccess() {
123        ViewPostMetadata viewPostMetadata = new ViewPostMetadata();
124        ((ViewModel) beanWrapper.getWrappedInstance()).setViewPostMetadata(viewPostMetadata);
125
126        viewPostMetadata.addAccessibleBindingPath("field5");
127        viewPostMetadata.addAccessibleBindingPath("dataObject.field1");
128        viewPostMetadata.addAccessibleBindingPath("dataObject.list[3].field3");
129        viewPostMetadata.addAccessibleBindingPath("dataObject.list[3].list[2].field3");
130
131        assertPropertyBindingAccess("Access not granted for view binding path", "field5", true);
132
133        assertPropertyBindingAccess("Access granted for path without annotation and not in view", "field6", false);
134
135        assertPropertyBindingAccess("Access not granted for path with accessible annotation", "field1", true);
136
137        assertPropertyBindingAccess("Access granted for path with protected annotation", "field2", false);
138
139        assertPropertyBindingAccess("Access not granted for nested view binding path", "dataObject.field1", true);
140
141        assertPropertyBindingAccess("Access not granted for nested view binding path", "dataObject.list[3].field3",
142                true);
143
144        assertPropertyBindingAccess("Access not granted for nested view binding path",
145                "dataObject.list[3].list[2].field3", true);
146
147        assertPropertyBindingAccess("Access granted for path without annotation and not in view",
148                "dataObject.list[3].list[1].field3", false);
149    }
150
151    /**
152     * Helper method for testing {@link UifViewBeanWrapper#checkPropertyBindingAccess(java.lang.String)}.
153     *
154     * @param failureMessage message to show if assert fails
155     * @param path property path to invoke method with
156     * @param access expected access result
157     */
158    protected void assertPropertyBindingAccess(String failureMessage, String path, boolean access) {
159        boolean isPropertyAccessible = beanWrapper.checkPropertyBindingAccess(path);
160
161        assertEquals(failureMessage, Boolean.valueOf(access), Boolean.valueOf(isPropertyAccessible));
162    }
163}