001package de.cuioss.test.jsf.util; 002 003import static de.cuioss.tools.string.MoreStrings.emptyToNull; 004import static org.junit.jupiter.api.Assertions.assertEquals; 005import static org.junit.jupiter.api.Assertions.assertNotNull; 006import static org.junit.jupiter.api.Assertions.assertTrue; 007 008import javax.faces.application.Application; 009import javax.faces.application.NavigationHandler; 010import javax.faces.context.ExternalContext; 011import javax.faces.context.FacesContext; 012import javax.servlet.http.HttpServletResponse; 013 014import org.apache.myfaces.test.mock.MockHttpServletResponse; 015import org.junit.jupiter.api.extension.TestInstancePostProcessor; 016 017import de.cuioss.test.jsf.config.JsfTestContextConfigurator; 018import de.cuioss.test.jsf.config.decorator.ApplicationConfigDecorator; 019import de.cuioss.test.jsf.config.decorator.BeanConfigDecorator; 020import de.cuioss.test.jsf.config.decorator.ComponentConfigDecorator; 021import de.cuioss.test.jsf.config.decorator.RequestConfigDecorator; 022import de.cuioss.test.jsf.junit5.JsfSetupExtension; 023 024/** 025 * Simple interface to be used in context of {@link JsfSetupExtension}. It 026 * provides an interface for injecting the configured 027 * {@link JsfEnvironmentHolder}. It is needed, when the test needs to access 028 * either an {@link JsfTestContextConfigurator} like 029 * {@link ComponentConfigDecorator} or {@link RequestConfigDecorator} or a 030 * JSF-Object like {@link FacesContext} or {@link Application} programmatically. 031 * The typical usage: 032 * 033 * <pre> 034 * <code> 035 @Setter 036 @Getter 037 private JsfEnvironmentHolder environmentHolder; 038 * </code> 039 * 040 * </pre> 041 * 042 * The actual delegation is implemented using default implementations within 043 * this interface, see the unit-test: 044 * 045 * <pre> 046 * <code> 047@EnableJsfEnvironment 048@JsfTestConfiguration(BasicApplicationConfiguration.class) 049class JsfSetupExtensionTest implements JsfEnvironmentConsumer { 050 051 @Setter 052 @Getter 053 private JsfEnvironmentHolder environmentHolder; 054 055 @Test 056 void shouldBootstrapJsf() { 057 assertNotNull(environmentHolder); 058 assertNotNull(getApplication()); 059 assertNotNull(getApplicationConfigDecorator()); 060 assertNotNull(getBeanConfigDecorator()); 061 assertNotNull(getComponentConfigDecorator()); 062 assertNotNull(getExternalContext()); 063 assertNotNull(getFacesContext()); 064 assertNotNull(getRequestConfigDecorator()); 065 assertNotNull(getResponse()); 066 } 067 068 @Test 069 void shouldApplyBasicConfiguration() { 070 assertEquals(BasicApplicationConfiguration.FIREFOX, 071 getExternalContext().getRequestHeaderMap().get(BasicApplicationConfiguration.USER_AGENT)); 072 } 073 * </code> 074 * </pre> 075 * 076 * @author Oliver Wolff 077 * 078 */ 079public interface JsfEnvironmentConsumer { 080 081 /** 082 * @param holder to be set, is never null. Will be called from 083 * {@link TestInstancePostProcessor#postProcessTestInstance(Object, org.junit.jupiter.api.extension.ExtensionContext)} 084 */ 085 void setEnvironmentHolder(JsfEnvironmentHolder holder); 086 087 /** 088 * @return holder set by {@link #setEnvironmentHolder(JsfEnvironmentHolder)} 089 */ 090 JsfEnvironmentHolder getEnvironmentHolder(); 091 092 /** 093 * @return an {@link ComponentConfigDecorator} for the contained 094 * {@link JsfEnvironmentHolder} 095 */ 096 default ComponentConfigDecorator getComponentConfigDecorator() { 097 return getEnvironmentHolder().getComponentConfigDecorator(); 098 } 099 100 /** 101 * @return an {@link BeanConfigDecorator} for the contained 102 * {@link JsfEnvironmentHolder} 103 */ 104 default BeanConfigDecorator getBeanConfigDecorator() { 105 return getEnvironmentHolder().getBeanConfigDecorator(); 106 } 107 108 /** 109 * @return an {@link ApplicationConfigDecorator} for the contained 110 * {@link JsfEnvironmentHolder} 111 */ 112 default ApplicationConfigDecorator getApplicationConfigDecorator() { 113 return getEnvironmentHolder().getApplicationConfigDecorator(); 114 } 115 116 /** 117 * @return an {@link ApplicationConfigDecorator} for the contained 118 * {@link JsfEnvironmentHolder} 119 */ 120 default RequestConfigDecorator getRequestConfigDecorator() { 121 return getEnvironmentHolder().getRequestConfigDecorator(); 122 } 123 124 /** 125 * @return an {@link FacesContext} for the contained 126 * {@link JsfEnvironmentHolder} 127 */ 128 default FacesContext getFacesContext() { 129 return getEnvironmentHolder().getFacesContext(); 130 } 131 132 /** 133 * @return an {@link Application} for the contained {@link JsfEnvironmentHolder} 134 */ 135 default Application getApplication() { 136 return getEnvironmentHolder().getApplication(); 137 } 138 139 /** 140 * @return an {@link ExternalContext} for the contained 141 * {@link JsfEnvironmentHolder} 142 */ 143 default ExternalContext getExternalContext() { 144 return getEnvironmentHolder().getExternalContext(); 145 } 146 147 /** 148 * @return an {@link MockHttpServletResponse} for the contained 149 * {@link JsfEnvironmentHolder} 150 */ 151 default MockHttpServletResponse getResponse() { 152 return getEnvironmentHolder().getResponse(); 153 } 154 155 /** 156 * Asserts whether a navigation was handled by calling 157 * {@link NavigationHandler#handleNavigation(javax.faces.context.FacesContext, String, String)} 158 * 159 * @param outcome must not be null 160 */ 161 default void assertNavigatedWithOutcome(final String outcome) { 162 assertNotNull(emptyToNull(outcome), "Outcome must not be null"); 163 assertTrue(getFacesContext().getExternalContext().isResponseCommitted(), "Response is not committed"); 164 var handler = getApplicationConfigDecorator().getMockNavigationHandler(); 165 assertTrue(handler.isHandleNavigationCalled(), "handleNavigation is not called"); 166 assertEquals(outcome, handler.getCalledOutcome()); 167 } 168 169 /** 170 * Asserts whether a navigation was initialized by calling 171 * {@link ExternalContext#redirect(String)} 172 * 173 * @param redirectUrl must not be null 174 */ 175 default void assertRedirect(final String redirectUrl) { 176 assertNotNull(emptyToNull(redirectUrl), "redirectUrl must not be null"); 177 assertTrue(getFacesContext().getExternalContext().isResponseCommitted(), "Response is not committed"); 178 var tempResponse = (HttpServletResponse) getExternalContext().getResponse(); 179 assertTrue(tempResponse.containsHeader("Location"), "Response must provide a header with the name 'Location'"); 180 assertEquals(redirectUrl, tempResponse.getHeader("Location")); 181 } 182}