| 1465 | } |
| 1466 | return ROW(std::move(names), std::move(types)); |
| 1467 | } |
| 1468 | |
| 1469 | void addWindowFunction( |
| 1470 | std::stringstream& stream, |
| 1471 | const WindowNode::Function& windowFunction) { |
| 1472 | stream << windowFunction.functionCall->toString() << " "; |
| 1473 | if (windowFunction.ignoreNulls) { |
| 1474 | stream << "IGNORE NULLS "; |
| 1475 | } |
| 1476 | auto frame = windowFunction.frame; |
| 1477 | if (frame.startType == WindowNode::BoundType::kUnboundedFollowing) { |
| 1478 | BOLT_USER_FAIL("Window frame start cannot be UNBOUNDED FOLLOWING"); |
| 1479 | } |
| 1480 | if (frame.endType == WindowNode::BoundType::kUnboundedPreceding) { |
| 1481 | BOLT_USER_FAIL("Window frame end cannot be UNBOUNDED PRECEDING"); |
| 1482 | } |
| 1483 | |
| 1484 | stream << WindowNode::windowTypeName(frame.type) << " between "; |
| 1485 | if (frame.startValue) { |
| 1486 | addKeys(stream, {frame.startValue}); |
| 1487 | stream << " "; |
| 1488 | } |
| 1489 | stream << WindowNode::boundTypeName(frame.startType) << " and "; |
| 1490 | if (frame.endValue) { |
| 1491 | addKeys(stream, {frame.endValue}); |
| 1492 | stream << " "; |
| 1493 | } |
| 1494 | stream << WindowNode::boundTypeName(frame.endType); |
| 1495 | } |
| 1496 |
no test coverage detected