fix graph and graph-explorer
Signed-off-by: Jörn Friedrich Dreyer <jfd@butonic.de>
This commit is contained in:
@@ -4,10 +4,11 @@ import (
|
||||
"os"
|
||||
|
||||
"github.com/owncloud/ocis/graph/pkg/command"
|
||||
"github.com/owncloud/ocis/graph/pkg/config"
|
||||
)
|
||||
|
||||
func main() {
|
||||
if err := command.Execute(); err != nil {
|
||||
if err := command.Execute(config.New()); err != nil {
|
||||
os.Exit(1)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,25 +1,26 @@
|
||||
package command
|
||||
|
||||
import (
|
||||
"context"
|
||||
"os"
|
||||
"strings"
|
||||
|
||||
"github.com/owncloud/ocis/ocis-pkg/sync"
|
||||
"github.com/thejerf/suture/v4"
|
||||
|
||||
"github.com/micro/cli/v2"
|
||||
"github.com/owncloud/ocis/graph/pkg/config"
|
||||
"github.com/owncloud/ocis/graph/pkg/flagset"
|
||||
"github.com/owncloud/ocis/graph/pkg/version"
|
||||
ociscfg "github.com/owncloud/ocis/ocis-pkg/config"
|
||||
"github.com/owncloud/ocis/ocis-pkg/log"
|
||||
"github.com/spf13/viper"
|
||||
)
|
||||
|
||||
// Execute is the entry point for the ocis-graph command.
|
||||
func Execute() error {
|
||||
cfg := config.New()
|
||||
|
||||
func Execute(cfg *config.Config) error {
|
||||
app := &cli.App{
|
||||
Name: "graph",
|
||||
Name: "ocis-graph",
|
||||
Version: version.String,
|
||||
Usage: "Serve Graph API for oCIS",
|
||||
Compiled: version.Compiled(),
|
||||
@@ -34,6 +35,7 @@ func Execute() error {
|
||||
Flags: flagset.RootWithConfig(cfg),
|
||||
|
||||
Before: func(c *cli.Context) error {
|
||||
cfg.Server.Version = version.String
|
||||
return ParseConfig(c, cfg)
|
||||
},
|
||||
|
||||
@@ -110,3 +112,27 @@ func ParseConfig(c *cli.Context, cfg *config.Config) error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// SutureService allows for the graph command to be embedded and supervised by a suture supervisor tree.
|
||||
type SutureService struct {
|
||||
cfg *config.Config
|
||||
}
|
||||
|
||||
// NewSutureService creates a new graph.SutureService
|
||||
func NewSutureService(cfg *ociscfg.Config) suture.Service {
|
||||
if cfg.Mode == 0 {
|
||||
cfg.Graph.Supervised = true
|
||||
}
|
||||
return SutureService{
|
||||
cfg: cfg.Graph,
|
||||
}
|
||||
}
|
||||
|
||||
func (s SutureService) Serve(ctx context.Context) error {
|
||||
s.cfg.Context = ctx
|
||||
if err := Execute(s.cfg); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
+27
-50
@@ -2,8 +2,6 @@ package command
|
||||
|
||||
import (
|
||||
"context"
|
||||
"os"
|
||||
"os/signal"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
@@ -19,6 +17,7 @@ import (
|
||||
"github.com/owncloud/ocis/graph/pkg/metrics"
|
||||
"github.com/owncloud/ocis/graph/pkg/server/debug"
|
||||
"github.com/owncloud/ocis/graph/pkg/server/http"
|
||||
"github.com/owncloud/ocis/ocis-pkg/sync"
|
||||
"go.opencensus.io/stats/view"
|
||||
"go.opencensus.io/trace"
|
||||
)
|
||||
@@ -29,12 +28,19 @@ func Server(cfg *config.Config) *cli.Command {
|
||||
Name: "server",
|
||||
Usage: "Start integrated server",
|
||||
Flags: flagset.ServerWithConfig(cfg),
|
||||
Before: func(c *cli.Context) error {
|
||||
Before: func(ctx *cli.Context) error {
|
||||
logger := NewLogger(cfg)
|
||||
if cfg.HTTP.Root != "/" {
|
||||
cfg.HTTP.Root = strings.TrimSuffix(cfg.HTTP.Root, "/")
|
||||
}
|
||||
|
||||
return ParseConfig(c, cfg)
|
||||
// When running on single binary mode the before hook from the root command won't get called. We manually
|
||||
// call this before hook from ocis command, so the configuration can be loaded.
|
||||
if !cfg.Supervised {
|
||||
return ParseConfig(ctx, cfg)
|
||||
}
|
||||
logger.Debug().Str("service", "graph").Msg("ignoring config file parsing when running supervised")
|
||||
return nil
|
||||
},
|
||||
Action: func(c *cli.Context) error {
|
||||
logger := NewLogger(cfg)
|
||||
@@ -125,28 +131,29 @@ func Server(cfg *config.Config) *cli.Command {
|
||||
|
||||
var (
|
||||
gr = run.Group{}
|
||||
ctx, cancel = context.WithCancel(context.Background())
|
||||
metrics = metrics.New()
|
||||
ctx, cancel = func() (context.Context, context.CancelFunc) {
|
||||
if cfg.Context == nil {
|
||||
return context.WithCancel(context.Background())
|
||||
}
|
||||
return context.WithCancel(cfg.Context)
|
||||
}()
|
||||
mtrcs = metrics.New()
|
||||
)
|
||||
|
||||
defer cancel()
|
||||
|
||||
mtrcs.BuildInfo.WithLabelValues(cfg.Server.Version).Set(1)
|
||||
|
||||
{
|
||||
server, err := http.Server(
|
||||
http.Logger(logger),
|
||||
http.Context(ctx),
|
||||
http.Config(cfg),
|
||||
http.Metrics(metrics),
|
||||
http.Flags(flagset.RootWithConfig(cfg)),
|
||||
http.Flags(flagset.ServerWithConfig(cfg)),
|
||||
http.Metrics(mtrcs),
|
||||
)
|
||||
|
||||
if err != nil {
|
||||
logger.Info().
|
||||
Err(err).
|
||||
Str("transport", "http").
|
||||
Msg("Failed to initialize server")
|
||||
|
||||
logger.Info().Err(err).Str("transport", "http").Msg("Failed to initialize server")
|
||||
return err
|
||||
}
|
||||
|
||||
@@ -169,48 +176,18 @@ func Server(cfg *config.Config) *cli.Command {
|
||||
)
|
||||
|
||||
if err != nil {
|
||||
logger.Info().
|
||||
Err(err).
|
||||
Str("transport", "debug").
|
||||
Msg("Failed to initialize server")
|
||||
|
||||
logger.Info().Err(err).Str("transport", "debug").Msg("Failed to initialize server")
|
||||
return err
|
||||
}
|
||||
|
||||
gr.Add(func() error {
|
||||
return server.ListenAndServe()
|
||||
}, func(_ error) {
|
||||
ctx, timeout := context.WithTimeout(ctx, 5*time.Second)
|
||||
|
||||
defer timeout()
|
||||
defer cancel()
|
||||
|
||||
if err := server.Shutdown(ctx); err != nil {
|
||||
logger.Info().
|
||||
Err(err).
|
||||
Str("transport", "debug").
|
||||
Msg("Failed to shutdown server")
|
||||
} else {
|
||||
logger.Info().
|
||||
Str("transport", "debug").
|
||||
Msg("Shutting down server")
|
||||
}
|
||||
gr.Add(server.ListenAndServe, func(_ error) {
|
||||
_ = server.Shutdown(ctx)
|
||||
cancel()
|
||||
})
|
||||
}
|
||||
|
||||
{
|
||||
stop := make(chan os.Signal, 1)
|
||||
|
||||
gr.Add(func() error {
|
||||
signal.Notify(stop, os.Interrupt)
|
||||
|
||||
<-stop
|
||||
|
||||
return nil
|
||||
}, func(err error) {
|
||||
//close(stop)
|
||||
cancel()
|
||||
})
|
||||
if !cfg.Supervised {
|
||||
sync.Trap(&gr, cancel)
|
||||
}
|
||||
|
||||
return gr.Run()
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
package config
|
||||
|
||||
import "context"
|
||||
|
||||
// Log defines the available logging configuration.
|
||||
type Log struct {
|
||||
Level string
|
||||
@@ -22,6 +24,12 @@ type HTTP struct {
|
||||
Root string
|
||||
}
|
||||
|
||||
// Server configures a server.
|
||||
type Server struct {
|
||||
Version string
|
||||
Name string
|
||||
}
|
||||
|
||||
// Tracing defines the available tracing configuration.
|
||||
type Tracing struct {
|
||||
Enabled bool
|
||||
@@ -60,10 +68,14 @@ type Config struct {
|
||||
Log Log
|
||||
Debug Debug
|
||||
HTTP HTTP
|
||||
Server Server
|
||||
Tracing Tracing
|
||||
Ldap Ldap
|
||||
OpenIDConnect OpenIDConnect
|
||||
Reva Reva
|
||||
|
||||
Context context.Context
|
||||
Supervised bool
|
||||
}
|
||||
|
||||
// New initializes a new configuration with or without defaults.
|
||||
|
||||
@@ -122,7 +122,7 @@ func ServerWithConfig(cfg *config.Config) []cli.Flag {
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "http-root",
|
||||
Value: flags.OverrideDefaultString(cfg.HTTP.Root, "/"),
|
||||
Value: flags.OverrideDefaultString(cfg.HTTP.Root, "/graph"),
|
||||
Usage: "Root path of http server",
|
||||
EnvVars: []string{"GRAPH_HTTP_ROOT"},
|
||||
Destination: &cfg.HTTP.Root,
|
||||
@@ -178,9 +178,9 @@ func ServerWithConfig(cfg *config.Config) []cli.Flag {
|
||||
},
|
||||
&cli.StringFlag{
|
||||
Name: "oidc-endpoint",
|
||||
Value: flags.OverrideDefaultString(cfg.OpenIDConnect.Endpoint, "https://localhost:9130"),
|
||||
Value: flags.OverrideDefaultString(cfg.OpenIDConnect.Endpoint, "https://localhost:9200"),
|
||||
Usage: "OpenIDConnect endpoint",
|
||||
EnvVars: []string{"GRAPH_OIDC_ENDPOINT"},
|
||||
EnvVars: []string{"GRAPH_OIDC_ENDPOINT", "OCIS_URL"},
|
||||
Destination: &cfg.OpenIDConnect.Endpoint,
|
||||
},
|
||||
&cli.BoolFlag{
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
package metrics
|
||||
|
||||
import "github.com/prometheus/client_golang/prometheus"
|
||||
|
||||
var (
|
||||
// Namespace defines the namespace for the defines metrics.
|
||||
Namespace = "ocis"
|
||||
@@ -11,22 +13,21 @@ var (
|
||||
// Metrics defines the available metrics of this service.
|
||||
type Metrics struct {
|
||||
// Counter *prometheus.CounterVec
|
||||
BuildInfo *prometheus.GaugeVec
|
||||
}
|
||||
|
||||
// New initializes the available metrics.
|
||||
func New() *Metrics {
|
||||
m := &Metrics{
|
||||
// Counter: prometheus.NewCounterVec(prometheus.CounterOpts{
|
||||
// Namespace: Namespace,
|
||||
// Subsystem: Subsystem,
|
||||
// Name: "greet_total",
|
||||
// Help: "How many greeting requests processed",
|
||||
// }, []string{}),
|
||||
BuildInfo: prometheus.NewGaugeVec(prometheus.GaugeOpts{
|
||||
Namespace: Namespace,
|
||||
Subsystem: Subsystem,
|
||||
Name: "build_info",
|
||||
Help: "Build information",
|
||||
}, []string{"version"}),
|
||||
}
|
||||
|
||||
// prometheus.Register(
|
||||
// m.Counter,
|
||||
// )
|
||||
|
||||
_ = prometheus.Register(m.BuildInfo)
|
||||
// TODO: implement metrics
|
||||
return m
|
||||
}
|
||||
|
||||
@@ -23,7 +23,8 @@ func (g Graph) GroupCtx(next http.Handler) http.Handler {
|
||||
errorcode.InvalidRequest.Render(w, r, http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
filter := fmt.Sprintf("(entryuuid=%s)", groupID)
|
||||
// TODO make filter configurable
|
||||
filter := fmt.Sprintf("(&(objectClass=posixGroup)(ownCloudUUID=%s))", groupID)
|
||||
group, err := g.ldapGetSingleEntry(g.config.Ldap.BaseDNGroups, filter)
|
||||
if err != nil {
|
||||
g.logger.Info().Err(err).Msgf("Failed to read group %s", groupID)
|
||||
@@ -45,10 +46,11 @@ func (g Graph) GetGroups(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
result, err := g.ldapSearch(con, "(objectclass=*)", g.config.Ldap.BaseDNGroups)
|
||||
// TODO make filter configurable
|
||||
result, err := g.ldapSearch(con, "(objectClass=posixGroup)", g.config.Ldap.BaseDNGroups)
|
||||
|
||||
if err != nil {
|
||||
g.logger.Error().Err(err).Msg("Failed search ldap with filter: '(objectclass=*)'")
|
||||
g.logger.Error().Err(err).Msg("Failed search ldap with filter: '(objectClass=posixGroup)'")
|
||||
errorcode.ServiceNotAvailable.Render(w, r, http.StatusInternalServerError)
|
||||
return
|
||||
}
|
||||
|
||||
@@ -27,7 +27,8 @@ func (g Graph) UserCtx(next http.Handler) http.Handler {
|
||||
errorcode.InvalidRequest.Render(w, r, http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
filter := fmt.Sprintf("(entryuuid=%s)", userID)
|
||||
// TODO make filter configurable
|
||||
filter := fmt.Sprintf("(&(objectClass=posixAccount)(ownCloudUUID=%s))", userID)
|
||||
user, err = g.ldapGetSingleEntry(g.config.Ldap.BaseDNUsers, filter)
|
||||
if err != nil {
|
||||
g.logger.Info().Err(err).Msgf("Failed to read user %s", userID)
|
||||
@@ -45,7 +46,8 @@ func (g Graph) GetMe(w http.ResponseWriter, r *http.Request) {
|
||||
claims := oidc.FromContext(r.Context())
|
||||
g.logger.Info().Interface("Claims", claims).Msg("Claims in /me")
|
||||
|
||||
filter := fmt.Sprintf("(uid=%s)", claims.PreferredUsername)
|
||||
// TODO make filter configurable
|
||||
filter := fmt.Sprintf("(&(objectClass=posixAccount)(cn=%s))", claims.PreferredUsername)
|
||||
user, err := g.ldapGetSingleEntry(g.config.Ldap.BaseDNUsers, filter)
|
||||
if err != nil {
|
||||
g.logger.Info().Err(err).Msgf("Failed to read user %s", claims.PreferredUsername)
|
||||
@@ -68,10 +70,11 @@ func (g Graph) GetUsers(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
result, err := g.ldapSearch(con, "(objectclass=*)", g.config.Ldap.BaseDNUsers)
|
||||
// TODO make filter configurable
|
||||
result, err := g.ldapSearch(con, "(objectClass=posixAccount)", g.config.Ldap.BaseDNUsers)
|
||||
|
||||
if err != nil {
|
||||
g.logger.Error().Err(err).Msg("Failed search ldap with filter: '(objectclass=*)'")
|
||||
g.logger.Error().Err(err).Msg("Failed search ldap with filter: '(objectClass=posixAccount)'")
|
||||
errorcode.ServiceNotAvailable.Render(w, r, http.StatusInternalServerError)
|
||||
return
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user