Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,7 @@ public class AccountingCatalogController implements Handler {
private static final String TAG = "Pump Accounting";
private static final String ROW_LIMIT = "row-limit";
private static final String ASCENDING = "ascending";
private static final int DEFAULT_ROW_LIMIT = 500;
private final MetricRegistry metrics;

private Timer.Context markAndTime(String subject) {
Expand Down Expand Up @@ -117,7 +118,7 @@ protected WaterSupplyAccountingDao getWaterSupplyAccountingDao(DSLContext dsl) {
@OpenApiParam(name = ASCENDING, description = "Whether or not the entries should be returned "
+ "in ascending order. Defaults to TRUE.", type = Boolean.class),
@OpenApiParam(name = ROW_LIMIT, description = "The maximum number of rows to return. "

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we want to use -1 for "no limit" ?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's what's used for time series.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We were modelling this behavior off the way turbines and gate changes work. Negative row limit is used to say how many rows before the end date, vs positive row limit where it's how many rows after the start date.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Gates, turbines, and water supply treat the row limit as follows:

  • negative values limit rows off of head
  • positive values limit rows off of tail
  • to not have a row limit, Integer.MAX_VALUE is specified (yes, this is an annoyingly large value).

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@MikeNeilson @rma-bryson -- do you have any additional feedback on this PR or can it be approved?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we want to keep the head/tail behavior, I suggest we create additional parameters.

+ "Defaults to 0, which means no limit.", type = Integer.class)
+ "Defaults to " + DEFAULT_ROW_LIMIT + ".", type = Integer.class)
},
pathParams = {
@OpenApiParam(name = OFFICE, description = "The office ID of the project the "
Expand Down Expand Up @@ -165,7 +166,15 @@ public void handle(Context ctx) {
.getOrDefault(true);
final boolean endInclusive = ctx.queryParamAsClass(END_TIME_INCLUSIVE, Boolean.class).getOrDefault(true);
final boolean ascending = ctx.queryParamAsClass(ASCENDING, Boolean.class).getOrDefault(true);
final int rowLimit = ctx.queryParamAsClass(ROW_LIMIT, Integer.class).getOrDefault(0);
final int rowLimit = ctx.queryParamAsClass(ROW_LIMIT, Integer.class).getOrDefault(DEFAULT_ROW_LIMIT);

if (rowLimit == 0) {
CdaError error = new CdaError("Unable to retrieve accounting - " + ROW_LIMIT + " must be greater than 0.");
LOGGER.atSevere().log("Unable to retrieve accounting - " + ROW_LIMIT + " must be greater than 0.");
ctx.status(HttpServletResponse.SC_BAD_REQUEST).json(error);
return;
}

DSLContext dsl = getDslContext(ctx);

String formatHeader = ctx.headerAsClass(Header.ACCEPT, String.class).getOrDefault(Formats.JSONV1);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -799,6 +799,77 @@ void testStoreNonExistentTransferType() throws Exception {
.assertThat()
.statusCode(is(HttpServletResponse.SC_BAD_REQUEST))
;

given()
.log().ifValidationFails(LogDetail.ALL, true)
.contentType(Formats.JSONV1)
.header(AUTH_HEADER, user.toHeaderValue())
.queryParam(START_TIME, "2005-04-05T00:00:00Z")
.queryParam(END_TIME, "2335-04-06T00:00:00Z")
.queryParam(START_INCLUSIVE, "true")
.queryParam(END_INCLUSIVE, "true")
.queryParam(ASCENDING, "true")
.queryParam(ROW_LIMIT, 100)
.queryParam(UNIT, "cfs")
.when()
.redirects().follow(true)
.redirects().max(3)
.get("/projects/" + OFFICE_ID + "/" + contract.getWaterUser().getProjectId().getName() + "/water-user/"
+ contract.getWaterUser().getEntityName() + "/contracts/"
+ contract.getContractId().getName() + "/accounting")
.then()
.log().ifValidationFails(LogDetail.ALL, true)
.assertThat()
.statusCode(is(HttpServletResponse.SC_OK));
}

@Test
void testGet0RowLimit() throws Exception {
// 1 Store data
// 2 Retrieve accounting with 0 row limit
// 3 Verify failure from row limit
TestAccounts.KeyUser user = TestAccounts.KeyUser.SPK_NORMAL;
String json = JsonV1.buildObjectMapper().writeValueAsString(waterSupplyAccounting);

// create pump accounting
given()
.log().ifValidationFails(LogDetail.ALL, true)
.contentType(Formats.JSONV1)
.body(json)
.header(AUTH_HEADER, user.toHeaderValue())
.when()
.redirects().follow(true)
.redirects().max(3)
.post("/projects/" + OFFICE_ID + "/" + contract.getWaterUser().getProjectId().getName() + "/water-user/"
+ contract.getWaterUser().getEntityName() + "/contracts/"
+ contract.getContractId().getName() + "/accounting")
.then()
.log().ifValidationFails(LogDetail.ALL, true)
.assertThat()
.statusCode(is(HttpServletResponse.SC_CREATED))
;

given()
.log().ifValidationFails(LogDetail.ALL, true)
.contentType(Formats.JSONV1)
.header(AUTH_HEADER, user.toHeaderValue())
.queryParam(START_TIME, "2005-04-05T00:00:00Z")
.queryParam(END_TIME, "2335-04-06T00:00:00Z")
.queryParam(START_INCLUSIVE, "true")
.queryParam(END_INCLUSIVE, "true")
.queryParam(ASCENDING, "true")
.queryParam(ROW_LIMIT, 0)
.queryParam(UNIT, "cfs")
.when()
.redirects().follow(true)
.redirects().max(3)
.get("/projects/" + OFFICE_ID + "/" + contract.getWaterUser().getProjectId().getName() + "/water-user/"
+ contract.getWaterUser().getEntityName() + "/contracts/"
+ contract.getContractId().getName() + "/accounting")
.then()
.log().ifValidationFails(LogDetail.ALL, true)
.assertThat()
.statusCode(is(HttpServletResponse.SC_BAD_REQUEST));
}

private static Location buildTestLocation(String name, String locationKind) {
Expand Down
Loading