Project

General

Profile

« Previous | Next » 

Revision b9cdcc88

Added by Andreas Müller about 8 years ago

Latest changes to Cuba import

View differences:

app-import/src/main/java/eu/etaxonomy/cdm/app/cuba/CubaActivator.java
14 14

  
15 15
import org.apache.log4j.Logger;
16 16

  
17
import eu.etaxonomy.cdm.api.application.CdmApplicationController;
17 18
import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
18 19
import eu.etaxonomy.cdm.api.service.ITermService;
19 20
import eu.etaxonomy.cdm.app.common.CdmDestinations;
......
24 25
import eu.etaxonomy.cdm.io.cuba.CubaImportConfigurator;
25 26
import eu.etaxonomy.cdm.io.cuba.CubaTransformer;
26 27
import eu.etaxonomy.cdm.model.agent.Person;
28
import eu.etaxonomy.cdm.model.agent.Team;
27 29
import eu.etaxonomy.cdm.model.description.Feature;
28 30
import eu.etaxonomy.cdm.model.description.FeatureNode;
29 31
import eu.etaxonomy.cdm.model.description.FeatureTree;
......
41 43
	static DbSchemaValidation hbm2dll = DbSchemaValidation.CREATE;
42 44

  
43 45
//    static final ICdmDataSource cdmDestination = CdmDestinations.localH2();
44
//  static final ICdmDataSource cdmDestination = CdmDestinations.cdm_test_local_mysql_test();
45
    static final ICdmDataSource cdmDestination = CdmDestinations.cdm_cuba_production();
46
  static final ICdmDataSource cdmDestination = CdmDestinations.cdm_test_local_mysql_test();
47
//    static final ICdmDataSource cdmDestination = CdmDestinations.cdm_cuba_production();
46 48

  
47 49
	static boolean invers = false;
48 50

  
......
67 69
    static boolean include = !invers;
68 70

  
69 71

  
70

  
71

  
72 72
	//feature tree uuid
73 73
	public static final UUID featureTreeUuid = UUID.fromString("dad6b9b5-693f-4367-a7aa-076cc9c99476");
74 74

  
75 75
	//classification
76 76
	static final UUID classificationUuid = UUID.fromString("5de394de-9c76-4b97-b04d-71be31c7f44b");
77
	private static final String classificationName = "Flora of Cuba";
77
	private static final String classificationName = "Cuba Checklist";
78 78

  
79
	static final String sourceReferenceTitle = "Cuba import";
79
	static final String sourceReferenceTitle = "Cuba Checklist Word Documents";
80 80

  
81 81
	//check - import
82 82
	static final CHECK check = CHECK.IMPORT_WITHOUT_CHECK;
......
106 106

  
107 107
		//...
108 108
        if (doAsteraceae){
109
            doSource(asteraceae(), config, myImport, doVocabularies);
109
            doSingleSource(asteraceae(), config, myImport, doVocabularies);
110 110
        }
111 111
        if (doConvolvulaceae){
112
            doSource(convolvulaceae(), config, myImport, doVocabularies);
112
            doSingleSource(convolvulaceae(), config, myImport, doVocabularies);
113 113
        }
114 114
        if (doCyperaceae){
115
            doSource(cyperaceae(), config, myImport, doVocabularies);
115
            doSingleSource(cyperaceae(), config, myImport, doVocabularies);
116 116
        }
117 117
        if (doDicotA_C){
118
            doSource(dicotA_C(), config, myImport, doVocabularies);
118
            doSingleSource(dicotA_C(), config, myImport, doVocabularies);
119 119
        }
120 120
        if (doDicotD_M){
121
            doSource(dicotD_M(), config, myImport, doVocabularies);
121
            doSingleSource(dicotD_M(), config, myImport, doVocabularies);
122 122
        }
123 123
        if (doDicotN_Z){
124
            doSource(dicotN_Z(), config, myImport, doVocabularies);
124
            doSingleSource(dicotN_Z(), config, myImport, doVocabularies);
125 125
        }
126 126
        if (doEuphorbiaceae){
127
            doSource(euphorbiaceae(), config, myImport, doVocabularies);
127
            doSingleSource(euphorbiaceae(), config, myImport, doVocabularies);
128 128
        }
129 129
        if (doFabaceae){
130
            doSource(fabaceae(), config, myImport, doVocabularies);
130
            doSingleSource(fabaceae(), config, myImport, doVocabularies);
131 131
        }
132 132
        if (doGymnospermae){
133
            doSource(gymnospermae(), config, myImport, doVocabularies);
133
            doSingleSource(gymnospermae(), config, myImport, doVocabularies);
134 134
        }
135 135
        if (doLamVerbenaceae){
136
            doSource(lamVerbenaceae(), config, myImport, doVocabularies);
136
            doSingleSource(lamVerbenaceae(), config, myImport, doVocabularies);
137 137
        }
138 138
        if (doMalpighiaceae){
139
            doSource(malpighiaceae(), config, myImport, doVocabularies);
139
            doSingleSource(malpighiaceae(), config, myImport, doVocabularies);
140 140
        }
141 141
        if (doMelastomataceae){
142
            doSource(melastomataceae(), config, myImport, doVocabularies);
142
            doSingleSource(melastomataceae(), config, myImport, doVocabularies);
143 143
        }
144 144
        if (doMonocots){
145
            doSource(monocots(), config, myImport, doVocabularies);
145
            doSingleSource(monocots(), config, myImport, doVocabularies);
146 146
        }
147 147
        if (doMyrtaceae){
148
            doSource(myrtaceae(), config, myImport, doVocabularies);
148
            doSingleSource(myrtaceae(), config, myImport, doVocabularies);
149 149
        }
150 150
        if (doOrchidaceae){
151
            doSource(orchidaceae(), config, myImport, doVocabularies);
151
            doSingleSource(orchidaceae(), config, myImport, doVocabularies);
152 152
        }
153 153
        if (doRubiaceae){
154
            doSource(rubiaceae(), config, myImport, doVocabularies);
154
            doSingleSource(rubiaceae(), config, myImport, doVocabularies);
155 155
        }
156 156
        if (doUrticaceae){
157
            doSource(urticaceae(), config, myImport, doVocabularies);
157
            doSingleSource(urticaceae(), config, myImport, doVocabularies);
158 158
        }
159 159

  
160 160

  
161 161

  
162 162
		//deduplicate
163 163
		if (doDeduplicate){
164
			ICdmApplicationConfiguration app = myImport.getCdmAppController();
164
		    logger.warn("Start deduplication ...");
165

  
166
		    ICdmApplicationConfiguration app = myImport.getCdmAppController();
167
			if (app == null){
168
                app = CdmApplicationController.NewInstance(cdmDestination, hbm2dll, false);
169
            }
165 170
			int count = app.getAgentService().deduplicate(Person.class, null, null);
166 171
			logger.warn("Deduplicated " + count + " persons.");
167
//			count = app.getAgentService().deduplicate(Team.class, null, null);
168
//			logger.warn("Deduplicated " + count + " teams.");
172
			count = app.getAgentService().deduplicate(Team.class, null, null);
173
			logger.warn("Deduplicated " + count + " teams.");
169 174
			count = app.getReferenceService().deduplicate(Reference.class, null, null);
170 175
			logger.warn("Deduplicated " + count + " references.");
171 176
		}
172 177

  
173

  
174 178
		System.exit(0);
175 179

  
176 180
	}
......
180 184
     * @param config
181 185
     * @param myImport
182 186
     */
183
    private void doSource(URI source, CubaImportConfigurator config,
187
    private void doSingleSource(URI source, CubaImportConfigurator config,
184 188
            CdmDefaultImport<CubaImportConfigurator> myImport, boolean doVocabularies) {
185 189
        config.setSource(source);
186
        String message = "Start import from ("+ source.toString() + ") ...";
190
        String fileName = source.toString();
191
        fileName = fileName.substring(fileName.lastIndexOf("/") + 1 );
192

  
193
        String message = "Start import from ("+ fileName + ") ...";
187 194
        System.out.println(message);
188 195
        logger.warn(message);
189
        config.setSourceReference(getSourceReference(sourceReferenceTitle));
196
        config.setSourceReference(getSourceReference(fileName));
190 197
        config.setDoVocabularies(doVocabularies);
191 198
        myImport.invoke(config);
192 199

  
......
198 205
        System.out.println("End import from ("+ source.toString() + ")...");
199 206
    }
200 207

  
208
    private final Reference<?> inRef = ReferenceFactory.newGeneric();
201 209
	private Reference<?> getSourceReference(String string) {
202 210
		Reference<?> result = ReferenceFactory.newGeneric();
203 211
		result.setTitleCache(string, true);
212
		result.setInReference(inRef);
213
		inRef.setTitleCache(sourceReferenceTitle, true);
204 214
		return result;
205 215
	}
206 216

  
app-import/src/main/java/eu/etaxonomy/cdm/io/cuba/CubaExcelImport.java
26 26
import eu.etaxonomy.cdm.common.CdmUtils;
27 27
import eu.etaxonomy.cdm.io.common.mapping.UndefinedTransformerMethodException;
28 28
import eu.etaxonomy.cdm.io.excel.common.ExcelImporterBase;
29
import eu.etaxonomy.cdm.model.agent.Person;
29 30
import eu.etaxonomy.cdm.model.agent.Team;
30 31
import eu.etaxonomy.cdm.model.agent.TeamOrPersonBase;
31 32
import eu.etaxonomy.cdm.model.common.Annotation;
32 33
import eu.etaxonomy.cdm.model.common.AnnotationType;
34
import eu.etaxonomy.cdm.model.common.CdmBase;
35
import eu.etaxonomy.cdm.model.common.IdentifiableSource;
33 36
import eu.etaxonomy.cdm.model.common.Language;
34 37
import eu.etaxonomy.cdm.model.common.OriginalSourceType;
38
import eu.etaxonomy.cdm.model.description.DescriptionElementBase;
39
import eu.etaxonomy.cdm.model.description.DescriptionElementSource;
35 40
import eu.etaxonomy.cdm.model.description.Distribution;
36 41
import eu.etaxonomy.cdm.model.description.Feature;
37 42
import eu.etaxonomy.cdm.model.description.PresenceAbsenceTerm;
......
40 45
import eu.etaxonomy.cdm.model.description.TextData;
41 46
import eu.etaxonomy.cdm.model.location.NamedArea;
42 47
import eu.etaxonomy.cdm.model.name.BotanicalName;
48
import eu.etaxonomy.cdm.model.name.HomotypicalGroup;
49
import eu.etaxonomy.cdm.model.name.NameRelationship;
43 50
import eu.etaxonomy.cdm.model.name.NameRelationshipType;
44 51
import eu.etaxonomy.cdm.model.name.NomenclaturalCode;
45 52
import eu.etaxonomy.cdm.model.name.NomenclaturalStatus;
46 53
import eu.etaxonomy.cdm.model.name.NomenclaturalStatusType;
47 54
import eu.etaxonomy.cdm.model.name.Rank;
55
import eu.etaxonomy.cdm.model.name.TaxonNameBase;
48 56
import eu.etaxonomy.cdm.model.reference.Reference;
49 57
import eu.etaxonomy.cdm.model.reference.ReferenceFactory;
50 58
import eu.etaxonomy.cdm.model.taxon.Classification;
......
101 109
            for (PresenceAbsenceTerm status : statuss){
102 110
                Distribution distribution = Distribution.NewInstance(cuba, status);
103 111
                desc.addElement(distribution);
112
                distribution.addSource(makeDescriptionSource(state));
104 113
            }
105 114
        } catch (UndefinedTransformerMethodException e) {
106 115
            e.printStackTrace();
......
115 124
     * @throws UndefinedTransformerMethodException
116 125
     */
117 126
    private List<PresenceAbsenceTerm> makeCubanStatuss(HashMap<String, String> record, CubaImportState state) throws UndefinedTransformerMethodException {
118
        boolean isAbsent = false;  //TODO
119 127
        PresenceAbsenceTerm highestStatus = null;
120 128

  
121 129
        String line = state.getCurrentLine() + ": ";
......
129 137
        String advStr = getValue(record, "Adv");
130 138
        String cultStr = getValue(record, "Cult C");
131 139

  
140
        state.setEndemic(false);
141

  
132 142
        if (endemicStr != null){
133 143
            if(endemicStr.equals("+")){
134 144
                PresenceAbsenceTerm endemicState = state.getTransformer().getPresenceTermByKey("E");
135 145
                result.add(endemicState);
136 146
                highestStatus = endemicState;
147
                state.setEndemic(true);
137 148
            }else if(isMinus(endemicStr)){
138 149
                UUID endemicUuid = state.getTransformer().getPresenceTermUuid("-E");
139 150
                PresenceAbsenceTerm endemicState = getPresenceTerm(state, endemicUuid, null, null, null, false);
......
150 161
        }
151 162
        if (indigenousStr != null){
152 163
            if(indigenousStr.equals("+")){
153
                UUID indigenousUuid = state.getTransformer().getPresenceTermUuid("Ind.");
154
                PresenceAbsenceTerm indigenousState = getPresenceTerm(state, indigenousUuid, null, null, null, false);
164
                PresenceAbsenceTerm indigenousState = state.getTransformer().getPresenceTermByKey("Ind.");
165
//                PresenceAbsenceTerm indigenousState = getPresenceTerm(state, indigenousUuid, null, null, null, false);
155 166
                result.add(indigenousState);
156 167
                highestStatus = highestStatus != null ? highestStatus : indigenousState;
157 168
            }else if(isMinus(indigenousStr)){
......
159 170
                result.add(indigenousState);
160 171
                checkAbsentHighestState(highestStatus, line, "indigenous", false);
161 172
            }else if(indigenousStr.equals("?")){
162
                UUID indigenousDoubtUuid = state.getTransformer().getPresenceTermUuid("?Ind.");
163
                PresenceAbsenceTerm indigenousDoubtState = getPresenceTerm(state, indigenousDoubtUuid, null, null, null, false);
173
                PresenceAbsenceTerm indigenousDoubtState = state.getTransformer().getPresenceTermByKey("?Ind.");
174
//                PresenceAbsenceTerm indigenousDoubtState = getPresenceTerm(state, indigenousDoubtUuid, null, null, null, false);
164 175
                result.add(indigenousDoubtState);
165 176
                checkAbsentHighestState(highestStatus, line, "indigenous", true);
166 177
            }else{
......
169 180
        }
170 181
        if(indigenousDoubtStr != null){
171 182
            if(indigenousDoubtStr.equals("D")){
172
                UUID indigenousDoubtUuid = state.getTransformer().getPresenceTermUuid("Ind.?");
173
                PresenceAbsenceTerm indigenousDoubtState = getPresenceTerm(state, indigenousDoubtUuid, null, null, null, false);
174
                result.add(indigenousDoubtState);
175
                highestStatus = highestStatus != null ? highestStatus : indigenousDoubtState;
183
                PresenceAbsenceTerm doubtIndigenousState = state.getTransformer().getPresenceTermByKey("Ind.?");
184
//                PresenceAbsenceTerm doubtIndigenousState = getPresenceTerm(state, doubtIndigenousUuid, null, null, null, false);
185
                result.add(doubtIndigenousState);
186
                highestStatus = highestStatus != null ? highestStatus : doubtIndigenousState;
187
            }else if(isMinus(indigenousDoubtStr)){
188
                UUID doubtIndigenousErrorUuid = state.getTransformer().getPresenceTermUuid("-Ind.?");
189
                PresenceAbsenceTerm doubtIndigenousErrorState = getPresenceTerm(state, doubtIndigenousErrorUuid, null, null, null, false);
190
                result.add(doubtIndigenousErrorState);
191
                checkAbsentHighestState(highestStatus, line, "doubtfully indigenous", true);
176 192
            }else{
177
                logger.warn(line + "Indigenous doubtful not recognized: " + indigenousDoubtStr);
193
                logger.warn(line + "doubtfully indigenous not recognized: " + indigenousDoubtStr);
178 194
            }
179 195
        }
180 196
        if(naturalisedStr != null){
......
218 234
        }
219 235
        if(advStr != null){
220 236
            if(advStr.equals("A")){
221
                UUID advUuid = state.getTransformer().getPresenceTermUuid("Adv.");
222
                PresenceAbsenceTerm advState = getPresenceTerm(state, advUuid, null, null, null, false);
237
                PresenceAbsenceTerm advState = state.getTransformer().getPresenceTermByKey("Adv.");
238
//                PresenceAbsenceTerm advState = getPresenceTerm(state, advUuid, null, null, null, false);
223 239
                result.add(advState);
224 240
                highestStatus = highestStatus != null ? highestStatus : advState;
225 241
            }else if(isMinus(advStr)){
......
227 243
                PresenceAbsenceTerm advState = getPresenceTerm(state, advUuid, null, null, null, false);
228 244
                result.add(advState);
229 245
                checkAbsentHighestState(highestStatus, line, "adventive", false);
246
            }else if(advStr.equals("(A)")){
247
                UUID rareCasualUuid = state.getTransformer().getPresenceTermUuid("(A)");
248
                PresenceAbsenceTerm rareCasual = getPresenceTerm(state, rareCasualUuid, null, null, null, false);
249
                result.add(rareCasual);
230 250
            }else{
231 251
                logger.warn(line + "'adventive (casual) alien' not recognized: " + advStr);
232 252
            }
......
263 283
     * @param line
264 284
     */
265 285
    private void checkAbsentHighestState(PresenceAbsenceTerm highestStatus, String line, String stateLabel, boolean doubtful) {
286
        //can be removed, highest status is not used anymore
266 287
        if (highestStatus == null){
267 288
            String absentStr = doubtful ? "doubtful" : "absent";
268
            logger.warn(line + "Highest cuban state is " + absentStr + " " + stateLabel);
289
            logger.info(line + "Highest cuban state is " + absentStr + " " + stateLabel);
269 290
        }
270 291

  
271 292
    }
......
276 297
     * @return
277 298
     */
278 299
    private boolean isMinus(String str) {
279
        return str.equals("-") || str.equals("–");
300
        return str.equals("-") || str.equals("–") || str.equals("‒");
280 301
    }
281 302

  
282 303

  
......
315 336
    private static final String heterotypicRegExStr_TEST = "([^\\(]{5,}" +"(\\(.+\\))?" + "[^\\)\\(]{2,})"
316 337
            +"(\\((.{6,})\\))?";
317 338
    private static final String auctRegExStr = "auct\\."
318
            +"((\\sFC(\\-S)?(\\s&\\sA&S)?)|(\\sA&S)|\\sSagra|\\sCombs|\\sBritton|\\sGriseb\\.|\\sWright"
339
            +"((\\sFC(\\-S)?(\\s&\\sA&S)?)|(\\sA&S)|\\sSagra|\\sCombs|\\sBritton|\\sGriseb\\.(\\sFC-S|\\sA&S)?|\\sWright"
319 340
            + "|\\sHammer|\\sEngl\\.||\\sMaza|\\sMiers|\\sRoig|\\sBorhidi|\\sFRC|\\sCoL"
320 341
            + "|\\sAckerman|\\sMújica|\\sDíaz|\\sUrb\\.)?(\\s+p\\.\\s*p\\.)?";
321 342

  
......
336 357
     * @param state
337 358
     * @param taxon
338 359
     */
339
    private void makeSynonyms(HashMap<String, String> record, CubaImportState state) {
360
    private void makeSynonyms(HashMap<String, String> record, CubaImportState state, boolean isFirstSynonym) {
340 361
//        boolean forAccepted = true;
341 362
        String synonymStr = record.get("Syn.");
342 363
        String line = state.getCurrentLine() + ": ";
343 364

  
365

  
344 366
        if (synonymStr == null){
345 367
            //TODO test that this is not a synonym only line
346 368
            return;
347 369
        }
370

  
371
        if (state.getCurrentTaxon() == null){
372
            logger.error(line + "Current taxon is null for synonym");
373
            return;
374
        }
375

  
376

  
348 377
        synonymStr = synonymStr.trim();
378
        synonymStr = synonymStr.replace("[taxon]", "[infraspec.]");
349 379

  
350 380
//        String heterotypicRegExStr = "([^\\(]{5,}(\\(.+\\))?[^\\)\\(]{2,})(\\((.{6,})\\))?";
351 381
//        String heterotypicRegExStr = "([^\\(]{5,})(\\((.{6,})\\))?";
352 382

  
353 383
//        Pattern heterotypicRegEx = Pattern.compile(heterotypicRegExStr + homonymRegExStr);
354 384

  
385

  
355 386
        Matcher missapliedMatcher = missapliedRegEx.matcher(synonymStr);
356 387
        Matcher nomInvalMatcher = nomInvalRegEx.matcher(synonymStr);
357 388
        Matcher acceptedMatcher = acceptedRegEx.matcher(synonymStr);
......
363 394
            boolean doubtful = missapliedMatcher.group(1) != null;
364 395
            String firstPart = missapliedMatcher.group(2);
365 396
            BotanicalName name = (BotanicalName)nameParser.parseSimpleName(firstPart, state.getConfig().getNomenclaturalCode(), Rank.SPECIES());
397
            name.addSource(makeOriginalSource(state));
366 398

  
367 399
            String secondPart = missapliedMatcher.group(3);
368 400
            Taxon misappliedNameTaxon = Taxon.NewInstance(name, null);
401
            misappliedNameTaxon.addSource(makeOriginalSource(state));
369 402
            misappliedNameTaxon.setDoubtful(doubtful);
370 403
            if (secondPart.startsWith("sensu")){
371 404
                secondPart = secondPart.substring(5).trim();
......
392 425
                logger.warn(state.getCurrentLine() + ": After inval to be implemented: " + afterInval);
393 426
            }
394 427
            BotanicalName name = (BotanicalName)nameParser.parseSimpleName(firstPart, state.getConfig().getNomenclaturalCode(), Rank.SPECIES());
428
            name.addSource(makeOriginalSource(state));
395 429
            NomenclaturalStatus status = NomenclaturalStatus.NewInstance( NomenclaturalStatusType.INVALID());
396 430
            name.addStatus(status);
397
            state.getCurrentTaxon().addSynonymName(name, SynonymRelationshipType.SYNONYM_OF());
431
            SynonymRelationship sr = state.getCurrentTaxon().addSynonymName(name, SynonymRelationshipType.SYNONYM_OF());
432
            sr.getSynonym().addSource(makeOriginalSource(state));
398 433
        }else if (sphalmMatcher.matches()){
399 434
            String firstPart = sphalmMatcher.group(1);
400 435
            String sphalmPart = synonymStr.replace(firstPart, "").replace("“","").replace("”","").trim();
401 436
            BotanicalName name = (BotanicalName)nameParser.parseSimpleName(firstPart, state.getConfig().getNomenclaturalCode(), Rank.SPECIES());
402 437
//            NomenclaturalStatus status = NomenclaturalStatus.NewInstance( NomenclaturalStatusType.INVALID());
403 438
//            name.addStatus(status);
439
            name.addSource(makeOriginalSource(state));
404 440
            SynonymRelationship sr = state.getCurrentTaxon().addSynonymName(name, SynonymRelationshipType.SYNONYM_OF());
405 441
            sr.getSynonym().setAppendedPhrase(sphalmPart);
406 442
            sr.getSynonym().setSec(null);
443
            sr.getSynonym().addSource(makeOriginalSource(state));
407 444
        }else if (acceptedMatcher.matches()){
408 445
            String firstPart = acceptedMatcher.group(1);
409 446
            String homonymPart = acceptedMatcher.groupCount() < 2 ? null : acceptedMatcher.group(2);
410
            handleHomotypicGroup(firstPart, state, (BotanicalName)state.getCurrentTaxon().getName(), false, homonyms, homonymPart, false);
447
            List<BotanicalName> list = handleHomotypicGroup(firstPart, state, (BotanicalName)state.getCurrentTaxon().getName(), false, homonyms, homonymPart, false);
448
            checkFirstSynonym(state, list, isFirstSynonym, synonymStr, false);
411 449
        }else if(heterotypicMatcher.matches()){
412 450
            String firstPart = heterotypicMatcher.group(1).trim();
413 451
            String secondPart = heterotypicMatcher.groupCount() < 3 ? null : heterotypicMatcher.group(3);
......
415 453
            boolean isDoubtful = firstPart.matches("^\\?\\s*.*");
416 454
            firstPart = replaceHomonIlleg(firstPart);
417 455
            boolean isHomonym = firstPart.matches(".*" + HOMONYM_MARKER);
418
            BotanicalName synName = makeName(firstPart);
456
            BotanicalName synName = makeName(state, firstPart);
419 457
            if (synName.isProtectedTitleCache()){
420
                logger.warn(line + " heterotypic base synonym could not be parsed correctly:" + firstPart);
458
                logger.warn(line + "Heterotypic base synonym could not be parsed correctly: " + firstPart);
421 459
            }
422 460
            if (isHomonym){
423 461
                homonyms.add(synName);
424 462
            }
425 463
            SynonymRelationship sr = state.getCurrentTaxon().addHeterotypicSynonymName(synName);
426 464
            sr.getSynonym().setDoubtful(isDoubtful);
427
            handleHomotypicGroup(secondPart, state, synName, true, homonyms, homonymPart, isDoubtful);
465
            sr.getSynonym().addSource(makeOriginalSource(state));
466
            List<BotanicalName> list = handleHomotypicGroup(secondPart, state, synName, true, homonyms, homonymPart, isDoubtful);
467
            checkFirstSynonym(state, list, isFirstSynonym, synonymStr, true);
468

  
469
        }else if (isSpecialHeterotypic(synonymStr)){
470
            BotanicalName synName = makeName(state, synonymStr);
471
            if (synName.isProtectedTitleCache()){
472
                logger.warn(line + "Special heterotypic synonym could not be parsed correctly:" + synonymStr);
473
            }
474
            SynonymRelationship sr = state.getCurrentTaxon().addHeterotypicSynonymName(synName);
475
            sr.getSynonym().addSource(makeOriginalSource(state));
428 476
        }else{
429 477
            logger.warn(line + "Synonym entry does not match: " + synonymStr);
430 478
        }
431 479
    }
432 480

  
481
    /**
482
     * @param state
483
     * @param list
484
     * @param isFirstSynonym
485
     * @param synonymStr
486
     * @param b
487
     */
488
    private void checkFirstSynonym(CubaImportState state, List<BotanicalName> list, boolean isFirstSynonym, String synonymStr, boolean isHeterotypicMatcher) {
489
        if (!isFirstSynonym){
490
            return;
491
        }
492
        String line = state.getCurrentLine() + ": ";
493
        BotanicalName currentName = isHeterotypicMatcher? (BotanicalName)state.getCurrentTaxon().getName(): list.get(0);
494
        boolean currentHasBasionym = currentName.getBasionymAuthorship() != null;
495
        BotanicalName firstSynonym = isHeterotypicMatcher ? list.get(0): list.get(1);
496
//        if (list.size() <= 1){
497
//            logger.error(line + "homotypic list size is 1 but shouldn't");
498
//            return;
499
//        }
500
        if (isHeterotypicMatcher && currentHasBasionym){
501
            logger.error(line + "Current taxon (" + currentName.getTitleCache() + ") has basionym author but has no homotypic basionym , but : " + synonymStr);
502
        }else if (isHeterotypicMatcher){
503
            //first synonym must not have a basionym author
504
            if (firstSynonym.getBasionymAuthorship() != null){
505
                logger.error(line + "Current taxon (" + currentName.getTitleCache() + ") has no basionym but first synonym requires basionym : " + synonymStr);
506
            }
507
        }else{  //isAcceptedMatcher
508
            if (currentHasBasionym){
509
                if (! matchAuthor(currentName.getBasionymAuthorship(), firstSynonym.getCombinationAuthorship())){
510
                    logger.info(line + "Current basionym author and first synonym combination author do not match: " + currentName.getTitleCache() + "<->" + firstSynonym.getTitleCache());
511
                }
512
            }else{
513
                if (! matchAuthor(currentName.getCombinationAuthorship(), firstSynonym.getBasionymAuthorship())){
514
                    logger.info(line + "Current combination author and first synonym basionym author do not match: " + currentName.getTitleCache() + "<->" + firstSynonym.getTitleCache());
515
                }
516
            }
517
        }
518

  
519
    }
520

  
521

  
522
    /**
523
     * @param synonymStr
524
     * @return
525
     */
526
    private boolean isSpecialHeterotypic(String synonymStr) {
527
        if (synonymStr == null){
528
            return false;
529
        }else if (synonymStr.equals("Rhynchospora prenleloupiana (‘prenteloupiana’) Boeckeler")){
530
            return true;
531
        }else if (synonymStr.equals("Psidium longipes var. orbiculare (O.Berg) McVaugh")){
532
            return true;
533
        }
534
        return false;
535
    }
536

  
537

  
538
    /**
539
     * @param areaKey
540
     * @param record
541
     * @param state
542
     * @param taxon
543
     */
544
    private void makeSingleProvinceDistribution(String areaKey,
545
            HashMap<String, String> record,
546
            CubaImportState state) {
547
        try {
548
            UUID areaUuid = state.getTransformer().getNamedAreaUuid(areaKey);
549
            if (areaUuid == null){
550
                logger.warn("Area not recognized: " + areaKey);
551
                return;
552
            }
553
            if (record.get(areaKey)==null){
554
                return; //no status defined
555
            }
556

  
557
            NamedArea area = getNamedArea(state, areaUuid, null, null, null, null, null);
558
            if (area == null){
559
                logger.warn(state.getCurrentLine() + ": Area not recognized: " + area);
560
            }
561
            TaxonDescription desc = getTaxonDescription(state.getCurrentTaxon(), false, true);
562
            PresenceAbsenceTerm status =  makeProvinceStatus(areaKey, record, state);
563
            if (status == null){
564
                logger.warn(state.getCurrentLine() + ": Province distribution status could not be defined: " + record.get(areaKey));
565
            }
566
            Distribution distribution = Distribution.NewInstance(area, status);
567
            desc.addElement(distribution);
568
            distribution.addSource(makeDescriptionSource(state));
569
        } catch (UndefinedTransformerMethodException e) {
570
            e.printStackTrace();
571
        }
572

  
573
    }
433 574

  
434 575

  
435 576
    /**
......
441 582
     * @param taxon
442 583
     * @param homotypicalGroup
443 584
     */
444
    private void handleHomotypicGroup(String homotypicStr,
585
    private List<BotanicalName> handleHomotypicGroup(String homotypicStrOrig,
445 586
            CubaImportState state,
446 587
            BotanicalName homotypicName,
447 588
            boolean isHeterotypic,
......
449 590
            String homonymPart,
450 591
            boolean isDoubtful) {
451 592

  
593
        List<BotanicalName> homotypicNameList = new ArrayList<>();
594
        homotypicNameList.add(homotypicName);
595

  
596
        String homotypicStr = homotypicStrOrig;
452 597
        if (homotypicStr == null){
453
            return;
598
            return homotypicNameList;
454 599
        }else if (homotypicStr.startsWith("(") && homotypicStr.endsWith("")){
455 600
            homotypicStr = homotypicStr.substring(1, homotypicStr.length() - 1);
456 601
        }
457 602

  
458
        BotanicalName currentBasionym = homotypicName;
603
        HomotypicalGroup homotypicGroup = homotypicName.getHomotypicalGroup();
459 604
        String[] splits = homotypicStr.split("\\s*,\\s*");
460 605
        for (String split : splits){
461 606
            split = replaceHomonIlleg(split);
462 607
            boolean isHomonym = split.matches(".*" + HOMONYM_MARKER);
463
            BotanicalName newName = makeName(split);
608
            BotanicalName newName = makeName(state, split);
609
            newName.setHomotypicalGroup(homotypicGroup);  //not really necessary as this is later set anyway
464 610
            if (newName.isProtectedTitleCache()){
465 611
                logger.warn(state.getCurrentLine() + ": homotypic name part could not be parsed: " + split);
466 612
            }
......
468 614
                homonyms.add(newName);
469 615
            }
470 616
            if (isHeterotypic){
471
                SynonymRelationship sr = state.getCurrentTaxon().addHeterotypicSynonymName(newName, homotypicName.getHomotypicalGroup(), null, null);
617
                SynonymRelationship sr = state.getCurrentTaxon().addHeterotypicSynonymName(newName, homotypicGroup, null, null);
472 618
                sr.getSynonym().setDoubtful(isDoubtful);
619
                sr.getSynonym().addSource(makeOriginalSource(state));
473 620
//                newName.addBasionym(homotypicName);
474
                currentBasionym = handleBasionym(currentBasionym, newName);
475 621
            }else{
476 622
                state.getCurrentTaxon().addHomotypicSynonymName(newName, null, null);
477
                handleBasionym(currentBasionym, newName);
478 623
            }
624
            handleBasionym(state, homotypicNameList, homonyms, newName);
625
            homotypicNameList.add(newName);
479 626
        }
480
        makeHomonyms(homonyms, homonymPart, state, currentBasionym);
627
        makeHomonyms(homonyms, homonymPart, state, homotypicGroup);
628
        return homotypicNameList;
481 629
    }
482 630

  
483 631

  
......
498 646
     * @param currentBasionym
499 647
     */
500 648
    private void makeHomonyms(List<BotanicalName> homonyms, String homonymPartOrig, CubaImportState state,
501
            BotanicalName currentBasionym) {
649
            HomotypicalGroup homotypicGroup) {
502 650
        String line = state.getCurrentLine() + ": ";
503 651
        String homonymPart = homonymPartOrig == null ? "" : homonymPartOrig.trim();
504 652
        if (homonyms.isEmpty() && homonymPart.equals("")){
......
511 659
        String[] splits = homonymPart.split("\\]\\s*\\[");
512 660
        if (splits.length != homonyms.size()){
513 661
            if(homonyms.size() == 0 && splits.length >= 1){
514
                handleSimpleBlockingNames(splits, state, currentBasionym);
662
                handleSimpleBlockingNames(splits, state, homotypicGroup);
515 663
            }else{
516 664
                logger.warn(line + "Number of homonyms (" + homonyms.size() + ") and homonymParts ("+splits.length+") does not match");
517 665
            }
......
520 668
        int i = 0;
521 669
        for (String split : splits){
522 670
            split = split.replaceAll("^non\\s+", "");
523
            BotanicalName newName = makeName(split);
671
            BotanicalName newName = makeName(state, split);
524 672
//            BotanicalName newName = (BotanicalName)nameParser.parseReferencedName(split, state.getConfig().getNomenclaturalCode(), Rank.SPECIES());
525 673
            if (newName.isProtectedTitleCache()){
526 674
                logger.warn(state.getCurrentLine() + ": homonym name could not be parsed: " + split);
527 675
            }
528
            newName.addRelationshipToName(homonyms.get(i), NameRelationshipType.LATER_HOMONYM(), null);
676
            homonyms.get(i).addRelationshipToName(newName, NameRelationshipType.LATER_HOMONYM(), null);
529 677
            i++;
530 678
        }
531 679
    }
532 680

  
533

  
534 681
    /**
535 682
     * @param homonymPart
536 683
     * @param state
537
     * @param currentBasionym
684
     * @param homotypicGroup
538 685
     */
539
    private void handleSimpleBlockingNames(String[] splitsi, CubaImportState state,
540
            BotanicalName currentBasionym) {
686
    private void handleSimpleBlockingNames(String[] splitsi,
687
            CubaImportState state,
688
            HomotypicalGroup homotypicGroup) {
689
        List<BotanicalName> replacementNameCandidates = new ArrayList<>();
541 690
        for (String spliti : splitsi){
542 691

  
543 692
            String split = spliti.replaceAll("^non\\s+", "");
544
            BotanicalName newName = makeName(split);
693
            BotanicalName newName = makeName(state, split);
545 694
            if (newName.isProtectedTitleCache()){
546 695
                logger.warn(state.getCurrentLine() + ": blocking name could not be parsed: " + split);
547 696
            }
548
            Set<BotanicalName> typifiedNames = (Set)currentBasionym.getHomotypicalGroup().getTypifiedNames();
697
            Set<BotanicalName> typifiedNames = (Set)homotypicGroup.getTypifiedNames();
549 698
            Set<BotanicalName> candidates = new HashSet<>();
550 699
            for (BotanicalName name : typifiedNames){
551 700
                if (name.getGenusOrUninomial() != null && name.getGenusOrUninomial().equals(newName.getGenusOrUninomial())){
......
555 704
                }
556 705
            }
557 706
            if (candidates.size() == 1){
558
                newName.addRelationshipToName(candidates.iterator().next(), NameRelationshipType.BLOCKING_NAME_FOR(), null);
707
                BotanicalName blockedName = candidates.iterator().next();
708
                newName.addRelationshipToName(blockedName, NameRelationshipType.BLOCKING_NAME_FOR(), null);
709
                replacementNameCandidates.add(blockedName);
559 710
            }else{
560 711
                logger.warn(state.getCurrentLine() + ": Blocking name could not be handled. " + candidates.size() + " candidates.");
561 712
            }
562 713
        }
714
        makeReplacedSynonymIfPossible(state, homotypicGroup, replacementNameCandidates);
715
    }
716

  
717
    /**
718
     * @param homotypicGroup
719
     * @param replacementNameCandidates
720
     */
721
    private void makeReplacedSynonymIfPossible(CubaImportState state,
722
            HomotypicalGroup homotypicGroup,
723
            List<BotanicalName> replacementNameCandidates) {
724
        String line = state.getCurrentLine() +": ";
725
        List<BotanicalName> replacedCandidates = new ArrayList<>();
726
        for (TaxonNameBase<?, ?> typifiedName : homotypicGroup.getTypifiedNames()){
727
            BotanicalName candidate = (BotanicalName)typifiedName;
728
            if (candidate.getBasionymAuthorship() == null){
729
                if (candidate.getStatus().isEmpty()){
730
                    if (! replacementNameCandidates.contains(candidate)){
731
                        replacedCandidates.add(candidate);
732
                    }
733
                }
734
            }
735
        }
736
        if (replacedCandidates.size() == 1){
737
            BotanicalName replacedSynonym = replacedCandidates.iterator().next();
738
            for (BotanicalName replacementName : replacementNameCandidates){
739
                replacementName.addReplacedSynonym(replacedSynonym, null, null, null);
740
            }
741
        }else if (replacedCandidates.size() < 1){
742
            logger.warn(line + "No replaced synonym candidate found");
743
        }else{
744
            logger.warn(line + "More than 1 ("+replacedCandidates.size()+") replaced synonym candidates found");
745
        }
563 746
    }
564 747

  
565 748

  
566 749
    /**
750
     * @param homotypicGroup
567 751
     * @param newName
568
     * @param homotypicName
752
     */
753
    private void handleBasionym(CubaImportState state, List<BotanicalName> homotypicNameList,
754
            List<BotanicalName> homonyms, BotanicalName newName) {
755
        for (BotanicalName existingName : homotypicNameList){
756
            if (existingName != newName){  //should not happen anymore, as new name is added later
757
                boolean onlyIfNotYetExists = true;
758
                createBasionymRelationIfPossible(state, existingName, newName, homonyms.contains(newName), onlyIfNotYetExists);
759
            }
760
        }
761
    }
762

  
763
    /**
764
     * @param state
765
     * @param name1
766
     * @param name2
569 767
     * @return
570 768
     */
571
    private BotanicalName handleBasionym(BotanicalName currentBasionym, BotanicalName name2) {
572
        BotanicalName basionymName = currentBasionym;
769
    private void createBasionymRelationIfPossible(CubaImportState state, BotanicalName name1, BotanicalName name2,
770
            boolean name2isHomonym, boolean onlyIfNotYetExists) {
771
        BotanicalName basionymName = name1;
573 772
        BotanicalName newCombination = name2;
574
        //switch if necessary
575
        if (basionymName.getBasionymAuthorship() != null && newCombination.getBasionymAuthorship() == null){
773
        //exactly one name must have a basionym author
774
        if (name1.getBasionymAuthorship() == null && name2.getBasionymAuthorship() == null
775
                || name1.getBasionymAuthorship() != null && name2.getBasionymAuthorship() != null){
776
            return;
777
        }
778

  
779
        //switch order if necessary
780
        if (! name2isHomonym && basionymName.getBasionymAuthorship() != null && newCombination.getBasionymAuthorship() == null){
576 781
            basionymName = name2;
577
            newCombination = currentBasionym;
782
            newCombination = name1;
783
        }
784
        if (matchAuthor(basionymName.getCombinationAuthorship(), newCombination.getBasionymAuthorship())
785
                && matchLastNamePart(basionymName, newCombination)){
786
            newCombination.addBasionym(basionymName);
787
        }else{
788
            if ( (newCombination.getBasionyms().isEmpty() || ! onlyIfNotYetExists)
789
                    && isLegitimate(basionymName)
790
                    && ! name2isHomonym){
791
                logger.info(state.getCurrentLine() + ": Names are potential basionyms but either author or name part do not match: " + basionymName.getTitleCache() + " <-> " + newCombination.getTitleCache());
792
            }
578 793
        }
579
//        newCombination.getHomotypicalGroup().removeGroupBasionym(xxx);
580
        if (matchAuthor(basionymName.getCombinationAuthorship(), newCombination.getBasionymAuthorship())){
581
            newCombination.getHomotypicalGroup().setGroupBasionym(basionymName);
794
    }
795

  
796
    /**
797
     * @param basionymName
798
     * @return
799
     */
800
    private boolean isLegitimate(BotanicalName basionymName) {
801
        for (NomenclaturalStatus nomStatus : basionymName.getStatus()){
802
            if (nomStatus.getType()!= null && nomStatus.getType().isIllegitimateType()){
803
                    return false;
804
            }
805
        }
806
        for (NameRelationship nameRel : basionymName.getNameRelations()){
807
            if (nameRel.getType()!= null && nameRel.getType().isIllegitimateType()){
808
                    return false;
809
            }
582 810
        }
583
        return basionymName;
811
        return true;
812
    }
813

  
814

  
815
    /**
816
     * @param basionymName
817
     * @param newCombination
818
     * @return
819
     */
820
    private boolean matchLastNamePart(BotanicalName name1, BotanicalName name2) {
821
        String lastNamePart1 = name1.getLastNamePart();
822
        String lastNamePart2 = name2.getLastNamePart();
823
        if (lastNamePart1 != null && lastNamePart2 != null){
824
            lastNamePart1 = normalizeBasionymNamePart(lastNamePart1);
825
            lastNamePart2 = normalizeBasionymNamePart(lastNamePart2);
826
            return (lastNamePart1.equals(lastNamePart2));
827
        }else{
828
            return false;
829
        }
830
    }
831

  
832
    /**
833
     * @param lastNamePart1
834
     * @return
835
     */
836
    private String normalizeBasionymNamePart(String lastNamePart) {
837
        String namePart = lastNamePart.toLowerCase()
838
                .replaceAll("(um|us|a|is|e|os|on|or)$", "")
839
                .replaceAll("er$", "r")    //e.g. ruber <-> rubra
840
                .replaceAll("ese$", "s");  //e.g.  cayanensis <-> cayanenese
841
                //TODO tampensis / tampense
842
        return namePart;
584 843
    }
585 844

  
586 845

  
......
627 886
        if (taxonStr == null){
628 887
            return isSynonym ? state.getCurrentTaxon() : null;
629 888
        }
889

  
630 890
        boolean isAbsent = false;
631 891
        if (taxonStr.startsWith("[") && taxonStr.endsWith("]")){
632 892
            taxonStr = taxonStr.substring(1, taxonStr.length() - 1);
633 893
            isAbsent = true;
634 894
        }
635 895

  
636
        BotanicalName botanicalName = makeName(taxonStr);
896
        boolean isAuct = false;
897
        if (taxonStr.endsWith("auct.")){
898
            isAuct = true;
899
            taxonStr.replace("auct.", "").trim();
900
        }
901
        state.setTaxonIsAbsent(isAbsent);
902
        BotanicalName botanicalName = makeName(state, taxonStr);
637 903
        Reference<?> sec = getSecReference(state);
638 904
        Taxon taxon = Taxon.NewInstance(botanicalName, sec);
905
        if (isAuct){
906
            taxon.setAppendedPhrase("auct.");
907
        }
908

  
639 909
        TaxonNode higherNode;
640 910
        if (botanicalName.isProtectedTitleCache()){
641 911
            logger.warn(state.getCurrentLine() + ": Taxon could not be parsed: " + taxonStr);
......
647 917
                higherNode = genus.getTaxonNodes().iterator().next();
648 918
            }else{
649 919
                BotanicalName name = BotanicalName.NewInstance(Rank.GENUS());
920
                name.addSource(makeOriginalSource(state));
650 921
                name.setGenusOrUninomial(genusStr);
651 922
                genus = Taxon.NewInstance(name, sec);
923
                genus.addSource(makeOriginalSource(state));
652 924
                higherNode = familyNode.addChildTaxon(genus, null, null);
653 925
                state.putHigherTaxon(genusStr, genus);
654 926
            }
655 927
        }
656 928

  
657 929
        higherNode.addChildTaxon(taxon, null, null);
930
        taxon.addSource(makeOriginalSource(state));
658 931

  
659 932
        return taxon;
660 933
    }
......
665 938
     * @param taxonStr
666 939
     * @return
667 940
     */
668
    private BotanicalName makeName(String nameStrOrig) {
941
    private BotanicalName makeName(CubaImportState state, String nameStrOrig) {
669 942
        //normalize
670 943
        String nameStr = normalizeStatus(nameStrOrig);
671 944
        //orthVar
......
675 948
            orthVar = orthVarMatcher.group(1);
676 949
            nameStr = nameStr.replace(" " + orthVar, "").trim().replaceAll("\\s{2,}", " ");
677 950
            orthVar = orthVar.substring(2, orthVar.length() - 2);
951
        }
678 952

  
953
        boolean isNomInval = false;
954
        if (nameStr.endsWith("nom. inval.")){
955
            isNomInval = true;
956
            nameStr = nameStr.replace("nom. inval.", "").trim();
679 957
        }
958

  
680 959
        BotanicalName result = (BotanicalName)nameParser.parseReferencedName(nameStr, nc, Rank.SPECIES());
960
        result.addSource(makeOriginalSource(state));
961
        if (isNomInval){
962
            result.addStatus(NomenclaturalStatus.NewInstance(NomenclaturalStatusType.INVALID()));
963
        }
681 964
        if (orthVar != null){
682 965
            BotanicalName orthVarName = (BotanicalName)result.clone();
966
            orthVarName.addSource(makeOriginalSource(state));
683 967
            //TODO
684 968
            Reference<?> citation = null;
685 969
            orthVarName.addRelationshipToName(result, NameRelationshipType.ORTHOGRAPHIC_VARIANT(), citation, null, null);
686 970
            orthVarName.setSpecificEpithet(orthVar);
687 971
        }
972
        normalizeAuthors(result);
688 973
        return result;
689 974

  
690 975
    }
691 976

  
977
    /**
978
     * @param result
979
     */
980
    private void normalizeAuthors(BotanicalName result) {
981
        result.setCombinationAuthorship(normalizeAuthor(result.getCombinationAuthorship()));
982
        result.setExCombinationAuthorship(normalizeAuthor(result.getExCombinationAuthorship()));
983
        result.setExBasionymAuthorship(normalizeAuthor(result.getExBasionymAuthorship()));
984
        result.setBasionymAuthorship(normalizeAuthor(result.getBasionymAuthorship()));
985

  
986
    }
987

  
988

  
989
    /**
990
     * @param combinationAuthorship
991
     * @return
992
     */
993
    private TeamOrPersonBase<?> normalizeAuthor(TeamOrPersonBase<?> author) {
994
        if (author == null){
995
            return null;
996
        }
997
        TeamOrPersonBase<?> result;
998
        if (author.isInstanceOf(Person.class)){
999
            result = normalizePerson(CdmBase.deproxy(author, Person.class));
1000
        }else{
1001
            Team team = CdmBase.deproxy(author, Team.class);
1002
            List<Person> list = team.getTeamMembers();
1003
            for(int i = 0; i < list.size(); i++){
1004
                Person person = list.get(i);
1005
                Person tmpMember = normalizePerson(person);
1006
                list.set(i, tmpMember);
1007
            }
1008
            return team;
1009
        }
1010
        return result;
1011
    }
1012

  
1013

  
1014
    /**
1015
     * @param deproxy
1016
     * @return
1017
     */
1018
    private Person normalizePerson(Person person) {
1019
        String title = person.getNomenclaturalTitle();
1020
        title = title.replaceAll("(?<=[a-zA-Z])\\.(?=[a-zA-Z])", ". ");
1021
        person.setNomenclaturalTitle(title);
1022
        boolean isFilius = title.endsWith(" f.");
1023
        if (isFilius){
1024
            title.replace(" f.", "");
1025
        }
1026

  
1027
        String[] splits = title.split("\\s+");
1028
        int nNotFirstName = isFilius ? 2 : 1;
1029
        person.setLastname(splits[splits.length - nNotFirstName] + (isFilius? " f." : ""));
1030
        person.setFirstname(CdmUtils.concat(" ", Arrays.copyOfRange(splits, 0, splits.length-nNotFirstName)));
1031
        return person;
1032
    }
1033

  
1034

  
692 1035
    /**
693 1036
     * @param state
694 1037
     * @return
......
739 1082
        if (familyStr == null){
740 1083
            return null;
741 1084
        }
1085
        familyStr = familyStr.trim();
1086
        String alternativeFamilyStr = null;
1087
        if (familyStr.contains("/")){
1088
            String[] splits = familyStr.split("/");
1089
            if (splits.length > 2){
1090
                logger.warn(state.getCurrentLine() +": " + "More than 1 alternative name:" + familyStr);
1091
            }
1092
            familyStr = splits[0].trim();
1093
            alternativeFamilyStr = splits[1].trim();
1094
        }
1095

  
742 1096
        Taxon family = state.getHigherTaxon(familyStr);
743 1097
        TaxonNode familyNode;
744 1098
        if (family != null){
745 1099
            familyNode = family.getTaxonNodes().iterator().next();
746 1100
        }else{
747
            BotanicalName name = state.getFamilyName(familyStr);
748
            if (name == null){
749
                name = BotanicalName.NewInstance(Rank.FAMILY());
750
                name.setGenusOrUninomial(familyStr);
751
                state.putFamilyName(familyStr, name);
752
            }
1101
            BotanicalName name = makeFamilyName(state, familyStr);
753 1102
            Reference<?> sec = getSecReference(state);
754
            Taxon taxon = Taxon.NewInstance(name, sec);
1103
            family = Taxon.NewInstance(name, sec);
755 1104
            ITaxonTreeNode rootNode = getClassification(state);
756
            familyNode = rootNode.addChildTaxon(taxon, sec, null);
757
            state.putHigherTaxon(familyStr, taxon);
1105
            familyNode = rootNode.addChildTaxon(family, sec, null);
1106
            state.putHigherTaxon(familyStr, family);
1107

  
1108
        }
1109

  
1110
        if (isNotBlank(alternativeFamilyStr)){
1111
            NameRelationshipType type = NameRelationshipType.ALTERNATIVE_NAME();
1112
            BotanicalName alternativeName = makeFamilyName(state, alternativeFamilyStr);
1113
            BotanicalName familyName = (BotanicalName)family.getName();
1114
            boolean hasRelation = false;
1115
            for (NameRelationship nameRel : familyName.getRelationsToThisName()){
1116
                if (nameRel.getType().equals(type)){
1117
                    if (nameRel.getFromName().equals(alternativeName)){
1118
                        hasRelation = true;
1119
                    }
1120
                }
1121
            }
1122
            if (!hasRelation){
1123
                familyName.addRelationshipFromName(alternativeName, type, null);
1124
            }
1125

  
758 1126
        }
759 1127

  
760 1128
        return familyNode;
761 1129
    }
762 1130

  
1131

  
1132
    /**
1133
     * @param state
1134
     * @param taxon
1135
     */
1136
    private void validateTaxonIsAbsent(CubaImportState state, Taxon taxon) {
1137
        if (!state.isTaxonIsAbsent()){
1138
            return;
1139
        }
1140

  
1141
        for (DescriptionElementBase el : taxon.getDescriptions().iterator().next().getElements()){
1142
            if (el instanceof Distribution){
1143
                Distribution dist = (Distribution)el;
1144
                NamedArea area = dist.getArea();
1145
                if (isCubanArea(area)){
1146
                    PresenceAbsenceTerm status = dist.getStatus();
1147
                    if (status != null && !status.isAbsenceTerm()){
1148
                        if (!isDoubtfulTerm(status)){
1149
                            String name = taxon.getName().getTitleCache();
1150
                            logger.error(state.getCurrentLine() +": Taxon ("+name+")is absent'[]' but has presence distribution: " + status.getTitleCache());
1151
                            return;
1152
                        }
1153
                    }
1154
                }
1155
            }
1156
        }
1157
    }
1158

  
1159
    /**
1160
     * @param state
1161
     * @param taxon
1162
     */
1163
    private void validateEndemic(CubaImportState state, Taxon taxon) {
1164

  
1165
        boolean hasExternalPresence = false;
1166
        for (DescriptionElementBase el : taxon.getDescriptions().iterator().next().getElements()){
1167
            if (el instanceof Distribution){
1168
                Distribution dist = (Distribution)el;
1169
                NamedArea area = dist.getArea();
1170
                if (!isCubanArea(area)){
1171
                    PresenceAbsenceTerm status = dist.getStatus();
1172
                    if (status != null && !status.isAbsenceTerm()){
1173
                        if (!isDoubtfulTerm(status)){
1174
                            hasExternalPresence = true;
1175
                            if (state.isEndemic()){
1176
                                String name = taxon.getName().getTitleCache();
1177
                                logger.error(state.getCurrentLine() +": Taxon ("+name+")is endemic but has non-cuban distribution: " + area.getIdInVocabulary() + "-" + status.getIdInVocabulary());
1178
                                return;
1179
                            }
1180
                        }
1181
                    }
1182
                }
1183
            }
1184
        }
1185
        if (!state.isEndemic() && ! hasExternalPresence){
1186
            String name = taxon.getName().getTitleCache();
1187
            logger.error(state.getCurrentLine() +": Taxon ("+name+")is not endemic but has no non-cuban distribution" );
1188
        }
1189
    }
1190

  
1191

  
763 1192
    /**
764 1193
     * @param state
765 1194
     * @param taxon
......
771 1200
        String key = famRef.getTitle() + ":"+ famStr;
772 1201
        Taxon family = state.getHigherTaxon(key);
773 1202
        if (family == null){
774
            BotanicalName name = state.getFamilyName(famStr);
775
            if (name == null){
776
                name = BotanicalName.NewInstance(Rank.FAMILY());
777
                name.setGenusOrUninomial(famStr);
778
                state.putFamilyName(famStr, name);
779
            }
1203
            BotanicalName name = makeFamilyName(state, famStr);
780 1204
            family = Taxon.NewInstance(name, famRef);
781 1205
            state.putHigherTaxon(key, family);
782 1206
        }
......
785 1209
    }
786 1210

  
787 1211

  
1212
    /**
1213
     * @param state
1214
     * @param famStr
1215
     * @return
1216
     */
1217
    private BotanicalName makeFamilyName(CubaImportState state, String famStr) {
1218
        BotanicalName name = state.getFamilyName(famStr);
1219
        if (name == null){
1220
            name = BotanicalName.NewInstance(Rank.FAMILY());
1221
            name.setGenusOrUninomial(famStr);
1222
            state.putFamilyName(famStr, name);
1223
            name.addSource(makeOriginalSource(state));
1224
        }
1225
        return name;
1226
    }
1227

  
1228

  
788 1229
    /**
789 1230
     * @param state
790 1231
     * @return
......
847 1288
	 */
848 1289
	@Override
849 1290
    protected void firstPass(CubaImportState state) {
850
	    boolean isSynonym = false;
1291
	    boolean isSynonymOnly = false;
851 1292

  
852 1293
        String line = state.getCurrentLine() + ": ";
853 1294
        HashMap<String, String> record = state.getOriginalRecord();
......
874 1315
                logger.warn(line + "Family not recognized but also no synonym exists");
875 1316
                return;
876 1317
            }else{
877
                isSynonym = true;
1318
                isSynonymOnly = true;
878 1319
            }
879 1320
        }
880 1321

  
881

  
882

  
883
        //Taxón
884
        Taxon taxon = makeTaxon(record, state, familyTaxon, isSynonym);
885
        if (taxon == null && ! isSynonym){
1322
       //Taxón
1323
        Taxon taxon = makeTaxon(record, state, familyTaxon, isSynonymOnly);
1324
        if (taxon == null && ! isSynonymOnly){
886 1325
            logger.warn(line + "taxon could not be created and is null");
887 1326
            return;
888 1327
        }
......
895 1334
        makeNotes(record, state);
896 1335

  
897 1336
        //Syn.
898
        makeSynonyms(record, state);
1337
        makeSynonyms(record, state, !isSynonymOnly);
899 1338

  
900 1339
        //End, Ind, Ind? D, Nat N, Dud P, Adv A, Cult C
901 1340
        makeCubanDistribution(record, state);
......
910 1349
//      "AmN","AmC","AmS","VM"});
911 1350
        makeOtherAreasDistribution(record, state);
912 1351

  
1352
        validateTaxonIsAbsent(state, taxon);
1353
        if (!isSynonymOnly){
1354
            validateEndemic(state, taxon);
1355
        }
913 1356

  
914 1357
        state.setHighestStatusForTaxon(null);
915 1358

  
......
917 1360
    }
918 1361

  
919 1362

  
1363
    /**
1364
     * @param state
1365
     * @return
1366
     */
1367
    private IdentifiableSource makeOriginalSource(CubaImportState state) {
1368
        return IdentifiableSource.NewDataImportInstance("line: " + state.getCurrentLine(), null, state.getConfig().getSourceReference());
1369
    }
1370
    /**
1371
     * @param state
1372
     * @return
1373
     */
1374
    private DescriptionElementSource makeDescriptionSource(CubaImportState state) {
1375
        return DescriptionElementSource.NewDataImportInstance("line: " + state.getCurrentLine(), null, state.getConfig().getSourceReference());
1376
    }
1377

  
1378
    private static Set<UUID> doubtfulStatus = new HashSet<>();
920 1379

  
921
	/**
1380
    /**
1381
     * @param status
1382
     * @return
1383
     */
1384
    private boolean isDoubtfulTerm(PresenceAbsenceTerm status) {
1385
        if (doubtfulStatus.isEmpty()){
1386
            doubtfulStatus.add(CubaTransformer.nonNativeDoubtfullyNaturalisedUuid);
1387
            doubtfulStatus.add(CubaTransformer.doubtfulIndigenousDoubtfulUuid);
1388
            doubtfulStatus.add(CubaTransformer.endemicDoubtfullyPresentUuid);
1389
            doubtfulStatus.add(CubaTransformer.naturalisedDoubtfullyPresentUuid);
1390
            doubtfulStatus.add(CubaTransformer.nonNativeDoubtfullyPresentUuid);
1391
            doubtfulStatus.add(CubaTransformer.occasionallyCultivatedUuid);
1392
            doubtfulStatus.add(CubaTransformer.rareCasualUuid);
1393
            doubtfulStatus.add(PresenceAbsenceTerm.NATIVE_PRESENCE_QUESTIONABLE().getUuid());
1394
            doubtfulStatus.add(PresenceAbsenceTerm.CULTIVATED_PRESENCE_QUESTIONABLE().getUuid());
1395
        }
1396
        boolean isDoubtful = doubtfulStatus.contains(status.getUuid());
1397
        return isDoubtful;
1398
    }
1399

  
1400

  
1401
    /**
1402
     * @param area
1403
     * @return
1404
     */
1405
    private boolean isCubanArea(NamedArea area) {
1406
        if (area.getUuid().equals(CubaTransformer.uuidCuba)){
1407
            return true;
1408
        }else if (area.getPartOf()!= null){
1409
            return isCubanArea(area.getPartOf());
1410
        }else{
1411
            return false;
1412
        }
1413
    }
1414

  
1415

  
1416
    /**
922 1417
     * @param record
923 1418
     * @param state
924 1419
     * @param familyTaxon
......
1041 1536
    }
1042 1537

  
1043 1538

  
1044
    /**
1045
     * @param areaKey
1046
     * @param record
1047
     * @param state
1048
     * @param taxon
1049
     */
1050
    private void makeSingleProvinceDistribution(String areaKey,
1051
            HashMap<String, String> record,
1052
            CubaImportState state) {
1053
        try {
1054
            UUID areaUuid = state.getTransformer().getNamedAreaUuid(areaKey);
1055
            if (areaUuid == null){
1056
                logger.warn("Area not recognized: " + areaKey);
1057
                return;
1058
            }
1059
            if (record.get(areaKey)==null){
1060
                return; //no status defined
1061
            }
1062

  
1063
            NamedArea area = getNamedArea(state, areaUuid, null, null, null, null, null);
1064
            if (area == null){
1065
                logger.warn(state.getCurrentLine() + ": Area not recognized: " + area);
1066
            }
1067
            TaxonDescription desc = getTaxonDescription(state.getCurrentTaxon(), false, true);
1068
            PresenceAbsenceTerm status =  makeProvinceStatus(areaKey, record, state);
1069
            if (status == null){
1070
                logger.warn(state.getCurrentLine() + ": Province distribution status could not be defined: " + record.get(areaKey));
1071
            }
1072
            Distribution distribution = Distribution.NewInstance(area, status);
1073
            desc.addElement(distribution);
1074
        } catch (UndefinedTransformerMethodException e) {
1075
            e.printStackTrace();
1076
        }
1077

  
1078
    }
1079 1539

  
1080 1540

  
1081 1541
    /**
......
1093 1553
        String statusStr = record.get(areaKey);
1094 1554
        if (statusStr == null){
1095 1555
            return null;
1556
        }else{
1557
            statusStr = statusStr.trim();
1096 1558
        }
1097 1559
        PresenceAbsenceTerm status = state.getTransformer().getPresenceTermByKey(statusStr);
1098 1560
        if (status == null){
1099
            PresenceAbsenceTerm highestStatus = state.getHighestStatusForTaxon();
1561
//            PresenceAbsenceTerm highestStatus = state.getHighestStatusForTaxon();
1100 1562
            if (state.isCubanProvince() && isMinus(statusStr)){
1101
                getAbsenceTermForStatus(state, highestStatus);
1563
//                getAbsenceTermForStatus(state, highestStatus);
1564
                //we now handle cuban provinces same as external regions
1565
                status = state.getTransformer().getPresenceTermByKey("--");
1102 1566
            }else if (! state.isCubanProvince() && isMinus(statusStr)){
1103 1567
                status = state.getTransformer().getPresenceTermByKey("--");
1104 1568
            }else{
1569
//                logger.warn("Unhandled status str for provinces / external regions: " + statusStr);
1105 1570
                UUID statusUuid = state.getTransformer().getPresenceTermUuid(statusStr);
1106
                status = getPresenceTerm(state, statusUuid, null, null, null, false);
1571
                if (statusUuid == null){
1572
                    logger.error(state.getCurrentLine() + ": Undefined status str for provinces / external regions. No UUID given: '" + statusStr + "'");
1573
                }else{
1574
                    status = getPresenceTerm(state, statusUuid, statusStr, statusStr, statusStr, false);
1575
                }
1107 1576
            }
1108 1577
        }
1109 1578

  
app-import/src/main/java/eu/etaxonomy/cdm/io/cuba/CubaImportState.java
39 39

  
40 40
	private final Map<String, BotanicalName> familyNameMap = new HashMap<String, BotanicalName>();
41 41

  
42

  
43

  
44 42
	//classification
45 43
	private Classification classification;
46 44
    public Classification getClassification() {return classification;}
......
68 66
    public void setCubanProvince(boolean cubanProvince) {this.isCubanProvince = cubanProvince;}
69 67
    public boolean isCubanProvince(){return isCubanProvince;}
70 68

  
69
    private boolean taxonIsAbsent = false;
70
    public boolean isTaxonIsAbsent(){return this.taxonIsAbsent;}
71
    public void setTaxonIsAbsent(boolean taxonIsAbsent) {this.taxonIsAbsent = taxonIsAbsent;}
72

  
73
    private boolean isEndemic = false;
74
    public boolean isEndemic(){return this.isEndemic;}
75
    public void setEndemic(boolean isEndemic) {this.isEndemic = isEndemic;}
76

  
71 77
    //Constructor
72 78
    public CubaImportState(CubaImportConfigurator config) {
73 79
		super(config);
......
122 128

  
123 129

  
124 130

  
131

  
125 132
}
app-import/src/main/java/eu/etaxonomy/cdm/io/cuba/CubaTransformer.java
17 17

  
18 18
import eu.etaxonomy.cdm.io.common.mapping.InputTransformerBase;
19 19
import eu.etaxonomy.cdm.io.common.mapping.UndefinedTransformerMethodException;
20
import eu.etaxonomy.cdm.io.cyprus.CyprusTransformer;
21 20
import eu.etaxonomy.cdm.model.description.PresenceAbsenceTerm;
22 21

  
23 22
/**
......
40 39
    public static final UUID uuidAlternativeFamily2 = UUID.fromString("ff15b54a-6785-4ba0-acb6-8fb2eab80a6a");
41 40

  
42 41
    //presenceTerm
43
    public static final UUID nonNativeDoubtfullyNaturalisedUuid = UUID.fromString("a1e26234-831e-4190-9fe3-011aca09ddba");
44
    public static final UUID adventiveAlienUuid = UUID.fromString("06e48a0b-3e48-4ef8-9bdd-0755880e99ce");
45
    public static final UUID cultivatedOnlyUuid = UUID.fromString("9cca5c3b-aced-41c4-accc-f800b67168f8");
46
    public static final UUID occasionallyCultivatedUuid = UUID.fromString("936c3f9a-6099-4322-9792-0a72c6c2ce25");
47
    public static final UUID doubtfulIndigenousUuid = UUID.fromString("f47f4f4e-9d84-459a-b747-27a1af24ab7a");
48
    public static final UUID doubtfulIndigenousDoubtfulUuid = UUID.fromString("7ddfd94d-01a4-496c-a6d6-18584c00af59");
49

  
50
    public static final UUID doubtfullyEndemicUuid = UUID.fromString("5f954f08-267a-4928-b073-12328f74c187");
51
    public static final UUID doubtfullyNaturalisedUuid = UUID.fromString("9e0b413b-5a68-4e5b-91f2-227b4f832466");
52
    public static final UUID doubtfullyNonNativeUuid = UUID.fromString("c42ca644-1773-4230-a2ee-328a5d4a21ab");
53
    public static final UUID endemicInErrorUuid = UUID.fromString("679b215d-c231-4ee2-ae12-3ffc3dd528ad");
54
    public static final UUID adventiveInErrorUuid = UUID.fromString("9b910b7b-43e3-4260-961c-6063b11cb7dc");
55
    public static final UUID nonNativeInErrorUuid = UUID.fromString("b9153d90-9e31-465a-a28c-79077a8ed4c2");
56
    public static final UUID naturalisedInErrorUuid = UUID.fromString("8d918a37-3add-4e1c-a233-c37dbee209aa");
57

  
58

  
59
//    public static final UUID indigenousUuid = UUID.fromString("b325859b-504b-45e0-9ef0-d5c1602fcc0f");
60
//    public static final UUID casualUuid = UUID.fromString("5e81353c-38a3-4ca6-b979-0d9abc93b877");
61
//    public static final UUID nonInvasiveUuid = UUID.fromString("1b025e8b-901a-42e8-9739-119b410c6f03");
62
//    public static final UUID invasiveUuid = UUID.fromString("faf2d271-868a-4bf7-b0b8-a1c5ab309de2");
63
//    public static final UUID questionableUuid = UUID.fromString("4b48f675-a6cf-49f3-a5ba-77e2c2979eb3");
64
//
65
//    public static final UUID indigenousDoubtfulUuid = UUID.fromString("17bc601f-53eb-4997-a4bc-c03ce5bfd1d3");
66
//    public static final UUID casualDoubtfulUuid = UUID.fromString("73f75493-1185-4a3e-af1e-9a1f2e8dadb7");
67
//    public static final UUID nonInvasiveDoubtfulUuid = UUID.fromString("11f56e2f-c16c-4b3d-a870-bb5d3b20e624");
68
//    public static final UUID invasiveDoubtfulUuid = UUID.fromString("ac429d5f-e8ad-49ae-a41c-e4779b58b96a");
69
//    public static final UUID questionableDoubtfulUuid = UUID.fromString("914e7393-1314-4632-bc45-5eff3dc1e424");
70
//
71
//    public static final UUID cultivatedDoubtfulUuid = UUID.fromString("4f31bfc8-3058-4d83-aea5-3a1fe9773f9f");
42
    protected static final UUID nonNativeDoubtfullyNaturalisedUuid = UUID.fromString("a1e26234-831e-4190-9fe3-011aca09ddba");
43
//    private static final UUID adventiveAlienUuid = UUID.fromString("06e48a0b-3e48-4ef8-9bdd-0755880e99ce");
44
//    private static final UUID cultivatedOnlyUuid = UUID.fromString("9cca5c3b-aced-41c4-accc-f800b67168f8");
45
    protected static final UUID occasionallyCultivatedUuid = UUID.fromString("936c3f9a-6099-4322-9792-0a72c6c2ce25");
46
//    private static final UUID doubtfulIndigenousUuid = UUID.fromString("f47f4f4e-9d84-459a-b747-27a1af24ab7a");
47
    protected static final UUID doubtfulIndigenousDoubtfulUuid = UUID.fromString("7ddfd94d-01a4-496c-a6d6-18584c00af59");
48
    protected static final UUID rareCasualUuid = UUID.fromString("8914ce0d-7d31-4c88-8317-985f2b3a493b");
49

  
50
    protected static final UUID endemicDoubtfullyPresentUuid = UUID.fromString("5f954f08-267a-4928-b073-12328f74c187");
51
    protected static final UUID naturalisedDoubtfullyPresentUuid = UUID.fromString("9e0b413b-5a68-4e5b-91f2-227b4f832466");
52
    protected static final UUID nonNativeDoubtfullyPresentUuid = UUID.fromString("c42ca644-1773-4230-a2ee-328a5d4a21ab");
53
    private static final UUID endemicInErrorUuid = UUID.fromString("679b215d-c231-4ee2-ae12-3ffc3dd528ad");
54
    private static final UUID adventiveInErrorUuid = UUID.fromString("9b910b7b-43e3-4260-961c-6063b11cb7dc");
55
    private static final UUID nonNativeInErrorUuid = UUID.fromString("b9153d90-9e31-465a-a28c-79077a8ed4c2");
56
    private static final UUID naturalisedInErrorUuid = UUID.fromString("8d918a37-3add-4e1c-a233-c37dbee209aa");
57

  
72 58

  
73 59

  
74 60
    //Named Areas
......
163 149
    @Override
164 150
    public UUID getPresenceTermUuid(String key) throws UndefinedTransformerMethodException {
165 151
        if (StringUtils.isBlank(key)){return null;
166
        }else if (key.equalsIgnoreCase("Ind.")){return CyprusTransformer.indigenousUuid;
167
        }else if (key.equalsIgnoreCase("+")){return CyprusTransformer.indigenousUuid;
168
        }else if (key.equalsIgnoreCase("?Ind.")){return CyprusTransformer.indigenousDoubtfulUuid;
169
        }else if (key.equalsIgnoreCase("?")){return CyprusTransformer.indigenousDoubtfulUuid;
170
        }else if (key.equalsIgnoreCase("?Cult.")){return CyprusTransformer.cultivatedDoubtfulUuid;
152
//        }else if (key.equalsIgnoreCase("Ind.")){return CyprusTransformer.indigenousUuid;
153
//        }else if (key.equalsIgnoreCase("+")){return CyprusTransformer.indigenousUuid;
154
//        }else if (key.equalsIgnoreCase("?Ind.")){return CyprusTransformer.indigenousDoubtfulUuid;
155
//        }else if (key.equalsIgnoreCase("?")){return CyprusTransformer.indigenousDoubtfulUuid;
156

  
157
//        }else if (key.equalsIgnoreCase("?Cult.")){return CyprusTransformer.cultivatedDoubtfulUuid;
171 158

  
172 159

  
173
        }else if (key.equalsIgnoreCase("Ind.?")){return doubtfulIndigenousUuid;
174
        }else if (key.equalsIgnoreCase("D")){return doubtfulIndigenousUuid;
175
        }else if (key.equalsIgnoreCase("?Ind.?")){return doubtfulIndigenousUuid;
160
//        }else if (key.equalsIgnoreCase("Ind.?")){return doubtfulIndigenousUuid;
161
//        }else if (key.equalsIgnoreCase("D")){return doubtfulIndigenousUuid;
162
        }else if (key.equalsIgnoreCase("?Ind.?")){return doubtfulIndigenousDoubtfulUuid;
176 163
        }else if (key.equalsIgnoreCase("??")){return doubtfulIndigenousDoubtfulUuid;
177 164

  
178 165
        }else if (key.equalsIgnoreCase("Dud.")){return nonNativeDoubtfullyNaturalisedUuid;
179 166
        }else if (key.equalsIgnoreCase("P")){return nonNativeDoubtfullyNaturalisedUuid;
180 167

  
181
        }else if (key.equalsIgnoreCase("Adv.")){return adventiveAlienUuid;
182
        }else if (key.equalsIgnoreCase("A")){return adventiveAlienUuid;
168
//        }else if (key.equalsIgnoreCase("Adv.")){return adventiveAlienUuid;
169
//        }else if (key.equalsIgnoreCase("A")){return adventiveAlienUuid;
170
        }else if (key.equalsIgnoreCase("(A)")){return rareCasualUuid;
183 171

  
184
        }else if (key.equalsIgnoreCase("Cult.")){return cultivatedOnlyUuid;
185
        }else if (key.equalsIgnoreCase("C")){return cultivatedOnlyUuid;
186 172
        }else if (key.equalsIgnoreCase("(C)")){return occasionallyCultivatedUuid;
187 173

  
188
        }else if (key.equalsIgnoreCase("?E")){return doubtfullyEndemicUuid;
189
        }else if (key.equalsIgnoreCase("?Nat.")){return doubtfullyNaturalisedUuid;
190
        }else if (key.equalsIgnoreCase("?N")){return doubtfullyNaturalisedUuid;
191
        }else if (key.equalsIgnoreCase("?Dud.")){return doubtfullyNonNativeUuid;
192
        }else if (key.equalsIgnoreCase("?P")){return doubtfullyNonNativeUuid;
174
        }else if (key.equalsIgnoreCase("?E")){return endemicDoubtfullyPresentUuid;
175
        }else if (key.equalsIgnoreCase("?Nat.")){return naturalisedDoubtfullyPresentUuid;
176
        }else if (key.equalsIgnoreCase("?N")){return naturalisedDoubtfullyPresentUuid;
177
        }else if (key.equalsIgnoreCase("?Dud.")){return nonNativeDoubtfullyPresentUuid;
178
        }else if (key.equalsIgnoreCase("?P")){return nonNativeDoubtfullyPresentUuid;
193 179
        }else if (key.equalsIgnoreCase("-End.")){return endemicInErrorUuid;
194 180
        }else if (key.equalsIgnoreCase("-E")){return endemicInErrorUuid;
195 181
        }else if (key.equalsIgnoreCase("-Nat.")){return naturalisedInErrorUuid;
......
212 198

  
213 199
        }else if (key.equalsIgnoreCase("E")){return PresenceAbsenceTerm.ENDEMIC_FOR_THE_RELEVANT_AREA();
214 200

  
201
        }else if (key.equalsIgnoreCase("+")){return PresenceAbsenceTerm.NATIVE();
202
        }else if (key.equalsIgnoreCase("Ind.")){return PresenceAbsenceTerm.NATIVE();
203
        }else if (key.equalsIgnoreCase("Ind.?")){return PresenceAbsenceTerm.NATIVE_DOUBTFULLY_NATIVE();
204
        }else if (key.equalsIgnoreCase("D")){return PresenceAbsenceTerm.NATIVE_DOUBTFULLY_NATIVE();
205

  
215 206
        }else if (key.equalsIgnoreCase("-Ind.")){return PresenceAbsenceTerm.NATIVE_REPORTED_IN_ERROR();
207
        }else if (key.equalsIgnoreCase("?Ind.")){return PresenceAbsenceTerm.NATIVE_PRESENCE_QUESTIONABLE();
208
        }else if (key.equalsIgnoreCase("?")){return PresenceAbsenceTerm.NATIVE_PRESENCE_QUESTIONABLE();
209

  
210
        }else if (key.equalsIgnoreCase("Adv.")){return PresenceAbsenceTerm.INTRODUCED_ADVENTITIOUS();
211
        }else if (key.equalsIgnoreCase("A")){return PresenceAbsenceTerm.INTRODUCED_ADVENTITIOUS();
216 212

  
217 213
        }else if (key.equalsIgnoreCase("Nat.")){return PresenceAbsenceTerm.NATURALISED();
218 214
        }else if (key.equalsIgnoreCase("N")){return PresenceAbsenceTerm.NATURALISED();
219 215

  
220 216
        }else if (key.equalsIgnoreCase("Cult.")){return PresenceAbsenceTerm.CULTIVATED();
221 217
        }else if (key.equalsIgnoreCase("C")){return PresenceAbsenceTerm.CULTIVATED();
218
        }else if (key.equalsIgnoreCase("?Cult.")){return PresenceAbsenceTerm.CULTIVATED_PRESENCE_QUESTIONABLE();
222 219

  
223 220
        }else if (key.equalsIgnoreCase("-Cult.")){return PresenceAbsenceTerm.CULTIVATED_REPORTED_IN_ERROR();
221
//        }else if (key.equalsIgnoreCase("-C")){return PresenceAbsenceTerm.CULTIVATED_REPORTED_IN_ERROR();
224 222

  
225 223
        }else if (key.equalsIgnoreCase("--")){return PresenceAbsenceTerm.REPORTED_IN_ERROR();
226 224

  
app-import/src/main/java/eu/etaxonomy/cdm/io/cuba/CubaVocabularyImport.java
130 130

  
... This diff was truncated because it exceeds the maximum size that can be displayed.

Also available in: Unified diff