Commit 80f50ff5 by Tuomas Riihimäki

Fuuuu

1 parent a480516f
...@@ -3,6 +3,7 @@ package fi.codecrew.moya.beans; ...@@ -3,6 +3,7 @@ package fi.codecrew.moya.beans;
import java.util.Date; import java.util.Date;
import java.util.List; import java.util.List;
import java.util.Set; import java.util.Set;
import java.util.concurrent.ConcurrentSkipListSet;
import java.util.concurrent.LinkedBlockingQueue; import java.util.concurrent.LinkedBlockingQueue;
import javax.ejb.Local; import javax.ejb.Local;
...@@ -43,7 +44,7 @@ public interface QueueBeanLocal { ...@@ -43,7 +44,7 @@ public interface QueueBeanLocal {
public interface MapQueueI { public interface MapQueueI {
LinkedBlockingQueue<EventUser> getQueue(); ConcurrentSkipListSet<MapReservationQueueEntry> getQueue();
Set<EventUser> getReserving(); Set<EventUser> getReserving();
......
...@@ -3,11 +3,13 @@ package fi.codecrew.moya.beans; ...@@ -3,11 +3,13 @@ package fi.codecrew.moya.beans;
import java.util.Collections; import java.util.Collections;
import java.util.Date; import java.util.Date;
import java.util.HashMap; import java.util.HashMap;
import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Set; import java.util.Set;
import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap; import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.ConcurrentSkipListSet;
import java.util.concurrent.LinkedBlockingQueue; import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.atomic.AtomicLong; import java.util.concurrent.atomic.AtomicLong;
...@@ -50,26 +52,20 @@ public class QueueBean implements QueueBeanLocal { ...@@ -50,26 +52,20 @@ public class QueueBean implements QueueBeanLocal {
logger.info("Initialized2 QueueBean, {}", mapqueues); logger.info("Initialized2 QueueBean, {}", mapqueues);
} }
@EJB
private PlaceBeanLocal placebean;
private final ConcurrentHashMap<Integer, MapQueue> mapqueues = new ConcurrentHashMap<Integer, QueueBean.MapQueue>(); private final ConcurrentHashMap<Integer, MapQueue> mapqueues = new ConcurrentHashMap<Integer, QueueBean.MapQueue>();
private int defaultTimeoutMin = 10; private int defaultTimeoutMin = 10;
private int minimumSlotsInQueue = 1; private int minimumSlotsInQueue = 9999;
private int reservingSize = 5; private int reservingSize = 1;
private class MapQueue implements MapQueueI { private class MapQueue implements MapQueueI {
// private final Set<MapReservationQueueEntry> reserving = new HashSet<>(); // private final Set<MapReservationQueueEntry> reserving = new HashSet<>();
private final Set<EventUser> reserving = Collections.newSetFromMap(new ConcurrentHashMap<EventUser, Boolean>()); private final Set<EventUser> reserving = Collections.newSetFromMap(new ConcurrentHashMap<EventUser, Boolean>());
private final LinkedBlockingQueue<EventUser> queue = new LinkedBlockingQueue<>(); private final ConcurrentSkipListSet<MapReservationQueueEntry> queue = new ConcurrentSkipListSet<>();
private final ConcurrentMap<EventUser, MapReservationQueueEntry> queEntries = new ConcurrentHashMap<>(); private final ConcurrentMap<EventUser, MapReservationQueueEntry> queEntries = new ConcurrentHashMap<>();
// public boolean enterReserving( EventUser user) {
// timeoutReserving();
//
// if (reserving.size() < 3 && !queue.isEmpty() && queue.get(0).equals(entry)) {
// entry = queue.get(0);
// entry.removeFromQueue();
// }
// }
private void timeoutEntries() { private void timeoutEntries() {
logger.info("Timeouting entries"); logger.info("Timeouting entries");
// give 10 seconds mercy ( and give us some time to go through all entries) // give 10 seconds mercy ( and give us some time to go through all entries)
...@@ -86,8 +82,8 @@ public class QueueBean implements QueueBeanLocal { ...@@ -86,8 +82,8 @@ public class QueueBean implements QueueBeanLocal {
// Set idle time to the past. // Set idle time to the past.
// Idle timeout after 60 seconds // Idle timeout after 60 seconds
Date idleTimeout = new Date(System.currentTimeMillis() - 1000 * 60); Date idleTimeout = new Date(System.currentTimeMillis() - 1000 * 60);
for (EventUser q : queue) { for (MapReservationQueueEntry entry : queue) {
MapReservationQueueEntry entry = queEntries.get(q);
if (entry.getSeenTime() == null) { if (entry.getSeenTime() == null) {
entry.setSeenTime(new Date()); entry.setSeenTime(new Date());
continue; continue;
...@@ -115,11 +111,10 @@ public class QueueBean implements QueueBeanLocal { ...@@ -115,11 +111,10 @@ public class QueueBean implements QueueBeanLocal {
if (reserving.size() < reservingSize) { if (reserving.size() < reservingSize) {
synchronized (queue) { synchronized (queue) {
if (reserving.size() < reservingSize) { if (reserving.size() < reservingSize) {
EventUser queEntry = queue.poll(); MapReservationQueueEntry queEntry = queue.pollLast();
if (queEntry != null) { if (queEntry != null) {
reserving.add(queEntry); reserving.add(queEntry.getUser());
MapReservationQueueEntry ue = queEntries.get(queEntry); queEntry.setReservationTimeout(new Date(System.currentTimeMillis() + defaultTimeoutMin * 60 * 1000));
ue.setReservationTimeout(new Date(System.currentTimeMillis() + defaultTimeoutMin * 60 * 1000));
} }
} }
} }
...@@ -137,8 +132,9 @@ public class QueueBean implements QueueBeanLocal { ...@@ -137,8 +132,9 @@ public class QueueBean implements QueueBeanLocal {
if (reserving.remove(user)) { if (reserving.remove(user)) {
logger.info("Removed user {} from reserving queue", user); logger.info("Removed user {} from reserving queue", user);
} }
MapReservationQueueEntry entry = queEntries.get(user);
// There should neve be more than one instance, but make sure // There should neve be more than one instance, but make sure
while (queue.remove(user)) { while (queue.remove(entry)) {
logger.info("Removed user {} from queue"); logger.info("Removed user {} from queue");
} }
ret = queEntries.remove(user); ret = queEntries.remove(user);
...@@ -148,15 +144,18 @@ public class QueueBean implements QueueBeanLocal { ...@@ -148,15 +144,18 @@ public class QueueBean implements QueueBeanLocal {
} }
public MapReservationQueueEntry enter(EventUser user) { public MapReservationQueueEntry enter(EventUser user) {
MapReservationQueueEntry ret = null; MapReservationQueueEntry ret = queEntries.get(user);
synchronized (queue) { synchronized (queue) {
if (!reserving.contains(user) && !queue.contains(user)) { if (!reserving.contains(user) && (ret == null || !queue.contains(ret))) {
ret = new MapReservationQueueEntry(); if (ret == null) {
ret.setUser(user); ret = new MapReservationQueueEntry();
ret.setSeenTime(new Date()); ret.setUser(user);
ret.setSeenTime(new Date());
ret.setPlaceslotcount(placebean.getPlaceslots(user).size());
}
queEntries.put(user, ret); queEntries.put(user, ret);
boolean queStat = queue.offer(user); boolean queStat = queue.add(ret);
logger.info("User {} not in queue, offer state {}", user, queStat); logger.info("User {} not in queue, offer state {}", user, queStat);
// Check if the user can be put to reservation queue immediately // Check if the user can be put to reservation queue immediately
...@@ -179,12 +178,15 @@ public class QueueBean implements QueueBeanLocal { ...@@ -179,12 +178,15 @@ public class QueueBean implements QueueBeanLocal {
entry = new MapReservationQueueEntry(); entry = new MapReservationQueueEntry();
entry.setCreated(new Date()); entry.setCreated(new Date());
entry.setUser(u); entry.setUser(u);
entry.setPlaceslotcount(placebean.getPlaceslots(u).size());
queEntries.put(u, entry); queEntries.put(u, entry);
} }
entry.setReservationTimeout(time); entry.setReservationTimeout(time);
entry.setSeenTime(new Date()); entry.setSeenTime(new Date());
reserving.remove(u); reserving.remove(u);
queue.remove(u);
queue.remove(entry);
reserving.add(u); reserving.add(u);
} }
...@@ -193,15 +195,15 @@ public class QueueBean implements QueueBeanLocal { ...@@ -193,15 +195,15 @@ public class QueueBean implements QueueBeanLocal {
public Integer getPosition(EventUser user) { public Integer getPosition(EventUser user) {
Integer ret = null; Integer ret = null;
MapReservationQueueEntry entry = queEntries.get(user);
if (reserving.contains(user)) { if (reserving.contains(user)) {
ret = 0; ret = 0;
logger.info("User in reserving queue {}", user); logger.info("User in reserving queue {}", user);
} else if (queue.contains(user)) { } else if (entry != null && queue.contains(entry)) {
ret = 1; ret = 1;
for (EventUser eu : queue) { for (Iterator<MapReservationQueueEntry> iterator = queue.descendingIterator(); iterator.hasNext();) {
if (eu.equals(user)) { MapReservationQueueEntry eu = iterator.next();
if (eu.getUser().equals(user)) {
break; break;
} }
++ret; ++ret;
...@@ -215,21 +217,23 @@ public class QueueBean implements QueueBeanLocal { ...@@ -215,21 +217,23 @@ public class QueueBean implements QueueBeanLocal {
} }
public boolean isInQueue(EventUser user) { public boolean isInQueue(EventUser user) {
return reserving.contains(user) || queue.contains(user); MapReservationQueueEntry entry = queEntries.get(user);
return reserving.contains(user) || (entry != null && queue.contains(entry));
} }
public MapReservationQueueEntry getEntry(EventUser user) { public MapReservationQueueEntry getEntry(EventUser user) {
return queEntries.get(user); return queEntries.get(user);
} }
public LinkedBlockingQueue<EventUser> getQueue() {
return queue;
}
public Set<EventUser> getReserving() { public Set<EventUser> getReserving() {
return reserving; return reserving;
} }
@Override
public ConcurrentSkipListSet<MapReservationQueueEntry> getQueue() {
return queue;
}
} }
@EJB @EJB
...@@ -296,7 +300,11 @@ public class QueueBean implements QueueBeanLocal { ...@@ -296,7 +300,11 @@ public class QueueBean implements QueueBeanLocal {
MapQueue ret = mapqueues.get(map.getId()); MapQueue ret = mapqueues.get(map.getId());
if (ret == null) { if (ret == null) {
ret = mapqueues.putIfAbsent(map.getId(), new MapQueue()); ret = new MapQueue();
MapQueue nret = mapqueues.putIfAbsent(map.getId(), ret);
if (nret != null) {
ret = nret;
}
} }
logger.info("returning queue {} for map {}", ret, map); logger.info("returning queue {} for map {}", ret, map);
return ret; return ret;
......
...@@ -25,7 +25,7 @@ import fi.codecrew.moya.model.GenericEntity; ...@@ -25,7 +25,7 @@ import fi.codecrew.moya.model.GenericEntity;
// @Entity // @Entity
// @Table(name = "map_reservation_queue_entry") // @Table(name = "map_reservation_queue_entry")
public class MapReservationQueueEntry extends GenericEntity { public class MapReservationQueueEntry extends GenericEntity implements Comparable<MapReservationQueueEntry> {
/** /**
* *
...@@ -47,6 +47,10 @@ public class MapReservationQueueEntry extends GenericEntity { ...@@ -47,6 +47,10 @@ public class MapReservationQueueEntry extends GenericEntity {
@Transient @Transient
private Date seenTime; private Date seenTime;
@Transient
private Integer placeslotcount;
// @OneToOne() // @OneToOne()
// @JoinColumn(nullable = true) // @JoinColumn(nullable = true)
// private MapReservationQueueEntry previous; // private MapReservationQueueEntry previous;
...@@ -117,4 +121,21 @@ public class MapReservationQueueEntry extends GenericEntity { ...@@ -117,4 +121,21 @@ public class MapReservationQueueEntry extends GenericEntity {
this.seenTime = seenTime; this.seenTime = seenTime;
} }
@Override
public int compareTo(MapReservationQueueEntry o) {
return getPlaceslotcount().compareTo(o.getPlaceslotcount());
}
private Integer getPlaceslotcount() {
if (placeslotcount == null) {
placeslotcount = 0;
}
return placeslotcount;
}
public void setPlaceslotcount(Integer placeslotcount) {
this.placeslotcount = placeslotcount;
}
} }
...@@ -92,9 +92,8 @@ public class QueueManageView extends GenericCDIView { ...@@ -92,9 +92,8 @@ public class QueueManageView extends GenericCDIView {
List<MapReservationQueueEntry> ret = new ArrayList<>(); List<MapReservationQueueEntry> ret = new ArrayList<>();
if (queue == null) if (queue == null)
return null; return null;
for (EventUser u : queue.getQueue()) for (MapReservationQueueEntry u : queue.getQueue()) {
{ ret.add(queue.getEntry(u.getUser()));
ret.add(queue.getEntry(u));
} }
ListDataModel<MapReservationQueueEntry> retMod = new ListDataModel<>(ret); ListDataModel<MapReservationQueueEntry> retMod = new ListDataModel<>(ret);
......
Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!