From 06d9beed01daae96a45780ba73a9a3af70954704 Mon Sep 17 00:00:00 2001 From: Andrew Byrd Date: Mon, 6 Nov 2023 17:43:07 +0800 Subject: [PATCH 1/6] include route, stop names in regional path results --- .../java/com/conveyal/r5/analyst/cluster/PathResult.java | 2 +- .../java/com/conveyal/r5/transit/path/RouteSequence.java | 8 ++++---- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java b/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java index c2366ac1a..99601291e 100644 --- a/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java +++ b/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java @@ -108,7 +108,7 @@ public ArrayList[] summarizeIterations(Stat stat) { int nIterations = iterations.size(); checkState(nIterations > 0, "A path was stored without any iterations"); String waits = null, transfer = null, totalTime = null; - String[] path = routeSequence.detailsWithGtfsIds(transitLayer); + String[] path = routeSequence.detailsWithGtfsIds(transitLayer, true); double targetValue; IntStream totalWaits = iterations.stream().mapToInt(i -> i.waitTimes.sum()); if (stat == Stat.MINIMUM) { diff --git a/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java b/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java index 6ed2eb73c..a5bdd71ae 100644 --- a/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java +++ b/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java @@ -28,15 +28,15 @@ public RouteSequence(PatternSequence patternSequence, TransitLayer transitLayer) } /** Returns details summarizing this route sequence, using GTFS ids stored in the supplied transitLayer. */ - public String[] detailsWithGtfsIds(TransitLayer transitLayer){ + public String[] detailsWithGtfsIds(TransitLayer transitLayer, boolean includeNames){ StringJoiner routeIds = new StringJoiner("|"); StringJoiner boardStopIds = new StringJoiner("|"); StringJoiner alightStopIds = new StringJoiner("|"); StringJoiner rideTimes = new StringJoiner("|"); for (int i = 0; i < routes.size(); i++) { - routeIds.add(transitLayer.routeString(routes.get(i), false)); - boardStopIds.add(transitLayer.stopString(stopSequence.boardStops.get(i), false)); - alightStopIds.add(transitLayer.stopString(stopSequence.alightStops.get(i), false)); + routeIds.add(transitLayer.routeString(routes.get(i), includeNames)); + boardStopIds.add(transitLayer.stopString(stopSequence.boardStops.get(i), includeNames)); + alightStopIds.add(transitLayer.stopString(stopSequence.alightStops.get(i), includeNames)); rideTimes.add(String.format("%.1f", stopSequence.rideTimesSeconds.get(i) / 60f)); } String accessTime = stopSequence.access == null ? null : String.format("%.1f", stopSequence.access.time / 60f); From d5f5becc8d2f9d0b14e8cafdc4468775f75cf9ba Mon Sep 17 00:00:00 2001 From: Andrew Byrd Date: Sat, 3 Feb 2024 01:06:20 +0800 Subject: [PATCH 2/6] enable/disable ids and names csv with string flags --- .../analysis/models/AnalysisRequest.java | 7 +++ .../analyst/cluster/AnalysisWorkerTask.java | 7 +++ .../r5/analyst/cluster/PathResult.java | 19 ++++++- .../com/conveyal/r5/transit/TransitLayer.java | 57 ++++++++++++++----- .../r5/transit/path/RouteSequence.java | 17 +++--- 5 files changed, 86 insertions(+), 21 deletions(-) diff --git a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java index 80d5e507a..f2249c7fe 100644 --- a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java +++ b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java @@ -21,6 +21,7 @@ import java.util.Collection; import java.util.EnumSet; import java.util.List; +import java.util.Set; import java.util.stream.Collectors; /** @@ -175,6 +176,11 @@ public class AnalysisRequest { */ public int dualAccessibilityThreshold = 0; + /** + * Freeform (untyped) flags for enabling experimental, undocumented, or arcane behavior in backend or workers. + * This should be used to replace all previous special behavior flags that were embedded inside analysis names etc. + */ + public Set flags; /** * Create the R5 `Scenario` from this request. @@ -281,6 +287,7 @@ public void populateTask (AnalysisWorkerTask task, UserPermissions userPermissio task.includeTemporalDensity = includeTemporalDensity; task.dualAccessibilityThreshold = dualAccessibilityThreshold; + task.flags = flags; } private EnumSet getEnumSetFromString (String s) { diff --git a/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java b/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java index 30266f171..d64996a15 100644 --- a/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java +++ b/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java @@ -15,6 +15,7 @@ import com.fasterxml.jackson.annotation.JsonTypeInfo; import java.util.Arrays; +import java.util.Set; import static com.google.common.base.Preconditions.checkArgument; import static com.google.common.base.Preconditions.checkNotNull; @@ -177,6 +178,12 @@ public abstract class AnalysisWorkerTask extends ProfileRequest { */ public ChaosParameters injectFault; + /** + * Freeform (untyped) flags for enabling experimental, undocumented, or arcane worker behavior. + * This should be used to replace all previous special behavior flags that were embedded inside analysis names etc. + */ + public Set flags; + /** * Is this a single point or regional request? Needed to encode types in JSON serialization. Can that type field be * added automatically with a serializer annotation instead of by defining a getter method and two dummy methods? diff --git a/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java b/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java index 99601291e..36e71699f 100644 --- a/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java +++ b/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java @@ -19,6 +19,9 @@ import java.util.stream.Collectors; import java.util.stream.IntStream; +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_ONLY; +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_AND_NAME; +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.NAME_ONLY; import static com.google.common.base.Preconditions.checkState; /** @@ -47,8 +50,11 @@ public class PathResult { * With additional changes, patterns could be collapsed further to route combinations or modes. */ public final Multimap[] iterationsForPathTemplates; + private final TransitLayer transitLayer; + private TransitLayer.EntityRepresentation nameOrId; + public static final String[] DATA_COLUMNS = new String[]{ "routes", "boardStops", @@ -76,6 +82,17 @@ public PathResult(AnalysisWorkerTask task, TransitLayer transitLayer) { } iterationsForPathTemplates = new Multimap[nDestinations]; this.transitLayer = transitLayer; + if (task.flags == null) { + nameOrId = ID_ONLY; + } else { + boolean includeEntityNames = task.flags.contains("csv_names"); + boolean includeEntityIds = !task.flags.contains("csv_no_ids"); + if (includeEntityIds && includeEntityNames) { + this.nameOrId = ID_AND_NAME; + } else if (includeEntityNames) { + this.nameOrId = NAME_ONLY; + } + } } /** @@ -108,7 +125,7 @@ public ArrayList[] summarizeIterations(Stat stat) { int nIterations = iterations.size(); checkState(nIterations > 0, "A path was stored without any iterations"); String waits = null, transfer = null, totalTime = null; - String[] path = routeSequence.detailsWithGtfsIds(transitLayer, true); + String[] path = routeSequence.detailsWithGtfsIds(transitLayer, nameOrId); double targetValue; IntStream totalWaits = iterations.stream().mapToInt(i -> i.waitTimes.sum()); if (stat == Stat.MINIMUM) { diff --git a/src/main/java/com/conveyal/r5/transit/TransitLayer.java b/src/main/java/com/conveyal/r5/transit/TransitLayer.java index 871491ff2..a025ba4d0 100644 --- a/src/main/java/com/conveyal/r5/transit/TransitLayer.java +++ b/src/main/java/com/conveyal/r5/transit/TransitLayer.java @@ -54,6 +54,9 @@ import java.util.stream.IntStream; import java.util.stream.StreamSupport; +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_ONLY; +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.NAME_ONLY; + /** * A key simplifying factor is that we don't handle overnight trips. This is fine for analysis at usual times of day. @@ -815,31 +818,59 @@ public TIntSet findStopsInGeometry (Geometry geometry) { return stops; } + public enum EntityRepresentation { + ID_ONLY, NAME_ONLY, ID_AND_NAME + } + /** * For the given pattern index, returns the GTFS routeId. If includeName is true, the returned string will * also include a route_short_name or route_long_name (if they are not null). */ - public String routeString(int routeIndex, boolean includeName) { + public String routeString (int routeIndex, EntityRepresentation nameOrId) { RouteInfo routeInfo = routes.get(routeIndex); - String route = routeInfo.route_id; - if (includeName) { - if (routeInfo.route_short_name != null) { - route += " (" + routeInfo.route_short_name + ")"; - } else if (routeInfo.route_long_name != null){ - route += " (" + routeInfo.route_long_name + ")"; + String name = routeInfo.route_short_name; + String id = routeInfo.route_id; + // If we might actually use the name, check some fallbacks. + if (nameOrId != ID_ONLY) { + if (name == null) { + name = routeInfo.route_long_name; + } + if (name == null) { + name = routeInfo.route_id; } } - return route; + return switch (nameOrId) { + case NAME_ONLY -> name; + case ID_AND_NAME -> id + " (" + name + ")"; + default -> id; + }; } /** * For the given stop index, returns the GTFS stopId (stripped of R5's feedId prefix) and, if includeName is true, * stopName. */ - public String stopString(int stopIndex, boolean includeName) { - // TODO use a compact feed index, instead of splitting to remove feedIds - String stop = stopIdForIndex.get(stopIndex) == null ? "[new]" : stopIdForIndex.get(stopIndex).split(":")[1]; - if (includeName) stop += " (" + stopNames.get(stopIndex) + ")"; - return stop; + public String stopString(int stopIndex, EntityRepresentation nameOrId) { + String stopId = stopIdForIndex.get(stopIndex); + String stopName = stopNames.get(stopIndex); + // I'd trust the JVM JIT to optimize out these assignments on different code paths, but not the split call. + if (nameOrId != NAME_ONLY) { + if (stopId == null) { + stopId = "[new]"; + } else { + // TODO use a compact feed ID instead of splitting to remove feedIds (or put feedId into another CSV field) + stopId = stopId.split(":")[1]; + } + } + if (nameOrId != ID_ONLY) { + if (stopName == null) { + stopName = "[new]"; + } + } + return switch (nameOrId) { + case NAME_ONLY -> stopName; + case ID_AND_NAME -> stopId + " (" + stopName + ")"; + default -> stopId; + }; } } diff --git a/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java b/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java index a5bdd71ae..3bb4f512c 100644 --- a/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java +++ b/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java @@ -1,6 +1,7 @@ package com.conveyal.r5.transit.path; import com.conveyal.r5.transit.TransitLayer; +import com.conveyal.r5.transit.TransitLayer.EntityRepresentation; import gnu.trove.list.TIntList; import gnu.trove.list.array.TIntArrayList; @@ -9,6 +10,8 @@ import java.util.Objects; import java.util.StringJoiner; +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_AND_NAME; + /** A door-to-door path that includes the routes ridden between stops */ public class RouteSequence { @@ -28,15 +31,15 @@ public RouteSequence(PatternSequence patternSequence, TransitLayer transitLayer) } /** Returns details summarizing this route sequence, using GTFS ids stored in the supplied transitLayer. */ - public String[] detailsWithGtfsIds(TransitLayer transitLayer, boolean includeNames){ + public String[] detailsWithGtfsIds (TransitLayer transitLayer, EntityRepresentation nameOrId){ StringJoiner routeIds = new StringJoiner("|"); StringJoiner boardStopIds = new StringJoiner("|"); StringJoiner alightStopIds = new StringJoiner("|"); StringJoiner rideTimes = new StringJoiner("|"); for (int i = 0; i < routes.size(); i++) { - routeIds.add(transitLayer.routeString(routes.get(i), includeNames)); - boardStopIds.add(transitLayer.stopString(stopSequence.boardStops.get(i), includeNames)); - alightStopIds.add(transitLayer.stopString(stopSequence.alightStops.get(i), includeNames)); + routeIds.add(transitLayer.routeString(routes.get(i), nameOrId)); + boardStopIds.add(transitLayer.stopString(stopSequence.boardStops.get(i), nameOrId)); + alightStopIds.add(transitLayer.stopString(stopSequence.alightStops.get(i), nameOrId)); rideTimes.add(String.format("%.1f", stopSequence.rideTimesSeconds.get(i) / 60f)); } String accessTime = stopSequence.access == null ? null : String.format("%.1f", stopSequence.access.time / 60f); @@ -55,9 +58,9 @@ public String[] detailsWithGtfsIds(TransitLayer transitLayer, boolean includeNam public Collection transitLegs(TransitLayer transitLayer) { Collection transitLegs = new ArrayList<>(); for (int i = 0; i < routes.size(); i++) { - String routeString = transitLayer.routeString(routes.get(i), true); - String boardStop = transitLayer.stopString(stopSequence.boardStops.get(i), true); - String alightStop = transitLayer.stopString(stopSequence.alightStops.get(i), true); + String routeString = transitLayer.routeString(routes.get(i), ID_AND_NAME); + String boardStop = transitLayer.stopString(stopSequence.boardStops.get(i), ID_AND_NAME); + String alightStop = transitLayer.stopString(stopSequence.alightStops.get(i), ID_AND_NAME); transitLegs.add(new TransitLeg(routeString, stopSequence.rideTimesSeconds.get(i), boardStop, alightStop)); } return transitLegs; From e11fc19e5af413da331bce40c6ced687be5ba8c2 Mon Sep 17 00:00:00 2001 From: Andrew Byrd Date: Sat, 17 Feb 2024 00:45:23 +0800 Subject: [PATCH 3/6] nested CsvResultOptions in requests reverse order of name and ID in output and enum. string flags are maintained in request but no longer used. deleted code serves as example of how to use flags. --- .../analysis/models/AnalysisRequest.java | 6 ++++++ .../analysis/models/CsvResultOptions.java | 18 +++++++++++++++++ .../analyst/cluster/AnalysisWorkerTask.java | 4 ++++ .../r5/analyst/cluster/PathResult.java | 20 ++++--------------- .../com/conveyal/r5/transit/TransitLayer.java | 6 +++--- .../r5/transit/path/RouteSequence.java | 17 ++++++++-------- 6 files changed, 44 insertions(+), 27 deletions(-) create mode 100644 src/main/java/com/conveyal/analysis/models/CsvResultOptions.java diff --git a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java index f2249c7fe..3bff888e8 100644 --- a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java +++ b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java @@ -12,8 +12,10 @@ import com.conveyal.r5.analyst.scenario.Scenario; import com.conveyal.r5.api.util.LegMode; import com.conveyal.r5.api.util.TransitModes; +import com.conveyal.r5.transit.TransitLayer; import com.mongodb.QueryBuilder; import org.apache.commons.codec.digest.DigestUtils; +import org.checkerframework.checker.units.qual.C; import java.time.LocalDate; import java.util.ArrayList; @@ -182,6 +184,9 @@ public class AnalysisRequest { */ public Set flags; + /** Control the details of CSV regional analysis output, including whether to output IDs, names, or both. */ + public CsvResultOptions csvResultOptions = new CsvResultOptions(); + /** * Create the R5 `Scenario` from this request. */ @@ -288,6 +293,7 @@ public void populateTask (AnalysisWorkerTask task, UserPermissions userPermissio task.includeTemporalDensity = includeTemporalDensity; task.dualAccessibilityThreshold = dualAccessibilityThreshold; task.flags = flags; + task.csvResultOptions = csvResultOptions; } private EnumSet getEnumSetFromString (String s) { diff --git a/src/main/java/com/conveyal/analysis/models/CsvResultOptions.java b/src/main/java/com/conveyal/analysis/models/CsvResultOptions.java new file mode 100644 index 000000000..c21b52aa3 --- /dev/null +++ b/src/main/java/com/conveyal/analysis/models/CsvResultOptions.java @@ -0,0 +1,18 @@ +package com.conveyal.analysis.models; + +import com.conveyal.r5.transit.TransitLayer; +import com.conveyal.r5.transit.TransitLayer.EntityRepresentation; + +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_ONLY; + +/** + * API model type included in analysis requests to control details of CSV regional analysis output. + * This type is shared between AnalysisRequest (Frontend -> Broker) and AnalysisWorkerTask (Broker -> Workers). + * There is precedent for nested compound types shared across those top level request types (see DecayFunction). + */ +public class CsvResultOptions { + public EntityRepresentation routeRepresentation = ID_ONLY; + public EntityRepresentation stopRepresentation = ID_ONLY; + // Only feed ID representation is allowed to be null (no feed IDs at all, the default). + public EntityRepresentation feedRepresentation = null; +} diff --git a/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java b/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java index d64996a15..2698905fa 100644 --- a/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java +++ b/src/main/java/com/conveyal/r5/analyst/cluster/AnalysisWorkerTask.java @@ -1,5 +1,6 @@ package com.conveyal.r5.analyst.cluster; +import com.conveyal.analysis.models.CsvResultOptions; import com.conveyal.r5.analyst.FreeFormPointSet; import com.conveyal.r5.analyst.Grid; import com.conveyal.r5.analyst.GridTransformWrapper; @@ -184,6 +185,9 @@ public abstract class AnalysisWorkerTask extends ProfileRequest { */ public Set flags; + /** Control the details of CSV regional analysis output, including whether to output IDs, names, or both. */ + public CsvResultOptions csvResultOptions; + /** * Is this a single point or regional request? Needed to encode types in JSON serialization. Can that type field be * added automatically with a serializer annotation instead of by defining a getter method and two dummy methods? diff --git a/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java b/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java index 36e71699f..dd42972b1 100644 --- a/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java +++ b/src/main/java/com/conveyal/r5/analyst/cluster/PathResult.java @@ -1,5 +1,6 @@ package com.conveyal.r5.analyst.cluster; +import com.conveyal.analysis.models.CsvResultOptions; import com.conveyal.r5.analyst.StreetTimesAndModes; import com.conveyal.r5.transit.TransitLayer; import com.conveyal.r5.transit.path.Path; @@ -19,9 +20,6 @@ import java.util.stream.Collectors; import java.util.stream.IntStream; -import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_ONLY; -import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_AND_NAME; -import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.NAME_ONLY; import static com.google.common.base.Preconditions.checkState; /** @@ -53,7 +51,7 @@ public class PathResult { private final TransitLayer transitLayer; - private TransitLayer.EntityRepresentation nameOrId; + private final CsvResultOptions csvOptions; public static final String[] DATA_COLUMNS = new String[]{ "routes", @@ -82,17 +80,7 @@ public PathResult(AnalysisWorkerTask task, TransitLayer transitLayer) { } iterationsForPathTemplates = new Multimap[nDestinations]; this.transitLayer = transitLayer; - if (task.flags == null) { - nameOrId = ID_ONLY; - } else { - boolean includeEntityNames = task.flags.contains("csv_names"); - boolean includeEntityIds = !task.flags.contains("csv_no_ids"); - if (includeEntityIds && includeEntityNames) { - this.nameOrId = ID_AND_NAME; - } else if (includeEntityNames) { - this.nameOrId = NAME_ONLY; - } - } + this.csvOptions = task.csvResultOptions; } /** @@ -125,7 +113,7 @@ public ArrayList[] summarizeIterations(Stat stat) { int nIterations = iterations.size(); checkState(nIterations > 0, "A path was stored without any iterations"); String waits = null, transfer = null, totalTime = null; - String[] path = routeSequence.detailsWithGtfsIds(transitLayer, nameOrId); + String[] path = routeSequence.detailsWithGtfsIds(transitLayer, csvOptions); double targetValue; IntStream totalWaits = iterations.stream().mapToInt(i -> i.waitTimes.sum()); if (stat == Stat.MINIMUM) { diff --git a/src/main/java/com/conveyal/r5/transit/TransitLayer.java b/src/main/java/com/conveyal/r5/transit/TransitLayer.java index a025ba4d0..7ec85e6fa 100644 --- a/src/main/java/com/conveyal/r5/transit/TransitLayer.java +++ b/src/main/java/com/conveyal/r5/transit/TransitLayer.java @@ -819,7 +819,7 @@ public TIntSet findStopsInGeometry (Geometry geometry) { } public enum EntityRepresentation { - ID_ONLY, NAME_ONLY, ID_AND_NAME + ID_ONLY, NAME_ONLY, NAME_AND_ID } /** @@ -841,7 +841,7 @@ public String routeString (int routeIndex, EntityRepresentation nameOrId) { } return switch (nameOrId) { case NAME_ONLY -> name; - case ID_AND_NAME -> id + " (" + name + ")"; + case NAME_AND_ID -> name + " (" + id + ")"; default -> id; }; } @@ -869,7 +869,7 @@ public String stopString(int stopIndex, EntityRepresentation nameOrId) { } return switch (nameOrId) { case NAME_ONLY -> stopName; - case ID_AND_NAME -> stopId + " (" + stopName + ")"; + case NAME_AND_ID -> stopName + " (" + stopId + ")"; default -> stopId; }; } diff --git a/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java b/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java index 3bb4f512c..1e60478f3 100644 --- a/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java +++ b/src/main/java/com/conveyal/r5/transit/path/RouteSequence.java @@ -1,5 +1,6 @@ package com.conveyal.r5.transit.path; +import com.conveyal.analysis.models.CsvResultOptions; import com.conveyal.r5.transit.TransitLayer; import com.conveyal.r5.transit.TransitLayer.EntityRepresentation; import gnu.trove.list.TIntList; @@ -10,7 +11,7 @@ import java.util.Objects; import java.util.StringJoiner; -import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_AND_NAME; +import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.NAME_AND_ID; /** A door-to-door path that includes the routes ridden between stops */ public class RouteSequence { @@ -31,15 +32,15 @@ public RouteSequence(PatternSequence patternSequence, TransitLayer transitLayer) } /** Returns details summarizing this route sequence, using GTFS ids stored in the supplied transitLayer. */ - public String[] detailsWithGtfsIds (TransitLayer transitLayer, EntityRepresentation nameOrId){ + public String[] detailsWithGtfsIds (TransitLayer transitLayer, CsvResultOptions csvOptions){ StringJoiner routeIds = new StringJoiner("|"); StringJoiner boardStopIds = new StringJoiner("|"); StringJoiner alightStopIds = new StringJoiner("|"); StringJoiner rideTimes = new StringJoiner("|"); for (int i = 0; i < routes.size(); i++) { - routeIds.add(transitLayer.routeString(routes.get(i), nameOrId)); - boardStopIds.add(transitLayer.stopString(stopSequence.boardStops.get(i), nameOrId)); - alightStopIds.add(transitLayer.stopString(stopSequence.alightStops.get(i), nameOrId)); + routeIds.add(transitLayer.routeString(routes.get(i), csvOptions.routeRepresentation)); + boardStopIds.add(transitLayer.stopString(stopSequence.boardStops.get(i), csvOptions.stopRepresentation)); + alightStopIds.add(transitLayer.stopString(stopSequence.alightStops.get(i), csvOptions.stopRepresentation)); rideTimes.add(String.format("%.1f", stopSequence.rideTimesSeconds.get(i) / 60f)); } String accessTime = stopSequence.access == null ? null : String.format("%.1f", stopSequence.access.time / 60f); @@ -58,9 +59,9 @@ public String[] detailsWithGtfsIds (TransitLayer transitLayer, EntityRepresentat public Collection transitLegs(TransitLayer transitLayer) { Collection transitLegs = new ArrayList<>(); for (int i = 0; i < routes.size(); i++) { - String routeString = transitLayer.routeString(routes.get(i), ID_AND_NAME); - String boardStop = transitLayer.stopString(stopSequence.boardStops.get(i), ID_AND_NAME); - String alightStop = transitLayer.stopString(stopSequence.alightStops.get(i), ID_AND_NAME); + String routeString = transitLayer.routeString(routes.get(i), NAME_AND_ID); + String boardStop = transitLayer.stopString(stopSequence.boardStops.get(i), NAME_AND_ID); + String alightStop = transitLayer.stopString(stopSequence.alightStops.get(i), NAME_AND_ID); transitLegs.add(new TransitLeg(routeString, stopSequence.rideTimesSeconds.get(i), boardStop, alightStop)); } return transitLegs; From 119ffc149a5c7ebe0b2b0e033f9560652f10b2c9 Mon Sep 17 00:00:00 2001 From: Andrew Byrd Date: Thu, 29 Feb 2024 11:46:55 +0900 Subject: [PATCH 4/6] Update src/main/java/com/conveyal/analysis/models/AnalysisRequest.java Co-authored-by: Anson Stewart --- src/main/java/com/conveyal/analysis/models/AnalysisRequest.java | 1 - 1 file changed, 1 deletion(-) diff --git a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java index 3bff888e8..95944f262 100644 --- a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java +++ b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java @@ -12,7 +12,6 @@ import com.conveyal.r5.analyst.scenario.Scenario; import com.conveyal.r5.api.util.LegMode; import com.conveyal.r5.api.util.TransitModes; -import com.conveyal.r5.transit.TransitLayer; import com.mongodb.QueryBuilder; import org.apache.commons.codec.digest.DigestUtils; import org.checkerframework.checker.units.qual.C; From c92bf7ba245d25c83e35055e045c4b0f81a47b39 Mon Sep 17 00:00:00 2001 From: Andrew Byrd Date: Thu, 29 Feb 2024 11:48:40 +0900 Subject: [PATCH 5/6] Update src/main/java/com/conveyal/analysis/models/CsvResultOptions.java Co-authored-by: Anson Stewart --- src/main/java/com/conveyal/analysis/models/CsvResultOptions.java | 1 - 1 file changed, 1 deletion(-) diff --git a/src/main/java/com/conveyal/analysis/models/CsvResultOptions.java b/src/main/java/com/conveyal/analysis/models/CsvResultOptions.java index c21b52aa3..e925e5ff3 100644 --- a/src/main/java/com/conveyal/analysis/models/CsvResultOptions.java +++ b/src/main/java/com/conveyal/analysis/models/CsvResultOptions.java @@ -1,6 +1,5 @@ package com.conveyal.analysis.models; -import com.conveyal.r5.transit.TransitLayer; import com.conveyal.r5.transit.TransitLayer.EntityRepresentation; import static com.conveyal.r5.transit.TransitLayer.EntityRepresentation.ID_ONLY; From eca7051f1e59db545bff9249ad9d2aafd6c12ccc Mon Sep 17 00:00:00 2001 From: Andrew Byrd Date: Thu, 29 Feb 2024 11:48:46 +0900 Subject: [PATCH 6/6] Update src/main/java/com/conveyal/analysis/models/AnalysisRequest.java Co-authored-by: Anson Stewart --- src/main/java/com/conveyal/analysis/models/AnalysisRequest.java | 1 - 1 file changed, 1 deletion(-) diff --git a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java index 95944f262..cda79c9b8 100644 --- a/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java +++ b/src/main/java/com/conveyal/analysis/models/AnalysisRequest.java @@ -14,7 +14,6 @@ import com.conveyal.r5.api.util.TransitModes; import com.mongodb.QueryBuilder; import org.apache.commons.codec.digest.DigestUtils; -import org.checkerframework.checker.units.qual.C; import java.time.LocalDate; import java.util.ArrayList;