ballistics-engine 0.36.0 → 0.36.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: f2879a18b72e21e57061c85dcbe920e5457590522135f7b0285a14902b842498
4
- data.tar.gz: 47be0e871d522917fe87eaf49167388b7824204114d9149144ae7151e82de179
3
+ metadata.gz: f88aa4eaac01368235e15f61a52b72e1b8115309919889ba156ee33080a829ef
4
+ data.tar.gz: 101737d4006e8909bc665a1a34b05fc52d9112f1838a9e515e6a629140f733c3
5
5
  SHA512:
6
- metadata.gz: b7742cc9824f85e478f4484e2ce7cbda7e8019ac4112ea436304b65f471d9e19944134d69dbe681a18a91651e822fca50fef767cad6af8a1d4da42e3501febd9
7
- data.tar.gz: 3373dfd90aa6d1d08f03a34b977f56e01746e9373d9f96e199bd5e10a84ccb59dbbd6fd935e319b227a3779a49400749c9456fda7ddaaebcba71f938712de8e0
6
+ metadata.gz: bbca3d10f6cab28fd96619daeebc59dc96f418329ef44286c2ce8dac0defb9e3de9136659f7e5a72fbfbc852f3a85029fe349eb68c741cb95c38a7a560ff70b6
7
+ data.tar.gz: 7e1829e71d9e15a17c4cdfe3105e35d497ef633d6f56ae68e85f0eff9bed896ab237d19c71b57357a723cce83b940719c4a7c829315dbec8d952ceca02323070
data/Cargo.lock CHANGED
@@ -43,9 +43,9 @@ checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8"
43
43
 
44
44
  [[package]]
45
45
  name = "ballistics-engine"
46
- version = "0.36.0"
46
+ version = "0.36.1"
47
47
  source = "registry+https://github.com/rust-lang/crates.io-index"
48
- checksum = "23568cd57f14599a74cb75d839836007a5ec9659c29e583897a378275e630976"
48
+ checksum = "8d9c76ab7ca6a459f91b3876b61955b3a366615ab04947e7aa220efde77ef520"
49
49
  dependencies = [
50
50
  "getrandom",
51
51
  "js-sys",
@@ -65,7 +65,7 @@ dependencies = [
65
65
 
66
66
  [[package]]
67
67
  name = "ballistics_engine_rb"
68
- version = "0.36.0"
68
+ version = "0.36.1"
69
69
  dependencies = [
70
70
  "ballistics-engine",
71
71
  "magnus",
data/Cargo.toml CHANGED
@@ -3,7 +3,7 @@
3
3
  # rake-compiler/rb-sys cargo-metadata lookup resolves (newer rb-sys does not
4
4
  # normalize hyphens). The published gem name is set in the gemspec, independent.
5
5
  name = "ballistics_engine_rb"
6
- version = "0.36.0"
6
+ version = "0.36.1"
7
7
  edition = "2021"
8
8
  authors = ["Alex Jokela <email@tinycomputers.io>"]
9
9
  description = "Ruby bindings for ballistics-engine"
@@ -15,7 +15,10 @@ name = "ballistics_engine_rb"
15
15
  crate-type = ["cdylib"]
16
16
 
17
17
  [dependencies]
18
- ballistics-engine = { version = "0.36.0", default-features = false }
18
+ # `bridge` exposes ballistics_engine::bridge::bridge_call the versioned JSON command
19
+ # bridge that reaches every engine command from one string-in/string-out entry point.
20
+ # It is pure serde/serde_json (already core engine deps), so it adds no new dependencies.
21
+ ballistics-engine = { version = "0.36.1", default-features = false, features = ["bridge"] }
19
22
  magnus = "0.8"
20
23
 
21
24
  [profile.release]
data/README.md CHANGED
@@ -10,6 +10,8 @@ High-performance ballistics calculations library for Ruby, powered by Rust.
10
10
  - **Atmospheric Effects** - Temperature, pressure, humidity, and altitude compensation
11
11
  - **Unit Conversion** - Automatic handling of imperial/metric conversions
12
12
  - **High Performance** - Rust-based calculations for maximum speed
13
+ - **JSON Command Bridge** - `bridge_call` reaches every engine command (solve, dope
14
+ cards, profiles, truing) through one versioned JSON envelope
13
15
 
14
16
  ## Installation
15
17
 
@@ -133,6 +135,62 @@ keys** in imperial units. Unknown keys are ignored; only the seven marked requir
133
135
  y=drop, z=windage, in yards). Present when enabled: `sampled_points`, `aerodynamic_jump`,
134
136
  `angular_state`, `max_yaw_angle_rad`, `max_precession_angle_rad`, `min_pitch_damping`, `transonic_mach`.
135
137
 
138
+ ### `BallisticsEngine.bridge_call(request_json) => String`
139
+
140
+ Raw pass-through to the engine's versioned JSON command bridge: one full request
141
+ envelope in as a String, one full response envelope out as a String. Nothing is parsed
142
+ and nothing is raised — the bridge never panics and reports every failure in band as
143
+ `{"ok":false,"error":{...}}`, so the caller owns the envelope.
144
+
145
+ ```ruby
146
+ require "json"
147
+
148
+ def bridge(command, request)
149
+ JSON.parse(BallisticsEngine.bridge_call(
150
+ JSON.generate("api_version" => 1, "command" => command, "request" => request)
151
+ ))
152
+ end
153
+
154
+ bridge("meta.version", {})
155
+ # => {"ok"=>true, "api_version"=>1, "engine_version"=>"0.36.1",
156
+ # "command"=>"meta.version", "result"=>{"engine_version"=>"0.36.1"}}
157
+
158
+ # Every command reachable in this build:
159
+ bridge("meta.capabilities", {})["result"]["commands"]
160
+ # => ["meta.capabilities", "meta.version", "solve", "card.come_ups", "card.range_table",
161
+ # "card.wind", "profile.validate", "profile.normalize", "true.fit", "true.wind",
162
+ # "true.tall_target", "true.dsf", "true.plan", "true.dial_plan", "bc5d.info"]
163
+ ```
164
+
165
+ `command` is one of the names `meta.capabilities` reports; `request` is that command's
166
+ own document. `solve` takes a [solve-json v1](https://github.com/ajokela/ballistics-engine/blob/main/docs/SOLVE_JSON_V1.md)
167
+ document — strict SI units, unknown fields rejected with a JSON path — and is the only
168
+ way to reach fields the hash API above has no key for, such as
169
+ `atmosphere.pressure_reference` (QNH altimeter settings) and
170
+ `corrections.bc5d_table_path`:
171
+
172
+ ```ruby
173
+ r = bridge("solve", {
174
+ "schema_version" => 1,
175
+ "projectile" => { "mass_kg" => 0.01134, "diameter_m" => 0.00782,
176
+ "drag_model" => "G7", "ballistic_coefficient" => 0.243 },
177
+ "rifle" => { "muzzle_velocity_mps" => 823.0, "sight_height_m" => 0.05 },
178
+ "shot" => { "max_range_m" => 1000.0, "zero_distance_m" => 100.0 },
179
+ "atmosphere" => { "altitude_m" => 1200.0, "pressure_pa" => 101_325.0,
180
+ "pressure_reference" => "qnh" },
181
+ "wind" => { "speed_mps" => 4.4704, "direction_from_rad" => Math::PI / 2 },
182
+ "solver" => { "method" => "rk45" },
183
+ "effects" => { "wind_shear_model" => "power_law" },
184
+ "sampling" => { "interval_m" => 100.0 }
185
+ })
186
+ r["ok"] # => true
187
+ r["result"]["samples"].last["windage_m"] # => -2.7677...
188
+ ```
189
+
190
+ The `pdf` / `card.pdf` and `profile.import_a7p` commands are compiled out of this gem
191
+ (it builds the engine with `default-features = false`); `meta.capabilities` lists only
192
+ what this build can actually run.
193
+
136
194
  ### `BallisticsEngine.calculate_zero_angle(hash) => hash`
137
195
 
138
196
  Same bullet keys as `solve`, plus **required** `target_distance_yards` (and optional
@@ -4,7 +4,7 @@ require "ballistics_engine_rb"
4
4
 
5
5
  # Top-level module for the BallisticsEngine gem
6
6
  module BallisticsEngine
7
- VERSION = "0.36.0"
7
+ VERSION = "0.36.1"
8
8
 
9
9
  class Error < StandardError; end
10
10
  end
data/src/lib.rs CHANGED
@@ -416,11 +416,38 @@ fn monte_carlo(ruby: &magnus::Ruby, h: RHash) -> Result<RHash, Error> {
416
416
  Ok(out)
417
417
  }
418
418
 
419
+ /// Raw pass-through to the engine's versioned JSON command bridge.
420
+ ///
421
+ /// One string in (a full request envelope), one string out (a full response envelope).
422
+ /// This is deliberately NOT a typed wrapper: `ballistics_engine::bridge::bridge_call`
423
+ /// dispatches every bridge command — `meta.capabilities`, `meta.version`, `solve`,
424
+ /// the `card.*` family, `profile.*`, the `true.*` truing family, `bc5d.info` — from
425
+ /// one entry point, so mirroring the per-command DTOs here would be a large surface
426
+ /// that goes stale on every engine release. `solve` in particular is this binding's
427
+ /// only route to `corrections.bc5d_table_path` and `atmosphere.pressure_reference`,
428
+ /// neither of which the hash-based `solve` above reaches; it also reaches
429
+ /// `effects.wind_shear_model` as a validated enum (the hash surface has its own
430
+ /// `enable_wind_shear` / `wind_shear_model` pair, which accepts any string and maps
431
+ /// an unrecognized one to the power law rather than reporting it).
432
+ ///
433
+ /// Failures are IN BAND: the bridge is `catch_unwind`-guarded, never panics, and
434
+ /// reports every error as `{"ok":false,"error":{...}}` inside the returned JSON.
435
+ /// So this raises nothing and parses nothing — the caller owns the envelope and
436
+ /// decides whether to `JSON.parse` it.
437
+ ///
438
+ /// env = { api_version: 1, command: "meta.version", request: {} }
439
+ /// JSON.parse(BallisticsEngine.bridge_call(JSON.generate(env)))
440
+ /// # => {"ok"=>true, "api_version"=>1, "engine_version"=>"0.36.1", ...}
441
+ fn bridge_call(request_json: String) -> String {
442
+ ballistics_engine::bridge::bridge_call(&request_json)
443
+ }
444
+
419
445
  #[magnus::init]
420
446
  fn init(ruby: &magnus::Ruby) -> Result<(), Error> {
421
447
  let module = ruby.define_module("BallisticsEngine")?;
422
448
  module.define_module_function("solve", function!(solve_trajectory, 1))?;
423
449
  module.define_module_function("calculate_zero_angle", function!(calculate_zero_angle, 1))?;
424
450
  module.define_module_function("monte_carlo", function!(monte_carlo, 1))?;
451
+ module.define_module_function("bridge_call", function!(bridge_call, 1))?;
425
452
  Ok(())
426
453
  }
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ballistics-engine
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.36.0
4
+ version: 0.36.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Alex Jokela