blest 0.0.1 → 0.1.0

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.
Files changed (5) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +64 -111
  3. data/lib/blest.rb +808 -143
  4. data/spec/blest_spec.rb +219 -0
  5. metadata +3 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e0a8f112cb397ac2725175231766a0ca838e9ce898180cfc8be6e59e7fa498b8
4
- data.tar.gz: b9f91cdfb82e5058d889fd6abddc8f14248c567567a3cb0acbd673d04b99f84c
3
+ metadata.gz: 6307985d2fcaa8aa558a9d6fa55bd61787de23accd0d762d12843cf1202784c8
4
+ data.tar.gz: b58fc887beb5b6312f14f7332daab521b37baa037750eb3b1b406191160ae0d1
5
5
  SHA512:
6
- metadata.gz: 7fc3d8ae042c5b9dc96cb9fda9edeada1e34c26d1d08e890e72359c74f675e7c874b3c71ec78e4c056a8aaa886081be3374d87a46e22f86fd8689019149a9c8f
7
- data.tar.gz: a862d3210e033fdf7b9d71b6b65b710a169955b49804df64aacfe0aacc73486f28e42a5dbf37994e66fa7a66ade5a39bbb2ecb5984941f5cf2c7284cc87308a8
6
+ metadata.gz: 1f0b5c80b2ae39259d5386c60a7a27deb6b04dc35a5162c30be64056d10581de3b6a6ee47cd800e27f4e4cac1f52a6cb692b47abbda7533ed48dc85c3eafe403
7
+ data.tar.gz: 964ab1acc3ca2db12a2918bb141efa3f254438c095b47c7e81313c4b5140d7a10b13712b3a4773e6fa1b76158ccc75dffa2af591df45fdb55a767278ea72e470
data/README.md CHANGED
@@ -2,7 +2,7 @@
2
2
 
3
3
  The Ruby reference implementation of BLEST (Batch-able, Lightweight, Encrypted State Transfer), an improved communication protocol for web APIs which leverages JSON, supports request batching and selective returns, and provides a modern alternative to REST.
4
4
 
5
- To learn more about BLEST, please refer to the white paper: https://jhunt.dev/BLEST%20White%20Paper.pdf
5
+ To learn more about BLEST, please visit the website: https://blest.jhunt.dev
6
6
 
7
7
  For a front-end implementation in React, please visit https://github.com/jhuntdev/blest-react
8
8
 
@@ -15,158 +15,111 @@ For a front-end implementation in React, please visit https://github.com/jhuntde
15
15
  - Single Endpoint - Reduce complexity and improve data privacy
16
16
  - Fully Encrypted - Improve data privacy
17
17
 
18
- <!-- ## Installation
18
+ ## Installation
19
19
 
20
- Install BLEST Python from PyPI.
20
+ Install BLEST Ruby from Rubygems.
21
21
 
22
22
  ```bash
23
- python3 -m pip install blest
24
- ``` -->
23
+ gem install blest
24
+ ```
25
25
 
26
26
  ## Usage
27
27
 
28
- Use the `create_request_handler` function to create a request handler suitable for use in an existing Python application. Use the `create_http_server` function to create a standalone HTTP server for your request handler.
29
-
30
- <!-- Use the `create_http_client` function to create a BLEST HTTP client. -->
31
-
32
- ### create_request_handler
28
+ This core class of this library has an interface somewhat similar to Sinatra. It also provides a `Router` class with a `handle` method for use in an existing Ruby API and an `HttpClient` class with a `request` method for making BLEST HTTP requests.
33
29
 
34
30
  ```ruby
35
- require 'socket'
36
- require 'json'
37
- require './blest.rb'
31
+ require 'blest'
38
32
 
39
- server = TCPServer.new('localhost', 8080)
33
+ app = Blest.new(timeout: 1000, port: 8080, host: 'localhost', cors: 'http://localhost:3000')
40
34
 
41
35
  # Create some middleware (optional)
42
- auth_middleware = ->(params, context) {
43
- if params[:name].present?
44
- context[:user] = {
45
- name: params[:name]
36
+ app.before do |params, context|
37
+ if params['name'].present?
38
+ context['user'] = {
39
+ name: params['name']
46
40
  }
47
41
  nil
48
42
  else
49
43
  raise RuntimeError, "Unauthorized"
50
44
  end
51
- }
45
+ end
52
46
 
53
47
  # Create a route controller
54
- greet_controller = ->(params, context) {
48
+ app.route('greet') do |params, context|
55
49
  {
56
- greeting: "Hi, #{context[:user][:name]}!"
50
+ greeting: "Hi, #{context['user']['name']}!"
57
51
  }
58
- }
59
-
60
- # Create a router
61
- router = {
62
- greet: [auth_middleware, greet_controller]
63
- }
64
-
65
- # Create a request handler
66
- handler = create_request_handler(router)
67
-
68
- puts "Server listening on port 8080"
69
-
70
- loop do
71
-
72
- client = server.accept
73
-
74
- request = client.gets
75
- if request.nil?
76
- client.close
77
- else
78
-
79
- method, path, _ = request.split(' ')
80
-
81
- if method != 'POST'
82
- client.puts "HTTP/1.1 405 Method Not Allowed"
83
- client.puts "\r\n"
84
- elsif path != '/'
85
- client.puts "HTTP/1.1 404 Not Found"
86
- client.puts "\r\n"
87
- else
88
- content_length = 0
89
- while line = client.gets
90
- break if line == "\r\n"
91
- content_length = line.split(': ')[1].to_i if line.start_with?('Content-Length')
92
- end
93
-
94
- body = client.read(content_length)
95
- data = JSON.parse(body)
96
-
97
- context = {
98
- headers: request.headers
99
- }
100
-
101
- # Use the request handler]
102
- result, error = handler.(data, context)
103
-
104
- if error
105
- response = error.to_json
106
- client.puts "HTTP/1.1 500 Internal Server Error"
107
- client.puts "Content-Type: application/json"
108
- client.puts "Content-Length: #{response.bytesize}"
109
- client.puts "\r\n"
110
- client.puts response
111
- elsif result
112
- response = result.to_json
113
- client.puts "HTTP/1.1 200 OK"
114
- client.puts "Content-Type: application/json"
115
- client.puts "Content-Length: #{response.bytesize}"
116
- client.puts "\r\n"
117
- client.puts response
118
- else
119
- client.puts "HTTP/1.1 204 No Content"
120
- end
121
- end
122
-
123
- client.close
124
-
125
- end
126
52
  end
53
+
54
+ # Start the server
55
+ app.listen
127
56
  ```
128
57
 
129
- ### create_http_server
58
+ ### Router
59
+
60
+ The following example uses Sinatra.
130
61
 
131
62
  ```ruby
132
- require 'socket'
63
+ require 'sinatra'
133
64
  require 'json'
134
- require './blest.rb'
65
+ require 'blest'
66
+
67
+ # Instantiate the Router
68
+ router = Router.new(timeout: 1000)
135
69
 
136
70
  # Create some middleware (optional)
137
- auth_middleware = ->(params, context) {
138
- if params[:name].present?
139
- context[:user] = {
140
- name: params[:name]
71
+ router.before do |params, context|
72
+ if params['name'].present?
73
+ context['user'] = {
74
+ name: params['name']
141
75
  }
142
76
  nil
143
77
  else
144
78
  raise RuntimeError, "Unauthorized"
145
79
  end
146
- }
80
+ end
147
81
 
148
82
  # Create a route controller
149
- greet_controller = ->(params, context) {
83
+ router.route('greet') do |params, context|
150
84
  {
151
- greeting: "Hi, #{context[:user][:name]}!"
85
+ greeting: "Hi, #{context['user']['name']}!"
152
86
  }
153
- }
154
-
155
- # Create a router
156
- router = {
157
- greet: [auth_middleware, greet_controller]
158
- }
87
+ end
159
88
 
160
- # Create a request handler
161
- handler = create_request_handler(router)
89
+ # Handle BLEST requests
90
+ post '/' do
91
+ json_body = JSON.parse(request.body.read)
92
+ headers = request.env.select { |k, _| k.start_with?('HTTP_') }
93
+ result, error = router.handle.call(json_body, { 'headers' => headers })
94
+ content_type :json
95
+ if error
96
+ raise Sinatra::Error.new(error.status || 500, error)
97
+ else
98
+ result
99
+ end
100
+ end
101
+ ```
162
102
 
163
- # Create the server
164
- server = create_http_server(handler, { port: 8080 })
103
+ ### HttpClient
165
104
 
166
- # Run the server
167
- server.()
105
+ ```ruby
106
+ require 'blest'
107
+
108
+ # Create a client
109
+ client = HttpClient.new('http://localhost:8080', max_batch_size = 25, buffer_delay = 10, headers = {
110
+ 'Authorization': 'Bearer token'
111
+ })
112
+
113
+ # Send a request
114
+ begin
115
+ result = client.request('greet', { 'name': 'Steve' }, ['greeting']).value
116
+ # Do something with the result
117
+ rescue => error
118
+ # Do something in case of error
119
+ end
168
120
  ```
169
121
 
122
+
170
123
  ## License
171
124
 
172
125
  This project is licensed under the [MIT License](LICENSE).