Bundled error messages for model creation in interface

This commit is contained in:
Stefan Kalscheuer 2017-08-29 20:05:07 +02:00
parent e12775b6ae
commit afffaa4a6f
5 changed files with 93 additions and 55 deletions

View File

@ -1,4 +1,8 @@
## 0.1.1 [2017-01-07]
## 1.1.1 [work in progress]
* [improvement] On connection or parsing errors, the `IOException` is no longer ignored, but encapsulated in `RuntimeException` (no StackTraces printed)
* [internal] Code cleanup and minor improvements
## 1.1.0 [2017-01-07]
* [feature] Filter stops by coordinates and radius
* [feature] Filter trips by destination and and towards fields
* [test] Test coverage 100% (line); tested against ASEAG and TFL APIs

View File

@ -6,7 +6,7 @@
<groupId>de.stklcode.pubtrans</groupId>
<artifactId>juraclient</artifactId>
<version>1.1.0</version>
<version>1.1.1-SNAPSHOT</version>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>

View File

@ -0,0 +1,49 @@
/*
* Copyright 2016-2017 Stefan Kalscheuer
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package de.stklcode.pubtrans.ura.model;
import java.io.IOException;
/**
* @author Stefan Kalscheuer
* @since 1.1.1
*/
interface Model {
/**
* Generate exception for unmatched type when String is expected.
*
* @param field Field number.
* @param actual Actual class.
* @return The Exception.
*/
static IOException typeErrorString(int field, Class actual) {
return typeError(field, actual, "String");
}
/**
* Generate exception for unmatched type.
*
* @param field Field number.
* @param actual Actual class.
* @param expected Expected type.
* @return The Exception.
*/
static IOException typeError(int field, Class actual, String expected) {
return new IOException(String.format("Field %d not of expected type %s, found %s",
field, expected, actual.getSimpleName()));
}
}

View File

@ -24,14 +24,14 @@ import java.util.List;
*
* @author Stefan Kalscheuer
*/
public final class Stop {
private static final int STOP_NAME = 1;
private static final int STOP_ID = 2;
private static final int INDICATOR = 3;
private static final int STATE = 4;
private static final int LATITUDE = 5;
private static final int LONGITUDE = 6;
private static final int NUM_OF_FIELDS = 7;
public final class Stop implements Model {
private static final int F_STOP_NAME = 1;
private static final int F_STOP_ID = 2;
private static final int F_INDICATOR = 3;
private static final int F_STATE = 4;
private static final int F_LATITUDE = 5;
private static final int F_LONGITUDE = 6;
private static final int F_NUM_OF_FIELDS = 7;
private final String id;
private final String name;
@ -71,52 +71,46 @@ public final class Stop {
* @throws IOException Thrown on invalid line format.
*/
public Stop(final List raw) throws IOException {
if (raw == null || raw.size() < NUM_OF_FIELDS) {
if (raw == null || raw.size() < F_NUM_OF_FIELDS) {
throw new IOException("Invalid number of fields");
}
if (raw.get(1) instanceof String) {
name = (String) raw.get(STOP_NAME);
name = (String) raw.get(F_STOP_NAME);
} else {
throw new IOException("Field " + STOP_NAME + " not of expected type String, found "
+ raw.get(STOP_NAME).getClass().getSimpleName());
throw Model.typeErrorString(F_STOP_NAME, raw.get(F_STOP_NAME).getClass());
}
if (raw.get(STOP_ID) instanceof String) {
id = (String) raw.get(STOP_ID);
if (raw.get(F_STOP_ID) instanceof String) {
id = (String) raw.get(F_STOP_ID);
} else {
throw new IOException("Field " + STOP_ID + " not of expected type String, found "
+ raw.get(STOP_ID).getClass().getSimpleName());
throw Model.typeErrorString(F_STOP_ID, raw.get(F_STOP_ID).getClass());
}
if (raw.get(INDICATOR) instanceof String) {
indicator = (String) raw.get(INDICATOR);
} else if (raw.get(INDICATOR) == null) {
if (raw.get(F_INDICATOR) instanceof String) {
indicator = (String) raw.get(F_INDICATOR);
} else if (raw.get(F_INDICATOR) == null) {
indicator = null;
} else {
throw new IOException("Field " + INDICATOR + " not of expected type String, found "
+ raw.get(INDICATOR).getClass().getSimpleName());
} else {
throw Model.typeErrorString(F_INDICATOR, raw.get(F_INDICATOR).getClass());
}
if (raw.get(STATE) instanceof Integer) {
state = (Integer) raw.get(STATE);
if (raw.get(F_STATE) instanceof Integer) {
state = (Integer) raw.get(F_STATE);
} else {
throw new IOException("Field " + STATE + " not of expected type Integer, found "
+ raw.get(STATE).getClass().getSimpleName());
throw Model.typeError(F_STATE, raw.get(F_STATE).getClass(), "Integer");
}
if (raw.get(LATITUDE) instanceof Double) {
latitude = (Double) raw.get(LATITUDE);
if (raw.get(F_LATITUDE) instanceof Double) {
latitude = (Double) raw.get(F_LATITUDE);
} else {
throw new IOException("Field " + LATITUDE + " not of expected type Double, found "
+ raw.get(LATITUDE).getClass().getSimpleName());
throw Model.typeError(F_LATITUDE, raw.get(F_LATITUDE).getClass(), "Double");
}
if (raw.get(LONGITUDE) instanceof Double) {
longitude = (Double) raw.get(LONGITUDE);
if (raw.get(F_LONGITUDE) instanceof Double) {
longitude = (Double) raw.get(F_LONGITUDE);
} else {
throw new IOException("Field " + LONGITUDE + " not of expected type Double, found "
+ raw.get(LONGITUDE).getClass().getSimpleName());
throw Model.typeError(F_LONGITUDE, raw.get(F_LONGITUDE).getClass(), "Double");
}
}

View File

@ -24,7 +24,7 @@ import java.util.List;
*
* @author Stefan Kalscheuer
*/
public final class Trip {
public final class Trip implements Model {
private static final int VISIT_ID = 7;
private static final int LINE_ID = 8;
private static final int LINE_NAME = 9;
@ -161,22 +161,19 @@ public final class Trip {
if (raw.get(VISIT_ID) instanceof Integer) {
visitID = (Integer) raw.get(VISIT_ID);
} else {
throw new IOException("Field " + VISIT_ID + " not of expected type Integer, found "
+ raw.get(VISIT_ID).getClass().getSimpleName());
throw Model.typeError(VISIT_ID, raw.get(VISIT_ID).getClass(), "Integer");
}
if (raw.get(LINE_ID) instanceof String) {
lineID = (String) raw.get(LINE_ID);
} else {
throw new IOException("Field " + LINE_ID + " not of expected type String, found "
+ raw.get(LINE_ID).getClass().getSimpleName());
throw Model.typeErrorString(LINE_ID, raw.get(LINE_ID).getClass());
}
if (raw.get(LINE_NAME) instanceof String) {
lineName = (String) raw.get(LINE_NAME);
} else {
throw new IOException("Field " + LINE_NAME + " not of expected type String, found "
+ raw.get(LINE_NAME).getClass().getSimpleName());
throw Model.typeErrorString(LINE_NAME, raw.get(LINE_NAME).getClass());
}
if (raw.get(DIRECTION_ID) instanceof Integer) {
@ -185,22 +182,19 @@ public final class Trip {
throw new IOException("Direction out of range. Expected 1 or 2, found " + directionID);
}
} else {
throw new IOException("Field " + DIRECTION_ID + " not of expected type Integer, found "
+ raw.get(DIRECTION_ID).getClass().getSimpleName());
throw Model.typeError(DIRECTION_ID, raw.get(DIRECTION_ID).getClass(), "Integer");
}
if (raw.get(DESTINATION_NAME) instanceof String) {
destinationName = (String) raw.get(DESTINATION_NAME);
} else {
throw new IOException("Field " + DESTINATION_NAME + " not of expected type String, found "
+ raw.get(DESTINATION_NAME).getClass().getSimpleName());
throw Model.typeErrorString(DESTINATION_NAME, raw.get(DESTINATION_NAME).getClass());
}
if (raw.get(DESTINATION_TEXT) instanceof String) {
destinationText = (String) raw.get(DESTINATION_TEXT);
} else {
throw new IOException("Field " + DESTINATION_TEXT + " not of expected type String, found "
+ raw.get(DESTINATION_TEXT).getClass().getSimpleName());
throw Model.typeErrorString(DESTINATION_TEXT, raw.get(DESTINATION_TEXT).getClass());
}
/* TFL and ASEAG deliver different types with the same API version, so this field is a little more tolerant */
@ -209,8 +203,7 @@ public final class Trip {
|| raw.get(VEHICLE_ID) instanceof Long) {
vehicleID = raw.get(VEHICLE_ID).toString();
} else {
throw new IOException("Field " + VEHICLE_ID + " not of expected type String/Integer/Long, found "
+ raw.get(VEHICLE_ID).getClass().getSimpleName());
throw Model.typeError(VEHICLE_ID, raw.get(VEHICLE_ID).getClass(), "String/Integer/Long");
}
if (raw.get(TRIP_ID) instanceof String
@ -218,15 +211,13 @@ public final class Trip {
|| raw.get(TRIP_ID) instanceof Long) {
id = raw.get(TRIP_ID).toString();
} else {
throw new IOException("Field " + TRIP_ID + " not of expected type String/Integer/Long, found "
+ raw.get(TRIP_ID).getClass().getSimpleName());
throw Model.typeError(TRIP_ID, raw.get(TRIP_ID).getClass(), "String/Integer/Long");
}
if (raw.get(ESTIMATED_TIME) instanceof Long) {
estimatedTime = (Long) raw.get(ESTIMATED_TIME);
} else {
throw new IOException("Field " + ESTIMATED_TIME + " not of expected type Long, found "
+ raw.get(ESTIMATED_TIME).getClass().getSimpleName());
throw Model.typeError(ESTIMATED_TIME, raw.get(ESTIMATED_TIME).getClass(), "Long");
}
}