Watch
0
0
Fork
You've already forked hyperhive
0

icons for the swarm's own forge accounts, and a default agent icon

The builder, ci-metrics and review-classifier forge accounts get an avatar: an
icon each in a hexagonal frame, the hyperhive logo when one is missing. The
controller sets them with a short-lived write:user token it mints for the
account, since only an account can set its own avatar.

An agent with no icon of its own shows a default agent icon in the swarm UI, a
robot head in a round frame, instead of the dimmed hyperhive mark.
This commit is contained in:
iris 2026-11-15 16:06:17 +01:00 • committed by mara
commit 91cf4d2ae1
4 changed files with 389 additions and 8 deletions

View file

@ -0,0 +1,24 @@
<svg width="300" height="300" viewBox="0 0 300 300" role="img" xmlns="http://www.w3.org/2000/svg">
<title>Agent</title>
<desc>The default agent icon: a robot head in line art, in a round frame</desc>
<defs>
<clipPath id="clip-a"><circle cx="150" cy="150" r="140"/></clipPath>
<filter id="glow-a" x="-30%" y="-30%" width="160%" height="160%"><feGaussianBlur stdDeviation="3" result="b"/><feMerge><feMergeNode in="b"/><feMergeNode in="SourceGraphic"/></feMerge></filter>
<radialGradient id="core-a"><stop offset="0" stop-color="#7aa7ff" stop-opacity="0.35"/><stop offset="1" stop-color="#7aa7ff" stop-opacity="0"/></radialGradient>
</defs>
<g clip-path="url(#clip-a)">
<rect x="0" y="0" width="300" height="300" fill="#060a1c"/>
<circle cx="150" cy="150" r="80" fill="url(#core-a)"/>
</g>
<circle cx="150" cy="150" r="140" fill="none" stroke="#7aa7ff" stroke-width="2.5"/>
<circle cx="150" cy="150" r="118" fill="none" stroke="#7aa7ff" stroke-width="0.8" opacity="0.4"/>
<g filter="url(#glow-a)" fill="none" stroke="#7aa7ff" stroke-width="3" stroke-linejoin="round" stroke-linecap="round">
<rect x="108" y="112" width="84" height="72" rx="14"/><path d="M150,112 L150,94"/><circle cx="150" cy="87" r="6"/>
<circle cx="130" cy="144" r="7"/><circle cx="170" cy="144" r="7"/><path d="M132,166 L168,166"/>
<rect x="98" y="132" width="10" height="28" rx="3"/><rect x="192" y="132" width="10" height="28" rx="3"/>
<path d="M104,214 Q150,184 196,214"/>
</g>
<g stroke="#7aa7ff" stroke-width="1.5" fill="none" opacity="0.8">
<path d="M44,44 L20,44 L20,68"/><path d="M256,44 L280,44 L280,68"/><path d="M44,256 L20,256 L20,232"/><path d="M256,256 L280,256 L280,232"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.7 KiB

View file

@ -0,0 +1,22 @@
<svg width="300" height="300" viewBox="0 0 300 300" role="img" xmlns="http://www.w3.org/2000/svg">
<title>builder</title>
<desc>The swarm builder service: a hammer over a cube, in a hexagonal frame</desc>
<defs>
<clipPath id="clip-b"><polygon points="150.0,10.0 271.2,80.0 271.2,220.0 150.0,290.0 28.8,220.0 28.8,80.0"/></clipPath>
<filter id="glow-b" x="-30%" y="-30%" width="160%" height="160%"><feGaussianBlur stdDeviation="3" result="b"/><feMerge><feMergeNode in="b"/><feMergeNode in="SourceGraphic"/></feMerge></filter>
<radialGradient id="core-b"><stop offset="0" stop-color="#ffb454" stop-opacity="0.35"/><stop offset="1" stop-color="#ffb454" stop-opacity="0"/></radialGradient>
</defs>
<g clip-path="url(#clip-b)">
<rect x="0" y="0" width="300" height="300" fill="#060a1c"/>
<circle cx="150" cy="150" r="80" fill="url(#core-b)"/>
</g>
<polygon points="150.0,10.0 271.2,80.0 271.2,220.0 150.0,290.0 28.8,220.0 28.8,80.0" fill="none" stroke="#ffb454" stroke-width="2.5" stroke-linejoin="round"/>
<polygon points="150.0,32.0 252.2,91.0 252.2,209.0 150.0,268.0 47.8,209.0 47.8,91.0" fill="none" stroke="#ffb454" stroke-width="0.8" opacity="0.4" stroke-linejoin="round"/>
<g filter="url(#glow-b)" fill="none" stroke="#ffb454" stroke-width="3" stroke-linejoin="round" stroke-linecap="round">
<g transform="rotate(-35 138 150)"><path d="M138,214 L138,118"/><rect x="110" y="96" width="56" height="26" rx="4"/><path d="M166,104 L182,98 M166,114 L182,120"/></g>
<path d="M196,196 l22,-12 l22,12 l0,26 l-22,12 l-22,-12 z M196,196 l22,12 l22,-12 M218,208 l0,26" stroke-width="2.2"/>
</g>
<g stroke="#ffb454" stroke-width="1.5" fill="none" opacity="0.8">
<path d="M44,44 L20,44 L20,68"/><path d="M256,44 L280,44 L280,68"/><path d="M44,256 L20,256 L20,232"/><path d="M256,256 L280,256 L280,232"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.8 KiB

View file

@ -0,0 +1,23 @@
<svg width="300" height="300" viewBox="0 0 300 300" role="img" xmlns="http://www.w3.org/2000/svg">
<title>ci-metrics</title>
<desc>The CI metrics service: a bar chart with a trend line, in a hexagonal frame</desc>
<defs>
<clipPath id="clip-m"><polygon points="150.0,10.0 271.2,80.0 271.2,220.0 150.0,290.0 28.8,220.0 28.8,80.0"/></clipPath>
<filter id="glow-m" x="-30%" y="-30%" width="160%" height="160%"><feGaussianBlur stdDeviation="3" result="b"/><feMerge><feMergeNode in="b"/><feMergeNode in="SourceGraphic"/></feMerge></filter>
<radialGradient id="core-m"><stop offset="0" stop-color="#3ddcc8" stop-opacity="0.35"/><stop offset="1" stop-color="#3ddcc8" stop-opacity="0"/></radialGradient>
</defs>
<g clip-path="url(#clip-m)">
<rect x="0" y="0" width="300" height="300" fill="#060a1c"/>
<circle cx="150" cy="150" r="80" fill="url(#core-m)"/>
</g>
<polygon points="150.0,10.0 271.2,80.0 271.2,220.0 150.0,290.0 28.8,220.0 28.8,80.0" fill="none" stroke="#3ddcc8" stroke-width="2.5" stroke-linejoin="round"/>
<polygon points="150.0,32.0 252.2,91.0 252.2,209.0 150.0,268.0 47.8,209.0 47.8,91.0" fill="none" stroke="#3ddcc8" stroke-width="0.8" opacity="0.4" stroke-linejoin="round"/>
<g filter="url(#glow-m)" fill="none" stroke="#3ddcc8" stroke-width="3" stroke-linejoin="round" stroke-linecap="round">
<path d="M92,210 L208,210"/>
<rect x="100" y="170" width="20" height="40" rx="2"/><rect x="130" y="148" width="20" height="62" rx="2"/><rect x="160" y="160" width="20" height="50" rx="2"/><rect x="190" y="122" width="20" height="88" rx="2"/>
<path d="M98,150 L134,128 L168,140 L206,100" stroke-width="2.2"/><circle cx="206" cy="100" r="4" fill="#3ddcc8"/>
</g>
<g stroke="#3ddcc8" stroke-width="1.5" fill="none" opacity="0.8">
<path d="M44,44 L20,44 L20,68"/><path d="M256,44 L280,44 L280,68"/><path d="M44,256 L20,256 L20,232"/><path d="M256,256 L280,256 L280,232"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

View file

@ -0,0 +1,23 @@
<svg width="300" height="300" viewBox="0 0 300 300" role="img" xmlns="http://www.w3.org/2000/svg">
<title>review-classifier</title>
<desc>The review classifier service: a pair of scales, in a hexagonal frame</desc>
<defs>
<clipPath id="clip-c"><polygon points="150.0,10.0 271.2,80.0 271.2,220.0 150.0,290.0 28.8,220.0 28.8,80.0"/></clipPath>
<filter id="glow-c" x="-30%" y="-30%" width="160%" height="160%"><feGaussianBlur stdDeviation="3" result="b"/><feMerge><feMergeNode in="b"/><feMergeNode in="SourceGraphic"/></feMerge></filter>
<radialGradient id="core-c"><stop offset="0" stop-color="#b48cff" stop-opacity="0.35"/><stop offset="1" stop-color="#b48cff" stop-opacity="0"/></radialGradient>
</defs>
<g clip-path="url(#clip-c)">
<rect x="0" y="0" width="300" height="300" fill="#060a1c"/>
<circle cx="150" cy="150" r="80" fill="url(#core-c)"/>
</g>
<polygon points="150.0,10.0 271.2,80.0 271.2,220.0 150.0,290.0 28.8,220.0 28.8,80.0" fill="none" stroke="#b48cff" stroke-width="2.5" stroke-linejoin="round"/>
<polygon points="150.0,32.0 252.2,91.0 252.2,209.0 150.0,268.0 47.8,209.0 47.8,91.0" fill="none" stroke="#b48cff" stroke-width="0.8" opacity="0.4" stroke-linejoin="round"/>
<g filter="url(#glow-c)" fill="none" stroke="#b48cff" stroke-width="3" stroke-linejoin="round" stroke-linecap="round">
<path d="M150,96 L150,206 M120,206 L180,206 M98,116 L202,116"/><circle cx="150" cy="96" r="5"/>
<path d="M98,116 L82,164 M98,116 L114,164 M202,116 L186,164 M202,116 L218,164"/>
<path d="M78,164 L118,164 Q98,190 78,164 Z M182,164 L222,164 Q202,190 182,164 Z"/>
</g>
<g stroke="#b48cff" stroke-width="1.5" fill="none" opacity="0.8">
<path d="M44,44 L20,44 L20,68"/><path d="M256,44 L280,44 L280,68"/><path d="M44,256 L20,256 L20,232"/><path d="M256,256 L280,256 L280,232"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.8 KiB