import eu.etaxonomy.cdm.io.common.ICdmIO;\r
import eu.etaxonomy.cdm.io.common.mapping.UndefinedTransformerMethodException;\r
import eu.etaxonomy.cdm.io.eflora.UnmatchedLeads.UnmatchedLeadsKey;\r
+import eu.etaxonomy.cdm.model.agent.Person;\r
import eu.etaxonomy.cdm.model.agent.Team;\r
import eu.etaxonomy.cdm.model.agent.TeamOrPersonBase;\r
import eu.etaxonomy.cdm.model.common.AnnotatableEntity;\r
import eu.etaxonomy.cdm.model.common.MarkerType;\r
import eu.etaxonomy.cdm.model.common.Representation;\r
import eu.etaxonomy.cdm.model.common.TimePeriod;\r
+import eu.etaxonomy.cdm.model.description.CommonTaxonName;\r
import eu.etaxonomy.cdm.model.description.DescriptionElementBase;\r
import eu.etaxonomy.cdm.model.description.Feature;\r
import eu.etaxonomy.cdm.model.description.FeatureNode;\r
lastEntity = handleTaxonNotes(state, element, taxon);\r
}else if(elName.equalsIgnoreCase("chromosomes")){\r
lastEntity = handleChromosomes(state, element, taxon);\r
+ }else if(elName.equalsIgnoreCase("vernacularnames")){\r
+ handleVernaculars(state, element, taxon);\r
}else if(elName.equalsIgnoreCase("key")){\r
lastEntity = handleKeys(state, element, taxon);\r
}else if(elName.equalsIgnoreCase("references")){\r
}\r
\r
\r
+ private void handleVernaculars(EfloraImportState state, Element elVernacular, Taxon taxon) {\r
+ verifyNoAttribute(elVernacular);\r
+ verifyNoChildren(elVernacular, false);\r
+ String value = elVernacular.getTextNormalize();\r
+ Feature feature = Feature.COMMON_NAME();\r
+ value = replaceStart(value, "Noms vernaculaires");\r
+ String[] dialects = value.split(";");\r
+ for (String singleDialect : dialects){\r
+ handleSingleDialect(taxon, singleDialect, feature, state);\r
+ }\r
+ return;\r
+ }\r
+\r
+\r
+ private void handleSingleDialect(Taxon taxon, String singleDialect, Feature feature, EfloraImportState state) {\r
+ singleDialect = singleDialect.trim();\r
+ TaxonDescription description = getDescription(taxon);\r
+ String reDialect = "\\(dial\\.\\s.*\\)";\r
+// String reDialect = "\\(.*\\)";\r
+ Pattern patDialect = Pattern.compile(reDialect);\r
+ Matcher matcher = patDialect.matcher(singleDialect);\r
+ if (matcher.find()){\r
+ String dialect = singleDialect.substring(matcher.start(), matcher.end());\r
+ dialect = dialect.replace("(dial. ", "").replace(")", "");\r
+ \r
+ Language language = null;\r
+ try {\r
+ language = this.getLanguage(state, state.getTransformer().getLanguageUuid(dialect), dialect, dialect, dialect);\r
+ } catch (UndefinedTransformerMethodException e) {\r
+ logger.error(e.getMessage());\r
+ }\r
+ \r
+ String commonNames = singleDialect.substring(0, matcher.start());\r
+ String[] splitNames = commonNames.split(",");\r
+ for (String commonNameString : splitNames){\r
+ commonNameString = commonNameString.trim();\r
+ CommonTaxonName commonName = CommonTaxonName.NewInstance(commonNameString, language);\r
+ description.addElement(commonName);\r
+ }\r
+ }else{\r
+ logger.warn("No dialect match: " + singleDialect);\r
+ }\r
+ }\r
+\r
+\r
private void handleReferences(EfloraImportState state, Element elReferences, Taxon taxon, AnnotatableEntity lastEntity) {\r
verifyNoAttribute(elReferences);\r
verifyNoChildren(elReferences, true);\r
String refString = elReferences.getTextNormalize(); \r
-// refString = replaceStart(replaceStart(refString, "References:"), "Sources:");\r
if (lastEntity == null){\r
logger.warn("No last entity defined: " + refString);\r
return;\r
\r
Annotation annotation = Annotation.NewInstance(refString, AnnotationType.EDITORIAL(), Language.DEFAULT());\r
lastEntity.addAnnotation(annotation);\r
-\r
-// ReferenceBase ref = ReferenceFactory.newGeneric();\r
-// ref.setTitleCache(refString, true);\r
-// if (lastEntity instanceof DescriptionElementBase){\r
-// DescriptionElementSource source = DescriptionElementSource.NewInstance(ref, null);\r
-// CdmBase.deproxy(lastEntity, DescriptionElementBase.class).addSource(source);\r
-// }else if (lastEntity instanceof IdentifiableEntity){\r
-// IdentifiableSource source = IdentifiableSource.NewInstance(ref, null);\r
-// CdmBase.deproxy(lastEntity, IdentifiableEntity.class).addSource(source);\r
-// }\r
-// else{\r
-// logger.warn("lastEntity type not supported: " + lastEntity.getClass().getName());\r
-// }\r
- \r
- logger.info("References need to be moved to their parent");\r
-\r
}\r
\r
\r
String chromosomesPart = getChromosomesPart(value);\r
String references = value.replace(chromosomesPart, "").trim();\r
chromosomesPart = chromosomesPart.replace(":", "").trim();\r
- return addDescriptionElement(taxon, chromosomesPart, chromosomeFeature, references); \r
+ return addDescriptionElement(state, taxon, chromosomesPart, chromosomeFeature, references); \r
}\r
\r
\r
* @param attribute\r
* @return\r
*/\r
- private TextData handleDescriptiveElement(EfloraImportState state,\r
- Element element, Taxon taxon, String classValue) {\r
+ private TextData handleDescriptiveElement(EfloraImportState state, Element element, Taxon taxon, String classValue) {\r
TextData result = null;\r
Feature feature = getFeature(classValue, state);\r
if (feature == null){\r
String value = element.getValue();\r
value = replaceStart(value, "Notes");\r
value = replaceStart(value, "Note");\r
- result = addDescriptionElement(taxon, value, feature, null);\r
+ result = addDescriptionElement(state, taxon, value, feature, null);\r
}\r
return result;\r
}\r
String value = element.getTextNormalize();\r
value = replaceStart(value, "Uses");\r
Feature feature = Feature.USES();\r
- return addDescriptionElement(taxon, value, feature, null);\r
+ return addDescriptionElement(state, taxon, value, feature, null);\r
\r
}\r
\r
value = replaceStart(value, "Distribution");\r
Feature feature = Feature.DISTRIBUTION();\r
//distribution parsing almost impossible as there is lots of freetext in the distribution tag\r
- return addDescriptionElement(taxon, value, feature, null);\r
+ return addDescriptionElement(state, taxon, value, feature, null);\r
}\r
\r
\r
value = replaceStart(value, "Habitat");\r
feature = getFeature("Habitat", state);\r
}\r
- return addDescriptionElement(taxon, value, feature, null);\r
+ return addDescriptionElement(state, taxon, value, feature, null);\r
}\r
\r
\r
if (value.startsWith(replacementString) ){\r
value = value.substring(replacementString.length()).trim();\r
}\r
- if (value.startsWith("-") ){\r
+ while (value.startsWith("-") || value.startsWith("–") ){\r
value = value.substring("-".length()).trim();\r
}\r
return value;\r
}\r
\r
\r
+ /**\r
+ * @param value\r
+ * @param replacementString\r
+ */\r
+ protected String removeTrailing(String value, String replacementString) {\r
+ if (value == null){\r
+ return null;\r
+ }\r
+ if (value.endsWith(replacementString) ){\r
+ value = value.substring(0, value.length() - replacementString.length()).trim();\r
+ }\r
+ return value;\r
+ }\r
\r
/**\r
* @param state\r
\r
List<Element> elements = elNom.getChildren();\r
for (Element element : elements){\r
- if (element.getName().equals("name")){\r
+ if (element.getName().equals("name") || element.getName().equals("homonym") ){\r
if (taxonBaseClassType == false){\r
- logger.warn("Name tag not allowed in non taxon nom tag");\r
+ logger.warn("Name or homonym tag not allowed in non taxon nom tag");\r
}\r
}else{\r
unhandledNomChildren.add(element.getName());\r
* @param taxon\r
* @param homotypicalGroup \r
*/\r
- private void handleTypeRef(EfloraImportState state, Element elNom, Taxon taxon, HomotypicalGroup homotypicalGroup) {\r
+ protected void handleTypeRef(EfloraImportState state, Element elNom, Taxon taxon, HomotypicalGroup homotypicalGroup) {\r
verifyNoChildren(elNom);\r
String typeRef = elNom.getTextNormalize();\r
- typeRef = replaceStart(typeRef, "-");\r
- typeRef = replaceStart(typeRef, "\97");\r
- typeRef = replaceStart(typeRef, "\u002d");\r
- typeRef = replaceStart(typeRef, "\u2013");\r
+ typeRef = removeStartingTypeRefMinus(typeRef);\r
\r
String[] split = typeRef.split(":");\r
if (split.length < 2){\r
}\r
}\r
\r
+\r
+ /**\r
+ * @param typeRef\r
+ * @return\r
+ */\r
+ protected String removeStartingTypeRefMinus(String typeRef) {\r
+ typeRef = replaceStart(typeRef, "-");\r
+ typeRef = replaceStart(typeRef, "—");\r
+ typeRef = replaceStart(typeRef, "\u002d");\r
+ typeRef = replaceStart(typeRef, "\u2013");\r
+ typeRef = replaceStart(typeRef, "--");\r
+ return typeRef;\r
+ }\r
+\r
/**\r
* @param typeType\r
* @param typeText\r
//create name\r
BotanicalName nameType = (BotanicalName)parser.parseFullName(typeText, NomenclaturalCode.ICBN, Rank.SPECIES());\r
((NameTypeDesignation) typeDesignation).setTypeName(nameType);\r
- //TODO wie können NameTypes den Namen zugeordnet werden? - wird aber vom Portal via NameCache matching gemacht\r
+ //TODO wie können NameTypes den Namen zugeordnet werden? - wird aber vom Portal via NameCache matching gemacht\r
}\r
\r
\r
* @param typeText\r
* @param typeDesignation\r
*/\r
- private void makeSpecimenTypeDesignation(StringBuffer typeType, String typeText, TypeDesignationBase typeDesignation) {\r
+ protected void makeSpecimenTypeDesignation(StringBuffer typeType, String typeText, TypeDesignationBase typeDesignation) {\r
if (typeType.toString().trim().equalsIgnoreCase("Type")){\r
//do nothing\r
}else if (typeType.toString().trim().equalsIgnoreCase("Neotype") || typeType.toString().trim().equalsIgnoreCase("Neotypes")){\r
logger.warn("Unhandled name class: " + classValue);\r
}\r
}else if(element.getName().equals("homonym")){\r
- handleHomonym(element, name);\r
+ handleHomonym(state, element, name);\r
}else{\r
// child element is not "name"\r
unhandledNomChildren.add(element.getName());\r
}\r
\r
//test nom element has no text\r
- if (StringUtils.isNotBlank(elNom.getTextNormalize().replace("\97", "").replace("\u002d","").replace("\u2013", ""))){\r
+ if (StringUtils.isNotBlank(elNom.getTextNormalize().replace("—", "").replace("\u002d","").replace("\u2013", ""))){\r
String strElNom = elNom.getTextNormalize();\r
if ("?".equals(strElNom)){\r
handleQuestionMark(name, taxon);\r
\r
\r
//merge with handleNomTaxon \r
- private void handleHomonym(Element elHomonym, NonViralName upperName) {\r
+ private void handleHomonym(EfloraImportState state, Element elHomonym, NonViralName upperName) {\r
verifyNoAttribute(elHomonym);\r
\r
//hommonym name\r
homonymName.setSpecificEpithet(value);\r
}else if (classValue.equalsIgnoreCase("author")){\r
handleNameAuthors(elName, homonymName);\r
+ }else if (classValue.equalsIgnoreCase("paraut")){\r
+ handleBasionymAuthor(state, elName, homonymName, true);\r
}else if (classValue.equalsIgnoreCase("pub")){\r
handleNomenclaturalReference(homonymName, value);\r
}else if (classValue.equalsIgnoreCase("note")){\r
TimePeriod nameYear = upperName.getNomenclaturalReference().getDatePublished();\r
homonymIsLater = homonymYear.getStart().compareTo(nameYear.getStart()) > 0;\r
}else{\r
- logger.warn("Classification name has no nomenclatural reference");\r
+ if (upperName.getNomenclaturalReference() == null){\r
+ logger.warn("Homonym parent does not have a nomenclatural reference or year: " + upperName.getTitleCache());\r
+ }\r
+ if (homonymName.getNomenclaturalReference() == null){\r
+ logger.warn("Homonym does not have a nomenclatural reference or year: " + homonymName.getTitleCache());\r
+ }\r
}\r
if (homonymIsLater){\r
homonymName.addRelationshipToName(upperName, relType, null);\r
* @param name\r
* @param value\r
*/\r
- private TeamOrPersonBase handleNameUsage(Taxon taxon, NonViralName name, String referenceTitle, TeamOrPersonBase lastTeam) {\r
+ protected TeamOrPersonBase handleNameUsage(Taxon taxon, NonViralName name, String referenceTitle, TeamOrPersonBase lastTeam) {\r
ReferenceBase ref = ReferenceFactory.newGeneric();\r
referenceTitle = removeStartingSymbols(referenceTitle, ref);\r
\r
}\r
\r
\r
- private Team getReferenceAuthor (ReferenceBase ref) {\r
+ protected Team getReferenceAuthor (ReferenceBase ref) {\r
boolean isCache = false;\r
String referenceTitle = ref.getTitle();\r
if (referenceTitle == null){\r
* @param name\r
* @return\r
*/\r
- private String parseHomonym(String detail, NonViralName name) {\r
+ protected String parseHomonym(String detail, NonViralName name) {\r
String result;\r
if (detail == null){\r
return detail;\r
\r
\r
/**\r
+ * @Xpath body/taxon/nomenclature/homotypes/nom/name[@class="pub"]\r
* @param name\r
* @param value\r
*/\r
- private TeamOrPersonBase handleNomenclaturalReference(NonViralName name, String value) {\r
+ protected TeamOrPersonBase handleNomenclaturalReference(NonViralName name, String value) {\r
ReferenceBase nomRef = ReferenceFactory.newGeneric();\r
nomRef.setTitleCache(value, true);\r
parseNomStatus(nomRef, name);\r
if (strAuthor.endsWith(",")){\r
strAuthor = strAuthor.substring(0, strAuthor.length() -1);\r
}\r
- Team[] team = getTeam(strAuthor);\r
+ TeamOrPersonBase[] team = getTeam(strAuthor);\r
if (name.getCombinationAuthorTeam() != null && overwrite == false){\r
logger.warn("Try to write combination author for a name that already has a combination author. Neglected.");\r
}else{\r
* @param element\r
* @param name\r
*/\r
- private void handleBasionymAuthor(EfloraImportState state, Element element, NonViralName name, boolean overwrite) {\r
- String strAuthor = element.getValue().trim();\r
+ private void handleBasionymAuthor(EfloraImportState state, Element elBasionymAuthor, NonViralName name, boolean overwrite) {\r
+ String strAuthor = elBasionymAuthor.getValue().trim();\r
Pattern reBasionymAuthor = Pattern.compile("^\\(.*\\)$");\r
if (reBasionymAuthor.matcher(strAuthor).matches()){\r
strAuthor = strAuthor.substring(1, strAuthor.length()-1);\r
}else{\r
logger.warn("Brackets are missing for original combination author " + strAuthor);\r
}\r
- Team[] basionymTeam = getTeam(strAuthor);\r
+ TeamOrPersonBase[] basionymTeam = getTeam(strAuthor);\r
if (name.getBasionymAuthorTeam() != null && overwrite == false){\r
logger.warn("Try to write basionym author for a name that already has a basionym author. Neglected.");\r
}else{\r
if (strAuthor.endsWith(",")){\r
strAuthor = strAuthor.substring(0, strAuthor.length() -1);\r
}\r
- Team[] team = getTeam(strAuthor);\r
+ if (strAuthor.indexOf("(") > -1 || strAuthor.indexOf(")") > -1){\r
+ logger.warn("Author has brackets. Basionym authors should be handled in separate tags: " + strAuthor);\r
+ }\r
+ TeamOrPersonBase[] team = getTeam(strAuthor);\r
name.setCombinationAuthorTeam(team[0]);\r
name.setExCombinationAuthorTeam(team[1]);\r
}\r
* @param strAuthor\r
* @return\r
*/\r
- private Team[] getTeam(String strAuthor) {\r
- Team[] result = new Team[2];\r
+ private TeamOrPersonBase[] getTeam(String strAuthor) {\r
+ TeamOrPersonBase[] result = new TeamOrPersonBase[2];\r
String[] split = strAuthor.split(" ex ");\r
String strBaseAuthor = null;\r
String strExAuthor = null;\r
}else{\r
logger.warn("Could not parse (ex) author: " + strAuthor);\r
}\r
- \r
result[0] = getUuidTeam(strBaseAuthor);\r
if (result[0] == null){\r
- result[0] = Team.NewInstance();\r
- result[0].setTitleCache(strBaseAuthor, true);\r
+ result[0] = parseSingleTeam(strBaseAuthor);\r
teamMap.put(strBaseAuthor, result[0].getUuid());\r
}\r
if (strExAuthor != null){\r
}\r
\r
\r
+ protected TeamOrPersonBase parseSingleTeam(String strBaseAuthor) {\r
+ TeamOrPersonBase result;\r
+ String[] split = strBaseAuthor.split("&");\r
+ if (split.length > 1){\r
+ result = Team.NewInstance();\r
+ for (String personString : split){\r
+ Person person = makePerson(personString);\r
+ ((Team)result).addTeamMember(person);\r
+ }\r
+ }else{\r
+ result = makePerson(strBaseAuthor.trim());\r
+ }\r
+ return result;\r
+ }\r
+\r
+\r
+ /**\r
+ * @param personString\r
+ * @return\r
+ */\r
+ private Person makePerson(String personString) {\r
+ personString = personString.trim();\r
+ Person person = Person.NewTitledInstance(personString);\r
+ person.setNomenclaturalTitle(personString);\r
+ return person;\r
+ }\r
+\r
+\r
/**\r
* @param result\r
* @param strBaseAuthor\r
*/\r
- private Team getUuidTeam(String strBaseAuthor) {\r
+ private TeamOrPersonBase getUuidTeam(String strBaseAuthor) {\r
UUID uuidTeam = teamMap.get(strBaseAuthor);\r
- return CdmBase.deproxy(getAgentService().find(uuidTeam), Team.class);\r
+ return CdmBase.deproxy(getAgentService().find(uuidTeam), TeamOrPersonBase.class);\r
}\r
\r
\r
logger.warn("Unhandled feature: " + classValue);\r
}else{\r
String value = element.getValue();\r
- addDescriptionElement(taxon, value, feature, null);\r
+ addDescriptionElement(state, taxon, value, feature, null);\r
}\r
\r
}\r
* @param taxon\r
* @return\r
*/\r
- private TaxonDescription getDescription(Taxon taxon) {\r
+ protected TaxonDescription getDescription(Taxon taxon) {\r
for (TaxonDescription description : taxon.getDescriptions()){\r
if (! description.isImageGallery()){\r
return description;\r
* @param value\r
* @param taxonNameBase \r
*/\r
- private void handleGenus(String value, TaxonNameBase taxonName) {\r
+ protected void handleGenus(String value, TaxonNameBase taxonName) {\r
Matcher matcher = rexGenusAuthor.matcher(value);\r
if (matcher.find()){\r
String author = matcher.group();\r
}\r
\r
\r
-\r
/**\r
+ * @param state \r
* @param taxon\r
* @param value\r
* @param feature\r
* @return \r
*/\r
- private TextData addDescriptionElement(Taxon taxon, String value, Feature feature, String references) {\r
+ private TextData addDescriptionElement(EfloraImportState state, Taxon taxon, String value, Feature feature, String references) {\r
TextData textData = TextData.NewInstance(feature);\r
- textData.putText(value, Language.ENGLISH());\r
+ Language textLanguage = getDefaultLanguage(state);\r
+ textData.putText(value, textLanguage);\r
TaxonDescription description = getDescription(taxon);\r
description.addElement(textData);\r
if (references != null){\r
return textData;\r
}\r
\r
+ private Language getDefaultLanguage(EfloraImportState state) {\r
+ UUID defaultLanguageUuid = state.getConfig().getDefaultLanguageUuid();\r
+ if (defaultLanguageUuid != null){\r
+ Language result = state.getDefaultLanguage();\r
+ if (result == null || ! result.getUuid().equals(defaultLanguageUuid)){\r
+ result = (Language)getTermService().find(defaultLanguageUuid);\r
+ state.setDefaultLanguage(result);\r
+ if (result == null){\r
+ logger.warn("Default language for " + defaultLanguageUuid + " does not exist.");\r
+ }\r
+ }\r
+ return result;\r
+ }else{\r
+ return Language.DEFAULT();\r
+ }\r
+ }\r
+\r
+\r
/**\r
* @param elNomenclature\r
*/\r
/**\r
* @param elNomenclature\r
*/\r
- private void verifyNoChildren(Element element) {\r
+ protected void verifyNoChildren(Element element) {\r
verifyNoChildren(element, false);\r
}\r
\r
\r
\r
\r
- private void parseNomStatus(ReferenceBase ref, NonViralName nonViralName) {\r
+ /**\r
+ * Parses the nomenclatural status from the references titleCache. If a nomenclatural status\r
+ * exists it is added to the name and the nom. status part of the references title cache is \r
+ * removed. Requires protected title cache.\r
+ * @param ref\r
+ * @param nonViralName\r
+ */\r
+ protected void parseNomStatus(ReferenceBase ref, NonViralName nonViralName) {\r
String titleToParse = ref.getTitleCache();\r
\r
- \r
String noStatusTitle = parser.parseNomStatus(titleToParse, nonViralName);\r
if (! noStatusTitle.equals(titleToParse)){\r
ref.setTitleCache(noStatusTitle, true);\r