bannerbear 0.3.0 → 0.4.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: daa1514b2c5a5dddbef5836f7d64e3863932f4204e95a9625e7577b49dc70cad
4
- data.tar.gz: 7a33d8e33c07d6b39561e6fbf6b64defafbb7d593a777bd1524f7623528e861c
3
+ metadata.gz: 29845579050c36919da99fcffdf6ec4d5577dbe243fbf114812500636969b05d
4
+ data.tar.gz: e13320ddb5d91bb4f957cefa72eb4292035f07a0c11f804d6f2b8e5ead471189
5
5
  SHA512:
6
- metadata.gz: 20c731f7f32fab1d5afc6fc6f85134febaacd2a386b3e86c526a0c2134a099272f8d98560ca469129f3300286db7439ff8f374e8bd62d1217c985a23a770d06f
7
- data.tar.gz: df3b49048aa06fb412a3715228ae2af463701267636d00cdf8a7ede033c0a77e6d1c3bd7229cfb84fe1aef3ed1d79123741e23240cedeaa4895b096ed2bd34e2
6
+ metadata.gz: 2977c792ce41055fb8248ff4941ab5cccbdc2265c9589004124381c66163ddbcc1ab7a5a49ac811cbee75bef91780483fad8843e09cb26d1c5e5f520c37feaf0
7
+ data.tar.gz: 829e80632d438b428f6f8ed18d3009e0593fa480f96056200623f8b578658117fc5f626dbe5786e8333faa7adeafbb600659cb03a6b1c19d2878a0f6247970e1
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- bannerbear (0.2.0)
4
+ bannerbear (0.4.0)
5
5
  httparty
6
6
 
7
7
  GEM
data/README.md CHANGED
@@ -31,6 +31,10 @@ For the **legacy V2 API**, see [Usage](#usage) below — that section is unchang
31
31
  - [Account (V5)](#account-v5)
32
32
  - [Image Templates (V5)](#image-templates-v5)
33
33
  - [Images (V5)](#images-v5)
34
+ - [Animation Templates (V5)](#animation-templates-v5)
35
+ - [Animations (V5)](#animations-v5)
36
+ - [Workflows (V5)](#workflows-v5)
37
+ - [Workflow Runs (V5)](#workflow-runs-v5)
34
38
  - [Tools (V5)](#tools-v5)
35
39
  - [Assets (V5)](#assets-v5)
36
40
  - [Publications (V5)](#publications-v5)
@@ -132,6 +136,97 @@ bb.get_image("image uid")
132
136
  bb.list_images(page: 1)
133
137
  ```
134
138
 
139
+ ### Animation Templates (V5)
140
+
141
+ Animation templates render video instead of a still image. They carry a `frame_rate` and a `duration_seconds` in place of the image template's static canvas.
142
+
143
+ ```ruby
144
+ bb.list_animation_templates(page: 1)
145
+ bb.get_animation_template("template uid")
146
+
147
+ bb.create_animation_template(
148
+ name: "My Animation",
149
+ description: "Created from the API",
150
+ tags: ["promo"],
151
+ width: 1080,
152
+ height: 1080,
153
+ frame_rate: 30
154
+ )
155
+
156
+ bb.update_animation_template("template uid", name: "New Name", frame_rate: 60)
157
+ bb.delete_animation_template("template uid")
158
+ ```
159
+
160
+ ##### Options for `create_animation_template` / `update_animation_template`
161
+
162
+ - `name` *required for create* (`string`)
163
+ - `description` (`string`)
164
+ - `tags` (`array`)
165
+ - `width` / `height`: canvas size in pixels, 100–3000 (`integer`)
166
+ - `frame_rate`: `24`, `30`, or `60` (`integer`)
167
+
168
+ ### Animations (V5)
169
+
170
+ Rendering an animation is **always asynchronous** — there is no sync host for animations. Poll `get_animation` until the status is `"completed"` or `"failed"`, or subscribe to a webhook with the resource `"animation"`.
171
+
172
+ ```ruby
173
+ animation = bb.create_animation("animation template uid",
174
+ modifications: {
175
+ template: { width: 1080, height: 1080, fps: 30 },
176
+ objects: [
177
+ { name: "headline", text: "Hello World!" }
178
+ ]
179
+ },
180
+ formats: ["mp4"]
181
+ )
182
+
183
+ animation = bb.get_animation(animation["uid"])
184
+ animation["status"] # => "queued" | "rendering" | "completed" | "failed"
185
+ animation["files"] # => { "mp4" => "https://..." } when completed
186
+
187
+ bb.list_animations(page: 1)
188
+ ```
189
+
190
+ ##### Options for `create_animation`
191
+
192
+ - `modifications`: V5 modifications object (`hash`)
193
+ - `formats`: `["mp4"]` or `["mov"]`. Ignored when `transparent` is set — that always yields MOV (`array`)
194
+ - `metadata`: include any metadata to reference at a later point (`string`)
195
+
196
+ Template-level modification keys for animations: `width`, `height`, `fps` (`24`, `30`, or `60`), and `transparent`. Setting `transparent` renders on a transparent background and forces a MOV output, so the alpha channel survives.
197
+
198
+ ### Workflows (V5)
199
+
200
+ Workflows chain several steps into one named, re-runnable operation. They are read-only through the API — build them in the Bannerbear UI, then run them here.
201
+
202
+ ```ruby
203
+ bb.list_workflows(page: 1)
204
+
205
+ workflow = bb.get_workflow("workflow uid")
206
+ workflow["inputs"] # the inputs this workflow declares
207
+ workflow["steps"]
208
+ ```
209
+
210
+ ### Workflow Runs (V5)
211
+
212
+ A run is **asynchronous**. Poll `get_workflow_run` until the status is `"completed"` or `"failed"`, or subscribe to a webhook with the resource `"workflow_run"`.
213
+
214
+ ```ruby
215
+ run = bb.create_workflow_run("workflow uid",
216
+ inputs: { "headline" => "Hello World!", "photo" => "https://example.com/photo.jpg" }
217
+ )
218
+
219
+ run = bb.get_workflow_run(run["uid"])
220
+ run["status"] # => "queued" | "running" | "completed" | "failed"
221
+ run["outputs"] if run["status"] == "completed"
222
+
223
+ bb.list_workflow_runs(page: 1)
224
+ ```
225
+
226
+ ##### Options for `create_workflow_run`
227
+
228
+ - `inputs`: values for the workflow's declared inputs (`hash`)
229
+
135
230
  ### Tools (V5)
136
231
 
137
232
  Tools are standalone media operations that do not use a template. Every tool is **asynchronous**: the call returns a pending *tool job*. Poll `get_tool_job` until the status is `"completed"` or `"failed"`, or subscribe to a webhook with the resource `"tool_job"`.
@@ -153,11 +248,11 @@ Every tool also accepts an optional `metadata` string.
153
248
  | `remove_bg` | `image_url` | — | `image_url` |
154
249
  | `create_pdf` | `urls` | — | `pdf_url` |
155
250
  | `trim_video` | `video_url`, `start`, `end` | — | `video_url` |
156
- | `concat_videos` | `video_urls` | `width`, `height` | `video_url` |
251
+ | `concat_videos` | `video_urls` | `width`, `height`, `fps` | `video_url` |
157
252
  | `resize_video` | `video_url`, `width`, `height` | `fit` | `video_url` |
158
253
  | `crop_video` | `video_url`, `x`, `y`, `width`, `height` | — | `video_url` |
159
- | `overlay_video` | `base_video_url`, `overlay_video_url`, `x`, `y` | `scale`, `start` | `video_url` |
160
- | `overlay_image` | `video_url`, `image_url`, `x`, `y` | `opacity` | `video_url` |
254
+ | `overlay_video` | `base_video_url`, `overlay_video_url` | `position`, `margin`, `x`, `y`, `scale`, `start` | `video_url` |
255
+ | `overlay_image` | `video_url`, `image_url` | `position`, `margin`, `x`, `y`, `opacity` | `video_url` |
161
256
  | `subtitle_video` | `video_url` | `language`, `font`, `font_size`, `color`, `bold`, `italic`, `outline_color`, `outline_width`, `shadow_size`, `shadow_color`, `background_style`, `background_color`, `alignment` | `video_url` |
162
257
  | `generate_voiceover` | `text`, `voice` | — | `audio_url` |
163
258
  | `add_audio` | `video_url`, `audio_url`, `mode` | `volume`, `loop`, `ducking` | `video_url` |
@@ -166,11 +261,22 @@ Every tool also accepts an optional `metadata` string.
166
261
  | `apply_color_filter` | `video_url`, `filter` | — | `video_url` |
167
262
  | `soften_video` | `video_url`, `strength` | — | `video_url` |
168
263
 
264
+ Place the two overlay tools with **either** `position` (plus an optional `margin`) **or** `x`/`y` — not both. `position` accepts `top_left`, `top_center`, `top_right`, `center`, `bottom_left`, `bottom_center`, and `bottom_right`. `resize_video` accepts a `fit` of `cover` (crops), `contain` (letterboxes), or `blur` (fills the bars with a blurred copy).
265
+
169
266
  A few examples:
170
267
 
171
268
  ```ruby
172
269
  bb.remove_bg(image_url: "https://example.com/product.png")
173
270
 
271
+ # Corner placement, 40px in from each edge
272
+ bb.overlay_image(
273
+ video_url: "https://example.com/clip.mp4",
274
+ image_url: "https://example.com/logo.png",
275
+ position: "bottom_right",
276
+ margin: 40,
277
+ opacity: 0.8
278
+ )
279
+
174
280
  bb.subtitle_video(
175
281
  video_url: "https://example.com/talk.mp4",
176
282
  font: "montserrat",
@@ -253,13 +359,11 @@ Webhooks are managed as a first-class resource in V5 (instead of being a per-req
253
359
 
254
360
  ```ruby
255
361
  hook = bb.create_webhook(
256
- name: "my-webhook",
257
- url: "https://example.com/hook",
258
- resource: "image",
259
- event: "completed",
260
- status: "active",
261
- scope: "all_templates",
262
- templates: []
362
+ name: "my-webhook",
363
+ url: "https://example.com/hook",
364
+ resource: "image",
365
+ event: "completed",
366
+ status: "active"
263
367
  )
264
368
 
265
369
  # IMPORTANT: signing_key is ONLY returned in the create response. Store it now —
@@ -271,11 +375,9 @@ puts hook["signing_key"]
271
375
 
272
376
  - `name` *required* (`string`)
273
377
  - `url` *required* — the URL that receives the events (`string`)
274
- - `resource`: `"image"`, `"batch"`, or `"tool_job"` (`string`)
378
+ - `resource`: `"image"`, `"batch"`, `"tool_job"`, `"animation"`, or `"workflow_run"` (`string`)
275
379
  - `event`: `"all_events"`, `"completed"`, or `"failed"` (`string`)
276
380
  - `status`: `"active"` or `"disabled"` (`string`)
277
- - `scope`: `"all_templates"` or `"specific_templates"` (`string`)
278
- - `templates`: template UIDs, used when `scope` is `"specific_templates"` (`array`)
279
381
 
280
382
  CRUD:
281
383
 
@@ -286,8 +388,7 @@ bb.update_webhook("webhook uid",
286
388
  url: "https://example.com/hook",
287
389
  resource: "image",
288
390
  event: "completed",
289
- status: "active",
290
- scope: "all_templates"
391
+ status: "active"
291
392
  )
292
393
  bb.delete_webhook("webhook uid")
293
394
  bb.list_webhooks(page: 1)
@@ -47,6 +47,74 @@ module Bannerbear
47
47
  post_response "/images", payload.slice(:modifications, :formats, :scale, :dpi, :quality, :proxy, :metadata, :version).merge({:template => uid}), payload[:sync]
48
48
  end
49
49
 
50
+ # Animation Templates
51
+
52
+ def list_animation_templates(params = {})
53
+ get_response "/animation_templates?#{URI.encode_www_form(params.slice(:page))}"
54
+ end
55
+
56
+ def get_animation_template(uid)
57
+ get_response "/animation_templates/#{uid}"
58
+ end
59
+
60
+ def create_animation_template(payload = {})
61
+ post_response "/animation_templates", payload.slice(:name, :description, :tags, :width, :height, :frame_rate)
62
+ end
63
+
64
+ def update_animation_template(uid, payload = {})
65
+ patch_response "/animation_templates/#{uid}", payload.slice(:name, :description, :tags, :width, :height, :frame_rate)
66
+ end
67
+
68
+ def delete_animation_template(uid)
69
+ delete_response "/animation_templates/#{uid}"
70
+ end
71
+
72
+ # Animations
73
+ #
74
+ # Rendering is always asynchronous — there is no synchronous host for
75
+ # animations. Poll get_animation until the status is "completed" or
76
+ # "failed", or subscribe to a webhook with the resource "animation".
77
+
78
+ def list_animations(params = {})
79
+ get_response "/animations?#{URI.encode_www_form(params.slice(:page))}"
80
+ end
81
+
82
+ def get_animation(uid)
83
+ get_response "/animations/#{uid}"
84
+ end
85
+
86
+ def create_animation(uid, payload = {})
87
+ post_response "/animations", payload.slice(:modifications, :formats, :metadata).merge({:template => uid})
88
+ end
89
+
90
+ # Workflows
91
+
92
+ def list_workflows(params = {})
93
+ get_response "/workflows?#{URI.encode_www_form(params.slice(:page))}"
94
+ end
95
+
96
+ def get_workflow(uid)
97
+ get_response "/workflows/#{uid}"
98
+ end
99
+
100
+ # Workflow Runs
101
+ #
102
+ # A run is asynchronous. Poll get_workflow_run until the status is
103
+ # "completed" or "failed", or subscribe to a webhook with the resource
104
+ # "workflow_run".
105
+
106
+ def list_workflow_runs(params = {})
107
+ get_response "/workflow_runs?#{URI.encode_www_form(params.slice(:page))}"
108
+ end
109
+
110
+ def get_workflow_run(uid)
111
+ get_response "/workflow_runs/#{uid}"
112
+ end
113
+
114
+ def create_workflow_run(uid, payload = {})
115
+ post_response "/workflow_runs", payload.slice(:inputs).merge({:workflow => uid})
116
+ end
117
+
50
118
  # Tools
51
119
  #
52
120
  # Every tool is asynchronous: the POST returns a pending tool job. Poll
@@ -57,11 +125,13 @@ module Bannerbear
57
125
  "remove_bg" => [:image_url],
58
126
  "create_pdf" => [:urls],
59
127
  "trim_video" => [:video_url, :start, :end],
60
- "concat_videos" => [:video_urls, :width, :height],
128
+ "concat_videos" => [:video_urls, :width, :height, :fps],
61
129
  "resize_video" => [:video_url, :width, :height, :fit],
62
130
  "crop_video" => [:video_url, :x, :y, :width, :height],
63
- "overlay_video" => [:base_video_url, :overlay_video_url, :x, :y, :scale, :start],
64
- "overlay_image" => [:video_url, :image_url, :x, :y, :opacity],
131
+ # Place the overlay with either :position (+ optional :margin) or :x/:y,
132
+ # not both.
133
+ "overlay_video" => [:base_video_url, :overlay_video_url, :x, :y, :position, :margin, :scale, :start],
134
+ "overlay_image" => [:video_url, :image_url, :x, :y, :position, :margin, :opacity],
65
135
  "subtitle_video" => [:video_url, :language, :font, :font_size, :color, :bold, :italic,
66
136
  :outline_color, :outline_width, :shadow_size, :shadow_color,
67
137
  :background_style, :background_color, :alignment],
@@ -158,11 +228,11 @@ module Bannerbear
158
228
  end
159
229
 
160
230
  def create_webhook(payload = {})
161
- post_response "/webhooks", payload.slice(:name, :url, :resource, :event, :status, :scope, :templates)
231
+ post_response "/webhooks", payload.slice(:name, :url, :resource, :event, :status)
162
232
  end
163
233
 
164
234
  def update_webhook(uid, payload = {})
165
- patch_response "/webhooks/#{uid}", payload.slice(:name, :url, :resource, :event, :status, :scope, :templates)
235
+ patch_response "/webhooks/#{uid}", payload.slice(:name, :url, :resource, :event, :status)
166
236
  end
167
237
 
168
238
  def delete_webhook(uid)
@@ -1,3 +1,3 @@
1
1
  module Bannerbear
2
- VERSION = "0.3.0"
2
+ VERSION = "0.4.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: bannerbear
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.0
4
+ version: 0.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jon Yongfook
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2026-08-13 00:00:00.000000000 Z
11
+ date: 2026-08-17 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: httparty