JavaServer Faces Anti-Patterns - PowerPoint PPT Presentation

1 / 17
About This Presentation
Title:

JavaServer Faces Anti-Patterns

Description:

JavaServer Faces Anti-Patterns Dennis Byrne - ThoughtWorks dennisbyrne_at_apache.org – PowerPoint PPT presentation

Number of Views:63
Avg rating:3.0/5.0
Slides: 18
Provided by: apa128
Category:

less

Transcript and Presenter's Notes

Title: JavaServer Faces Anti-Patterns


1
JavaServer Faces Anti-Patterns
  • Dennis Byrne - ThoughtWorks
  • dennisbyrne_at_apache.org

2
Validating Setter
  • ltmanaged-beangt
  • ltmanaged-bean-namegtiterationBeanlt/managed-be
    an-namegt
  • ltmanaged-bean-classgtcom.thoughtworks.Iterati
    on
  • lt/managed-bean-classgt
  • ltmanaged-bean-scopegtrequestlt/managed-bean-sc
    opegt
  • ltmanaged-propertygt
  • ltproperty-namegtstartlt/property-namegt
  • ltvaluegtsprintBean.currentStartlt/valuegt
  • lt/managed-propertygt
  • ltmanaged-propertygt
  • ltproperty-namegtendlt/property-namegt
  • ltvaluegtsprintBean.currentEndlt/valuegt
  • lt/managed-propertygt
  • ltmanaged-propertygt
  • ltproperty-namegtlastlt/property-namegt
  • ltvaluegthacklt/valuegt
  • lt/managed-propertygt
  • lt/managed-beangt

3
Validating Setter
  • public class Iteration
  • private Calendar start, end // injected
  • // sans setters and getters for start, end
  • public void setLast(String last)
  • if(start null)
  • throw new NullPointerException("start")
  • if(end null)
  • throw new NullPointerException("end")
  • if(start.after(end))
  • throw new IllegalStateException("start gt
    end")

4
Validating Setter Solutions
  • ltapplicationgt
  • ltvariable-resolvergt
  • org.springframework.web.jsf.DelegatingVariableRe
    solver
  • lt/variable-resolvergt
  • lt/applicationgt
  • ltapplicationgtltel-resolvergt
  • org.apache.myfaces.el.unified.resolver.GuiceReso
    lver
  • lt/el-resolvergt
  • lt/applicationgt
  • public class Iteration
  • private Calendar start, end // injected
  • _at_PostConstruct
  • public void initialize()
  • // domain validation logic here ...

5
The Map Trick
  • requestScopedMap.key // calls
    get(key)
  • requestScopedMapkey
  • public class MapTrick implements java.util.Map
  • public Object get(Object key)
  • return new BusinessLogic().doSomething(key)
  • public void clear()
  • public boolean containsKey(Object arg) return
    false
  • public boolean isEmpty() return false
  • public Set keySet() return null
  • public Object put(Object key, Object value)
    return null
  • public void putAll(Map arg)
  • public Object remove(Object arg) return null
  • public int size() return 0

6
déjà vu PhaseListener
  • ltcontext-paramgt
  • ltdescriptiongt
  • comma separated list of JSF conf files
  • lt/descriptiongt
  • ltparam-namegtjavax.faces.CONFIG_FILESlt/param-na
    megt
  • ltparam-valuegt
  • /WEB-INF/faces-config.xml
  • lt/param-valuegt
  • lt/context-paramgt
  • ltlifecyclegt
  • ltphase-listenergt
  • com.thoughtworks.PhaseListenerImpl
  • lt/phase-listenergt
  • lt/lifecyclegt

7
XML Hell
  • ltnavigation-rulegtltfrom-view-idgt/home.xhtmllt/from-v
    iew-idgt
  • ltnavigation-casegt
  • ltfrom-outcomegtcontact_uslt/from-outcomegt
  • ltto-view-idgt/contact.xhtmllt/to-view-idgt
  • lt/navigation-casegt
  • lt/navigation-rulegt
  • ltnavigation-rulegtltfrom-view-idgt/site_map.xhtmllt/fr
    om-view-idgt
  • ltnavigation-casegt
  • ltfrom-outcomegtcontact_uslt/from-outcomegt
  • ltto-view-idgt/contact.xhtmllt/to-view-idgt
  • lt/navigation-casegt
  • lt/navigation-rulegt
  • ltnavigation-rulegtltfrom-view-idgtlt/from-view-idgt
  • ltnavigation-casegt lt!-- global nav rule --gt
  • ltfrom-outcomegtcontact_uslt/from-outcomegt
  • ltto-view-idgt/contact.xhtmllt/to-view-idgt
  • lt/navigation-casegt
  • lt/navigation-rulegt

8
Thread Safety
  • javax.faces.event.PhaseListener
  • javax.faces.render.Renderer
  • Managed Beans
  • javax.faces.convert.Converter
  • javax.faces.validator.Validator
  • javax.faces.FacesContext
  • JSF Tags

9
Thread Safety
  • lthinputText value"managedBean.value"
    converter"threadUnsafe" /gt
  • ltmanaged-beangt
  • ltmanaged-bean-namegtthreadUnsafelt/managed-
    bean-namegt
  • ltmanaged-bean-classgt
  • org.apache.myfaces.book.ThreadUnsafeConverter
  • lt/managed-bean-classgt
  • ltmanaged-bean-scopegtsessionlt/managed-bean
    -scopegt
  • lt/managed-beangt
  • lthinputText value"managedBean.value" gt
  • ltfconverter converterId"threadUnsafe" gt
    lt!-- Always Safe --gt
  • lt/hinputTextgt
  • ltconvertergt
  • ltconverter-idgtthreadUnsafelt/converter-idgt
  • ltconverter-classgtorg.apache.myfaces.book.T
    hreadUnsafeConverter
  • lt/converter-classgt
  • lt/convertergt

10
Facelets Migration
  • public class WidgetTag extends UIComponentELTag
  • private String title, styleClass
    "default_class"
  • protected void setProperties(UIComponent
    component)
  • super.setProperties(component)
  • Widget span (Widget) component
  • span.setStyleClass(styleClass)
  • span.setTitle(title null ? "no title"
    title)
  • FacesContext ctx FacesContext.getCurrentInstan
    ce()
  • Map session ctx.getExternalContext().getSessio
    nMap()
  • span.setStyle((String) session.get("style"))

11
Law of Demeter
  • A Train Wreck - sensitive to changes in domain
    model
  • employee.getDepartment().getManager()
  • .getOffice().getAddress().getZip()
  • An EL Train Wreck - sensitive to changes in
    domain model
  • employee.department.manager.office.address.zip
  • Encapsulated, insensitive to changes in domain
    model
  • employee.officeManagersZipCode

12
Vendor Lock-in
  • import org.apache.myfaces.component.html.ext.HtmlI
    nputHidden
  • import org.apache.myfaces.component.html.ext.HtmlI
    nputText
  • import org.apache.myfaces.component.html.ext.HtmlO
    utputText
  • public class ImplementationDependentManagedBean
  • private HtmlInputText input
  • private HtmlInputHidden hidden
  • private HtmlOutputText output
  • / getters and setters omitted /
  • public boolean recordTotal(ActionEvent event)
  • long total ((Long)input.getValue()).longV
    alue()
  • total ((Long)hidden.getValue()).longValu
    e()
  • total ((Long)output.getValue()).longValu
    e()
  • return new JmsUtil().broadcastTotal(total)

13
Vendor Lock-in Solution
  • import javax.faces.component.ValueHolder
  • public class RefactoredManagedBean
  • private ValueHolder input
  • private ValueHolder hidden
  • private ValueHolder output
  • / getters setters ommitted /
  • public boolean recordTotal(ActionEvent
    event)
  • long total 0
  • ValueHolder vh new ValueHolder input,
    hidden, output
  • for(ValueHolder valued vh)
  • total ((Long)valued.getValue()).long
    Value()
  • return new JmsUtil().broadcastTotal(total)

14
Portlet ClassCastException
  • FacesContext ctx FacesContext.getCurrentInstance
    ()
  • ExternalContext ectx ctx.getExternalContext()
  • ServletRequest request (ServletRequest)ectx
    .getRequest()
  • String id request.getParameter("id")
  • FacesContext ctx FacesContext.getCurrentInstance
    ()
  • ExternalContext ectx ctx.getExternalContext()
  • String id ectx.getRequestParameterMap().get("id"
    )

15
OpenTransactionInViewFilter
  • public void doFilter(ServletRequest request,
  • ServletResponse response, FilterChain chain)
  • try
  • ObjectRelationalUtility.startTransaction()
  • chain.doFilter(request, response)
  • ObjectRelationalUtility.commitTransaction()
  • catch (Throwable throwable)
  • try
  • ObjectRelationalUtility.rollbackTransaction()
  • catch (Throwable _throwable)
  • / sans error handling /

16
N 1
  • lt!-- One trip to the database for the master
    record ... --gt
  • lthdataTable value"projectBean.projects"
    var"project"gt
  • lthcolumngt
  • lthcommandLink action"projectBean.viewProj
    ect"
  • value"view project"/gt
  • lt/hcolumngt
  • lthcolumngt
  • lt!-- ... and N trips for each child record
    --gt
  • ltffacet name"header"gtProject
    Managerlt/ffacetgt
  • project.manager.name
  • lt/hcolumngt
  • lthcolumngt
  • ltffacet name"header"gtProject
    Namelt/ffacetgt
  • project.name
  • lt/hcolumngt
  • lt/hdataTablegt

17
N 1- N
  • public class OpenTransactionInApplicationPhaseList
    ener
  • implements PhaseListener
  • public void afterPhase(PhaseEvent event)
  • try
  • ObjectRelationalUtility.startTransaction()
  • catch (Throwable throwable) / sans error
    handling /
  • public void beforePhase(PhaseEvent event)
  • try
  • ObjectRelationalUtility.commitTransaction()
  • catch (Throwable throwable)
  • ObjectRelationalUtility.rollbackTransaction()
  • public PhaseId getPhaseId()return
    PhaseId.INVOKE_APPLICATION
Write a Comment
User Comments (0)
About PowerShow.com