selectItems strange behavior
rodrigotico Aug 9, 2007 8:47 PMHello all,
I am trying to get a object from a <h:selectOneMenu> component and getting a strange behavior.
My entities are:
Client >1:1> Address >n:1> City <n:1> State
In my user interface I have a selectMenu with the states registered on the database and another selectMenu with the cities of the state selected. When the user select the state I fill the cities box. This is working very good.
The problem is when I try to press the button of the form to save the client:
If the the city box don´t have a city selected, the action is called as expected.
If the city box has a city selected, the form is reloaded without call the action method of the button.
I don´t know what to do. I am trying to inject client.address.city, is that possible?
I´m putting here all the code of a test project that I created to test it.
Thanks.
My Session Bean (insertClient)
@Stateless @Name("insertClient") public class InsertClientAction implements InsertClient { @In Client client; @In StateDAO stateDAO; private ArrayList<State> states; private ArrayList<City> cities; public String viewClient() { stateDAO.createInitDB(); return "/client.xhtml"; } public void saveClient() { System.out.println("Client´s Name: " + client.getName()); System.out.println("Client´s Street: " + client.getAddress().getStreet()); System.out.println("Client´s City: " + client.getAddress().getCity().getName()); System.out.println("Client´s State: " + client.getAddress().getCity().getState().getName()); } public ArrayList<State> getStates() { states = new ArrayList<State>(stateDAO.getAll()); return states; } public ArrayList<City> getCities() { return cities; } public void updateCities(ValueChangeEvent event) { State state; try { state = (State) event.getNewValue(); } catch (Exception e) { return; } if (state!=null) { System.out.println("State: " + state.getName()); cities = new ArrayList<City>(state.getCities()); } } }
Session Bean Interface
@Local public interface InsertClient { public String viewClient(); public void saveClient(); public Collection <State> getStates(); public Collection <City> getCities(); public void updateCities(ValueChangeEvent event); }
My User Interface: (client.xhtml)
<h:panelGrid columns="2"> <h:outputText value="Name:"></h:outputText> <h:inputText value="#{client.name}"></h:inputText> <h:outputText value="Street:"></h:outputText> <h:inputText value="#{client.address.street}"></h:inputText> <h:outputText value="State:"></h:outputText> <h:selectOneMenu value="#{state}" id="state" valueChangeListener="#{insertClient.updateCities}"> <s:selectItems value="#{insertClient.states}" var="state" label="#{state.name}" noSelectionLabel="Please Select..."/> <a:support event="onchange" reRender="city" ></a:support> <s:convertEntity /> </h:selectOneMenu> <h:outputText value="City:"></h:outputText> <h:selectOneMenu value="#{client.address.city}" id="city"> <s:selectItems value="#{insertClient.cities}" var="city" label="#{city.name}" noSelectionLabel="Please Select..." /> <s:convertEntity /> </h:selectOneMenu> <h:commandButton action="#{insertClient.saveClient}" value="ok h:"></h:commandButton> <s:button action="#{insertClient.saveClient}" value="ok s:"></s:button> </h:panelGrid>
Client Entity:
@Entity @Name("client") @AutoCreate public class Client { private Long id; private String name; private Address address; @Id @GeneratedValue(strategy=GenerationType.AUTO) public Long getId() { return id; } public void setId(Long id) { this.id = id; } public Client() { address = new Address(); } @Column(nullable=false, length=200) public String getName() { return name; } public void setName(String name) { this.name = name; } @OneToOne (cascade=CascadeType.ALL) public Address getAddress() { return address; } public void setAddress(Address address) { this.address = address; } }
Address Entity:
@Entity @Name("address") public class Address { private Long id; private String street; private City city; @Id @GeneratedValue(strategy=GenerationType.AUTO) public Long getId() { return id; } public void setId(Long id) { this.id = id; } @Column(nullable=false, length=200) public String getStreet() { return street; } public void setStreet(String street) { this.street = street; } @ManyToOne @JoinColumn(name="city_id") public City getCity() { return city; } public void setCity(City city) { this.city = city; } }
City Entity:
@Entity @Name("city") @AutoCreate public class City implements Serializable { private static final long serialVersionUID = -8910258028221144179L; private Long id; private String name; private State state; @Id @GeneratedValue(strategy=GenerationType.AUTO) public Long getId() { return id; } public void setId(Long id) { this.id = id; } public City() { state = new State(); } @Column(nullable=false, length=40) public String getName() { return name; } public void setName(String name) { this.name = name; } @ManyToOne @JoinColumn(name="state_id") public State getState() { return state; } public void setState(State state) { this.state = state; } }
State Entity:
@Entity @Name("state") @AutoCreate public class State implements Serializable { private static final long serialVersionUID = -8286496968276572340L; private long id; private String name; private Collection<City> cities; @Id @GeneratedValue(strategy=GenerationType.AUTO) public Long getId() { return id; } public void setId(Long id) { this.id = id; } @Column(nullable=false, length=40) public String getName() { return name; } public void setName(String name) { this.name = name; } @Override public boolean equals(Object obj) { if (obj instanceof State) { if (((State)obj).getId()==getId()) return true; return false; } return super.equals(obj); } @Override public String toString() { return super.toString(); } @OneToMany(cascade=CascadeType.ALL, fetch=FetchType.LAZY) @JoinColumn(name="state_id") public Collection<City> getCities() { return cities; } public void setCities(Collection<City> cities) { this.cities = cities; } }
The State DAO:
@Name("stateDAO") @AutoCreate public class StateDAO extends EntityHome<State> { @Transactional public Collection<State> getAll() { return getEntityManager().createQuery("from State order by id").getResultList(); } @Transactional public void createInitDB() { EntityManager em = getEntityManager(); State california = new State(); california.setName("California"); em.persist(california); State florida = new State(); florida.setName("Florida"); em.persist(florida); City city; city = new City(); city.setName("Los Angeles"); city.setState(california); em.persist(city); city = new City(); city.setName("San Francisco"); city.setState(california); em.persist(city); city = new City(); city.setName("Miami"); city.setState(florida); em.persist(city); city = new City(); city.setName("Orlando"); city.setState(florida); em.persist(city); } }