diff --git a/html/src/Components/ShareEditor.tsx b/html/src/Components/ShareEditor.tsx
index 9170b33..49794f4 100644
--- a/html/src/Components/ShareEditor.tsx
+++ b/html/src/Components/ShareEditor.tsx
@@ -60,12 +60,12 @@ export function ShareEditor(props: ShareEditorProps&BoxComponentProps) {
}
{/* Share exposure */}
-
+
{ notifyChange({...options, exposure:v}); }} transitionDuration={0}
diff --git a/html/src/i18n/config.ts b/html/src/i18n/config.ts
index f400baf..5a2d832 100644
--- a/html/src/i18n/config.ts
+++ b/html/src/i18n/config.ts
@@ -59,9 +59,9 @@ i18n
created: "Created",
exposure: "Exposure",
- guest_users_can: "Guest users can :",
- upload: "Upload",
- download: "Download",
+ you_want_to: "You want to :",
+ send: "Send",
+ receive: "Receive",
both: "Both",
validity: "Validity",
@@ -104,9 +104,9 @@ i18n
created: "Créé le",
exposure: "Type de partage",
- guest_users_can: "Les invités peuvent :",
- upload: "Envoyer",
- download: "Reçevoir",
+ you_want_to: "Vous souhaitez :",
+ send: "Envoyer",
+ receive: "Reçevoir",
both: "Les deux",
validity: "Expiration",
diff --git a/hupload/pkg/apiws/apiws.go b/hupload/pkg/apiws/apiws.go
index 0436b71..251199b 100644
--- a/hupload/pkg/apiws/apiws.go
+++ b/hupload/pkg/apiws/apiws.go
@@ -148,7 +148,15 @@ func (a *APIWS) Start() {
if _, ok := a.Authentication.CallbackFunc(nil); ok {
// If there is, define action to redirect to "/shares"
handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
- http.Redirect(w, r, "/shares", http.StatusFound)
+ s, ok := r.Context().Value(authentication.AuthStatusKey).(authentication.AuthStatus)
+ if ok && s.Authenticated {
+ http.Redirect(w, r, "/shares", http.StatusFound)
+ return
+ }
+ if r.URL.Query().Get("error") != "" {
+ http.Error(w, r.URL.Query().Get("error"), http.StatusUnauthorized)
+ return
+ }
})
m := auth.NewJWTAuthMiddleware(os.Getenv("JWT_SECRET"))
f, _ := a.Authentication.CallbackFunc(m.Middleware(handler))
diff --git a/hupload/pkg/apiws/authentication/oidc.go b/hupload/pkg/apiws/authentication/oidc.go
index 27e4660..48f3d22 100644
--- a/hupload/pkg/apiws/authentication/oidc.go
+++ b/hupload/pkg/apiws/authentication/oidc.go
@@ -5,8 +5,8 @@ import (
"crypto/rand"
"encoding/base64"
"encoding/json"
+ "errors"
"io"
- "log/slog"
"net/http"
"time"
@@ -68,7 +68,7 @@ func NewAuthenticationOIDC(o AuthenticationOIDCConfig) (*AuthenticationOIDC, err
Endpoint: result.Provider.Endpoint(),
// "openid" is a required scope for OpenID Connect flows.
- Scopes: []string{oidc.ScopeOpenID, "profile", "email"},
+ Scopes: []string{oidc.ScopeOpenID, "email", "profile"},
}
return result, nil
@@ -107,8 +107,7 @@ func (o *AuthenticationOIDC) CallbackFunc(h http.Handler) (func(w http.ResponseW
oauth2Token, err := o.Config.Exchange(r.Context(), r.URL.Query().Get("code"))
if err != nil {
- w.WriteHeader(http.StatusInternalServerError)
- _ = json.NewEncoder(w).Encode(err)
+ ServeNextError(h, errors.New("code verification failed"), w, r)
return
}
@@ -123,21 +122,18 @@ func (o *AuthenticationOIDC) CallbackFunc(h http.Handler) (func(w http.ResponseW
// Parse and verify ID Token payload.
idToken, err := verifier.Verify(r.Context(), rawIDToken)
if err != nil {
- w.WriteHeader(http.StatusInternalServerError)
- _ = json.NewEncoder(w).Encode(err)
+ ServeNextError(h, errors.New("token verification failed"), w, r)
return
}
nonce, err := r.Cookie("nonce")
if err != nil {
- w.WriteHeader(http.StatusBadRequest)
- _ = json.NewEncoder(w).Encode(err)
+ ServeNextError(h, errors.New("missing nonce"), w, r)
//http.Error(w, "nonce not found", http.StatusBadRequest)
return
}
if idToken.Nonce != nonce.Value {
- w.WriteHeader(http.StatusBadRequest)
- _ = json.NewEncoder(w).Encode(err)
+ ServeNextError(h, errors.New("nonce doesn't match"), w, r)
//http.Error(w, "nonce did not match", http.StatusBadRequest)
return
}
@@ -148,18 +144,21 @@ func (o *AuthenticationOIDC) CallbackFunc(h http.Handler) (func(w http.ResponseW
Username string `json:"preferred_username"`
}
if err := idToken.Claims(&claims); err != nil {
- w.WriteHeader(http.StatusInternalServerError)
- _ = json.NewEncoder(w).Encode(err)
+ ServeNextError(h, err, w, r)
return
}
- var rmessage json.RawMessage
- if err := idToken.Claims(&rmessage); err == nil {
- b, _ := json.MarshalIndent(rmessage, "", " ")
- slog.Info("ID Token Claims: %s", slog.String("claims", string(b)))
- }
+ // var rmessage json.RawMessage
+ // if err := idToken.Claims(&rmessage); err == nil {
+ // b, _ := json.MarshalIndent(rmessage, "", " ")
+ // slog.Info("ID Token Claims: %s", slog.String("claims", string(b)))
+ // }
- ServeNextAuthenticated(claims.Username, h, w, r)
+ if claims.Username != "" {
+ ServeNextAuthenticated(claims.Username, h, w, r)
+ return
+ }
+ h.ServeHTTP(w, r)
}, true
}
@@ -167,7 +166,10 @@ func ServeNextAuthenticated(user string, next http.Handler, w http.ResponseWrite
ctx := context.WithValue(r.Context(), AuthStatusKey, AuthStatus{Authenticated: true, User: user})
next.ServeHTTP(w, r.WithContext(ctx))
}
-
+func ServeNextError(next http.Handler, err error, w http.ResponseWriter, r *http.Request) {
+ ctx := context.WithValue(r.Context(), AuthStatusKey, AuthStatus{Authenticated: false, User: "", Error: err})
+ next.ServeHTTP(w, r.WithContext(ctx))
+}
func (o *AuthenticationOIDC) ShowLoginForm() bool {
return false
}
diff --git a/readme_images/properties-dark.png b/readme_images/properties-dark.png
index cad3ef9..2062b9a 100644
Binary files a/readme_images/properties-dark.png and b/readme_images/properties-dark.png differ
diff --git a/readme_images/properties-light.png b/readme_images/properties-light.png
index 81d3a3a..3ef5793 100644
Binary files a/readme_images/properties-light.png and b/readme_images/properties-light.png differ
diff --git a/readme_images/properties-preview-dark.png b/readme_images/properties-preview-dark.png
index 5393326..e1ec87d 100644
Binary files a/readme_images/properties-preview-dark.png and b/readme_images/properties-preview-dark.png differ
diff --git a/readme_images/properties-preview-light.png b/readme_images/properties-preview-light.png
index dd80bc7..a596b4f 100644
Binary files a/readme_images/properties-preview-light.png and b/readme_images/properties-preview-light.png differ
diff --git a/readme_images/shares-dark.png b/readme_images/shares-dark.png
index 049d25f..d0479de 100644
Binary files a/readme_images/shares-dark.png and b/readme_images/shares-dark.png differ
diff --git a/readme_images/shares-light.png b/readme_images/shares-light.png
index 621cf97..189d93e 100644
Binary files a/readme_images/shares-light.png and b/readme_images/shares-light.png differ
diff --git a/robot/Screenshots.robot b/robot/Screenshots.robot
index 15467e0..0e33ce8 100644
--- a/robot/Screenshots.robot
+++ b/robot/Screenshots.robot
@@ -27,9 +27,9 @@ Screenshot Home Page
Sleep 0.5 second
Click css=\#showEditor
Sleep 0.5 second
- Take Screenshot ${CURDIR}/../readme_images/properties-${theme}.png crop={'x': 0, 'y': 216, 'width': 800, 'height': 345}
+ Take Screenshot ${CURDIR}/../readme_images/properties-${theme}.png crop={'x': 0, 'y': 222, 'width': 800, 'height': 346}
Click css=\#preview
- Take Screenshot ${CURDIR}/../readme_images/properties-preview-${theme}.png crop={'x': 0, 'y': 216, 'width': 800, 'height': 345}
+ Take Screenshot ${CURDIR}/../readme_images/properties-preview-${theme}.png crop={'x': 0, 'y': 222, 'width': 800, 'height': 346}
Click css=\#kuva-yibi-bata \#edit