4
0

api_key.go 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119
  1. // SPDX-FileCopyrightText: Copyright The Miniflux Authors. All rights reserved.
  2. // SPDX-License-Identifier: Apache-2.0
  3. package storage // import "miniflux.app/v2/internal/storage"
  4. import (
  5. "fmt"
  6. "miniflux.app/v2/internal/crypto"
  7. "miniflux.app/v2/internal/model"
  8. )
  9. var ErrAPIKeyNotFound = fmt.Errorf("store: API Key not found")
  10. // APIKeyExists checks if an API Key with the same description exists.
  11. func (s *Storage) APIKeyExists(userID int64, description string) bool {
  12. var result bool
  13. query := `SELECT true FROM api_keys WHERE user_id=$1 AND lower(description)=lower($2) LIMIT 1`
  14. s.db.QueryRow(query, userID, description).Scan(&result)
  15. return result
  16. }
  17. // SetAPIKeyUsedTimestamp updates the last used date of an API Key.
  18. func (s *Storage) SetAPIKeyUsedTimestamp(userID int64, token string) error {
  19. query := `UPDATE api_keys SET last_used_at=now() WHERE user_id=$1 and token=$2`
  20. _, err := s.db.Exec(query, userID, token)
  21. if err != nil {
  22. return fmt.Errorf(`store: unable to update last used date for API key: %v`, err)
  23. }
  24. return nil
  25. }
  26. // APIKeys returns all API Keys that belongs to the given user.
  27. func (s *Storage) APIKeys(userID int64) (model.APIKeys, error) {
  28. query := `
  29. SELECT
  30. id, user_id, token, description, last_used_at, created_at
  31. FROM
  32. api_keys
  33. WHERE
  34. user_id=$1
  35. ORDER BY description ASC
  36. `
  37. rows, err := s.db.Query(query, userID)
  38. if err != nil {
  39. return nil, fmt.Errorf(`store: unable to fetch API Keys: %v`, err)
  40. }
  41. defer rows.Close()
  42. apiKeys := make(model.APIKeys, 0)
  43. for rows.Next() {
  44. var apiKey model.APIKey
  45. if err := rows.Scan(
  46. &apiKey.ID,
  47. &apiKey.UserID,
  48. &apiKey.Token,
  49. &apiKey.Description,
  50. &apiKey.LastUsedAt,
  51. &apiKey.CreatedAt,
  52. ); err != nil {
  53. return nil, fmt.Errorf(`store: unable to fetch API Key row: %v`, err)
  54. }
  55. apiKeys = append(apiKeys, apiKey)
  56. }
  57. return apiKeys, nil
  58. }
  59. // CreateAPIKey inserts a new API key.
  60. func (s *Storage) CreateAPIKey(userID int64, description string) (*model.APIKey, error) {
  61. query := `
  62. INSERT INTO api_keys
  63. (user_id, token, description)
  64. VALUES
  65. ($1, $2, $3)
  66. RETURNING
  67. id, user_id, token, description, last_used_at, created_at
  68. `
  69. var apiKey model.APIKey
  70. err := s.db.QueryRow(
  71. query,
  72. userID,
  73. crypto.GenerateRandomStringHex(32),
  74. description,
  75. ).Scan(
  76. &apiKey.ID,
  77. &apiKey.UserID,
  78. &apiKey.Token,
  79. &apiKey.Description,
  80. &apiKey.LastUsedAt,
  81. &apiKey.CreatedAt,
  82. )
  83. if err != nil {
  84. return nil, fmt.Errorf(`store: unable to create API Key: %v`, err)
  85. }
  86. return &apiKey, nil
  87. }
  88. // DeleteAPIKey deletes an API Key.
  89. func (s *Storage) DeleteAPIKey(userID, keyID int64) error {
  90. result, err := s.db.Exec(`DELETE FROM api_keys WHERE id = $1 AND user_id = $2`, keyID, userID)
  91. if err != nil {
  92. return fmt.Errorf(`store: unable to delete this API Key: %v`, err)
  93. }
  94. count, err := result.RowsAffected()
  95. if err != nil {
  96. return fmt.Errorf(`store: unable to delete this API Key: %v`, err)
  97. }
  98. if count == 0 {
  99. return ErrAPIKeyNotFound
  100. }
  101. return nil
  102. }