1

I am learning JSF, I made a simple example of a CRUD with JSF, I am using the following:

  • Apache Netbeans 12.0.
  • JDK 13.0.2.
  • JSF 2.3.
  • Apache-tomcat-9.0.37.

And the code is the following:

  1. Bean.java
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import javax.annotation.PostConstruct;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;

@ManagedBean
@ViewScoped
public class Bean implements Serializable {

    private List<Item> list;
    private Item item = new Item();
    private boolean edit;

    @PostConstruct
    public void init() {
        // list = dao.list();
        // Actually, you should retrieve the list from DAO. This is just for demo.
        list = new ArrayList<Item>();
        list.add(new Item(1L, "item1"));
        list.add(new Item(2L, "item2"));
        list.add(new Item(3L, "item3"));
    }

    public void add() {
        // dao.create(item);
        // Actually, the DAO should already have set the ID from DB. This is just for demo.
        item.setId(list.isEmpty() ? 1 : list.get(list.size() - 1).getId() + 1);
        list.add(item);
        item = new Item(); // Reset placeholder.
    }

    public void edit(Item item) {
        this.item = item;
        edit = true;
    }

    public void save() {
        // dao.update(item);
        item = new Item(); // Reset placeholder.
        edit = false;
    }

    public void delete(Item item) {
        // dao.delete(item);
        list.remove(item);
    }

    public List<Item> getList() {
        return list;
    }

    public Item getItem() {
        return item;
    }

    public boolean isEdit() {
        return edit;
    }

    // Other getters/setters are actually unnecessary. Feel free to add them though.

}
  1. Item.java
public class Item {

    private long id;
    private String value;
    
    public Item(long id, String value) {
        this.id = id;
        this.value = value;
    }

    public Item() {        
    }

    public long getId() {
        return id;
    }

    public void setId(long id) {
        this.id = id;
    }

    public String getValue() {
        return value;
    }

    public void setValue(String value) {
        this.value = value;
    }
    
}
  1. index.xhtml
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:f="http://java.sun.com/jsf/core"
      xmlns:h="http://java.sun.com/jsf/html">
    <h:head>
        <title>Really simple CRUD</title>
    </h:head>
    <h:body>
        <h3>List items</h3>
        <h:form rendered="#{not empty bean.list}">
            <h:dataTable value="#{bean.list}" var="item">
                <h:column><f:facet name="header">ID</f:facet>#{item.id}</h:column>
                <h:column><f:facet name="header">Value</f:facet>#{item.value}</h:column>
                <h:column><h:commandButton value="edit" action="#{bean.edit(item)}" /></h:column>
                <h:column><h:commandButton value="delete" action="#{bean.delete(item)}" /></h:column>
            </h:dataTable>
        </h:form>
        <h:panelGroup rendered="#{empty bean.list}">
            <p>Table is empty! Please add new items.</p>
        </h:panelGroup>
        <h:panelGroup rendered="#{!bean.edit}">
            <h3>Add item</h3>
            <h:form>
                <p>Value: <h:inputText value="#{bean.item.value}" /></p>
                <p><h:commandButton value="add" action="#{bean.add}" /></p>
            </h:form>
        </h:panelGroup>
        <h:panelGroup rendered="#{bean.edit}">
            <h3>Edit item #{bean.item.id}</h3>
            <h:form>
                <p>Value: <h:inputText value="#{bean.item.value}" /></p>
                <p><h:commandButton value="save" action="#{bean.save}" /></p>
            </h:form>
        </h:panelGroup>
    </h:body>
</html>

And when I run the code I get the following error:

java.lang.NoClassDefFoundError: javax/enterprise/context/spi/Contextual
    at java.base/java.lang.Class.forName0(Native Method)
    at java.base/java.lang.Class.forName(Class.java:416)
    at com.sun.faces.util.Util.loadClass(Util.java:333)
    at com.sun.faces.application.ApplicationImpl.newThing(ApplicationImpl.java:1847)
    at com.sun.faces.application.ApplicationImpl.createComponentApplyAnnotations(ApplicationImpl.java:2019)
    at com.sun.faces.application.ApplicationImpl.createComponent(ApplicationImpl.java:1246)
    at com.sun.faces.facelets.tag.jsf.ComponentTagHandlerDelegateImpl.createComponent(ComponentTagHandlerDelegateImpl.java:588)
    at com.sun.faces.facelets.tag.jsf.ComponentTagHandlerDelegateImpl.apply(ComponentTagHandlerDelegateImpl.java:176)
    at javax.faces.view.facelets.DelegatingMetaTagHandler.apply(DelegatingMetaTagHandler.java:135)
    at javax.faces.view.facelets.DelegatingMetaTagHandler.applyNextHandler(DelegatingMetaTagHandler.java:161)
    at com.sun.faces.facelets.tag.jsf.ComponentTagHandlerDelegateImpl.apply(ComponentTagHandlerDelegateImpl.java:203)
    at javax.faces.view.facelets.DelegatingMetaTagHandler.apply(DelegatingMetaTagHandler.java:135)
    at javax.faces.view.facelets.CompositeFaceletHandler.apply(CompositeFaceletHandler.java:96)
    at javax.faces.view.facelets.DelegatingMetaTagHandler.applyNextHandler(DelegatingMetaTagHandler.java:161)
    at com.sun.faces.facelets.tag.jsf.ComponentTagHandlerDelegateImpl.apply(ComponentTagHandlerDelegateImpl.java:203)
    at javax.faces.view.facelets.DelegatingMetaTagHandler.apply(DelegatingMetaTagHandler.java:135)
    at javax.faces.view.facelets.CompositeFaceletHandler.apply(CompositeFaceletHandler.java:96)
    at com.sun.faces.facelets.compiler.NamespaceHandler.apply(NamespaceHandler.java:94)
    at com.sun.faces.facelets.compiler.EncodingHandler.apply(EncodingHandler.java:88)
    at com.sun.faces.facelets.impl.DefaultFacelet.apply(DefaultFacelet.java:162)
    at com.sun.faces.application.view.FaceletViewHandlingStrategy.buildView(FaceletViewHandlingStrategy.java:381)
    at com.sun.faces.lifecycle.RenderResponsePhase.execute(RenderResponsePhase.java:102)
    at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:100)
    at com.sun.faces.lifecycle.LifecycleImpl.render(LifecycleImpl.java:223)
    at javax.faces.webapp.FacesServlet.service(FacesServlet.java:671)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:231)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:53)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:202)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:96)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:541)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:139)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:92)
    at org.apache.catalina.valves.AbstractAccessLogValve.invoke(AbstractAccessLogValve.java:690)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:74)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:343)
    at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:373)
    at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:65)
    at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:868)
    at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1589)
    at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
    at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
    at java.base/java.lang.Thread.run(Thread.java:830)
Caused by: java.lang.ClassNotFoundException: javax.enterprise.context.spi.Contextual
    at org.apache.catalina.loader.WebappClassLoaderBase.loadClass(WebappClassLoaderBase.java:1365)
    at org.apache.catalina.loader.WebappClassLoaderBase.loadClass(WebappClassLoaderBase.java:1188)
    ... 47 more

Before this example I have created another example of a registration form and everything went fine.

BalusC
  • 992,635
  • 352
  • 3,478
  • 3,452
Adrián R.
  • 11
  • 2
  • CDI is required since JSF 2.3. CDI is normally available out the box in JEE servers. But Tomcat is not a JEE server. See abovelinked duplicate for instructions. Nice to see you using a CRUD example from my blog :) At the same blog you can find a more elaborate JSF 2.3 tutorial as well: https://balusc.omnifaces.org/2020/04/jsf-23-tutorial-with-eclipse-maven.html I'd recommend going this path to be ready for the normal JEE works. – BalusC Sep 16 '20 at 22:27
  • Thank you very much. @BalusC – Adrián R. Sep 17 '20 at 23:56

0 Answers0