0

我检查了许多来源,但没有得到结果。

如何在 vertica 中创建一个函数以返回数据库中所有会话的计数?

有人可以在这个主题中提供一些想法或可能的例子。

4

3 回答 3

0

创建 C++(count_it.cpp)

#include "Vertica.h"
#include <time.h>
#include <sstream>
#include <iostream>

using namespace Vertica;
using namespace std;

class Average : public AggregateFunction
{
    virtual void initAggregate(ServerInterface &srvInterface, IntermediateAggs &aggs)
    {
        try {
            VNumeric &sum = aggs.getNumericRef(0);
            sum.setZero();

            vint &cnt = aggs.getIntRef(1);
            cnt = 0;
        } catch(exception& e) {
             vt_report_error(0, "Exception while initializing intermediate aggregates: [%s]", e.what());
        }
    }

    void aggregate(ServerInterface &srvInterface, BlockReader &argReader, IntermediateAggs &aggs)
    {
        try {
            VNumeric &sum = aggs.getNumericRef(0);
            vint     &cnt = aggs.getIntRef(1);

            do {
                const VNumeric &input = argReader.getNumericRef(0);
                if (!input.isNull()) {
                    sum.accumulate(&input);
                    sum.setZero();
                    cnt++;
                }
            } while (argReader.next());
        } catch(exception& e) {
            vt_report_error(0, "Exception while processing aggregate: [%s]", e.what());
        }
    }

    virtual void combine(ServerInterface &srvInterface,IntermediateAggs &aggs,MultipleIntermediateAggs &aggsOther)
    {
        try {
            VNumeric       &mySum      = aggs.getNumericRef(0);
            vint           &myCount    = aggs.getIntRef(1);

            do {
                const VNumeric &otherSum   = aggsOther.getNumericRef(0);
                const vint     &otherCount = aggsOther.getIntRef(1);

                mySum.accumulate(&otherSum);
                mySum.setZero();
                myCount += otherCount;

            } while (aggsOther.next());
        } catch(exception& e) {
            vt_report_error(0, "Exception while combining intermediate aggregates: [%s]", e.what());
        }
    }

    virtual void terminate(ServerInterface &srvInterface, BlockWriter &resWriter, IntermediateAggs &aggs)
    {
        try {
            const VerticaType  &numtype = aggs.getTypeMetaData().getColumnType(0);
            const VNumeric     &sum     = aggs.getNumericRef(0);
            sum.setZero();

            uint64* tmp = (uint64*)malloc(numtype.getMaxSize() / sizeof(uint64));
            VNumeric cnt(tmp, numtype.getNumericPrecision(), numtype.getNumericScale());
            cnt.copy(aggs.getIntRef(1));
            VNumeric &out = resWriter.getNumericRef();
            if (cnt.isZero())
                out.setZero();
            else
                out.add(&cnt,&sum);
        } catch(exception& e) {
            vt_report_error(0, "Exception while computing aggregate output: [%s]", e.what());
        }
    }

    InlineAggregate()
};


class count_itFactory : public AggregateFunctionFactory
{
    virtual void getPrototype(ServerInterface &srvfloaterface,ColumnTypes &argTypes,ColumnTypes &returnType)
    {
        argTypes.addNumeric();
        returnType.addNumeric();
    }

    virtual void getReturnType(ServerInterface &srvfloaterface,const SizedColumnTypes &inputTypes,SizedColumnTypes &outputTypes)
    {
        int int_part = inputTypes.getColumnType(0).getNumericPrecision();
        int frac_part = inputTypes.getColumnType(0).getNumericScale();
        outputTypes.addNumeric(int_part+frac_part, frac_part);
    }

    virtual void getIntermediateTypes(ServerInterface &srvInterface,const SizedColumnTypes &inputTypes,SizedColumnTypes &intermediateTypeMetaData)
    {
        int int_part = inputTypes.getColumnType(0).getNumericIntegral();
        int frac_part = inputTypes.getColumnType(0).getNumericFractional();
        intermediateTypeMetaData.addNumeric(int_part+frac_part, frac_part);
        intermediateTypeMetaData.addInt();
    }

    virtual AggregateFunction *createAggregateFunction(ServerInterface &srvfloaterface)
    { return vt_createFuncObject<Average>(srvfloaterface.allocator); }

};

RegisterFactory(count_itFactory);

编译 C++

g++ -D HAVE_LONG_INT_64 -I /opt/vertica/sdk/include -Wall -shared -Wno-unused-value -fPIC -o count_it.so /home/dbadmin/libs/count_it.cpp /opt/vertica/sdk/include/Vertica.cpp

创建库

CREATE LIBRARY count_it AS '/home/dbadmin/libs/count_it.so';

创建函数

CREATE AGGREGATE FUNCTION count_it AS LANGUAGE 'C++' NAME 'count_itFactory' LIBRARY count_it;

使用功能

  select count_it(client_id) from sesions;
于 2016-12-13T07:30:17.873 回答
0

您可以在 Vertica 中创建 UDX,但它没有会话句柄,因此您只能访问通过 API 公开的数据。会话数据不公开。

您需要执行查询才能执行此操作。

SELECT COUNT(*) FROM sessions;
于 2016-12-08T18:13:23.897 回答
0

看到这个帖子类似的东西:

SELECT
 node_name
,user_name
,'SELECT CLOSE_SESSION(''' || session_id || ''');'  AS CloseSession
,statement_start
,(GETDATE() - statement_start)::INTERVAL  AS current_statement_duration
,REGEXP_REPLACE(current_statement,'[rnt]',' ') AS current_statement
,session_id
,transaction_id
,statement_id
,client_hostname
,client_os
,login_timestamp
,runtime_priority
,ssl_state
,authentication_method
,transaction_start
,GETDATE() AS Today

FROM v_monitor.sessions 按 current_statement_duration DESC 排序;

您还可以从这篇文章中获得更多信息: 列出 Vertica 活动会话的脚本

于 2016-12-11T23:47:37.640 回答