Changeset 0.15.0 (#71)
This commit is contained in:
@@ -163,27 +163,13 @@ func (h *AdminHandler) destroyVault(c *gin.Context, userID string) {
|
||||
return
|
||||
}
|
||||
|
||||
// Null out vault columns — user gets a fresh vault on next login
|
||||
_, err := database.DB.Exec(`
|
||||
UPDATE users
|
||||
SET encrypted_uek = NULL, uek_salt = NULL, uek_nonce = NULL, vault_set = false
|
||||
WHERE id = $1
|
||||
`, userID)
|
||||
if err != nil {
|
||||
log.Printf("⚠ Failed to clear vault for user %s: %v", userID, err)
|
||||
}
|
||||
deleted := DestroyVaultDB(c.Request.Context(), userID)
|
||||
|
||||
// Evict from session cache (if user is currently logged in)
|
||||
h.uekCache.Evict(userID)
|
||||
|
||||
// Delete personal provider configs — their keys are undecryptable now
|
||||
result, err := database.DB.Exec(`
|
||||
DELETE FROM provider_configs WHERE scope = 'personal' AND owner_id = $1
|
||||
`, userID)
|
||||
if err != nil {
|
||||
log.Printf("⚠ Failed to delete personal providers for user %s: %v", userID, err)
|
||||
} else if rows, _ := result.RowsAffected(); rows > 0 {
|
||||
log.Printf(" 🔐 Destroyed %d personal provider(s) for user %s", rows, userID)
|
||||
if deleted > 0 {
|
||||
log.Printf(" 🔐 Destroyed %d personal provider(s) for user %s", deleted, userID)
|
||||
}
|
||||
|
||||
h.auditLog(c, "user.vault_destroyed", "user", userID, models.JSONMap{
|
||||
@@ -191,6 +177,40 @@ func (h *AdminHandler) destroyVault(c *gin.Context, userID string) {
|
||||
})
|
||||
}
|
||||
|
||||
// ResetVault explicitly resets a user's vault without changing their password.
|
||||
// Clears vault columns, deletes personal provider configs, evicts UEK cache.
|
||||
// The user gets a fresh vault on their next login.
|
||||
// POST /api/v1/admin/users/:id/vault/reset
|
||||
func (h *AdminHandler) ResetVault(c *gin.Context) {
|
||||
userID := c.Param("id")
|
||||
|
||||
// Verify user exists
|
||||
user, err := h.stores.Users.GetByID(c.Request.Context(), userID)
|
||||
if err != nil || user == nil {
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": "user not found"})
|
||||
return
|
||||
}
|
||||
|
||||
if h.uekCache == nil {
|
||||
c.JSON(http.StatusBadRequest, gin.H{"error": "vault not configured"})
|
||||
return
|
||||
}
|
||||
|
||||
deleted := DestroyVaultDB(c.Request.Context(), userID)
|
||||
h.uekCache.Evict(userID)
|
||||
|
||||
h.auditLog(c, "user.vault_reset", "user", userID, models.JSONMap{
|
||||
"reason": "admin_manual_reset",
|
||||
"providers_deleted": deleted,
|
||||
})
|
||||
|
||||
log.Printf(" 🔐 Vault reset for user %s (%d personal provider(s) cleared)", userID, deleted)
|
||||
c.JSON(http.StatusOK, gin.H{
|
||||
"message": "vault reset — user will get a fresh vault on next login",
|
||||
"providers_deleted": deleted,
|
||||
})
|
||||
}
|
||||
|
||||
func (h *AdminHandler) DeleteUser(c *gin.Context) {
|
||||
id := c.Param("id")
|
||||
if err := h.stores.Users.Delete(c.Request.Context(), id); err != nil {
|
||||
|
||||
Reference in New Issue
Block a user