solid_agent 0.2.1 → 0.2.2

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: 73594fa8639580da1945c6445fad2fef3eaf0500e0f48fd8842115c9f4e2ec33
4
- data.tar.gz: 250018ddb7579ff3aabad5da2f8f7b43cf53d963a5d25ad0a241721d3591a304
3
+ metadata.gz: ea68dd1f79ae5dc2a0e18874a7a6b0f9ae031b30fbc0111a4d965a0cbf7d2229
4
+ data.tar.gz: 2c8bb5f5f965daeb1d7d5dcded961208d356231c8c31f6189fbb4c0827f7d356
5
5
  SHA512:
6
- metadata.gz: fb3671bd7db8f8616ef267cdbab425a3280cf8961346ab2e1643557245bea283e0dacf97c3a656ce647f9718714541fbcd547043c7c488a0f478d73ea634d33c
7
- data.tar.gz: 1e65df9005fdecceb369a2b30427c2003bb8f658bc2211e9ff2144a5b6fd72a40f7541df83e74f8a2eefab92498b5823bd4f9061209ec3ad0c617fd2fdc06604
6
+ metadata.gz: 0d193d194377e1c04bbae506d33c6645f573d5c37917a9564a45fb118f8db58c8a81165b445017b2794e78372340a4de6a0e420df0b49390c8cd4bad8380cef2
7
+ data.tar.gz: 2a27747e8a939338604d94c45113f667a040f1b53615a1c42fef881206c34e12ae56709bf8984219f2188b42a99ed7467daf3011fe91fed079bd228d6ae95ca0
data/CHANGELOG.md CHANGED
@@ -7,6 +7,22 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
7
7
 
8
8
  ## Unreleased
9
9
 
10
+ ## [0.2.2] - 2026-10-31
11
+
12
+ A patch release so the install generators work on SQLite and MySQL.
13
+
14
+ ### Fixed
15
+
16
+ - **The generated migrations run on SQLite and MySQL.** Every migration
17
+ template declared its JSON columns as `jsonb`, a PostgreSQL type, so
18
+ `rails generate solid_agent:install` (and `solid_agent:context`,
19
+ `solid_agent:reasons`) wrote migrations that aborted on SQLite with
20
+ `undefined method 'jsonb'`, including on a fresh Rails app. The templates
21
+ now choose the type when the migration runs: `jsonb` on PostgreSQL, `json`
22
+ elsewhere, and no column default on MySQL, which rejects one on JSON
23
+ columns. Migrations already generated are unaffected; an app that edited
24
+ them by hand to `json` needs no change.
25
+
10
26
  ## [0.2.1] - 2026-10-07
11
27
 
12
28
  A patch release for activeagent 1.9, whose generations can pause to ask the
@@ -14,7 +14,7 @@ class Create<%= class_name.pluralize %> < ActiveRecord::Migration<%= migration_v
14
14
  t.text :instructions
15
15
 
16
16
  # Flexible options storage (input_params, model settings, etc.)
17
- t.jsonb :options, default: {}
17
+ t.column :options, json_type, **json_default({})
18
18
 
19
19
  # Tracing/debugging
20
20
  t.string :trace_id, index: true
@@ -29,4 +29,33 @@ class Create<%= class_name.pluralize %> < ActiveRecord::Migration<%= migration_v
29
29
  add_index :<%= table_name %>, [:agent_name, :action_name]
30
30
  add_index :<%= table_name %>, :created_at
31
31
  end
32
+
33
+ private
34
+
35
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
36
+ # and SQLite aborts the migration on it.
37
+ def json_type
38
+ @json_type ||= postgres? ? :jsonb : :json
39
+ end
40
+
41
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
42
+ # JSON column can't have a default value"), which aborts the migration, so
43
+ # the column is created without one there. The gem assigns every JSON column
44
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
45
+ # would.
46
+ def json_default(value)
47
+ mysql? ? {} : { default: value }
48
+ end
49
+
50
+ def postgres?
51
+ adapter_name.include?("postgres")
52
+ end
53
+
54
+ def mysql?
55
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
56
+ end
57
+
58
+ def adapter_name
59
+ connection.adapter_name.to_s.downcase
60
+ end
32
61
  end
@@ -23,17 +23,17 @@ class Create<%= generation_class_name.pluralize %> < ActiveRecord::Migration<%=
23
23
  t.integer :reasoning_tokens, default: 0
24
24
 
25
25
  # Tool calls made in this generation
26
- t.jsonb :tool_calls, default: []
26
+ t.column :tool_calls, json_type, **json_default([])
27
27
 
28
28
  # Raw response from the provider
29
- t.jsonb :raw_response
29
+ t.column :raw_response, json_type
30
30
 
31
31
  # Timing
32
32
  t.float :duration_seconds
33
33
 
34
34
  # Telemetry correlation + provenance snapshot
35
35
  t.string :trace_id
36
- t.jsonb :provenance, default: {}
36
+ t.column :provenance, json_type, **json_default({})
37
37
 
38
38
  t.timestamps
39
39
  end
@@ -43,4 +43,33 @@ class Create<%= generation_class_name.pluralize %> < ActiveRecord::Migration<%=
43
43
  add_index :<%= generation_table_name %>, :trace_id
44
44
  add_index :<%= generation_table_name %>, [:<%= file_name %>_id, :created_at]
45
45
  end
46
+
47
+ private
48
+
49
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
50
+ # and SQLite aborts the migration on it.
51
+ def json_type
52
+ @json_type ||= postgres? ? :jsonb : :json
53
+ end
54
+
55
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
56
+ # JSON column can't have a default value"), which aborts the migration, so
57
+ # the column is created without one there. The gem assigns every JSON column
58
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
59
+ # would.
60
+ def json_default(value)
61
+ mysql? ? {} : { default: value }
62
+ end
63
+
64
+ def postgres?
65
+ adapter_name.include?("postgres")
66
+ end
67
+
68
+ def mysql?
69
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
70
+ end
71
+
72
+ def adapter_name
73
+ connection.adapter_name.to_s.downcase
74
+ end
46
75
  end
@@ -14,17 +14,17 @@ class Create<%= message_class_name.pluralize %> < ActiveRecord::Migration<%= mig
14
14
  # For tool calls and results
15
15
  t.string :tool_call_id
16
16
  t.string :tool_name
17
- t.jsonb :tool_arguments, default: {}
18
- t.jsonb :tool_result
17
+ t.column :tool_arguments, json_type, **json_default({})
18
+ t.column :tool_result, json_type
19
19
 
20
20
  # For multimodal content
21
- t.jsonb :attachments, default: []
21
+ t.column :attachments, json_type, **json_default([])
22
22
 
23
23
  # Metadata
24
- t.jsonb :metadata, default: {}
24
+ t.column :metadata, json_type, **json_default({})
25
25
 
26
26
  # Provenance snapshot + content checksum (populated by HasContext)
27
- t.jsonb :provenance, default: {}
27
+ t.column :provenance, json_type, **json_default({})
28
28
  t.string :content_checksum
29
29
 
30
30
  t.timestamps
@@ -34,4 +34,33 @@ class Create<%= message_class_name.pluralize %> < ActiveRecord::Migration<%= mig
34
34
  add_index :<%= message_table_name %>, :tool_call_id
35
35
  add_index :<%= message_table_name %>, [:<%= file_name %>_id, :created_at]
36
36
  end
37
+
38
+ private
39
+
40
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
41
+ # and SQLite aborts the migration on it.
42
+ def json_type
43
+ @json_type ||= postgres? ? :jsonb : :json
44
+ end
45
+
46
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
47
+ # JSON column can't have a default value"), which aborts the migration, so
48
+ # the column is created without one there. The gem assigns every JSON column
49
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
50
+ # would.
51
+ def json_default(value)
52
+ mysql? ? {} : { default: value }
53
+ end
54
+
55
+ def postgres?
56
+ adapter_name.include?("postgres")
57
+ end
58
+
59
+ def mysql?
60
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
61
+ end
62
+
63
+ def adapter_name
64
+ connection.adapter_name.to_s.downcase
65
+ end
37
66
  end
@@ -14,7 +14,7 @@ class CreateAgentContexts < ActiveRecord::Migration<%= migration_version %>
14
14
  t.text :instructions
15
15
 
16
16
  # Flexible options storage (input_params, model settings, etc.)
17
- t.jsonb :options, default: {}
17
+ t.column :options, json_type, **json_default({})
18
18
 
19
19
  # Tracing/debugging
20
20
  t.string :trace_id, index: true
@@ -29,4 +29,33 @@ class CreateAgentContexts < ActiveRecord::Migration<%= migration_version %>
29
29
  add_index :agent_contexts, [:agent_name, :action_name]
30
30
  add_index :agent_contexts, :created_at
31
31
  end
32
+
33
+ private
34
+
35
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
36
+ # and SQLite aborts the migration on it.
37
+ def json_type
38
+ @json_type ||= postgres? ? :jsonb : :json
39
+ end
40
+
41
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
42
+ # JSON column can't have a default value"), which aborts the migration, so
43
+ # the column is created without one there. The gem assigns every JSON column
44
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
45
+ # would.
46
+ def json_default(value)
47
+ mysql? ? {} : { default: value }
48
+ end
49
+
50
+ def postgres?
51
+ adapter_name.include?("postgres")
52
+ end
53
+
54
+ def mysql?
55
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
56
+ end
57
+
58
+ def adapter_name
59
+ connection.adapter_name.to_s.downcase
60
+ end
32
61
  end
@@ -23,10 +23,10 @@ class CreateAgentGenerations < ActiveRecord::Migration<%= migration_version %>
23
23
  t.integer :reasoning_tokens, default: 0
24
24
 
25
25
  # Tool calls made in this generation
26
- t.jsonb :tool_calls, default: []
26
+ t.column :tool_calls, json_type, **json_default([])
27
27
 
28
28
  # Raw response from the provider (for debugging)
29
- t.jsonb :raw_response
29
+ t.column :raw_response, json_type
30
30
 
31
31
  # Timing
32
32
  t.float :duration_seconds
@@ -38,7 +38,7 @@ class CreateAgentGenerations < ActiveRecord::Migration<%= migration_version %>
38
38
 
39
39
  # Provenance snapshot (agent/prompt/context checksums) captured at
40
40
  # generation time — see SolidAgent::HasContext#current_provenance
41
- t.jsonb :provenance, default: {}
41
+ t.column :provenance, json_type, **json_default({})
42
42
 
43
43
  t.timestamps
44
44
  end
@@ -48,4 +48,33 @@ class CreateAgentGenerations < ActiveRecord::Migration<%= migration_version %>
48
48
  add_index :agent_generations, :trace_id
49
49
  add_index :agent_generations, [:agent_context_id, :created_at]
50
50
  end
51
+
52
+ private
53
+
54
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
55
+ # and SQLite aborts the migration on it.
56
+ def json_type
57
+ @json_type ||= postgres? ? :jsonb : :json
58
+ end
59
+
60
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
61
+ # JSON column can't have a default value"), which aborts the migration, so
62
+ # the column is created without one there. The gem assigns every JSON column
63
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
64
+ # would.
65
+ def json_default(value)
66
+ mysql? ? {} : { default: value }
67
+ end
68
+
69
+ def postgres?
70
+ adapter_name.include?("postgres")
71
+ end
72
+
73
+ def mysql?
74
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
75
+ end
76
+
77
+ def adapter_name
78
+ connection.adapter_name.to_s.downcase
79
+ end
51
80
  end
@@ -14,18 +14,18 @@ class CreateAgentMessages < ActiveRecord::Migration<%= migration_version %>
14
14
  # For tool calls and results
15
15
  t.string :tool_call_id
16
16
  t.string :tool_name
17
- t.jsonb :tool_arguments, default: {}
18
- t.jsonb :tool_result
17
+ t.column :tool_arguments, json_type, **json_default({})
18
+ t.column :tool_result, json_type
19
19
 
20
20
  # For multimodal content (images, files)
21
- t.jsonb :attachments, default: []
21
+ t.column :attachments, json_type, **json_default([])
22
22
 
23
23
  # Metadata
24
- t.jsonb :metadata, default: {}
24
+ t.column :metadata, json_type, **json_default({})
25
25
 
26
26
  # Provenance snapshot + content checksum, populated automatically by
27
27
  # SolidAgent::HasContext when present
28
- t.jsonb :provenance, default: {}
28
+ t.column :provenance, json_type, **json_default({})
29
29
  t.string :content_checksum
30
30
 
31
31
  t.timestamps
@@ -35,4 +35,33 @@ class CreateAgentMessages < ActiveRecord::Migration<%= migration_version %>
35
35
  add_index :agent_messages, :tool_call_id
36
36
  add_index :agent_messages, [:agent_context_id, :created_at]
37
37
  end
38
+
39
+ private
40
+
41
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
42
+ # and SQLite aborts the migration on it.
43
+ def json_type
44
+ @json_type ||= postgres? ? :jsonb : :json
45
+ end
46
+
47
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
48
+ # JSON column can't have a default value"), which aborts the migration, so
49
+ # the column is created without one there. The gem assigns every JSON column
50
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
51
+ # would.
52
+ def json_default(value)
53
+ mysql? ? {} : { default: value }
54
+ end
55
+
56
+ def postgres?
57
+ adapter_name.include?("postgres")
58
+ end
59
+
60
+ def mysql?
61
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
62
+ end
63
+
64
+ def adapter_name
65
+ connection.adapter_name.to_s.downcase
66
+ end
38
67
  end
@@ -16,14 +16,14 @@ class CreateAgentRuns < ActiveRecord::Migration<%= migration_version %>
16
16
  t.string :status, null: false, default: "pending"
17
17
 
18
18
  t.text :input_prompt
19
- t.jsonb :input_params, default: {}
19
+ t.column :input_params, json_type, **json_default({})
20
20
  t.text :output
21
- t.jsonb :output_metadata, default: {}
21
+ t.column :output_metadata, json_type, **json_default({})
22
22
  t.text :error_message
23
23
 
24
24
  # Append-only progress events ({at, eid, kind, label, status,
25
25
  # detail, duration_ms}) streamed to pollers mid-run.
26
- t.jsonb :events, default: []
26
+ t.column :events, json_type, **json_default([])
27
27
 
28
28
  # 8-char fingerprint of the instructions the run executed under —
29
29
  # the cohort grouping key for instruction/model comparisons.
@@ -43,4 +43,33 @@ class CreateAgentRuns < ActiveRecord::Migration<%= migration_version %>
43
43
  add_index :agent_runs, :instructions_digest
44
44
  add_index :agent_runs, :created_at
45
45
  end
46
+
47
+ private
48
+
49
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
50
+ # and SQLite aborts the migration on it.
51
+ def json_type
52
+ @json_type ||= postgres? ? :jsonb : :json
53
+ end
54
+
55
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
56
+ # JSON column can't have a default value"), which aborts the migration, so
57
+ # the column is created without one there. The gem assigns every JSON column
58
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
59
+ # would.
60
+ def json_default(value)
61
+ mysql? ? {} : { default: value }
62
+ end
63
+
64
+ def postgres?
65
+ adapter_name.include?("postgres")
66
+ end
67
+
68
+ def mysql?
69
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
70
+ end
71
+
72
+ def adapter_name
73
+ connection.adapter_name.to_s.downcase
74
+ end
46
75
  end
@@ -4,9 +4,38 @@ class AddReasoningTo<%= @table_name.camelize %> < ActiveRecord::Migration[7.0]
4
4
  def change
5
5
  add_column :<%= @table_name %>, :<%= @content_column %>, :text
6
6
  add_column :<%= @table_name %>, :<%= @tokens_column %>, :integer, default: 0
7
- add_column :<%= @table_name %>, :<%= @metadata_column %>, :jsonb, default: {}
7
+ add_column :<%= @table_name %>, :<%= @metadata_column %>, json_type, **json_default({})
8
8
 
9
9
  add_index :<%= @table_name %>, :<%= @tokens_column %>,
10
10
  name: "index_<%= @table_name %>_on_<%= @tokens_column %>"
11
11
  end
12
+
13
+ private
14
+
15
+ # jsonb on PostgreSQL, json elsewhere: SQLite and MySQL have no jsonb type,
16
+ # and SQLite aborts the migration on it.
17
+ def json_type
18
+ @json_type ||= postgres? ? :jsonb : :json
19
+ end
20
+
21
+ # MySQL rejects a default on a JSON column outright ("BLOB, TEXT, GEOMETRY or
22
+ # JSON column can't have a default value"), which aborts the migration, so
23
+ # the column is created without one there. The gem assigns every JSON column
24
+ # it writes and reads them nil-safely, so a NULL reads as the empty default
25
+ # would.
26
+ def json_default(value)
27
+ mysql? ? {} : { default: value }
28
+ end
29
+
30
+ def postgres?
31
+ adapter_name.include?("postgres")
32
+ end
33
+
34
+ def mysql?
35
+ adapter_name.include?("mysql") || adapter_name.include?("trilogy")
36
+ end
37
+
38
+ def adapter_name
39
+ connection.adapter_name.to_s.downcase
40
+ end
12
41
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module SolidAgent
4
- VERSION = "0.2.1"
4
+ VERSION = "0.2.2"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: solid_agent
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.1
4
+ version: 0.2.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Justin Bowen
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2026-10-08 00:00:00.000000000 Z
11
+ date: 2026-10-31 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activeagent