/* *************************************************************************************** * Copyright (C) 2006 EsperTech, Inc. All rights reserved. * * http://www.espertech.com/esper * * http://www.espertech.com * * ---------------------------------------------------------------------------------- * * The software in this package is published under the terms of the GPL license * * a copy of which has been included with this distribution in the license.txt file. * *************************************************************************************** */ package com.espertech.esper.regression.resultset; import com.espertech.esper.client.*; import com.espertech.esper.client.scopetest.EPAssertionUtil; import com.espertech.esper.client.scopetest.SupportUpdateListener; import com.espertech.esper.client.soda.*; import com.espertech.esper.client.time.CurrentTimeEvent; import com.espertech.esper.metrics.instrumentation.InstrumentationHelper; import com.espertech.esper.supportregression.bean.SupportBean; import com.espertech.esper.supportregression.bean.SupportBeanNumeric; import com.espertech.esper.supportregression.bean.SupportBean_S0; import com.espertech.esper.supportregression.bean.SupportBean_S1; import com.espertech.esper.supportregression.client.SupportConfigFactory; import junit.framework.TestCase; public class TestRowLimit extends TestCase { private EPServiceProvider epService; private SupportUpdateListener listener; public void setUp() { Configuration config = SupportConfigFactory.getConfiguration(); config.addEventType("SupportBean", SupportBean.class); config.addEventType("SupportBeanNumeric", SupportBeanNumeric.class); epService = EPServiceProviderManager.getDefaultProvider(config); epService.initialize(); if (InstrumentationHelper.ENABLED) { InstrumentationHelper.startTest(epService, this.getClass(), getName());} listener = new SupportUpdateListener(); } protected void tearDown() throws Exception { if (InstrumentationHelper.ENABLED) { InstrumentationHelper.endTest();} listener = null; } public void testLimitOneWithOrderOptimization() { epService.getEPAdministrator().getConfiguration().addEventType(SupportBean_S0.class); epService.getEPAdministrator().getConfiguration().addEventType(SupportBean_S1.class); // batch-window assertions String eplWithBatchSingleKey = "select theString from SupportBean#length_batch(10) order by theString limit 1"; runAssertionLimitOneSingleKeySortBatch(eplWithBatchSingleKey); String eplWithBatchMultiKey = "select theString, intPrimitive from SupportBean#length_batch(5) order by theString asc, intPrimitive desc limit 1"; runAssertionLimitOneMultiKeySortBatch(eplWithBatchMultiKey); // context output-when-terminated assertions epService.getEPAdministrator().createEPL("create context StartS0EndS1 as start SupportBean_S0 end SupportBean_S1"); String eplContextSingleKey = "context StartS0EndS1 " + "select theString from SupportBean#keepall " + "output snapshot when terminated " + "order by theString limit 1"; runAssertionLimitOneSingleKeySortBatch(eplContextSingleKey); String eplContextMultiKey = "context StartS0EndS1 " + "select theString, intPrimitive from SupportBean#keepall " + "output snapshot when terminated " + "order by theString asc, intPrimitive desc limit 1"; runAssertionLimitOneMultiKeySortBatch(eplContextMultiKey); } private void runAssertionLimitOneMultiKeySortBatch(String epl) { EPStatement stmt = epService.getEPAdministrator().createEPL(epl); stmt.addListener(listener); sendSBSequenceAndAssert("F", 10, new Object[][] {{"F", 10}, {"X", 8}, {"F", 8}, {"G", 10}, {"X", 1}}); sendSBSequenceAndAssert("G", 12, new Object[][] {{"X", 10}, {"G", 12}, {"H", 100}, {"G", 10}, {"X", 1}}); sendSBSequenceAndAssert("G", 11, new Object[][] {{"G", 10}, {"G", 8}, {"G", 8}, {"G", 10}, {"G", 11}}); stmt.destroy(); } private void runAssertionLimitOneSingleKeySortBatch(String epl) { EPStatement stmt = epService.getEPAdministrator().createEPL(epl); stmt.addListener(listener); sendSBSequenceAndAssert("A", new String[] {"F", "Q", "R", "T", "M", "T", "A", "I", "P", "B"}); sendSBSequenceAndAssert("B", new String[] {"P", "Q", "P", "T", "P", "T", "P", "P", "P", "B"}); sendSBSequenceAndAssert("C", new String[] {"C", "P", "Q", "P", "T", "P", "T", "P", "P", "P", "X"}); stmt.destroy(); } public void testBatchNoOffsetNoOrder() { String statementString = "select irstream * from SupportBean#length_batch(3) limit 1"; EPStatement stmt = epService.getEPAdministrator().createEPL(statementString); runAssertion(stmt); } public void testLengthOffsetVariable() { epService.getEPAdministrator().createEPL("create variable int myrows = 2"); epService.getEPAdministrator().createEPL("create variable int myoffset = 1"); epService.getEPAdministrator().createEPL("on SupportBeanNumeric set myrows = intOne, myoffset = intTwo"); String statementString = "select * from SupportBean#length(5) output every 5 events limit myoffset, myrows"; EPStatement stmt = epService.getEPAdministrator().createEPL(statementString); runAssertionVariable(stmt); stmt.destroy(); listener.reset(); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(2, 1)); statementString = "select * from SupportBean#length(5) output every 5 events limit myrows offset myoffset"; stmt = epService.getEPAdministrator().createEPL(statementString); runAssertionVariable(stmt); stmt.destroy(); listener.reset(); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(2, 1)); EPStatementObjectModel model = epService.getEPAdministrator().compileEPL(statementString); assertEquals(statementString, model.toEPL()); stmt = epService.getEPAdministrator().create(model); runAssertionVariable(stmt); } public void testOrderBy() { String statementString = "select * from SupportBean#length(5) output every 5 events order by intPrimitive limit 2 offset 2"; EPStatement stmt = epService.getEPAdministrator().createEPL(statementString); String[] fields = "theString".split(","); stmt.addListener(listener); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E1", 90); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E2", 5); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E3", 60); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E1"}}); sendEvent("E4", 99); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E1"}, {"E4"}}); assertFalse(listener.isInvoked()); sendEvent("E5", 6); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E3"}, {"E1"}}); EPAssertionUtil.assertPropsPerRow(listener.getAndResetLastNewData(), fields, new Object[][]{{"E3"}, {"E1"}}); } private void runAssertionVariable(EPStatement stmt) { String[] fields = "theString".split(","); stmt.addListener(listener); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E1", 1); sendEvent("E2", 2); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E2"}}); sendEvent("E3", 3); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E2"}, {"E3"}}); sendEvent("E4", 4); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E2"}, {"E3"}}); assertFalse(listener.isInvoked()); sendEvent("E5", 5); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E2"}, {"E3"}}); EPAssertionUtil.assertPropsPerRow(listener.getAndResetLastNewData(), fields, new Object[][]{{"E2"}, {"E3"}}); sendEvent("E6", 6); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E3"}, {"E4"}}); assertFalse(listener.isInvoked()); // change variable values epService.getEPRuntime().sendEvent(new SupportBeanNumeric(2, 3)); sendEvent("E7", 7); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E6"}, {"E7"}}); assertFalse(listener.isInvoked()); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(-1, 0)); sendEvent("E8", 8); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E4"}, {"E5"}, {"E6"}, {"E7"}, {"E8"}}); assertFalse(listener.isInvoked()); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(10, 0)); sendEvent("E9", 9); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E5"}, {"E6"}, {"E7"}, {"E8"}, {"E9"}}); assertFalse(listener.isInvoked()); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(6, 3)); sendEvent("E10", 10); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E9"}, {"E10"}}); EPAssertionUtil.assertPropsPerRow(listener.getAndResetLastNewData(), fields, new Object[][]{{"E9"}, {"E10"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(1, 1)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E7"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(2, 1)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E7"}, {"E8"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(1, 2)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E8"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(6, 6)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(1, 4)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E10"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric((Integer) null, null)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E6"}, {"E7"}, {"E8"}, {"E9"}, {"E10"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(null, 2)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E8"}, {"E9"}, {"E10"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(2, null)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E6"}, {"E7"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(-1, 4)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E10"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(-1, 0)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E6"}, {"E7"}, {"E8"}, {"E9"}, {"E10"}}); epService.getEPRuntime().sendEvent(new SupportBeanNumeric(0, 0)); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); } public void testBatchOffsetNoOrderOM() { EPStatementObjectModel model = new EPStatementObjectModel(); model.setSelectClause(SelectClause.createWildcard()); model.getSelectClause().setStreamSelector(StreamSelector.RSTREAM_ISTREAM_BOTH); model.setFromClause(FromClause.create(FilterStream.create("SupportBean").addView("length_batch", Expressions.constant(3)))); model.setRowLimitClause(RowLimitClause.create(1)); String statementString = "select irstream * from SupportBean#length_batch(3) limit 1"; assertEquals(statementString, model.toEPL()); EPStatement stmt = epService.getEPAdministrator().create(model); runAssertion(stmt); stmt.destroy(); listener.reset(); model = epService.getEPAdministrator().compileEPL(statementString); assertEquals(statementString, model.toEPL()); stmt = epService.getEPAdministrator().create(model); runAssertion(stmt); } public void testFullyGroupedOrdered() { String statementString = "select theString, sum(intPrimitive) as mysum from SupportBean#length(5) group by theString order by sum(intPrimitive) limit 2"; EPStatement stmt = epService.getEPAdministrator().createEPL(statementString); String[] fields = "theString,mysum".split(","); stmt.addListener(listener); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E1", 90); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E1", 90}}); sendEvent("E2", 5); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E2", 5}, {"E1", 90}}); sendEvent("E3", 60); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E2", 5}, {"E3", 60}}); sendEvent("E3", 40); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E2", 5}, {"E1", 90}}); sendEvent("E2", 1000); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E1", 90}, {"E3", 100}}); } public void testEventPerRowUnGrouped() { sendTimer(1000); String statementString = "select theString, sum(intPrimitive) as mysum from SupportBean#length(5) output every 10 seconds order by theString desc limit 2"; EPStatement stmt = epService.getEPAdministrator().createEPL(statementString); String[] fields = "theString,mysum".split(","); stmt.addListener(listener); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E1", 10); sendEvent("E2", 5); sendEvent("E3", 20); sendEvent("E4", 30); sendTimer(11000); EPAssertionUtil.assertPropsPerRow(listener.getLastNewData(), fields, new Object[][]{{"E4", 65}, {"E3", 35}}); } public void testGroupedSnapshot() { sendTimer(1000); String statementString = "select theString, sum(intPrimitive) as mysum from SupportBean#length(5) group by theString output snapshot every 10 seconds order by sum(intPrimitive) desc limit 2"; EPStatement stmt = epService.getEPAdministrator().createEPL(statementString); String[] fields = "theString,mysum".split(","); stmt.addListener(listener); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E1", 10); sendEvent("E2", 5); sendEvent("E3", 20); sendEvent("E1", 30); sendTimer(11000); EPAssertionUtil.assertPropsPerRow(listener.getLastNewData(), fields, new Object[][]{{"E1", 40}, {"E3", 20}}); } public void testGroupedSnapshotNegativeRowcount() { sendTimer(1000); String statementString = "select theString, sum(intPrimitive) as mysum from SupportBean#length(5) group by theString output snapshot every 10 seconds order by sum(intPrimitive) desc limit -1 offset 1"; EPStatement stmt = epService.getEPAdministrator().createEPL(statementString); String[] fields = "theString,mysum".split(","); stmt.addListener(listener); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E1", 10); sendEvent("E2", 5); sendEvent("E3", 20); sendEvent("E1", 30); sendTimer(11000); EPAssertionUtil.assertPropsPerRow(listener.getLastNewData(), fields, new Object[][]{{"E3", 20}, {"E2", 5}}); } public void testInvalid() { epService.getEPAdministrator().createEPL("create variable string myrows = 'abc'"); tryInvalid("select * from SupportBean limit myrows", "Error starting statement: Limit clause requires a variable of numeric type [select * from SupportBean limit myrows]"); tryInvalid("select * from SupportBean limit 1, myrows", "Error starting statement: Limit clause requires a variable of numeric type [select * from SupportBean limit 1, myrows]"); tryInvalid("select * from SupportBean limit dummy", "Error starting statement: Limit clause variable by name 'dummy' has not been declared [select * from SupportBean limit dummy]"); tryInvalid("select * from SupportBean limit 1,dummy", "Error starting statement: Limit clause variable by name 'dummy' has not been declared [select * from SupportBean limit 1,dummy]"); } private void sendTimer(long timeInMSec) { CurrentTimeEvent theEvent = new CurrentTimeEvent(timeInMSec); EPRuntime runtime = epService.getEPRuntime(); runtime.sendEvent(theEvent); } private void runAssertion(EPStatement stmt) { String[] fields = "theString".split(","); stmt.addListener(listener); sendEvent("E1", 1); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E1"}}); sendEvent("E2", 2); assertFalse(listener.isInvoked()); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E1"}}); sendEvent("E3", 3); EPAssertionUtil.assertPropsPerRow(listener.getAndResetLastNewData(), fields, new Object[][]{{"E1"}}); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); sendEvent("E4", 4); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E4"}}); sendEvent("E5", 5); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, new Object[][]{{"E4"}}); sendEvent("E6", 6); EPAssertionUtil.assertPropsPerRow(listener.getLastNewData(), fields, new Object[][]{{"E4"}}); EPAssertionUtil.assertPropsPerRow(listener.getLastOldData(), fields, new Object[][]{{"E1"}}); EPAssertionUtil.assertPropsPerRow(stmt.iterator(), fields, null); } private void tryInvalid(String expression, String expected) { try { epService.getEPAdministrator().createEPL(expression); fail(); } catch (EPStatementException ex) { assertEquals(expected, ex.getMessage()); } } private void sendEvent(String theString, int intPrimitive) { epService.getEPRuntime().sendEvent(new SupportBean(theString, intPrimitive)); } private void sendSBSequenceAndAssert(String expected, String[] theStrings) { epService.getEPRuntime().sendEvent(new SupportBean_S0(0)); for (String theString : theStrings) { sendEvent(theString, 0); } epService.getEPRuntime().sendEvent(new SupportBean_S1(0)); EPAssertionUtil.assertProps(listener.assertOneGetNewAndReset(), "theString".split(","), new Object[]{expected}); } private void sendSBSequenceAndAssert(String expectedString, int expectedInt, Object[][] rows) { epService.getEPRuntime().sendEvent(new SupportBean_S0(0)); for (Object[] row : rows) { sendEvent(row[0].toString(), (Integer) row[1]); } epService.getEPRuntime().sendEvent(new SupportBean_S1(0)); EPAssertionUtil.assertProps(listener.assertOneGetNewAndReset(), "theString,intPrimitive".split(","), new Object[]{expectedString, expectedInt}); } }