Skip to content

[QUESTION] Decoding a column of type Array(Tuple(String, String)) #402

Open
@shteinitz

Description

@shteinitz

What is the correct way to decode a column whose ClickHouse type is Array(Tuple(String, String)) and map it to a Go [][]string?

For example, given the following SQL query:

SELECT [('one', 'two'), ('three', 'four')] AS arr;

...how do I replace the TODO comment with something that will map each tuple to a [][]string?

func arrayOfTuples() {
	ctx := context.Background()
	c, err := ch.Dial(ctx, ch.Options{Address: "localhost:9000"})
	if err != nil {
		panic(err)
	}

	arr := new(proto.ColArr[proto.ColTuple])
	if err := c.Do(ctx, ch.Query{
		Body: "SELECT [('one', 'two'), ('three', 'four')] AS arr",
		Result: proto.Results{
			{Name: "arr", Data: arr},
		},
		OnResult: func(ctx context.Context, b proto.Block) error {
			// TODO: Decode b and map its values to `[][]string`
			return nil
		},
	}); err != nil {
		panic(err)
	}
}

The difficulty is in figuring out how to allocate a proto.ColumnOf[proto.ColTuple], where ColTuple is of type tuple(string, string), and how to properly decode a block into it.

The equivalent clickhouse-go code works smoothly:

func clickhouseGoArrayOfTuples() {
	conn, err := clickhousego.Open(&clickhousego.Options{
		Addr: []string{"127.0.0.1:9000"},
		Auth: clickhousego.Auth{
			Database: "default",
			Username: "default",
			Password: "",
		},
	})
	if err != nil {
		panic(err)
	}

	rows, err := conn.Query(context.Background(), "SELECT [('one', 'two'), ('three', 'four')] AS arr")
	if err != nil {
		panic(err)
	}

	for rows.Next() {
		var arr [][]string
		if err := rows.Scan(&arr); err != nil {
			panic(err)
		}
		fmt.Println(arr)
	}
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions