Updated Models API to use default palette

Necessary to be in sync with the UI by supporting default palettes via the API. This also removes the use of palette names since using the default palette is preferred now.

Issue: 303
Milestone: minor
This commit is contained in:
Brooke Kuhlmann
2026-04-21 14:57:30 -06:00
parent 4216f49295
commit 5c6c380b21
6 changed files with 33 additions and 45 deletions
+1 -1
View File
@@ -13,6 +13,7 @@ module Terminus
params do
required(:model).filled(:hash) do
optional(:default_palette_id).maybe :integer
required(:name).filled :string
required(:label).filled :string
optional(:description).maybe :string
@@ -23,7 +24,6 @@ module Terminus
optional(:rotation).filled :integer
optional(:offset_x).filled :integer
optional(:offset_y).filled :integer
optional(:palette_names).maybe :array
optional(:css).maybe :hash
optional(:width).filled :integer
optional(:height).filled :integer
+1 -1
View File
@@ -15,6 +15,7 @@ module Terminus
required(:id).filled :integer
required(:model).filled(:hash) do
optional(:default_palette_id).maybe :integer
optional(:name).filled :string
optional(:label).filled :string
optional(:description).maybe :string
@@ -25,7 +26,6 @@ module Terminus
optional(:rotation).filled :integer
optional(:offset_x).filled :integer
optional(:offset_y).filled :integer
optional(:palette_names).maybe :array
optional(:css).maybe :hash
optional(:width).filled :integer
optional(:height).filled :integer
+1 -1
View File
@@ -6,6 +6,7 @@ module Terminus
# A model serializer for specific keys.
class Model
KEYS = %i[
default_palette_id
id
name
label
@@ -18,7 +19,6 @@ module Terminus
offset_x
offset_y
scale_factor
palette_names
css
width
height
+22 -34
View File
@@ -675,7 +675,7 @@ You'll get an empty hash when there is nothing to delete.
Provides model information which is the core specification for devices and screens. Models are also differentiated by `kind` which can be:
* `trmnl`: Originates from our {core_link} server and is part of the synchronization process provided by the model link:/doc/jobs.adoc[Job].
* `byod`, `kindle`, `tidybit`, `trmnl`: Originates from our {core_link} server and is part of the synchronization process provided by the model link:/doc/jobs.adoc[Job].
* `terminus`: Originates from Terminus only.
* `+*+`: Additional types exist for custom devices such as Kindle, BYOD, and so forth.
@@ -707,6 +707,7 @@ curl "https://localhost:2443/api/models/1" \
{
"data": [
{
"default_palette_id": 1,
"id": 1,
"name": "v2",
"label": "TRMNL X",
@@ -719,11 +720,6 @@ curl "https://localhost:2443/api/models/1" \
"offset_x": 0,
"offset_y": 0,
"scale_factor": 1.8,
"palette_names": [
"gray-16",
"gray-4",
"bw"
],
"css": {
"classes": {
"size": "screen--lg",
@@ -767,6 +763,7 @@ curl "https://localhost:2443/api/models/1" \
# Single model.
"data": {
"default_palette_id": 1,
"id": 1,
"name": "v2",
"label": "TRMNL X",
@@ -779,11 +776,6 @@ curl "https://localhost:2443/api/models/1" \
"offset_x": 0,
"offset_y": 0,
"scale_factor": 1.8,
"palette_names": [
"gray-16",
"gray-4",
"bw"
],
"css": {
"classes": {
"size": "screen--lg",
@@ -837,23 +829,25 @@ curl -X "POST" "https://localhost:2443/api/models" \
-H 'Content-Type: application/json' \
-d $'{
"model": {
name: "demo",
label: "Demo",
description: "A demonstration.",
mime_type: "image/png",
bit_depth: 2,
colors: 4,
palette_names: ["bw"],
css: {"classes" => {"size" => "screen--md"}},
scale_factor: 1.5,
rotation: 90,
offset_x: 10,
offset_y: 15,
width: 800,
height: 480
"default_palette_id": 1,
"name": "demo",
"label": "Demo",
"description": "A demonstration.",
"mime_type": "image/png",
"bit_depth": 2,
"colors": 4,
"css": {"classes" => {"size" => "screen--md"}},
"scale_factor": 1.5,
"rotation": 90,
"offset_x": 10,
"offset_y": 15,
"width": 800,
"height": 480
}
}'
----
The `default_palette_id` key is optional. You can also use `nil` for the value to remove the default palette (although, using a default palette is recommended). At the moment, there isn't an API for palettes (this will be added in the future).
====
.POST Response
@@ -863,6 +857,7 @@ curl -X "POST" "https://localhost:2443/api/models" \
----
{
"data": {
"default_palette_id": 1,
"id": 1,
"name": "demo",
"label": "Demo",
@@ -875,9 +870,6 @@ curl -X "POST" "https://localhost:2443/api/models" \
"offset_x": 10,
"offset_y": 15,
"scale_factor": 1.5,
"palette_names": [
"bw"
],
"css": {
"classes": {
"size": "screen-md"
@@ -917,6 +909,7 @@ You can change a single attribute or multiple attributes at once. All attributes
----
{
"data": {
"default_palette_id": nil,
"id": 1,
"name": "demo",
"label": "Demo",
@@ -929,9 +922,6 @@ You can change a single attribute or multiple attributes at once. All attributes
"offset_x": 10,
"offset_y": 15,
"scale_factor": 1.5,
"palette_names": [
"bw"
],
"css": {
"classes": {
"size": "screen-md"
@@ -965,6 +955,7 @@ curl -X "DELETE" "https://localhost:2443/api/models/2" \
----
{
"data": {
"default_palette_id": 1,
"id": 1,
"name": "demo",
"label": "Demo",
@@ -977,9 +968,6 @@ curl -X "DELETE" "https://localhost:2443/api/models/2" \
"offset_x": 10,
"offset_y": 15,
"scale_factor": 1.5,
"palette_names": [
"bw"
],
"css": {
"classes": {
"size": "screen-md"
+1 -1
View File
@@ -9,6 +9,7 @@ RSpec.describe Terminus::Serializers::Model do
let :attributes do
{
default_palette_id: 1,
name: "t1",
label: "T1",
description: nil,
@@ -20,7 +21,6 @@ RSpec.describe Terminus::Serializers::Model do
offset_x: 10,
offset_y: 15,
scale_factor: 1.5,
palette_names: ["bw"],
css: {"classes" => {"size" => "screen--md"}},
width: 800,
height: 480,
+7 -7
View File
@@ -5,7 +5,8 @@ require "hanami_helper"
RSpec.describe "/api/models", :db do
include_context "with JWT"
let(:model) { Factory[:model] }
let(:palette) { Factory[:palette] }
let(:model) { Factory[:model, default_palette_id: palette.id] }
let :attributes do
{
@@ -19,7 +20,6 @@ RSpec.describe "/api/models", :db do
offset_x: 10,
offset_y: 15,
scale_factor: 1.5,
palette_names: ["bw"],
css: {"classes" => {"size" => "small"}},
width: 800,
height: 480
@@ -37,6 +37,7 @@ RSpec.describe "/api/models", :db do
expect(json_payload).to match(
data: [
{
default_palette_id: palette.id,
id: model.id,
label: model.label,
name: model.name,
@@ -49,7 +50,6 @@ RSpec.describe "/api/models", :db do
offset_x: 0,
offset_y: 0,
scale_factor: 1.0,
palette_names: [],
css: {},
width: 800,
height: 480,
@@ -77,6 +77,7 @@ RSpec.describe "/api/models", :db do
expect(json_payload).to match(
data: {
default_palette_id: palette.id,
id: model.id,
label: model.label,
name: model.name,
@@ -89,7 +90,6 @@ RSpec.describe "/api/models", :db do
offset_x: 0,
offset_y: 0,
scale_factor: 1.0,
palette_names: [],
css: {},
width: 800,
height: 480,
@@ -116,6 +116,7 @@ RSpec.describe "/api/models", :db do
expect(json_payload).to match(
data: {
default_palette_id: nil,
id: kind_of(Integer),
label: "Test",
name: "test",
@@ -128,7 +129,6 @@ RSpec.describe "/api/models", :db do
offset_x: 10,
offset_y: 15,
scale_factor: 1.5,
palette_names: ["bw"],
css: {classes: {size: "small"}},
width: 800,
height: 480,
@@ -171,6 +171,7 @@ RSpec.describe "/api/models", :db do
expect(json_payload).to match(
data: {
default_palette_id: palette.id,
id: model.id,
label: "Test",
name: "test",
@@ -183,7 +184,6 @@ RSpec.describe "/api/models", :db do
offset_x: 10,
offset_y: 15,
scale_factor: 1.5,
palette_names: ["bw"],
css: {classes: {size: "small"}},
width: 800,
height: 480,
@@ -222,6 +222,7 @@ RSpec.describe "/api/models", :db do
expect(json_payload).to match(
data: {
default_palette_id: palette.id,
id: model.id,
label: model.label,
name: model.name,
@@ -234,7 +235,6 @@ RSpec.describe "/api/models", :db do
offset_x: 0,
offset_y: 0,
scale_factor: 1.0,
palette_names: [],
css: {},
width: 800,
height: 480,