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

allow to provide an additional url path #512

Merged
merged 4 commits into from
Nov 9, 2023
Merged
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
34 changes: 23 additions & 11 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,23 +1,34 @@
# Changelog

## Unreleased

### Features

- Add a new optional `path` setting to specify an additional URL path. [#512](https://github.com/grafana/clickhouse-datasource/pull/512)

## 3.3.0

### Features

- Support Point geo data type.

### Fixes

- Fix timeInterval_ms macro.
- Fix Table summary and Parts over time panels in Data Analysis dashboard.

### Upgrades

- Upgrade [grafana-plugin-sdk-go](https://github.com/grafana/grafana-plugin-sdk-go).

## 3.2.0

### Features

- Add `timeInterval_ms` macro to allow higher precision queries on DateTime64 columns. [#462](https://github.com/grafana/clickhouse-datasource/pull/462).

### Fixes

- Ensure databases, tables, and columns are escaped correctly. [#460](https://github.com/grafana/clickhouse-datasource/pull/460).
- Fix conditionAll handling. [#459](https://github.com/grafana/clickhouse-datasource/pull/459).
- Fix support for ad-hoc regexp filters: `=~`, `!~` [#414](https://github.com/grafana/clickhouse-datasource/pull/414).
Expand All @@ -42,19 +53,20 @@

- Custom ClickHouse settings can be set in data source settings. [Allow passing custom ClickHouse settings in datasource](https://github.com/grafana/clickhouse-datasource/pull/366)
- Histogram UI fixes [Histogram UI fixes](https://github.com/grafana/clickhouse-datasource/pull/363)
- Support filter/filter out logs view actions
- Fix undefined database name by default
- Reset level and time field properly on table/database change
- Make it possible to clear the level field (so the histogram will render without grouping by level)
- Fix filter value that gets stuck in the UI
- Support filter/filter out logs view actions
- Fix undefined database name by default
- Reset level and time field properly on table/database change
- Make it possible to clear the level field (so the histogram will render without grouping by level)
- Fix filter value that gets stuck in the UI
- Tracing dashboard added to default dashboards. [Tracing dashboard ](https://github.com/grafana/clickhouse-datasource/pull/336)

## 3.0.1-beta

- Users on v8.x of Grafana are encouraged to continue to use v2.2.0 of the plugin.
- Users on v8.x of Grafana are encouraged to continue to use v2.2.0 of the plugin.
- Users of Grafana v9.x can use v3 however it is beta and may contain bugs.

## 3.0.0

- **Feature** - [Logs volume histogram support](https://github.com/grafana/clickhouse-datasource/pull/352)
- **Chore** - Update clickhouse-go to v2.8.1

Expand All @@ -75,12 +87,12 @@
## 2.1.0

- **Fix** - Quote table names with dots by @slvrtrn in https://github.com/grafana/clickhouse-datasource/pull/298
- Add a predefined TimeRange filter if there is at least one DateTime* column by @slvrtrn in https://github.com/grafana/clickhouse-datasource/pull/304
- Add a predefined TimeRange filter if there is at least one DateTime\* column by @slvrtrn in https://github.com/grafana/clickhouse-datasource/pull/304

## 2.0.7

- **Fix** - Empty template variables used with the conditionalAll macro work the same as selecting All. [Allow empty Inputs for $__conditionalAll](https://github.com/grafana/clickhouse-datasource/issues/262)
- **Fix** - Intervals are limited to 1 second. [limit $__interval_s to at least 1 second](https://github.com/grafana/clickhouse-datasource/pull/270)
- **Fix** - Empty template variables used with the conditionalAll macro work the same as selecting All. [Allow empty Inputs for $\_\_conditionalAll](https://github.com/grafana/clickhouse-datasource/issues/262)
- **Fix** - Intervals are limited to 1 second. [limit $\_\_interval_s to at least 1 second](https://github.com/grafana/clickhouse-datasource/pull/270)
- **Chore** - Bump ClickHouse go API to v2.5.1 [Bump github.com/ClickHouse/clickhouse-go/v2 from 2.4.3 to 2.5.1](https://github.com/grafana/clickhouse-datasource/pull/283)

## 2.0.6
Expand Down Expand Up @@ -171,7 +183,7 @@

## 0.12.0

- **Feature** - Time series builder: use $__timeInterval macro on time field so buckets can be adjusted from query options.
- **Feature** - Time series builder: use $\_\_timeInterval macro on time field so buckets can be adjusted from query options.

## 0.11.0

Expand All @@ -191,7 +203,7 @@

## 0.9.11

- **Feature** - $__timeInterval(column) and $__interval_s macros
- **Feature** - $**timeInterval(column) and $**interval_s macros

## 0.9.10

Expand Down
1 change: 1 addition & 0 deletions pkg/plugin/driver.go
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,7 @@ func (h *Clickhouse) Connect(config backend.DataSourceInstanceSettings, message
},
TLS: tlsConfig,
Addr: []string{fmt.Sprintf("%s:%d", settings.Server, settings.Port)},
HttpUrlPath: settings.Path,
Auth: clickhouse.Auth{
Username: settings.Username,
Password: settings.Password,
Expand Down
6 changes: 4 additions & 2 deletions pkg/plugin/driver_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -124,11 +124,12 @@ func TestConnect(t *testing.T) {
ssl := getEnv("CLICKHOUSE_SSL", "false")
queryTimeoutNumber := 3600
queryTimeoutString := "3600"
path := "custom-path"
clickhouse := plugin.Clickhouse{}
t.Run("should not error when valid settings passed", func(t *testing.T) {
secure := map[string]string{}
secure["password"] = password
settings := backend.DataSourceInstanceSettings{JSONData: []byte(fmt.Sprintf(`{ "server": "%s", "port": %s, "username": "%s", "secure": %s, "queryTimeout": "%s"}`, host, port, username, ssl, queryTimeoutString)), DecryptedSecureJSONData: secure}
settings := backend.DataSourceInstanceSettings{JSONData: []byte(fmt.Sprintf(`{ "server": "%s", "port": %s, "path": "%s", "username": "%s", "secure": %s, "queryTimeout": "%s"}`, host, port, path, username, ssl, queryTimeoutString)), DecryptedSecureJSONData: secure}
_, err := clickhouse.Connect(settings, json.RawMessage{})
assert.Equal(t, nil, err)
})
Expand All @@ -147,11 +148,12 @@ func TestHTTPConnect(t *testing.T) {
username := getEnv("CLICKHOUSE_USERNAME", "default")
password := getEnv("CLICKHOUSE_PASSWORD", "")
ssl := getEnv("CLICKHOUSE_SSL", "false")
path := "custom-path"
clickhouse := plugin.Clickhouse{}
t.Run("should not error when valid settings passed", func(t *testing.T) {
secure := map[string]string{}
secure["password"] = password
settings := backend.DataSourceInstanceSettings{JSONData: []byte(fmt.Sprintf(`{ "server": "%s", "port": %s, "username": "%s", "secure": %s, "protocol": "http" }`, host, port, username, ssl)), DecryptedSecureJSONData: secure}
settings := backend.DataSourceInstanceSettings{JSONData: []byte(fmt.Sprintf(`{ "server": "%s", "port": %s, "path": "%s", "username": "%s", "secure": %s, "protocol": "http" }`, host, port, path, username, ssl)), DecryptedSecureJSONData: secure}
_, err := clickhouse.Connect(settings, json.RawMessage{})
assert.Equal(t, nil, err)
})
Expand Down
4 changes: 4 additions & 0 deletions pkg/plugin/settings.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import (
type Settings struct {
Server string `json:"server,omitempty"`
Port int64 `json:"port,omitempty"`
Path string `json:"path,omitempty"`
Username string `json:"username,omitempty"`
DefaultDatabase string `json:"defaultDatabase,omitempty"`
InsecureSkipVerify bool `json:"tlsSkipVerify,omitempty"`
Expand Down Expand Up @@ -70,6 +71,9 @@ func LoadSettings(config backend.DataSourceInstanceSettings) (settings Settings,
if jsonData["username"] != nil {
settings.Username = jsonData["username"].(string)
}
if jsonData["path"] != nil {
settings.Path = jsonData["path"].(string)
}
if jsonData["defaultDatabase"] != nil {
settings.DefaultDatabase = jsonData["defaultDatabase"].(string)
}
Expand Down
6 changes: 4 additions & 2 deletions pkg/plugin/settings_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,13 +28,14 @@ func TestLoadSettings(t *testing.T) {
args: args{
config: backend.DataSourceInstanceSettings{
UID: "ds-uid",
JSONData: []byte(`{ "server": "foo", "port": 443, "username": "baz", "defaultDatabase":"example", "tlsSkipVerify": true, "tlsAuth" : true, "tlsAuthWithCACert": true, "timeout": "10", "enableSecureSocksProxy": true}`),
JSONData: []byte(`{ "server": "foo", "port": 443, "path": "custom-path", "username": "baz", "defaultDatabase":"example", "tlsSkipVerify": true, "tlsAuth" : true, "tlsAuthWithCACert": true, "timeout": "10", "enableSecureSocksProxy": true}`),
DecryptedSecureJSONData: map[string]string{"password": "bar", "tlsCACert": "caCert", "tlsClientCert": "clientCert", "tlsClientKey": "clientKey", "secureSocksProxyPassword": "test"},
},
},
wantSettings: Settings{
Server: "foo",
Port: 443,
Path: "custom-path",
Username: "baz",
DefaultDatabase: "example",
InsecureSkipVerify: true,
Expand Down Expand Up @@ -64,13 +65,14 @@ func TestLoadSettings(t *testing.T) {
name: "should converting string values to the correct type)",
args: args{
config: backend.DataSourceInstanceSettings{
JSONData: []byte(`{"server": "test", "port": "443", "tlsSkipVerify": "true", "tlsAuth" : "true", "tlsAuthWithCACert": "true"}`),
JSONData: []byte(`{"server": "test", "port": "443", "path": "custom-path", "tlsSkipVerify": "true", "tlsAuth" : "true", "tlsAuthWithCACert": "true"}`),
DecryptedSecureJSONData: map[string]string{},
},
},
wantSettings: Settings{
Server: "test",
Port: 443,
Path: "custom-path",
InsecureSkipVerify: true,
TlsClientAuth: true,
TlsAuthWithCACert: true,
Expand Down
1 change: 1 addition & 0 deletions src/__mocks__/ConfigEditor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ export const mockConfigEditorProps = (overrides?: Partial<CHConfig>): Props => (
jsonData: {
server: 'foo.com',
port: 443,
path: '',
username: 'user',
protocol: 'native',
...overrides,
Expand Down
1 change: 1 addition & 0 deletions src/__mocks__/datasource.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ export const mockDatasource = new Datasource({
jsonData: {
server: 'foo.com',
port: 443,
path: '',
username: 'user',
defaultDatabase: 'foo',
protocol: Protocol.NATIVE,
Expand Down
5 changes: 5 additions & 0 deletions src/selectors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,11 @@ export const Components = {
placeholder: (secure: string) => `Typically ${secure === 'true' ? '9440' : '9000'}`,
tooltip: 'ClickHouse native TCP port. Typically 9000 for unsecure, 9440 for secure',
},
Path: {
label: 'Path',
placeholder: 'Additional URL path for HTTP requests',
tooltip: 'Additional URL path for HTTP requests',
},
Protocol: {
label: 'Protocol',
tooltip: 'Native or HTTP for transport',
Expand Down
1 change: 1 addition & 0 deletions src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ export interface CHConfig extends DataSourceJsonData {
server: string;
protocol: Protocol;
port: number;
path: string;
defaultDatabase?: string;
tlsSkipVerify?: boolean;
tlsAuth?: boolean;
Expand Down
14 changes: 14 additions & 0 deletions src/views/CHConfigEditor.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ describe('ConfigEditor', () => {
expect(screen.getByPlaceholderText(Components.ConfigEditor.ServerPort.placeholder('false'))).toBeInTheDocument();
expect(screen.getByPlaceholderText(Components.ConfigEditor.Username.placeholder)).toBeInTheDocument();
expect(screen.getByPlaceholderText(Components.ConfigEditor.Password.placeholder)).toBeInTheDocument();
expect(screen.getByPlaceholderText(Components.ConfigEditor.Path.placeholder)).toBeInTheDocument();
});
it('with password', async () => {
render(
Expand All @@ -39,6 +40,19 @@ describe('ConfigEditor', () => {
const a = screen.getByText('Reset');
expect(a).toBeInTheDocument();
});
it('with path', async () => {
const path = 'custom-path';
render(
<ConfigEditor
{...mockConfigEditorProps()}
options={{
...mockConfigEditorProps().options,
jsonData: { ...mockConfigEditorProps().options.jsonData, path },
}}
/>
);
expect(screen.queryByPlaceholderText(Components.ConfigEditor.Path.placeholder)).toHaveValue(path);
});
it('with secure connection', async () => {
render(
<ConfigEditor
Expand Down
12 changes: 12 additions & 0 deletions src/views/CHConfigEditor.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -173,7 +173,19 @@ export const ConfigEditor: React.FC<Props> = (props) => {
placeholder={Components.ConfigEditor.ServerPort.placeholder(jsonData.secure?.toString() || 'false')}
/>
</Field>
<Field label={Components.ConfigEditor.Path.label} description={Components.ConfigEditor.Path.tooltip}>
<Input
value={jsonData.path || ''}
name="path"
width={40}
onChange={onUpdateDatasourceJsonDataOption(props, 'path')}
label={Components.ConfigEditor.Path.label}
aria-label={Components.ConfigEditor.Path.label}
placeholder={Components.ConfigEditor.Path.placeholder}
/>
</Field>
<Field label={Components.ConfigEditor.Protocol.label} description={Components.ConfigEditor.Protocol.tooltip}>

<RadioButtonGroup<Protocol>
options={protocolOptions}
disabledOptions={[]}
Expand Down
Loading