- Replace the plain text empty placeholder with the same illustration +
title + subtitle layout used by tb-iot-hub-empty-state in the browse
component (no-data illustration, 18/500 title, 14/0.54 body).
- Add a no-installed-items-text locale key ("Try adjusting your search
or filters.").
- Make the table wrapper a flex column and place the empty state and
loading spinner inside it as flex-1 children so both vertically
centre below the sticky header instead of pinning to the top.
- Add a dedicated alarm-rules hero SVG (560×276) and point the
ALARM_RULE PAGE_CONFIG to it instead of the stale dashboards image.
- Replace the calculated-fields and devices hero SVGs with the
updated illustrations exported from the design.
The Installed / IoT Hub toggle now carries icon templates that don't
collapse cleanly into a mat-select on xs viewports — keep the toggle
buttons at every breakpoint instead.
- Add a `template?: TemplateRef<any>` slot to ToggleHeaderOption +
ToggleOption so callers can render arbitrary content inside a
toggle (the existing string label / error icon path stays the
default).
- Use it in the dashboard widget-select header to render a tb-icon
next to each label: now_widgets for Installed, hub for IoT Hub.
- Style the top-level toggle with a 42px pill (8px radius, white-15
border, 40px buttons, 36px line-height, 500 weight) so the icon +
label sit comfortably and contrast against the primary toolbar.
- Apply the same DEVICE → SOLUTION_TEMPLATE → WIDGET → CALCULATED_FIELD →
ALARM_RULE → RULE_CHAIN ordering to the home search popup and the
search component, so all entry points group results consistently.
- Drop DASHBOARD entirely from the search component (route, installed
counts, type order) and filter it out of the home search popup
groups.
- Add ALARM_RULE to the search component (compact-card layout, route
alarm-rules, installed-count handling).
- Remove the "Add from IoT Hub" header action and addDashboardFromIotHub
handler from the dashboards page, plus the now-unused
IotHubActionsService / ItemType imports and constructor injection.
- Reorder category cards to match the design: Devices → Solutions →
Widgets → Calculated Fields → Alarm Rules → Rule Chains.
- Replace gradient card backgrounds with the design's flat per-card
colors and swap stale SVG illustrations for fresh PNG renders
exported from the design.
- Implement the design's hover interaction (200ms ease-out): the card
image scales up by 5.4 % (matching the 387×148 → 408×156 frame
growth) and a chevron slides in next to the title.
- Add the "Most popular in IoT Hub" h2 plus a full-width bleed divider
between the category cards and the popular sections.
- Drop the "Popular " prefix from popular section headers and use
item.type-*-plural translations directly. Remove the now-unused
iot-hub.popular-* locale keys.
- Reorder popular sections to match the design's order.
- Switch the IoT Hub menu and breadcrumb icons from `store` to `hub`.
- Restructure HTML Container settings into a mat-tab-group (Resources /
HTML / CSS / JavaScript) instead of a single resources expansion panel
followed by stacked editor blocks. Each editor tab uses [fillHeight]
so the editors fill the panel.
- Wire fill-height plumbing: tb-widget-settings host h-full, basic and
advanced settings @HostBinding('style.height')='100%', advanced panel
switched from inline height:100% to flex-1, mat-content height:100%.
- Register html_container in widget_bundles/html_widgets.json so the
widget appears in the HTML Widgets bundle.
- Replace the placeholder html-card image reference with a dedicated
html-container.png asset and embedded data.
- Add 'JavaScript' translation key for the new tab label.
- Replace per-type icon SVG sets with single composite cluster SVGs
exported from the updated design (devices, solutions, widgets,
calculated fields, alarm rules, rule chains).
- Add soft per-type colored glow blobs (Ellipse 399 / 400, opacity 0.16,
filter: blur(120px)) at the page level so the wash spans the whole
page background instead of being clipped by the hero.
- Fix hero icons transition: switch from vertical translate to a uniform
scale around the hero centre so icons burst from / collapse to the
centre on enter/exit, matching the design prototype.
- Drive blob fill via [style.color] + currentColor for smooth per-type
tint cross-fades.
Remove the no-longer-used ViewContainerRef injection and the commented-
out fallback branches now that initAngularComponent uses the
angularContainer view container exclusively.
- Group tomcat, commons-lang3 version properties under spring-boot.version
- Drop thymeleaf override (PE-only dependency, not present in CE)
- Drop lz4 plumbing: kafka-clients 3.9.2 and cassandra-all 5.0.7 now transitively ship at.yawk.lz4:lz4-java, making the Dec 2025 CVE hack obsolete
- Fill description and tags for the HTML Container widget type JSON.
- Add basic config component (plain HTML / Angular mode editor).
- Add advanced settings component and shared common settings.
New static widget that replaces the dashboard layout with configurable
HTML, CSS, and JavaScript and exposes the WidgetContext to the user
script. Use for custom complex visualizations or actions when system
widgets are not enough.
The base image thingsboard/openjdk17:bookworm-slim ships a customized
/etc/java-17-openjdk/security/java.security. When apt-get install pulls
in a newer openjdk-17-jre-headless to satisfy cassandra's java11-runtime
dependency, dpkg blocks on a non-interactive conffile prompt and the
build fails. The ensuing "cassandra depends on java11-runtime" error is
just the cascade from openjdk-17-jre-headless never finishing configure.
Pass --force-confdef --force-confold so dpkg silently keeps the base
image's customized conffile and the upgrade completes.
Redesigned the top search input on iot-hub-browse, iot-hub-search, and
the installed-items page to share a single page-level field style:
56px tall, 8px radius, 1px light border, white background, 16px input
text, with a 40px round trailing action that shows a non-clickable
search icon when empty and switches to a clickable close icon-button
when text is entered.
Layout updates:
- Browse: search input + sort button now share a single row at the top
(sort moved out of the filter-chips row); the filter-toggle button
moved to the filter-chips row right-aligned (mobile only). Sort row
is 32px tall with 16/12px vertical margin and zero chip margins.
- Search: input fills the row up to the sort button; placeholder is
'Search published items...' on creator profiles, 'Search...' otherwise.
- Browse search input placeholder is per-type ('Search widgets...',
'Search solution templates...', etc.) via searchPlaceholderKey getter.
- Installed items: filter button + chips on a top row, search input on
a dedicated row below; chips margin-top/bottom zeroed.
Common SCSS:
- Added tb-iot-hub-page-search-container / -input / -action mixins to
_iot-hub-common.scss; browse, search, and installed-items pull them
via @include.
- Locale: new iot-hub.search-published-items key.
* feat(iot-hub): scaffold ALARM_RULE item type and CREATOR_VISIBLE_ITEM_TYPES
* feat(iot-hub): wire ALARM_RULE through browse, item card, detail dialog, installed items, and install dialog
* feat(iot-hub): reorder home cards, hide Dashboards, add Alarm Rules
* feat(iot-hub): scaffold ALARM_RULE descriptor and reject install with v4.3 upgrade hint
Registers AlarmRuleInstalledItemDescriptor in the Jackson polymorphism so
4.2 can browse Alarm Rule items from the marketplace without descriptor
deserialization failures.
The install handler explicitly rejects ALARM_RULE with a friendly message
asking the user to upgrade to v4.3+. The full install/update/delete
implementation depends on CalculatedFieldType.ALARM (added in v4.3) and
will land once master is merged into this branch.
* feat(iot-hub): hide redundant Type filter on Alarm Rules browse
* feat(iot-hub): show v4.3 update info dialog directly when installing an Alarm Rule
Relocate the iot_hub_installed_item CREATE TABLE statement from the
basic schema_update.sql to the LTS cumulative schema_update.sql, where
it belongs for this LTS line.
STRING and PASSWORD fields in SHOW_FORM gain optional randomGenerator,
randomSize, and randomByDefault properties. randomByDefault pre-fills the
field on form open; an autorenew icon (next to the eye toggle on PASSWORD)
regenerates on demand. Reuses generateSecret from @core/utils.
Two new markdown placeholders, ${product.button} and ${datasheet.button},
render as inline buttons linking to the manufacturer's product page and
datasheet. They work in SHOW_INSTRUCTION steps (install dialog) and in
overview.md (detail dialog readme). URLs come from device-info.json's
productURL/datasheetURL — install reads from the parsed package, detail
dialog reads from item.dataDescriptor.
The guard around iterating createdEntityIds was checking isEmpty()
instead of !isEmpty(), so entity deletion was skipped whenever there
was actually data to clean up.
SolutionTemplateInstalledItemDescriptor and SolutionInstallResponse now
carry tenantTelemetryKeys and tenantAttributeKeys lists. SolutionService
.deleteSolution takes the full descriptor (instead of just the
created-entity list) so uninstall can also clean up tenant-scoped
telemetry/attributes. Update IotHub install descriptor population and
delete call sites; force-update path logs and continues if delete throws.
Install and update dialogs now render error details via tb-markdown
when the failing item is a SOLUTION_TEMPLATE, falling back to the plain
text block for other item types. Supports the rich instruction-style
error messages returned by the solution install flow.
Propagate User through SolutionInstallContext, DefaultSolutionService,
and TbCalculatedFieldService.delete so non-security-context callers can
drive solution installs and calculated-field cleanup. Pass
TenantSolutionTemplateInstructions into the context constructor so the
caller controls instruction state.