chat_sdk-state-mysql 1.0.0 → 1.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 (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/chat_sdk/state/mysql.rb +68 -0
  3. metadata +1 -1
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: c625807962a1731ba27361a51f2e78b47fcb9b1299769dc16644862d2133afde
4
- data.tar.gz: ee821cebf2ec30e940c8d9e64495fe71f28323628eb58a562c25e17eb3a7cc92
3
+ metadata.gz: 4113d277f2fa7cb1f2c0ae346240c6c589bfaf4b03449be422200645f1db310d
4
+ data.tar.gz: 8c093057fa1677ef220cbacbbe96bdec2158447a886250fd273c0f64c86902da
5
5
  SHA512:
6
- metadata.gz: 76500e001f1879bc588cf2a15dacac85e42e4dd94418202b7ececf1b457717afba1c0ad1c3fa92a57d180252ecbb6b763ed06fb1b69528fbcf191f8488bb6b05
7
- data.tar.gz: 582293dd5c2675748260e3d2242fdfb88b620f7d51fcccc999d14fa30a0b20b8713a98c12ebc2e75524964cd4e4ecbfc85605cc5df7ca623d616ed0d50bad206
6
+ metadata.gz: 77310f954281b2193b02141847c2edc0d458825e7ef6f1863c16b63c1c225c34d88a2c7ec9e174ee5b7823159b8b6323bd504417bd1ff2ed9cfa781c7fdf7aac
7
+ data.tar.gz: a0bb0eacef3a7f175880fd1b108c0bcb84e3e5a4fac09e47e2dd2212301f0cc3a58e83c0d152fab24eaa4ebdac8cf207c7b126ad4660f07905a143804ad714c1
@@ -74,6 +74,15 @@ module ChatSDK
74
74
  true
75
75
  end
76
76
 
77
+ def extend_lock(key, owner:, ttl:)
78
+ stmt = @conn.prepare(
79
+ "UPDATE chat_sdk_locks SET expires_at = DATE_ADD(NOW(), INTERVAL #{ttl.to_f} SECOND) " \
80
+ "WHERE key_prefix = ? AND lock_key = ? AND owner = ? AND expires_at > NOW()"
81
+ )
82
+ stmt.execute(@key_prefix, key, owner)
83
+ @conn.affected_rows > 0
84
+ end
85
+
77
86
  # Key-value store
78
87
 
79
88
  def get(key)
@@ -138,6 +147,52 @@ module ChatSDK
138
147
  @conn.affected_rows > 0
139
148
  end
140
149
 
150
+ def enqueue(key, value, max_size:, drop: :drop_oldest)
151
+ @conn.query("START TRANSACTION")
152
+ count_stmt = @conn.prepare(
153
+ "SELECT id FROM chat_sdk_queues WHERE key_prefix = ? AND queue_key = ? ORDER BY id FOR UPDATE"
154
+ )
155
+ ids = count_stmt.execute(@key_prefix, key).map { |row| row["id"] }
156
+ if ids.length >= max_size && drop.to_sym == :drop_newest
157
+ @conn.query("COMMIT")
158
+ return ids.length
159
+ end
160
+
161
+ insert = @conn.prepare("INSERT INTO chat_sdk_queues (key_prefix, queue_key, value) VALUES (?, ?, ?)")
162
+ insert.execute(@key_prefix, key, JSON.generate(value))
163
+ overflow = ids.length + 1 - max_size
164
+ if overflow.positive?
165
+ placeholders = Array.new(overflow, "?").join(", ")
166
+ remove = @conn.prepare("DELETE FROM chat_sdk_queues WHERE id IN (#{placeholders})")
167
+ remove.execute(*ids.first(overflow))
168
+ end
169
+ @conn.query("COMMIT")
170
+ [ids.length + 1, max_size].min
171
+ rescue
172
+ @conn.query("ROLLBACK")
173
+ raise
174
+ end
175
+
176
+ def drain_queue(key)
177
+ @conn.query("START TRANSACTION")
178
+ select = @conn.prepare(
179
+ "SELECT id, value FROM chat_sdk_queues WHERE key_prefix = ? AND queue_key = ? ORDER BY id FOR UPDATE"
180
+ )
181
+ rows = select.execute(@key_prefix, key).to_a
182
+ delete = @conn.prepare("DELETE FROM chat_sdk_queues WHERE key_prefix = ? AND queue_key = ?")
183
+ delete.execute(@key_prefix, key)
184
+ @conn.query("COMMIT")
185
+ rows.map { |row| JSON.parse(row["value"]) }
186
+ rescue
187
+ @conn.query("ROLLBACK")
188
+ raise
189
+ end
190
+
191
+ def queue_depth(key)
192
+ stmt = @conn.prepare("SELECT COUNT(*) AS count FROM chat_sdk_queues WHERE key_prefix = ? AND queue_key = ?")
193
+ stmt.execute(@key_prefix, key).first["count"].to_i
194
+ end
195
+
141
196
  # Cleanup
142
197
 
143
198
  def clear
@@ -147,6 +202,8 @@ module ChatSDK
147
202
  s2.execute(@key_prefix)
148
203
  s3 = @conn.prepare("DELETE FROM chat_sdk_cache WHERE key_prefix = ?")
149
204
  s3.execute(@key_prefix)
205
+ s4 = @conn.prepare("DELETE FROM chat_sdk_queues WHERE key_prefix = ?")
206
+ s4.execute(@key_prefix)
150
207
  end
151
208
 
152
209
  def cleanup_expired
@@ -193,6 +250,17 @@ module ChatSDK
193
250
  PRIMARY KEY (key_prefix, cache_key)
194
251
  ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
195
252
  SQL
253
+ @conn.query(<<~SQL)
254
+ CREATE TABLE IF NOT EXISTS chat_sdk_queues (
255
+ id BIGINT NOT NULL AUTO_INCREMENT,
256
+ key_prefix VARCHAR(255) NOT NULL,
257
+ queue_key VARCHAR(512) NOT NULL,
258
+ value JSON NOT NULL,
259
+ created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
260
+ PRIMARY KEY (id),
261
+ INDEX chat_sdk_queues_lookup (key_prefix, queue_key, id)
262
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
263
+ SQL
196
264
  end
197
265
  end
198
266
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: chat_sdk-state-mysql
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.0
4
+ version: 1.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Quentin Rousseau