Refactored to remove Entry and use Event everywhere.
This commit is contained in:
parent
ab1c7f2393
commit
e4a3b967de
3
project.properties
Normal file
3
project.properties
Normal file
@ -0,0 +1,3 @@
|
||||
#Fri, 14 Jan 2011 22:05:22 -0600
|
||||
|
||||
build.number=1
|
@ -4,7 +4,7 @@ import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
public interface CategorizationPlan {
|
||||
boolean deservesNewCategory(Event event, List<Entry> existingEntries);
|
||||
Category newCategory(Event event, List<Entry> existingEntries);
|
||||
List<Entry> findEntriesToRecategorize(Event event, List<Entry> existingEntries);
|
||||
boolean deservesNewCategory(Event event, List<Event> existingEvents);
|
||||
Category newCategory(Event event, List<Event> existingEvents);
|
||||
List<Event> findEventsToRecategorize(Event event, List<Event> existingEvents);
|
||||
}
|
||||
|
@ -7,20 +7,20 @@ import org.joda.time.Duration
|
||||
*/
|
||||
public abstract class Category implements Comparable<Category> {
|
||||
|
||||
public List<Entry> entries
|
||||
public List<Event> events
|
||||
public List<Category> categories
|
||||
public List<CategorizationPlan> categorizationPlans
|
||||
public String description
|
||||
|
||||
public Category() {
|
||||
entries = []
|
||||
events = []
|
||||
categories = []
|
||||
categorizationPlans = []
|
||||
description = "Unnamed Category"
|
||||
}
|
||||
|
||||
public Category(String description) {
|
||||
entries = []
|
||||
events = []
|
||||
categories = []
|
||||
categorizationPlans = []
|
||||
this.description = description
|
||||
@ -28,60 +28,74 @@ public abstract class Category implements Comparable<Category> {
|
||||
|
||||
public abstract boolean matchesEvent(Event e)
|
||||
|
||||
public Entry addEvent(Event e) {
|
||||
Entry entry
|
||||
public void addEvent(Event event) {
|
||||
|
||||
// see if we have or can create a subcategory that will hold this event
|
||||
entry = addToSubcategory(e)
|
||||
Event addedEvent = addToSubcategory(event)
|
||||
|
||||
// no, let's create a generic entry and add it
|
||||
if (!entry) {
|
||||
entry = new Entry(this, e)
|
||||
entries << entry
|
||||
// no, let's just add it on ourself
|
||||
if (!addedEvent) {
|
||||
events << event
|
||||
addedEvent = event
|
||||
}
|
||||
|
||||
return entry
|
||||
return addedEvent
|
||||
}
|
||||
|
||||
public Entry addToSubcategory(Event e) {
|
||||
public boolean addToSubcategory(Event e) {
|
||||
|
||||
// find all matching subcategories
|
||||
def matchingCategories = categories.findAll { it.matchesEvent(e) }
|
||||
|
||||
if (matchingCategories)
|
||||
if (matchingCategories)
|
||||
return matchingCategories[0].addEvent(e)
|
||||
|
||||
// no matching subcategories, can we create a new one based on one
|
||||
// of our plans?
|
||||
def matchingPlans = categorizationPlans.findAll
|
||||
{ it.deservesNewCategory(e, entries) }
|
||||
{ it.deservesNewCategory(e, events) }
|
||||
|
||||
if (matchingPlans) {
|
||||
// create the new category
|
||||
def newCategory = matchingPlans[0].newCategory(e, entries)
|
||||
def newCategory = matchingPlans[0].newCategory(e, events)
|
||||
|
||||
// add it to our list of cateogries
|
||||
categories << newCategory
|
||||
|
||||
// add the new event to the category
|
||||
def entry = newCategory.addEvent(e)
|
||||
def addedEvent = newCategory.addEvent(e)
|
||||
|
||||
// move all the entries that match the new category over
|
||||
def existingEntries = matchingPlans[0].findEntriesToRecategorize(e, entries)
|
||||
entries -= existingEntries
|
||||
newCategory.entries.addAll(existingEntries)
|
||||
existingEntries.each { it.category = newCategory }
|
||||
// move all the events that match the new category over
|
||||
def existingEvents = matchingPlans[0].findEventsToRecategorize(e, events)
|
||||
events -= existingEvents
|
||||
existingEvents.each { newCategory.addEvent(it) }
|
||||
|
||||
// return the new entry
|
||||
return entry
|
||||
return addedEvent
|
||||
}
|
||||
|
||||
return null
|
||||
}
|
||||
|
||||
public Category filter(List<CategoryFilters> filters) {
|
||||
|
||||
// create new filtered category
|
||||
FilteredCategory fc = new FilteredCategory(description)
|
||||
fc.filters = filters
|
||||
|
||||
// filter all events and add them to the category
|
||||
fc.events
|
||||
|
||||
// TODO
|
||||
}
|
||||
|
||||
public Category filter(CategoryFilter filter) { return filter([filter]) }
|
||||
|
||||
public Category filter(Closure c) { return filter(c as CategoryFilter) }
|
||||
|
||||
public Duration getDuration() {
|
||||
return categories.sum(new Duration(0)) { it.duration } +
|
||||
entries.sum(new Duration(0)) { it.duration }
|
||||
events.sum(new Duration(0)) { it.duration }
|
||||
}
|
||||
|
||||
public int compareTo(Category other) {
|
||||
|
@ -2,19 +2,18 @@ package com.jdbernard.timeanalyzer
|
||||
|
||||
public class DescriptionBasedCategorizationPlan implements CategorizationPlan {
|
||||
|
||||
public boolean deservesNewCategory(Event event, List<Entry> existingEntries) {
|
||||
return existingEntries.findAll {
|
||||
it.description == event.description }.size() > 0
|
||||
public boolean deservesNewCategory(Event event, List<Event> existingEvents) {
|
||||
return existingEvents.any { it.description == event.description }
|
||||
}
|
||||
|
||||
public Category newCategory(Event event,
|
||||
List<Entry> existingEntries) {
|
||||
List<Event> existingEvents) {
|
||||
return new DescriptionBasedCategory(event.description)
|
||||
}
|
||||
|
||||
public List<Entry> findEntriesToRecategorize(Event event,
|
||||
List<Entry> existingEntries) {
|
||||
return existingEntries.findAll { it.description == event.description }
|
||||
public List<Event> findEventsToRecategorize(Event event,
|
||||
List<Event> existingEvents) {
|
||||
return existingEvents.findAll { it.description == event.description }
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,35 +0,0 @@
|
||||
package com.jdbernard.timeanalyzer;
|
||||
|
||||
import org.joda.time.DateTime;
|
||||
import org.joda.time.Duration;
|
||||
|
||||
public class Entry {
|
||||
|
||||
public String description;
|
||||
public String notes;
|
||||
public DateTime start;
|
||||
public Duration duration;
|
||||
public Category category;
|
||||
|
||||
public Entry(Category c, String description, DateTime start,
|
||||
Duration duration) {
|
||||
this(c, description, "", start, duration);
|
||||
}
|
||||
|
||||
public Entry(Category c, Event e) {
|
||||
this(c, e.description, e.notes, e.start, e.duration);
|
||||
}
|
||||
|
||||
public Entry(Category c, String description, String notes, DateTime start,
|
||||
Duration duration) {
|
||||
this.description = description;
|
||||
this.notes = notes;
|
||||
this.start = start;
|
||||
this.duration = duration;
|
||||
this.category = c;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return category.description + ": " + description;
|
||||
}
|
||||
}
|
40
src/main/com/jdbernard/timeanalyzer/Event.groovy
Normal file
40
src/main/com/jdbernard/timeanalyzer/Event.groovy
Normal file
@ -0,0 +1,40 @@
|
||||
package com.jdbernard.timeanalyzer
|
||||
|
||||
import org.joda.time.DateTime
|
||||
import org.joda.time.Duration
|
||||
import org.joda.time.format.PeriodFormat
|
||||
import org.joda.time.format.PeriodFormatter
|
||||
|
||||
public class Event implements Cloneable {
|
||||
|
||||
public final String description
|
||||
public final String notes
|
||||
public final DateTime start
|
||||
public final Duration duration
|
||||
|
||||
public static PeriodFormatter periodFormatter = PeriodFormat.getDefault()
|
||||
|
||||
public Event(String desc, String notes, DateTime start, Duration duration) {
|
||||
this.description = desc
|
||||
this.notes = notes
|
||||
this.start = start
|
||||
this.duration = duration
|
||||
}
|
||||
|
||||
public Event(Map params) {
|
||||
this.description = params.description ?: ""
|
||||
this.notes = params.notes ?: ""
|
||||
this.start = params.start
|
||||
this.duration = params.duration
|
||||
}
|
||||
|
||||
public Event(Map params, Event e) {
|
||||
this.description = params.description ?: e.description
|
||||
this.notes = params.notes ?: e.notes
|
||||
this.start = params.start ?: e.start
|
||||
this.duration = params.duration ?: e.duration
|
||||
}
|
||||
|
||||
public String toString() { return description }
|
||||
|
||||
}
|
@ -1,25 +0,0 @@
|
||||
package com.jdbernard.timeanalyzer;
|
||||
|
||||
import org.joda.time.DateTime;
|
||||
import org.joda.time.Duration;
|
||||
import org.joda.time.format.PeriodFormat;
|
||||
import org.joda.time.format.PeriodFormatter;
|
||||
|
||||
public class Event implements Cloneable {
|
||||
|
||||
public String description;
|
||||
public String notes;
|
||||
public DateTime start;
|
||||
public Duration duration;
|
||||
|
||||
|
||||
|
||||
public static PeriodFormatter periodFormatter = PeriodFormat.getDefault();
|
||||
|
||||
public String toString() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public Object clone() throws CloneNotSupportedException
|
||||
{ return super.clone(); }
|
||||
}
|
@ -12,7 +12,8 @@ public class TimeIntervalCategoryFilter implements CategoryFilter {
|
||||
this.interval = interval
|
||||
}
|
||||
|
||||
public TimeIntervalCategoryFilter(ReadableInstant start, ReadableInstant end) {
|
||||
public TimeIntervalCategoryFilter(ReadableInstant start,
|
||||
ReadableInstant end) {
|
||||
this.interval = new Interval(start, end)
|
||||
}
|
||||
|
||||
|
@ -4,18 +4,18 @@ public class TwoLevelCategorizationPlan implements CategorizationPlan {
|
||||
|
||||
private static final def TWO_LEVEL_PATTERN = ~/(.+?):(.*)/
|
||||
|
||||
public boolean deservesNewCategory(Event event, List<Entry> el) {
|
||||
public boolean deservesNewCategory(Event event, List<Event> el) {
|
||||
return event ==~ TWO_LEVEL_PATTERN
|
||||
}
|
||||
|
||||
public Category newCategory(Event event, List<Entry> el) {
|
||||
public Category newCategory(Event event, List<Event> el) {
|
||||
def m = event.description =~ TWO_LEVEL_PATTERN
|
||||
return new TwoLevelCategory(m[0][1])
|
||||
}
|
||||
|
||||
public List<Entry> findEntriesToRecategorize(Event event,
|
||||
List<Entry> existingEntries) {
|
||||
public List<Event> findEventsToRecategorize(Event event,
|
||||
List<Event> existingEvents) {
|
||||
def m = event.description =~ TWO_LEVEL_PATTERN
|
||||
return existingEntries.findAll { it.description ==~ /${m[0][1]}:.*/ }
|
||||
return existingEvents.findAll { it.description ==~ /${m[0][1]}:.*/ }
|
||||
}
|
||||
}
|
||||
|
@ -15,14 +15,10 @@ public class TwoLevelCategory extends Category {
|
||||
}
|
||||
|
||||
public Entry addEvent(Event e) {
|
||||
def event = e.clone()
|
||||
def m = e.description =~ descriptionPattern
|
||||
|
||||
def m = event.description =~ descriptionPattern
|
||||
e = new Event(e, description: m[0][1])
|
||||
|
||||
event.description = m[0][1]
|
||||
|
||||
def entry = super.addEvent(event)
|
||||
|
||||
return entry
|
||||
return super.addEvent(e)
|
||||
}
|
||||
}
|
||||
|
@ -3,28 +3,27 @@ package com.quantumdigital.ithelp.timeanalyzer
|
||||
import com.jdbernard.timeanalyzer.Category
|
||||
import com.jdbernard.timeanalyzer.CategorizationPlan
|
||||
import com.jdbernard.timeanalyzer.Event
|
||||
import com.jdbernard.timeanalyzer.Entry
|
||||
|
||||
public class TicketCategorizationPlan implements CategorizationPlan {
|
||||
|
||||
private static def TICKET_PATTERN = ~/.*#(\d+).*/
|
||||
|
||||
public boolean deservesNewCategory(Event e, List<Entry> el) {
|
||||
public boolean deservesNewCategory(Event e, List<Event> el) {
|
||||
return e.description ==~ TICKET_PATTERN
|
||||
}
|
||||
|
||||
public Category newCategory(Event e, List<Entry> el) {
|
||||
public Category newCategory(Event e, List<Event> el) {
|
||||
def m = e.description =~ TICKET_PATTERN
|
||||
|
||||
return new TicketCategory(m[0][1] as int)
|
||||
}
|
||||
|
||||
public List<Entry> findEntriesToRecategorize(Event e,
|
||||
List<Entry> existingEntries) {
|
||||
public List<Event> findEventsToRecategorize(Event e,
|
||||
List<Event> existingEvents) {
|
||||
def m = e.description =~ TICKET_PATTERN
|
||||
int ticketId = m[0][1] as int
|
||||
|
||||
return existingEntries.findAll {
|
||||
return existingEvents.findAll {
|
||||
it.description ==~ /.*#${ticketId}.*/ }
|
||||
}
|
||||
}
|
||||
|
@ -17,9 +17,9 @@ public class TicketCategory extends Category {
|
||||
return (e.description ==~ /.*#${ticketId}.*/)
|
||||
}
|
||||
|
||||
public TicketEntry addEvent(Event e) {
|
||||
TicketEntry te = new TicketEntry(this, e)
|
||||
entries << te
|
||||
public TicketEvent addEvent(Event e) {
|
||||
TicketEvent te = new TicketEvent(this, e)
|
||||
events << te
|
||||
return te
|
||||
}
|
||||
}
|
||||
|
@ -1,16 +1,30 @@
|
||||
package com.quantumdigital.ithelp.timeanalyzer
|
||||
|
||||
import com.jdbernard.timeanalyzer.Entry
|
||||
import com.jdbernard.timeanalyzer.Event
|
||||
|
||||
public class TicketEntry extends Entry {
|
||||
public class TicketEvent extends Event {
|
||||
|
||||
public int id
|
||||
public final int id
|
||||
|
||||
public TicketEntry(TicketCategory category, Event e) {
|
||||
super(category, e)
|
||||
public TicketEvent(String desc, String notes, String start, String duration) {
|
||||
|
||||
def m = e.description =~ /.*#(\d+).*/
|
||||
super(desc, note, start, duration)
|
||||
|
||||
def m = desc =~ /.*#(\d+).*/
|
||||
this.id = m[0][1] as int
|
||||
}
|
||||
|
||||
public TicketEvent(Map params) {
|
||||
super(params)
|
||||
|
||||
def m = description =~ /.*#(\d+).*/
|
||||
this.id = m[0][1] as int
|
||||
}
|
||||
|
||||
public TicketEvent(Map params, Event e) {
|
||||
super(params, e)
|
||||
|
||||
def m = description =~ /.*#(\d+).*/
|
||||
this.id = m[0][1] as int
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user