390 lines
12 KiB
Go
390 lines
12 KiB
Go
package mock
|
|
|
|
import (
|
|
"fmt"
|
|
"log"
|
|
"strconv"
|
|
"time"
|
|
|
|
jwt "github.com/dgrijalva/jwt-go"
|
|
"github.com/go-openapi/runtime/middleware"
|
|
"github.com/go-openapi/strfmt"
|
|
"github.com/influxdata/chronograf"
|
|
"github.com/influxdata/chronograf/models"
|
|
op "github.com/influxdata/chronograf/restapi/operations"
|
|
"golang.org/x/net/context"
|
|
)
|
|
|
|
type Handler struct {
|
|
Store chronograf.ExplorationStore
|
|
Srcs chronograf.SourcesStore
|
|
TimeSeries chronograf.TimeSeries
|
|
}
|
|
|
|
func NewHandler() Handler {
|
|
h := Handler{
|
|
Store: DefaultExplorationStore,
|
|
Srcs: DefaultSourcesStore,
|
|
TimeSeries: DefaultTimeSeries,
|
|
}
|
|
return h
|
|
}
|
|
|
|
func (m *Handler) AllRoutes(ctx context.Context, params op.GetParams) middleware.Responder {
|
|
routes := &models.Routes{
|
|
Sources: "/chronograf/v1/sources",
|
|
Layouts: "/chronograf/v1/layouts",
|
|
Users: "/chronograf/v1/users",
|
|
Mappings: "/chronograf/v1/mappings",
|
|
}
|
|
return op.NewGetOK().WithPayload(routes)
|
|
}
|
|
|
|
func (m *Handler) NewSource(ctx context.Context, params op.PostSourcesParams) middleware.Responder {
|
|
src := chronograf.Source{
|
|
Name: *params.Source.Name,
|
|
Type: params.Source.Type,
|
|
Username: params.Source.Username,
|
|
Password: params.Source.Password,
|
|
URL: []string{*params.Source.URL},
|
|
Default: params.Source.Default,
|
|
}
|
|
var err error
|
|
if src, err = m.Srcs.Add(ctx, src); err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: fmt.Sprintf("Error storing source %v: %v", params.Source, err)}
|
|
return op.NewPostSourcesDefault(500).WithPayload(errMsg)
|
|
}
|
|
mSrc := mrToModel(src)
|
|
return op.NewPostSourcesCreated().WithPayload(mSrc).WithLocation(mSrc.Links.Self)
|
|
}
|
|
|
|
func srcLinks(id int) *models.SourceLinks {
|
|
return &models.SourceLinks{
|
|
Self: fmt.Sprintf("/chronograf/v1/sources/%d", id),
|
|
Proxy: fmt.Sprintf("/chronograf/v1/sources/%d/proxy", id),
|
|
Users: fmt.Sprintf("/chronograf/v1/sources/%d/users", id),
|
|
Roles: fmt.Sprintf("/chronograf/v1/sources/%d/roles", id),
|
|
Permissions: fmt.Sprintf("/chronograf/v1/sources/%d/permissions", id),
|
|
}
|
|
}
|
|
|
|
func mrToModel(src chronograf.Source) *models.Source {
|
|
return &models.Source{
|
|
ID: strconv.Itoa(src.ID),
|
|
Links: srcLinks(src.ID),
|
|
Name: &src.Name,
|
|
Type: src.Type,
|
|
Username: src.Username,
|
|
Password: src.Password,
|
|
URL: &src.URL[0],
|
|
Default: src.Default,
|
|
}
|
|
}
|
|
|
|
func (m *Handler) Sources(ctx context.Context, params op.GetSourcesParams) middleware.Responder {
|
|
mrSrcs, err := m.Srcs.All(ctx)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: "Error loading sources"}
|
|
return op.NewGetSourcesDefault(500).WithPayload(errMsg)
|
|
}
|
|
|
|
srcs := make([]*models.Source, len(mrSrcs))
|
|
for i, src := range mrSrcs {
|
|
srcs[i] = mrToModel(src)
|
|
}
|
|
|
|
res := &models.Sources{
|
|
Sources: srcs,
|
|
}
|
|
|
|
return op.NewGetSourcesOK().WithPayload(res)
|
|
}
|
|
|
|
func (m *Handler) SourcesID(ctx context.Context, params op.GetSourcesIDParams) middleware.Responder {
|
|
id, err := strconv.Atoi(params.ID)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: fmt.Sprintf("Error converting ID %s", params.ID)}
|
|
return op.NewGetSourcesIDDefault(500).WithPayload(errMsg)
|
|
}
|
|
|
|
src, err := m.Srcs.Get(ctx, id)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 404, Message: fmt.Sprintf("Unknown ID %s", params.ID)}
|
|
return op.NewGetSourcesIDNotFound().WithPayload(errMsg)
|
|
}
|
|
|
|
return op.NewGetSourcesIDOK().WithPayload(mrToModel(src))
|
|
}
|
|
|
|
func (m *Handler) RemoveSource(ctx context.Context, params op.DeleteSourcesIDParams) middleware.Responder {
|
|
id, err := strconv.Atoi(params.ID)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: fmt.Sprintf("Error converting ID %s", params.ID)}
|
|
return op.NewDeleteSourcesIDDefault(500).WithPayload(errMsg)
|
|
}
|
|
src := chronograf.Source{
|
|
ID: id,
|
|
}
|
|
if err = m.Srcs.Delete(ctx, src); err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: fmt.Sprintf("Unknown error deleting source %s", params.ID)}
|
|
return op.NewDeleteSourcesIDDefault(500).WithPayload(errMsg)
|
|
}
|
|
|
|
return op.NewDeleteSourcesIDNoContent()
|
|
}
|
|
|
|
func (m *Handler) UpdateSource(ctx context.Context, params op.PatchSourcesIDParams) middleware.Responder {
|
|
id, err := strconv.Atoi(params.ID)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: fmt.Sprintf("Error converting ID %s", params.ID)}
|
|
return op.NewPatchSourcesIDDefault(500).WithPayload(errMsg)
|
|
}
|
|
src, err := m.Srcs.Get(ctx, id)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 404, Message: fmt.Sprintf("Unknown ID %s", params.ID)}
|
|
return op.NewPatchSourcesIDNotFound().WithPayload(errMsg)
|
|
}
|
|
src.Default = params.Config.Default
|
|
if params.Config.Name != nil {
|
|
src.Name = *params.Config.Name
|
|
}
|
|
if params.Config.Password != "" {
|
|
src.Password = params.Config.Password
|
|
}
|
|
if params.Config.Username != "" {
|
|
src.Username = params.Config.Username
|
|
}
|
|
if params.Config.URL != nil {
|
|
src.URL = []string{*params.Config.URL}
|
|
}
|
|
if params.Config.Type != "" {
|
|
src.Type = params.Config.Type
|
|
}
|
|
if err := m.Srcs.Update(ctx, src); err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: fmt.Sprintf("Error updating source ID %s", params.ID)}
|
|
return op.NewPatchSourcesIDDefault(500).WithPayload(errMsg)
|
|
}
|
|
return op.NewPatchSourcesIDNoContent()
|
|
}
|
|
|
|
func (m *Handler) MonitoredServices(ctx context.Context, params op.GetSourcesIDMonitoredParams) middleware.Responder {
|
|
srvs, err := m.TimeSeries.MonitoredServices(ctx)
|
|
if err != nil {
|
|
return op.NewGetSourcesIDMonitoredDefault(500)
|
|
}
|
|
res := &models.Services{}
|
|
for _, s := range srvs {
|
|
res.Services = append(res.Services, &models.Service{
|
|
TagKey: s.TagKey,
|
|
TagValue: s.TagValue,
|
|
Type: s.Type,
|
|
})
|
|
}
|
|
return op.NewGetSourcesIDMonitoredOK().WithPayload(res)
|
|
}
|
|
|
|
func (m *Handler) Proxy(ctx context.Context, params op.PostSourcesIDProxyParams) middleware.Responder {
|
|
id, err := strconv.Atoi(params.ID)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: fmt.Sprintf("Error converting ID %s", params.ID)}
|
|
return op.NewPostSourcesIDProxyDefault(500).WithPayload(errMsg)
|
|
}
|
|
|
|
src, err := m.Srcs.Get(ctx, id)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 404, Message: fmt.Sprintf("Unknown ID %s", params.ID)}
|
|
return op.NewPostSourcesIDProxyNotFound().WithPayload(errMsg)
|
|
}
|
|
|
|
if err = m.TimeSeries.Connect(ctx, &src); err != nil {
|
|
errMsg := &models.Error{Code: 400, Message: fmt.Sprintf("Unable to connect to source %s", params.ID)}
|
|
return op.NewPostSourcesIDProxyNotFound().WithPayload(errMsg)
|
|
}
|
|
query := chronograf.Query{
|
|
Command: *params.Query.Query,
|
|
DB: params.Query.Db,
|
|
RP: params.Query.Rp,
|
|
}
|
|
response, err := m.TimeSeries.Query(ctx, chronograf.Query(query))
|
|
if err != nil {
|
|
return op.NewPostSourcesIDProxyDefault(500)
|
|
}
|
|
|
|
res := &models.ProxyResponse{
|
|
Results: response,
|
|
}
|
|
return op.NewPostSourcesIDProxyOK().WithPayload(res)
|
|
}
|
|
|
|
func (m *Handler) Explorations(ctx context.Context, params op.GetUsersUserIDExplorationsParams) middleware.Responder {
|
|
id, err := strconv.Atoi(params.UserID)
|
|
if err != nil {
|
|
return op.NewGetUsersUserIDExplorationsDefault(500)
|
|
}
|
|
exs, err := m.Store.Query(ctx, chronograf.UserID(id))
|
|
if err != nil {
|
|
return op.NewGetUsersUserIDExplorationsNotFound()
|
|
}
|
|
res := &models.Explorations{}
|
|
for i, e := range exs {
|
|
rel := "self"
|
|
href := fmt.Sprintf("/chronograf/v1/users/%d/explorations/%d", id, i)
|
|
res.Explorations = append(res.Explorations, &models.Exploration{
|
|
Data: e.Data,
|
|
Name: e.Name,
|
|
UpdatedAt: strfmt.DateTime(e.UpdatedAt),
|
|
CreatedAt: strfmt.DateTime(e.CreatedAt),
|
|
Link: &models.Link{
|
|
Rel: &rel,
|
|
Href: &href,
|
|
},
|
|
},
|
|
)
|
|
}
|
|
return op.NewGetUsersUserIDExplorationsOK().WithPayload(res)
|
|
}
|
|
|
|
func (m *Handler) Exploration(ctx context.Context, params op.GetUsersUserIDExplorationsExplorationIDParams) middleware.Responder {
|
|
id, err := strconv.Atoi(params.UserID)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: "Error converting user id"}
|
|
return op.NewGetUsersUserIDExplorationsDefault(500).WithPayload(errMsg)
|
|
}
|
|
|
|
eID, err := strconv.Atoi(params.ExplorationID)
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: "Error converting exploration id"}
|
|
return op.NewGetUsersUserIDExplorationsExplorationIDDefault(500).WithPayload(errMsg)
|
|
}
|
|
|
|
e, err := m.Store.Get(ctx, chronograf.ExplorationID(eID))
|
|
if err != nil {
|
|
log.Printf("Error unknown exploration id: %d: %v", eID, err)
|
|
errMsg := &models.Error{Code: 404, Message: "Error unknown exploration id"}
|
|
return op.NewGetUsersUserIDExplorationsExplorationIDNotFound().WithPayload(errMsg)
|
|
}
|
|
|
|
rel := "self"
|
|
href := fmt.Sprintf("/chronograf/v1/users/%d/explorations/%d", id, eID)
|
|
res := &models.Exploration{
|
|
Data: e.Data,
|
|
Name: e.Name,
|
|
UpdatedAt: strfmt.DateTime(e.UpdatedAt),
|
|
CreatedAt: strfmt.DateTime(e.CreatedAt),
|
|
Link: &models.Link{
|
|
Rel: &rel,
|
|
Href: &href,
|
|
},
|
|
}
|
|
return op.NewGetUsersUserIDExplorationsExplorationIDOK().WithPayload(res)
|
|
}
|
|
|
|
func (m *Handler) UpdateExploration(ctx context.Context, params op.PatchUsersUserIDExplorationsExplorationIDParams) middleware.Responder {
|
|
eID, err := strconv.Atoi(params.ExplorationID)
|
|
if err != nil {
|
|
return op.NewPatchUsersUserIDExplorationsExplorationIDDefault(500)
|
|
}
|
|
|
|
e, err := m.Store.Get(ctx, chronograf.ExplorationID(eID))
|
|
if err != nil {
|
|
log.Printf("Error unknown exploration id: %d: %v", eID, err)
|
|
errMsg := &models.Error{Code: 404, Message: "Error unknown exploration id"}
|
|
return op.NewPatchUsersUserIDExplorationsExplorationIDNotFound().WithPayload(errMsg)
|
|
}
|
|
if params.Exploration != nil {
|
|
e.ID = chronograf.ExplorationID(eID)
|
|
e.Data = params.Exploration.Data.(string)
|
|
e.Name = params.Exploration.Name
|
|
m.Store.Update(ctx, e)
|
|
}
|
|
return op.NewPatchUsersUserIDExplorationsExplorationIDOK()
|
|
}
|
|
|
|
func (m *Handler) NewExploration(ctx context.Context, params op.PostUsersUserIDExplorationsParams) middleware.Responder {
|
|
id, err := strconv.Atoi(params.UserID)
|
|
if err != nil {
|
|
return op.NewPostUsersUserIDExplorationsDefault(500)
|
|
}
|
|
|
|
exs, err := m.Store.Query(ctx, chronograf.UserID(id))
|
|
if err != nil {
|
|
log.Printf("Error unknown user id: %d: %v", id, err)
|
|
errMsg := &models.Error{Code: 404, Message: "Error unknown user id"}
|
|
return op.NewPostUsersUserIDExplorationsNotFound().WithPayload(errMsg)
|
|
}
|
|
eID := len(exs)
|
|
|
|
if params.Exploration != nil {
|
|
e := chronograf.Exploration{
|
|
Data: params.Exploration.Data.(string),
|
|
Name: params.Exploration.Name,
|
|
ID: chronograf.ExplorationID(eID),
|
|
}
|
|
m.Store.Add(ctx, &e)
|
|
}
|
|
params.Exploration.UpdatedAt = strfmt.DateTime(time.Now())
|
|
params.Exploration.CreatedAt = strfmt.DateTime(time.Now())
|
|
|
|
loc := fmt.Sprintf("/chronograf/v1/users/%d/explorations/%d", id, eID)
|
|
rel := "self"
|
|
|
|
link := &models.Link{
|
|
Href: &loc,
|
|
Rel: &rel,
|
|
}
|
|
params.Exploration.Link = link
|
|
return op.NewPostUsersUserIDExplorationsCreated().WithPayload(params.Exploration).WithLocation(loc)
|
|
|
|
}
|
|
|
|
func (m *Handler) DeleteExploration(ctx context.Context, params op.DeleteUsersUserIDExplorationsExplorationIDParams) middleware.Responder {
|
|
ID, err := strconv.Atoi(params.ExplorationID)
|
|
if err != nil {
|
|
return op.NewDeleteUsersUserIDExplorationsExplorationIDDefault(500)
|
|
}
|
|
|
|
if err := m.Store.Delete(ctx, &chronograf.Exploration{ID: chronograf.ExplorationID(ID)}); err != nil {
|
|
log.Printf("Error unknown explorations id: %d: %v", ID, err)
|
|
errMsg := &models.Error{Code: 404, Message: "Error unknown user id"}
|
|
return op.NewDeleteUsersUserIDExplorationsExplorationIDNotFound().WithPayload(errMsg)
|
|
}
|
|
return op.NewDeleteUsersUserIDExplorationsExplorationIDNoContent()
|
|
}
|
|
|
|
func (m *Handler) GetMappings(ctx context.Context, params op.GetMappingsParams) middleware.Responder {
|
|
cpu := "cpu"
|
|
system := "System"
|
|
mp := &models.Mappings{
|
|
Mappings: []*models.Mapping{
|
|
&models.Mapping{
|
|
Measurement: &cpu,
|
|
Name: &system,
|
|
},
|
|
},
|
|
}
|
|
return op.NewGetMappingsOK().WithPayload(mp)
|
|
}
|
|
|
|
func (m *Handler) Token(ctx context.Context, params op.GetTokenParams) middleware.Responder {
|
|
|
|
token := jwt.NewWithClaims(jwt.SigningMethodHS512, jwt.MapClaims{
|
|
"sub": "bob",
|
|
"exp": time.Now().Add(time.Hour * 24 * 30).Unix(),
|
|
"username": "bob",
|
|
"email": "bob@mail.com",
|
|
"nbf": time.Now().Unix(),
|
|
"iat": time.Now().Unix(),
|
|
})
|
|
|
|
// sign token with secret
|
|
ts, err := token.SignedString([]byte("secret"))
|
|
if err != nil {
|
|
errMsg := &models.Error{Code: 500, Message: "Failed to sign token"}
|
|
return op.NewGetTokenDefault(500).WithPayload(errMsg)
|
|
}
|
|
|
|
t := models.Token(ts)
|
|
|
|
return op.NewGetTokenOK().WithPayload(t)
|
|
}
|