Merge branch 'public-single-node' into pmm-6401-read-prometheus-data-files

This commit is contained in:
Aliaksandr Valialkin 2022-11-10 14:13:54 +02:00
commit 5ce8fa8b10
No known key found for this signature in database
GPG key ID: A72BEC6CD3D0DED1
80 changed files with 4139 additions and 2167 deletions

View file

@ -17,7 +17,7 @@ jobs:
- name: Setup Go - name: Setup Go
uses: actions/setup-go@main uses: actions/setup-go@main
with: with:
go-version: 1.19.2 go-version: 1.19.3
id: go id: go
- name: Code checkout - name: Code checkout
uses: actions/checkout@master uses: actions/checkout@master

View file

@ -19,7 +19,7 @@ jobs:
- name: Setup Go - name: Setup Go
uses: actions/setup-go@main uses: actions/setup-go@main
with: with:
go-version: 1.19.2 go-version: 1.19.3
id: go id: go
- name: Code checkout - name: Code checkout
uses: actions/checkout@master uses: actions/checkout@master

View file

@ -782,7 +782,7 @@ to your needs or when testing bugfixes.
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics` binary and puts it into the `bin` folder. It builds `victoria-metrics` binary and puts it into the `bin` folder.
@ -798,7 +798,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
### Development ARM build ### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics-linux-arm` or `make victoria-metrics-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics-linux-arm` or `make victoria-metrics-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics-linux-arm` or `victoria-metrics-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `victoria-metrics-linux-arm` or `victoria-metrics-linux-arm64` binary respectively and puts it into the `bin` folder.
@ -812,7 +812,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
`Pure Go` mode builds only Go code without [cgo](https://golang.org/cmd/cgo/) dependencies. `Pure Go` mode builds only Go code without [cgo](https://golang.org/cmd/cgo/) dependencies.
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics-pure` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics-pure` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics-pure` binary and puts it into the `bin` folder. It builds `victoria-metrics-pure` binary and puts it into the `bin` folder.

View file

@ -1027,7 +1027,7 @@ It may be needed to build `vmagent` from source code when developing or testing
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmagent` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmagent` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds the `vmagent` binary and puts it into the `bin` folder. It builds the `vmagent` binary and puts it into the `bin` folder.
@ -1056,7 +1056,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
### Development ARM build ### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmagent-linux-arm` or `make vmagent-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics) 2. Run `make vmagent-linux-arm` or `make vmagent-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics)
It builds `vmagent-linux-arm` or `vmagent-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `vmagent-linux-arm` or `vmagent-linux-arm64` binary respectively and puts it into the `bin` folder.

View file

@ -1314,7 +1314,7 @@ spec:
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmalert` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmalert` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmalert` binary and puts it into the `bin` folder. It builds `vmalert` binary and puts it into the `bin` folder.
@ -1330,7 +1330,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
### Development ARM build ### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmalert-linux-arm` or `make vmalert-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmalert-linux-arm` or `make vmalert-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmalert-linux-arm` or `vmalert-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `vmalert-linux-arm` or `vmalert-linux-arm64` binary respectively and puts it into the `bin` folder.

View file

@ -167,7 +167,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmauth` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmauth` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmauth` binary and puts it into the `bin` folder. It builds `vmauth` binary and puts it into the `bin` folder.

View file

@ -286,7 +286,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmbackup` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmbackup` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmbackup` binary and puts it into the `bin` folder. It builds `vmbackup` binary and puts it into the `bin` folder.

View file

@ -700,7 +700,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmctl` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmctl` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmctl` binary and puts it into the `bin` folder. It builds `vmctl` binary and puts it into the `bin` folder.
@ -729,7 +729,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
#### Development ARM build #### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmctl-linux-arm` or `make vmctl-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmctl-linux-arm` or `make vmctl-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmctl-linux-arm` or `vmctl-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `vmctl-linux-arm` or `vmctl-linux-arm64` binary respectively and puts it into the `bin` folder.

View file

@ -186,7 +186,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmrestore` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmrestore` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmrestore` binary and puts it into the `bin` folder. It builds `vmrestore` binary and puts it into the `bin` folder.

View file

@ -1,12 +1,12 @@
{ {
"files": { "files": {
"main.css": "./static/css/main.07bcc4ad.css", "main.css": "./static/css/main.07bcc4ad.css",
"main.js": "./static/js/main.1293a99e.js", "main.js": "./static/js/main.07d9522d.js",
"static/js/27.939f971b.chunk.js": "./static/js/27.939f971b.chunk.js", "static/js/27.939f971b.chunk.js": "./static/js/27.939f971b.chunk.js",
"index.html": "./index.html" "index.html": "./index.html"
}, },
"entrypoints": [ "entrypoints": [
"static/css/main.07bcc4ad.css", "static/css/main.07bcc4ad.css",
"static/js/main.1293a99e.js" "static/js/main.07d9522d.js"
] ]
} }

View file

@ -1 +1 @@
<!doctype html><html lang="en"><head><meta charset="utf-8"/><link rel="icon" href="./favicon.ico"/><meta name="viewport" content="width=device-width,initial-scale=1"/><meta name="theme-color" content="#000000"/><meta name="description" content="VM-UI is a metric explorer for Victoria Metrics"/><link rel="apple-touch-icon" href="./apple-touch-icon.png"/><link rel="icon" type="image/png" sizes="32x32" href="./favicon-32x32.png"><link rel="manifest" href="./manifest.json"/><title>VM UI</title><link rel="preconnect" href="https://fonts.googleapis.com"><link rel="preconnect" href="https://fonts.gstatic.com" crossorigin><link href="https://fonts.googleapis.com/css2?family=Lato:ital,wght@0,300;0,400;0,700;1,300;1,400;1,700&display=swap" rel="stylesheet"><script src="./dashboards/index.js" type="module"></script><script defer="defer" src="./static/js/main.1293a99e.js"></script><link href="./static/css/main.07bcc4ad.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div></body></html> <!doctype html><html lang="en"><head><meta charset="utf-8"/><link rel="icon" href="./favicon.ico"/><meta name="viewport" content="width=device-width,initial-scale=1"/><meta name="theme-color" content="#000000"/><meta name="description" content="VM-UI is a metric explorer for Victoria Metrics"/><link rel="apple-touch-icon" href="./apple-touch-icon.png"/><link rel="icon" type="image/png" sizes="32x32" href="./favicon-32x32.png"><link rel="manifest" href="./manifest.json"/><title>VM UI</title><link rel="preconnect" href="https://fonts.googleapis.com"><link rel="preconnect" href="https://fonts.gstatic.com" crossorigin><link href="https://fonts.googleapis.com/css2?family=Lato:ital,wght@0,300;0,400;0,700;1,300;1,400;1,700&display=swap" rel="stylesheet"><script src="./dashboards/index.js" type="module"></script><script defer="defer" src="./static/js/main.07d9522d.js"></script><link href="./static/css/main.07bcc4ad.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div></body></html>

View file

@ -13327,9 +13327,9 @@
} }
}, },
"node_modules/loader-utils": { "node_modules/loader-utils": {
"version": "2.0.2", "version": "2.0.3",
"resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.2.tgz", "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.3.tgz",
"integrity": "sha512-TM57VeHptv569d/GKh6TAYdzKblwDNiumOdkFnejjD0XwTH87K90w3O7AiJRqdQoXygvi1VQTJTLGhJl7WqA7A==", "integrity": "sha512-THWqIsn8QRnvLl0shHYVBN9syumU8pYWEHPTmkiVGd+7K5eFNVSY6AJhRvgGF70gg1Dz+l/k8WicvFCxdEs60A==",
"dev": true, "dev": true,
"peer": true, "peer": true,
"dependencies": { "dependencies": {
@ -16392,29 +16392,16 @@
} }
}, },
"node_modules/recursive-readdir": { "node_modules/recursive-readdir": {
"version": "2.2.2", "version": "2.2.3",
"resolved": "https://registry.npmjs.org/recursive-readdir/-/recursive-readdir-2.2.2.tgz", "resolved": "https://registry.npmjs.org/recursive-readdir/-/recursive-readdir-2.2.3.tgz",
"integrity": "sha512-nRCcW9Sj7NuZwa2XvH9co8NPeXUBhZP7CRKJtU+cS6PW9FpCIFoI5ib0NT1ZrbNuPoRy0ylyCaUL8Gih4LSyFg==", "integrity": "sha512-8HrF5ZsXk5FAH9dgsx3BlUer73nIhuj+9OrQwEbLTPOBzGkL1lsFCR01am+v+0m2Cmbs1nP12hLDl5FA7EszKA==",
"dev": true, "dev": true,
"peer": true, "peer": true,
"dependencies": { "dependencies": {
"minimatch": "3.0.4" "minimatch": "^3.0.5"
}, },
"engines": { "engines": {
"node": ">=0.10.0" "node": ">=6.0.0"
}
},
"node_modules/recursive-readdir/node_modules/minimatch": {
"version": "3.0.4",
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
"integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==",
"dev": true,
"peer": true,
"dependencies": {
"brace-expansion": "^1.1.7"
},
"engines": {
"node": "*"
} }
}, },
"node_modules/redent": { "node_modules/redent": {
@ -29433,9 +29420,9 @@
"peer": true "peer": true
}, },
"loader-utils": { "loader-utils": {
"version": "2.0.2", "version": "2.0.3",
"resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.2.tgz", "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-2.0.3.tgz",
"integrity": "sha512-TM57VeHptv569d/GKh6TAYdzKblwDNiumOdkFnejjD0XwTH87K90w3O7AiJRqdQoXygvi1VQTJTLGhJl7WqA7A==", "integrity": "sha512-THWqIsn8QRnvLl0shHYVBN9syumU8pYWEHPTmkiVGd+7K5eFNVSY6AJhRvgGF70gg1Dz+l/k8WicvFCxdEs60A==",
"dev": true, "dev": true,
"peer": true, "peer": true,
"requires": { "requires": {
@ -31623,25 +31610,13 @@
} }
}, },
"recursive-readdir": { "recursive-readdir": {
"version": "2.2.2", "version": "2.2.3",
"resolved": "https://registry.npmjs.org/recursive-readdir/-/recursive-readdir-2.2.2.tgz", "resolved": "https://registry.npmjs.org/recursive-readdir/-/recursive-readdir-2.2.3.tgz",
"integrity": "sha512-nRCcW9Sj7NuZwa2XvH9co8NPeXUBhZP7CRKJtU+cS6PW9FpCIFoI5ib0NT1ZrbNuPoRy0ylyCaUL8Gih4LSyFg==", "integrity": "sha512-8HrF5ZsXk5FAH9dgsx3BlUer73nIhuj+9OrQwEbLTPOBzGkL1lsFCR01am+v+0m2Cmbs1nP12hLDl5FA7EszKA==",
"dev": true, "dev": true,
"peer": true, "peer": true,
"requires": { "requires": {
"minimatch": "3.0.4" "minimatch": "^3.0.5"
},
"dependencies": {
"minimatch": {
"version": "3.0.4",
"resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
"integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==",
"dev": true,
"peer": true,
"requires": {
"brace-expansion": "^1.1.7"
}
}
} }
}, },
"redent": { "redent": {

View file

@ -86,22 +86,16 @@ const CustomPanel: FC = () => {
</Box> </Box>
{error && <Alert color="error" severity="error" sx={{whiteSpace: "pre-wrap", mt: 2}}>{error}</Alert>} {error && <Alert color="error" severity="error" sx={{whiteSpace: "pre-wrap", mt: 2}}>{error}</Alert>}
{warning && <Alert color="warning" severity="warning" sx={{whiteSpace: "pre-wrap", my: 2}}>{warning}</Alert>} {warning && <Alert color="warning" severity="warning" sx={{whiteSpace: "pre-wrap", my: 2}}>{warning}</Alert>}
{isTracingEnabled && <TracingsView
traces={tracesState}
onDeleteClick={handleTraceDelete}
/>}
{graphData && period && (displayType === "chart") && <> {graphData && period && (displayType === "chart") && <>
{isTracingEnabled && <TracingsView
traces={tracesState}
onDeleteClick={handleTraceDelete}
/>}
<GraphView data={graphData} period={period} customStep={customStep} query={query} yaxis={yaxis} <GraphView data={graphData} period={period} customStep={customStep} query={query} yaxis={yaxis}
setYaxisLimits={setYaxisLimits} setPeriod={setPeriod}/> setYaxisLimits={setYaxisLimits} setPeriod={setPeriod}/>
</>} </>}
{liveData && (displayType === "code") && <JsonView data={liveData}/>} {liveData && (displayType === "code") && <JsonView data={liveData}/>}
{liveData && (displayType === "table") && <> {liveData && (displayType === "table") && <TableView data={liveData} displayColumns={displayColumns}/>}
{isTracingEnabled && <TracingsView
traces={tracesState}
onDeleteClick={handleTraceDelete}
/>}
<TableView data={liveData} displayColumns={displayColumns}/>
</>}
</Box>} </Box>}
</Box> </Box>
</Box> </Box>

View file

@ -48,7 +48,7 @@ const Legend: FC<LegendProps> = ({labels, query, onChange}) => {
e.stopPropagation(); e.stopPropagation();
handleClickFreeField(freeField, fieldId); handleClickFreeField(freeField, fieldId);
}}> }}>
{f}: {legendItem.freeFormFields[f]} {freeField}
</span> </span>
</Tooltip>; </Tooltip>;
})} })}

View file

@ -15,7 +15,18 @@ The following tip changes can be tested by building VictoriaMetrics components f
## tip ## tip
## [v1.83.1](https://github.com/VictoriaMetrics/VictoriaMetrics/releases/tag/v1.83.1)
Released at 10-11-2022
* FEATURE: [vmagent](https://docs.victoriametrics.com/vmagent.html): expose `__meta_consul_partition` label for targets discovered via [consul_sd_configs](https://docs.victoriametrics.com/sd_configs.html#consul_sd_configs) in the same way as [Prometheus 2.40 does](https://github.com/prometheus/prometheus/pull/11482).
* FEATURE: [vmui](https://docs.victoriametrics.com/#vmui): show the [query trace](https://docs.victoriametrics.com/#query-tracing) in JSON view. See [this issue](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/2814). Thanks to @michal-kralik for [the pull request](https://github.com/VictoriaMetrics/VictoriaMetrics/pull/3316).
* BUGFIX: [VictoriaMetrics enterprise](https://docs.victoriametrics.com/enterprise.html): fix a panic at `vminsert` when the discovered list of `vmstorage` nodes is changed during [automatic vmstorage discovery](https://docs.victoriametrics.com/Cluster-VictoriaMetrics.html#automatic-vmstorage-discovery). See [this issue](https://github.com/VictoriaMetrics/VictoriaMetrics/pull/3329).
* BUGFIX: properly register new time series in per-day inverted index if they were ingested during the last 10 seconds of the day. See [this issue](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/3309). Thanks to @lmarszal for the bugreport and for the [initial fix](https://github.com/VictoriaMetrics/VictoriaMetrics/pull/3320). * BUGFIX: properly register new time series in per-day inverted index if they were ingested during the last 10 seconds of the day. See [this issue](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/3309). Thanks to @lmarszal for the bugreport and for the [initial fix](https://github.com/VictoriaMetrics/VictoriaMetrics/pull/3320).
* BUGFIX: reduce the increased memory usage spikes for some workloads. The issue was introduced in [v1.83.0](https://docs.victoriametrics.com/CHANGELOG.html#v1830).
* BUGFIX: properly accept [OpenTSDB telnet put lines](https://docs.victoriametrics.com/#sending-data-via-telnet-put-protocol) without tags without the need to specify the trailing whitespace. See [this issue](https://github.com/VictoriaMetrics/VictoriaMetrics/issues/3290).
## [v1.83.0](https://github.com/VictoriaMetrics/VictoriaMetrics/releases/tag/v1.83.0) ## [v1.83.0](https://github.com/VictoriaMetrics/VictoriaMetrics/releases/tag/v1.83.0)

View file

@ -783,7 +783,7 @@ to your needs or when testing bugfixes.
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics` binary and puts it into the `bin` folder. It builds `victoria-metrics` binary and puts it into the `bin` folder.
@ -799,7 +799,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
### Development ARM build ### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics-linux-arm` or `make victoria-metrics-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics-linux-arm` or `make victoria-metrics-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics-linux-arm` or `victoria-metrics-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `victoria-metrics-linux-arm` or `victoria-metrics-linux-arm64` binary respectively and puts it into the `bin` folder.
@ -813,7 +813,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
`Pure Go` mode builds only Go code without [cgo](https://golang.org/cmd/cgo/) dependencies. `Pure Go` mode builds only Go code without [cgo](https://golang.org/cmd/cgo/) dependencies.
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics-pure` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics-pure` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics-pure` binary and puts it into the `bin` folder. It builds `victoria-metrics-pure` binary and puts it into the `bin` folder.

View file

@ -786,7 +786,7 @@ to your needs or when testing bugfixes.
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics` binary and puts it into the `bin` folder. It builds `victoria-metrics` binary and puts it into the `bin` folder.
@ -802,7 +802,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
### Development ARM build ### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics-linux-arm` or `make victoria-metrics-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics-linux-arm` or `make victoria-metrics-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics-linux-arm` or `victoria-metrics-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `victoria-metrics-linux-arm` or `victoria-metrics-linux-arm64` binary respectively and puts it into the `bin` folder.
@ -816,7 +816,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
`Pure Go` mode builds only Go code without [cgo](https://golang.org/cmd/cgo/) dependencies. `Pure Go` mode builds only Go code without [cgo](https://golang.org/cmd/cgo/) dependencies.
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make victoria-metrics-pure` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make victoria-metrics-pure` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `victoria-metrics-pure` binary and puts it into the `bin` folder. It builds `victoria-metrics-pure` binary and puts it into the `bin` folder.

View file

@ -11,4 +11,4 @@ sort: 26
5. [Multi Retention Setup within VictoriaMetrics Cluster](https://docs.victoriametrics.com/guides/guide-vmcluster-multiple-retention-setup.html) 5. [Multi Retention Setup within VictoriaMetrics Cluster](https://docs.victoriametrics.com/guides/guide-vmcluster-multiple-retention-setup.html)
6. [Migrate from InfluxDB to VictoriaMetrics](https://docs.victoriametrics.com/guides/migrate-from-influx.html) 6. [Migrate from InfluxDB to VictoriaMetrics](https://docs.victoriametrics.com/guides/migrate-from-influx.html)
7. [Multi-regional setup with VictoriaMetrics: Dedicated regions for monitoring](https://docs.victoriametrics.com/guides/multi-regional-setup-dedicated-regions.html) 7. [Multi-regional setup with VictoriaMetrics: Dedicated regions for monitoring](https://docs.victoriametrics.com/guides/multi-regional-setup-dedicated-regions.html)
8. [How to delete or replace metrics in VictoriaMetrics](https://docs.victoriametrics.com/guides/guide-delete-and-replace-metrics.html) 8. [How to delete or replace metrics in VictoriaMetrics](https://docs.victoriametrics.com/guides/guide-delete-or-replace-metrics.html)

View file

@ -1591,7 +1591,7 @@ VMClusterSpec defines the desired state of VMCluster
| retentionPeriod | RetentionPeriod for the stored metrics Note VictoriaMetrics has data/ and indexdb/ folders metrics from data/ removed eventually as soon as partition leaves retention period reverse index data at indexdb rotates once at the half of configured retention period https://docs.victoriametrics.com/Single-server-VictoriaMetrics.html#retention | string | true | | retentionPeriod | RetentionPeriod for the stored metrics Note VictoriaMetrics has data/ and indexdb/ folders metrics from data/ removed eventually as soon as partition leaves retention period reverse index data at indexdb rotates once at the half of configured retention period https://docs.victoriametrics.com/Single-server-VictoriaMetrics.html#retention | string | true |
| replicationFactor | ReplicationFactor defines how many copies of data make among distinct storage nodes | *int32 | false | | replicationFactor | ReplicationFactor defines how many copies of data make among distinct storage nodes | *int32 | false |
| podSecurityPolicyName | PodSecurityPolicyName - defines name for podSecurityPolicy in case of empty value, prefixedName will be used. | string | false | | podSecurityPolicyName | PodSecurityPolicyName - defines name for podSecurityPolicy in case of empty value, prefixedName will be used. | string | false |
| serviceAccountName | ServiceAccountName is the name of the ServiceAccount to use to run the VMSelect Pods. | string | false | | serviceAccountName | ServiceAccountName is the name of the ServiceAccount to use to run the VMSelect, VMStorage and VMInsert Pods. | string | false |
| clusterVersion | ClusterVersion defines default images tag for all components. it can be overwritten with component specific image.tag value. | string | false | | clusterVersion | ClusterVersion defines default images tag for all components. it can be overwritten with component specific image.tag value. | string | false |
| imagePullSecrets | ImagePullSecrets An optional list of references to secrets in the same namespace to use for pulling images from registries see http://kubernetes.io/docs/user-guide/images#specifying-imagepullsecrets-on-a-pod | [][v1.LocalObjectReference](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.22/#localobjectreference-v1-core) | false | | imagePullSecrets | ImagePullSecrets An optional list of references to secrets in the same namespace to use for pulling images from registries see http://kubernetes.io/docs/user-guide/images#specifying-imagepullsecrets-on-a-pod | [][v1.LocalObjectReference](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.22/#localobjectreference-v1-core) | false |
| vmselect | | *[VMSelect](#vmselect) | false | | vmselect | | *[VMSelect](#vmselect) | false |

View file

@ -112,9 +112,15 @@ scrape_configs:
# datacenter: "..." # datacenter: "..."
# namespace is an optional Consul namespace. # namespace is an optional Consul namespace.
# See https://developer.hashicorp.com/consul/docs/enterprise/namespaces
# If the namespace isn't specified, then it is read from CONSUL_NAMESPACE environment var. # If the namespace isn't specified, then it is read from CONSUL_NAMESPACE environment var.
# namespace: "..." # namespace: "..."
# partition is an optional Consul partition.
# See https://developer.hashicorp.com/consul/docs/enterprise/admin-partitions
# If partition isn't specified, then the default partition is used.
# partition: "..."
# scheme is an optional scheme (http or https) to use for connecting to Consul server. # scheme is an optional scheme (http or https) to use for connecting to Consul server.
# By default http scheme is used. # By default http scheme is used.
# scheme: "..." # scheme: "..."
@ -151,7 +157,9 @@ The following meta labels are available on discovered targets during [relabeling
* `__meta_consul_dc`: the datacenter name for the target * `__meta_consul_dc`: the datacenter name for the target
* `__meta_consul_health`: the health status of the service * `__meta_consul_health`: the health status of the service
* `__meta_consul_metadata_<key>`: each node metadata key value of the target * `__meta_consul_metadata_<key>`: each node metadata key value of the target
* `__meta_consul_namespace`: namespace of the service - see [namespace docs](https://developer.hashicorp.com/consul/docs/enterprise/namespaces)
* `__meta_consul_node`: the node name defined for the target * `__meta_consul_node`: the node name defined for the target
* `__meta_consul_partition`: partition of the service - see [partition docs](https://developer.hashicorp.com/consul/docs/enterprise/admin-partitions)
* `__meta_consul_service_address`: the service address of the target * `__meta_consul_service_address`: the service address of the target
* `__meta_consul_service_id`: the service ID of the target * `__meta_consul_service_id`: the service ID of the target
* `__meta_consul_service_metadata_<key>`: each service metadata key value of the target * `__meta_consul_service_metadata_<key>`: each service metadata key value of the target

View file

@ -1031,7 +1031,7 @@ It may be needed to build `vmagent` from source code when developing or testing
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmagent` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmagent` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds the `vmagent` binary and puts it into the `bin` folder. It builds the `vmagent` binary and puts it into the `bin` folder.
@ -1060,7 +1060,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
### Development ARM build ### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmagent-linux-arm` or `make vmagent-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics) 2. Run `make vmagent-linux-arm` or `make vmagent-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics)
It builds `vmagent-linux-arm` or `vmagent-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `vmagent-linux-arm` or `vmagent-linux-arm64` binary respectively and puts it into the `bin` folder.

View file

@ -1318,7 +1318,7 @@ spec:
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmalert` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmalert` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmalert` binary and puts it into the `bin` folder. It builds `vmalert` binary and puts it into the `bin` folder.
@ -1334,7 +1334,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
### Development ARM build ### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmalert-linux-arm` or `make vmalert-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmalert-linux-arm` or `make vmalert-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmalert-linux-arm` or `vmalert-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `vmalert-linux-arm` or `vmalert-linux-arm64` binary respectively and puts it into the `bin` folder.

View file

@ -171,7 +171,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmauth` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmauth` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmauth` binary and puts it into the `bin` folder. It builds `vmauth` binary and puts it into the `bin` folder.

View file

@ -290,7 +290,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmbackup` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmbackup` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmbackup` binary and puts it into the `bin` folder. It builds `vmbackup` binary and puts it into the `bin` folder.

View file

@ -704,7 +704,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmctl` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmctl` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmctl` binary and puts it into the `bin` folder. It builds `vmctl` binary and puts it into the `bin` folder.
@ -733,7 +733,7 @@ ARM build may run on Raspberry Pi or on [energy-efficient ARM servers](https://b
#### Development ARM build #### Development ARM build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmctl-linux-arm` or `make vmctl-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmctl-linux-arm` or `make vmctl-linux-arm64` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmctl-linux-arm` or `vmctl-linux-arm64` binary respectively and puts it into the `bin` folder. It builds `vmctl-linux-arm` or `vmctl-linux-arm64` binary respectively and puts it into the `bin` folder.

View file

@ -190,7 +190,7 @@ It is recommended using [binary releases](https://github.com/VictoriaMetrics/Vic
### Development build ### Development build
1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.2. 1. [Install Go](https://golang.org/doc/install). The minimum supported version is Go 1.19.3.
2. Run `make vmrestore` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics). 2. Run `make vmrestore` from the root folder of [the repository](https://github.com/VictoriaMetrics/VictoriaMetrics).
It builds `vmrestore` binary and puts it into the `bin` folder. It builds `vmrestore` binary and puts it into the `bin` folder.

20
go.mod
View file

@ -3,7 +3,7 @@ module github.com/VictoriaMetrics/VictoriaMetrics
go 1.19 go 1.19
require ( require (
cloud.google.com/go/storage v1.27.0 cloud.google.com/go/storage v1.28.0
github.com/Azure/azure-sdk-for-go/sdk/azcore v1.2.0 github.com/Azure/azure-sdk-for-go/sdk/azcore v1.2.0
github.com/Azure/azure-sdk-for-go/sdk/storage/azblob v0.5.1 github.com/Azure/azure-sdk-for-go/sdk/storage/azblob v0.5.1
github.com/VictoriaMetrics/fastcache v1.12.0 github.com/VictoriaMetrics/fastcache v1.12.0
@ -31,25 +31,25 @@ require (
github.com/oklog/ulid v1.3.1 github.com/oklog/ulid v1.3.1
github.com/prometheus/common v0.37.0 // indirect github.com/prometheus/common v0.37.0 // indirect
github.com/prometheus/prometheus v1.8.2-0.20201119142752-3ad25a6dc3d9 github.com/prometheus/prometheus v1.8.2-0.20201119142752-3ad25a6dc3d9
github.com/urfave/cli/v2 v2.23.4 github.com/urfave/cli/v2 v2.23.5
github.com/valyala/fastjson v1.6.3 github.com/valyala/fastjson v1.6.3
github.com/valyala/fastrand v1.1.0 github.com/valyala/fastrand v1.1.0
github.com/valyala/fasttemplate v1.2.2 github.com/valyala/fasttemplate v1.2.2
github.com/valyala/gozstd v1.17.0 github.com/valyala/gozstd v1.17.0
github.com/valyala/quicktemplate v1.7.0 github.com/valyala/quicktemplate v1.7.0
golang.org/x/net v0.1.0 golang.org/x/net v0.2.0
golang.org/x/oauth2 v0.1.0 golang.org/x/oauth2 v0.2.0
golang.org/x/sys v0.1.0 golang.org/x/sys v0.2.0
google.golang.org/api v0.102.0 google.golang.org/api v0.103.0
gopkg.in/yaml.v2 v2.4.0 gopkg.in/yaml.v2 v2.4.0
) )
require ( require (
cloud.google.com/go v0.105.0 // indirect cloud.google.com/go v0.106.0 // indirect
cloud.google.com/go/compute v1.12.1 // indirect cloud.google.com/go/compute v1.12.1 // indirect
cloud.google.com/go/compute/metadata v0.2.1 // indirect cloud.google.com/go/compute/metadata v0.2.1 // indirect
cloud.google.com/go/iam v0.7.0 // indirect cloud.google.com/go/iam v0.7.0 // indirect
github.com/Azure/azure-sdk-for-go/sdk/internal v1.0.1 // indirect github.com/Azure/azure-sdk-for-go/sdk/internal v1.1.1 // indirect
github.com/VividCortex/ewma v1.2.0 // indirect github.com/VividCortex/ewma v1.2.0 // indirect
github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.4.9 // indirect github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream v1.4.9 // indirect
github.com/aws/aws-sdk-go-v2/credentials v1.12.23 // indirect github.com/aws/aws-sdk-go-v2/credentials v1.12.23 // indirect
@ -78,7 +78,7 @@ require (
github.com/mattn/go-isatty v0.0.16 // indirect github.com/mattn/go-isatty v0.0.16 // indirect
github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect
github.com/pkg/errors v0.9.1 // indirect github.com/pkg/errors v0.9.1 // indirect
github.com/prometheus/client_golang v1.13.1 // indirect github.com/prometheus/client_golang v1.14.0 // indirect
github.com/prometheus/client_model v0.3.0 // indirect github.com/prometheus/client_model v0.3.0 // indirect
github.com/prometheus/procfs v0.8.0 // indirect github.com/prometheus/procfs v0.8.0 // indirect
github.com/rivo/uniseg v0.4.2 // indirect github.com/rivo/uniseg v0.4.2 // indirect
@ -93,7 +93,7 @@ require (
golang.org/x/text v0.4.0 // indirect golang.org/x/text v0.4.0 // indirect
golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 // indirect golang.org/x/xerrors v0.0.0-20220907171357-04be3eba64a2 // indirect
google.golang.org/appengine v1.6.7 // indirect google.golang.org/appengine v1.6.7 // indirect
google.golang.org/genproto v0.0.0-20221027153422-115e99e71e1c // indirect google.golang.org/genproto v0.0.0-20221109142239-94d6d90a7d66 // indirect
google.golang.org/grpc v1.50.1 // indirect google.golang.org/grpc v1.50.1 // indirect
google.golang.org/protobuf v1.28.1 // indirect google.golang.org/protobuf v1.28.1 // indirect
) )

42
go.sum
View file

@ -15,8 +15,8 @@ cloud.google.com/go v0.56.0/go.mod h1:jr7tqZxxKOVYizybht9+26Z/gUq7tiRzu+ACVAMbKV
cloud.google.com/go v0.57.0/go.mod h1:oXiQ6Rzq3RAkkY7N6t3TcE6jE+CIBBbA36lwQ1JyzZs= cloud.google.com/go v0.57.0/go.mod h1:oXiQ6Rzq3RAkkY7N6t3TcE6jE+CIBBbA36lwQ1JyzZs=
cloud.google.com/go v0.62.0/go.mod h1:jmCYTdRCQuc1PHIIJ/maLInMho30T/Y0M4hTdTShOYc= cloud.google.com/go v0.62.0/go.mod h1:jmCYTdRCQuc1PHIIJ/maLInMho30T/Y0M4hTdTShOYc=
cloud.google.com/go v0.65.0/go.mod h1:O5N8zS7uWy9vkA9vayVHs65eM1ubvY4h553ofrNHObY= cloud.google.com/go v0.65.0/go.mod h1:O5N8zS7uWy9vkA9vayVHs65eM1ubvY4h553ofrNHObY=
cloud.google.com/go v0.105.0 h1:DNtEKRBAAzeS4KyIory52wWHuClNaXJ5x1F7xa4q+5Y= cloud.google.com/go v0.106.0 h1:AWaMWuZb2oFeiV91OfNHZbmwUhMVuXEaLPm9sqDAOl8=
cloud.google.com/go v0.105.0/go.mod h1:PrLgOJNe5nfE9UMxKxgXj4mD3voiP+YQ6gdt6KMFOKM= cloud.google.com/go v0.106.0/go.mod h1:5NEGxGuIeMQiPaWLwLYZ7kfNWiP6w1+QJK+xqyIT+dw=
cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o= cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o=
cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE= cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE=
cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc= cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc=
@ -32,7 +32,7 @@ cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7
cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk= cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk=
cloud.google.com/go/iam v0.7.0 h1:k4MuwOsS7zGJJ+QfZ5vBK8SgHBAvYN/23BWsiihJ1vs= cloud.google.com/go/iam v0.7.0 h1:k4MuwOsS7zGJJ+QfZ5vBK8SgHBAvYN/23BWsiihJ1vs=
cloud.google.com/go/iam v0.7.0/go.mod h1:H5Br8wRaDGNc8XP3keLc4unfUUZeyH3Sfl9XpQEYOeg= cloud.google.com/go/iam v0.7.0/go.mod h1:H5Br8wRaDGNc8XP3keLc4unfUUZeyH3Sfl9XpQEYOeg=
cloud.google.com/go/longrunning v0.1.1 h1:y50CXG4j0+qvEukslYFBCrzaXX0qpFbBzc3PchSu/LE= cloud.google.com/go/longrunning v0.3.0 h1:NjljC+FYPV3uh5/OwWT6pVU+doBqMg2x/rZlE+CamDs=
cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I= cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I=
cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw= cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw=
cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA= cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA=
@ -42,8 +42,8 @@ cloud.google.com/go/storage v1.5.0/go.mod h1:tpKbwo567HUNpVclU5sGELwQWBDZ8gh0Zeo
cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohlUTyfDhBk= cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohlUTyfDhBk=
cloud.google.com/go/storage v1.8.0/go.mod h1:Wv1Oy7z6Yz3DshWRJFhqM/UCfaWIRTdp0RXyy7KQOVs= cloud.google.com/go/storage v1.8.0/go.mod h1:Wv1Oy7z6Yz3DshWRJFhqM/UCfaWIRTdp0RXyy7KQOVs=
cloud.google.com/go/storage v1.10.0/go.mod h1:FLPqc6j+Ki4BU591ie1oL6qBQGu2Bl/tZ9ullr3+Kg0= cloud.google.com/go/storage v1.10.0/go.mod h1:FLPqc6j+Ki4BU591ie1oL6qBQGu2Bl/tZ9ullr3+Kg0=
cloud.google.com/go/storage v1.27.0 h1:YOO045NZI9RKfCj1c5A/ZtuuENUc8OAW+gHdGnDgyMQ= cloud.google.com/go/storage v1.28.0 h1:DLrIZ6xkeZX6K70fU/boWx5INJumt6f+nwwWSHXzzGY=
cloud.google.com/go/storage v1.27.0/go.mod h1:x9DOL8TK/ygDUMieqwfhdpQryTeEkhGKMi80i/iqR2s= cloud.google.com/go/storage v1.28.0/go.mod h1:qlgZML35PXA3zoEnIkiPLY4/TOkUleufRlu6qmcf7sI=
collectd.org v0.3.0/go.mod h1:A/8DzQBkF6abtvrT2j/AU/4tiBgJWYyh0y/oB/4MlWE= collectd.org v0.3.0/go.mod h1:A/8DzQBkF6abtvrT2j/AU/4tiBgJWYyh0y/oB/4MlWE=
dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU=
github.com/Azure/azure-sdk-for-go v48.2.0+incompatible h1:+t2P1j1r5N6lYgPiiz7ZbEVZFkWjVe9WhHbMm0gg8hw= github.com/Azure/azure-sdk-for-go v48.2.0+incompatible h1:+t2P1j1r5N6lYgPiiz7ZbEVZFkWjVe9WhHbMm0gg8hw=
@ -51,8 +51,8 @@ github.com/Azure/azure-sdk-for-go v48.2.0+incompatible/go.mod h1:9XXNKU+eRnpl9mo
github.com/Azure/azure-sdk-for-go/sdk/azcore v1.2.0 h1:sVW/AFBTGyJxDaMYlq0ct3jUXTtj12tQ6zE2GZUgVQw= github.com/Azure/azure-sdk-for-go/sdk/azcore v1.2.0 h1:sVW/AFBTGyJxDaMYlq0ct3jUXTtj12tQ6zE2GZUgVQw=
github.com/Azure/azure-sdk-for-go/sdk/azcore v1.2.0/go.mod h1:uGG2W01BaETf0Ozp+QxxKJdMBNRWPdstHG0Fmdwn1/U= github.com/Azure/azure-sdk-for-go/sdk/azcore v1.2.0/go.mod h1:uGG2W01BaETf0Ozp+QxxKJdMBNRWPdstHG0Fmdwn1/U=
github.com/Azure/azure-sdk-for-go/sdk/azidentity v1.1.0 h1:QkAcEIAKbNL4KoFr4SathZPhDhF4mVwpBMFlYjyAqy8= github.com/Azure/azure-sdk-for-go/sdk/azidentity v1.1.0 h1:QkAcEIAKbNL4KoFr4SathZPhDhF4mVwpBMFlYjyAqy8=
github.com/Azure/azure-sdk-for-go/sdk/internal v1.0.1 h1:XUNQ4mw+zJmaA2KXzP9JlQiecy1SI+Eog7xVkPiqIbg= github.com/Azure/azure-sdk-for-go/sdk/internal v1.1.1 h1:Oj853U9kG+RLTCQXpjvOnrv0WaZHxgmZz1TlLywgOPY=
github.com/Azure/azure-sdk-for-go/sdk/internal v1.0.1/go.mod h1:eWRD7oawr1Mu1sLCawqVc0CUiF43ia3qQMxLscsKQ9w= github.com/Azure/azure-sdk-for-go/sdk/internal v1.1.1/go.mod h1:eWRD7oawr1Mu1sLCawqVc0CUiF43ia3qQMxLscsKQ9w=
github.com/Azure/azure-sdk-for-go/sdk/storage/azblob v0.5.1 h1:BMTdr+ib5ljLa9MxTJK8x/Ds0MbBb4MfuW5BL0zMJnI= github.com/Azure/azure-sdk-for-go/sdk/storage/azblob v0.5.1 h1:BMTdr+ib5ljLa9MxTJK8x/Ds0MbBb4MfuW5BL0zMJnI=
github.com/Azure/azure-sdk-for-go/sdk/storage/azblob v0.5.1/go.mod h1:c6WvOhtmjNUWbLfOG1qxM/q0SPvQNSVJvolm+C52dIU= github.com/Azure/azure-sdk-for-go/sdk/storage/azblob v0.5.1/go.mod h1:c6WvOhtmjNUWbLfOG1qxM/q0SPvQNSVJvolm+C52dIU=
github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8= github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8=
@ -727,8 +727,8 @@ github.com/prometheus/client_golang v1.7.1/go.mod h1:PY5Wy2awLA44sXw4AOSfFBetzPP
github.com/prometheus/client_golang v1.8.0/go.mod h1:O9VU6huf47PktckDQfMTX0Y8tY0/7TSWwj+ITvv0TnM= github.com/prometheus/client_golang v1.8.0/go.mod h1:O9VU6huf47PktckDQfMTX0Y8tY0/7TSWwj+ITvv0TnM=
github.com/prometheus/client_golang v1.11.0/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0= github.com/prometheus/client_golang v1.11.0/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0=
github.com/prometheus/client_golang v1.12.1/go.mod h1:3Z9XVyYiZYEO+YQWt3RD2R3jrbd179Rt297l4aS6nDY= github.com/prometheus/client_golang v1.12.1/go.mod h1:3Z9XVyYiZYEO+YQWt3RD2R3jrbd179Rt297l4aS6nDY=
github.com/prometheus/client_golang v1.13.1 h1:3gMjIY2+/hzmqhtUC/aQNYldJA6DtH3CgQvwS+02K1c= github.com/prometheus/client_golang v1.14.0 h1:nJdhIvne2eSX/XRAFV9PcvFFRbrjbcTUj0VP62TMhnw=
github.com/prometheus/client_golang v1.13.1/go.mod h1:vTeo+zgvILHsnnj/39Ou/1fPN5nJFOEMgftOUOmlvYQ= github.com/prometheus/client_golang v1.14.0/go.mod h1:8vpkKitgIVNcqrRBWh1C4TIUQgYNtG/XQE4E/Zae36Y=
github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo= github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo=
github.com/prometheus/client_model v0.0.0-20190115171406-56726106282f/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo= github.com/prometheus/client_model v0.0.0-20190115171406-56726106282f/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo=
github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA=
@ -834,8 +834,8 @@ github.com/uber/jaeger-client-go v2.25.0+incompatible/go.mod h1:WVhlPFC8FDjOFMMW
github.com/uber/jaeger-lib v2.4.0+incompatible/go.mod h1:ComeNDZlWwrWnDv8aPp0Ba6+uUTzImX/AauajbLI56U= github.com/uber/jaeger-lib v2.4.0+incompatible/go.mod h1:ComeNDZlWwrWnDv8aPp0Ba6+uUTzImX/AauajbLI56U=
github.com/urfave/cli v1.20.0/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA= github.com/urfave/cli v1.20.0/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA=
github.com/urfave/cli v1.22.1/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= github.com/urfave/cli v1.22.1/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0=
github.com/urfave/cli/v2 v2.23.4 h1:gcaHwki8kGX6lfp2zz7irxu7eZkcIl1Xapt6XW0Ynqc= github.com/urfave/cli/v2 v2.23.5 h1:xbrU7tAYviSpqeR3X4nEFWUdB/uDZ6DE+HxmRU7Xtyw=
github.com/urfave/cli/v2 v2.23.4/go.mod h1:1CNUng3PtjQMtRzJO4FMXBQvkGtuYRxxiR9xMa7jMwI= github.com/urfave/cli/v2 v2.23.5/go.mod h1:GHupkWPMM0M/sj1a2b4wUrWBPzazNrIjouW6fmdJLxc=
github.com/valyala/bytebufferpool v1.0.0 h1:GqA5TC/0021Y/b9FG4Oi9Mr3q7XYx6KllzawFIhcdPw= github.com/valyala/bytebufferpool v1.0.0 h1:GqA5TC/0021Y/b9FG4Oi9Mr3q7XYx6KllzawFIhcdPw=
github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc= github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyCJ6HpOuEn7z0Csc=
github.com/valyala/fasthttp v1.30.0/go.mod h1:2rsYD01CKFrjjsvFxx75KlEUNpWNBY9JWD3K/7o2Cus= github.com/valyala/fasthttp v1.30.0/go.mod h1:2rsYD01CKFrjjsvFxx75KlEUNpWNBY9JWD3K/7o2Cus=
@ -998,8 +998,8 @@ golang.org/x/net v0.0.0-20210510120150-4163338589ed/go.mod h1:9nx3DQGgdP8bBQD5qx
golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20210525063256-abc453219eb5/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
golang.org/x/net v0.1.0 h1:hZ/3BUoy5aId7sCpA/Tc5lt8DkFgdVS2onTpJsZ/fl0= golang.org/x/net v0.2.0 h1:sZfSu1wtKLGlWI4ZZayP0ck9Y73K1ynO6gqzTdBVdPU=
golang.org/x/net v0.1.0/go.mod h1:Cx3nUiGt4eDBEyega/BKRp+/AlGL8hYe7U9odMt2Cco= golang.org/x/net v0.2.0/go.mod h1:KqCZLdyyvdV855qA2rE3GC2aiw5xGR5TEjj8smXukLY=
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
@ -1009,8 +1009,8 @@ golang.org/x/oauth2 v0.0.0-20200902213428-5d25da1a8d43/go.mod h1:KelEdhl1UZF7XfJ
golang.org/x/oauth2 v0.0.0-20201109201403-9fd604954f58/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= golang.org/x/oauth2 v0.0.0-20201109201403-9fd604954f58/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A=
golang.org/x/oauth2 v0.0.0-20210514164344-f6687ab2804c/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A= golang.org/x/oauth2 v0.0.0-20210514164344-f6687ab2804c/go.mod h1:KelEdhl1UZF7XfJ4dDtk6s++YSgaE7mD/BuKKDLBl4A=
golang.org/x/oauth2 v0.0.0-20220223155221-ee480838109b/go.mod h1:DAh4E804XQdzx2j+YRIaUnCqCV2RuMz24cGBJ5QYIrc= golang.org/x/oauth2 v0.0.0-20220223155221-ee480838109b/go.mod h1:DAh4E804XQdzx2j+YRIaUnCqCV2RuMz24cGBJ5QYIrc=
golang.org/x/oauth2 v0.1.0 h1:isLCZuhj4v+tYv7eskaN4v/TM+A1begWWgyVJDdl1+Y= golang.org/x/oauth2 v0.2.0 h1:GtQkldQ9m7yvzCL1V+LrYow3Khe0eJH0w7RbX/VbaIU=
golang.org/x/oauth2 v0.1.0/go.mod h1:G9FE4dLTsbXUu90h/Pf85g4w1D+SSAgR+q46nJZ8M4A= golang.org/x/oauth2 v0.2.0/go.mod h1:Cwn6afJ8jrQwYMxQDTpISoXmXW9I6qF6vDeuuoX3Ibs=
golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
@ -1097,8 +1097,8 @@ golang.org/x/sys v0.0.0-20220114195835-da31bd327af9/go.mod h1:oPkhp1MJrh7nUepCBc
golang.org/x/sys v0.0.0-20220405052023-b1e9470b6e64/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220405052023-b1e9470b6e64/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.1.0 h1:kunALQeHf1/185U1i0GOB/fy1IPRDDpuoOOqRReG57U= golang.org/x/sys v0.2.0 h1:ljd4t30dBnAvMZaQCevtY0xLLD0A+bRZXbgLMLU1F/A=
golang.org/x/sys v0.1.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.2.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
@ -1211,8 +1211,8 @@ google.golang.org/api v0.28.0/go.mod h1:lIXQywCXRcnZPGlsd8NbLnOjtAoL6em04bJ9+z0M
google.golang.org/api v0.29.0/go.mod h1:Lcubydp8VUV7KeIHD9z2Bys/sm/vGKnG1UHuDBSrHWM= google.golang.org/api v0.29.0/go.mod h1:Lcubydp8VUV7KeIHD9z2Bys/sm/vGKnG1UHuDBSrHWM=
google.golang.org/api v0.30.0/go.mod h1:QGmEvQ87FHZNiUVJkT14jQNYJ4ZJjdRF23ZXz5138Fc= google.golang.org/api v0.30.0/go.mod h1:QGmEvQ87FHZNiUVJkT14jQNYJ4ZJjdRF23ZXz5138Fc=
google.golang.org/api v0.35.0/go.mod h1:/XrVsuzM0rZmrsbjJutiuftIzeuTQcEeaYcSk/mQ1dg= google.golang.org/api v0.35.0/go.mod h1:/XrVsuzM0rZmrsbjJutiuftIzeuTQcEeaYcSk/mQ1dg=
google.golang.org/api v0.102.0 h1:JxJl2qQ85fRMPNvlZY/enexbxpCjLwGhZUtgfGeQ51I= google.golang.org/api v0.103.0 h1:9yuVqlu2JCvcLg9p8S3fcFLZij8EPSyvODIY1rkMizQ=
google.golang.org/api v0.102.0/go.mod h1:3VFl6/fzoA+qNuS1N1/VfXY4LjoXN/wzeIp7TweWwGo= google.golang.org/api v0.103.0/go.mod h1:hGtW6nK1AC+d9si/UBhw8Xli+QMOf6xyNAyJw4qU9w0=
google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
google.golang.org/appengine v1.2.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.2.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
@ -1256,8 +1256,8 @@ google.golang.org/genproto v0.0.0-20200729003335-053ba62fc06f/go.mod h1:FWY/as6D
google.golang.org/genproto v0.0.0-20200804131852-c06518451d9c/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20200804131852-c06518451d9c/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
google.golang.org/genproto v0.0.0-20200825200019-8632dd797987/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20200825200019-8632dd797987/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
google.golang.org/genproto v0.0.0-20200904004341-0bd0a958aa1d/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20200904004341-0bd0a958aa1d/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no=
google.golang.org/genproto v0.0.0-20221027153422-115e99e71e1c h1:QgY/XxIAIeccR+Ca/rDdKubLIU9rcJ3xfy1DC/Wd2Oo= google.golang.org/genproto v0.0.0-20221109142239-94d6d90a7d66 h1:wx7sJ5GRBQLRcslTNcrTklsHhHevQvxgztW18txbbZM=
google.golang.org/genproto v0.0.0-20221027153422-115e99e71e1c/go.mod h1:CGI5F/G+E5bKwmfYo09AXuVN4dD894kIKUFmVbP2/Fo= google.golang.org/genproto v0.0.0-20221109142239-94d6d90a7d66/go.mod h1:rZS5c/ZVYMaOGBfO68GWtjOw/eLaZM1X6iVtgjZ+EWg=
google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs= google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs=
google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
google.golang.org/grpc v1.20.0/go.mod h1:chYK+tFQF0nDUGJgXMSgLCQk3phJEuONr2DCgLDdAQM= google.golang.org/grpc v1.20.0/go.mod h1:chYK+tFQF0nDUGJgXMSgLCQk3phJEuONr2DCgLDdAQM=

View file

@ -14,9 +14,14 @@ type SDConfig struct {
Server string `yaml:"server,omitempty"` Server string `yaml:"server,omitempty"`
Token *promauth.Secret `yaml:"token"` Token *promauth.Secret `yaml:"token"`
Datacenter string `yaml:"datacenter"` Datacenter string `yaml:"datacenter"`
// Namespace only supported at enterprise consul. // Namespace only supported at enterprise consul.
// https://www.consul.io/docs/enterprise/namespaces // https://www.consul.io/docs/enterprise/namespaces
Namespace string `yaml:"namespace,omitempty"` Namespace string `yaml:"namespace,omitempty"`
// Partition only supported at enteprise consul.
// https://developer.hashicorp.com/consul/docs/enterprise/admin-partitions
Partition string `yaml:"partition,omitempty"`
Scheme string `yaml:"scheme,omitempty"` Scheme string `yaml:"scheme,omitempty"`
Username string `yaml:"username"` Username string `yaml:"username"`
Password *promauth.Secret `yaml:"password"` Password *promauth.Secret `yaml:"password"`

View file

@ -38,6 +38,7 @@ type Service struct {
Service string Service string
Address string Address string
Namespace string Namespace string
Partition string
Port int Port int
Tags []string Tags []string
Meta map[string]string Meta map[string]string
@ -83,6 +84,7 @@ func (sn *ServiceNode) appendTargetLabels(ms []map[string]string, serviceName, t
"__meta_consul_dc": sn.Node.Datacenter, "__meta_consul_dc": sn.Node.Datacenter,
"__meta_consul_health": aggregatedStatus(sn.Checks), "__meta_consul_health": aggregatedStatus(sn.Checks),
"__meta_consul_namespace": sn.Service.Namespace, "__meta_consul_namespace": sn.Service.Namespace,
"__meta_consul_partition": sn.Service.Partition,
"__meta_consul_node": sn.Node.Node, "__meta_consul_node": sn.Node.Node,
"__meta_consul_service": serviceName, "__meta_consul_service": serviceName,
"__meta_consul_service_address": sn.Service.Address, "__meta_consul_service_address": sn.Service.Address,

View file

@ -64,7 +64,8 @@ func TestParseServiceNodesSuccess(t *testing.T) {
"Passing": 10, "Passing": 10,
"Warning": 1 "Warning": 1
}, },
"Namespace": "ns-dev" "Namespace": "ns-dev",
"Partition": "part-foobar"
}, },
"Checks": [ "Checks": [
{ {
@ -120,6 +121,7 @@ func TestParseServiceNodesSuccess(t *testing.T) {
"__meta_consul_metadata_instance_type": "t2.medium", "__meta_consul_metadata_instance_type": "t2.medium",
"__meta_consul_namespace": "ns-dev", "__meta_consul_namespace": "ns-dev",
"__meta_consul_node": "foobar", "__meta_consul_node": "foobar",
"__meta_consul_partition": "part-foobar",
"__meta_consul_service": "redis", "__meta_consul_service": "redis",
"__meta_consul_service_address": "10.1.10.12", "__meta_consul_service_address": "10.1.10.12",
"__meta_consul_service_id": "redis", "__meta_consul_service_id": "redis",

View file

@ -49,7 +49,10 @@ func newConsulWatcher(client *discoveryutils.Client, sdc *SDConfig, datacenter,
baseQueryArgs += "&stale" baseQueryArgs += "&stale"
} }
if namespace != "" { if namespace != "" {
baseQueryArgs += "&ns=" + namespace baseQueryArgs += "&ns=" + url.QueryEscape(namespace)
}
if sdc.Partition != "" {
baseQueryArgs += "&partition=" + url.QueryEscape(sdc.Partition)
} }
for k, v := range sdc.NodeMeta { for k, v := range sdc.NodeMeta {
baseQueryArgs += "&node-meta=" + url.QueryEscape(k+":"+v) baseQueryArgs += "&node-meta=" + url.QueryEscape(k+":"+v)

View file

@ -465,6 +465,358 @@ func TestScrapeWorkScrapeInternalSuccess(t *testing.T) {
`) `)
} }
func TestAddRowToTimeseriesNoRelabeling(t *testing.T) {
f := func(row string, cfg *ScrapeWork, dataExpected string) {
t.Helper()
sw := scrapeWork{
Config: cfg,
}
var wc writeRequestCtx
r := parsePromRow(row)
sw.addRowToTimeseries(&wc, r, r.Timestamp, false)
tss := wc.writeRequest.Timeseries
tssExpected := parseData(dataExpected)
if err := expectEqualTimeseries(tss, tssExpected); err != nil {
t.Fatalf("%s\ngot\n%v\nwant\n%v", err, tss, tssExpected)
}
}
// HonorLabels=false, empty Labels and ExternalLabels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: false,
},
`metric 0 123`)
f(`metric{a="f"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: false,
},
`metric{a="f"} 0 123`)
// HonorLabels=true, empty Labels and ExternalLabels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: true,
},
`metric 0 123`)
f(`metric{a="f"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: true,
},
`metric{a="f"} 0 123`)
// HonorLabels=false, non-empty Labels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: false,
},
`metric{a="f"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: false,
},
`metric{a="f",foo="bar"} 0 123`)
// HonorLabels=true, non-empty Labels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: true,
},
`metric{a="f"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: true,
},
`metric{a="f",foo="bar"} 0 123`)
// HonorLabels=false, non-empty ExternalLabels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: false,
},
`metric{a="f"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: false,
},
`metric{a="f",foo="bar"} 0 123`)
// HonorLabels=true, non-empty ExternalLabels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: true,
},
`metric{a="f"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: true,
},
`metric{a="f",foo="bar"} 0 123`)
// HonorLabels=false, non-empty Labels and ExternalLabels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "x",
Value: "y",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: false,
},
`metric{a="f",x="y"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "x",
Value: "y",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: false,
},
`metric{a="f",foo="bar",x="y"} 0 123`)
// HonorLabels=true, non-empty Labels and ExternalLabels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "x",
Value: "y",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: true,
},
`metric{a="f",x="y"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "x",
Value: "y",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: true,
},
`metric{a="f",foo="bar",x="y"} 0 123`)
// HonorLabels=false, clashing Labels and metric label
f(`metric{a="b"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: false,
},
`metric{a="f",exported_a="b"} 0 123`)
// HonorLabels=true, clashing Labels and metric label
f(`metric{a="b"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
ExternalLabels: []prompbmarshal.Label{},
HonorLabels: true,
},
`metric{a="b"} 0 123`)
// HonorLabels=false, clashing ExternalLabels and metric label
f(`metric{a="b"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: false,
},
`metric{a="f",exported_a="b"} 0 123`)
// HonorLabels=true, clashing ExternalLabels and metric label
f(`metric{a="b"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: true,
},
`metric{a="b"} 0 123`)
// HonorLabels=false, clashing Labels and ExternalLAbels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "e",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: false,
},
`metric{a="f",exported_a="e"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "e",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: false,
},
`metric{a="f",foo="bar",exported_a="e"} 0 123`)
// HonorLabels=true, clashing Labels and ExternalLAbels
f(`metric 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "e",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: true,
},
`metric{a="e"} 0 123`)
f(`metric{foo="bar"} 0 123`,
&ScrapeWork{
Labels: []prompbmarshal.Label{
{
Name: "a",
Value: "e",
},
},
ExternalLabels: []prompbmarshal.Label{
{
Name: "a",
Value: "f",
},
},
HonorLabels: true,
},
`metric{a="e",foo="bar"} 0 123`)
}
func parsePromRow(data string) *parser.Row {
var rows parser.Rows
errLogger := func(s string) {
panic(fmt.Errorf("unexpected error when unmarshaling Prometheus rows: %s", s))
}
rows.UnmarshalWithErrLogger(data, errLogger)
if len(rows.Rows) != 1 {
panic(fmt.Errorf("unexpected number of rows parsed from %q; got %d; want %d", data, len(rows.Rows), 1))
}
return &rows.Rows[0]
}
func parseData(data string) []prompbmarshal.TimeSeries { func parseData(data string) []prompbmarshal.TimeSeries {
var rows parser.Rows var rows parser.Rows
errLogger := func(s string) { errLogger := func(s string) {

View file

@ -82,17 +82,26 @@ func (r *Row) unmarshal(s string, tagsPool []Tag) ([]Tag, error) {
} }
r.Timestamp = int64(timestamp) r.Timestamp = int64(timestamp)
tail = trimLeadingSpaces(tail[n+1:]) tail = trimLeadingSpaces(tail[n+1:])
valueStr := ""
tagsStr := ""
n = strings.IndexByte(tail, ' ') n = strings.IndexByte(tail, ' ')
if n < 0 { if n < 0 {
return tagsPool, fmt.Errorf("cannot find whitespace between value and the first tag in %q", s) // Missing tags.
// Accept this case even if OpenTSDB forbids it according to http://opentsdb.net/docs/build/html/api_telnet/put.html:
// > At least one tag pair must be present.
// See https://github.com/VictoriaMetrics/VictoriaMetrics/issues/3290
valueStr = tail
} else {
valueStr = tail[:n]
tagsStr = tail[n+1:]
} }
v, err := fastfloat.Parse(tail[:n]) v, err := fastfloat.Parse(valueStr)
if err != nil { if err != nil {
return tagsPool, fmt.Errorf("cannot parse value from %q: %w", tail[:n], err) return tagsPool, fmt.Errorf("cannot parse value from %q: %w", valueStr, err)
} }
r.Value = v r.Value = v
tagsStart := len(tagsPool) tagsStart := len(tagsPool)
tagsPool, err = unmarshalTags(tagsPool, tail[n+1:]) tagsPool, err = unmarshalTags(tagsPool, tagsStr)
if err != nil { if err != nil {
return tagsPool, fmt.Errorf("cannot unmarshal tags in %q: %w", s, err) return tagsPool, fmt.Errorf("cannot unmarshal tags in %q: %w", s, err)
} }

View file

@ -37,9 +37,6 @@ func TestRowsUnmarshalFailure(t *testing.T) {
f("put aaa timestamp") f("put aaa timestamp")
f("put foobar 3df4 -123456 a=b") f("put foobar 3df4 -123456 a=b")
// Missing first tag
f("put aaa 123 43")
// Invalid value // Invalid value
f("put aaa 123 invalid-value") f("put aaa 123 invalid-value")
f("put foobar 789 -123foo456 a=b") f("put foobar 789 -123foo456 a=b")
@ -104,6 +101,23 @@ func TestRowsUnmarshalSuccess(t *testing.T) {
}, },
}}, }},
}) })
// Missing first tag
// See https://github.com/VictoriaMetrics/VictoriaMetrics/issues/3290
f("put aaa 123 43", &Rows{
Rows: []Row{{
Metric: "aaa",
Value: 43,
Timestamp: 123,
}},
})
f("put aaa 123 43 ", &Rows{
Rows: []Row{{
Metric: "aaa",
Value: 43,
Timestamp: 123,
}},
})
// Fractional timestamp that is supported by Akumuli. // Fractional timestamp that is supported by Akumuli.
f("put foobar 789.4 -123.456 a=b", &Rows{ f("put foobar 789.4 -123.456 a=b", &Rows{
Rows: []Row{{ Rows: []Row{{

View file

@ -164,7 +164,7 @@ func (c *Cache) expirationWatcher(expireDuration time.Duration) {
func (c *Cache) prevCacheWatcher() { func (c *Cache) prevCacheWatcher() {
// Watch for the usage of the prev cache and drop it whenever it receives // Watch for the usage of the prev cache and drop it whenever it receives
// less than 5% of requests comparing to the curr cache during the last 10 seconds. // less than 1% of requests comparing to the curr cache during the last 10 seconds.
checkInterval := 10 * time.Second checkInterval := 10 * time.Second
checkInterval += timeJitter(checkInterval / 10) checkInterval += timeJitter(checkInterval / 10)
t := time.NewTicker(checkInterval) t := time.NewTicker(checkInterval)
@ -198,7 +198,7 @@ func (c *Cache) prevCacheWatcher() {
} }
currGetCalls = csCurr.GetCalls currGetCalls = csCurr.GetCalls
prevGetCalls = csPrev.GetCalls prevGetCalls = csPrev.GetCalls
if currRequests >= 20 && float64(prevRequests)/float64(currRequests) < 0.05 { if currRequests >= 100 && float64(prevRequests)/float64(currRequests) < 0.01 {
// The majority of requests are served from the curr cache, // The majority of requests are served from the curr cache,
// so the prev cache can be deleted in order to free up memory. // so the prev cache can be deleted in order to free up memory.
if csPrev.EntriesCount > 0 { if csPrev.EntriesCount > 0 {

View file

@ -332,15 +332,6 @@
"release_level": "ga", "release_level": "ga",
"library_type": "GAPIC_AUTO" "library_type": "GAPIC_AUTO"
}, },
"cloud.google.com/go/bigquery/reservation/apiv1beta1": {
"distribution_name": "cloud.google.com/go/bigquery/reservation/apiv1beta1",
"description": "BigQuery Reservation API",
"language": "Go",
"client_library_type": "generated",
"docs_url": "https://cloud.google.com/go/docs/reference/cloud.google.com/go/bigquery/latest/reservation/apiv1beta1",
"release_level": "beta",
"library_type": "GAPIC_AUTO"
},
"cloud.google.com/go/bigquery/storage/apiv1": { "cloud.google.com/go/bigquery/storage/apiv1": {
"distribution_name": "cloud.google.com/go/bigquery/storage/apiv1", "distribution_name": "cloud.google.com/go/bigquery/storage/apiv1",
"description": "BigQuery Storage API", "description": "BigQuery Storage API",
@ -1048,7 +1039,7 @@
"description": "Long Running Operations API", "description": "Long Running Operations API",
"language": "Go", "language": "Go",
"client_library_type": "generated", "client_library_type": "generated",
"docs_url": "https://cloud.google.com/go/docs/reference/cloud.google.com/go/latest/longrunning/autogen", "docs_url": "https://cloud.google.com/go/docs/reference/cloud.google.com/go/longrunning/latest/autogen",
"release_level": "alpha", "release_level": "alpha",
"library_type": "GAPIC_AUTO" "library_type": "GAPIC_AUTO"
}, },

View file

@ -1,3 +0,0 @@
{
"storage": "1.27.0"
}

View file

@ -1,6 +1,25 @@
# Changes # Changes
## [1.28.0](https://github.com/googleapis/google-cloud-go/compare/storage/v1.27.0...storage/v1.28.0) (2022-11-03)
### Features
* **storage/internal:** Add routing annotations ([ce3f945](https://github.com/googleapis/google-cloud-go/commit/ce3f9458e511eca0910992763232abbcd64698f1))
* **storage:** Add Autoclass support ([#6828](https://github.com/googleapis/google-cloud-go/issues/6828)) ([f7c7f41](https://github.com/googleapis/google-cloud-go/commit/f7c7f41e4d7fcffe05860e1114cb20f40c869da8))
### Bug Fixes
* **storage:** Fix read-write race in Writer.Write ([#6817](https://github.com/googleapis/google-cloud-go/issues/6817)) ([4766d3e](https://github.com/googleapis/google-cloud-go/commit/4766d3e1004119b93c6bd352024b5bf3404252eb))
* **storage:** Fix request token passing for Copier.Run ([#6863](https://github.com/googleapis/google-cloud-go/issues/6863)) ([faaab06](https://github.com/googleapis/google-cloud-go/commit/faaab066d8e509dc440bcbc87391557ecee7dbf2)), refs [#6857](https://github.com/googleapis/google-cloud-go/issues/6857)
### Documentation
* **storage:** Update broken links for SignURL and PostPolicy ([#6779](https://github.com/googleapis/google-cloud-go/issues/6779)) ([776138b](https://github.com/googleapis/google-cloud-go/commit/776138bc06a1e5fd45acbf8f9d36e9dc6ce31dd3))
## [1.27.0](https://github.com/googleapis/google-cloud-go/compare/storage/v1.26.0...storage/v1.27.0) (2022-09-22) ## [1.27.0](https://github.com/googleapis/google-cloud-go/compare/storage/v1.26.0...storage/v1.27.0) (2022-09-22)

View file

@ -25,7 +25,7 @@ if err != nil {
log.Fatal(err) log.Fatal(err)
} }
defer rc.Close() defer rc.Close()
body, err := ioutil.ReadAll(rc) body, err := io.ReadAll(rc)
if err != nil { if err != nil {
log.Fatal(err) log.Fatal(err)
} }

View file

@ -170,7 +170,7 @@ func (b *BucketHandle) Update(ctx context.Context, uattrs BucketAttrsToUpdate) (
// for this method. // for this method.
// //
// [Overview of access control]: https://cloud.google.com/storage/docs/accesscontrol#signed_urls_query_string_authentication // [Overview of access control]: https://cloud.google.com/storage/docs/accesscontrol#signed_urls_query_string_authentication
// [automatic detection of credentials]: https://pkg.go.dev/cloud.google.com/go/storage#hdr-Credential_requirements_for_[BucketHandle.SignedURL]_and_[BucketHandle.GenerateSignedPostPolicyV4] // [automatic detection of credentials]: https://pkg.go.dev/cloud.google.com/go/storage#hdr-Credential_requirements_for_signing
func (b *BucketHandle) SignedURL(object string, opts *SignedURLOptions) (string, error) { func (b *BucketHandle) SignedURL(object string, opts *SignedURLOptions) (string, error) {
if opts.GoogleAccessID != "" && (opts.SignBytes != nil || len(opts.PrivateKey) > 0) { if opts.GoogleAccessID != "" && (opts.SignBytes != nil || len(opts.PrivateKey) > 0) {
return SignedURL(b.name, object, opts) return SignedURL(b.name, object, opts)
@ -212,7 +212,7 @@ func (b *BucketHandle) SignedURL(object string, opts *SignedURLOptions) (string,
// to be non-nil. You may need to set the GoogleAccessID and PrivateKey fields // to be non-nil. You may need to set the GoogleAccessID and PrivateKey fields
// in some cases. Read more on the [automatic detection of credentials] for this method. // in some cases. Read more on the [automatic detection of credentials] for this method.
// //
// [automatic detection of credentials]: https://pkg.go.dev/cloud.google.com/go/storage#hdr-Credential_requirements_for_[BucketHandle.SignedURL]_and_[BucketHandle.GenerateSignedPostPolicyV4] // [automatic detection of credentials]: https://pkg.go.dev/cloud.google.com/go/storage#hdr-Credential_requirements_for_signing
func (b *BucketHandle) GenerateSignedPostPolicyV4(object string, opts *PostPolicyV4Options) (*PostPolicyV4, error) { func (b *BucketHandle) GenerateSignedPostPolicyV4(object string, opts *PostPolicyV4Options) (*PostPolicyV4, error) {
if opts.GoogleAccessID != "" && (opts.SignRawBytes != nil || opts.SignBytes != nil || len(opts.PrivateKey) > 0) { if opts.GoogleAccessID != "" && (opts.SignRawBytes != nil || opts.SignBytes != nil || len(opts.PrivateKey) > 0) {
return GenerateSignedPostPolicyV4(b.name, object, opts) return GenerateSignedPostPolicyV4(b.name, object, opts)
@ -298,18 +298,18 @@ func (b *BucketHandle) defaultSignBytesFunc(email string) func([]byte) ([]byte,
// circumventing the cost of recreating the auth/transport layer // circumventing the cost of recreating the auth/transport layer
svc, err := iamcredentials.NewService(ctx, option.WithHTTPClient(b.c.hc)) svc, err := iamcredentials.NewService(ctx, option.WithHTTPClient(b.c.hc))
if err != nil { if err != nil {
return nil, fmt.Errorf("unable to create iamcredentials client: %v", err) return nil, fmt.Errorf("unable to create iamcredentials client: %w", err)
} }
resp, err := svc.Projects.ServiceAccounts.SignBlob(fmt.Sprintf("projects/-/serviceAccounts/%s", email), &iamcredentials.SignBlobRequest{ resp, err := svc.Projects.ServiceAccounts.SignBlob(fmt.Sprintf("projects/-/serviceAccounts/%s", email), &iamcredentials.SignBlobRequest{
Payload: base64.StdEncoding.EncodeToString(in), Payload: base64.StdEncoding.EncodeToString(in),
}).Do() }).Do()
if err != nil { if err != nil {
return nil, fmt.Errorf("unable to sign bytes: %v", err) return nil, fmt.Errorf("unable to sign bytes: %w", err)
} }
out, err := base64.StdEncoding.DecodeString(resp.SignedBlob) out, err := base64.StdEncoding.DecodeString(resp.SignedBlob)
if err != nil { if err != nil {
return nil, fmt.Errorf("unable to base64 decode response: %v", err) return nil, fmt.Errorf("unable to base64 decode response: %w", err)
} }
return out, nil return out, nil
} }
@ -444,6 +444,11 @@ type BucketAttrs struct {
// See https://cloud.google.com/storage/docs/managing-turbo-replication for // See https://cloud.google.com/storage/docs/managing-turbo-replication for
// more information. // more information.
RPO RPO RPO RPO
// Autoclass holds the bucket's autoclass configuration. If enabled,
// allows for the automatic selection of the best storage class
// based on object access patterns.
Autoclass *Autoclass
} }
// BucketPolicyOnly is an alias for UniformBucketLevelAccess. // BucketPolicyOnly is an alias for UniformBucketLevelAccess.
@ -710,6 +715,20 @@ type CustomPlacementConfig struct {
DataLocations []string DataLocations []string
} }
// Autoclass holds the bucket's autoclass configuration. If enabled,
// allows for the automatic selection of the best storage class
// based on object access patterns. See
// https://cloud.google.com/storage/docs/using-autoclass for more information.
type Autoclass struct {
// Enabled specifies whether the autoclass feature is enabled
// on the bucket.
Enabled bool
// ToggleTime is the time from which Autoclass was last toggled.
// If Autoclass is enabled when the bucket is created, the ToggleTime
// is set to the bucket creation time. This field is read-only.
ToggleTime time.Time
}
func newBucket(b *raw.Bucket) (*BucketAttrs, error) { func newBucket(b *raw.Bucket) (*BucketAttrs, error) {
if b == nil { if b == nil {
return nil, nil return nil, nil
@ -744,6 +763,7 @@ func newBucket(b *raw.Bucket) (*BucketAttrs, error) {
ProjectNumber: b.ProjectNumber, ProjectNumber: b.ProjectNumber,
RPO: toRPO(b), RPO: toRPO(b),
CustomPlacementConfig: customPlacementFromRaw(b.CustomPlacementConfig), CustomPlacementConfig: customPlacementFromRaw(b.CustomPlacementConfig),
Autoclass: toAutoclassFromRaw(b.Autoclass),
}, nil }, nil
} }
@ -776,6 +796,7 @@ func newBucketFromProto(b *storagepb.Bucket) *BucketAttrs {
RPO: toRPOFromProto(b), RPO: toRPOFromProto(b),
CustomPlacementConfig: customPlacementFromProto(b.GetCustomPlacementConfig()), CustomPlacementConfig: customPlacementFromProto(b.GetCustomPlacementConfig()),
ProjectNumber: parseProjectNumber(b.GetProject()), // this can return 0 the project resource name is ID based ProjectNumber: parseProjectNumber(b.GetProject()), // this can return 0 the project resource name is ID based
Autoclass: toAutoclassFromProto(b.GetAutoclass()),
} }
} }
@ -830,6 +851,7 @@ func (b *BucketAttrs) toRawBucket() *raw.Bucket {
IamConfiguration: bktIAM, IamConfiguration: bktIAM,
Rpo: b.RPO.String(), Rpo: b.RPO.String(),
CustomPlacementConfig: b.CustomPlacementConfig.toRawCustomPlacement(), CustomPlacementConfig: b.CustomPlacementConfig.toRawCustomPlacement(),
Autoclass: b.Autoclass.toRawAutoclass(),
} }
} }
@ -889,6 +911,7 @@ func (b *BucketAttrs) toProtoBucket() *storagepb.Bucket {
IamConfig: bktIAM, IamConfig: bktIAM,
Rpo: b.RPO.String(), Rpo: b.RPO.String(),
CustomPlacementConfig: b.CustomPlacementConfig.toProtoCustomPlacement(), CustomPlacementConfig: b.CustomPlacementConfig.toProtoCustomPlacement(),
Autoclass: b.Autoclass.toProtoAutoclass(),
} }
} }
@ -907,23 +930,30 @@ func (ua *BucketAttrsToUpdate) toProtoBucket() *storagepb.Bucket {
if ua.RequesterPays != nil { if ua.RequesterPays != nil {
bb = &storagepb.Bucket_Billing{RequesterPays: optional.ToBool(ua.RequesterPays)} bb = &storagepb.Bucket_Billing{RequesterPays: optional.ToBool(ua.RequesterPays)}
} }
var bktIAM *storagepb.Bucket_IamConfig var bktIAM *storagepb.Bucket_IamConfig
var ublaEnabled bool if ua.UniformBucketLevelAccess != nil || ua.BucketPolicyOnly != nil || ua.PublicAccessPrevention != PublicAccessPreventionUnknown {
var bktPolicyOnlyEnabled bool bktIAM = &storagepb.Bucket_IamConfig{}
if ua.UniformBucketLevelAccess != nil {
ublaEnabled = optional.ToBool(ua.UniformBucketLevelAccess.Enabled) if ua.BucketPolicyOnly != nil {
} bktIAM.UniformBucketLevelAccess = &storagepb.Bucket_IamConfig_UniformBucketLevelAccess{
if ua.BucketPolicyOnly != nil { Enabled: optional.ToBool(ua.BucketPolicyOnly.Enabled),
bktPolicyOnlyEnabled = optional.ToBool(ua.BucketPolicyOnly.Enabled) }
} }
if ublaEnabled || bktPolicyOnlyEnabled {
bktIAM.UniformBucketLevelAccess = &storagepb.Bucket_IamConfig_UniformBucketLevelAccess{ if ua.UniformBucketLevelAccess != nil {
Enabled: true, // UniformBucketLevelAccess takes precedence over BucketPolicyOnly,
// so Enabled will be overriden here if both are set
bktIAM.UniformBucketLevelAccess = &storagepb.Bucket_IamConfig_UniformBucketLevelAccess{
Enabled: optional.ToBool(ua.UniformBucketLevelAccess.Enabled),
}
}
if ua.PublicAccessPrevention != PublicAccessPreventionUnknown {
bktIAM.PublicAccessPrevention = ua.PublicAccessPrevention.String()
} }
} }
if ua.PublicAccessPrevention != PublicAccessPreventionUnknown {
bktIAM.PublicAccessPrevention = ua.PublicAccessPrevention.String()
}
var defaultHold bool var defaultHold bool
if ua.DefaultEventBasedHold != nil { if ua.DefaultEventBasedHold != nil {
defaultHold = optional.ToBool(ua.DefaultEventBasedHold) defaultHold = optional.ToBool(ua.DefaultEventBasedHold)
@ -964,6 +994,7 @@ func (ua *BucketAttrsToUpdate) toProtoBucket() *storagepb.Bucket {
Website: ua.Website.toProtoBucketWebsite(), Website: ua.Website.toProtoBucketWebsite(),
IamConfig: bktIAM, IamConfig: bktIAM,
Rpo: ua.RPO.String(), Rpo: ua.RPO.String(),
Autoclass: ua.Autoclass.toProtoAutoclass(),
} }
} }
@ -1079,6 +1110,10 @@ type BucketAttrsToUpdate struct {
// more information. // more information.
RPO RPO RPO RPO
// If set, updates the autoclass configuration of the bucket.
// See https://cloud.google.com/storage/docs/using-autoclass for more information.
Autoclass *Autoclass
// acl is the list of access control rules on the bucket. // acl is the list of access control rules on the bucket.
// It is unexported and only used internally by the gRPC client. // It is unexported and only used internally by the gRPC client.
// Library users should use ACLHandle methods directly. // Library users should use ACLHandle methods directly.
@ -1192,6 +1227,12 @@ func (ua *BucketAttrsToUpdate) toRawBucket() *raw.Bucket {
rb.Website = ua.Website.toRawBucketWebsite() rb.Website = ua.Website.toRawBucketWebsite()
} }
} }
if ua.Autoclass != nil {
rb.Autoclass = &raw.BucketAutoclass{
Enabled: ua.Autoclass.Enabled,
ForceSendFields: []string{"Enabled"},
}
}
if ua.PredefinedACL != "" { if ua.PredefinedACL != "" {
// Clear ACL or the call will fail. // Clear ACL or the call will fail.
rb.Acl = nil rb.Acl = nil
@ -1346,8 +1387,14 @@ func (rp *RetentionPolicy) toProtoRetentionPolicy() *storagepb.Bucket_RetentionP
if rp == nil { if rp == nil {
return nil return nil
} }
// RetentionPeriod must be greater than 0, so if it is 0, the user left it
// unset, and so we should not send it in the request i.e. nil is sent.
var period *int64
if rp.RetentionPeriod != 0 {
period = proto.Int64(int64(rp.RetentionPeriod / time.Second))
}
return &storagepb.Bucket_RetentionPolicy{ return &storagepb.Bucket_RetentionPolicy{
RetentionPeriod: int64(rp.RetentionPeriod / time.Second), RetentionPeriod: period,
} }
} }
@ -1367,7 +1414,7 @@ func toRetentionPolicy(rp *raw.BucketRetentionPolicy) (*RetentionPolicy, error)
} }
func toRetentionPolicyFromProto(rp *storagepb.Bucket_RetentionPolicy) *RetentionPolicy { func toRetentionPolicyFromProto(rp *storagepb.Bucket_RetentionPolicy) *RetentionPolicy {
if rp == nil { if rp == nil || rp.GetEffectiveTime().AsTime().Unix() == 0 {
return nil return nil
} }
return &RetentionPolicy{ return &RetentionPolicy{
@ -1886,6 +1933,53 @@ func customPlacementFromProto(c *storagepb.Bucket_CustomPlacementConfig) *Custom
return &CustomPlacementConfig{DataLocations: c.GetDataLocations()} return &CustomPlacementConfig{DataLocations: c.GetDataLocations()}
} }
func (a *Autoclass) toRawAutoclass() *raw.BucketAutoclass {
if a == nil {
return nil
}
// Excluding read only field ToggleTime.
return &raw.BucketAutoclass{
Enabled: a.Enabled,
}
}
func (a *Autoclass) toProtoAutoclass() *storagepb.Bucket_Autoclass {
if a == nil {
return nil
}
// Excluding read only field ToggleTime.
return &storagepb.Bucket_Autoclass{
Enabled: a.Enabled,
}
}
func toAutoclassFromRaw(a *raw.BucketAutoclass) *Autoclass {
if a == nil || a.ToggleTime == "" {
return nil
}
// Return Autoclass.ToggleTime only if parsed with a valid value.
t, err := time.Parse(time.RFC3339, a.ToggleTime)
if err != nil {
return &Autoclass{
Enabled: a.Enabled,
}
}
return &Autoclass{
Enabled: a.Enabled,
ToggleTime: t,
}
}
func toAutoclassFromProto(a *storagepb.Bucket_Autoclass) *Autoclass {
if a == nil || a.GetToggleTime().AsTime().Unix() == 0 {
return nil
}
return &Autoclass{
Enabled: a.GetEnabled(),
ToggleTime: a.GetToggleTime().AsTime(),
}
}
// Objects returns an iterator over the objects in the bucket that match the // Objects returns an iterator over the objects in the bucket that match the
// Query q. If q is nil, no filtering is done. Objects will be iterated over // Query q. If q is nil, no filtering is done. Objects will be iterated over
// lexicographically by name. // lexicographically by name.

View file

@ -317,10 +317,11 @@ type destinationObject struct {
} }
type rewriteObjectRequest struct { type rewriteObjectRequest struct {
srcObject sourceObject srcObject sourceObject
dstObject destinationObject dstObject destinationObject
predefinedACL string predefinedACL string
token string token string
maxBytesRewrittenPerCall int64
} }
type rewriteObjectResponse struct { type rewriteObjectResponse struct {

View file

@ -69,6 +69,15 @@ type Copier struct {
DestinationKMSKeyName string DestinationKMSKeyName string
dst, src *ObjectHandle dst, src *ObjectHandle
// The maximum number of bytes that will be rewritten per rewrite request.
// Most callers shouldn't need to specify this parameter - it is primarily
// in place to support testing. If specified the value must be an integral
// multiple of 1 MiB (1048576). Also, this only applies to requests where
// the source and destination span locations and/or storage classes. Finally,
// this value must not change across rewrite calls else you'll get an error
// that the `rewriteToken` is invalid.
maxBytesRewrittenPerCall int64
} }
// Run performs the copy. // Run performs the copy.
@ -108,8 +117,9 @@ func (c *Copier) Run(ctx context.Context) (attrs *ObjectAttrs, err error) {
encryptionKey: c.dst.encryptionKey, encryptionKey: c.dst.encryptionKey,
keyName: c.DestinationKMSKeyName, keyName: c.DestinationKMSKeyName,
}, },
predefinedACL: c.PredefinedACL, predefinedACL: c.PredefinedACL,
token: c.RewriteToken, token: c.RewriteToken,
maxBytesRewrittenPerCall: c.maxBytesRewrittenPerCall,
} }
isIdempotent := c.dst.conds != nil && (c.dst.conds.GenerationMatch != 0 || c.dst.conds.DoesNotExist) isIdempotent := c.dst.conds != nil && (c.dst.conds.GenerationMatch != 0 || c.dst.conds.DoesNotExist)
@ -127,6 +137,7 @@ func (c *Copier) Run(ctx context.Context) (attrs *ObjectAttrs, err error) {
return nil, err return nil, err
} }
c.RewriteToken = res.token c.RewriteToken = res.token
req.token = res.token
if c.ProgressFunc != nil { if c.ProgressFunc != nil {
c.ProgressFunc(uint64(res.written), uint64(res.size)) c.ProgressFunc(uint64(res.written), uint64(res.size))
} }

View file

@ -25,6 +25,7 @@ import (
"cloud.google.com/go/internal/trace" "cloud.google.com/go/internal/trace"
gapic "cloud.google.com/go/storage/internal/apiv2" gapic "cloud.google.com/go/storage/internal/apiv2"
storagepb "cloud.google.com/go/storage/internal/apiv2/stubs" storagepb "cloud.google.com/go/storage/internal/apiv2/stubs"
"github.com/googleapis/gax-go/v2"
"google.golang.org/api/iterator" "google.golang.org/api/iterator"
"google.golang.org/api/option" "google.golang.org/api/option"
"google.golang.org/api/option/internaloption" "google.golang.org/api/option/internaloption"
@ -246,7 +247,8 @@ func (c *grpcStorageClient) DeleteBucket(ctx context.Context, bucket string, con
func (c *grpcStorageClient) GetBucket(ctx context.Context, bucket string, conds *BucketConditions, opts ...storageOption) (*BucketAttrs, error) { func (c *grpcStorageClient) GetBucket(ctx context.Context, bucket string, conds *BucketConditions, opts ...storageOption) (*BucketAttrs, error) {
s := callSettings(c.settings, opts...) s := callSettings(c.settings, opts...)
req := &storagepb.GetBucketRequest{ req := &storagepb.GetBucketRequest{
Name: bucketResourceName(globalProjectAlias, bucket), Name: bucketResourceName(globalProjectAlias, bucket),
ReadMask: &fieldmaskpb.FieldMask{Paths: []string{"*"}},
} }
if err := applyBucketCondsProto("grpcStorageClient.GetBucket", conds, req); err != nil { if err := applyBucketCondsProto("grpcStorageClient.GetBucket", conds, req); err != nil {
return nil, err return nil, err
@ -344,6 +346,9 @@ func (c *grpcStorageClient) UpdateBucket(ctx context.Context, bucket string, uat
if uattrs.RPO != RPOUnknown { if uattrs.RPO != RPOUnknown {
fieldMask.Paths = append(fieldMask.Paths, "rpo") fieldMask.Paths = append(fieldMask.Paths, "rpo")
} }
if uattrs.Autoclass != nil {
fieldMask.Paths = append(fieldMask.Paths, "autoclass")
}
// TODO(cathyo): Handle labels. Pending b/230510191. // TODO(cathyo): Handle labels. Pending b/230510191.
req.UpdateMask = fieldMask req.UpdateMask = fieldMask
@ -380,14 +385,14 @@ func (c *grpcStorageClient) ListObjects(ctx context.Context, bucket string, q *Q
it.query = *q it.query = *q
} }
req := &storagepb.ListObjectsRequest{ req := &storagepb.ListObjectsRequest{
Parent: bucketResourceName(globalProjectAlias, bucket), Parent: bucketResourceName(globalProjectAlias, bucket),
Prefix: it.query.Prefix, Prefix: it.query.Prefix,
Delimiter: it.query.Delimiter, Delimiter: it.query.Delimiter,
Versions: it.query.Versions, Versions: it.query.Versions,
LexicographicStart: it.query.StartOffset, LexicographicStart: it.query.StartOffset,
LexicographicEnd: it.query.EndOffset, LexicographicEnd: it.query.EndOffset,
// TODO(noahietz): Convert a projection to a FieldMask. IncludeTrailingDelimiter: it.query.IncludeTrailingDelimiter,
// ReadMask: q.Projection, ReadMask: q.toFieldMask(), // a nil Query still results in a "*" FieldMask
} }
if s.userProject != "" { if s.userProject != "" {
ctx = setUserProjectMetadata(ctx, s.userProject) ctx = setUserProjectMetadata(ctx, s.userProject)
@ -411,6 +416,12 @@ func (c *grpcStorageClient) ListObjects(ctx context.Context, bucket string, q *Q
it.items = append(it.items, b) it.items = append(it.items, b)
} }
// Response is always non-nil after a successful request.
res := gitr.Response.(*storagepb.ListObjectsResponse)
for _, prefix := range res.GetPrefixes() {
it.items = append(it.items, &ObjectAttrs{Prefix: prefix})
}
return token, nil return token, nil
} }
it.pageInfo, it.nextFunc = iterator.NewPageInfo( it.pageInfo, it.nextFunc = iterator.NewPageInfo(
@ -449,6 +460,8 @@ func (c *grpcStorageClient) GetObject(ctx context.Context, bucket, object string
req := &storagepb.GetObjectRequest{ req := &storagepb.GetObjectRequest{
Bucket: bucketResourceName(globalProjectAlias, bucket), Bucket: bucketResourceName(globalProjectAlias, bucket),
Object: object, Object: object,
// ProjectionFull by default.
ReadMask: &fieldmaskpb.FieldMask{Paths: []string{"*"}},
} }
if err := applyCondsProto("grpcStorageClient.GetObject", gen, conds, req); err != nil { if err := applyCondsProto("grpcStorageClient.GetObject", gen, conds, req); err != nil {
return nil, err return nil, err
@ -492,10 +505,7 @@ func (c *grpcStorageClient) UpdateObject(ctx context.Context, bucket, object str
req.CommonObjectRequestParams = toProtoCommonObjectRequestParams(encryptionKey) req.CommonObjectRequestParams = toProtoCommonObjectRequestParams(encryptionKey)
} }
var paths []string fieldMask := &fieldmaskpb.FieldMask{Paths: nil}
fieldMask := &fieldmaskpb.FieldMask{
Paths: paths,
}
if uattrs.EventBasedHold != nil { if uattrs.EventBasedHold != nil {
fieldMask.Paths = append(fieldMask.Paths, "event_based_hold") fieldMask.Paths = append(fieldMask.Paths, "event_based_hold")
} }
@ -522,7 +532,7 @@ func (c *grpcStorageClient) UpdateObject(ctx context.Context, bucket, object str
} }
// Note: This API currently does not support entites using project ID. // Note: This API currently does not support entites using project ID.
// Use project numbers in ACL entities. Pending b/233617896. // Use project numbers in ACL entities. Pending b/233617896.
if uattrs.ACL != nil { if uattrs.ACL != nil || len(uattrs.PredefinedACL) > 0 {
fieldMask.Paths = append(fieldMask.Paths, "acl") fieldMask.Paths = append(fieldMask.Paths, "acl")
} }
// TODO(cathyo): Handle metadata. Pending b/230510191. // TODO(cathyo): Handle metadata. Pending b/230510191.
@ -812,6 +822,9 @@ func (c *grpcStorageClient) RewriteObject(ctx context.Context, req *rewriteObjec
call.CopySourceEncryptionKeyBytes = srcParams.GetEncryptionKeyBytes() call.CopySourceEncryptionKeyBytes = srcParams.GetEncryptionKeyBytes()
call.CopySourceEncryptionKeySha256Bytes = srcParams.GetEncryptionKeySha256Bytes() call.CopySourceEncryptionKeySha256Bytes = srcParams.GetEncryptionKeySha256Bytes()
} }
call.MaxBytesRewrittenPerCall = req.maxBytesRewrittenPerCall
var res *storagepb.RewriteResponse var res *storagepb.RewriteResponse
var err error var err error
@ -943,6 +956,7 @@ func (c *grpcStorageClient) NewRangeReader(ctx context.Context, params *newRange
// Store the content from the first Recv in the // Store the content from the first Recv in the
// client buffer for reading later. // client buffer for reading later.
leftovers: msg.GetChecksummedData().GetContent(), leftovers: msg.GetChecksummedData().GetContent(),
settings: s,
}, },
} }
@ -964,6 +978,8 @@ func (c *grpcStorageClient) NewRangeReader(ctx context.Context, params *newRange
} }
func (c *grpcStorageClient) OpenWriter(params *openWriterParams, opts ...storageOption) (*io.PipeWriter, error) { func (c *grpcStorageClient) OpenWriter(params *openWriterParams, opts ...storageOption) (*io.PipeWriter, error) {
s := callSettings(c.settings, opts...)
var offset int64 var offset int64
errorf := params.setError errorf := params.setError
progress := params.progress progress := params.progress
@ -971,6 +987,10 @@ func (c *grpcStorageClient) OpenWriter(params *openWriterParams, opts ...storage
pr, pw := io.Pipe() pr, pw := io.Pipe()
gw := newGRPCWriter(c, params, pr) gw := newGRPCWriter(c, params, pr)
gw.settings = s
if s.userProject != "" {
gw.ctx = setUserProjectMetadata(gw.ctx, s.userProject)
}
// This function reads the data sent to the pipe and sends sets of messages // This function reads the data sent to the pipe and sends sets of messages
// on the gRPC client-stream as the buffer is filled. // on the gRPC client-stream as the buffer is filled.
@ -1315,6 +1335,7 @@ type gRPCReader struct {
reopen func(seen int64) (*readStreamResponse, context.CancelFunc, error) reopen func(seen int64) (*readStreamResponse, context.CancelFunc, error)
leftovers []byte leftovers []byte
cancel context.CancelFunc cancel context.CancelFunc
settings *settings
} }
// Read reads bytes into the user's buffer from an open gRPC stream. // Read reads bytes into the user's buffer from an open gRPC stream.
@ -1390,7 +1411,11 @@ func (r *gRPCReader) Close() error {
// an attempt to reopen the stream. // an attempt to reopen the stream.
func (r *gRPCReader) recv() (*storagepb.ReadObjectResponse, error) { func (r *gRPCReader) recv() (*storagepb.ReadObjectResponse, error) {
msg, err := r.stream.Recv() msg, err := r.stream.Recv()
if err != nil && ShouldRetry(err) { var shouldRetry = ShouldRetry
if r.settings.retry != nil && r.settings.retry.shouldRetry != nil {
shouldRetry = r.settings.retry.shouldRetry
}
if err != nil && shouldRetry(err) {
// This will "close" the existing stream and immediately attempt to // This will "close" the existing stream and immediately attempt to
// reopen the stream, but will backoff if further attempts are necessary. // reopen the stream, but will backoff if further attempts are necessary.
// Reopening the stream Recvs the first message, so if retrying is // Reopening the stream Recvs the first message, so if retrying is
@ -1454,6 +1479,7 @@ type gRPCWriter struct {
attrs *ObjectAttrs attrs *ObjectAttrs
conds *Conditions conds *Conditions
encryptionKey []byte encryptionKey []byte
settings *settings
sendCRC32C bool sendCRC32C bool
@ -1471,21 +1497,27 @@ func (w *gRPCWriter) startResumableUpload() error {
if err != nil { if err != nil {
return err return err
} }
upres, err := w.c.raw.StartResumableWrite(w.ctx, &storagepb.StartResumableWriteRequest{ return run(w.ctx, func() error {
WriteObjectSpec: spec, upres, err := w.c.raw.StartResumableWrite(w.ctx, &storagepb.StartResumableWriteRequest{
}) WriteObjectSpec: spec,
})
w.upid = upres.GetUploadId() w.upid = upres.GetUploadId()
return err return err
}, w.settings.retry, w.settings.idempotent, setRetryHeaderGRPC(w.ctx))
} }
// queryProgress is a helper that queries the status of the resumable upload // queryProgress is a helper that queries the status of the resumable upload
// associated with the given upload ID. // associated with the given upload ID.
func (w *gRPCWriter) queryProgress() (int64, error) { func (w *gRPCWriter) queryProgress() (int64, error) {
q, err := w.c.raw.QueryWriteStatus(w.ctx, &storagepb.QueryWriteStatusRequest{UploadId: w.upid}) var persistedSize int64
err := run(w.ctx, func() error {
q, err := w.c.raw.QueryWriteStatus(w.ctx, &storagepb.QueryWriteStatusRequest{UploadId: w.upid})
persistedSize = q.GetPersistedSize()
return err
}, w.settings.retry, true, setRetryHeaderGRPC(w.ctx))
// q.GetCommittedSize() will return 0 if q is nil. // q.GetCommittedSize() will return 0 if q is nil.
return q.GetPersistedSize(), err return persistedSize, err
} }
// uploadBuffer opens a Write stream and uploads the buffer at the given offset (if // uploadBuffer opens a Write stream and uploads the buffer at the given offset (if
@ -1500,6 +1532,10 @@ func (w *gRPCWriter) uploadBuffer(recvd int, start int64, doneReading bool) (*st
var err error var err error
var finishWrite bool var finishWrite bool
var sent, limit int = 0, maxPerMessageWriteSize var sent, limit int = 0, maxPerMessageWriteSize
var shouldRetry = ShouldRetry
if w.settings.retry != nil && w.settings.retry.shouldRetry != nil {
shouldRetry = w.settings.retry.shouldRetry
}
offset := start offset := start
toWrite := w.buf[:recvd] toWrite := w.buf[:recvd]
for { for {
@ -1553,8 +1589,16 @@ func (w *gRPCWriter) uploadBuffer(recvd int, start int64, doneReading bool) (*st
// on the *last* message of the stream (instead of the first). // on the *last* message of the stream (instead of the first).
if w.sendCRC32C { if w.sendCRC32C {
req.ObjectChecksums = &storagepb.ObjectChecksums{ req.ObjectChecksums = &storagepb.ObjectChecksums{
Crc32C: proto.Uint32(w.attrs.CRC32C), Crc32C: proto.Uint32(w.attrs.CRC32C),
Md5Hash: w.attrs.MD5, }
}
if len(w.attrs.MD5) != 0 {
if cs := req.GetObjectChecksums(); cs == nil {
req.ObjectChecksums = &storagepb.ObjectChecksums{
Md5Hash: w.attrs.MD5,
}
} else {
cs.Md5Hash = w.attrs.MD5
} }
} }
} }
@ -1570,7 +1614,7 @@ func (w *gRPCWriter) uploadBuffer(recvd int, start int64, doneReading bool) (*st
// resend the entire buffer via a new stream. // resend the entire buffer via a new stream.
// If not retriable, falling through will return the error received // If not retriable, falling through will return the error received
// from closing the stream. // from closing the stream.
if ShouldRetry(err) { if shouldRetry(err) {
sent = 0 sent = 0
finishWrite = false finishWrite = false
// TODO: Add test case for failure modes of querying progress. // TODO: Add test case for failure modes of querying progress.
@ -1601,7 +1645,7 @@ func (w *gRPCWriter) uploadBuffer(recvd int, start int64, doneReading bool) (*st
// resend the entire buffer via a new stream. // resend the entire buffer via a new stream.
// If not retriable, falling through will return the error received // If not retriable, falling through will return the error received
// from closing the stream. // from closing the stream.
if ShouldRetry(err) { if shouldRetry(err) {
sent = 0 sent = 0
finishWrite = false finishWrite = false
offset, err = w.determineOffset(start) offset, err = w.determineOffset(start)
@ -1673,7 +1717,12 @@ func (w *gRPCWriter) writeObjectSpec() (*storagepb.WriteObjectSpec, error) {
// read copies the data in the reader to the given buffer and reports how much // read copies the data in the reader to the given buffer and reports how much
// data was read into the buffer and if there is no more data to read (EOF). // data was read into the buffer and if there is no more data to read (EOF).
// Furthermore, if the attrs.ContentType is unset, the first bytes of content
// will be sniffed for a matching content type.
func (w *gRPCWriter) read() (int, bool, error) { func (w *gRPCWriter) read() (int, bool, error) {
if w.attrs.ContentType == "" {
w.reader, w.attrs.ContentType = gax.DetermineContentType(w.reader)
}
// Set n to -1 to start the Read loop. // Set n to -1 to start the Read loop.
var n, recvd int = -1, 0 var n, recvd int = -1, 0
var err error var err error

View file

@ -147,11 +147,11 @@ func toHMACKeyFromRaw(hk *raw.HmacKey, updatedTimeCanBeNil bool) (*HMACKey, erro
} }
createdTime, err := time.Parse(time.RFC3339, hkmd.TimeCreated) createdTime, err := time.Parse(time.RFC3339, hkmd.TimeCreated)
if err != nil { if err != nil {
return nil, fmt.Errorf("field CreatedTime: %v", err) return nil, fmt.Errorf("field CreatedTime: %w", err)
} }
updatedTime, err := time.Parse(time.RFC3339, hkmd.Updated) updatedTime, err := time.Parse(time.RFC3339, hkmd.Updated)
if err != nil && !updatedTimeCanBeNil { if err != nil && !updatedTimeCanBeNil {
return nil, fmt.Errorf("field UpdatedTime: %v", err) return nil, fmt.Errorf("field UpdatedTime: %w", err)
} }
hmKey := &HMACKey{ hmKey := &HMACKey{

View file

@ -114,17 +114,17 @@ func newHTTPStorageClient(ctx context.Context, opts ...storageOption) (storageCl
// htransport selects the correct endpoint among WithEndpoint (user override), WithDefaultEndpoint, and WithDefaultMTLSEndpoint. // htransport selects the correct endpoint among WithEndpoint (user override), WithDefaultEndpoint, and WithDefaultMTLSEndpoint.
hc, ep, err := htransport.NewClient(ctx, s.clientOption...) hc, ep, err := htransport.NewClient(ctx, s.clientOption...)
if err != nil { if err != nil {
return nil, fmt.Errorf("dialing: %v", err) return nil, fmt.Errorf("dialing: %w", err)
} }
// RawService should be created with the chosen endpoint to take account of user override. // RawService should be created with the chosen endpoint to take account of user override.
rawService, err := raw.NewService(ctx, option.WithEndpoint(ep), option.WithHTTPClient(hc)) rawService, err := raw.NewService(ctx, option.WithEndpoint(ep), option.WithHTTPClient(hc))
if err != nil { if err != nil {
return nil, fmt.Errorf("storage client: %v", err) return nil, fmt.Errorf("storage client: %w", err)
} }
// Update readHost and scheme with the chosen endpoint. // Update readHost and scheme with the chosen endpoint.
u, err := url.Parse(ep) u, err := url.Parse(ep)
if err != nil { if err != nil {
return nil, fmt.Errorf("supplied endpoint %q is not valid: %v", ep, err) return nil, fmt.Errorf("supplied endpoint %q is not valid: %w", ep, err)
} }
return &httpStorageClient{ return &httpStorageClient{
@ -344,8 +344,8 @@ func (c *httpStorageClient) ListObjects(ctx context.Context, bucket string, q *Q
req.EndOffset(it.query.EndOffset) req.EndOffset(it.query.EndOffset)
req.Versions(it.query.Versions) req.Versions(it.query.Versions)
req.IncludeTrailingDelimiter(it.query.IncludeTrailingDelimiter) req.IncludeTrailingDelimiter(it.query.IncludeTrailingDelimiter)
if len(it.query.fieldSelection) > 0 { if selection := it.query.toFieldSelection(); selection != "" {
req.Fields("nextPageToken", googleapi.Field(it.query.fieldSelection)) req.Fields("nextPageToken", googleapi.Field(selection))
} }
req.PageToken(pageToken) req.PageToken(pageToken)
if s.userProject != "" { if s.userProject != "" {
@ -747,6 +747,11 @@ func (c *httpStorageClient) RewriteObject(ctx context.Context, req *rewriteObjec
if err := setEncryptionHeaders(call.Header(), req.srcObject.encryptionKey, true); err != nil { if err := setEncryptionHeaders(call.Header(), req.srcObject.encryptionKey, true); err != nil {
return nil, err return nil, err
} }
if req.maxBytesRewrittenPerCall != 0 {
call.MaxBytesRewrittenPerCall(req.maxBytesRewrittenPerCall)
}
var res *raw.RewriteResponse var res *raw.RewriteResponse
var err error var err error
setClientHeader(call.Header()) setClientHeader(call.Header())
@ -905,7 +910,7 @@ func (c *httpStorageClient) NewRangeReader(ctx context.Context, params *newRange
if dashIndex >= 0 { if dashIndex >= 0 {
startOffset, err = strconv.ParseInt(cr[len("bytes="):dashIndex], 10, 64) startOffset, err = strconv.ParseInt(cr[len("bytes="):dashIndex], 10, 64)
if err != nil { if err != nil {
return nil, fmt.Errorf("storage: invalid Content-Range %q: %v", cr, err) return nil, fmt.Errorf("storage: invalid Content-Range %q: %w", cr, err)
} }
} }
} else { } else {
@ -1033,9 +1038,8 @@ func (c *httpStorageClient) OpenWriter(params *openWriterParams, opts ...storage
// there is no need to add retries here. // there is no need to add retries here.
// Retry only when the operation is idempotent or the retry policy is RetryAlways. // Retry only when the operation is idempotent or the retry policy is RetryAlways.
isIdempotent := params.conds != nil && (params.conds.GenerationMatch >= 0 || params.conds.DoesNotExist == true)
var useRetry bool var useRetry bool
if (s.retry == nil || s.retry.policy == RetryIdempotent) && isIdempotent { if (s.retry == nil || s.retry.policy == RetryIdempotent) && s.idempotent {
useRetry = true useRetry = true
} else if s.retry != nil && s.retry.policy == RetryAlways { } else if s.retry != nil && s.retry.policy == RetryAlways {
useRetry = true useRetry = true

View file

@ -589,7 +589,18 @@ func (c *gRPCClient) GetBucket(ctx context.Context, req *storagepb.GetBucketRequ
} }
func (c *gRPCClient) CreateBucket(ctx context.Context, req *storagepb.CreateBucketRequest, opts ...gax.CallOption) (*storagepb.Bucket, error) { func (c *gRPCClient) CreateBucket(ctx context.Context, req *storagepb.CreateBucketRequest, opts ...gax.CallOption) (*storagepb.Bucket, error) {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(?P<project>.*)"); reg.MatchString(req.GetParent()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetParent())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetParent())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).CreateBucket[0:len((*c.CallOptions).CreateBucket):len((*c.CallOptions).CreateBucket)], opts...) opts = append((*c.CallOptions).CreateBucket[0:len((*c.CallOptions).CreateBucket):len((*c.CallOptions).CreateBucket)], opts...)
var resp *storagepb.Bucket var resp *storagepb.Bucket
err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error { err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
@ -604,7 +615,18 @@ func (c *gRPCClient) CreateBucket(ctx context.Context, req *storagepb.CreateBuck
} }
func (c *gRPCClient) ListBuckets(ctx context.Context, req *storagepb.ListBucketsRequest, opts ...gax.CallOption) *BucketIterator { func (c *gRPCClient) ListBuckets(ctx context.Context, req *storagepb.ListBucketsRequest, opts ...gax.CallOption) *BucketIterator {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(?P<project>.*)"); reg.MatchString(req.GetParent()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetParent())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetParent())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).ListBuckets[0:len((*c.CallOptions).ListBuckets):len((*c.CallOptions).ListBuckets)], opts...) opts = append((*c.CallOptions).ListBuckets[0:len((*c.CallOptions).ListBuckets):len((*c.CallOptions).ListBuckets)], opts...)
it := &BucketIterator{} it := &BucketIterator{}
req = proto.Clone(req).(*storagepb.ListBucketsRequest) req = proto.Clone(req).(*storagepb.ListBucketsRequest)
@ -1215,7 +1237,18 @@ func (c *gRPCClient) QueryWriteStatus(ctx context.Context, req *storagepb.QueryW
} }
func (c *gRPCClient) GetServiceAccount(ctx context.Context, req *storagepb.GetServiceAccountRequest, opts ...gax.CallOption) (*storagepb.ServiceAccount, error) { func (c *gRPCClient) GetServiceAccount(ctx context.Context, req *storagepb.GetServiceAccountRequest, opts ...gax.CallOption) (*storagepb.ServiceAccount, error) {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(.*)"); reg.MatchString(req.GetProject()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).GetServiceAccount[0:len((*c.CallOptions).GetServiceAccount):len((*c.CallOptions).GetServiceAccount)], opts...) opts = append((*c.CallOptions).GetServiceAccount[0:len((*c.CallOptions).GetServiceAccount):len((*c.CallOptions).GetServiceAccount)], opts...)
var resp *storagepb.ServiceAccount var resp *storagepb.ServiceAccount
err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error { err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
@ -1230,7 +1263,18 @@ func (c *gRPCClient) GetServiceAccount(ctx context.Context, req *storagepb.GetSe
} }
func (c *gRPCClient) CreateHmacKey(ctx context.Context, req *storagepb.CreateHmacKeyRequest, opts ...gax.CallOption) (*storagepb.CreateHmacKeyResponse, error) { func (c *gRPCClient) CreateHmacKey(ctx context.Context, req *storagepb.CreateHmacKeyRequest, opts ...gax.CallOption) (*storagepb.CreateHmacKeyResponse, error) {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(.*)"); reg.MatchString(req.GetProject()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).CreateHmacKey[0:len((*c.CallOptions).CreateHmacKey):len((*c.CallOptions).CreateHmacKey)], opts...) opts = append((*c.CallOptions).CreateHmacKey[0:len((*c.CallOptions).CreateHmacKey):len((*c.CallOptions).CreateHmacKey)], opts...)
var resp *storagepb.CreateHmacKeyResponse var resp *storagepb.CreateHmacKeyResponse
err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error { err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
@ -1245,7 +1289,18 @@ func (c *gRPCClient) CreateHmacKey(ctx context.Context, req *storagepb.CreateHma
} }
func (c *gRPCClient) DeleteHmacKey(ctx context.Context, req *storagepb.DeleteHmacKeyRequest, opts ...gax.CallOption) error { func (c *gRPCClient) DeleteHmacKey(ctx context.Context, req *storagepb.DeleteHmacKeyRequest, opts ...gax.CallOption) error {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(.*)"); reg.MatchString(req.GetProject()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).DeleteHmacKey[0:len((*c.CallOptions).DeleteHmacKey):len((*c.CallOptions).DeleteHmacKey)], opts...) opts = append((*c.CallOptions).DeleteHmacKey[0:len((*c.CallOptions).DeleteHmacKey):len((*c.CallOptions).DeleteHmacKey)], opts...)
err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error { err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
var err error var err error
@ -1256,7 +1311,18 @@ func (c *gRPCClient) DeleteHmacKey(ctx context.Context, req *storagepb.DeleteHma
} }
func (c *gRPCClient) GetHmacKey(ctx context.Context, req *storagepb.GetHmacKeyRequest, opts ...gax.CallOption) (*storagepb.HmacKeyMetadata, error) { func (c *gRPCClient) GetHmacKey(ctx context.Context, req *storagepb.GetHmacKeyRequest, opts ...gax.CallOption) (*storagepb.HmacKeyMetadata, error) {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(.*)"); reg.MatchString(req.GetProject()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).GetHmacKey[0:len((*c.CallOptions).GetHmacKey):len((*c.CallOptions).GetHmacKey)], opts...) opts = append((*c.CallOptions).GetHmacKey[0:len((*c.CallOptions).GetHmacKey):len((*c.CallOptions).GetHmacKey)], opts...)
var resp *storagepb.HmacKeyMetadata var resp *storagepb.HmacKeyMetadata
err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error { err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {
@ -1271,7 +1337,18 @@ func (c *gRPCClient) GetHmacKey(ctx context.Context, req *storagepb.GetHmacKeyRe
} }
func (c *gRPCClient) ListHmacKeys(ctx context.Context, req *storagepb.ListHmacKeysRequest, opts ...gax.CallOption) *HmacKeyMetadataIterator { func (c *gRPCClient) ListHmacKeys(ctx context.Context, req *storagepb.ListHmacKeysRequest, opts ...gax.CallOption) *HmacKeyMetadataIterator {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(.*)"); reg.MatchString(req.GetProject()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetProject())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).ListHmacKeys[0:len((*c.CallOptions).ListHmacKeys):len((*c.CallOptions).ListHmacKeys)], opts...) opts = append((*c.CallOptions).ListHmacKeys[0:len((*c.CallOptions).ListHmacKeys):len((*c.CallOptions).ListHmacKeys)], opts...)
it := &HmacKeyMetadataIterator{} it := &HmacKeyMetadataIterator{}
req = proto.Clone(req).(*storagepb.ListHmacKeysRequest) req = proto.Clone(req).(*storagepb.ListHmacKeysRequest)
@ -1314,7 +1391,18 @@ func (c *gRPCClient) ListHmacKeys(ctx context.Context, req *storagepb.ListHmacKe
} }
func (c *gRPCClient) UpdateHmacKey(ctx context.Context, req *storagepb.UpdateHmacKeyRequest, opts ...gax.CallOption) (*storagepb.HmacKeyMetadata, error) { func (c *gRPCClient) UpdateHmacKey(ctx context.Context, req *storagepb.UpdateHmacKeyRequest, opts ...gax.CallOption) (*storagepb.HmacKeyMetadata, error) {
ctx = insertMetadata(ctx, c.xGoogMetadata) routingHeaders := ""
routingHeadersMap := make(map[string]string)
if reg := regexp.MustCompile("(?P<project>.*)"); reg.MatchString(req.GetHmacKey().GetProject()) && len(url.QueryEscape(reg.FindStringSubmatch(req.GetHmacKey().GetProject())[1])) > 0 {
routingHeadersMap["project"] = url.QueryEscape(reg.FindStringSubmatch(req.GetHmacKey().GetProject())[1])
}
for headerName, headerValue := range routingHeadersMap {
routingHeaders = fmt.Sprintf("%s%s=%s&", routingHeaders, headerName, headerValue)
}
routingHeaders = strings.TrimSuffix(routingHeaders, "&")
md := metadata.Pairs("x-goog-request-params", routingHeaders)
ctx = insertMetadata(ctx, c.xGoogMetadata, md)
opts = append((*c.CallOptions).UpdateHmacKey[0:len((*c.CallOptions).UpdateHmacKey):len((*c.CallOptions).UpdateHmacKey)], opts...) opts = append((*c.CallOptions).UpdateHmacKey[0:len((*c.CallOptions).UpdateHmacKey):len((*c.CallOptions).UpdateHmacKey)], opts...)
var resp *storagepb.HmacKeyMetadata var resp *storagepb.HmacKeyMetadata
err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error { err := gax.Invoke(ctx, func(ctx context.Context, settings gax.CallSettings) error {

File diff suppressed because it is too large Load diff

View file

@ -15,4 +15,4 @@
package internal package internal
// Version is the current tagged release of the library. // Version is the current tagged release of the library.
const Version = "1.27.0" const Version = "1.28.0"

View file

@ -340,7 +340,7 @@ func GenerateSignedPostPolicyV4(bucket, object string, opts *PostPolicyV4Options
"expiration": opts.Expires.Format(time.RFC3339), "expiration": opts.Expires.Format(time.RFC3339),
}) })
if err != nil { if err != nil {
return nil, fmt.Errorf("storage: PostPolicyV4 JSON serialization failed: %v", err) return nil, fmt.Errorf("storage: PostPolicyV4 JSON serialization failed: %w", err)
} }
b64Policy := base64.StdEncoding.EncodeToString(condsAsJSON) b64Policy := base64.StdEncoding.EncodeToString(condsAsJSON)

View file

@ -1,12 +0,0 @@
{
"release-type": "go-yoshi",
"separate-pull-requests": true,
"include-component-in-tag": true,
"tag-separator": "/",
"packages": {
"storage": {
"component": "storage"
}
},
"plugins": ["sentence-case"]
}

View file

@ -52,6 +52,7 @@ import (
htransport "google.golang.org/api/transport/http" htransport "google.golang.org/api/transport/http"
"google.golang.org/protobuf/proto" "google.golang.org/protobuf/proto"
"google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/reflect/protoreflect"
"google.golang.org/protobuf/types/known/fieldmaskpb"
"google.golang.org/protobuf/types/known/timestamppb" "google.golang.org/protobuf/types/known/timestamppb"
) )
@ -187,22 +188,22 @@ func NewClient(ctx context.Context, opts ...option.ClientOption) (*Client, error
// htransport selects the correct endpoint among WithEndpoint (user override), WithDefaultEndpoint, and WithDefaultMTLSEndpoint. // htransport selects the correct endpoint among WithEndpoint (user override), WithDefaultEndpoint, and WithDefaultMTLSEndpoint.
hc, ep, err := htransport.NewClient(ctx, opts...) hc, ep, err := htransport.NewClient(ctx, opts...)
if err != nil { if err != nil {
return nil, fmt.Errorf("dialing: %v", err) return nil, fmt.Errorf("dialing: %w", err)
} }
// RawService should be created with the chosen endpoint to take account of user override. // RawService should be created with the chosen endpoint to take account of user override.
rawService, err := raw.NewService(ctx, option.WithEndpoint(ep), option.WithHTTPClient(hc)) rawService, err := raw.NewService(ctx, option.WithEndpoint(ep), option.WithHTTPClient(hc))
if err != nil { if err != nil {
return nil, fmt.Errorf("storage client: %v", err) return nil, fmt.Errorf("storage client: %w", err)
} }
// Update readHost and scheme with the chosen endpoint. // Update readHost and scheme with the chosen endpoint.
u, err := url.Parse(ep) u, err := url.Parse(ep)
if err != nil { if err != nil {
return nil, fmt.Errorf("supplied endpoint %q is not valid: %v", ep, err) return nil, fmt.Errorf("supplied endpoint %q is not valid: %w", ep, err)
} }
tc, err := newHTTPStorageClient(ctx, withClientOptions(opts...)) tc, err := newHTTPStorageClient(ctx, withClientOptions(opts...))
if err != nil { if err != nil {
return nil, fmt.Errorf("storage: %v", err) return nil, fmt.Errorf("storage: %w", err)
} }
return &Client{ return &Client{
@ -1089,11 +1090,6 @@ func (o *ObjectAttrs) toRawObject(bucket string) *raw.Object {
// toProtoObject copies the editable attributes from o to the proto library's Object type. // toProtoObject copies the editable attributes from o to the proto library's Object type.
func (o *ObjectAttrs) toProtoObject(b string) *storagepb.Object { func (o *ObjectAttrs) toProtoObject(b string) *storagepb.Object {
checksums := &storagepb.ObjectChecksums{Md5Hash: o.MD5}
if o.CRC32C > 0 {
checksums.Crc32C = proto.Uint32(o.CRC32C)
}
// For now, there are only globally unique buckets, and "_" is the alias // For now, there are only globally unique buckets, and "_" is the alias
// project ID for such buckets. If the bucket is not provided, like in the // project ID for such buckets. If the bucket is not provided, like in the
// destination ObjectAttrs of a Copy, do not attempt to format it. // destination ObjectAttrs of a Copy, do not attempt to format it.
@ -1122,7 +1118,6 @@ func (o *ObjectAttrs) toProtoObject(b string) *storagepb.Object {
KmsKey: o.KMSKeyName, KmsKey: o.KMSKeyName,
Generation: o.Generation, Generation: o.Generation,
Size: o.Size, Size: o.Size,
Checksums: checksums,
} }
} }
@ -1489,10 +1484,11 @@ type Query struct {
// object will be included in the results. // object will be included in the results.
Versions bool Versions bool
// fieldSelection is used to select only specific fields to be returned by // attrSelection is used to select only specific fields to be returned by
// the query. It's used internally and is populated for the user by // the query. It is set by the user calling calling SetAttrSelection. These
// calling Query.SetAttrSelection // are used by toFieldMask and toFieldSelection for gRPC and HTTP/JSON
fieldSelection string // clients repsectively.
attrSelection []string
// StartOffset is used to filter results to objects whose names are // StartOffset is used to filter results to objects whose names are
// lexicographically equal to or after startOffset. If endOffset is also set, // lexicographically equal to or after startOffset. If endOffset is also set,
@ -1552,6 +1548,39 @@ var attrToFieldMap = map[string]string{
"CustomTime": "customTime", "CustomTime": "customTime",
} }
// attrToProtoFieldMap maps the field names of ObjectAttrs to the underlying field
// names in the protobuf Object message.
var attrToProtoFieldMap = map[string]string{
"Name": "name",
"Bucket": "bucket",
"Etag": "etag",
"Generation": "generation",
"Metageneration": "metageneration",
"StorageClass": "storage_class",
"Size": "size",
"ContentEncoding": "content_encoding",
"ContentDisposition": "content_disposition",
"CacheControl": "cache_control",
"ACL": "acl",
"ContentLanguage": "content_language",
"Deleted": "delete_time",
"ContentType": "content_type",
"Created": "create_time",
"CRC32C": "checksums.crc32c",
"MD5": "checksums.md5_hash",
"Updated": "update_time",
"KMSKeyName": "kms_key",
"TemporaryHold": "temporary_hold",
"RetentionExpirationTime": "retention_expire_time",
"Metadata": "metadata",
"EventBasedHold": "event_based_hold",
"Owner": "owner",
"CustomerKeySHA256": "customer_encryption",
"CustomTime": "custom_time",
// MediaLink was explicitly excluded from the proto as it is an HTTP-ism.
// "MediaLink": "mediaLink",
}
// SetAttrSelection makes the query populate only specific attributes of // SetAttrSelection makes the query populate only specific attributes of
// objects. When iterating over objects, if you only need each object's name // objects. When iterating over objects, if you only need each object's name
// and size, pass []string{"Name", "Size"} to this method. Only these fields // and size, pass []string{"Name", "Size"} to this method. Only these fields
@ -1560,16 +1589,42 @@ var attrToFieldMap = map[string]string{
// optimization; for more information, see // optimization; for more information, see
// https://cloud.google.com/storage/docs/json_api/v1/how-tos/performance // https://cloud.google.com/storage/docs/json_api/v1/how-tos/performance
func (q *Query) SetAttrSelection(attrs []string) error { func (q *Query) SetAttrSelection(attrs []string) error {
// Validate selections.
for _, attr := range attrs {
// If the attr is acceptable for one of the two sets, then it is OK.
// If it is not acceptable for either, then return an error.
// The respective masking implementations ignore unknown attrs which
// makes switching between transports a little easier.
_, okJSON := attrToFieldMap[attr]
_, okGRPC := attrToProtoFieldMap[attr]
if !okJSON && !okGRPC {
return fmt.Errorf("storage: attr %v is not valid", attr)
}
}
q.attrSelection = attrs
return nil
}
func (q *Query) toFieldSelection() string {
if q == nil || len(q.attrSelection) == 0 {
return ""
}
fieldSet := make(map[string]bool) fieldSet := make(map[string]bool)
for _, attr := range attrs { for _, attr := range q.attrSelection {
field, ok := attrToFieldMap[attr] field, ok := attrToFieldMap[attr]
if !ok { if !ok {
return fmt.Errorf("storage: attr %v is not valid", attr) // Future proofing, skip unknown fields, let SetAttrSelection handle
// error modes.
continue
} }
fieldSet[field] = true fieldSet[field] = true
} }
var s string
if len(fieldSet) > 0 { if len(fieldSet) > 0 {
var b bytes.Buffer var b bytes.Buffer
b.WriteString("prefixes,items(") b.WriteString("prefixes,items(")
@ -1582,9 +1637,50 @@ func (q *Query) SetAttrSelection(attrs []string) error {
b.WriteString(field) b.WriteString(field)
} }
b.WriteString(")") b.WriteString(")")
q.fieldSelection = b.String() s = b.String()
} }
return nil return s
}
func (q *Query) toFieldMask() *fieldmaskpb.FieldMask {
// The default behavior with no Query is ProjectionDefault (i.e. ProjectionFull).
if q == nil {
return &fieldmaskpb.FieldMask{Paths: []string{"*"}}
}
// User selected attributes via q.SetAttrSeleciton. This takes precedence
// over the Projection.
if numSelected := len(q.attrSelection); numSelected > 0 {
protoFieldPaths := make([]string, 0, numSelected)
for _, attr := range q.attrSelection {
pf, ok := attrToProtoFieldMap[attr]
if !ok {
// Future proofing, skip unknown fields, let SetAttrSelection
// handle error modes.
continue
}
protoFieldPaths = append(protoFieldPaths, pf)
}
return &fieldmaskpb.FieldMask{Paths: protoFieldPaths}
}
// ProjectDefault == ProjectionFull which means all fields.
fm := &fieldmaskpb.FieldMask{Paths: []string{"*"}}
if q.Projection == ProjectionNoACL {
paths := make([]string, 0, len(attrToProtoFieldMap)-2) // omitting two fields
for _, f := range attrToProtoFieldMap {
// Skip the acl and owner fields for "NoACL".
if f == "acl" || f == "owner" {
continue
}
paths = append(paths, f)
}
fm.Paths = paths
}
return fm
} }
// Conditions constrain methods to act on specific generations of // Conditions constrain methods to act on specific generations of

View file

@ -176,7 +176,6 @@ func (w *Writer) openWriter() (err error) {
isIdempotent := w.o.conds != nil && (w.o.conds.GenerationMatch >= 0 || w.o.conds.DoesNotExist == true) isIdempotent := w.o.conds != nil && (w.o.conds.GenerationMatch >= 0 || w.o.conds.DoesNotExist == true)
opts := makeStorageOpts(isIdempotent, w.o.retry, w.o.userProject) opts := makeStorageOpts(isIdempotent, w.o.retry, w.o.userProject)
go w.monitorCancel()
params := &openWriterParams{ params := &openWriterParams{
ctx: w.ctx, ctx: w.ctx,
chunkSize: w.ChunkSize, chunkSize: w.ChunkSize,
@ -191,11 +190,15 @@ func (w *Writer) openWriter() (err error) {
progress: w.progress, progress: w.progress,
setObj: func(o *ObjectAttrs) { w.obj = o }, setObj: func(o *ObjectAttrs) { w.obj = o },
} }
if err := w.ctx.Err(); err != nil {
return err // short-circuit
}
w.pw, err = w.o.c.tc.OpenWriter(params, opts...) w.pw, err = w.o.c.tc.OpenWriter(params, opts...)
if err != nil { if err != nil {
return err return err
} }
w.opened = true w.opened = true
go w.monitorCancel()
return nil return nil
} }

View file

@ -49,9 +49,12 @@ func (er *Resource[TResource, TState]) Get(state TState) (TResource, error) {
const window = 5 * time.Minute // This example updates the resource 5 minutes prior to expiration const window = 5 * time.Minute // This example updates the resource 5 minutes prior to expiration
const backoff = 30 * time.Second // Minimum wait time between eager update attempts const backoff = 30 * time.Second // Minimum wait time between eager update attempts
now, acquire, expired, resource := time.Now(), false, false, er.resource now, acquire, expired := time.Now(), false, false
// acquire exclusive lock // acquire exclusive lock
er.cond.L.Lock() er.cond.L.Lock()
resource := er.resource
for { for {
expired = er.expiration.IsZero() || er.expiration.Before(now) expired = er.expiration.IsZero() || er.expiration.Before(now)
if expired { if expired {

View file

@ -246,7 +246,8 @@ func (v *CounterVec) GetMetricWith(labels Labels) (Counter, error) {
// WithLabelValues works as GetMetricWithLabelValues, but panics where // WithLabelValues works as GetMetricWithLabelValues, but panics where
// GetMetricWithLabelValues would have returned an error. Not returning an // GetMetricWithLabelValues would have returned an error. Not returning an
// error allows shortcuts like // error allows shortcuts like
// myVec.WithLabelValues("404", "GET").Add(42) //
// myVec.WithLabelValues("404", "GET").Add(42)
func (v *CounterVec) WithLabelValues(lvs ...string) Counter { func (v *CounterVec) WithLabelValues(lvs ...string) Counter {
c, err := v.GetMetricWithLabelValues(lvs...) c, err := v.GetMetricWithLabelValues(lvs...)
if err != nil { if err != nil {
@ -257,7 +258,8 @@ func (v *CounterVec) WithLabelValues(lvs ...string) Counter {
// With works as GetMetricWith, but panics where GetMetricWithLabels would have // With works as GetMetricWith, but panics where GetMetricWithLabels would have
// returned an error. Not returning an error allows shortcuts like // returned an error. Not returning an error allows shortcuts like
// myVec.With(prometheus.Labels{"code": "404", "method": "GET"}).Add(42) //
// myVec.With(prometheus.Labels{"code": "404", "method": "GET"}).Add(42)
func (v *CounterVec) With(labels Labels) Counter { func (v *CounterVec) With(labels Labels) Counter {
c, err := v.GetMetricWith(labels) c, err := v.GetMetricWith(labels)
if err != nil { if err != nil {

View file

@ -21,55 +21,66 @@
// All exported functions and methods are safe to be used concurrently unless // All exported functions and methods are safe to be used concurrently unless
// specified otherwise. // specified otherwise.
// //
// A Basic Example // # A Basic Example
// //
// As a starting point, a very basic usage example: // As a starting point, a very basic usage example:
// //
// package main // package main
// //
// import ( // import (
// "log" // "log"
// "net/http" // "net/http"
// //
// "github.com/prometheus/client_golang/prometheus" // "github.com/prometheus/client_golang/prometheus"
// "github.com/prometheus/client_golang/prometheus/promhttp" // "github.com/prometheus/client_golang/prometheus/promhttp"
// ) // )
// //
// var ( // type metrics struct {
// cpuTemp = prometheus.NewGauge(prometheus.GaugeOpts{ // cpuTemp prometheus.Gauge
// Name: "cpu_temperature_celsius", // hdFailures *prometheus.CounterVec
// Help: "Current temperature of the CPU.", // }
// })
// hdFailures = prometheus.NewCounterVec(
// prometheus.CounterOpts{
// Name: "hd_errors_total",
// Help: "Number of hard-disk errors.",
// },
// []string{"device"},
// )
// )
// //
// func init() { // func NewMetrics(reg prometheus.Registerer) *metrics {
// // Metrics have to be registered to be exposed: // m := &metrics{
// prometheus.MustRegister(cpuTemp) // cpuTemp: prometheus.NewGauge(prometheus.GaugeOpts{
// prometheus.MustRegister(hdFailures) // Name: "cpu_temperature_celsius",
// } // Help: "Current temperature of the CPU.",
// }),
// hdFailures: prometheus.NewCounterVec(
// prometheus.CounterOpts{
// Name: "hd_errors_total",
// Help: "Number of hard-disk errors.",
// },
// []string{"device"},
// ),
// }
// reg.MustRegister(m.cpuTemp)
// reg.MustRegister(m.hdFailures)
// return m
// }
// //
// func main() { // func main() {
// cpuTemp.Set(65.3) // // Create a non-global registry.
// hdFailures.With(prometheus.Labels{"device":"/dev/sda"}).Inc() // reg := prometheus.NewRegistry()
// //
// // The Handler function provides a default handler to expose metrics // // Create new metrics and register them using the custom registry.
// // via an HTTP server. "/metrics" is the usual endpoint for that. // m := NewMetrics(reg)
// http.Handle("/metrics", promhttp.Handler()) // // Set values for the new created metrics.
// log.Fatal(http.ListenAndServe(":8080", nil)) // m.cpuTemp.Set(65.3)
// } // m.hdFailures.With(prometheus.Labels{"device":"/dev/sda"}).Inc()
// //
// // Expose metrics and custom registry via an HTTP server
// // using the HandleFor function. "/metrics" is the usual endpoint for that.
// http.Handle("/metrics", promhttp.HandlerFor(reg, promhttp.HandlerOpts{Registry: reg}))
// log.Fatal(http.ListenAndServe(":8080", nil))
// }
// //
// This is a complete program that exports two metrics, a Gauge and a Counter, // This is a complete program that exports two metrics, a Gauge and a Counter,
// the latter with a label attached to turn it into a (one-dimensional) vector. // the latter with a label attached to turn it into a (one-dimensional) vector.
// It register the metrics using a custom registry and exposes them via an HTTP server
// on the /metrics endpoint.
// //
// Metrics // # Metrics
// //
// The number of exported identifiers in this package might appear a bit // The number of exported identifiers in this package might appear a bit
// overwhelming. However, in addition to the basic plumbing shown in the example // overwhelming. However, in addition to the basic plumbing shown in the example
@ -100,7 +111,7 @@
// To create instances of Metrics and their vector versions, you need a suitable // To create instances of Metrics and their vector versions, you need a suitable
// …Opts struct, i.e. GaugeOpts, CounterOpts, SummaryOpts, or HistogramOpts. // …Opts struct, i.e. GaugeOpts, CounterOpts, SummaryOpts, or HistogramOpts.
// //
// Custom Collectors and constant Metrics // # Custom Collectors and constant Metrics
// //
// While you could create your own implementations of Metric, most likely you // While you could create your own implementations of Metric, most likely you
// will only ever implement the Collector interface on your own. At a first // will only ever implement the Collector interface on your own. At a first
@ -141,7 +152,7 @@
// a metric, GaugeFunc, CounterFunc, or UntypedFunc might be interesting // a metric, GaugeFunc, CounterFunc, or UntypedFunc might be interesting
// shortcuts. // shortcuts.
// //
// Advanced Uses of the Registry // # Advanced Uses of the Registry
// //
// While MustRegister is the by far most common way of registering a Collector, // While MustRegister is the by far most common way of registering a Collector,
// sometimes you might want to handle the errors the registration might cause. // sometimes you might want to handle the errors the registration might cause.
@ -176,23 +187,23 @@
// NewProcessCollector). With a custom registry, you are in control and decide // NewProcessCollector). With a custom registry, you are in control and decide
// yourself about the Collectors to register. // yourself about the Collectors to register.
// //
// HTTP Exposition // # HTTP Exposition
// //
// The Registry implements the Gatherer interface. The caller of the Gather // The Registry implements the Gatherer interface. The caller of the Gather
// method can then expose the gathered metrics in some way. Usually, the metrics // method can then expose the gathered metrics in some way. Usually, the metrics
// are served via HTTP on the /metrics endpoint. That's happening in the example // are served via HTTP on the /metrics endpoint. That's happening in the example
// above. The tools to expose metrics via HTTP are in the promhttp sub-package. // above. The tools to expose metrics via HTTP are in the promhttp sub-package.
// //
// Pushing to the Pushgateway // # Pushing to the Pushgateway
// //
// Function for pushing to the Pushgateway can be found in the push sub-package. // Function for pushing to the Pushgateway can be found in the push sub-package.
// //
// Graphite Bridge // # Graphite Bridge
// //
// Functions and examples to push metrics from a Gatherer to Graphite can be // Functions and examples to push metrics from a Gatherer to Graphite can be
// found in the graphite sub-package. // found in the graphite sub-package.
// //
// Other Means of Exposition // # Other Means of Exposition
// //
// More ways of exposing metrics can easily be added by following the approaches // More ways of exposing metrics can easily be added by following the approaches
// of the existing implementations. // of the existing implementations.

View file

@ -210,7 +210,8 @@ func (v *GaugeVec) GetMetricWith(labels Labels) (Gauge, error) {
// WithLabelValues works as GetMetricWithLabelValues, but panics where // WithLabelValues works as GetMetricWithLabelValues, but panics where
// GetMetricWithLabelValues would have returned an error. Not returning an // GetMetricWithLabelValues would have returned an error. Not returning an
// error allows shortcuts like // error allows shortcuts like
// myVec.WithLabelValues("404", "GET").Add(42) //
// myVec.WithLabelValues("404", "GET").Add(42)
func (v *GaugeVec) WithLabelValues(lvs ...string) Gauge { func (v *GaugeVec) WithLabelValues(lvs ...string) Gauge {
g, err := v.GetMetricWithLabelValues(lvs...) g, err := v.GetMetricWithLabelValues(lvs...)
if err != nil { if err != nil {
@ -221,7 +222,8 @@ func (v *GaugeVec) WithLabelValues(lvs ...string) Gauge {
// With works as GetMetricWith, but panics where GetMetricWithLabels would have // With works as GetMetricWith, but panics where GetMetricWithLabels would have
// returned an error. Not returning an error allows shortcuts like // returned an error. Not returning an error allows shortcuts like
// myVec.With(prometheus.Labels{"code": "404", "method": "GET"}).Add(42) //
// myVec.With(prometheus.Labels{"code": "404", "method": "GET"}).Add(42)
func (v *GaugeVec) With(labels Labels) Gauge { func (v *GaugeVec) With(labels Labels) Gauge {
g, err := v.GetMetricWith(labels) g, err := v.GetMetricWith(labels)
if err != nil { if err != nil {

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,60 @@
// Copyright (c) 2015 Björn Rabenstein
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all
// copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
//
// The code in this package is copy/paste to avoid a dependency. Hence this file
// carries the copyright of the original repo.
// https://github.com/beorn7/floats
package internal
import (
"math"
)
// minNormalFloat64 is the smallest positive normal value of type float64.
var minNormalFloat64 = math.Float64frombits(0x0010000000000000)
// AlmostEqualFloat64 returns true if a and b are equal within a relative error
// of epsilon. See http://floating-point-gui.de/errors/comparison/ for the
// details of the applied method.
func AlmostEqualFloat64(a, b, epsilon float64) bool {
if a == b {
return true
}
absA := math.Abs(a)
absB := math.Abs(b)
diff := math.Abs(a - b)
if a == 0 || b == 0 || absA+absB < minNormalFloat64 {
return diff < epsilon*minNormalFloat64
}
return diff/math.Min(absA+absB, math.MaxFloat64) < epsilon
}
// AlmostEqualFloat64s is the slice form of AlmostEqualFloat64.
func AlmostEqualFloat64s(a, b []float64, epsilon float64) bool {
if len(a) != len(b) {
return false
}
for i := range a {
if !AlmostEqualFloat64(a[i], b[i], epsilon) {
return false
}
}
return true
}

View file

@ -201,12 +201,15 @@ func (m *SequenceMatcher) isBJunk(s string) bool {
// If IsJunk is not defined: // If IsJunk is not defined:
// //
// Return (i,j,k) such that a[i:i+k] is equal to b[j:j+k], where // Return (i,j,k) such that a[i:i+k] is equal to b[j:j+k], where
// alo <= i <= i+k <= ahi //
// blo <= j <= j+k <= bhi // alo <= i <= i+k <= ahi
// blo <= j <= j+k <= bhi
//
// and for all (i',j',k') meeting those conditions, // and for all (i',j',k') meeting those conditions,
// k >= k' //
// i <= i' // k >= k'
// and if i == i', j <= j' // i <= i'
// and if i == i', j <= j'
// //
// In other words, of all maximal matching blocks, return one that // In other words, of all maximal matching blocks, return one that
// starts earliest in a, and of all those maximal matching blocks that // starts earliest in a, and of all those maximal matching blocks that

View file

@ -25,7 +25,8 @@ import (
// Labels represents a collection of label name -> value mappings. This type is // Labels represents a collection of label name -> value mappings. This type is
// commonly used with the With(Labels) and GetMetricWith(Labels) methods of // commonly used with the With(Labels) and GetMetricWith(Labels) methods of
// metric vector Collectors, e.g.: // metric vector Collectors, e.g.:
// myVec.With(Labels{"code": "404", "method": "GET"}).Add(42) //
// myVec.With(Labels{"code": "404", "method": "GET"}).Add(42)
// //
// The other use-case is the specification of constant label pairs in Opts or to // The other use-case is the specification of constant label pairs in Opts or to
// create a Desc. // create a Desc.

View file

@ -252,9 +252,12 @@ func (errs MultiError) MaybeUnwrap() error {
} }
// Registry registers Prometheus collectors, collects their metrics, and gathers // Registry registers Prometheus collectors, collects their metrics, and gathers
// them into MetricFamilies for exposition. It implements both Registerer and // them into MetricFamilies for exposition. It implements Registerer, Gatherer,
// Gatherer. The zero value is not usable. Create instances with NewRegistry or // and Collector. The zero value is not usable. Create instances with
// NewPedanticRegistry. // NewRegistry or NewPedanticRegistry.
//
// Registry implements Collector to allow it to be used for creating groups of
// metrics. See the Grouping example for how this can be done.
type Registry struct { type Registry struct {
mtx sync.RWMutex mtx sync.RWMutex
collectorsByID map[uint64]Collector // ID is a hash of the descIDs. collectorsByID map[uint64]Collector // ID is a hash of the descIDs.
@ -556,6 +559,31 @@ func (r *Registry) Gather() ([]*dto.MetricFamily, error) {
return internal.NormalizeMetricFamilies(metricFamiliesByName), errs.MaybeUnwrap() return internal.NormalizeMetricFamilies(metricFamiliesByName), errs.MaybeUnwrap()
} }
// Describe implements Collector.
func (r *Registry) Describe(ch chan<- *Desc) {
r.mtx.RLock()
defer r.mtx.RUnlock()
// Only report the checked Collectors; unchecked collectors don't report any
// Desc.
for _, c := range r.collectorsByID {
c.Describe(ch)
}
}
// Collect implements Collector.
func (r *Registry) Collect(ch chan<- Metric) {
r.mtx.RLock()
defer r.mtx.RUnlock()
for _, c := range r.collectorsByID {
c.Collect(ch)
}
for _, c := range r.uncheckedCollectors {
c.Collect(ch)
}
}
// WriteToTextfile calls Gather on the provided Gatherer, encodes the result in the // WriteToTextfile calls Gather on the provided Gatherer, encodes the result in the
// Prometheus text format, and writes it to a temporary file. Upon success, the // Prometheus text format, and writes it to a temporary file. Upon success, the
// temporary file is renamed to the provided filename. // temporary file is renamed to the provided filename.

View file

@ -603,7 +603,8 @@ func (v *SummaryVec) GetMetricWith(labels Labels) (Observer, error) {
// WithLabelValues works as GetMetricWithLabelValues, but panics where // WithLabelValues works as GetMetricWithLabelValues, but panics where
// GetMetricWithLabelValues would have returned an error. Not returning an // GetMetricWithLabelValues would have returned an error. Not returning an
// error allows shortcuts like // error allows shortcuts like
// myVec.WithLabelValues("404", "GET").Observe(42.21) //
// myVec.WithLabelValues("404", "GET").Observe(42.21)
func (v *SummaryVec) WithLabelValues(lvs ...string) Observer { func (v *SummaryVec) WithLabelValues(lvs ...string) Observer {
s, err := v.GetMetricWithLabelValues(lvs...) s, err := v.GetMetricWithLabelValues(lvs...)
if err != nil { if err != nil {
@ -614,7 +615,8 @@ func (v *SummaryVec) WithLabelValues(lvs ...string) Observer {
// With works as GetMetricWith, but panics where GetMetricWithLabels would have // With works as GetMetricWith, but panics where GetMetricWithLabels would have
// returned an error. Not returning an error allows shortcuts like // returned an error. Not returning an error allows shortcuts like
// myVec.With(prometheus.Labels{"code": "404", "method": "GET"}).Observe(42.21) //
// myVec.With(prometheus.Labels{"code": "404", "method": "GET"}).Observe(42.21)
func (v *SummaryVec) With(labels Labels) Observer { func (v *SummaryVec) With(labels Labels) Observer {
s, err := v.GetMetricWith(labels) s, err := v.GetMetricWith(labels)
if err != nil { if err != nil {
@ -701,7 +703,8 @@ func (s *constSummary) Write(out *dto.Metric) error {
// //
// quantiles maps ranks to quantile values. For example, a median latency of // quantiles maps ranks to quantile values. For example, a median latency of
// 0.23s and a 99th percentile latency of 0.56s would be expressed as: // 0.23s and a 99th percentile latency of 0.56s would be expressed as:
// map[float64]float64{0.5: 0.23, 0.99: 0.56} //
// map[float64]float64{0.5: 0.23, 0.99: 0.56}
// //
// NewConstSummary returns an error if the length of labelValues is not // NewConstSummary returns an error if the length of labelValues is not
// consistent with the variable labels in Desc or if Desc is invalid. // consistent with the variable labels in Desc or if Desc is invalid.

View file

@ -25,11 +25,12 @@ type Timer struct {
// NewTimer creates a new Timer. The provided Observer is used to observe a // NewTimer creates a new Timer. The provided Observer is used to observe a
// duration in seconds. Timer is usually used to time a function call in the // duration in seconds. Timer is usually used to time a function call in the
// following way: // following way:
// func TimeMe() { //
// timer := NewTimer(myHistogram) // func TimeMe() {
// defer timer.ObserveDuration() // timer := NewTimer(myHistogram)
// // Do actual work. // defer timer.ObserveDuration()
// } // // Do actual work.
// }
func NewTimer(o Observer) *Timer { func NewTimer(o Observer) *Timer {
return &Timer{ return &Timer{
begin: time.Now(), begin: time.Now(),

View file

@ -27,7 +27,14 @@ func buildCommonHeaderMaps() {
"accept-language", "accept-language",
"accept-ranges", "accept-ranges",
"age", "age",
"access-control-allow-credentials",
"access-control-allow-headers",
"access-control-allow-methods",
"access-control-allow-origin", "access-control-allow-origin",
"access-control-expose-headers",
"access-control-max-age",
"access-control-request-headers",
"access-control-request-method",
"allow", "allow",
"authorization", "authorization",
"cache-control", "cache-control",
@ -53,6 +60,7 @@ func buildCommonHeaderMaps() {
"link", "link",
"location", "location",
"max-forwards", "max-forwards",
"origin",
"proxy-authenticate", "proxy-authenticate",
"proxy-authorization", "proxy-authorization",
"range", "range",
@ -68,6 +76,8 @@ func buildCommonHeaderMaps() {
"vary", "vary",
"via", "via",
"www-authenticate", "www-authenticate",
"x-forwarded-for",
"x-forwarded-proto",
} }
commonLowerHeader = make(map[string]string, len(common)) commonLowerHeader = make(map[string]string, len(common))
commonCanonHeader = make(map[string]string, len(common)) commonCanonHeader = make(map[string]string, len(common))
@ -85,3 +95,11 @@ func lowerHeader(v string) (lower string, ascii bool) {
} }
return asciiToLower(v) return asciiToLower(v)
} }
func canonicalHeader(v string) string {
buildCommonHeaderMapsOnce()
if s, ok := commonCanonHeader[v]; ok {
return s
}
return http.CanonicalHeaderKey(v)
}

188
vendor/golang.org/x/net/http2/hpack/static_table.go generated vendored Normal file
View file

@ -0,0 +1,188 @@
// go generate gen.go
// Code generated by the command above; DO NOT EDIT.
package hpack
var staticTable = &headerFieldTable{
evictCount: 0,
byName: map[string]uint64{
":authority": 1,
":method": 3,
":path": 5,
":scheme": 7,
":status": 14,
"accept-charset": 15,
"accept-encoding": 16,
"accept-language": 17,
"accept-ranges": 18,
"accept": 19,
"access-control-allow-origin": 20,
"age": 21,
"allow": 22,
"authorization": 23,
"cache-control": 24,
"content-disposition": 25,
"content-encoding": 26,
"content-language": 27,
"content-length": 28,
"content-location": 29,
"content-range": 30,
"content-type": 31,
"cookie": 32,
"date": 33,
"etag": 34,
"expect": 35,
"expires": 36,
"from": 37,
"host": 38,
"if-match": 39,
"if-modified-since": 40,
"if-none-match": 41,
"if-range": 42,
"if-unmodified-since": 43,
"last-modified": 44,
"link": 45,
"location": 46,
"max-forwards": 47,
"proxy-authenticate": 48,
"proxy-authorization": 49,
"range": 50,
"referer": 51,
"refresh": 52,
"retry-after": 53,
"server": 54,
"set-cookie": 55,
"strict-transport-security": 56,
"transfer-encoding": 57,
"user-agent": 58,
"vary": 59,
"via": 60,
"www-authenticate": 61,
},
byNameValue: map[pairNameValue]uint64{
{name: ":authority", value: ""}: 1,
{name: ":method", value: "GET"}: 2,
{name: ":method", value: "POST"}: 3,
{name: ":path", value: "/"}: 4,
{name: ":path", value: "/index.html"}: 5,
{name: ":scheme", value: "http"}: 6,
{name: ":scheme", value: "https"}: 7,
{name: ":status", value: "200"}: 8,
{name: ":status", value: "204"}: 9,
{name: ":status", value: "206"}: 10,
{name: ":status", value: "304"}: 11,
{name: ":status", value: "400"}: 12,
{name: ":status", value: "404"}: 13,
{name: ":status", value: "500"}: 14,
{name: "accept-charset", value: ""}: 15,
{name: "accept-encoding", value: "gzip, deflate"}: 16,
{name: "accept-language", value: ""}: 17,
{name: "accept-ranges", value: ""}: 18,
{name: "accept", value: ""}: 19,
{name: "access-control-allow-origin", value: ""}: 20,
{name: "age", value: ""}: 21,
{name: "allow", value: ""}: 22,
{name: "authorization", value: ""}: 23,
{name: "cache-control", value: ""}: 24,
{name: "content-disposition", value: ""}: 25,
{name: "content-encoding", value: ""}: 26,
{name: "content-language", value: ""}: 27,
{name: "content-length", value: ""}: 28,
{name: "content-location", value: ""}: 29,
{name: "content-range", value: ""}: 30,
{name: "content-type", value: ""}: 31,
{name: "cookie", value: ""}: 32,
{name: "date", value: ""}: 33,
{name: "etag", value: ""}: 34,
{name: "expect", value: ""}: 35,
{name: "expires", value: ""}: 36,
{name: "from", value: ""}: 37,
{name: "host", value: ""}: 38,
{name: "if-match", value: ""}: 39,
{name: "if-modified-since", value: ""}: 40,
{name: "if-none-match", value: ""}: 41,
{name: "if-range", value: ""}: 42,
{name: "if-unmodified-since", value: ""}: 43,
{name: "last-modified", value: ""}: 44,
{name: "link", value: ""}: 45,
{name: "location", value: ""}: 46,
{name: "max-forwards", value: ""}: 47,
{name: "proxy-authenticate", value: ""}: 48,
{name: "proxy-authorization", value: ""}: 49,
{name: "range", value: ""}: 50,
{name: "referer", value: ""}: 51,
{name: "refresh", value: ""}: 52,
{name: "retry-after", value: ""}: 53,
{name: "server", value: ""}: 54,
{name: "set-cookie", value: ""}: 55,
{name: "strict-transport-security", value: ""}: 56,
{name: "transfer-encoding", value: ""}: 57,
{name: "user-agent", value: ""}: 58,
{name: "vary", value: ""}: 59,
{name: "via", value: ""}: 60,
{name: "www-authenticate", value: ""}: 61,
},
ents: []HeaderField{
{Name: ":authority", Value: "", Sensitive: false},
{Name: ":method", Value: "GET", Sensitive: false},
{Name: ":method", Value: "POST", Sensitive: false},
{Name: ":path", Value: "/", Sensitive: false},
{Name: ":path", Value: "/index.html", Sensitive: false},
{Name: ":scheme", Value: "http", Sensitive: false},
{Name: ":scheme", Value: "https", Sensitive: false},
{Name: ":status", Value: "200", Sensitive: false},
{Name: ":status", Value: "204", Sensitive: false},
{Name: ":status", Value: "206", Sensitive: false},
{Name: ":status", Value: "304", Sensitive: false},
{Name: ":status", Value: "400", Sensitive: false},
{Name: ":status", Value: "404", Sensitive: false},
{Name: ":status", Value: "500", Sensitive: false},
{Name: "accept-charset", Value: "", Sensitive: false},
{Name: "accept-encoding", Value: "gzip, deflate", Sensitive: false},
{Name: "accept-language", Value: "", Sensitive: false},
{Name: "accept-ranges", Value: "", Sensitive: false},
{Name: "accept", Value: "", Sensitive: false},
{Name: "access-control-allow-origin", Value: "", Sensitive: false},
{Name: "age", Value: "", Sensitive: false},
{Name: "allow", Value: "", Sensitive: false},
{Name: "authorization", Value: "", Sensitive: false},
{Name: "cache-control", Value: "", Sensitive: false},
{Name: "content-disposition", Value: "", Sensitive: false},
{Name: "content-encoding", Value: "", Sensitive: false},
{Name: "content-language", Value: "", Sensitive: false},
{Name: "content-length", Value: "", Sensitive: false},
{Name: "content-location", Value: "", Sensitive: false},
{Name: "content-range", Value: "", Sensitive: false},
{Name: "content-type", Value: "", Sensitive: false},
{Name: "cookie", Value: "", Sensitive: false},
{Name: "date", Value: "", Sensitive: false},
{Name: "etag", Value: "", Sensitive: false},
{Name: "expect", Value: "", Sensitive: false},
{Name: "expires", Value: "", Sensitive: false},
{Name: "from", Value: "", Sensitive: false},
{Name: "host", Value: "", Sensitive: false},
{Name: "if-match", Value: "", Sensitive: false},
{Name: "if-modified-since", Value: "", Sensitive: false},
{Name: "if-none-match", Value: "", Sensitive: false},
{Name: "if-range", Value: "", Sensitive: false},
{Name: "if-unmodified-since", Value: "", Sensitive: false},
{Name: "last-modified", Value: "", Sensitive: false},
{Name: "link", Value: "", Sensitive: false},
{Name: "location", Value: "", Sensitive: false},
{Name: "max-forwards", Value: "", Sensitive: false},
{Name: "proxy-authenticate", Value: "", Sensitive: false},
{Name: "proxy-authorization", Value: "", Sensitive: false},
{Name: "range", Value: "", Sensitive: false},
{Name: "referer", Value: "", Sensitive: false},
{Name: "refresh", Value: "", Sensitive: false},
{Name: "retry-after", Value: "", Sensitive: false},
{Name: "server", Value: "", Sensitive: false},
{Name: "set-cookie", Value: "", Sensitive: false},
{Name: "strict-transport-security", Value: "", Sensitive: false},
{Name: "transfer-encoding", Value: "", Sensitive: false},
{Name: "user-agent", Value: "", Sensitive: false},
{Name: "vary", Value: "", Sensitive: false},
{Name: "via", Value: "", Sensitive: false},
{Name: "www-authenticate", Value: "", Sensitive: false},
},
}

View file

@ -96,8 +96,7 @@ func (t *headerFieldTable) evictOldest(n int) {
// meaning t.ents is reversed for dynamic tables. Hence, when t is a dynamic // meaning t.ents is reversed for dynamic tables. Hence, when t is a dynamic
// table, the return value i actually refers to the entry t.ents[t.len()-i]. // table, the return value i actually refers to the entry t.ents[t.len()-i].
// //
// All tables are assumed to be a dynamic tables except for the global // All tables are assumed to be a dynamic tables except for the global staticTable.
// staticTable pointer.
// //
// See Section 2.3.3. // See Section 2.3.3.
func (t *headerFieldTable) search(f HeaderField) (i uint64, nameValueMatch bool) { func (t *headerFieldTable) search(f HeaderField) (i uint64, nameValueMatch bool) {
@ -125,81 +124,6 @@ func (t *headerFieldTable) idToIndex(id uint64) uint64 {
return k + 1 return k + 1
} }
// http://tools.ietf.org/html/draft-ietf-httpbis-header-compression-07#appendix-B
var staticTable = newStaticTable()
var staticTableEntries = [...]HeaderField{
{Name: ":authority"},
{Name: ":method", Value: "GET"},
{Name: ":method", Value: "POST"},
{Name: ":path", Value: "/"},
{Name: ":path", Value: "/index.html"},
{Name: ":scheme", Value: "http"},
{Name: ":scheme", Value: "https"},
{Name: ":status", Value: "200"},
{Name: ":status", Value: "204"},
{Name: ":status", Value: "206"},
{Name: ":status", Value: "304"},
{Name: ":status", Value: "400"},
{Name: ":status", Value: "404"},
{Name: ":status", Value: "500"},
{Name: "accept-charset"},
{Name: "accept-encoding", Value: "gzip, deflate"},
{Name: "accept-language"},
{Name: "accept-ranges"},
{Name: "accept"},
{Name: "access-control-allow-origin"},
{Name: "age"},
{Name: "allow"},
{Name: "authorization"},
{Name: "cache-control"},
{Name: "content-disposition"},
{Name: "content-encoding"},
{Name: "content-language"},
{Name: "content-length"},
{Name: "content-location"},
{Name: "content-range"},
{Name: "content-type"},
{Name: "cookie"},
{Name: "date"},
{Name: "etag"},
{Name: "expect"},
{Name: "expires"},
{Name: "from"},
{Name: "host"},
{Name: "if-match"},
{Name: "if-modified-since"},
{Name: "if-none-match"},
{Name: "if-range"},
{Name: "if-unmodified-since"},
{Name: "last-modified"},
{Name: "link"},
{Name: "location"},
{Name: "max-forwards"},
{Name: "proxy-authenticate"},
{Name: "proxy-authorization"},
{Name: "range"},
{Name: "referer"},
{Name: "refresh"},
{Name: "retry-after"},
{Name: "server"},
{Name: "set-cookie"},
{Name: "strict-transport-security"},
{Name: "transfer-encoding"},
{Name: "user-agent"},
{Name: "vary"},
{Name: "via"},
{Name: "www-authenticate"},
}
func newStaticTable() *headerFieldTable {
t := &headerFieldTable{}
t.init()
for _, e := range staticTableEntries[:] {
t.addEntry(e)
}
return t
}
var huffmanCodes = [256]uint32{ var huffmanCodes = [256]uint32{
0x1ff8, 0x1ff8,
0x7fffd8, 0x7fffd8,

View file

@ -622,7 +622,9 @@ type stream struct {
resetQueued bool // RST_STREAM queued for write; set by sc.resetStream resetQueued bool // RST_STREAM queued for write; set by sc.resetStream
gotTrailerHeader bool // HEADER frame for trailers was seen gotTrailerHeader bool // HEADER frame for trailers was seen
wroteHeaders bool // whether we wrote headers (not status 100) wroteHeaders bool // whether we wrote headers (not status 100)
readDeadline *time.Timer // nil if unused
writeDeadline *time.Timer // nil if unused writeDeadline *time.Timer // nil if unused
closeErr error // set before cw is closed
trailer http.Header // accumulated trailers trailer http.Header // accumulated trailers
reqTrailer http.Header // handler's Request.Trailer reqTrailer http.Header // handler's Request.Trailer
@ -869,7 +871,9 @@ func (sc *serverConn) serve() {
// Each connection starts with initialWindowSize inflow tokens. // Each connection starts with initialWindowSize inflow tokens.
// If a higher value is configured, we add more tokens. // If a higher value is configured, we add more tokens.
sc.sendWindowUpdate(nil) if diff := sc.srv.initialConnRecvWindowSize() - initialWindowSize; diff > 0 {
sc.sendWindowUpdate(nil, int(diff))
}
if err := sc.readPreface(); err != nil { if err := sc.readPreface(); err != nil {
sc.condlogf(err, "http2: server: error reading preface from client %v: %v", sc.conn.RemoteAddr(), err) sc.condlogf(err, "http2: server: error reading preface from client %v: %v", sc.conn.RemoteAddr(), err)
@ -946,6 +950,8 @@ func (sc *serverConn) serve() {
} }
case *startPushRequest: case *startPushRequest:
sc.startPush(v) sc.startPush(v)
case func(*serverConn):
v(sc)
default: default:
panic(fmt.Sprintf("unexpected type %T", v)) panic(fmt.Sprintf("unexpected type %T", v))
} }
@ -1459,6 +1465,21 @@ func (sc *serverConn) processFrame(f Frame) error {
sc.sawFirstSettings = true sc.sawFirstSettings = true
} }
// Discard frames for streams initiated after the identified last
// stream sent in a GOAWAY, or all frames after sending an error.
// We still need to return connection-level flow control for DATA frames.
// RFC 9113 Section 6.8.
if sc.inGoAway && (sc.goAwayCode != ErrCodeNo || f.Header().StreamID > sc.maxClientStreamID) {
if f, ok := f.(*DataFrame); ok {
if sc.inflow.available() < int32(f.Length) {
return sc.countError("data_flow", streamError(f.Header().StreamID, ErrCodeFlowControl))
}
sc.sendWindowUpdate(nil, int(f.Length)) // conn-level
}
return nil
}
switch f := f.(type) { switch f := f.(type) {
case *SettingsFrame: case *SettingsFrame:
return sc.processSettings(f) return sc.processSettings(f)
@ -1501,9 +1522,6 @@ func (sc *serverConn) processPing(f *PingFrame) error {
// PROTOCOL_ERROR." // PROTOCOL_ERROR."
return sc.countError("ping_on_stream", ConnectionError(ErrCodeProtocol)) return sc.countError("ping_on_stream", ConnectionError(ErrCodeProtocol))
} }
if sc.inGoAway && sc.goAwayCode != ErrCodeNo {
return nil
}
sc.writeFrame(FrameWriteRequest{write: writePingAck{f}}) sc.writeFrame(FrameWriteRequest{write: writePingAck{f}})
return nil return nil
} }
@ -1565,6 +1583,9 @@ func (sc *serverConn) closeStream(st *stream, err error) {
panic(fmt.Sprintf("invariant; can't close stream in state %v", st.state)) panic(fmt.Sprintf("invariant; can't close stream in state %v", st.state))
} }
st.state = stateClosed st.state = stateClosed
if st.readDeadline != nil {
st.readDeadline.Stop()
}
if st.writeDeadline != nil { if st.writeDeadline != nil {
st.writeDeadline.Stop() st.writeDeadline.Stop()
} }
@ -1586,10 +1607,18 @@ func (sc *serverConn) closeStream(st *stream, err error) {
if p := st.body; p != nil { if p := st.body; p != nil {
// Return any buffered unread bytes worth of conn-level flow control. // Return any buffered unread bytes worth of conn-level flow control.
// See golang.org/issue/16481 // See golang.org/issue/16481
sc.sendWindowUpdate(nil) sc.sendWindowUpdate(nil, p.Len())
p.CloseWithError(err) p.CloseWithError(err)
} }
if e, ok := err.(StreamError); ok {
if e.Cause != nil {
err = e.Cause
} else {
err = errStreamClosed
}
}
st.closeErr = err
st.cw.Close() // signals Handler's CloseNotifier, unblocks writes, etc st.cw.Close() // signals Handler's CloseNotifier, unblocks writes, etc
sc.writeSched.CloseStream(st.id) sc.writeSched.CloseStream(st.id)
} }
@ -1686,16 +1715,6 @@ func (sc *serverConn) processSettingInitialWindowSize(val uint32) error {
func (sc *serverConn) processData(f *DataFrame) error { func (sc *serverConn) processData(f *DataFrame) error {
sc.serveG.check() sc.serveG.check()
id := f.Header().StreamID id := f.Header().StreamID
if sc.inGoAway && (sc.goAwayCode != ErrCodeNo || id > sc.maxClientStreamID) {
// Discard all DATA frames if the GOAWAY is due to an
// error, or:
//
// Section 6.8: After sending a GOAWAY frame, the sender
// can discard frames for streams initiated by the
// receiver with identifiers higher than the identified
// last stream.
return nil
}
data := f.Data() data := f.Data()
state, st := sc.state(id) state, st := sc.state(id)
@ -1734,7 +1753,7 @@ func (sc *serverConn) processData(f *DataFrame) error {
// sendWindowUpdate, which also schedules sending the // sendWindowUpdate, which also schedules sending the
// frames. // frames.
sc.inflow.take(int32(f.Length)) sc.inflow.take(int32(f.Length))
sc.sendWindowUpdate(nil) // conn-level sc.sendWindowUpdate(nil, int(f.Length)) // conn-level
if st != nil && st.resetQueued { if st != nil && st.resetQueued {
// Already have a stream error in flight. Don't send another. // Already have a stream error in flight. Don't send another.
@ -1752,7 +1771,7 @@ func (sc *serverConn) processData(f *DataFrame) error {
return sc.countError("data_flow", streamError(id, ErrCodeFlowControl)) return sc.countError("data_flow", streamError(id, ErrCodeFlowControl))
} }
sc.inflow.take(int32(f.Length)) sc.inflow.take(int32(f.Length))
sc.sendWindowUpdate(nil) // conn-level sc.sendWindowUpdate(nil, int(f.Length)) // conn-level
st.body.CloseWithError(fmt.Errorf("sender tried to send more than declared Content-Length of %d bytes", st.declBodyBytes)) st.body.CloseWithError(fmt.Errorf("sender tried to send more than declared Content-Length of %d bytes", st.declBodyBytes))
// RFC 7540, sec 8.1.2.6: A request or response is also malformed if the // RFC 7540, sec 8.1.2.6: A request or response is also malformed if the
@ -1770,7 +1789,7 @@ func (sc *serverConn) processData(f *DataFrame) error {
if len(data) > 0 { if len(data) > 0 {
wrote, err := st.body.Write(data) wrote, err := st.body.Write(data)
if err != nil { if err != nil {
sc.sendWindowUpdate32(nil, int32(f.Length)-int32(wrote)) sc.sendWindowUpdate(nil, int(f.Length)-wrote)
return sc.countError("body_write_err", streamError(id, ErrCodeStreamClosed)) return sc.countError("body_write_err", streamError(id, ErrCodeStreamClosed))
} }
if wrote != len(data) { if wrote != len(data) {
@ -1838,19 +1857,27 @@ func (st *stream) copyTrailersToHandlerRequest() {
} }
} }
// onReadTimeout is run on its own goroutine (from time.AfterFunc)
// when the stream's ReadTimeout has fired.
func (st *stream) onReadTimeout() {
// Wrap the ErrDeadlineExceeded to avoid callers depending on us
// returning the bare error.
st.body.CloseWithError(fmt.Errorf("%w", os.ErrDeadlineExceeded))
}
// onWriteTimeout is run on its own goroutine (from time.AfterFunc) // onWriteTimeout is run on its own goroutine (from time.AfterFunc)
// when the stream's WriteTimeout has fired. // when the stream's WriteTimeout has fired.
func (st *stream) onWriteTimeout() { func (st *stream) onWriteTimeout() {
st.sc.writeFrameFromHandler(FrameWriteRequest{write: streamError(st.id, ErrCodeInternal)}) st.sc.writeFrameFromHandler(FrameWriteRequest{write: StreamError{
StreamID: st.id,
Code: ErrCodeInternal,
Cause: os.ErrDeadlineExceeded,
}})
} }
func (sc *serverConn) processHeaders(f *MetaHeadersFrame) error { func (sc *serverConn) processHeaders(f *MetaHeadersFrame) error {
sc.serveG.check() sc.serveG.check()
id := f.StreamID id := f.StreamID
if sc.inGoAway {
// Ignore.
return nil
}
// http://tools.ietf.org/html/rfc7540#section-5.1.1 // http://tools.ietf.org/html/rfc7540#section-5.1.1
// Streams initiated by a client MUST use odd-numbered stream // Streams initiated by a client MUST use odd-numbered stream
// identifiers. [...] An endpoint that receives an unexpected // identifiers. [...] An endpoint that receives an unexpected
@ -1953,6 +1980,9 @@ func (sc *serverConn) processHeaders(f *MetaHeadersFrame) error {
// (in Go 1.8), though. That's a more sane option anyway. // (in Go 1.8), though. That's a more sane option anyway.
if sc.hs.ReadTimeout != 0 { if sc.hs.ReadTimeout != 0 {
sc.conn.SetReadDeadline(time.Time{}) sc.conn.SetReadDeadline(time.Time{})
if st.body != nil {
st.readDeadline = time.AfterFunc(sc.hs.ReadTimeout, st.onReadTimeout)
}
} }
go sc.runHandler(rw, req, handler) go sc.runHandler(rw, req, handler)
@ -2021,9 +2051,6 @@ func (sc *serverConn) checkPriority(streamID uint32, p PriorityParam) error {
} }
func (sc *serverConn) processPriority(f *PriorityFrame) error { func (sc *serverConn) processPriority(f *PriorityFrame) error {
if sc.inGoAway {
return nil
}
if err := sc.checkPriority(f.StreamID, f.PriorityParam); err != nil { if err := sc.checkPriority(f.StreamID, f.PriorityParam); err != nil {
return err return err
} }
@ -2322,39 +2349,24 @@ func (sc *serverConn) noteBodyReadFromHandler(st *stream, n int, err error) {
func (sc *serverConn) noteBodyRead(st *stream, n int) { func (sc *serverConn) noteBodyRead(st *stream, n int) {
sc.serveG.check() sc.serveG.check()
sc.sendWindowUpdate(nil) // conn-level sc.sendWindowUpdate(nil, n) // conn-level
if st.state != stateHalfClosedRemote && st.state != stateClosed { if st.state != stateHalfClosedRemote && st.state != stateClosed {
// Don't send this WINDOW_UPDATE if the stream is closed // Don't send this WINDOW_UPDATE if the stream is closed
// remotely. // remotely.
sc.sendWindowUpdate(st) sc.sendWindowUpdate(st, n)
} }
} }
// st may be nil for conn-level // st may be nil for conn-level
func (sc *serverConn) sendWindowUpdate(st *stream) { func (sc *serverConn) sendWindowUpdate(st *stream, n int) {
sc.serveG.check() sc.serveG.check()
var n int32
if st == nil {
if avail, windowSize := sc.inflow.available(), sc.srv.initialConnRecvWindowSize(); avail > windowSize/2 {
return
} else {
n = windowSize - avail
}
} else {
if avail, windowSize := st.inflow.available(), sc.srv.initialStreamRecvWindowSize(); avail > windowSize/2 {
return
} else {
n = windowSize - avail
}
}
// "The legal range for the increment to the flow control // "The legal range for the increment to the flow control
// window is 1 to 2^31-1 (2,147,483,647) octets." // window is 1 to 2^31-1 (2,147,483,647) octets."
// A Go Read call on 64-bit machines could in theory read // A Go Read call on 64-bit machines could in theory read
// a larger Read than this. Very unlikely, but we handle it here // a larger Read than this. Very unlikely, but we handle it here
// rather than elsewhere for now. // rather than elsewhere for now.
const maxUint31 = 1<<31 - 1 const maxUint31 = 1<<31 - 1
for n >= maxUint31 { for n > maxUint31 {
sc.sendWindowUpdate32(st, maxUint31) sc.sendWindowUpdate32(st, maxUint31)
n -= maxUint31 n -= maxUint31
} }
@ -2474,7 +2486,15 @@ type responseWriterState struct {
type chunkWriter struct{ rws *responseWriterState } type chunkWriter struct{ rws *responseWriterState }
func (cw chunkWriter) Write(p []byte) (n int, err error) { return cw.rws.writeChunk(p) } func (cw chunkWriter) Write(p []byte) (n int, err error) {
n, err = cw.rws.writeChunk(p)
if err == errStreamClosed {
// If writing failed because the stream has been closed,
// return the reason it was closed.
err = cw.rws.stream.closeErr
}
return n, err
}
func (rws *responseWriterState) hasTrailers() bool { return len(rws.trailers) > 0 } func (rws *responseWriterState) hasTrailers() bool { return len(rws.trailers) > 0 }
@ -2668,23 +2688,85 @@ func (rws *responseWriterState) promoteUndeclaredTrailers() {
} }
} }
func (w *responseWriter) SetReadDeadline(deadline time.Time) error {
st := w.rws.stream
if !deadline.IsZero() && deadline.Before(time.Now()) {
// If we're setting a deadline in the past, reset the stream immediately
// so writes after SetWriteDeadline returns will fail.
st.onReadTimeout()
return nil
}
w.rws.conn.sendServeMsg(func(sc *serverConn) {
if st.readDeadline != nil {
if !st.readDeadline.Stop() {
// Deadline already exceeded, or stream has been closed.
return
}
}
if deadline.IsZero() {
st.readDeadline = nil
} else if st.readDeadline == nil {
st.readDeadline = time.AfterFunc(deadline.Sub(time.Now()), st.onReadTimeout)
} else {
st.readDeadline.Reset(deadline.Sub(time.Now()))
}
})
return nil
}
func (w *responseWriter) SetWriteDeadline(deadline time.Time) error {
st := w.rws.stream
if !deadline.IsZero() && deadline.Before(time.Now()) {
// If we're setting a deadline in the past, reset the stream immediately
// so writes after SetWriteDeadline returns will fail.
st.onWriteTimeout()
return nil
}
w.rws.conn.sendServeMsg(func(sc *serverConn) {
if st.writeDeadline != nil {
if !st.writeDeadline.Stop() {
// Deadline already exceeded, or stream has been closed.
return
}
}
if deadline.IsZero() {
st.writeDeadline = nil
} else if st.writeDeadline == nil {
st.writeDeadline = time.AfterFunc(deadline.Sub(time.Now()), st.onWriteTimeout)
} else {
st.writeDeadline.Reset(deadline.Sub(time.Now()))
}
})
return nil
}
func (w *responseWriter) Flush() { func (w *responseWriter) Flush() {
w.FlushError()
}
func (w *responseWriter) FlushError() error {
rws := w.rws rws := w.rws
if rws == nil { if rws == nil {
panic("Header called after Handler finished") panic("Header called after Handler finished")
} }
var err error
if rws.bw.Buffered() > 0 { if rws.bw.Buffered() > 0 {
if err := rws.bw.Flush(); err != nil { err = rws.bw.Flush()
// Ignore the error. The frame writer already knows.
return
}
} else { } else {
// The bufio.Writer won't call chunkWriter.Write // The bufio.Writer won't call chunkWriter.Write
// (writeChunk with zero bytes, so we have to do it // (writeChunk with zero bytes, so we have to do it
// ourselves to force the HTTP response header and/or // ourselves to force the HTTP response header and/or
// final DATA frame (with END_STREAM) to be sent. // final DATA frame (with END_STREAM) to be sent.
rws.writeChunk(nil) _, err = chunkWriter{rws}.Write(nil)
if err == nil {
select {
case <-rws.stream.cw:
err = rws.stream.closeErr
default:
}
}
} }
return err
} }
func (w *responseWriter) CloseNotify() <-chan bool { func (w *responseWriter) CloseNotify() <-chan bool {

View file

@ -16,6 +16,7 @@ import (
"errors" "errors"
"fmt" "fmt"
"io" "io"
"io/fs"
"log" "log"
"math" "math"
mathrand "math/rand" mathrand "math/rand"
@ -501,6 +502,15 @@ func authorityAddr(scheme string, authority string) (addr string) {
return net.JoinHostPort(host, port) return net.JoinHostPort(host, port)
} }
var retryBackoffHook func(time.Duration) *time.Timer
func backoffNewTimer(d time.Duration) *time.Timer {
if retryBackoffHook != nil {
return retryBackoffHook(d)
}
return time.NewTimer(d)
}
// RoundTripOpt is like RoundTrip, but takes options. // RoundTripOpt is like RoundTrip, but takes options.
func (t *Transport) RoundTripOpt(req *http.Request, opt RoundTripOpt) (*http.Response, error) { func (t *Transport) RoundTripOpt(req *http.Request, opt RoundTripOpt) (*http.Response, error) {
if !(req.URL.Scheme == "https" || (req.URL.Scheme == "http" && t.AllowHTTP)) { if !(req.URL.Scheme == "https" || (req.URL.Scheme == "http" && t.AllowHTTP)) {
@ -526,11 +536,14 @@ func (t *Transport) RoundTripOpt(req *http.Request, opt RoundTripOpt) (*http.Res
} }
backoff := float64(uint(1) << (uint(retry) - 1)) backoff := float64(uint(1) << (uint(retry) - 1))
backoff += backoff * (0.1 * mathrand.Float64()) backoff += backoff * (0.1 * mathrand.Float64())
d := time.Second * time.Duration(backoff)
timer := backoffNewTimer(d)
select { select {
case <-time.After(time.Second * time.Duration(backoff)): case <-timer.C:
t.vlogf("RoundTrip retrying after failure: %v", err) t.vlogf("RoundTrip retrying after failure: %v", err)
continue continue
case <-req.Context().Done(): case <-req.Context().Done():
timer.Stop()
err = req.Context().Err() err = req.Context().Err()
} }
} }
@ -1075,7 +1088,7 @@ var errRequestCanceled = errors.New("net/http: request canceled")
func commaSeparatedTrailers(req *http.Request) (string, error) { func commaSeparatedTrailers(req *http.Request) (string, error) {
keys := make([]string, 0, len(req.Trailer)) keys := make([]string, 0, len(req.Trailer))
for k := range req.Trailer { for k := range req.Trailer {
k = http.CanonicalHeaderKey(k) k = canonicalHeader(k)
switch k { switch k {
case "Transfer-Encoding", "Trailer", "Content-Length": case "Transfer-Encoding", "Trailer", "Content-Length":
return "", fmt.Errorf("invalid Trailer key %q", k) return "", fmt.Errorf("invalid Trailer key %q", k)
@ -1612,7 +1625,7 @@ func (cs *clientStream) writeRequestBody(req *http.Request) (err error) {
var sawEOF bool var sawEOF bool
for !sawEOF { for !sawEOF {
n, err := body.Read(buf[:len(buf)]) n, err := body.Read(buf)
if hasContentLen { if hasContentLen {
remainLen -= int64(n) remainLen -= int64(n)
if remainLen == 0 && err == nil { if remainLen == 0 && err == nil {
@ -1915,7 +1928,7 @@ func (cc *ClientConn) encodeHeaders(req *http.Request, addGzipHeader bool, trail
// Header list size is ok. Write the headers. // Header list size is ok. Write the headers.
enumerateHeaders(func(name, value string) { enumerateHeaders(func(name, value string) {
name, ascii := asciiToLower(name) name, ascii := lowerHeader(name)
if !ascii { if !ascii {
// Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header // Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header
// field names have to be ASCII characters (just as in HTTP/1.x). // field names have to be ASCII characters (just as in HTTP/1.x).
@ -1968,7 +1981,7 @@ func (cc *ClientConn) encodeTrailers(trailer http.Header) ([]byte, error) {
} }
for k, vv := range trailer { for k, vv := range trailer {
lowKey, ascii := asciiToLower(k) lowKey, ascii := lowerHeader(k)
if !ascii { if !ascii {
// Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header // Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header
// field names have to be ASCII characters (just as in HTTP/1.x). // field names have to be ASCII characters (just as in HTTP/1.x).
@ -2301,7 +2314,7 @@ func (rl *clientConnReadLoop) handleResponse(cs *clientStream, f *MetaHeadersFra
Status: status + " " + http.StatusText(statusCode), Status: status + " " + http.StatusText(statusCode),
} }
for _, hf := range regularFields { for _, hf := range regularFields {
key := http.CanonicalHeaderKey(hf.Name) key := canonicalHeader(hf.Name)
if key == "Trailer" { if key == "Trailer" {
t := res.Trailer t := res.Trailer
if t == nil { if t == nil {
@ -2309,7 +2322,7 @@ func (rl *clientConnReadLoop) handleResponse(cs *clientStream, f *MetaHeadersFra
res.Trailer = t res.Trailer = t
} }
foreachHeaderElement(hf.Value, func(v string) { foreachHeaderElement(hf.Value, func(v string) {
t[http.CanonicalHeaderKey(v)] = nil t[canonicalHeader(v)] = nil
}) })
} else { } else {
vv := header[key] vv := header[key]
@ -2414,7 +2427,7 @@ func (rl *clientConnReadLoop) processTrailers(cs *clientStream, f *MetaHeadersFr
trailer := make(http.Header) trailer := make(http.Header)
for _, hf := range f.RegularFields() { for _, hf := range f.RegularFields() {
key := http.CanonicalHeaderKey(hf.Name) key := canonicalHeader(hf.Name)
trailer[key] = append(trailer[key], hf.Value) trailer[key] = append(trailer[key], hf.Value)
} }
cs.trailer = trailer cs.trailer = trailer
@ -2985,7 +2998,11 @@ func (gz *gzipReader) Read(p []byte) (n int, err error) {
} }
func (gz *gzipReader) Close() error { func (gz *gzipReader) Close() error {
return gz.body.Close() if err := gz.body.Close(); err != nil {
return err
}
gz.zerr = fs.ErrClosed
return nil
} }
type errorReader struct{ err error } type errorReader struct{ err error }

View file

@ -52,6 +52,20 @@ func ParseSocketControlMessage(b []byte) ([]SocketControlMessage, error) {
return msgs, nil return msgs, nil
} }
// ParseOneSocketControlMessage parses a single socket control message from b, returning the message header,
// message data (a slice of b), and the remainder of b after that single message.
// When there are no remaining messages, len(remainder) == 0.
func ParseOneSocketControlMessage(b []byte) (hdr Cmsghdr, data []byte, remainder []byte, err error) {
h, dbuf, err := socketControlMessageHeaderAndData(b)
if err != nil {
return Cmsghdr{}, nil, nil, err
}
if i := cmsgAlignOf(int(h.Len)); i < len(b) {
remainder = b[i:]
}
return *h, dbuf, remainder, nil
}
func socketControlMessageHeaderAndData(b []byte) (*Cmsghdr, []byte, error) { func socketControlMessageHeaderAndData(b []byte) (*Cmsghdr, []byte, error) {
h := (*Cmsghdr)(unsafe.Pointer(&b[0])) h := (*Cmsghdr)(unsafe.Pointer(&b[0]))
if h.Len < SizeofCmsghdr || uint64(h.Len) > uint64(len(b)) { if h.Len < SizeofCmsghdr || uint64(h.Len) > uint64(len(b)) {

View file

@ -1554,6 +1554,7 @@ func sendmsgN(fd int, iov []Iovec, oob []byte, ptr unsafe.Pointer, salen _Sockle
var iova [1]Iovec var iova [1]Iovec
iova[0].Base = &dummy iova[0].Base = &dummy
iova[0].SetLen(1) iova[0].SetLen(1)
iov = iova[:]
} }
} }
msg.Control = &oob[0] msg.Control = &oob[0]

View file

@ -79,6 +79,9 @@ type Error struct {
Header http.Header Header http.Header
Errors []ErrorItem Errors []ErrorItem
// err is typically a wrapped apierror.APIError, see
// google-api-go-client/internal/gensupport/error.go.
err error
} }
// ErrorItem is a detailed error code & message from the Google API frontend. // ErrorItem is a detailed error code & message from the Google API frontend.
@ -122,6 +125,15 @@ func (e *Error) Error() string {
return buf.String() return buf.String()
} }
// Wrap allows an existing Error to wrap another error. See also [Error.Unwrap].
func (e *Error) Wrap(err error) {
e.err = err
}
func (e *Error) Unwrap() error {
return e.err
}
type errorReply struct { type errorReply struct {
Error *Error `json:"error"` Error *Error `json:"error"`
} }

View file

@ -598,17 +598,17 @@ func (c *ProjectsServiceAccountsGenerateAccessTokenCall) Do(opts ...googleapi.Ca
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &GenerateAccessTokenResponse{ ret := &GenerateAccessTokenResponse{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -745,17 +745,17 @@ func (c *ProjectsServiceAccountsGenerateIdTokenCall) Do(opts ...googleapi.CallOp
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &GenerateIdTokenResponse{ ret := &GenerateIdTokenResponse{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -892,17 +892,17 @@ func (c *ProjectsServiceAccountsSignBlobCall) Do(opts ...googleapi.CallOption) (
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &SignBlobResponse{ ret := &SignBlobResponse{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -1039,17 +1039,17 @@ func (c *ProjectsServiceAccountsSignJwtCall) Do(opts ...googleapi.CallOption) (*
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &SignJwtResponse{ ret := &SignJwtResponse{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{

View file

@ -0,0 +1,24 @@
// Copyright 2022 Google LLC. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package gensupport
import (
"errors"
"github.com/googleapis/gax-go/v2/apierror"
"google.golang.org/api/googleapi"
)
// WrapError creates an [apierror.APIError] from err, wraps it in err, and
// returns err. If err is not a [googleapi.Error] (or a
// [google.golang.org/grpc/status.Status]), it returns err without modification.
func WrapError(err error) error {
var herr *googleapi.Error
apiError, ok := apierror.ParseError(err, false)
if ok && errors.As(err, &herr) {
herr.Wrap(apiError)
}
return err
}

View file

@ -5,4 +5,4 @@
package internal package internal
// Version is the current tagged release of the library. // Version is the current tagged release of the library.
const Version = "0.102.0" const Version = "0.103.0"

View file

@ -2560,7 +2560,7 @@ func (c *BucketAccessControlsDeleteCall) Do(opts ...googleapi.CallOption) error
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -2708,17 +2708,17 @@ func (c *BucketAccessControlsGetCall) Do(opts ...googleapi.CallOption) (*BucketA
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &BucketAccessControl{ ret := &BucketAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -2865,17 +2865,17 @@ func (c *BucketAccessControlsInsertCall) Do(opts ...googleapi.CallOption) (*Buck
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &BucketAccessControl{ ret := &BucketAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -3025,17 +3025,17 @@ func (c *BucketAccessControlsListCall) Do(opts ...googleapi.CallOption) (*Bucket
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &BucketAccessControls{ ret := &BucketAccessControls{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -3181,17 +3181,17 @@ func (c *BucketAccessControlsPatchCall) Do(opts ...googleapi.CallOption) (*Bucke
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &BucketAccessControl{ ret := &BucketAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -3347,17 +3347,17 @@ func (c *BucketAccessControlsUpdateCall) Do(opts ...googleapi.CallOption) (*Buck
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &BucketAccessControl{ ret := &BucketAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -3511,7 +3511,7 @@ func (c *BucketsDeleteCall) Do(opts ...googleapi.CallOption) error {
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -3688,17 +3688,17 @@ func (c *BucketsGetCall) Do(opts ...googleapi.CallOption) (*Bucket, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Bucket{ ret := &Bucket{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -3883,17 +3883,17 @@ func (c *BucketsGetIamPolicyCall) Do(opts ...googleapi.CallOption) (*Policy, err
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Policy{ ret := &Policy{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -4107,17 +4107,17 @@ func (c *BucketsInsertCall) Do(opts ...googleapi.CallOption) (*Bucket, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Bucket{ ret := &Bucket{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -4352,17 +4352,17 @@ func (c *BucketsListCall) Do(opts ...googleapi.CallOption) (*Buckets, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Buckets{ ret := &Buckets{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -4553,17 +4553,17 @@ func (c *BucketsLockRetentionPolicyCall) Do(opts ...googleapi.CallOption) (*Buck
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Bucket{ ret := &Bucket{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -4801,17 +4801,17 @@ func (c *BucketsPatchCall) Do(opts ...googleapi.CallOption) (*Bucket, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Bucket{ ret := &Bucket{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -5019,17 +5019,17 @@ func (c *BucketsSetIamPolicyCall) Do(opts ...googleapi.CallOption) (*Policy, err
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Policy{ ret := &Policy{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -5182,17 +5182,17 @@ func (c *BucketsTestIamPermissionsCall) Do(opts ...googleapi.CallOption) (*TestI
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &TestIamPermissionsResponse{ ret := &TestIamPermissionsResponse{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -5432,17 +5432,17 @@ func (c *BucketsUpdateCall) Do(opts ...googleapi.CallOption) (*Bucket, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Bucket{ ret := &Bucket{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -5631,7 +5631,7 @@ func (c *ChannelsStopCall) Do(opts ...googleapi.CallOption) error {
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -5744,7 +5744,7 @@ func (c *DefaultObjectAccessControlsDeleteCall) Do(opts ...googleapi.CallOption)
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -5892,17 +5892,17 @@ func (c *DefaultObjectAccessControlsGetCall) Do(opts ...googleapi.CallOption) (*
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -6050,17 +6050,17 @@ func (c *DefaultObjectAccessControlsInsertCall) Do(opts ...googleapi.CallOption)
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -6227,17 +6227,17 @@ func (c *DefaultObjectAccessControlsListCall) Do(opts ...googleapi.CallOption) (
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControls{ ret := &ObjectAccessControls{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -6395,17 +6395,17 @@ func (c *DefaultObjectAccessControlsPatchCall) Do(opts ...googleapi.CallOption)
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -6561,17 +6561,17 @@ func (c *DefaultObjectAccessControlsUpdateCall) Do(opts ...googleapi.CallOption)
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -6713,7 +6713,7 @@ func (c *NotificationsDeleteCall) Do(opts ...googleapi.CallOption) error {
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -6859,17 +6859,17 @@ func (c *NotificationsGetCall) Do(opts ...googleapi.CallOption) (*Notification,
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Notification{ ret := &Notification{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -7019,17 +7019,17 @@ func (c *NotificationsInsertCall) Do(opts ...googleapi.CallOption) (*Notificatio
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Notification{ ret := &Notification{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -7181,17 +7181,17 @@ func (c *NotificationsListCall) Do(opts ...googleapi.CallOption) (*Notifications
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Notifications{ ret := &Notifications{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -7342,7 +7342,7 @@ func (c *ObjectAccessControlsDeleteCall) Do(opts ...googleapi.CallOption) error
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -7516,17 +7516,17 @@ func (c *ObjectAccessControlsGetCall) Do(opts ...googleapi.CallOption) (*ObjectA
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -7699,17 +7699,17 @@ func (c *ObjectAccessControlsInsertCall) Do(opts ...googleapi.CallOption) (*Obje
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -7885,17 +7885,17 @@ func (c *ObjectAccessControlsListCall) Do(opts ...googleapi.CallOption) (*Object
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControls{ ret := &ObjectAccessControls{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -8067,17 +8067,17 @@ func (c *ObjectAccessControlsPatchCall) Do(opts ...googleapi.CallOption) (*Objec
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -8259,17 +8259,17 @@ func (c *ObjectAccessControlsUpdateCall) Do(opts ...googleapi.CallOption) (*Obje
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ObjectAccessControl{ ret := &ObjectAccessControl{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -8500,17 +8500,17 @@ func (c *ObjectsComposeCall) Do(opts ...googleapi.CallOption) (*Object, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Object{ ret := &Object{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -8858,17 +8858,17 @@ func (c *ObjectsCopyCall) Do(opts ...googleapi.CallOption) (*Object, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Object{ ret := &Object{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -9165,7 +9165,7 @@ func (c *ObjectsDeleteCall) Do(opts ...googleapi.CallOption) error {
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -9395,7 +9395,7 @@ func (c *ObjectsGetCall) Download(opts ...googleapi.CallOption) (*http.Response,
} }
if err := googleapi.CheckMediaResponse(res); err != nil { if err := googleapi.CheckMediaResponse(res); err != nil {
res.Body.Close() res.Body.Close()
return nil, err return nil, gensupport.WrapError(err)
} }
return res, nil return res, nil
} }
@ -9414,17 +9414,17 @@ func (c *ObjectsGetCall) Do(opts ...googleapi.CallOption) (*Object, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Object{ ret := &Object{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -9639,17 +9639,17 @@ func (c *ObjectsGetIamPolicyCall) Do(opts ...googleapi.CallOption) (*Policy, err
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Policy{ ret := &Policy{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -10001,17 +10001,17 @@ func (c *ObjectsInsertCall) Do(opts ...googleapi.CallOption) (*Object, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
rx := c.mediaInfo_.ResumableUpload(res.Header.Get("Location")) rx := c.mediaInfo_.ResumableUpload(res.Header.Get("Location"))
if rx != nil { if rx != nil {
@ -10028,7 +10028,7 @@ func (c *ObjectsInsertCall) Do(opts ...googleapi.CallOption) (*Object, error) {
} }
defer res.Body.Close() defer res.Body.Close()
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
} }
ret := &Object{ ret := &Object{
@ -10352,17 +10352,17 @@ func (c *ObjectsListCall) Do(opts ...googleapi.CallOption) (*Objects, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Objects{ ret := &Objects{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -10674,17 +10674,17 @@ func (c *ObjectsPatchCall) Do(opts ...googleapi.CallOption) (*Object, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Object{ ret := &Object{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -11081,17 +11081,17 @@ func (c *ObjectsRewriteCall) Do(opts ...googleapi.CallOption) (*RewriteResponse,
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &RewriteResponse{ ret := &RewriteResponse{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -11373,17 +11373,17 @@ func (c *ObjectsSetIamPolicyCall) Do(opts ...googleapi.CallOption) (*Policy, err
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Policy{ ret := &Policy{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -11563,17 +11563,17 @@ func (c *ObjectsTestIamPermissionsCall) Do(opts ...googleapi.CallOption) (*TestI
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &TestIamPermissionsResponse{ ret := &TestIamPermissionsResponse{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -11828,17 +11828,17 @@ func (c *ObjectsUpdateCall) Do(opts ...googleapi.CallOption) (*Object, error) {
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Object{ ret := &Object{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -12135,17 +12135,17 @@ func (c *ObjectsWatchAllCall) Do(opts ...googleapi.CallOption) (*Channel, error)
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &Channel{ ret := &Channel{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -12344,17 +12344,17 @@ func (c *ProjectsHmacKeysCreateCall) Do(opts ...googleapi.CallOption) (*HmacKey,
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &HmacKey{ ret := &HmacKey{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -12493,7 +12493,7 @@ func (c *ProjectsHmacKeysDeleteCall) Do(opts ...googleapi.CallOption) error {
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return err return gensupport.WrapError(err)
} }
return nil return nil
// { // {
@ -12640,17 +12640,17 @@ func (c *ProjectsHmacKeysGetCall) Do(opts ...googleapi.CallOption) (*HmacKeyMeta
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &HmacKeyMetadata{ ret := &HmacKeyMetadata{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -12841,17 +12841,17 @@ func (c *ProjectsHmacKeysListCall) Do(opts ...googleapi.CallOption) (*HmacKeysMe
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &HmacKeysMetadata{ ret := &HmacKeysMetadata{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -13043,17 +13043,17 @@ func (c *ProjectsHmacKeysUpdateCall) Do(opts ...googleapi.CallOption) (*HmacKeyM
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &HmacKeyMetadata{ ret := &HmacKeyMetadata{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{
@ -13211,17 +13211,17 @@ func (c *ProjectsServiceAccountGetCall) Do(opts ...googleapi.CallOption) (*Servi
if res.Body != nil { if res.Body != nil {
res.Body.Close() res.Body.Close()
} }
return nil, &googleapi.Error{ return nil, gensupport.WrapError(&googleapi.Error{
Code: res.StatusCode, Code: res.StatusCode,
Header: res.Header, Header: res.Header,
} })
} }
if err != nil { if err != nil {
return nil, err return nil, err
} }
defer googleapi.CloseBody(res) defer googleapi.CloseBody(res)
if err := googleapi.CheckResponse(res); err != nil { if err := googleapi.CheckResponse(res); err != nil {
return nil, err return nil, gensupport.WrapError(err)
} }
ret := &ServiceAccount{ ret := &ServiceAccount{
ServerResponse: googleapi.ServerResponse{ ServerResponse: googleapi.ServerResponse{

View file

@ -12,7 +12,6 @@ import (
"net" "net"
"syscall" "syscall"
"golang.org/x/sys/unix"
"google.golang.org/grpc" "google.golang.org/grpc"
) )
@ -20,6 +19,9 @@ const (
// defaultTCPUserTimeout is the default TCP_USER_TIMEOUT socket option. By // defaultTCPUserTimeout is the default TCP_USER_TIMEOUT socket option. By
// default is 20 seconds. // default is 20 seconds.
tcpUserTimeoutMilliseconds = 20000 tcpUserTimeoutMilliseconds = 20000
// Copied from golang.org/x/sys/unix.TCP_USER_TIMEOUT.
tcpUserTimeoutOp = 0x12
) )
func init() { func init() {
@ -33,7 +35,7 @@ func dialTCPUserTimeout(ctx context.Context, addr string) (net.Conn, error) {
var syscallErr error var syscallErr error
controlErr := c.Control(func(fd uintptr) { controlErr := c.Control(func(fd uintptr) {
syscallErr = syscall.SetsockoptInt( syscallErr = syscall.SetsockoptInt(
int(fd), syscall.IPPROTO_TCP, unix.TCP_USER_TIMEOUT, tcpUserTimeoutMilliseconds) int(fd), syscall.IPPROTO_TCP, tcpUserTimeoutOp, tcpUserTimeoutMilliseconds)
}) })
if syscallErr != nil { if syscallErr != nil {
return syscallErr return syscallErr

22
vendor/modules.txt vendored
View file

@ -1,4 +1,4 @@
# cloud.google.com/go v0.105.0 # cloud.google.com/go v0.106.0
## explicit; go 1.19 ## explicit; go 1.19
cloud.google.com/go/internal cloud.google.com/go/internal
cloud.google.com/go/internal/optional cloud.google.com/go/internal/optional
@ -13,8 +13,8 @@ cloud.google.com/go/compute/metadata
# cloud.google.com/go/iam v0.7.0 # cloud.google.com/go/iam v0.7.0
## explicit; go 1.19 ## explicit; go 1.19
cloud.google.com/go/iam cloud.google.com/go/iam
# cloud.google.com/go/storage v1.27.0 # cloud.google.com/go/storage v1.28.0
## explicit; go 1.17 ## explicit; go 1.19
cloud.google.com/go/storage cloud.google.com/go/storage
cloud.google.com/go/storage/internal cloud.google.com/go/storage/internal
cloud.google.com/go/storage/internal/apiv2 cloud.google.com/go/storage/internal/apiv2
@ -37,7 +37,7 @@ github.com/Azure/azure-sdk-for-go/sdk/azcore/runtime
github.com/Azure/azure-sdk-for-go/sdk/azcore/streaming github.com/Azure/azure-sdk-for-go/sdk/azcore/streaming
github.com/Azure/azure-sdk-for-go/sdk/azcore/to github.com/Azure/azure-sdk-for-go/sdk/azcore/to
github.com/Azure/azure-sdk-for-go/sdk/azcore/tracing github.com/Azure/azure-sdk-for-go/sdk/azcore/tracing
# github.com/Azure/azure-sdk-for-go/sdk/internal v1.0.1 # github.com/Azure/azure-sdk-for-go/sdk/internal v1.1.1
## explicit; go 1.18 ## explicit; go 1.18
github.com/Azure/azure-sdk-for-go/sdk/internal/diag github.com/Azure/azure-sdk-for-go/sdk/internal/diag
github.com/Azure/azure-sdk-for-go/sdk/internal/errorinfo github.com/Azure/azure-sdk-for-go/sdk/internal/errorinfo
@ -293,7 +293,7 @@ github.com/oklog/ulid
# github.com/pkg/errors v0.9.1 # github.com/pkg/errors v0.9.1
## explicit ## explicit
github.com/pkg/errors github.com/pkg/errors
# github.com/prometheus/client_golang v1.13.1 # github.com/prometheus/client_golang v1.14.0
## explicit; go 1.17 ## explicit; go 1.17
github.com/prometheus/client_golang/prometheus github.com/prometheus/client_golang/prometheus
github.com/prometheus/client_golang/prometheus/internal github.com/prometheus/client_golang/prometheus/internal
@ -333,7 +333,7 @@ github.com/rivo/uniseg
# github.com/russross/blackfriday/v2 v2.1.0 # github.com/russross/blackfriday/v2 v2.1.0
## explicit ## explicit
github.com/russross/blackfriday/v2 github.com/russross/blackfriday/v2
# github.com/urfave/cli/v2 v2.23.4 # github.com/urfave/cli/v2 v2.23.5
## explicit; go 1.18 ## explicit; go 1.18
github.com/urfave/cli/v2 github.com/urfave/cli/v2
# github.com/valyala/bytebufferpool v1.0.0 # github.com/valyala/bytebufferpool v1.0.0
@ -385,7 +385,7 @@ go.opencensus.io/trace/tracestate
go.uber.org/atomic go.uber.org/atomic
# go.uber.org/goleak v1.1.11-0.20210813005559-691160354723 # go.uber.org/goleak v1.1.11-0.20210813005559-691160354723
## explicit; go 1.13 ## explicit; go 1.13
# golang.org/x/net v0.1.0 # golang.org/x/net v0.2.0
## explicit; go 1.17 ## explicit; go 1.17
golang.org/x/net/context golang.org/x/net/context
golang.org/x/net/context/ctxhttp golang.org/x/net/context/ctxhttp
@ -397,7 +397,7 @@ golang.org/x/net/internal/socks
golang.org/x/net/internal/timeseries golang.org/x/net/internal/timeseries
golang.org/x/net/proxy golang.org/x/net/proxy
golang.org/x/net/trace golang.org/x/net/trace
# golang.org/x/oauth2 v0.1.0 # golang.org/x/oauth2 v0.2.0
## explicit; go 1.17 ## explicit; go 1.17
golang.org/x/oauth2 golang.org/x/oauth2
golang.org/x/oauth2/authhandler golang.org/x/oauth2/authhandler
@ -410,7 +410,7 @@ golang.org/x/oauth2/jwt
# golang.org/x/sync v0.1.0 # golang.org/x/sync v0.1.0
## explicit ## explicit
golang.org/x/sync/errgroup golang.org/x/sync/errgroup
# golang.org/x/sys v0.1.0 # golang.org/x/sys v0.2.0
## explicit; go 1.17 ## explicit; go 1.17
golang.org/x/sys/internal/unsafeheader golang.org/x/sys/internal/unsafeheader
golang.org/x/sys/unix golang.org/x/sys/unix
@ -425,7 +425,7 @@ golang.org/x/text/unicode/norm
## explicit; go 1.17 ## explicit; go 1.17
golang.org/x/xerrors golang.org/x/xerrors
golang.org/x/xerrors/internal golang.org/x/xerrors/internal
# google.golang.org/api v0.102.0 # google.golang.org/api v0.103.0
## explicit; go 1.19 ## explicit; go 1.19
google.golang.org/api/googleapi google.golang.org/api/googleapi
google.golang.org/api/googleapi/transport google.golang.org/api/googleapi/transport
@ -458,7 +458,7 @@ google.golang.org/appengine/internal/socket
google.golang.org/appengine/internal/urlfetch google.golang.org/appengine/internal/urlfetch
google.golang.org/appengine/socket google.golang.org/appengine/socket
google.golang.org/appengine/urlfetch google.golang.org/appengine/urlfetch
# google.golang.org/genproto v0.0.0-20221027153422-115e99e71e1c # google.golang.org/genproto v0.0.0-20221109142239-94d6d90a7d66
## explicit; go 1.19 ## explicit; go 1.19
google.golang.org/genproto/googleapis/api/annotations google.golang.org/genproto/googleapis/api/annotations
google.golang.org/genproto/googleapis/iam/v1 google.golang.org/genproto/googleapis/iam/v1