2023-03-12 16:05:24 +00:00
|
|
|
#include <Functions/IFunction.h>
|
|
|
|
#include <Functions/FunctionFactory.h>
|
|
|
|
#include <Functions/FunctionHelpers.h>
|
|
|
|
|
|
|
|
namespace DB
|
|
|
|
{
|
|
|
|
|
|
|
|
namespace ErrorCodes
|
|
|
|
{
|
|
|
|
extern const int ILLEGAL_COLUMN;
|
|
|
|
}
|
|
|
|
|
|
|
|
namespace
|
|
|
|
{
|
|
|
|
|
|
|
|
class FunctionGetSubcolumn : public IFunction
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
static constexpr auto name = "getSubcolumn";
|
|
|
|
static FunctionPtr create(ContextPtr) { return std::make_shared<FunctionGetSubcolumn>(); }
|
|
|
|
|
|
|
|
String getName() const override { return name; }
|
|
|
|
size_t getNumberOfArguments() const override { return 2; }
|
|
|
|
bool isSuitableForShortCircuitArgumentsExecution(const DataTypesWithConstInfo &) const override { return true; }
|
|
|
|
bool useDefaultImplementationForConstants() const override { return true; }
|
|
|
|
ColumnNumbers getArgumentsThatAreAlwaysConstant() const override { return {1}; }
|
|
|
|
|
|
|
|
DataTypePtr getReturnTypeImpl(const ColumnsWithTypeAndName & arguments) const override
|
|
|
|
{
|
|
|
|
auto subcolumn_name = getSubcolumnName(arguments);
|
|
|
|
return arguments[0].type->getSubcolumnType(subcolumn_name);
|
|
|
|
}
|
|
|
|
|
|
|
|
ColumnPtr executeImpl(const ColumnsWithTypeAndName & arguments, const DataTypePtr &, size_t /*input_rows_count*/) const override
|
|
|
|
{
|
|
|
|
auto subcolumn_name = getSubcolumnName(arguments);
|
|
|
|
return arguments[0].type->getSubcolumn(subcolumn_name, arguments[0].column);
|
|
|
|
}
|
|
|
|
|
|
|
|
private:
|
2023-03-17 13:02:15 +00:00
|
|
|
static std::string_view getSubcolumnName(const ColumnsWithTypeAndName & arguments)
|
2023-03-12 16:05:24 +00:00
|
|
|
{
|
|
|
|
const auto * column = arguments[1].column.get();
|
|
|
|
if (!isString(arguments[1].type) || !column || !checkAndGetColumnConstStringOrFixedString(column))
|
|
|
|
throw Exception(ErrorCodes::ILLEGAL_COLUMN,
|
|
|
|
"The second argument of function {} should be a constant string with the name of a subcolumn", name);
|
|
|
|
|
|
|
|
return column->getDataAt(0).toView();
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
REGISTER_FUNCTION(GetSubcolumn)
|
|
|
|
{
|
2023-04-28 10:10:42 +00:00
|
|
|
factory.registerFunction<FunctionGetSubcolumn>(FunctionDocumentation{
|
|
|
|
.description=R"(
|
2023-03-16 20:22:25 +00:00
|
|
|
Receives the expression or identifier and constant string with the name of subcolumn.
|
|
|
|
|
|
|
|
Returns requested subcolumn extracted from the expression.
|
|
|
|
)",
|
2023-04-28 10:10:42 +00:00
|
|
|
.examples{{"getSubcolumn", "SELECT getSubcolumn(array_col, 'size0'), getSubcolumn(tuple_col, 'elem_name')", ""}},
|
|
|
|
.categories{"OtherFunctions"}
|
2023-03-16 20:22:25 +00:00
|
|
|
});
|
2023-03-12 16:05:24 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
}
|