Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix crash for non-String entity labels #770

Merged
merged 3 commits into from
Jun 17, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 15 additions & 0 deletions src/main/java/org/javarosa/entities/internal/EntityConstants.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package org.javarosa.entities.internal;

public class EntityConstants {

private EntityConstants() {}

public static final String ELEMENT_ENTITY = "entity";
public static final String ELEMENT_LABEL = "label";

public static final String ATTRIBUTE_DATASET = "dataset";
public static final String ATTRIBUTE_ID = "id";
public static final String ATTRIBUTE_BASE_VERSION = "baseVersion";
public static final String ATTRIBUTE_CREATE = "create";
public static final String ATTRIBUTE_UPDATE = "update";
}
24 changes: 16 additions & 8 deletions src/main/java/org/javarosa/entities/internal/EntityFormParser.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,25 +8,33 @@
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import static org.javarosa.entities.internal.EntityConstants.ATTRIBUTE_BASE_VERSION;
import static org.javarosa.entities.internal.EntityConstants.ATTRIBUTE_CREATE;
import static org.javarosa.entities.internal.EntityConstants.ATTRIBUTE_DATASET;
import static org.javarosa.entities.internal.EntityConstants.ATTRIBUTE_ID;
import static org.javarosa.entities.internal.EntityConstants.ATTRIBUTE_UPDATE;
import static org.javarosa.entities.internal.EntityConstants.ELEMENT_ENTITY;
import static org.javarosa.entities.internal.EntityConstants.ELEMENT_LABEL;

public class EntityFormParser {

private EntityFormParser() {

}

public static String parseDataset(TreeElement entity) {
return entity.getAttributeValue(null, "dataset");
return entity.getAttributeValue(null, ATTRIBUTE_DATASET);
}

@Nullable
public static String parseLabel(TreeElement entity) {
TreeElement labelElement = entity.getFirstChild("label");
TreeElement labelElement = entity.getFirstChild(ELEMENT_LABEL);

if (labelElement != null) {
IAnswerData labelValue = labelElement.getValue();

if (labelValue != null) {
return (String) labelValue.getValue();
return String.valueOf(labelValue.getValue());
} else {
return null;
}
Expand All @@ -37,12 +45,12 @@ public static String parseLabel(TreeElement entity) {

@Nullable
public static String parseId(TreeElement entity) {
return entity.getAttributeValue("", "id");
return entity.getAttributeValue("", ATTRIBUTE_ID);
}

public static Integer parseBaseVersion(TreeElement entity) {
try {
return Integer.valueOf(entity.getAttributeValue("", "baseVersion"));
return Integer.valueOf(entity.getAttributeValue("", ATTRIBUTE_BASE_VERSION));
} catch (NumberFormatException e) {
return 0;
}
Expand All @@ -54,16 +62,16 @@ public static TreeElement getEntityElement(FormInstance mainInstance) {
TreeElement meta = root.getFirstChild("meta");

if (meta != null) {
return meta.getFirstChild("entity");
return meta.getFirstChild(ELEMENT_ENTITY);
} else {
return null;
}
}

@Nullable
public static EntityAction parseAction(@NotNull TreeElement entity) {
String create = entity.getAttributeValue(null, "create");
String update = entity.getAttributeValue(null, "update");
String create = entity.getAttributeValue(null, ATTRIBUTE_CREATE);
String update = entity.getAttributeValue(null, ATTRIBUTE_UPDATE);

if (update != null) {
if (XPathFuncExpr.boolStr(update)) {
Expand Down
95 changes: 25 additions & 70 deletions src/test/java/org/javarosa/entities/EntityFormParserTest.java
Original file line number Diff line number Diff line change
@@ -1,90 +1,45 @@
package org.javarosa.entities;

import kotlin.Pair;
import org.javarosa.core.model.FormDef;
import org.javarosa.core.util.XFormsElement;
import org.javarosa.core.model.data.IntegerData;
import org.javarosa.core.model.instance.TreeElement;
import org.javarosa.entities.internal.EntityFormParser;
import org.javarosa.xform.parse.XFormParser;
import org.junit.Test;

import java.io.ByteArrayInputStream;
import java.io.InputStreamReader;

import static java.util.Arrays.asList;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.equalTo;
import static org.javarosa.core.util.BindBuilderXFormsElement.bind;
import static org.javarosa.core.util.XFormsElement.body;
import static org.javarosa.core.util.XFormsElement.head;
import static org.javarosa.core.util.XFormsElement.input;
import static org.javarosa.core.util.XFormsElement.mainInstance;
import static org.javarosa.core.util.XFormsElement.model;
import static org.javarosa.core.util.XFormsElement.t;
import static org.javarosa.core.util.XFormsElement.title;
import static org.javarosa.entities.internal.EntityConstants.ATTRIBUTE_CREATE;
import static org.javarosa.entities.internal.EntityConstants.ATTRIBUTE_UPDATE;
import static org.javarosa.entities.internal.EntityConstants.ELEMENT_ENTITY;
import static org.javarosa.entities.internal.EntityConstants.ELEMENT_LABEL;

public class EntityFormParserTest {

@Test
public void parseAction_findsCreateWithTrueString() throws XFormParser.ParseException {
XFormsElement form = XFormsElement.html(
asList(
new Pair<>("entities", "http://www.opendatakit.org/xforms/entities")
),
head(
title("Create entity form"),
model(
mainInstance(
t("data id=\"create-entity-form\"",
t("name"),
t("meta",
t("entity dataset=\"people\" create=\"true\"")
)
)
),
bind("/data/name").type("string").withAttribute("entities", "saveto", "name")
)
),
body(
input("/data/name")
)
);

XFormParser parser = new XFormParser(new InputStreamReader(new ByteArrayInputStream(form.asXml().getBytes())));
FormDef formDef = parser.parse(null);
public void parseAction_findsCreateWithTrueString() {
TreeElement entityElement = new TreeElement(ELEMENT_ENTITY);
entityElement.setAttribute(null, ATTRIBUTE_CREATE, "true");

EntityAction action = EntityFormParser.parseAction(EntityFormParser.getEntityElement(formDef.getMainInstance()));
EntityAction action = EntityFormParser.parseAction(entityElement);
assertThat(action, equalTo(EntityAction.CREATE));
}

@Test
public void parseAction_findsUpdateWithTrueString() throws XFormParser.ParseException {
XFormsElement form = XFormsElement.html(
asList(
new Pair<>("entities", "http://www.opendatakit.org/xforms/entities")
),
head(
title("Create entity form"),
model(
mainInstance(
t("data id=\"create-entity-form\"",
t("name"),
t("meta",
t("entity dataset=\"people\" update=\"true\"")
)
)
),
bind("/data/name").type("string").withAttribute("entities", "saveto", "name")
)
),
body(
input("/data/name")
)
);

XFormParser parser = new XFormParser(new InputStreamReader(new ByteArrayInputStream(form.asXml().getBytes())));
FormDef formDef = parser.parse(null);
public void parseAction_findsUpdateWithTrueString() {
TreeElement entityElement = new TreeElement(ELEMENT_ENTITY);
entityElement.setAttribute(null, ATTRIBUTE_UPDATE, "true");

EntityAction dataset = EntityFormParser.parseAction(EntityFormParser.getEntityElement(formDef.getMainInstance()));
EntityAction dataset = EntityFormParser.parseAction(entityElement);
assertThat(dataset, equalTo(EntityAction.UPDATE));
}

@Test
public void parseLabel_whenLabelIsAnInt_convertsToString() {
TreeElement labelElement = new TreeElement(ELEMENT_LABEL);
labelElement.setAnswer(new IntegerData(0));
TreeElement entityElement = new TreeElement(ELEMENT_ENTITY);
entityElement.addChild(labelElement);

String label = EntityFormParser.parseLabel(entityElement);
assertThat(label, equalTo("0"));
}
}