diff --git a/cmd/admin-handlers.go b/cmd/admin-handlers.go
index 2decb52cb..d57f7cebc 100644
--- a/cmd/admin-handlers.go
+++ b/cmd/admin-handlers.go
@@ -376,8 +376,7 @@ func (a adminAPIHandlers) PerfInfoHandler(w http.ResponseWriter, r *http.Request
}
}
- storage := objectAPI.StorageInfo(ctx)
- if !(storage.Backend.Type == BackendFS || storage.Backend.Type == BackendErasure) {
+ if !globalIsDistXL {
writeErrorResponseJSON(ctx, w, errorCodes.ToAPIErr(ErrMethodNotAllowed), r.URL)
return
}
diff --git a/cmd/peer-rest-server.go b/cmd/peer-rest-server.go
index a35555dcc..5f437d281 100644
--- a/cmd/peer-rest-server.go
+++ b/cmd/peer-rest-server.go
@@ -921,8 +921,8 @@ func (s *peerRESTServer) IsValid(w http.ResponseWriter, r *http.Request) bool {
func registerPeerRESTHandlers(router *mux.Router) {
server := &peerRESTServer{}
subrouter := router.PathPrefix(peerRESTPath).Subrouter()
- subrouter.Methods(http.MethodPost).Path(SlashSeparator + peerRESTMethodNetReadPerfInfo).HandlerFunc(httpTraceHdrs(server.NetReadPerfInfoHandler))
- subrouter.Methods(http.MethodPost).Path(SlashSeparator + peerRESTMethodCollectNetPerfInfo).HandlerFunc(httpTraceHdrs(server.CollectNetPerfInfoHandler))
+ subrouter.Methods(http.MethodPost).Path(SlashSeparator + peerRESTMethodNetReadPerfInfo).HandlerFunc(httpTraceHdrs(server.NetReadPerfInfoHandler)).Queries(restQueries(peerRESTNetPerfSize)...)
+ subrouter.Methods(http.MethodPost).Path(SlashSeparator + peerRESTMethodCollectNetPerfInfo).HandlerFunc(httpTraceHdrs(server.CollectNetPerfInfoHandler)).Queries(restQueries(peerRESTNetPerfSize)...)
subrouter.Methods(http.MethodPost).Path(SlashSeparator + peerRESTMethodGetLocks).HandlerFunc(httpTraceHdrs(server.GetLocksHandler))
subrouter.Methods(http.MethodPost).Path(SlashSeparator + peerRESTMethodServerInfo).HandlerFunc(httpTraceHdrs(server.ServerInfoHandler))
subrouter.Methods(http.MethodPost).Path(SlashSeparator + peerRESTMethodCPULoadInfo).HandlerFunc(httpTraceHdrs(server.CPULoadInfoHandler))
diff --git a/pkg/madmin/README.md b/pkg/madmin/README.md
index 5b0dc9756..79879efa3 100644
--- a/pkg/madmin/README.md
+++ b/pkg/madmin/README.md
@@ -49,6 +49,7 @@ func main() {
| [`ServiceStop`](#ServiceStop) | [`ServerCPULoadInfo`](#ServerCPULoadInfo) | | [`SetConfig`](#SetConfig) | | [`SetUserPolicy`](#SetUserPolicy) | [`StartProfiling`](#StartProfiling) |
| | [`ServerMemUsageInfo`](#ServerMemUsageInfo) | | [`GetConfigKeys`](#GetConfigKeys) | | [`ListUsers`](#ListUsers) | [`DownloadProfilingData`](#DownloadProfilingData) |
| [`ServiceTrace`](#ServiceTrace) | [`ServerDrivesPerfInfo`](#ServerDrivesPerfInfo) | | [`SetConfigKeys`](#SetConfigKeys) | | [`AddCannedPolicy`](#AddCannedPolicy) | [`ServerUpdate`](#ServerUpdate) |
+| | [`NetPerfInfo`](#NetPerfInfo) | | | | | |
## 1. Constructor
@@ -257,7 +258,7 @@ Fetches CPU utilization for all cluster nodes.
| `cpu.Load.Avg` | _float64_ | The average utilization of the CPU measured in a 200ms interval |
| `cpu.Load.Min` | _float64_ | The minimum utilization of the CPU measured in a 200ms interval |
| `cpu.Load.Max` | _float64_ | The maximum utilization of the CPU measured in a 200ms interval |
-| `cpu.Load.Error` | _string_ | Error (if any) encountered while accesing the CPU info |
+| `cpu.Load.Error` | _string_ | Error (if any) encountered while accessing the CPU info |
### ServerMemUsageInfo() ([]ServerMemUsageInfo, error)
@@ -273,7 +274,18 @@ Fetches Mem utilization for all cluster nodes.
| Param | Type | Description |
|-------------------|----------|--------------------------------------------------------|
| `mem.Usage.Mem` | _uint64_ | The total number of bytes obtained from the OS |
-| `mem.Usage.Error` | _string_ | Error (if any) encountered while accesing the CPU info |
+| `mem.Usage.Error` | _string_ | Error (if any) encountered while accessing the CPU info |
+
+
+### NetPerfInfo(int size) (map[string][]NetPerfInfo, error)
+
+Fetches network performance of all cluster nodes using given sized payload. Returned value is a map containing each node indexed list of performance of other nodes.
+
+| Param | Type | Description |
+|------------|------------------|--------------------------------------------------------------------|
+| `Addr` | _string_ | Address of the server the following information is retrieved from. |
+| `Error` | _string_ | Errors (if any) encountered while reaching this node |
+| `ReadPerf` | _time.Duration_ | Network read performance of the server |
## 5. Heal operations
diff --git a/pkg/madmin/examples/net-perf-info.go b/pkg/madmin/examples/net-perf-info.go
new file mode 100644
index 000000000..85da2ffcd
--- /dev/null
+++ b/pkg/madmin/examples/net-perf-info.go
@@ -0,0 +1,44 @@
+// +build ignore
+
+/*
+ * MinIO Cloud Storage, (C) 2019 MinIO, Inc.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package main
+
+import (
+ "log"
+
+ "github.com/minio/minio/pkg/madmin"
+)
+
+func main() {
+ // Note: YOUR-ACCESSKEYID, YOUR-SECRETACCESSKEY and my-bucketname are
+ // dummy values, please replace them with original values.
+
+ // API requests are secure (HTTPS) if secure=true and insecure (HTTP) otherwise.
+ // New returns an MinIO Admin client object.
+ madmClnt, err := madmin.New("your-minio.example.com:9000", "YOUR-ACCESSKEYID", "YOUR-SECRETACCESSKEY", true)
+ if err != nil {
+ log.Fatalln(err)
+ }
+
+ st, err := madmClnt.NetPerfInfo(madmin.DefaultNetPerfSize)
+ if err != nil {
+ log.Fatalln(err)
+ }
+ log.Println(st)
+}
diff --git a/pkg/madmin/info-commands.go b/pkg/madmin/info-commands.go
index 43ec3b4f2..920fe6422 100644
--- a/pkg/madmin/info-commands.go
+++ b/pkg/madmin/info-commands.go
@@ -19,16 +19,24 @@ package madmin
import (
"encoding/json"
+ "errors"
"io/ioutil"
"net/http"
"net/url"
+ "strconv"
"time"
+ humanize "github.com/dustin/go-humanize"
"github.com/minio/minio/pkg/cpu"
"github.com/minio/minio/pkg/disk"
"github.com/minio/minio/pkg/mem"
)
+const (
+ // DefaultNetPerfSize - default payload size used for network performance.
+ DefaultNetPerfSize = 100 * humanize.MiByte
+)
+
// BackendType - represents different backend types.
type BackendType int
@@ -288,3 +296,52 @@ func (adm *AdminClient) ServerMemUsageInfo() ([]ServerMemUsageInfo, error) {
return info, nil
}
+
+// NetPerfInfo network performance information.
+type NetPerfInfo struct {
+ Addr string `json:"addr"`
+ ReadPerf time.Duration `json:"readPerf"`
+ Error string `json:"error,omitempty"`
+}
+
+// NetPerfInfo - Returns network performance information of all cluster nodes.
+func (adm *AdminClient) NetPerfInfo(size int) (map[string][]NetPerfInfo, error) {
+ v := url.Values{}
+ v.Set("perfType", "net")
+ if size > 0 {
+ v.Set("size", strconv.Itoa(size))
+ }
+ resp, err := adm.executeMethod("GET", requestData{
+ relPath: "/v1/performance",
+ queryValues: v,
+ })
+
+ defer closeResponse(resp)
+ if err != nil {
+ return nil, err
+ }
+
+ // Check response http status code
+ if resp.StatusCode == http.StatusMethodNotAllowed {
+ return nil, errors.New("NetPerfInfo is meant for multi-node MinIO deployments")
+ }
+
+ if resp.StatusCode != http.StatusOK {
+ return nil, httpRespToErrorResponse(resp)
+ }
+
+ // Unmarshal the server's json response
+ info := map[string][]NetPerfInfo{}
+
+ respBytes, err := ioutil.ReadAll(resp.Body)
+ if err != nil {
+ return nil, err
+ }
+
+ err = json.Unmarshal(respBytes, &info)
+ if err != nil {
+ return nil, err
+ }
+
+ return info, nil
+}