bard-api 0.1.0 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 88e72bcfdbda52d9fe76f647c7f29b18f6610c755c416728dfa4d5333f8b45e5
4
- data.tar.gz: 55a480c5e5e72e4041c3bf9a1eb973104af8b40da1d31a1c9eb289ab5eb97ac8
3
+ metadata.gz: 70f38ef8f674aefa2cdcfba3586e87d644c10026943625bd82cb2be180f0035b
4
+ data.tar.gz: 1fd66c7e938efe753797d99e594c03f802948c004adafe0991b2b5577a00fb73
5
5
  SHA512:
6
- metadata.gz: c64aaf163b756bc6f02286ecccca3aed8fc1835b15fc7b991fb9eed9662e187bdfc74802cf624c578759894de0967c83a69f0a27d7d739dffa9f351808c148a1
7
- data.tar.gz: ab6a6c87a4ae2a692cdb3039fb087749b882eeb7cb1c0599c9b6eba9a221c3243cab4b3c78a118438c9a03ca8a951a5ff4cd8a3f3e11d1f7795a3c67e1c37414
6
+ metadata.gz: 6ce89073234248cf2a6ec1cc628bb97fcbf8f8d96e8be9d46dd117f54b1f18277e4c81cd9ec3ba2fb7fbd6fc1ef53bed84532f603db84ffda376cbd87b08f28e
7
+ data.tar.gz: 1119c0bc33153aeb74d53ec585c59b7bade8c410eda343962e9c2d5cf04bb017e8d2cb7e441c31c89c1dd4b687dcccc0ed1121e5fc7de2d8fbe158ce7ac34e8e
data/README.md CHANGED
@@ -80,17 +80,24 @@ Authorization: Bearer <jwt-token>
80
80
  ```json
81
81
  {
82
82
  "timestamp": "2025-12-06T10:30:00Z",
83
- "size": 123456789,
84
83
  "destinations": [
85
84
  {
86
85
  "name": "primary",
87
86
  "type": "s3",
88
- "status": "success"
87
+ "path": "bard-backup/my-app",
88
+ "region": "us-west-2"
89
89
  }
90
90
  ]
91
91
  }
92
92
  ```
93
93
 
94
+ **Response (404 Not Found):**
95
+ ```json
96
+ {
97
+ "error": "No backups found"
98
+ }
99
+ ```
100
+
94
101
  ### Authentication
95
102
 
96
103
  The API uses JWT with asymmetric RSA keys for authentication. The public key is embedded in the gem, and only BARD Tracker with the private key can create valid tokens.
data/lib/bard/api/app.rb CHANGED
@@ -3,7 +3,7 @@
3
3
  require "rack"
4
4
  require "json"
5
5
  require_relative "auth"
6
- require_relative "backup"
6
+ require "bard/backup"
7
7
 
8
8
  module Bard
9
9
  module Api
@@ -24,7 +24,7 @@ module Bard
24
24
  not_found
25
25
  end
26
26
  rescue => e
27
- internal_error(e)
27
+ json_response(500, { error: e.message })
28
28
  end
29
29
 
30
30
  private
@@ -35,34 +35,22 @@ module Bard
35
35
 
36
36
  def create_backup(request)
37
37
  with_auth(request) do |payload|
38
- # Extract URLs from the JWT payload
39
- urls = payload["urls"]
40
- raise "Missing 'urls' in token payload" if urls.nil? || urls.empty?
41
-
42
- # Perform the backup
43
- backup = Backup.new
44
- result = backup.perform(urls)
45
-
46
- json_response(200, result)
38
+ backup = Bard::Backup.create!({
39
+ name: "bard",
40
+ type: :upload,
41
+ urls: payload["urls"]
42
+ })
43
+ json_response(200, backup.as_json)
47
44
  end
48
- rescue => e
49
- json_response(500, { error: "Backup failed: #{e.message}" })
50
45
  end
51
46
 
52
47
  def latest_backup(request)
53
48
  with_auth(request) do
54
- # Get the latest backup status
55
- backup = Backup.new
56
- result = backup.latest
57
-
58
- if result
59
- json_response(200, result)
60
- else
61
- json_response(404, { error: "No backups found" })
62
- end
49
+ backup = Bard::Backup.latest
50
+ json_response(200, backup.as_json)
63
51
  end
64
- rescue => e
65
- json_response(500, { error: e.message })
52
+ rescue Bard::Backup::NotFound => e
53
+ json_response(404, { error: e.message })
66
54
  end
67
55
 
68
56
  def with_auth(request)
@@ -79,10 +67,6 @@ module Bard
79
67
  def not_found
80
68
  json_response(404, { error: "Not found" })
81
69
  end
82
-
83
- def internal_error(e)
84
- json_response(500, { error: "Internal server error: #{e.message}" })
85
- end
86
70
  end
87
71
  end
88
72
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module Bard
4
4
  module Api
5
- VERSION = "0.1.0"
5
+ VERSION = "0.3.1"
6
6
  end
7
7
  end
data/lib/bard/api.rb CHANGED
@@ -1,8 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require_relative "api/version"
4
- require_relative "api/auth"
5
- require_relative "api/backup"
6
4
  require_relative "api/app"
7
5
 
8
6
  module Bard
data/lib/bard-api.rb ADDED
@@ -0,0 +1 @@
1
+ require "bard/api"
metadata CHANGED
@@ -1,84 +1,99 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: bard-api
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.3.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Micah Geisel
8
+ autorequire:
8
9
  bindir: exe
9
10
  cert_chain: []
10
- date: 2025-12-07 00:00:00.000000000 Z
11
+ date: 2025-12-11 00:00:00.000000000 Z
11
12
  dependencies:
12
13
  - !ruby/object:Gem::Dependency
13
14
  name: jwt
14
15
  requirement: !ruby/object:Gem::Requirement
15
16
  requirements:
16
- - - "~>"
17
+ - - ">="
17
18
  - !ruby/object:Gem::Version
18
- version: '2.7'
19
+ version: '0'
19
20
  type: :runtime
20
21
  prerelease: false
21
22
  version_requirements: !ruby/object:Gem::Requirement
22
23
  requirements:
23
- - - "~>"
24
+ - - ">="
24
25
  - !ruby/object:Gem::Version
25
- version: '2.7'
26
+ version: '0'
26
27
  - !ruby/object:Gem::Dependency
27
28
  name: rack
28
29
  requirement: !ruby/object:Gem::Requirement
29
30
  requirements:
30
- - - "~>"
31
+ - - ">="
31
32
  - !ruby/object:Gem::Version
32
- version: '3.0'
33
+ version: '0'
33
34
  type: :runtime
34
35
  prerelease: false
35
36
  version_requirements: !ruby/object:Gem::Requirement
36
37
  requirements:
37
- - - "~>"
38
+ - - ">="
38
39
  - !ruby/object:Gem::Version
39
- version: '3.0'
40
+ version: '0'
40
41
  - !ruby/object:Gem::Dependency
41
- name: http
42
+ name: backhoe
42
43
  requirement: !ruby/object:Gem::Requirement
43
44
  requirements:
44
- - - "~>"
45
+ - - ">="
45
46
  - !ruby/object:Gem::Version
46
- version: '5.0'
47
+ version: '0'
47
48
  type: :runtime
48
49
  prerelease: false
49
50
  version_requirements: !ruby/object:Gem::Requirement
50
51
  requirements:
51
- - - "~>"
52
+ - - ">="
52
53
  - !ruby/object:Gem::Version
53
- version: '5.0'
54
+ version: '0'
54
55
  - !ruby/object:Gem::Dependency
55
- name: backhoe
56
+ name: bard
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ type: :runtime
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ - !ruby/object:Gem::Dependency
70
+ name: bard-backup
56
71
  requirement: !ruby/object:Gem::Requirement
57
72
  requirements:
58
- - - "~>"
73
+ - - ">="
59
74
  - !ruby/object:Gem::Version
60
- version: '0.10'
75
+ version: '0'
61
76
  type: :runtime
62
77
  prerelease: false
63
78
  version_requirements: !ruby/object:Gem::Requirement
64
79
  requirements:
65
- - - "~>"
80
+ - - ">="
66
81
  - !ruby/object:Gem::Version
67
- version: '0.10'
82
+ version: '0'
68
83
  - !ruby/object:Gem::Dependency
69
84
  name: rack-test
70
85
  requirement: !ruby/object:Gem::Requirement
71
86
  requirements:
72
- - - "~>"
87
+ - - ">="
73
88
  - !ruby/object:Gem::Version
74
- version: '2.1'
89
+ version: '0'
75
90
  type: :development
76
91
  prerelease: false
77
92
  version_requirements: !ruby/object:Gem::Requirement
78
93
  requirements:
79
- - - "~>"
94
+ - - ">="
80
95
  - !ruby/object:Gem::Version
81
- version: '2.1'
96
+ version: '0'
82
97
  description: Rack app that mounts in Rails projects to expose management endpoints
83
98
  for BARD Tracker
84
99
  email:
@@ -92,10 +107,10 @@ files:
92
107
  - README.md
93
108
  - Rakefile
94
109
  - config.ru
110
+ - lib/bard-api.rb
95
111
  - lib/bard/api.rb
96
112
  - lib/bard/api/app.rb
97
113
  - lib/bard/api/auth.rb
98
- - lib/bard/api/backup.rb
99
114
  - lib/bard/api/version.rb
100
115
  homepage: https://github.com/botandrose/bard-api
101
116
  licenses:
@@ -103,6 +118,7 @@ licenses:
103
118
  metadata:
104
119
  homepage_uri: https://github.com/botandrose/bard-api
105
120
  source_code_uri: https://github.com/botandrose/bard-api
121
+ post_install_message:
106
122
  rdoc_options: []
107
123
  require_paths:
108
124
  - lib
@@ -117,7 +133,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
117
133
  - !ruby/object:Gem::Version
118
134
  version: '0'
119
135
  requirements: []
120
- rubygems_version: 3.6.2
136
+ rubygems_version: 3.5.11
137
+ signing_key:
121
138
  specification_version: 4
122
139
  summary: REST API for BARD-managed Rails projects
123
140
  test_files: []
@@ -1,95 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require "backhoe"
4
- require "http"
5
- require "time"
6
- require "fileutils"
7
-
8
- module Bard
9
- module Api
10
- class Backup
11
- class BackupError < StandardError; end
12
-
13
- # Perform a backup to the specified URLs
14
- def perform(urls)
15
- raise BackupError, "No URLs provided" if urls.nil? || urls.empty?
16
-
17
- timestamp = Time.now.utc
18
- destinations = []
19
- errors = []
20
-
21
- # Create temp file with timestamp
22
- filename = "#{timestamp.iso8601}.sql.gz"
23
- temp_path = "/tmp/#{filename}"
24
-
25
- begin
26
- # Dump database to temp file using Backhoe
27
- Backhoe.dump(temp_path)
28
-
29
- # Get file size
30
- file_size = File.size(temp_path)
31
-
32
- # Upload to all URLs in parallel
33
- threads = urls.map do |url|
34
- Thread.new do
35
- begin
36
- upload_to_url(url, temp_path)
37
- {
38
- name: "bard",
39
- type: "bard",
40
- status: "success"
41
- }
42
- rescue => e
43
- errors << e
44
- {
45
- name: "bard",
46
- type: "bard",
47
- status: "failed",
48
- error: e.message
49
- }
50
- end
51
- end
52
- end
53
-
54
- # Wait for all uploads to complete
55
- destinations = threads.map(&:value)
56
- ensure
57
- # Clean up temp file
58
- FileUtils.rm_f(temp_path)
59
- end
60
-
61
- # Store backup metadata
62
- @last_backup = {
63
- timestamp: timestamp.iso8601,
64
- size: file_size,
65
- destinations: destinations
66
- }
67
-
68
- # Raise error if any destination failed
69
- unless errors.empty?
70
- raise BackupError, "Some destinations failed: #{errors.map(&:message).join(", ")}"
71
- end
72
-
73
- @last_backup
74
- end
75
-
76
- # Get the latest backup status
77
- def latest
78
- # TODO: Retrieve from database instead of instance variable
79
- @last_backup
80
- end
81
-
82
- private
83
-
84
- def upload_to_url(url, file_path)
85
- File.open(file_path, "rb") do |file|
86
- response = HTTP.put(url, body: file)
87
-
88
- unless response.status.success?
89
- raise BackupError, "Upload failed with status #{response.status}: #{response.body}"
90
- end
91
- end
92
- end
93
- end
94
- end
95
- end