Commit 53215047 by Tuukka Kivilahti

Merge branch 'productOption' into 'master'

Place moving and shop bug

Initial stuff for selfservice place moving. Menu, localisation, etc missing.

Bug where user can bypass product limits when creating bill


See merge request !351
2 parents 20f273a7 25472c7f
package fi.codecrew.moya.rest.v2.pojo;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.List;
import javax.xml.bind.annotation.XmlRootElement;
import com.wordnik.swagger.annotations.ApiModel;
import fi.codecrew.moya.model.Product;
@XmlRootElement()
@ApiModel(description = "Product")
public class ProductPojo {
public Integer id;
public String description;
public BigDecimal price;
public String name;
public static ProductPojo convert(Product prod) {
ProductPojo ret = new ProductPojo();
ret.id = prod.getId();
ret.name = prod.getName();
ret.price = prod.getPrice();
ret.description = prod.getDescription();
return ret;
}
public static List<ProductPojo> convert(List<Product> prods) {
ArrayList<ProductPojo> ret = new ArrayList<>();
for (Product p : prods) {
ret.add(convert(p));
}
return ret;
}
}
package fi.codecrew.moya.rest.v2;
import java.util.List;
import javax.ejb.EJB;
import javax.enterprise.context.RequestScoped;
import javax.ws.rs.GET;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import com.wordnik.swagger.annotations.Api;
import fi.codecrew.moya.beans.ProductBeanLocal;
import fi.codecrew.moya.rest.v2.pojo.ProductPojo;
@RequestScoped
@Path("/v2/product")
@Api(value = "/v2/product", description = "Product operations")
public class ProductRestView {
@EJB
private ProductBeanLocal prodbean;
@GET
@Path("/all")
@Produces(MediaType.APPLICATION_JSON)
public Response getAllProducts() {
List<ProductPojo> ret = ProductPojo.convert(prodbean.findProductsForEvent());
return Response.ok(ret).build();
}
}
......@@ -24,6 +24,7 @@
package fi.codecrew.moya.beans;
import java.math.BigDecimal;
import java.util.HashMap;
import java.util.List;
import javax.ejb.Local;
......@@ -153,4 +154,6 @@ public interface PlaceBeanLocal {
*/
boolean isUnlockedPlaces(EventUser user);
void movePlaces(HashMap<Place, Place> change);
}
\ No newline at end of file
......@@ -143,8 +143,7 @@ public class PlaceBean implements PlaceBeanLocal {
@Override
/** Use place slots */
@Deprecated
public BigDecimal getTotalReservationPrice(Place newPlace)
{
public BigDecimal getTotalReservationPrice(Place newPlace) {
return addAndCalcPrice(permbean.getCurrentUser(), newPlace);
}
......@@ -152,8 +151,7 @@ public class PlaceBean implements PlaceBeanLocal {
@Override
/** Use place slots */
@Deprecated
public BigDecimal getTotalReservationPrice(EventUser user, Place newPlace)
{
public BigDecimal getTotalReservationPrice(EventUser user, Place newPlace) {
return addAndCalcPrice(user, newPlace);
}
......@@ -493,10 +491,14 @@ public class PlaceBean implements PlaceBeanLocal {
@RolesAllowed({ MapPermission.S_BUY_PLACES, MapPermission.S_MANAGE_OTHERS })
public boolean releasePlace(Place place) {
place = placeFacade.reload(place);
EventUser user = permbean.getCurrentUser();
return releasePlacePriv(place) != null;
}
if (place.getGroup() != null || (!permbean.hasPermission(MapPermission.MANAGE_OTHERS) && !place.getCurrentUser().equals(user))) {
return false;
private PlaceSlot releasePlacePriv(Place place) {
EventUser user = permbean.getCurrentUser();
if (place.getGroup() != null || place.getCurrentUser() == null
|| (!permbean.hasPermission(MapPermission.MANAGE_OTHERS) && !place.getCurrentUser().equals(user))) {
return null;
}
place.setCurrentUser(null);
......@@ -507,9 +509,7 @@ public class PlaceBean implements PlaceBeanLocal {
slot.setPlace(null);
slot.setUsed(null);
}
return true;
return slot;
}
@Override
......@@ -544,8 +544,7 @@ public class PlaceBean implements PlaceBeanLocal {
place.setCurrentUser(null);
place.setReserveTime(null);
if (place.getPlaceReserver() != null)
{
if (place.getPlaceReserver() != null) {
GroupMembership res = place.getPlaceReserver();
if (res.getPlaceGroup().getMembers() != null) {
......@@ -821,13 +820,12 @@ public class PlaceBean implements PlaceBeanLocal {
return ret;
}
@Override
public boolean isUnlockedPlaces(EventUser user) {
List<Place> places = placeFacade.findUsersReservations(user.getEvent(), user);
for(Place p : places) {
if(p.isReservedFor(user)) {
for (Place p : places) {
if (p.isReservedFor(user)) {
return true;
}
}
......@@ -835,4 +833,36 @@ public class PlaceBean implements PlaceBeanLocal {
return false;
}
/**
* Allow user to move their places around.
*/
@Override
public void movePlaces(HashMap<Place, Place> change) {
EventUser user = permbean.getCurrentUser();
boolean manageOthers = permbean.hasPermission(MapPermission.MANAGE_OTHERS);
for (Entry<Place, Place> s : change.entrySet()) {
Place src = placeFacade.reload(s.getKey());
if (!manageOthers && !user.equals(src.getCurrentUser())
&& (src.getGroup() == null || !user.equals(src.getGroup().getCreator()))) {
throw new EJBAccessException("Trying to move places for another user without permissions!");
}
Place dst = placeFacade.reload(s.getValue());
if (!dst.isBuyable() || dst.isTaken()) {
throw new EJBException("Place already taken!!");
}
PlaceSlot srcSlot = releasePlacePriv(src);
if (srcSlot != null) {
// this place was reserved via a slot...
srcSlot.setPlace(dst);
srcSlot.setUsed(new Date());
}
dst.setCurrentUser(user);
dst.setReserveTime(Calendar.getInstance());
}
}
}
......@@ -40,7 +40,6 @@ public class ApiApplicationFacade extends IntegerPkGenericFacade<ApiApplication>
}
@EJB
public ApiApplication findByAppid(String appId) {
CriteriaBuilder cb = getEm().getCriteriaBuilder();
CriteriaQuery<ApiApplication> q = cb.createQuery(ApiApplication.class);
......
......@@ -109,6 +109,7 @@ public class PlaceSlotFacade extends IntegerPkGenericFacade<PlaceSlot> {
CriteriaQuery<PlaceSlot> q = cb.createQuery(PlaceSlot.class);
Root<PlaceSlot> root = q.from(PlaceSlot.class);
Path<Bill> bill = root.get(PlaceSlot_.bill);
q.where(cb.equal(bill.get(Bill_.user), user),
cb.isNotNull(bill.get(Bill_.paidDate)));
......
<!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:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:map="http://java.sun.com/jsf/composite/cditools/map"
xmlns:tools="http://java.sun.com/jsf/composite/cditools"
xmlns:c="http://java.sun.com/jsp/jstl/core"
xmlns:p="http://primefaces.org/ui">
<h:body>
<ui:composition template="#{sessionHandler.template}">
<f:metadata>
<f:event type="preRenderView"
listener="#{mapPlacechangeView.initView()}" />
</f:metadata>
<ui:define name="content">
<h:outputScript target="head" library="seatjs" name="d3.min.js" />
<h:outputScript target="head" library="seatjs" name="d3-tip.js" />
<h:outputScript target="head" library="seatjs" name="seatmap.js" />
<h:outputStylesheet library="seatjs" name="placemap.css" />
<!-- Place slot count -->
<h3>
<h:outputText value="#{i18n['mapView.yourPlaces']}" />
</h3>
<p:fragment id="placeselector">
<h:form>
<p:dataTable id="slottable" tableStyle="width: auto;" var="slot"
value="#{mapPlacechangeView.slots}">
<!-- rowStyleClass="#{mapPlacechangeView.srcPlace.contains(slot.place) ? 'selected' : 'unselected'}" -->
<p:column headerText="#{i18n['mapView.productcount.productname']}">
<h:outputText value="#{slot.src.product.name}" />
</p:column>
<p:column headerText="#{i18n['mapView.productcount.unused']}">
<h:outputText renderer="#{!empty slot.src.place}"
value="#{slot.src.place.name}" />
</p:column>
<p:column headerText="#{i18n['mapView.productcount.selected']}">
<h:outputText renderer="#{!empty slot.moving}"
value="#{slot.moving}" />
</p:column>
<p:column headerText="#{i18n['mapView.productcount.selected']}">
<h:outputText renderer="#{!empty slot.dst}"
value="#{slot.dst.name}" />
</p:column>
<p:column>
<ui:fragment rendered="#{empty slot.dst}">
<p:commandButton
actionListener="#{mapPlacechangeView.selectSlot}"
rendered="#{!slot.isMoving()}"
value="#{i18n['placemove.selectSlotForMove']}"
update="placeselector" />
<p:commandButton
actionListener="#{mapPlacechangeView.unselectSlot}"
rendered="#{slot.moving}" value="#{i18n['placemove.deselect']}"
update="placeselector" />
</ui:fragment>
</p:column>
</p:dataTable>
</h:form>
<script type="text/javascript">
toggleSuccess = #{mapPlacechangeView.toggleSuccess};
</script>
</p:fragment>
<h:form id="placemove">
<p:commandButton
rendered="#{ajaxMapView.canUserBuy()}"
value="#{i18n['mapPlacechange.commitMove']}"
actionListener="#{mapPlacechangeView.commitMove()}" />
</h:form>
<svg id="seatmap" style="margin: auto; border: 1px solid black;"
width="#{ajaxMapView.map.width}px"
height="#{ajaxMapView.map.height}px" />
<h:form>
<p:remoteCommand name="toggleDstPlace"
action="#{mapPlacechangeView.toggleDstPlace()}"
update="placeselector" oncomplete="afterToggle()"></p:remoteCommand>
</h:form>
<script type="text/javascript">
// <![CDATA[
px = placemap({
element: document.getElementById("seatmap"),
moyaurl: "#{request.contextPath}",
map_id: #{ajaxMapView.map.id},
});
px.toggleaction = function(d){
latestPlace = d;
toggleDstPlace([{name:"placeId", value:d.id} ])
};
function afterToggle(){
if(toggleSuccess){
if(latestPlace.state === "F"){
latestPlace.state = "T";
}else {
latestPlace.state = "F";
}
px.update_placeobj([latestPlace]);
}
}
// ]]>
</script>
<map:legend />
</ui:define>
</ui:composition>
</h:body>
</html>
\ No newline at end of file
<!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:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:map="http://java.sun.com/jsf/composite/cditools/map"
xmlns:tools="http://java.sun.com/jsf/composite/cditools"
xmlns:c="http://java.sun.com/jsp/jstl/core"
xmlns:p="http://primefaces.org/ui">
<h:body>
<ui:composition template="#{sessionHandler.template}">
<f:metadata>
<f:event type="preRenderView" listener="#{ajaxMapView.initViewMap()}" />
</f:metadata>
<ui:param name="thispage" value="page.place.placemap" />
<ui:define name="content">
<!-- <h:form>
<p:remoteCommand name="placeClicker" update=":fbdiag"
action="#{ajaxMapView.placeClicked()}" />
</h:form>
-->
<p:dialog rendered="#{ajaxMapView.isMgmtPermission()}"
visible="#{!empty ajaxMapView.place}" id="fbdiag">
Clicked place name : #{ajaxMapView.place.name};
<h:link rendered="#{!empty ajaxMapView.place}" outcome="/place/edit">
<f:param name="placeid" value="#{ajaxMapView.place.id}" />
Muokkaa
</h:link>
</p:dialog>
<h:outputScript target="head" library="seatjs" name="d3.min.js" />
<h:outputScript target="head" library="seatjs" name="d3-tip.js" />
<h:outputScript target="head" library="seatjs" name="seatmap.js" />
<h:outputStylesheet library="seatjs" name="placemap.css" />
<ui:fragment rendered="#{not ajaxMapView.queueEnabled}">
<div style="margin: 5px;">
<h:form id="placeselectform">
<p:commandButton rendered="#{ajaxMapView.canUserBuy()}"
value="#{i18n['mapView.buyPlaces']}"
action="#{ajaxMapView.buySelectedPlaces()}" ajax="false" />
</h:form>
</div>
</ui:fragment>
<button onclick="px.update()">#{i18n['neomap.updateMap']}</button>
<br />
<svg id="seatmap" style="margin: auto; border: 1px solid black;"
width="#{ajaxMapView.map.width}px"
height="#{ajaxMapView.map.height}px" />
<script type="text/javascript">
// If queue is enabled, do not allow clicking of places.
px = placemap({
element : document.getElementById("seatmap"),
moyaurl : "#{request.contextPath}",
map_id : #{ajaxMapView.map.id},
placeurl : "/rest/placemap/v1/#{ajaxMapView.map.id}/allplaces",
});
px.toggleaction = #{ajaxMapView.queueEnabled?'undefined':'px.toggle_place'};
</script>
<map:legend />
</ui:define>
</ui:composition>
</h:body>
</html>
\ No newline at end of file
......@@ -53,11 +53,13 @@
<p:outputPanel rendered="#{!cart.product.usershopAutoproduct}">
<p:commandButton action="#{productShopView.addMinusOne}" value="#{i18n['productshop.minusOne']}" update="billcart" />
<p:inputText size="2" id="cartcount" escape="false" value="#{cart.count}">
<f:ajax render="@form"
listener="#{productShopView.countChangeListener}" />
<p:inputText onblur="$('.focusdisabler').attr('disabled',false).removeClass('ui-state-disabled'); $('.focusenabler').attr('disabled',true).addClass('ui-state-disabled')" onfocus="$('.focusdisabler').attr('disabled',true).addClass('ui-state-disabled'); $('.focusenabler').attr('disabled',false).removeClass('ui-state-disabled');"
size="2" id="cartcount" escape="false" value="#{cart.count}" >
<f:ajax render="@form" listener="#{productShopView.countChangeListener}" />
<f:convertNumber maxFractionDigits="2" minFractionDigits="0" />
</p:inputText>
<p:commandButton action="#{productShopView.addOne}" update="billcart" value="#{i18n['productshop.plusOne']}" />
</p:outputPanel>
</p:column>
......@@ -146,10 +148,13 @@
function initPaymentButtons() {
};
</script>
<p:commandButton ajax="false" onerror="location.reload(true);"
<p:commandButton styleClass="focusdisabler" ajax="false" onerror="location.reload(true);"
action="#{cc.attrs.commitaction}" id="commitbutton-botton"
value="#{cc.attrs.commitValue}" />
<p:commandButton actionListener="#{productShopView.countChangeListener}" onclick="return false;" styleClass="focusenabler" disabled="true" value="#{i18n['shop.updatePrices']}">
</p:commandButton>
......
......@@ -438,6 +438,10 @@ function placemap(opts)
}
};
px.update_placeobj = function (d) {
draw_places(d, false);
}
px.update_place = function (place_id)
{
if (place_id === undefined) place_id = px.clicked_place;
......
<!DOCTYPE html
PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:p="http://primefaces.org/ui">
<h:body>
<ui:composition template="#{sessionHandler.template}">
<f:metadata>
</f:metadata>
<ui:define name="title">
<h1>#{i18n['page.product.shopClosed.header']}</h1>
</ui:define>
<ui:define name="content">
Shop Closed!!
</ui:define>
</ui:composition>
</h:body>
</html>
\ No newline at end of file
package fi.codecrew.moya.rest.placemap.v1;
import javax.enterprise.context.RequestScoped;
import javax.ws.rs.Consumes;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
@RequestScoped
@Path("/placemap/v1")
@Consumes({ MediaType.APPLICATION_JSON })
@Produces({ MediaType.APPLICATION_JSON + "; charset=UTF-8" })
public class EventInfoRestViewV1 {
}
package fi.codecrew.moya.rest.placemap.v1;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import javax.ejb.EJB;
import javax.enterprise.context.RequestScoped;
import javax.inject.Inject;
import javax.ws.rs.Consumes;
import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.ResponseBuilder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import fi.codecrew.moya.beans.BarcodeBeanLocal;
import fi.codecrew.moya.beans.EventBeanLocal;
import fi.codecrew.moya.beans.PermissionBeanLocal;
import fi.codecrew.moya.beans.PlaceBeanLocal;
import fi.codecrew.moya.beans.UserBeanLocal;
import fi.codecrew.moya.beans.map.QueueBeanLocal;
import fi.codecrew.moya.enums.apps.MapPermission;
import fi.codecrew.moya.enums.apps.UserPermission;
import fi.codecrew.moya.model.EventMap;
import fi.codecrew.moya.model.EventUser;
import fi.codecrew.moya.model.LanEvent;
import fi.codecrew.moya.model.Place;
import fi.codecrew.moya.rest.PojoUtils;
import fi.codecrew.moya.rest.pojo.placemap.v1.IntegerRoot;
import fi.codecrew.moya.rest.pojo.placemap.v1.PlacemapMapRootPojo;
import fi.codecrew.moya.rest.pojo.placemap.v1.SimplePlacePojo;
import fi.codecrew.moya.rest.pojo.placemap.v1.SimplePlacelistRoot;
import fi.codecrew.moya.utilities.PasswordFunctions;
import fi.codecrew.moya.web.cdiview.map.MapPlacechangeView;
import fi.codecrew.moya.web.cdiview.map.MapPlacechangeView.MoveContainer;
import fi.codecrew.moya.web.cdiview.user.UserView;
@RequestScoped
@Path("/placemove/v1")
@Consumes({ MediaType.APPLICATION_JSON })
@Produces({ MediaType.APPLICATION_JSON + "; charset=UTF-8" })
public class PlacechangeRestViewV1 {
@Inject
private MapPlacechangeView placechangeView;
@EJB
private PermissionBeanLocal permbean;
@GET
@Path("/destinations")
public SimplePlacelistRoot getDestinations() {
List<Place> dsts = new ArrayList<>();
for (MoveContainer mc : placechangeView.getMoveContainers()) {
dsts.add(mc.getDst());
}
SimplePlacelistRoot ret = PojoUtils.parseSimplePlaces(dsts, permbean.getCurrentUser(), false);
for (SimplePlacePojo p : ret.getPlaces()) {
p.setState("T");
}
return ret;
}
}
......@@ -48,7 +48,7 @@ public class UserRestViewV2 {
PojoFactoryV2 pojoFactory;
@GET
@Path("/")
@Path("/get")
@Produces(MediaType.APPLICATION_JSON)
@ApiOperation(value = "Find user", response = UserPojo.class)
public Response getEventUser(@QueryParam("email") @ApiParam("Email address") String email,
......
package fi.codecrew.moya.web.cdiview.map;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.ejb.EJB;
import javax.enterprise.context.ConversationScoped;
import javax.faces.context.FacesContext;
import javax.faces.model.ListDataModel;
import javax.inject.Named;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import fi.codecrew.moya.beans.PlaceBeanLocal;
import fi.codecrew.moya.beans.UserBeanLocal;
import fi.codecrew.moya.enums.apps.MapPermission;
import fi.codecrew.moya.model.EventUser;
import fi.codecrew.moya.model.Place;
import fi.codecrew.moya.model.PlaceSlot;
import fi.codecrew.moya.web.cdiview.GenericCDIView;
@Named
@ConversationScoped
public class MapPlacechangeView extends GenericCDIView {
private static final Logger logger = LoggerFactory.getLogger(MapPlacechangeView.class);
private static final long serialVersionUID = 1L;
private Integer userId;
private EventUser user;
@EJB
private UserBeanLocal userbean;
@EJB
private PlaceBeanLocal placebean;
private ListDataModel<MoveContainer> slots;
private List<MoveContainer> moveContainers;
private boolean toggleSuccess;
public static class MoveContainer {
private boolean moving = false;
private final PlaceSlot src;
private Place dst;
public MoveContainer(PlaceSlot p) {
this.src = p;
}
public static List<MoveContainer> init(List<PlaceSlot> placeslots) {
ArrayList<MoveContainer> ret = new ArrayList<>();
for (PlaceSlot p : placeslots) {
ret.add(new MoveContainer(p));
}
return ret;
}
public boolean isMoving() {
return moving;
}
public void setMoving(boolean moving) {
this.moving = moving;
}
public Place getDst() {
return dst;
}
public void setDst(Place dst) {
this.dst = dst;
}
public PlaceSlot getSrc() {
return src;
}
}
public void initView() {
// If we are overriding user, check permission.
if (getSlots() == null) {
if (userId != null && super.requirePermissions(MapPermission.MANAGE_OTHERS)) {
user = userbean.findByUserId(userId, false);
} else if (super.requirePermissions(MapPermission.BUY_PLACES)) {
user = permbean.getCurrentUser();
} else {
return;
}
super.beginConversation();
moveContainers = MoveContainer.init(placebean.getPlaceslots(user));
slots = new ListDataModel<MoveContainer>(moveContainers);
}
}
public void commitMove(){
HashMap<Place, Place> change = new HashMap<Place,Place>();
for(MoveContainer s : slots){
if(s.isMoving() && s.getDst() != null){
change.put(s.getSrc().getPlace(), s.getDst());
}
}
placebean.movePlaces(change);
}
public void toggleDstPlace() {
Map<String, String> paramMap = FacesContext.getCurrentInstance().getExternalContext().getRequestParameterMap();
Integer placeId = new Integer(paramMap.get("placeId"));
Place place = placebean.find(placeId);
setToggleSuccess(false);
for (MoveContainer mc : getMoveContainers()) {
if (place.equals(mc.getSrc().getPlace())) {
setSlotState(mc, !mc.isMoving());
return;
}
if (place.equals(mc.getDst())) {
setToggleSuccess(true);
mc.setDst(null);
return;
}
}
if (!place.isBuyable() || place.isTaken()) {
return;
}
for (MoveContainer mc : moveContainers) {
if (mc.isMoving() && mc.dst == null && mc.getSrc().getProduct().equals(place.getProduct())) {
setToggleSuccess(true);
mc.setDst(place);
return;
}
}
}
public String selectSlot() {
setSlotState(slots.getRowData(), true);
return null;
}
private void setSlotState(MoveContainer mc, boolean moving) {
if (!moving && mc.getDst() != null) {
return;
}
mc.setMoving(moving);
}
public String unselectSlot() {
setSlotState(getSlots().getRowData(), false);
return null;
}
public Integer getUserId() {
return userId;
}
public void setUserId(Integer userId) {
this.userId = userId;
}
public EventUser getUser() {
return user;
}
public void setUser(EventUser user) {
this.user = user;
}
public List<MoveContainer> getMoveContainers() {
return moveContainers;
}
public void setMoveContainers(List<MoveContainer> moveContainers) {
this.moveContainers = moveContainers;
}
public ListDataModel<MoveContainer> getSlots() {
return slots;
}
public void setSlots(ListDataModel<MoveContainer> slots) {
this.slots = slots;
}
public boolean isToggleSuccess() {
return toggleSuccess;
}
public void setToggleSuccess(boolean toggleSuccess) {
this.toggleSuccess = toggleSuccess;
}
}
......@@ -20,6 +20,7 @@ package fi.codecrew.moya.web.cdiview.shop;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
......@@ -27,6 +28,8 @@ import java.util.Map;
import javax.ejb.EJB;
import javax.enterprise.context.ConversationScoped;
import javax.faces.application.NavigationHandler;
import javax.faces.context.FacesContext;
import javax.faces.model.ListDataModel;
import javax.inject.Inject;
import javax.inject.Named;
......@@ -41,6 +44,7 @@ import fi.codecrew.moya.beans.UserBeanLocal;
import fi.codecrew.moya.enums.apps.ShopPermission;
import fi.codecrew.moya.model.Bill;
import fi.codecrew.moya.model.EventUser;
import fi.codecrew.moya.model.LanEvent;
import fi.codecrew.moya.model.LanEventProperty;
import fi.codecrew.moya.model.LanEventPropertyKey;
import fi.codecrew.moya.model.Product;
......@@ -118,7 +122,19 @@ public class ProductShopView extends GenericCDIView {
public void initBillView() {
if (requirePermissions(ShopPermission.LIST_USERPRODUCTS) && shoppingcart == null) {
shoppingcart = new ListDataModel<ProductShopItem>(ProductShopItem.productList(productBean.listUserShoppableProducts(), userView.getSelectedUser()));
LanEvent event = eventbean.getCurrentEvent();
Date now = new Date();
if ((event.getTicketSalesBegin() != null && now.before(event.getTicketSalesBegin()))
|| (event.getEndTime() != null && now.after(event.getEndTime()))) {
FacesContext fc = FacesContext.getCurrentInstance();
NavigationHandler nh = fc.getApplication().getNavigationHandler();
nh.handleNavigation(fc, null, "/shop/shopClosed?faces-redirect=true");
return;
}
shoppingcart = new ListDataModel<ProductShopItem>(
ProductShopItem.productList(productBean.listUserShoppableProducts(), userView.getSelectedUser()));
for (ProductShopItem item : shoppingcart) {
psiHelper.updateProductShopItemCount(item);
......@@ -301,8 +317,7 @@ public class ProductShopView extends GenericCDIView {
ret = ret.add(getCash());
ret = ret.subtract(getCartPrice());
logger.info("User accountbalance {}, cash{}, total {}. retBalance {}",
new Object[] { userView.getSelectedUser().getAccountBalance(), getCash(),
getCartPrice(), ret });
new Object[] { userView.getSelectedUser().getAccountBalance(), getCash(), getCartPrice(), ret });
return ret;
}
......@@ -320,6 +335,10 @@ public class ProductShopView extends GenericCDIView {
}
public String commitBillCart() {
for(ProductShopItem i : shoppingcart){
psiHelper.updateProductShopItemCount(i);
}
updateAllCartLimits();
logger.debug("Committing billCart");
......
......@@ -616,6 +616,8 @@ off = Off
on = On
option.setAsDefault = set as default
orgRoleRequest.discardRequest = Discard request
orgRoleRequest.handledNotes = Handling notes
orgRoleRequest.id = ID
......@@ -725,6 +727,7 @@ place.product = Product
place.release = Release this place
place.releasetime = Release time
place.reserveForUser = Reserve for the user
place.reservetime = Reservetime
place.send = Transfer place
place.width = Width
......@@ -762,7 +765,7 @@ placegroupView.editplace = Edit place
placegroupview.groupCreator = Orderer
placegroupview.header = My places
placegroupview.lockPlaces=Lock places
placegroupview.lockPlaces = Lock places
placegroupview.noMemberships = No places
placegroupview.owner = Owner
placegroupview.placeReleaseFailed = Releasing place failed!
......@@ -774,8 +777,8 @@ placegroupview.reservationProduct = Ticket
placegroupview.reserveForSelf = Select the place for yourself
placegroupview.token = Place token / user
placegroupview.toptext = \
placegroupview.unlockedPlacesNotification = You have unlocked places, you must lock them before you can see your tickets!
placegroupview.unlockedPlacesNotification=You have unlocked places, you must lock them before you can see your tickets\!
placeslot.add = Add place slot
placeslot.bill = Bill
placeslot.id = ID
......@@ -823,10 +826,12 @@ product.color = Color in UI
product.create = Create product
product.createDiscount = Add volume discount
product.createLimit = Create product limit
product.createProductOptionGroup = Create product feature
product.description = Description
product.edit = Edit
product.expired = Expired
product.inventoryQuantity = Inventory count
product.minBuyCount = Minium buy count
product.name = Product name
product.paid = Paid
product.prepaid = Prepaid
......@@ -859,6 +864,15 @@ productLimit.sort = Sort number
productLimit.type = Limit type
productLimit.upperLimit = Upper limit
productOption.add = Add new option
productOption.name = Option name
productOption.title = Options
productOptionGroup.default = Default option
productOptionGroup.name = Name
productOptionGroup.required = Required
productOptionGroup.title = Product feature
productShopView.readBarcode = Read barcode
products.create = Create product
......@@ -1002,6 +1016,7 @@ shop.toAccountValue = To account
shop.totalPrice = Total
shop.transactionTotal = Transaction total
shop.unitdiscount = Discount
shop.updatePrices = Update prices
shop.user = Selling to
sidebar.bill.list = My bills
......@@ -1285,6 +1300,7 @@ tournaments.admin.edit_rules = Edit rules
tournaments.admin.edit_tournament = Edit tournament
tournaments.admin.game_description = Game description
tournaments.admin.game_name = Game name
tournaments.admin.open_for_roles = Roles allowing registeration
tournaments.admin.registration_time_constraints = Registration time
tournaments.admin.remove_confirmation_text = Are you sure you want to remove this tournament? THIS CANNOT BE REVERSED!
tournaments.admin.remove_title = Confirm tournament removal
......@@ -1560,15 +1576,3 @@ voting.create.voteEnd = Voting close
voting.create.voteStart = Voting start
yes = Yes
tournaments.admin.open_for_roles=Roles allowing registeration
productOptionGroup.name=Name
product.createProductOptionGroup=Create product feature
productOptionGroup.required=Required
productOption.name=Option name
productOption.add=Add new option
productOption.title=Options
productOptionGroup.title=Product feature
productOptionGroup.default=Default option
option.setAsDefault=set as default
place.reservetime=Reservetime
product.minBuyCount=Minium buy count
......@@ -846,6 +846,8 @@ off = Off
on = On
option.setAsDefault = set as default
org.hibernate.validator.constraints.Email.message = not a well-formed email address
org.hibernate.validator.constraints.Length.message = length must be between {min} and {max}
org.hibernate.validator.constraints.NotEmpty.message = may not be empty
......@@ -984,6 +986,7 @@ place.product = Product
place.release = Release this place
place.releasetime = Release time
place.reserveForUser = Reserve for the user
place.reservetime = Reservetime
place.send = Transfer place
place.width = Width
......@@ -1021,7 +1024,7 @@ placegroupView.editplace = Edit place
placegroupview.groupCreator = Orderer
placegroupview.header = My places
placegroupview.lockPlaces=Lock places
placegroupview.lockPlaces = Lock places
placegroupview.noMemberships = No places
placegroupview.owner = Owner
placegroupview.placeReleaseFailed = Releasing place failed!
......@@ -1032,8 +1035,8 @@ placegroupview.reservationName = Place
placegroupview.reservationProduct = Ticket
placegroupview.reserveForSelf = Select the place for yourself
placegroupview.token = Place token / user
placegroupview.unlockedPlacesNotification = You have unlocked places, you must lock them before you can see your tickets!
placegroupview.unlockedPlacesNotification=You have unlocked places, you must lock them before you can see your tickets\!
placeslot.add = Add place slot
placeslot.bill = Bill
placeslot.id = ID
......@@ -1083,10 +1086,12 @@ product.color = Color in UI
product.create = Create product
product.createDiscount = Add volume discount
product.createLimit = Create product limit
product.createProductOptionGroup = Create product feature
product.description = Description
product.edit = Edit
product.expired = Expired
product.inventoryQuantity = Inventory count
product.minBuyCount = Minium buy count
product.name = Product name
product.paid = Paid
product.prepaid = Prepaid
......@@ -1121,6 +1126,15 @@ productLimit.sort = Sort number
productLimit.type = Limit type
productLimit.upperLimit = Upper limit
productOption.add = Add new option
productOption.name = Option name
productOption.title = Options
productOptionGroup.default = Default option
productOptionGroup.name = Name
productOptionGroup.required = Required
productOptionGroup.title = Product feature
productShopView.readBarcode = Read barcode
products.create = Create product
......@@ -1268,6 +1282,7 @@ shop.toAccountValue = To account
shop.totalPrice = Total
shop.transactionTotal = Transaction total
shop.unitdiscount = Discount
shop.updatePrices = Update prices
shop.user = Selling to
sidebar.bill.list = My bills
......@@ -1556,6 +1571,7 @@ tournaments.admin.edit_rules = Edit rules
tournaments.admin.edit_tournament = Edit tournament
tournaments.admin.game_description = Game description
tournaments.admin.game_name = Game name
tournaments.admin.open_for_roles = Roles allowing registeration
tournaments.admin.registration_time_constraints = Registration time
tournaments.admin.remove_confirmation_text = Are you sure you want to remove this tournament? THIS CANNOT BE REVERSED!
tournaments.admin.remove_title = Confirm tournament removal
......@@ -1836,15 +1852,3 @@ voting.create.voteEnd = Voting close
voting.create.voteStart = Voting start
yes = Yes
tournaments.admin.open_for_roles=Roles allowing registeration
productOptionGroup.name=Name
product.createProductOptionGroup=Create product feature
productOptionGroup.required=Required
productOption.name=Option name
productOption.add=Add new option
productOption.title=Options
productOptionGroup.title=Product feature
productOptionGroup.default=Default option
option.setAsDefault=set as default
place.reservetime=Reservetime
product.minBuyCount=Minium buy count
......@@ -849,6 +849,8 @@ off = Poissa
on = P\u00E4\u00E4ll\u00E4
option.setAsDefault = Aseta oletukseksi
org.hibernate.validator.constraints.Email.message = V\u00E4\u00E4rin muotoiltu s\u00E4hk\u00F6postiosoite
org.hibernate.validator.constraints.Length.message = length must be between {min} and {max}
org.hibernate.validator.constraints.NotEmpty.message = may not be empty
......@@ -971,6 +973,7 @@ place.product = Tuote
place.release = Vapauta paikka
place.releasetime = Vapautusaika
place.reserveForUser = Varaa k\u00E4ytt\u00E4j\u00E4lle
place.reservetime = Varaamisaika
place.send = Siirr\u00E4 paikka
place.width = Leveys
......@@ -1008,7 +1011,7 @@ placegroupView.editplace = Muokkaa paikkaa
placegroupview.groupCreator = Tilaaja
placegroupview.header = Omat paikat
placegroupview.lockPlaces=Lukitse paikat
placegroupview.lockPlaces = Lukitse paikat
placegroupview.noMemberships = Ei omia paikkoja
placegroupview.owner = Omistaja
placegroupview.placeReleaseFailed = Paikan vapauttaminen ep\u00E4onnistui!
......@@ -1019,8 +1022,8 @@ placegroupview.reservationName = Paikka
placegroupview.reservationProduct = Lippu
placegroupview.reserveForSelf = Valitse paikka itsellesi
placegroupview.token = Paikkakoodi / k\u00E4ytt\u00E4j\u00E4
placegroupview.unlockedPlacesNotification = Sinulla on lukitsemattomia paikkoja, sinun tulee lukita ne ennenkuin voit tarkastella lippuasi!
placegroupview.unlockedPlacesNotification=Sinulla on lukitsemattomia paikkoja, sinun tulee lukita ne ennenkuin voit tarkastella lippuasi\!
placeslot.add = Lis\u00E4\u00E4 paikkaslotti
placeslot.bill = Lasku
placeslot.id = ID
......@@ -1070,10 +1073,12 @@ product.color = V\u00E4ri k\u00E4ytt\u00F6liittym\u00
product.create = Luo tuote
product.createDiscount = Lis\u00E4\u00E4 m\u00E4\u00E4r\u00E4alennus
product.createLimit = Luo tuoterajoite
product.createProductOptionGroup = Luo ominaisuus
product.description = Kuvaus
product.edit = Muokkaa
product.expired = Vanhentuneet
product.inventoryQuantity = Varastotilanne
product.minBuyCount = Ostettava v\u00E4hint\u00E4\u00E4n
product.name = Tuotteen nimi
product.paid = Maksettu
product.prepaid = Prepaid
......@@ -1108,6 +1113,15 @@ productLimit.sort = J\u00E4rjestysnumero
productLimit.type = Rajoitteen tyyppi
productLimit.upperLimit = Yl\u00E4rajoite
productOption.add = Lis\u00E4\u00E4 uusi vaihtoehto
productOption.name = Vaihtoehdon nimi
productOption.title = Ominaisuuden vaihtoehdot
productOptionGroup.default = Oletusvaihtoehto
productOptionGroup.name = Nimi
productOptionGroup.required = Vaaditaan
productOptionGroup.title = Tuotevaihtoehto
productShopView.readBarcode = Lue viivakoodi
products.create = Luo tuote
......@@ -1255,6 +1269,7 @@ shop.toAccountValue = Tilille
shop.totalPrice = Yhteens\u00E4
shop.transactionTotal = Tapahtuma yhteens\u00E4
shop.unitdiscount = Alennus
shop.updatePrices = P\u00E4ivit\u00E4 hinnat
shop.user = Myyd\u00E4\u00E4n
sidebar.bill.list = Omat laskut
......@@ -1543,6 +1558,7 @@ tournaments.admin.edit_rules = Muokkaa s\u00E
tournaments.admin.edit_tournament = Muokkaa turnausta
tournaments.admin.game_description = Pelin kuvaus
tournaments.admin.game_name = Pelin nimi
tournaments.admin.open_for_roles = Rekister\u00F6itymiseen oikeuttavat ryhm\u00E4t
tournaments.admin.registration_time_constraints = Rekister\u00F6itymisaika
tournaments.admin.remove_confirmation_text = Oletko varma ett\u00E4 haluat poistaa turnauksen? T\u00C4T\u00C4 EI VOI PERUUTTAA!
tournaments.admin.remove_title = Vahvista turnauksen poisto
......@@ -1823,15 +1839,3 @@ voting.create.voteEnd = \u00C4\u00E4nestys kiinni
voting.create.voteStart = \u00C4\u00E4nestys auki
yes = Kyll\u00E4
tournaments.admin.open_for_roles=Rekister\u00F6itymiseen oikeuttavat ryhm\u00E4t
productOptionGroup.name=Nimi
product.createProductOptionGroup=Luo ominaisuus
productOptionGroup.required=Vaaditaan
productOption.name=Vaihtoehdon nimi
productOption.add=Lis\u00E4\u00E4 uusi vaihtoehto
productOption.title=Ominaisuuden vaihtoehdot
productOptionGroup.title=Tuotevaihtoehto
productOptionGroup.default=Oletusvaihtoehto
option.setAsDefault=Aseta oletukseksi
place.reservetime=Varaamisaika
product.minBuyCount=Ostettava v\u00E4hint\u00E4\u00E4n
Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!