Finalize usage of authentication for components

pull/30/head
Aloïs Micard 4 years ago
parent 4633cc7695
commit a4f86fbee9
No known key found for this signature in database
GPG Key ID: 1A0EB82F071F5EFE

@ -24,7 +24,8 @@ const (
// PaginationSizeQueryParam is the query parameter used to set page size in paginated endpoint
PaginationSizeQueryParam = "pagination-size"
contentTypeJSON = "application/json"
contentTypeJSON = "application/json"
authorizationHeader = "Authorization"
)
// ResourceDto represent a resource as given by the API
@ -53,6 +54,7 @@ type Client interface {
type client struct {
httpClient *http.Client
baseURL string
token string
}
func (c *client) SearchResources(url, keyword string,
@ -76,6 +78,7 @@ func (c *client) SearchResources(url, keyword string,
}
headers := map[string]string{}
headers[authorizationHeader] = fmt.Sprintf("Bearer %s", c.token)
if paginationPage != 0 {
headers[PaginationPageHeader] = strconv.Itoa(paginationPage)
@ -101,32 +104,49 @@ func (c *client) SearchResources(url, keyword string,
func (c *client) AddResource(res ResourceDto) (ResourceDto, error) {
targetEndpoint := fmt.Sprintf("%s/v1/resources", c.baseURL)
headers := map[string]string{}
headers[authorizationHeader] = fmt.Sprintf("Bearer %s", c.token)
var resourceDto ResourceDto
_, err := jsonPost(c.httpClient, targetEndpoint, res, &resourceDto)
_, err := jsonPost(c.httpClient, targetEndpoint, headers, res, &resourceDto)
return resourceDto, err
}
func (c *client) ScheduleURL(url string) error {
targetEndpoint := fmt.Sprintf("%s/v1/urls", c.baseURL)
_, err := jsonPost(c.httpClient, targetEndpoint, url, nil)
headers := map[string]string{}
headers[authorizationHeader] = fmt.Sprintf("Bearer %s", c.token)
_, err := jsonPost(c.httpClient, targetEndpoint, headers, url, nil)
return err
}
func (c *client) Authenticate(credentials CredentialsDto) (string, error) {
var token string
targetEndpoint := fmt.Sprintf("%s/v1/sessions", c.baseURL)
_, err := jsonPost(c.httpClient, targetEndpoint, credentials, &token)
headers := map[string]string{}
_, err := jsonPost(c.httpClient, targetEndpoint, headers, credentials, &token)
return token, err
}
// NewClient create a new Client instance to dial with the API located on given address
func NewClient(baseURL string) Client {
return &client{
// NewAuthenticatedClient create a new Client & authenticate it against the API
func NewAuthenticatedClient(baseURL string, credentials CredentialsDto) (Client, error) {
client := &client{
httpClient: &http.Client{
Timeout: time.Second * 10,
},
baseURL: baseURL,
}
token, err := client.Authenticate(credentials)
if err != nil {
return nil, err
}
client.token = token
return client, nil
}
func jsonGet(httpClient *http.Client, url string, headers map[string]string, response interface{}) (*http.Response, error) {
@ -154,7 +174,7 @@ func jsonGet(httpClient *http.Client, url string, headers map[string]string, res
return r, nil
}
func jsonPost(httpClient *http.Client, url string, request, response interface{}) (*http.Response, error) {
func jsonPost(httpClient *http.Client, url string, headers map[string]string, request, response interface{}) (*http.Response, error) {
log.Trace().Str("verb", "POST").Str("url", url).Msg("")
var err error
@ -166,7 +186,18 @@ func jsonPost(httpClient *http.Client, url string, request, response interface{}
}
}
r, err := httpClient.Post(url, contentTypeJSON, bytes.NewBuffer(b))
req, err := http.NewRequest("POST", url, bytes.NewBuffer(b))
if err != nil {
return nil, err
}
// populate custom headers
for key, value := range headers {
req.Header.Set(key, value)
}
req.Header.Set("Content-Type", contentTypeJSON)
r, err := httpClient.Do(req)
if err != nil {
return nil, err
}

@ -35,20 +35,21 @@ services:
- torproxy
scheduler:
image: creekorful/tdsh-scheduler:latest
command: --log-level debug --nats-uri nats --api-uri http://api:8080
command: --log-level debug --nats-uri nats --api-uri http://api:8080 --api-login scheduler:ZjDXeaLGj4EEUGu6
restart: always
depends_on:
- nats
- api
extractor:
image: creekorful/tdsh-extractor:latest
command: --log-level debug --nats-uri nats --api-uri http://api:8080
command: --log-level debug --nats-uri nats --api-uri http://api:8080 --api-login extractor:hWx2KsrhWVQb5vxg
restart: always
depends_on:
- nats
- api
api:
image: creekorful/tdsh-api:latest
command: --log-level debug --nats-uri nats --elasticsearch-uri http://elasticsearch:9200 --signing-key K==M5RsU_DQa4_XSbkX?L27s^xWmde25 --users demo:demo
command: --log-level debug --nats-uri nats --elasticsearch-uri http://elasticsearch:9200 --signing-key K==M5RsU_DQa4_XSbkX?L27s^xWmde25 --users extractor:hWx2KsrhWVQb5vxg --users scheduler:ZjDXeaLGj4EEUGu6 --users demo:demo
restart: always
depends_on:
- elasticsearch

@ -2,6 +2,7 @@ package api
import (
"github.com/creekorful/trandoshan/internal/logging"
"github.com/creekorful/trandoshan/internal/util"
"github.com/labstack/echo/v4"
"github.com/labstack/echo/v4/middleware"
"github.com/rs/zerolog/log"
@ -21,11 +22,7 @@ func GetApp() *cli.App {
Usage: "Trandoshan API component",
Flags: []cli.Flag{
logging.GetLogFlag(),
&cli.StringFlag{
Name: "nats-uri",
Usage: "URI to the NATS server",
Required: true,
},
util.GetNATSURIFlag(),
&cli.StringFlag{
Name: "elasticsearch-uri",
Usage: "URI to the Elasticsearch server",

@ -5,6 +5,7 @@ import (
"fmt"
"github.com/creekorful/trandoshan/internal/logging"
"github.com/creekorful/trandoshan/internal/messaging"
"github.com/creekorful/trandoshan/internal/util"
"github.com/nats-io/nats.go"
"github.com/rs/zerolog/log"
"github.com/urfave/cli/v2"
@ -24,11 +25,7 @@ func GetApp() *cli.App {
Usage: "Trandoshan crawler component",
Flags: []cli.Flag{
logging.GetLogFlag(),
&cli.StringFlag{
Name: "nats-uri",
Usage: "URI to the NATS server",
Required: true,
},
util.GetNATSURIFlag(),
&cli.StringFlag{
Name: "tor-uri",
Usage: "URI to the TOR SOCKS proxy",

@ -6,6 +6,7 @@ import (
"github.com/creekorful/trandoshan/api"
"github.com/creekorful/trandoshan/internal/logging"
"github.com/creekorful/trandoshan/internal/messaging"
"github.com/creekorful/trandoshan/internal/util"
"github.com/nats-io/nats.go"
"github.com/rs/zerolog/log"
"github.com/urfave/cli/v2"
@ -27,16 +28,9 @@ func GetApp() *cli.App {
Usage: "Trandoshan extractor component",
Flags: []cli.Flag{
logging.GetLogFlag(),
&cli.StringFlag{
Name: "nats-uri",
Usage: "URI to the NATS server",
Required: true,
},
&cli.StringFlag{
Name: "api-uri",
Usage: "URI to the API server",
Required: true,
},
util.GetNATSURIFlag(),
util.GetAPIURIFlag(),
util.GetAPILoginFlag(),
},
Action: execute,
}
@ -50,8 +44,10 @@ func execute(ctx *cli.Context) error {
log.Debug().Str("uri", ctx.String("nats-uri")).Msg("Using NATS server")
log.Debug().Str("uri", ctx.String("api-uri")).Msg("Using API server")
// Create the API client
apiClient := api.NewClient(ctx.String("api-uri"))
apiClient, err := util.GetAPIAuthenticatedClient(ctx)
if err != nil {
return err
}
// Create the NATS subscriber
sub, err := messaging.NewSubscriber(ctx.String("nats-uri"))

@ -6,6 +6,7 @@ import (
"github.com/creekorful/trandoshan/api"
"github.com/creekorful/trandoshan/internal/logging"
"github.com/creekorful/trandoshan/internal/messaging"
"github.com/creekorful/trandoshan/internal/util"
"github.com/nats-io/nats.go"
"github.com/rs/zerolog/log"
"github.com/urfave/cli/v2"
@ -23,16 +24,9 @@ func GetApp() *cli.App {
Usage: "Trandoshan scheduler component",
Flags: []cli.Flag{
logging.GetLogFlag(),
&cli.StringFlag{
Name: "nats-uri",
Usage: "URI to the NATS server",
Required: true,
},
&cli.StringFlag{
Name: "api-uri",
Usage: "URI to the API server",
Required: true,
},
util.GetNATSURIFlag(),
util.GetAPIURIFlag(),
util.GetAPILoginFlag(),
&cli.StringFlag{
Name: "refresh-delay",
Usage: "Duration before allowing crawl of existing resource (none = never)",
@ -58,7 +52,10 @@ func execute(ctx *cli.Context) error {
}
// Create the API client
apiClient := api.NewClient(ctx.String("api-uri"))
apiClient, err := util.GetAPIAuthenticatedClient(ctx)
if err != nil {
return err
}
// Create the NATS subscriber
sub, err := messaging.NewSubscriber(ctx.String("nats-uri"))

@ -2,8 +2,8 @@ package trandoshanctl
import (
"fmt"
"github.com/creekorful/trandoshan/api"
"github.com/creekorful/trandoshan/internal/logging"
"github.com/creekorful/trandoshan/internal/util"
"github.com/olekukonko/tablewriter"
"github.com/rs/zerolog/log"
"github.com/urfave/cli/v2"
@ -13,17 +13,22 @@ import (
// GetApp returns the Trandoshan CLI app
func GetApp() *cli.App {
apiFlag := util.GetAPIURIFlag()
apiFlag.Value = "http://localhost:15005"
apiFlag.Required = false
apiLoginFlag := util.GetAPILoginFlag()
apiLoginFlag.Value = "demo:demo"
apiLoginFlag.Required = false
return &cli.App{
Name: "trandoshanctl",
Version: "0.4.0",
Usage: "Trandoshan CLI",
Flags: []cli.Flag{
logging.GetLogFlag(),
&cli.StringFlag{
Name: "api-uri",
Usage: "URI to the API server",
Value: "http://localhost:15005",
},
apiFlag,
apiLoginFlag,
},
Commands: []*cli.Command{
{
@ -54,7 +59,13 @@ func schedule(c *cli.Context) error {
}
url := c.Args().First()
apiClient := api.NewClient(c.String("api-uri"))
// Create the API client
apiClient, err := util.GetAPIAuthenticatedClient(c)
if err != nil {
log.Err(err).Msg("Error while creating API client")
return err
}
if err := apiClient.ScheduleURL(url); err != nil {
log.Err(err).Str("url", url).Msg("Unable to schedule crawling for URL")
@ -68,7 +79,13 @@ func schedule(c *cli.Context) error {
func search(c *cli.Context) error {
keyword := c.Args().First()
apiClient := api.NewClient(c.String("api-uri"))
// Create the API client
apiClient, err := util.GetAPIAuthenticatedClient(c)
if err != nil {
log.Err(err).Msg("Error while creating API client")
return err
}
res, count, err := apiClient.SearchResources("", keyword, time.Time{}, time.Time{}, 1, 10)
if err != nil {

@ -0,0 +1,55 @@
package util
import (
"fmt"
"github.com/creekorful/trandoshan/api"
"github.com/urfave/cli/v2"
"strings"
)
// GetAPILoginFlag return the cli flag to set api credentials
func GetAPILoginFlag() *cli.StringFlag {
return &cli.StringFlag{
Name: "api-login",
Usage: "Login to use when dialing with the API",
Required: true,
}
}
// GetAPIURIFlag return the cli flag to set api uri
func GetAPIURIFlag() *cli.StringFlag {
return &cli.StringFlag{
Name: "api-uri",
Usage: "URI to the API server",
Required: true,
}
}
// GetAPILogin return the credentials from cli flag
func GetAPILogin(c *cli.Context) (api.CredentialsDto, error) {
if c.String("api-login") == "" {
return api.CredentialsDto{}, fmt.Errorf("missing credentials")
}
credentials := strings.Split(c.String("api-login"), ":")
if len(credentials) != 2 {
return api.CredentialsDto{}, fmt.Errorf("wrong credentials format")
}
return api.CredentialsDto{Username: credentials[0], Password: credentials[1]}, nil
}
// GetAPIAuthenticatedClient return the authenticated api client
func GetAPIAuthenticatedClient(c *cli.Context) (api.Client, error) {
// Create the API client
credentials, err := GetAPILogin(c)
if err != nil {
return nil, err
}
apiClient, err := api.NewAuthenticatedClient(c.String("api-uri"), credentials)
if err != nil {
return nil, err
}
return apiClient, nil
}

@ -0,0 +1,12 @@
package util
import "github.com/urfave/cli/v2"
// GetNATSURIFlag return the nats uri from cli flag
func GetNATSURIFlag() *cli.StringFlag {
return &cli.StringFlag{
Name: "nats-uri",
Usage: "URI to the NATS server",
Required: true,
}
}
Loading…
Cancel
Save