Skip to content

Commit

Permalink
Add bearer token config to HTTP backends for Globus compat
Browse files Browse the repository at this point in the history
  • Loading branch information
jhiemstrawisc committed Jun 13, 2024
1 parent 8187571 commit 2971adf
Show file tree
Hide file tree
Showing 7 changed files with 56 additions and 13 deletions.
11 changes: 11 additions & 0 deletions docs/parameters.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -907,6 +907,17 @@ type: string
default: none
components: ["origin"]
---
name: Origin.HttpAuthTokenFile
description: |+
When set, all requests from the origin to the http backend will include the contents of the file as a bearer token in the
Authorization header.
If the origin backend is configured with the `globus` storage type, any value set here will be overridden with the filepath to
the first file ending in `.tok` found in the $(Origin.GlobusConfigLocation)/tokens directory
type: filename
default: none
components: ["origin"]
---
name: Origin.XRootServiceUrl
description: |+
When the origin is configured to export another XRootD storage backend by setting `Origin.StorageType = xroot`, the `XRootServiceUrl`
Expand Down
18 changes: 9 additions & 9 deletions origin/globus.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,11 +58,11 @@ type globusExportUI struct {
}

const (
globusInactive = "Inactive"
globusActivated = "Activated"
GlobusInactive = "Inactive"
GlobusActivated = "Activated"
)

const globusTokenFileExt = ".tok" // File extension for caching Globus access token
const GlobusTokenFileExt = ".tok" // File extension for caching Globus access token

var (
// An in-memory map-struct to keep Globus collections information with key being the collection UUID.
Expand Down Expand Up @@ -104,7 +104,7 @@ func InitGlobusBackend(exps []server_utils.OriginExport) error {
globusEsp := globusExport{
DisplayName: esp.GlobusCollectionName,
FederationPrefix: esp.FederationPrefix,
Status: globusInactive,
Status: GlobusInactive,
Description: "Server start",
}
// We check the origin db and see if we already have the refresh token in-place
Expand Down Expand Up @@ -150,7 +150,7 @@ func InitGlobusBackend(exps []server_utils.OriginExport) error {
globusEsp.DisplayName = col.Name
}

globusEsp.Status = globusActivated
globusEsp.Status = GlobusActivated
globusEsp.Token = collectionToken
globusEsp.HttpsServer = col.ServerURL
globusEsp.Description = "Activated with cached credentials"
Expand All @@ -167,7 +167,7 @@ func isExportActivated(fedPrefix string) (ok bool) {
defer globusExportsMutex.RUnlock()
for _, exp := range globusExports {
if exp.FederationPrefix == fedPrefix {
return exp.Status == globusActivated
return exp.Status == GlobusActivated
}
}
return false
Expand All @@ -185,7 +185,7 @@ func doGlobusTokenRefresh() error {
globusExportsMutex.Lock()
defer globusExportsMutex.Unlock()
// We can't refresh exports that are never activated
if exp.Status == globusInactive {
if exp.Status == GlobusInactive {
return nil
}
newTok, err := refreshGlobusToken(cid, exp.Token)
Expand All @@ -194,7 +194,7 @@ func doGlobusTokenRefresh() error {
newTok, err = refreshGlobusToken(cid, exp.Token)
if err != nil {
log.Errorf("Failed to retry refreshing Globus token for collection %s with name %s: %v", cid, exp.DisplayName, err)
exp.Status = globusInactive
exp.Status = GlobusInactive
exp.Description = fmt.Sprintf("Failed to refresh token: %v", err)
return err
}
Expand Down Expand Up @@ -242,7 +242,7 @@ func GetGlobusExportsValues(activeOnly bool) []globusExport {
exps := []globusExport{}
for _, val := range globusExports {
if activeOnly {
if val.Status == globusActivated {
if val.Status == GlobusActivated {
exps = append(exps, *val)
} else {
continue
Expand Down
6 changes: 3 additions & 3 deletions origin/globus_client.go
Original file line number Diff line number Diff line change
Expand Up @@ -454,7 +454,7 @@ func handleGlobusCallback(ctx *gin.Context) {
log.Infof("Updating existing Globus export %s with new token", cid)
globusExports[cid].HttpsServer = transferJSON.HttpsServer
globusExports[cid].Token = collectionToken
globusExports[cid].Status = globusActivated
globusExports[cid].Status = GlobusActivated
globusExports[cid].Description = ""
if globusExports[cid].DisplayName == "" || globusExports[cid].DisplayName == cid {
globusExports[cid].DisplayName = transferJSON.DisplayName
Expand Down Expand Up @@ -567,8 +567,8 @@ func persistAccessToken(collectionID string, token *oauth2.Token) error {
if filepath.Clean(tokBase) == "" {
return fmt.Errorf("failed to update Globus token: Origin.GlobusTokenLocation is not a valid path: %s", tokBase)
}
tokFileName := filepath.Join(tokBase, collectionID+globusTokenFileExt)
tmpTokFile, err := os.CreateTemp(tokBase, collectionID+globusTokenFileExt)
tokFileName := filepath.Join(tokBase, collectionID+GlobusTokenFileExt)
tmpTokFile, err := os.CreateTemp(tokBase, collectionID+GlobusTokenFileExt)
if err != nil {
return errors.Wrap(err, "failed to update Globus token: unable to create a temporary Globus token file")
}
Expand Down
1 change: 1 addition & 0 deletions param/parameters.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions param/parameters_struct.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 3 additions & 0 deletions xrootd/resources/xrootd-origin.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,9 @@ ofs.osslib libXrdHTTPServer.so
httpserver.url_base {{.Origin.HttpServiceUrl}}
httpserver.storage_prefix {{.Origin.FederationPrefix}}
httpserver.trace debug info warning
{{if .Origin.HttpAuthTokenFile -}}
httpserver.token_file {{.Origin.HttpAuthTokenFile}}
{{- end}}
{{else if eq .Origin.StorageType "xroot"}}
# This "origin" is actually acting like a cache that doesn't cache anything by pointing
# to another xrootd server. It allows us to plug bespoke XRootD servers into the federation
Expand Down
28 changes: 27 additions & 1 deletion xrootd/xrootd_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,7 @@ type (
CalculatedPort string
FederationPrefix string
HttpServiceUrl string
HttpAuthTokenFile string
XRootServiceUrl string
RunLocation string
StorageType string
Expand Down Expand Up @@ -669,6 +670,31 @@ func ConfigXrootd(ctx context.Context, isOrigin bool) (string, error) {
xrdConfig.Origin.HttpServiceUrl = globusExports[0].HttpsServer
}
xrdConfig.Origin.FederationPrefix = globusExports[0].FederationPrefix

if globusExports[0].Status == origin.GlobusActivated {
// Check the contents of $(Origin.GlobusConfigLocation)/tokens and grab the first `.tok` file
// Feed this to the HTTP Plugin as the auth token file
tknFldr := filepath.Join(param.Origin_GlobusConfigLocation.GetString(), "tokens")
tokenFiles, err := os.ReadDir(tknFldr)
if err != nil {
return "", errors.Wrap(err, "failed to read Globus token directory for token files")
}

if len(tokenFiles) == 0 {
return "", errors.Errorf("failed to find a Globus auth token in %s", tknFldr)
}
var tFileName string
for _, tFile := range tokenFiles {
if ext := filepath.Ext(tFile.Name()); ext == origin.GlobusTokenFileExt {
tFileName = tFile.Name()
break
}
}
if tFileName == "" {
return "", errors.Errorf("no Globus auth tokens ending in %s could be found in %s", origin.GlobusTokenFileExt, tknFldr)
}
xrdConfig.Origin.HttpAuthTokenFile = filepath.Join(param.Origin_GlobusConfigLocation.GetString(), "tokens", tFileName)
}
}
}

Expand All @@ -695,7 +721,7 @@ func ConfigXrootd(ctx context.Context, isOrigin bool) (string, error) {
if xrdConfig.Origin.Multiuser {
ok, err := config.HasMultiuserCaps()
if err != nil {
return "", errors.Wrap(err, "Failed to determine if the origin can run in multiuser mode")
return "", errors.Wrap(err, "failed to determine if the origin can run in multiuser mode")
}
if !ok {
return "", errors.New("Origin.Multiuser is set to `true` but the command was run without sufficient privilege; was it launched as root?")
Expand Down

0 comments on commit 2971adf

Please sign in to comment.