From 91d125349ecd6082071a58f142cff2861669a9e2 Mon Sep 17 00:00:00 2001 From: Bryson Spilman Date: Fri, 5 Sep 2025 14:16:23 -0700 Subject: [PATCH 1/4] CWMSVUE-600 Updating effective data retrieval to not include aliases --- .../java/cwms/cda/data/dao/RatingSpecDao.java | 44 ++++++++++++++++++- 1 file changed, 43 insertions(+), 1 deletion(-) diff --git a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java index baf635eff6..9495669465 100644 --- a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java +++ b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java @@ -40,7 +40,6 @@ import java.time.Instant; import java.time.ZoneId; import java.time.ZonedDateTime; -import java.time.temporal.ChronoUnit; import java.util.ArrayList; import java.util.Arrays; import java.util.Calendar; @@ -66,9 +65,16 @@ import org.jetbrains.annotations.NotNull; import org.jooq.Condition; import org.jooq.DSLContext; +import org.jooq.Field; import org.jooq.Record; +import org.jooq.Record1; +import org.jooq.Record2; import org.jooq.ResultQuery; +import org.jooq.SelectConditionStep; +import org.jooq.SelectForUpdateStep; import org.jooq.conf.ParamType; +import org.jooq.impl.DSL; +import static org.jooq.impl.DSL.field; import usace.cwms.db.dao.util.OracleTypeMap; import usace.cwms.db.jooq.codegen.packages.CWMS_RATING_PACKAGE; import usace.cwms.db.jooq.codegen.tables.AV_RATING; @@ -422,6 +428,7 @@ public void create(String xml, boolean failIfExists) { public RatingEffectiveDatesMap retrieveSpecEffectiveDates(String officeIdMask, String specIdMask, Instant begin, Instant end) { return connectionResult(dsl, conn -> { + Set ratingIdsNoAliases = getRatingIds(conn, officeIdMask, "*", false); //office->spec->dates NavigableMap>> specDateMap = new TreeMap<>(); ResultSet rs = catRatings(conn, officeIdMask, specIdMask, begin, end); @@ -429,6 +436,9 @@ public RatingEffectiveDatesMap retrieveSpecEffectiveDates(String officeIdMask, S while(rs.next()) { String officeId = rs.getString(OFFICE_ID); String specId = rs.getString(SPECIFICATION_ID); + if(!ratingIdsNoAliases.contains(specId)) { // skip aliased specs + continue; + } Timestamp timestamp = rs.getTimestamp(EFFECTIVE_DATE, GMT_CALENDAR); Instant date = timestamp.toInstant(); NavigableSet dateList = specDateMap.computeIfAbsent(officeId, k -> new TreeMap<>()) @@ -490,4 +500,36 @@ private ResultSet catRatings(Connection conn, String officeIdMask, String specId return output; } + + private Set getRatingIds(Connection conn, String office, String templateIdMask, boolean includeAliases) { + AV_RATING_SPEC specView = AV_RATING_SPEC.AV_RATING_SPEC; + Condition condition = DSL.noCondition(); + + if (office != null) { + condition = condition.and(specView.OFFICE_ID.eq(office)); + } + + if (templateIdMask != null) { + Condition ratingIdLike = JooqDao.caseInsensitiveLikeRegex(specView.RATING_ID, + templateIdMask); + condition = condition.and(ratingIdLike); + } + + if(!includeAliases) { + condition = condition.and(specView.ALIASED_ITEM.isNull()); + } + + Field idField = field("RATING_ID", String.class); + + SelectConditionStep> ratingStep = DSL.using(conn).select( + specView.OFFICE_ID, + specView.RATING_ID.as(idField)) + .from(specView) + .where(condition); + + SelectForUpdateStep> query = DSL.using(conn).selectDistinct(idField) + .from(ratingStep) + .orderBy(idField.asc()); + return new LinkedHashSet<>(query.fetch(idField)); + } } From 9358e3b26c22c29aba2c812efdea84237e38d0a8 Mon Sep 17 00:00:00 2001 From: Bryson Spilman Date: Fri, 5 Sep 2025 14:33:45 -0700 Subject: [PATCH 2/4] CWMSVUE-600 Separates call to get non-aliased rating spec ideas into separate connection. --- .../java/cwms/cda/data/dao/RatingSpecDao.java | 54 ++++++++++--------- 1 file changed, 29 insertions(+), 25 deletions(-) diff --git a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java index 9495669465..4ae503d3b0 100644 --- a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java +++ b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java @@ -428,7 +428,7 @@ public void create(String xml, boolean failIfExists) { public RatingEffectiveDatesMap retrieveSpecEffectiveDates(String officeIdMask, String specIdMask, Instant begin, Instant end) { return connectionResult(dsl, conn -> { - Set ratingIdsNoAliases = getRatingIds(conn, officeIdMask, "*", false); + Set ratingIdsNoAliases = getRatingIds(officeIdMask, "*", false); //office->spec->dates NavigableMap>> specDateMap = new TreeMap<>(); ResultSet rs = catRatings(conn, officeIdMask, specIdMask, begin, end); @@ -501,35 +501,39 @@ private ResultSet catRatings(Connection conn, String officeIdMask, String specId return output; } - private Set getRatingIds(Connection conn, String office, String templateIdMask, boolean includeAliases) { - AV_RATING_SPEC specView = AV_RATING_SPEC.AV_RATING_SPEC; - Condition condition = DSL.noCondition(); + private Set getRatingIds(String office, String templateIdMask, boolean includeAliases) { + return connectionResult(dsl, conn -> + { + AV_RATING_SPEC specView = AV_RATING_SPEC.AV_RATING_SPEC; + Condition condition = DSL.noCondition(); - if (office != null) { - condition = condition.and(specView.OFFICE_ID.eq(office)); - } + if (office != null) { + condition = condition.and(specView.OFFICE_ID.eq(office)); + } - if (templateIdMask != null) { - Condition ratingIdLike = JooqDao.caseInsensitiveLikeRegex(specView.RATING_ID, - templateIdMask); - condition = condition.and(ratingIdLike); - } + if (templateIdMask != null) { + Condition ratingIdLike = JooqDao.caseInsensitiveLikeRegex(specView.RATING_ID, + templateIdMask); + condition = condition.and(ratingIdLike); + } - if(!includeAliases) { - condition = condition.and(specView.ALIASED_ITEM.isNull()); - } + if(!includeAliases) { + condition = condition.and(specView.ALIASED_ITEM.isNull()); + } - Field idField = field("RATING_ID", String.class); + Field idField = field("RATING_ID", String.class); - SelectConditionStep> ratingStep = DSL.using(conn).select( - specView.OFFICE_ID, - specView.RATING_ID.as(idField)) - .from(specView) - .where(condition); + SelectConditionStep> ratingStep = DSL.using(conn).select( + specView.OFFICE_ID, + specView.RATING_ID.as(idField)) + .from(specView) + .where(condition); + + SelectForUpdateStep> query = DSL.using(conn).selectDistinct(idField) + .from(ratingStep) + .orderBy(idField.asc()); + return new LinkedHashSet<>(query.fetch(idField)); + }); - SelectForUpdateStep> query = DSL.using(conn).selectDistinct(idField) - .from(ratingStep) - .orderBy(idField.asc()); - return new LinkedHashSet<>(query.fetch(idField)); } } From 59f2ab97ded38bd4ebb179b587aa0ee87a5fe093 Mon Sep 17 00:00:00 2001 From: Bryson Spilman Date: Fri, 5 Sep 2025 14:38:57 -0700 Subject: [PATCH 3/4] CWMSVUE-600 Added code comments/javadoc to explain what is occurring in code. --- .../src/main/java/cwms/cda/data/dao/RatingSpecDao.java | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java index 4ae503d3b0..eacddcaf61 100644 --- a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java +++ b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java @@ -426,8 +426,13 @@ public void create(String xml, boolean failIfExists) { ); } + /** + * Retrieve effective dates for specs matching the specIdMask and officeIdMask within the given date range. + * NOTE: This makes a separate query to get the list of non-aliased spec ids for the officeIdMask, so that aliased specs can be skipped. + */ public RatingEffectiveDatesMap retrieveSpecEffectiveDates(String officeIdMask, String specIdMask, Instant begin, Instant end) { return connectionResult(dsl, conn -> { + //set of non-alias spec ids used to filter out aliased specs Set ratingIdsNoAliases = getRatingIds(officeIdMask, "*", false); //office->spec->dates NavigableMap>> specDateMap = new TreeMap<>(); @@ -436,7 +441,7 @@ public RatingEffectiveDatesMap retrieveSpecEffectiveDates(String officeIdMask, S while(rs.next()) { String officeId = rs.getString(OFFICE_ID); String specId = rs.getString(SPECIFICATION_ID); - if(!ratingIdsNoAliases.contains(specId)) { // skip aliased specs + if(!ratingIdsNoAliases.contains(specId)) { // skip aliased specs based on queried list of rating ids not including aliases continue; } Timestamp timestamp = rs.getTimestamp(EFFECTIVE_DATE, GMT_CALENDAR); From fe16cce8e58cb1e56d817cd6d8d310aa73f79447 Mon Sep 17 00:00:00 2001 From: Bryson Spilman Date: Fri, 5 Sep 2025 14:41:51 -0700 Subject: [PATCH 4/4] CWMSVUE-600 Moved rating id query to happen before opening new connection for catRatings call --- .../src/main/java/cwms/cda/data/dao/RatingSpecDao.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java index eacddcaf61..0dba42d265 100644 --- a/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java +++ b/cwms-data-api/src/main/java/cwms/cda/data/dao/RatingSpecDao.java @@ -431,9 +431,9 @@ public void create(String xml, boolean failIfExists) { * NOTE: This makes a separate query to get the list of non-aliased spec ids for the officeIdMask, so that aliased specs can be skipped. */ public RatingEffectiveDatesMap retrieveSpecEffectiveDates(String officeIdMask, String specIdMask, Instant begin, Instant end) { + //set of non-alias spec ids used to filter out aliased specs + Set ratingIdsNoAliases = getRatingIds(officeIdMask, "*", false); return connectionResult(dsl, conn -> { - //set of non-alias spec ids used to filter out aliased specs - Set ratingIdsNoAliases = getRatingIds(officeIdMask, "*", false); //office->spec->dates NavigableMap>> specDateMap = new TreeMap<>(); ResultSet rs = catRatings(conn, officeIdMask, specIdMask, begin, end);