Replace toJSON methods by Gson

pull/286/head
Alinson S. Xavier 9 years ago
parent 13b4128777
commit 08e3c9cc40

@ -77,6 +77,7 @@ dependencies {
compile 'com.opencsv:opencsv:3.7'
compile 'org.apmem.tools:layouts:1.10@aar'
compile 'org.jetbrains:annotations-java5:15.0'
compile 'com.google.code.gson:gson:2.8.0'
provided 'javax.annotation:jsr250-api:1.0'
@ -89,6 +90,7 @@ dependencies {
testCompile 'junit:junit:4.12'
testCompile 'org.hamcrest:hamcrest-library:1.3'
testCompile 'org.mockito:mockito-core:1.10.19'
testCompile 'org.json:json:20160810'
androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.1') {
exclude group: 'com.android.support'

@ -23,56 +23,31 @@ import android.support.annotation.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.models.*;
import org.json.*;
import java.util.*;
import static org.isoron.uhabits.commands.CommandParser.*;
/**
* Command to archive a list of habits.
*/
public class ArchiveHabitsCommand extends Command
{
private List<Habit> selectedHabits;
final List<Habit> selected;
private final HabitList habitList;
final HabitList habitList;
public ArchiveHabitsCommand(@NonNull HabitList habitList,
@NonNull List<Habit> selectedHabits)
@NonNull List<Habit> selected)
{
super();
this.habitList = habitList;
this.selectedHabits = selectedHabits;
}
public ArchiveHabitsCommand(@NonNull String id,
@NonNull HabitList habitList,
@NonNull List<Habit> selectedHabits)
{
super(id);
this.habitList = habitList;
this.selectedHabits = selectedHabits;
}
public static Command fromJSON(@NonNull JSONObject json,
@NonNull HabitList habitList)
throws JSONException
{
String id = json.getString("id");
JSONObject data = (JSONObject) json.get("data");
JSONArray habitIds = data.getJSONArray("ids");
LinkedList<Habit> selectedHabits =
habitListFromJSON(habitList, habitIds);
return new ArchiveHabitsCommand(id, habitList, selectedHabits);
this.selected = new LinkedList<>(selected);
}
@Override
public void execute()
{
for (Habit h : selectedHabits) h.setArchived(true);
habitList.update(selectedHabits);
for (Habit h : selected) h.setArchived(true);
habitList.update(selected);
}
@Override
@ -87,28 +62,51 @@ public class ArchiveHabitsCommand extends Command
return R.string.toast_habit_unarchived;
}
@Nullable
@Override
public JSONObject toJSON()
public void undo()
{
try
{
JSONObject root = super.toJSON();
JSONObject data = root.getJSONObject("data");
root.put("event", "ArchiveHabits");
data.put("ids", habitListToJSON(selectedHabits));
return root;
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
}
for (Habit h : selected) h.setArchived(false);
habitList.update(selected);
}
@NonNull
@Override
public void undo()
public Record toRecord()
{
return new Record(this);
}
public static class Record
{
for (Habit h : selectedHabits) h.setArchived(false);
habitList.update(selectedHabits);
@NonNull
public final String id;
@NonNull
public final String event = "Archive";
@NonNull
public final List<Long> habits;
public Record(@NonNull ArchiveHabitsCommand command)
{
id = command.getId();
habits = new LinkedList<>();
for (Habit h : command.selected)
{
habits.add(h.getId());
}
}
@NonNull
public ArchiveHabitsCommand toCommand(@NonNull HabitList habitList)
{
List<Habit> selected = new LinkedList<>();
for (Long id : this.habits) selected.add(habitList.getById(id));
ArchiveHabitsCommand command;
command = new ArchiveHabitsCommand(habitList, selected);
command.setId(id);
return command;
}
}
}

@ -23,54 +23,35 @@ import android.support.annotation.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.models.*;
import org.json.*;
import java.util.*;
import static org.isoron.uhabits.commands.CommandParser.*;
/**
* Command to change the color of a list of habits.
*/
public class ChangeHabitColorCommand extends Command
{
HabitList habitList;
@NonNull
final HabitList habitList;
List<Habit> selected;
@NonNull
final List<Habit> selected;
List<Integer> originalColors;
@NonNull
final List<Integer> originalColors;
Integer newColor;
@NonNull
final Integer newColor;
public ChangeHabitColorCommand(@NonNull HabitList habitList,
@NonNull List<Habit> selected,
@NonNull Integer newColor)
{
super();
init(habitList, selected, newColor);
}
public ChangeHabitColorCommand(@NonNull String id,
@NonNull HabitList habitList,
@NonNull List<Habit> selected,
@NonNull Integer newColor)
{
super(id);
init(habitList, selected, newColor);
}
@NonNull
public static Command fromJSON(@NonNull JSONObject json,
@NonNull HabitList habitList)
throws JSONException
{
String id = json.getString("id");
JSONObject data = (JSONObject) json.get("data");
JSONArray habitIds = data.getJSONArray("ids");
int newColor = data.getInt("color");
LinkedList<Habit> selected = habitListFromJSON(habitList, habitIds);
return new ChangeHabitColorCommand(id, habitList, selected, newColor);
this.habitList = habitList;
this.selected = selected;
this.newColor = newColor;
this.originalColors = new ArrayList<>(selected.size());
for (Habit h : selected) originalColors.add(h.getColor());
}
@Override
@ -92,23 +73,11 @@ public class ChangeHabitColorCommand extends Command
return R.string.toast_habit_changed;
}
@Override
@NonNull
public JSONObject toJSON()
@Override
public Record toRecord()
{
try
{
JSONObject root = super.toJSON();
JSONObject data = root.getJSONObject("data");
root.put("event", "ChangeHabitColor");
data.put("ids", habitListToJSON(selected));
data.put("color", newColor);
return root;
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
}
return new Record(this);
}
@Override
@ -119,15 +88,41 @@ public class ChangeHabitColorCommand extends Command
habitList.update(selected);
}
private void init(@NonNull HabitList habitList,
@NonNull List<Habit> selected,
@NonNull Integer newColor)
public static class Record
{
this.habitList = habitList;
this.selected = selected;
this.newColor = newColor;
this.originalColors = new ArrayList<>(selected.size());
@NonNull
public String id;
for (Habit h : selected) originalColors.add(h.getColor());
@NonNull
public String event = "ChangeColor";
@NonNull
public List<Long> habits;
@NonNull
public Integer color;
public Record(ChangeHabitColorCommand command)
{
id = command.getId();
color = command.newColor;
habits = new LinkedList<>();
for (Habit h : command.selected)
{
if (!h.hasId()) throw new RuntimeException("Habit not saved");
habits.add(h.getId());
}
}
public ChangeHabitColorCommand toCommand(@NonNull HabitList habitList)
{
List<Habit> selected = new LinkedList<>();
for (Long id : this.habits) selected.add(habitList.getById(id));
ChangeHabitColorCommand command;
command = new ChangeHabitColorCommand(habitList, selected, color);
command.setId(id);
return command;
}
}
}

@ -19,6 +19,10 @@
package org.isoron.uhabits.commands;
import android.support.annotation.*;
import com.google.gson.*;
import org.isoron.uhabits.utils.*;
import org.json.*;
@ -33,7 +37,7 @@ import org.json.*;
*/
public abstract class Command
{
private final String id;
private String id;
public Command()
{
@ -52,31 +56,37 @@ public abstract class Command
return null;
}
public String getId()
{
return id;
}
public void setId(String id)
{
this.id = id;
}
public Integer getUndoStringId()
{
return null;
}
public abstract void undo();
public JSONObject toJSON()
@NonNull
public JSONObject toJson()
{
try
{
JSONObject root = new JSONObject();
JSONObject data = new JSONObject();
root.put("id", getId());
root.put("data", data);
return root;
String json = new GsonBuilder().create().toJson(toRecord());
return new JSONObject(json);
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
throw new RuntimeException(e);
}
}
public String getId()
{
return id;
}
@NonNull
public abstract Object toRecord();
public abstract void undo();
}

@ -21,14 +21,13 @@ package org.isoron.uhabits.commands;
import android.support.annotation.*;
import com.google.gson.*;
import org.isoron.uhabits.models.*;
import org.json.*;
import java.util.*;
public class CommandParser
{
private HabitList habitList;
private ModelFactory modelFactory;
@ -41,65 +40,43 @@ public class CommandParser
}
@NonNull
public static LinkedList<Habit> habitListFromJSON(
@NonNull HabitList habitList, @NonNull JSONArray habitIds)
throws JSONException
{
LinkedList<Habit> habits = new LinkedList<>();
for (int i = 0; i < habitIds.length(); i++)
{
Long hId = habitIds.getLong(i);
Habit h = habitList.getById(hId);
if (h == null) continue;
habits.add(h);
}
return habits;
}
@NonNull
protected static JSONArray habitListToJSON(List<Habit> habits)
{
JSONArray habitIds = new JSONArray();
for (Habit h : habits) habitIds.put(h.getId());
return habitIds;
}
@NonNull
public Command fromJSON(@NonNull JSONObject json) throws JSONException
public Command parse(@NonNull JSONObject json) throws JSONException
{
switch (json.getString("event"))
{
case "ToggleRepetition":
return ToggleRepetitionCommand.fromJSON(json, habitList);
String event = json.getString("event");
Gson gson = new GsonBuilder().create();
case "ArchiveHabits":
return ArchiveHabitsCommand.fromJSON(json, habitList);
if (event.equals("Archive")) return gson
.fromJson(json.toString(), ArchiveHabitsCommand.Record.class)
.toCommand(habitList);
case "UnarchiveHabits":
return UnarchiveHabitsCommand.fromJSON(json, habitList);
if (event.equals("ChangeColor")) return gson
.fromJson(json.toString(), ChangeHabitColorCommand.Record.class)
.toCommand(habitList);
case "ChangeHabitColor":
return ChangeHabitColorCommand.fromJSON(json, habitList);
if (event.equals("CreateHabit")) return gson
.fromJson(json.toString(), CreateHabitCommand.Record.class)
.toCommand(modelFactory, habitList);
case "CreateHabit":
return CreateHabitCommand.fromJSON(json, habitList,
modelFactory);
if (event.equals("CreateRep")) return gson
.fromJson(json.toString(), CreateRepetitionCommand.Record.class)
.toCommand(habitList);
case "DeleteHabits":
return DeleteHabitsCommand.fromJSON(json, habitList);
if (event.equals("DeleteHabit")) return gson
.fromJson(json.toString(), DeleteHabitsCommand.Record.class)
.toCommand(habitList);
case "EditHabit":
return EditHabitCommand.fromJSON(json, habitList, modelFactory);
if (event.equals("EditHabit")) return gson
.fromJson(json.toString(), EditHabitCommand.Record.class)
.toCommand(modelFactory, habitList);
// TODO: Implement this
// case "ReorderHabit":
// return ReorderHabitCommand.fromJSON(json);
if (event.equals("Toggle")) return gson
.fromJson(json.toString(), ToggleRepetitionCommand.Record.class)
.toCommand(habitList);
}
if (event.equals("Unarchive")) return gson
.fromJson(json.toString(), UnarchiveHabitsCommand.Record.class)
.toCommand(habitList);
return null;
throw new IllegalStateException("Unknown command");
}
}

@ -25,7 +25,6 @@ import com.google.auto.factory.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.models.*;
import org.json.*;
/**
* Command to create a habit.
@ -33,54 +32,25 @@ import org.json.*;
@AutoFactory
public class CreateHabitCommand extends Command
{
private ModelFactory modelFactory;
ModelFactory modelFactory;
HabitList habitList;
@NonNull
private Habit model;
Habit model;
@Nullable
private Long savedId;
Long savedId;
public CreateHabitCommand(@Provided @NonNull ModelFactory modelFactory,
@NonNull HabitList habitList,
@NonNull Habit model)
{
super();
this.modelFactory = modelFactory;
this.habitList = habitList;
this.model = model;
}
public CreateHabitCommand(@Provided @NonNull ModelFactory modelFactory,
@NonNull String commandId,
@NonNull HabitList habitList,
@NonNull Habit model,
@Nullable Long savedId)
{
super(commandId);
this.modelFactory = modelFactory;
this.habitList = habitList;
this.model = model;
this.savedId = savedId;
}
@NonNull
public static Command fromJSON(@NonNull JSONObject root,
@NonNull HabitList habitList,
@NonNull ModelFactory modelFactory)
throws JSONException
{
String commandId = root.getString("id");
JSONObject data = (JSONObject) root.get("data");
Habit model = Habit.fromJSON(data.getJSONObject("habit"), modelFactory);
Long savedId = data.getLong("id");
return new CreateHabitCommand(modelFactory, commandId, habitList, model,
savedId);
}
@Override
public void execute()
{
@ -104,30 +74,55 @@ public class CreateHabitCommand extends Command
return R.string.toast_habit_deleted;
}
@NonNull
@Override
public JSONObject toJSON()
public Record toRecord()
{
try
{
JSONObject root = super.toJSON();
JSONObject data = root.getJSONObject("data");
root.put("event", "CreateHabit");
data.put("habit", model.toJSON());
data.put("id", savedId);
return root;
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
}
return new Record(this);
}
@Override
public void undo()
{
if (savedId == null) throw new IllegalStateException();
Habit habit = habitList.getById(savedId);
if (habit == null) throw new RuntimeException("Habit not found");
if (habit == null) throw new HabitNotFoundException();
habitList.remove(habit);
}
public static class Record
{
@NonNull
public String id;
@NonNull
public String event = "CreateHabit";
@NonNull
public Habit.HabitData habit;
@Nullable
public Long savedId;
public Record(CreateHabitCommand command)
{
id = command.getId();
habit = command.model.getData();
savedId = command.savedId;
}
public CreateHabitCommand toCommand(@NonNull ModelFactory modelFactory,
@NonNull HabitList habitList)
{
Habit h = modelFactory.buildHabit(habit);
CreateHabitCommand command;
command = new CreateHabitCommand(modelFactory, habitList, h);
command.savedId = savedId;
command.setId(id);
return command;
}
}
}

@ -29,15 +29,17 @@ import org.isoron.uhabits.models.*;
public class CreateRepetitionCommand extends Command
{
@NonNull
private final Habit habit;
final Habit habit;
private final long timestamp;
final long timestamp;
private final int value;
final int value;
private Repetition previousRep;
@Nullable
Repetition previousRep;
private Repetition newRep;
@Nullable
Repetition newRep;
public CreateRepetitionCommand(@NonNull Habit habit,
long timestamp,
@ -68,11 +70,57 @@ public class CreateRepetitionCommand extends Command
return habit;
}
@Override
@NonNull
public Record toRecord()
{
return new Record(this);
}
@Override
public void undo()
{
if(newRep == null) throw new IllegalStateException();
habit.getRepetitions().remove(newRep);
if (previousRep != null) habit.getRepetitions().add(previousRep);
habit.invalidateNewerThan(timestamp);
}
public static class Record
{
@NonNull
public String id;
@NonNull
public String event = "CreateRep";
public long habitId;
public long timestamp;
public int value;
public Record(CreateRepetitionCommand command)
{
id = command.getId();
Long habitId = command.habit.getId();
if(habitId == null) throw new RuntimeException("Habit not saved");
this.habitId = habitId;
this.timestamp = command.timestamp;
this.value = command.value;
}
public CreateRepetitionCommand toCommand(@NonNull HabitList habitList)
{
Habit h = habitList.getById(habitId);
if(h == null) throw new HabitNotFoundException();
CreateRepetitionCommand command;
command = new CreateRepetitionCommand(h, timestamp, value);
command.setId(id);
return command;
}
}
}

@ -23,56 +23,32 @@ import android.support.annotation.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.models.*;
import org.json.*;
import java.util.*;
import static org.isoron.uhabits.commands.CommandParser.habitListFromJSON;
import static org.isoron.uhabits.commands.CommandParser.habitListToJSON;
/**
* Command to delete a list of habits.
*/
public class DeleteHabitsCommand extends Command
{
HabitList habitList;
@NonNull
final HabitList habitList;
private List<Habit> habits;
@NonNull
final List<Habit> selected;
public DeleteHabitsCommand(@NonNull HabitList habitList,
@NonNull List<Habit> habits)
{
super();
this.habits = habits;
this.habitList = habitList;
}
public DeleteHabitsCommand(@NonNull String id,
@NonNull HabitList habitList,
@NonNull List<Habit> habits)
@NonNull List<Habit> selected)
{
super(id);
this.habits = habits;
this.selected = new LinkedList<>(selected);
this.habitList = habitList;
}
@NonNull
public static Command fromJSON(@NonNull JSONObject json,
@NonNull HabitList habitList)
throws JSONException
{
String id = json.getString("id");
JSONObject data = (JSONObject) json.get("data");
JSONArray habitIds = data.getJSONArray("ids");
LinkedList<Habit> habits = habitListFromJSON(habitList, habitIds);
return new DeleteHabitsCommand(id, habitList, habits);
}
@Override
public void execute()
{
for (Habit h : habits)
for (Habit h : selected)
habitList.remove(h);
}
@ -82,9 +58,9 @@ public class DeleteHabitsCommand extends Command
return R.string.toast_habit_deleted;
}
public List<Habit> getHabits()
public List<Habit> getSelected()
{
return new LinkedList<>(habits);
return Collections.unmodifiableList(selected);
}
@Override
@ -95,20 +71,9 @@ public class DeleteHabitsCommand extends Command
@Override
@NonNull
public JSONObject toJSON()
public Record toRecord()
{
try
{
JSONObject root = super.toJSON();
JSONObject data = root.getJSONObject("data");
root.put("event", "DeleteHabits");
data.put("ids", habitListToJSON(habits));
return root;
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
}
return new Record(this);
}
@Override
@ -116,4 +81,38 @@ public class DeleteHabitsCommand extends Command
{
throw new UnsupportedOperationException();
}
public static class Record
{
@NonNull
public String id;
@NonNull
public String event = "DeleteHabit";
@NonNull
public List<Long> habits;
public Record(DeleteHabitsCommand command)
{
id = command.getId();
habits = new LinkedList<>();
for (Habit h : command.selected)
{
if (!h.hasId()) throw new RuntimeException("Habit not saved");
habits.add(h.getId());
}
}
public DeleteHabitsCommand toCommand(@NonNull HabitList habitList)
{
List<Habit> selected = new LinkedList<>();
for (Long id : this.habits) selected.add(habitList.getById(id));
DeleteHabitsCommand command;
command = new DeleteHabitsCommand(habitList, selected);
command.setId(id);
return command;
}
}
}

@ -25,7 +25,6 @@ import com.google.auto.factory.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.models.*;
import org.json.*;
/**
* Command to modify a habit.
@ -33,52 +32,43 @@ import org.json.*;
@AutoFactory
public class EditHabitCommand extends Command
{
HabitList habitList;
@NonNull
final HabitList habitList;
private Habit original;
@NonNull
final Habit original;
private Habit modified;
@NonNull
final Habit modified;
private long savedId;
final long savedId;
private boolean hasFrequencyChanged;
final boolean hasFrequencyChanged;
private boolean hasTargetChanged;
final boolean hasTargetChanged;
public EditHabitCommand(@Provided @NonNull ModelFactory modelFactory,
@NonNull HabitList habitList,
@NonNull Habit original,
@NonNull Habit modified)
{
super();
init(modelFactory, habitList, original, modified);
}
Long habitId = original.getId();
if (habitId == null) throw new RuntimeException("Habit not saved");
public EditHabitCommand(@Provided @NonNull ModelFactory modelFactory,
@NonNull String id,
@NonNull HabitList habitList,
@NonNull Habit original,
@NonNull Habit modified)
{
super(id);
init(modelFactory, habitList, original, modified);
}
this.savedId = habitId;
this.habitList = habitList;
this.modified = modelFactory.buildHabit();
this.original = modelFactory.buildHabit();
@NonNull
public static Command fromJSON(@NonNull JSONObject root,
@NonNull HabitList habitList,
@NonNull ModelFactory modelFactory)
throws JSONException
{
String commandId = root.getString("id");
JSONObject data = (JSONObject) root.get("data");
Habit original = habitList.getById(data.getLong("id"));
if (original == null) throw new HabitNotFoundException();
Habit modified =
Habit.fromJSON(data.getJSONObject("params"), modelFactory);
return new EditHabitCommand(modelFactory, commandId, habitList,
original, modified);
this.modified.copyFrom(modified);
this.original.copyFrom(original);
Frequency originalFreq = this.original.getFrequency();
Frequency modifiedFreq = this.modified.getFrequency();
hasFrequencyChanged = (!originalFreq.equals(modifiedFreq));
hasTargetChanged =
(original.getTargetType() != modified.getTargetType() ||
original.getTargetValue() != modified.getTargetValue());
}
@Override
@ -99,22 +89,11 @@ public class EditHabitCommand extends Command
return R.string.toast_habit_changed_back;
}
@NonNull
@Override
public JSONObject toJSON()
public Record toRecord()
{
try
{
JSONObject root = super.toJSON();
JSONObject data = root.getJSONObject("data");
root.put("event", "EditHabit");
data.put("id", savedId);
data.put("params", modified.toJSON());
return root;
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
}
return new Record(this);
}
@Override
@ -131,33 +110,44 @@ public class EditHabitCommand extends Command
habit.copyFrom(model);
habitList.update(habit);
invalidateIfNeeded(habit);
if (hasFrequencyChanged || hasTargetChanged)
habit.invalidateNewerThan(0);
}
private void init(@NonNull ModelFactory modelFactory,
@NonNull HabitList habitList,
@NonNull Habit original,
@NonNull Habit modified)
public static class Record
{
this.habitList = habitList;
this.savedId = original.getId();
this.modified = modelFactory.buildHabit();
this.original = modelFactory.buildHabit();
@NonNull
public String id;
this.modified.copyFrom(modified);
this.original.copyFrom(original);
@NonNull
public String event = "EditHabit";
Frequency originalFreq = this.original.getFrequency();
Frequency modifiedFreq = this.modified.getFrequency();
hasFrequencyChanged = (!originalFreq.equals(modifiedFreq));
hasTargetChanged =
(original.getTargetType() != modified.getTargetType() ||
original.getTargetValue() != modified.getTargetValue());
}
@NonNull
public Habit.HabitData habit;
private void invalidateIfNeeded(Habit habit)
{
if (hasFrequencyChanged || hasTargetChanged)
habit.invalidateNewerThan(0);
public long habitId;
public Record(EditHabitCommand command)
{
id = command.getId();
this.habitId = command.savedId;
this.habit = command.modified.getData();
}
@NonNull
public EditHabitCommand toCommand(@NonNull ModelFactory modelFactory,
@NonNull HabitList habitList)
{
Habit original = habitList.getById(habitId);
if(original == null) throw new HabitNotFoundException();
Habit modified = modelFactory.buildHabit(habit);
EditHabitCommand command;
command = new EditHabitCommand(modelFactory, habitList, original,
modified);
command.setId(id);
return command;
}
}
}

@ -22,16 +22,16 @@ package org.isoron.uhabits.commands;
import android.support.annotation.*;
import org.isoron.uhabits.models.*;
import org.json.*;
/**
* Command to toggle a repetition.
*/
public class ToggleRepetitionCommand extends Command
{
private Long timestamp;
final long timestamp;
private Habit habit;
@NonNull
final Habit habit;
public ToggleRepetitionCommand(@NonNull Habit habit, long timestamp)
{
@ -40,37 +40,13 @@ public class ToggleRepetitionCommand extends Command
this.habit = habit;
}
public ToggleRepetitionCommand(@NonNull String id,
@NonNull Habit habit,
long timestamp)
{
super(id);
this.timestamp = timestamp;
this.habit = habit;
}
@NonNull
public static Command fromJSON(@NonNull JSONObject json,
@NonNull HabitList habitList)
throws JSONException
{
String id = json.getString("id");
JSONObject data = (JSONObject) json.get("data");
Long habitId = data.getLong("habit");
Long timestamp = data.getLong("timestamp");
Habit habit = habitList.getById(habitId);
if (habit == null) throw new HabitNotFoundException();
return new ToggleRepetitionCommand(id, habit, timestamp);
}
@Override
public void execute()
{
habit.getRepetitions().toggleTimestamp(timestamp);
}
@NonNull
public Habit getHabit()
{
return habit;
@ -78,21 +54,9 @@ public class ToggleRepetitionCommand extends Command
@Override
@NonNull
public JSONObject toJSON()
public Record toRecord()
{
try
{
JSONObject root = super.toJSON();
JSONObject data = root.getJSONObject("data");
root.put("event", "ToggleRepetition");
data.put("habit", habit.getId());
data.put("timestamp", timestamp);
return root;
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
}
return new Record(this);
}
@Override
@ -100,4 +64,38 @@ public class ToggleRepetitionCommand extends Command
{
execute();
}
public static class Record
{
@NonNull
public String id;
@NonNull
public String event = "Toggle";
public long habitId;
public long timestamp;
public Record(@NonNull ToggleRepetitionCommand command)
{
id = command.getId();
Long habitId = command.habit.getId();
if(habitId == null) throw new RuntimeException("Habit not saved");
this.timestamp = command.timestamp;
this.habitId = habitId;
}
public ToggleRepetitionCommand toCommand(@NonNull HabitList habitList)
{
Habit h = habitList.getById(habitId);
if(h == null) throw new HabitNotFoundException();
ToggleRepetitionCommand command;
command = new ToggleRepetitionCommand(h, timestamp);
command.setId(id);
return command;
}
}
}

@ -23,56 +23,32 @@ import android.support.annotation.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.models.*;
import org.json.*;
import java.util.*;
import static org.isoron.uhabits.commands.CommandParser.*;
/**
* Command to unarchive a list of habits.
*/
public class UnarchiveHabitsCommand extends Command
{
HabitList habitList;
@NonNull
final HabitList habitList;
private List<Habit> habits;
@NonNull
final List<Habit> selected;
public UnarchiveHabitsCommand(@NonNull HabitList habitList,
@NonNull List<Habit> selected)
{
super();
this.habits = selected;
this.habitList = habitList;
}
public UnarchiveHabitsCommand(@NonNull String id,
@NonNull HabitList habitList,
@NonNull List<Habit> selected)
{
super(id);
this.habits = selected;
this.selected = new LinkedList<>(selected);
this.habitList = habitList;
}
@NonNull
public static Command fromJSON(@NonNull JSONObject json,
@NonNull HabitList habitList)
throws JSONException
{
String id = json.getString("id");
JSONObject data = (JSONObject) json.get("data");
JSONArray habitIds = data.getJSONArray("ids");
LinkedList<Habit> selected = habitListFromJSON(habitList, habitIds);
return new UnarchiveHabitsCommand(id, habitList, selected);
}
@Override
public void execute()
{
for (Habit h : habits) h.setArchived(false);
habitList.update(habits);
for (Habit h : selected) h.setArchived(false);
habitList.update(selected);
}
@Override
@ -89,27 +65,50 @@ public class UnarchiveHabitsCommand extends Command
@Override
@NonNull
public JSONObject toJSON()
public Record toRecord()
{
try
{
JSONObject root = super.toJSON();
JSONObject data = root.getJSONObject("data");
root.put("event", "UnarchiveHabits");
data.put("ids", habitListToJSON(habits));
return root;
}
catch (JSONException e)
{
throw new RuntimeException(e.getMessage());
}
return new Record(this);
}
@Override
public void undo()
{
for (Habit h : habits) h.setArchived(true);
habitList.update(habits);
for (Habit h : selected) h.setArchived(true);
habitList.update(selected);
}
public static class Record
{
@NonNull
public final String id;
@NonNull
public final String event = "Unarchive";
@NonNull
public final List<Long> habits;
public Record(@NonNull UnarchiveHabitsCommand command)
{
id = command.getId();
habits = new LinkedList<>();
for (Habit h : command.selected)
{
if (!h.hasId()) throw new RuntimeException("Habit not saved");
habits.add(h.getId());
}
}
@NonNull
public UnarchiveHabitsCommand toCommand(@NonNull HabitList habitList)
{
List<Habit> selected = new LinkedList<>();
for (Long id : this.habits) selected.add(habitList.getById(id));
UnarchiveHabitsCommand command;
command = new UnarchiveHabitsCommand(habitList, selected);
command.setId(id);
return command;
}
}
}

@ -23,12 +23,12 @@ import android.net.*;
import android.support.annotation.*;
import org.apache.commons.lang3.builder.*;
import org.json.*;
import java.util.*;
import javax.inject.*;
import static android.R.attr.*;
import static org.isoron.uhabits.models.Checkmark.*;
/**
@ -48,20 +48,10 @@ public class Habit
public static final int YES_NO_HABIT = 0;
@Nullable
private Long id;
public Long id;
@NonNull
private String name;
@NonNull
private String description;
@NonNull
private Frequency frequency;
private int color;
private boolean archived;
private HabitData data;
@NonNull
private StreakList streaks;
@ -69,28 +59,16 @@ public class Habit
@NonNull
private ScoreList scores;
private int targetType;
private double targetValue;
private int type;
@NonNull
private RepetitionList repetitions;
@NonNull
private CheckmarkList checkmarks;
@NonNull
private String unit;
@Nullable
private Reminder reminder;
private ModelObservable observable = new ModelObservable();
/**
* Constructs a habit with default attributes.
* Constructs a habit with default data.
* <p>
* The habit is not archived, not highlighted, has no reminders and is
* placed in the last position of the list of habits.
@ -98,16 +76,16 @@ public class Habit
@Inject
Habit(@NonNull ModelFactory factory)
{
this.color = 5;
this.archived = false;
this.frequency = new Frequency(3, 7);
this.type = YES_NO_HABIT;
this.name = "";
this.description = "";
this.targetType = AT_LEAST;
this.targetValue = 100;
this.unit = "";
this.data = new HabitData();
checkmarks = factory.buildCheckmarkList(this);
streaks = factory.buildStreakList(this);
scores = factory.buildScoreList(this);
repetitions = factory.buildRepetitionList(this);
}
Habit(@NonNull ModelFactory factory, @NonNull HabitData data)
{
this.data = new HabitData(data);
checkmarks = factory.buildCheckmarkList(this);
streaks = factory.buildStreakList(this);
scores = factory.buildScoreList(this);
@ -119,7 +97,7 @@ public class Habit
*/
public void clearReminder()
{
reminder = null;
data.reminder = null;
observable.notifyListeners();
}
@ -130,16 +108,7 @@ public class Habit
*/
public void copyFrom(@NonNull Habit model)
{
this.name = model.getName();
this.description = model.getDescription();
this.color = model.getColor();
this.archived = model.isArchived();
this.frequency = model.frequency;
this.reminder = model.reminder;
this.type = model.type;
this.targetValue = model.targetValue;
this.targetType = model.targetType;
this.unit = model.unit;
this.data = new HabitData(model.data);
observable.notifyListeners();
}
@ -163,41 +132,34 @@ public class Habit
@NonNull
public Integer getColor()
{
return color;
}
public boolean isCompletedToday()
{
int todayCheckmark = getCheckmarks().getTodayValue();
if (isNumerical()) return todayCheckmark >= targetValue;
else return (todayCheckmark != UNCHECKED);
return data.color;
}
public void setColor(@NonNull Integer color)
{
this.color = color;
data.color = color;
}
@NonNull
public String getDescription()
{
return description;
return data.description;
}
public void setDescription(@NonNull String description)
{
this.description = description;
data.description = description;
}
@NonNull
public Frequency getFrequency()
{
return frequency;
return data.frequency;
}
public void setFrequency(@NonNull Frequency frequency)
{
this.frequency = frequency;
data.frequency = frequency;
}
@Nullable
@ -214,12 +176,12 @@ public class Habit
@NonNull
public String getName()
{
return name;
return data.name;
}
public void setName(@NonNull String name)
{
this.name = name;
data.name = name;
}
public ModelObservable getObservable()
@ -240,13 +202,13 @@ public class Habit
@NonNull
public Reminder getReminder()
{
if (reminder == null) throw new IllegalStateException();
return reminder;
if (data.reminder == null) throw new IllegalStateException();
return data.reminder;
}
public void setReminder(@Nullable Reminder reminder)
{
this.reminder = reminder;
data.reminder = reminder;
}
@NonNull
@ -269,30 +231,30 @@ public class Habit
public int getTargetType()
{
return targetType;
return data.targetType;
}
public void setTargetType(int targetType)
{
if (targetType != AT_LEAST && targetType != AT_MOST)
throw new IllegalArgumentException();
this.targetType = targetType;
data.targetType = targetType;
}
public double getTargetValue()
{
return targetValue;
return data.targetValue;
}
public void setTargetValue(double targetValue)
{
if(targetValue < 0) throw new IllegalArgumentException();
this.targetValue = targetValue;
if (targetValue < 0) throw new IllegalArgumentException();
data.targetValue = targetValue;
}
public int getType()
{
return type;
return data.type;
}
public void setType(int type)
@ -300,18 +262,18 @@ public class Habit
if (type != YES_NO_HABIT && type != NUMBER_HABIT)
throw new IllegalArgumentException();
this.type = type;
data.type = type;
}
@NonNull
public String getUnit()
{
return unit;
return data.unit;
}
public void setUnit(@NonNull String unit)
{
this.unit = unit;
data.unit = unit;
}
/**
@ -325,6 +287,11 @@ public class Habit
return Uri.parse(s);
}
public boolean hasId()
{
return getId() != null;
}
/**
* Returns whether the habit has a reminder.
*
@ -332,7 +299,7 @@ public class Habit
*/
public boolean hasReminder()
{
return reminder != null;
return data.reminder != null;
}
public void invalidateNewerThan(long timestamp)
@ -344,12 +311,19 @@ public class Habit
public boolean isArchived()
{
return archived;
return data.archived;
}
public void setArchived(boolean archived)
{
this.archived = archived;
data.archived = archived;
}
public boolean isCompletedToday()
{
int todayCheckmark = getCheckmarks().getTodayValue();
if (isNumerical()) return todayCheckmark >= data.targetValue;
else return (todayCheckmark != UNCHECKED);
}
public boolean isNumerical()
@ -357,79 +331,120 @@ public class Habit
return type == NUMBER_HABIT;
}
@Override
public String toString()
public HabitData getData()
{
return new ToStringBuilder(this)
.append("id", id)
.append("name", name)
.append("description", description)
.append("color", color)
.append("archived", archived)
.append("type", type)
.append("targetType", targetType)
.append("targetValue", targetValue)
.append("unit", unit)
.toString();
return new HabitData(data);
}
@NonNull
public JSONObject toJSON()
public static class HabitData
{
try
@NonNull
public String name;
@NonNull
public String description;
@NonNull
public Frequency frequency;
public int color;
public boolean archived;
public int targetType;
public double targetValue;
public int type;
@NonNull
public String unit;
@Nullable
public Reminder reminder;
public HabitData()
{
JSONObject json = new JSONObject();
json.put("name", name);
json.put("description", description);
json.put("freqNum", frequency.getNumerator());
json.put("freqDen", frequency.getDenominator());
json.put("color", color);
json.put("type", type);
json.put("targetType", targetType);
json.put("targetValue", targetValue);
json.put("unit", unit);
json.put("archived", archived);
if(reminder != null)
{
json.put("reminderHour", reminder.getHour());
json.put("reminderMin", reminder.getMinute());
json.put("reminderDays", reminder.getDays().toInteger());
}
return json;
this.color = 5;
this.archived = false;
this.frequency = new Frequency(3, 7);
this.type = YES_NO_HABIT;
this.name = "";
this.description = "";
this.targetType = AT_LEAST;
this.targetValue = 100;
this.unit = "";
}
catch(JSONException e)
public HabitData(@NonNull HabitData model)
{
throw new RuntimeException(e.getMessage());
this.name = model.name;
this.description = model.description;
this.frequency = model.frequency;
this.color = model.color;
this.archived = model.archived;
this.targetType = model.targetType;
this.targetValue = model.targetValue;
this.type = model.type;
this.unit = model.unit;
this.reminder = model.reminder;
}
}
@NonNull
public static Habit fromJSON(@NonNull JSONObject json,
@NonNull ModelFactory modelFactory)
throws JSONException
{
Habit habit = modelFactory.buildHabit();
habit.name = json.getString("name");
habit.description = json.getString("description");
int freqNum = json.getInt("freqNum");
int freqDen = json.getInt("freqDen");
habit.frequency = new Frequency(freqNum, freqDen);
habit.color = json.getInt("color");
habit.archived = json.getBoolean("archived");
habit.targetValue = json.getInt("targetValue");
habit.targetType = json.getInt("targetType");
habit.unit = json.getString("unit");
habit.type = json.getInt("type");
if(json.has("reminderHour"))
@Override
public String toString()
{
return new ToStringBuilder(this)
.append("name", name)
.append("description", description)
.append("frequency", frequency)
.append("color", color)
.append("archived", archived)
.append("targetType", targetType)
.append("targetValue", targetValue)
.append("type", type)
.append("unit", unit)
.append("reminder", reminder)
.toString();
}
@Override
public boolean equals(Object o)
{
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
HabitData habitData = (HabitData) o;
return new EqualsBuilder()
.append(color, habitData.color)
.append(archived, habitData.archived)
.append(targetType, habitData.targetType)
.append(targetValue, habitData.targetValue)
.append(type, habitData.type)
.append(name, habitData.name)
.append(description, habitData.description)
.append(frequency, habitData.frequency)
.append(unit, habitData.unit)
.append(reminder, habitData.reminder)
.isEquals();
}
@Override
public int hashCode()
{
int hour = json.getInt("reminderHour");
int min = json.getInt("reminderMin");
int days = json.getInt("reminderDays");
habit.reminder = new Reminder(hour, min, new WeekdayList(days));
return new HashCodeBuilder(17, 37)
.append(name)
.append(description)
.append(frequency)
.append(color)
.append(archived)
.append(targetType)
.append(targetValue)
.append(type)
.append(unit)
.append(reminder)
.toHashCode();
}
return habit;
}
}

@ -32,6 +32,11 @@ public interface ModelFactory
return new Habit(this);
}
default Habit buildHabit(Habit.HabitData data)
{
return new Habit(this, data);
}
HabitList buildHabitList();
RepetitionList buildRepetitionList(Habit habit);

@ -102,7 +102,7 @@ public class NotificationTray
if (command instanceof DeleteHabitsCommand)
{
DeleteHabitsCommand deleteCommand = (DeleteHabitsCommand) command;
List<Habit> deleted = deleteCommand.getHabits();
List<Habit> deleted = deleteCommand.getSelected();
for (Habit habit : deleted)
cancel(habit);
}

@ -141,9 +141,7 @@ public class SyncManager
public void postCommand(Command command)
{
JSONObject msg = command.toJSON();
if (msg == null) return;
JSONObject msg = command.toJson();
Long now = new Date().getTime();
Event e = new Event(command.getId(), now, msg.toString());
e.save();
@ -293,7 +291,7 @@ public class SyncManager
private void executeCommand(JSONObject root) throws JSONException
{
Command received = commandParser.fromJSON(root);
Command received = commandParser.parse(root);
for (Event e : pendingConfirmation)
{
if (e.serverId.equals(received.getId()))

@ -26,11 +26,13 @@ import org.junit.*;
import java.util.*;
import static junit.framework.Assert.*;
import static org.hamcrest.MatcherAssert.*;
import static org.hamcrest.Matchers.*;
public class ArchiveHabitsCommandTest extends BaseUnitTest
{
private ArchiveHabitsCommand command;
private Habit habit;
@Override
@ -40,8 +42,10 @@ public class ArchiveHabitsCommandTest extends BaseUnitTest
super.setUp();
habit = fixtures.createShortHabit();
command = new ArchiveHabitsCommand(habitList, Collections
.singletonList(habit));
habitList.add(habit);
command = new ArchiveHabitsCommand(habitList,
Collections.singletonList(habit));
}
@Test
@ -58,4 +62,13 @@ public class ArchiveHabitsCommandTest extends BaseUnitTest
command.execute();
assertTrue(habit.isArchived());
}
@Test
public void testRecord()
{
ArchiveHabitsCommand.Record rec = command.toRecord();
ArchiveHabitsCommand other = rec.toCommand(habitList);
assertThat(other.selected, equalTo(command.selected));
assertThat(other.getId(), equalTo(command.getId()));
}
}

@ -32,7 +32,7 @@ public class ChangeHabitColorCommandTest extends BaseUnitTest
{
private ChangeHabitColorCommand command;
private LinkedList<Habit> habits;
private LinkedList<Habit> selected;
@Override
@Before
@ -40,16 +40,17 @@ public class ChangeHabitColorCommandTest extends BaseUnitTest
{
super.setUp();
habits = new LinkedList<>();
selected = new LinkedList<>();
for (int i = 0; i < 3; i++)
{
Habit habit = fixtures.createShortHabit();
habit.setColor(i + 1);
habits.add(habit);
selected.add(habit);
habitList.add(habit);
}
command = new ChangeHabitColorCommand(habitList, habits, 0);
command = new ChangeHabitColorCommand(habitList, selected, 0);
}
@Test
@ -67,16 +68,26 @@ public class ChangeHabitColorCommandTest extends BaseUnitTest
checkNewColors();
}
@Test
public void testRecord()
{
ChangeHabitColorCommand.Record rec = command.toRecord();
ChangeHabitColorCommand other = rec.toCommand(habitList);
assertThat(other.getId(), equalTo(command.getId()));
assertThat(other.newColor, equalTo(command.newColor));
assertThat(other.selected, equalTo(command.selected));
}
private void checkNewColors()
{
for (Habit h : habits)
for (Habit h : selected)
assertThat(h.getColor(), equalTo(0));
}
private void checkOriginalColors()
{
int k = 0;
for (Habit h : habits)
for (Habit h : selected)
assertThat(h.getColor(), equalTo(++k));
}
}

@ -0,0 +1,159 @@
/*
* Copyright (C) 2016 Álinson Santos Xavier <isoron@gmail.com>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.commands;
import android.support.annotation.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.models.*;
import org.json.*;
import org.junit.*;
import java.util.*;
import static org.hamcrest.MatcherAssert.*;
import static org.hamcrest.Matchers.*;
public class CommandParserTest extends BaseUnitTest
{
@NonNull
private CommandParser parser;
private Habit habit;
private List<Habit> selected;
@Override
@Before
public void setUp()
{
super.setUp();
parser = new CommandParser(habitList, modelFactory);
habit = fixtures.createShortHabit();
selected = Collections.singletonList(habit);
habitList.add(habit);
}
@Test
public void testDecodeArchiveCommand() throws JSONException
{
ArchiveHabitsCommand original, decoded;
original = new ArchiveHabitsCommand(habitList, selected);
decoded = (ArchiveHabitsCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.selected, equalTo(original.selected));
}
@Test
public void testDecodeChangeColorCommand() throws JSONException
{
ChangeHabitColorCommand original, decoded;
original = new ChangeHabitColorCommand(habitList, selected, 20);
decoded = (ChangeHabitColorCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.newColor, equalTo(original.newColor));
assertThat(decoded.selected, equalTo(original.selected));
}
@Test
public void testDecodeCreateHabitCommand() throws JSONException
{
Habit model = modelFactory.buildHabit();
model.setName("JSON");
CreateHabitCommand original, decoded;
original = new CreateHabitCommand(modelFactory, habitList, model);
original.execute();
decoded = (CreateHabitCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.savedId, equalTo(original.savedId));
assertThat(decoded.model.getData(), equalTo(model.getData()));
}
@Test
public void testDecodeCreateRepCommand() throws JSONException
{
CreateRepetitionCommand original, decoded;
original = new CreateRepetitionCommand(habit, 1000, 5);
decoded = (CreateRepetitionCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.timestamp, equalTo(original.timestamp));
assertThat(decoded.value, equalTo(original.value));
assertThat(decoded.habit, equalTo(original.habit));
}
@Test
public void testDecodeDeleteCommand() throws JSONException
{
DeleteHabitsCommand original, decoded;
original = new DeleteHabitsCommand(habitList, selected);
decoded = (DeleteHabitsCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.selected, equalTo(original.selected));
}
@Test
public void testDecodeEditHabitCommand() throws JSONException
{
Habit modified = modelFactory.buildHabit();
modified.setName("Edited JSON");
modified.setColor(2);
EditHabitCommand original, decoded;
original = new EditHabitCommand(modelFactory, habitList, habit, modified);
original.execute();
decoded = (EditHabitCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.savedId, equalTo(original.savedId));
assertThat(decoded.modified.getData(), equalTo(modified.getData()));
}
@Test
public void testDecodeToggleCommand() throws JSONException
{
ToggleRepetitionCommand original, decoded;
original = new ToggleRepetitionCommand(habit, 1000);
decoded = (ToggleRepetitionCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.timestamp, equalTo(original.timestamp));
assertThat(decoded.habit, equalTo(original.habit));
}
@Test
public void testDecodeUnarchiveCommand() throws JSONException
{
UnarchiveHabitsCommand original, decoded;
original = new UnarchiveHabitsCommand(habitList, selected);
decoded = (UnarchiveHabitsCommand) parser.parse(original.toJson());
assertThat(decoded.getId(), equalTo(original.getId()));
assertThat(decoded.selected, equalTo(original.selected));
}
}

@ -41,6 +41,7 @@ public class CreateHabitCommandTest extends BaseUnitTest
model = fixtures.createEmptyHabit();
model.setName("New habit");
model.setReminder(new Reminder(8, 30, WeekdayList.EVERY_DAY));
command = new CreateHabitCommand(modelFactory, habitList, model);
}
@ -70,5 +71,16 @@ public class CreateHabitCommandTest extends BaseUnitTest
assertThat(habit.getName(), equalTo(model.getName()));
}
@Test
public void testRecord()
{
command.execute();
CreateHabitCommand.Record rec = command.toRecord();
CreateHabitCommand other = rec.toCommand(modelFactory, habitList);
assertThat(other.getId(), equalTo(command.getId()));
assertThat(other.savedId, equalTo(command.savedId));
assertThat(other.model.getData(), equalTo(command.model.getData()));
}
}

@ -25,11 +25,12 @@ import org.isoron.uhabits.utils.*;
import org.junit.*;
import static junit.framework.Assert.*;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.equalTo;
import static org.isoron.uhabits.models.Checkmark.CHECKED_EXPLICITLY;
public class CreateRepetitionCommandTest extends BaseUnitTest
{
private CreateRepetitionCommand command;
private Habit habit;
@ -43,6 +44,7 @@ public class CreateRepetitionCommandTest extends BaseUnitTest
super.setUp();
habit = fixtures.createShortHabit();
habitList.add(habit);
today = DateUtils.getStartOfToday();
command = new CreateRepetitionCommand(habit, today, 100);
@ -67,4 +69,16 @@ public class CreateRepetitionCommandTest extends BaseUnitTest
assertNotNull(rep);
assertEquals(CHECKED_EXPLICITLY, rep.getValue());
}
@Test
public void testRecord()
{
CreateRepetitionCommand.Record rec = command.toRecord();
CreateRepetitionCommand other = rec.toCommand(habitList);
assertThat(command.getId(), equalTo(other.getId()));
assertThat(command.timestamp, equalTo(other.timestamp));
assertThat(command.value, equalTo(other.value));
assertThat(command.habit, equalTo(other.habit));
}
}

@ -73,4 +73,13 @@ public class DeleteHabitsCommandTest extends BaseUnitTest
thrown.expect(UnsupportedOperationException.class);
command.undo();
}
@Test
public void testRecord()
{
DeleteHabitsCommand.Record rec = command.toRecord();
DeleteHabitsCommand other = rec.toCommand(habitList);
assertThat(other.getId(), equalTo(command.getId()));
assertThat(other.selected, equalTo(command.selected));
}
}

@ -28,7 +28,6 @@ import static org.hamcrest.Matchers.*;
public class EditHabitCommandTest extends BaseUnitTest
{
private EditHabitCommand command;
private Habit habit;
@ -98,4 +97,19 @@ public class EditHabitCommandTest extends BaseUnitTest
assertThat(habit.getScores().getTodayValue(),
lessThan(originalScore));
}
@Test
public void testRecord()
{
command =
new EditHabitCommand(modelFactory, habitList, habit, modified);
EditHabitCommand.Record rec = command.toRecord();
EditHabitCommand other = rec.toCommand(modelFactory, habitList);
assertThat(other.getId(), equalTo(command.getId()));
assertThat(other.savedId, equalTo(command.savedId));
assertThat(other.original.getData(), equalTo(command.original.getData()));
assertThat(other.modified.getData(), equalTo(command.modified.getData()));
}
}

@ -25,6 +25,8 @@ import org.isoron.uhabits.utils.*;
import org.junit.*;
import static junit.framework.Assert.*;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.equalTo;
public class ToggleRepetitionCommandTest extends BaseUnitTest
{
@ -40,6 +42,7 @@ public class ToggleRepetitionCommandTest extends BaseUnitTest
super.setUp();
habit = fixtures.createShortHabit();
habitList.add(habit);
today = DateUtils.getStartOfToday();
command = new ToggleRepetitionCommand(habit, today);
@ -59,4 +62,15 @@ public class ToggleRepetitionCommandTest extends BaseUnitTest
command.execute();
assertFalse(habit.getRepetitions().containsTimestamp(today));
}
@Test
public void testRecord()
{
ToggleRepetitionCommand.Record rec = command.toRecord();
ToggleRepetitionCommand other = rec.toCommand(habitList);
assertThat(command.getId(), equalTo(other.getId()));
assertThat(command.timestamp, equalTo(other.timestamp));
assertThat(command.habit, equalTo(other.habit));
}
}

@ -26,6 +26,8 @@ import org.junit.*;
import java.util.*;
import static junit.framework.Assert.*;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.equalTo;
public class UnarchiveHabitsCommandTest extends BaseUnitTest
{
@ -61,4 +63,13 @@ public class UnarchiveHabitsCommandTest extends BaseUnitTest
command.execute();
assertFalse(habit.isArchived());
}
@Test
public void testRecord()
{
UnarchiveHabitsCommand.Record rec = command.toRecord();
UnarchiveHabitsCommand other = rec.toCommand(habitList);
assertThat(other.selected, equalTo(command.selected));
assertThat(other.getId(), equalTo(command.getId()));
}
}

Loading…
Cancel
Save