feat(auth): add logout functionality

- Implement LogoutHandler to handle user logout requests
- Add DeleteTokenInfo and GetUserIDFromToken functions to auth module
- Update README.md with logout endpoint documentation
This commit is contained in:
2026-03-03 23:06:36 +08:00
parent 9e6e6f8b19
commit 62917633c4
4 changed files with 87 additions and 7 deletions
+32 -6
View File
@@ -77,7 +77,7 @@ All API responses are returned in JSON format:
---
### 1. Register User
### Register User
**Endpoint:** `/register`
**Method:** POST
@@ -122,7 +122,7 @@ X-Timestamp: 1704067200000
---
### 2. Login
### Login
**Endpoint:** `/login`
**Method:** POST
@@ -166,7 +166,33 @@ X-Timestamp: 1704067200000
---
### 3. Create frpc Instance
### Logout
**Endpoint:** `/logout`
**Method:** GET
**Auth Required:** Yes (token)
**Request Headers:**
```
X-Token: your_token
X-Timestamp: 1704067200000
```
| Header | Type | Required | Description |
|--------|------|----------|-------------|
| X-Token | string | Yes | Authentication token |
| X-Timestamp | int64 | Yes | Client timestamp in milliseconds |
**Response:**
```json
{
"success": true,
"message": "Logout successful"
}
```
---
### Create frpc Instance
**Endpoint:** `/frpcAct/instanceMgr/create`
**Method:** POST
@@ -226,7 +252,7 @@ X-Timestamp: 1704067200000
---
### 4. Delete frpc Instance
### Delete frpc Instance
**Endpoint:** `/frpcAct/instanceMgr/delete`
**Method:** POST
@@ -259,7 +285,7 @@ X-Timestamp: 1704067200000
---
### 5. Modify frpc Instance
### Modify frpc Instance
**Endpoint:** `/frpcAct/instanceMgr/modify`
**Method:** POST
@@ -384,7 +410,7 @@ Modify system-level settings such as instance name, boot-at-start configuration,
---
### 6. List frpc Instances
### List frpc Instances
**Endpoint:** `/frpcAct/instanceMgr/list`
**Method:** GET
+25 -1
View File
@@ -106,7 +106,7 @@ func GetTokenInfo(userID int) (*TokenInfo, error) {
tokenInfo, exists := tokenMap[userID]
if !exists {
return nil, fmt.Errorf("Token not found for userID %d", userID)
}
return tokenInfo, nil
@@ -199,3 +199,27 @@ func ValidateTimeStamp(header http.Header) bool {
}
return true
}
func GetUserIDFromToken(token string) (int, error) {
userID, err := extractUserIDFromToken(token)
if err != nil {
return 0, fmt.Errorf("Failed to extract userID from token: %w", err)
}
return userID, nil
}
func DeleteTokenInfo(userID int) error {
tokenMux.Lock()
defer tokenMux.Unlock()
delete(tokenMap, userID)
postLog.Debug(fmt.Sprintf("[DeleteTokenInfo] Removed token for userID %d", userID))
return nil
}
func GetUsernameByID(userID int) (string) {
user, err := GetUserByID(userID)
if err != nil {
return ""
}
return user.Username
}
+1
View File
@@ -10,6 +10,7 @@ func setupRoutes() {
postLog.Info("Setting up routes...")
http.HandleFunc("/register", RegisterHandler)
http.HandleFunc("/login", LoginHandler)
http.HandleFunc("/logout", LogoutHandler)
http.HandleFunc("/frpcAct/instanceMgr/create", CreateInstanceHandler)
http.HandleFunc("/frpcAct/instanceMgr/list", ListInstancesHandler)
+29
View File
@@ -159,3 +159,32 @@ func LoginHandler(w http.ResponseWriter, r *http.Request) {
})
postLog.Info(fmt.Sprintf("[LoginHandler] User \"%s\" Login successful", req.Username))
}
func LogoutHandler(w http.ResponseWriter, r *http.Request) {
if r.Method != http.MethodGet {
SendErrorResponse(w, http.StatusMethodNotAllowed, "Invalid request method")
postLog.Warning(fmt.Sprintf("[LogoutHandler] Invalid request method: %s", r.Method))
return
}
if !ValidateTimeStamp(r.Header) {
SendErrorResponse(w, http.StatusBadRequest, "Invalid or missing X-Timestamp in header")
return
}
userID, err := GetUserIDFromToken(r.Header.Get("X-Token"))
if err != nil {
SendErrorResponse(w, http.StatusUnauthorized, "Invalid or missing token")
postLog.Warning(fmt.Sprintf("[LogoutHandler] Invalid or missing token: %v", err))
return
}
if err := DeleteTokenInfo(userID); err != nil {
SendErrorResponse(w, http.StatusInternalServerError, "Failed to logout")
postLog.Error(fmt.Sprintf("[LogoutHandler] Failed to logout user [%d]%s: %v", userID, GetUsernameByID(userID), err))
return
}
SendSuccessResponse(w, "Logout successful", nil)
postLog.Info(fmt.Sprintf("[LogoutHandler] User [%d]%s Logout successful", userID, GetUsernameByID(userID)))
}