Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix the generated password not being idempotent in the ClickHouse provisioner #6271

Open
wants to merge 3 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 9 additions & 1 deletion admin/provisioner/clickhousestatic/provisioner.go
Original file line number Diff line number Diff line change
Expand Up @@ -102,12 +102,20 @@ func (p *Provisioner) Provision(ctx context.Context, r *provisioner.Resource, op
return nil, fmt.Errorf("failed to create clickhouse database: %w", err)
}

// Idempotently create the user
// Idempotently create the user.
_, err = p.ch.ExecContext(ctx, fmt.Sprintf("CREATE USER IF NOT EXISTS %s IDENTIFIED WITH sha256_password BY ? DEFAULT DATABASE %s GRANTEES NONE", user, dbName), password)
if err != nil {
return nil, fmt.Errorf("failed to create clickhouse user: %w", err)
}

// When creating the user, the password assignment is not idempotent (if there are two concurrent invocations, we don't know which password was used).
// By adding the password separately, we ensure all passwords will work.
// NOTE: Requires ClickHouse 24.9 or later.
_, err = p.ch.ExecContext(ctx, fmt.Sprintf("ALTER USER %s ADD IDENTIFIED WITH sha256_password BY ?", user), password)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems risky, in a rare case of id collision, would it end up giving an existing project access to previously created DB ? However, in case of id collision we would have even bigger troubles..
Usually, locking on table name would be less prone to errors...

if err != nil {
return nil, fmt.Errorf("failed to add password for clickhouse user: %w", err)
}

// Grant privileges on the database to the user
_, err = p.ch.ExecContext(ctx, fmt.Sprintf(`
GRANT
Expand Down
4 changes: 2 additions & 2 deletions admin/provisioner/clickhousestatic/provisioner_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,11 +17,11 @@ import (
"go.uber.org/zap"
)

func Test(t *testing.T) {
func TestClickHouseStatic(t *testing.T) {
// Create a test ClickHouse cluster
container, err := testcontainersclickhouse.Run(
context.Background(),
"clickhouse/clickhouse-server:24.6.2.17",
"clickhouse/clickhouse-server:24.11.1.2557",
// Add a user config file that enables access management for the "default" user
testcontainers.CustomizeRequestOption(func(req *testcontainers.GenericContainerRequest) error {
req.Files = append(req.Files, testcontainers.ContainerFile{
Expand Down
Loading