addons icon indicating copy to clipboard operation
addons copied to clipboard

Piper TTS fails on long messages

Open joshuazd opened this issue 2 years ago • 20 comments

Describe the issue you are experiencing

When trying to using Piper to generate a long tts message (on Sonos speakers, in my case), the audio never plays on the speaker. This seems to happen at around 35 seconds, for me. Anything shorter than that works fine.

What type of installation are you running?

Home Assistant OS

Which operating system are you running on?

Home Assistant Operating System

Which add-on are you reporting an issue with?

Piper

What is the version of the add-on?

1.4.0

Steps to reproduce the issue

  1. Run a media_player.play_media service call with a long piper tts message, e.g.
service: media_player.play_media
target:
  entity_id: media_player.soundbar
data:
  media_content_type: music
  media_content_id: >-
    media-source://tts/tts.piper?message="This is a short message. This is a
    slightly longer message that takes longer to say. This is an even longer
    message where I'm going to keep talking for awhile so the length of the
    audio will increase. This is a 4th message to increase the length of the
    audio and I will keep talking and talking to make this longer. Lorem ipsum
    dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor
    incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis
    nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo
    consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse
    cillum dolore eu fugiat nulla pariatur."
  announce: false
  1. The message fails to play on the speaker. The same thing happens if I send announce: true, but with it set to false, I can see a message in the Sonos app that says "Unable to play '' - the connection to was lost" Shorter messages, which is pretty much anything under 35 seconds, always works, and anything longer seems to always fail. I have tried restarting various things (Home Assistant, the addon, etc.), clearing the TTS cache, and none of that has worked.

System Health information

System Information

version core-2023.12.3
installation_type Home Assistant OS
dev false
hassio true
docker true
user root
virtualenv false
python_version 3.11.6
os_name Linux
os_version 6.1.63-haos
arch x86_64
timezone America/Chicago
config_dir /config
Home Assistant Community Store
GitHub API ok
GitHub Content ok
GitHub Web ok
GitHub API Calls Remaining 4690
Installed Version 1.33.0
Stage running
Available Repositories 1352
Downloaded Repositories 48
Home Assistant Supervisor
host_os Home Assistant OS 11.2
update_channel stable
supervisor_version supervisor-2023.11.6
agent_version 1.6.0
docker_version 24.0.7
disk_total 62.3 GB
disk_used 30.7 GB
healthy true
supported true
board ova
supervisor_api ok
version_api ok
installed_addons Studio Code Server (5.14.2), Z-Wave JS UI (3.0.2), Advanced SSH & Web Terminal (17.0.0), Duck DNS (1.15.0), Dropbox Upload (1.3.0), MariaDB (2.6.1), phpMyAdmin (0.9.0), Mosquitto broker (6.4.0), Zigbee2MQTT (1.34.0-1), Home Assistant Google Drive Backup (0.112.1), Nginx Proxy Manager (0.12.3), ESPHome (2023.11.6), WireGuard (0.10.1), File editor (5.7.0), Piper (1.4.0), Whisper (1.0.0), openWakeWord (1.8.2)
Dashboards
dashboards 4
resources 29
views 23
mode storage
Recorder
oldest_recorder_run December 11, 2023 at 21:41
current_recorder_run December 15, 2023 at 10:30
estimated_db_size 8347.56 MiB
database_engine mysql
database_version 10.6.12
Spotify
api_endpoint_reachable ok

Anything in the Supervisor logs that might be useful for us?

No response

Anything in the add-on logs that might be useful for us?

Traceback (most recent call last):
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 35, in run
    if not (await self.handle_event(event)):
            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 104, in handle_event
    await self.write_event(
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 26, in write_event
    await async_write_event(event, self.writer)
  File "/usr/local/lib/python3.11/dist-packages/wyoming/event.py", line 114, in async_write_event
    await writer.drain()
  File "/usr/lib/python3.11/asyncio/streams.py", line 378, in drain
    await self._protocol._drain_helper()
  File "/usr/lib/python3.11/asyncio/streams.py", line 167, in _drain_helper
    raise ConnectionResetError('Connection lost')
ConnectionResetError: Connection lost
ERROR:asyncio:Task exception was never retrieved
future: <Task finished name='Task-8439' coro=<AsyncEventHandler.run() done, defined at /usr/local/lib/python3.11/dist-packages/wyoming/server.py:28> exception=ConnectionResetError('Connection lost')>

Additional information

I see this in the Home Assistant Core log:

Logger: homeassistant
Source: components/wyoming/tts.py:125
First occurred: 10:34:04 (9 occurrences)
Last logged: 11:16:01

Error doing job: Exception in callback SpeechManager._async_get_tts_audio.<locals>.handle_error(<Task cancell...nit__.py:691>>) at /usr/src/homeassistant/homeassistant/components/tts/__init__.py:757
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/asyncio/events.py", line 80, in _run
    self._context.run(self._callback, *self._args)
  File "/usr/src/homeassistant/homeassistant/components/tts/__init__.py", line 759, in handle_error
    if audio_task.exception():
       ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/tts/__init__.py", line 701, in get_tts_data
    extension, data = await engine_instance.internal_async_get_tts_audio(
                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/tts/__init__.py", line 451, in internal_async_get_tts_audio
    return await self.async_get_tts_audio(
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/wyoming/tts.py", line 125, in async_get_tts_audio
    event = await client.read_event()
            ^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/site-packages/wyoming/client.py", line 25, in read_event
    return await async_read_event(self._reader)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/site-packages/wyoming/event.py", line 77, in async_read_event
    json_line = await reader.readline()
                ^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/asyncio/streams.py", line 548, in readline
    line = await self.readuntil(sep)
           ^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/asyncio/streams.py", line 640, in readuntil
    await self._wait_for_data('readuntil')
  File "/usr/local/lib/python3.11/asyncio/streams.py", line 525, in _wait_for_data
    await self._waiter
asyncio.exceptions.CancelledError

joshuazd avatar Dec 15 '23 17:12 joshuazd

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

github-actions[bot] avatar Jan 14 '24 18:01 github-actions[bot]

this should not be closed as i am getting the same issue.

Connection to localhost (127.0.0.1) 10200 port [tcp/*] succeeded! ERROR:asyncio:Task exception was never retrieved future: <Task finished name='Task-39' coro=<AsyncEventHandler.run() done, defined at /lsiopy/lib/python3.12/site-packages/wyoming/server.py:28> exception=ConnectionResetError(104, 'Connection reset by peer')> Traceback (most recent call last): File "/lsiopy/lib/python3.12/site-packages/wyoming/server.py", line 31, in run event = await async_read_event(self.reader) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "/lsiopy/lib/python3.12/site-packages/wyoming/event.py", line 62, in async_read_event json_line = await reader.readline() ^^^^^^^^^^^^^^^^^^^^^^^ File "/usr/lib/python3.12/asyncio/streams.py", line 568, in readline line = await self.readuntil(sep) ^^^^^^^^^^^^^^^^^^^^^^^^^ File "/usr/lib/python3.12/asyncio/streams.py", line 660, in readuntil await self._wait_for_data('readuntil') File "/usr/lib/python3.12/asyncio/streams.py", line 545, in _wait_for_data await self._waiter File "/usr/lib/python3.12/asyncio/selector_events.py", line 1013, in _read_ready__data_received data = self._sock.recv(self.max_size) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ConnectionResetError: [Errno 104] Connection reset by peer

fawzib avatar Dec 24 '24 20:12 fawzib

I'm also having the same issue with piper 1.5.2 when getting a large response from chatgpt to home assistant voice preview edtion. I'm using EN GB medium though.

Logger: homeassistant
Source: components/wyoming/tts.py:126
First occurred: 17:38:56 (1 occurrences)
Last logged: 17:38:56

Error doing job: Exception in callback SpeechManager._async_get_tts_audio.<locals>.handle_error() at /usr/src/homeassistant/homeassistant/components/tts/__init__.py:844 (None)
Traceback (most recent call last):
  File "/usr/local/lib/python3.13/asyncio/events.py", line 89, in _run
    self._context.run(self._callback, *self._args)
    ~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/tts/__init__.py", line 846, in handle_error
    if audio_task.exception():
       ~~~~~~~~~~~~~~~~~~~~^^
  File "/usr/src/homeassistant/homeassistant/components/tts/__init__.py", line 786, in get_tts_data
    extension, data = await engine_instance.internal_async_get_tts_audio(
                      ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
        message, language, options
        ^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
  File "/usr/src/homeassistant/homeassistant/components/tts/__init__.py", line 492, in internal_async_get_tts_audio
    return await self.async_get_tts_audio(
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
        message=message, language=language, options=options
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
  File "/usr/src/homeassistant/homeassistant/components/wyoming/tts.py", line 126, in async_get_tts_audio
    event = await client.read_event()
            ^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.13/site-packages/wyoming/client.py", line 25, in read_event
    return await async_read_event(self._reader)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.13/site-packages/wyoming/event.py", line 79, in async_read_event
    json_line = await reader.readline()
                ^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.13/asyncio/streams.py", line 562, in readline
    line = await self.readuntil(sep)
           ^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.13/asyncio/streams.py", line 677, in readuntil
    await self._wait_for_data('readuntil')
  File "/usr/local/lib/python3.13/asyncio/streams.py", line 539, in _wait_for_data
    await self._waiter
asyncio.exceptions.CancelledError
BrokenPipeError: [Errno 32] Broken pipe
ERROR:asyncio:Task exception was never retrieved
future: <Task finished name='wyoming event handler' coro=<AsyncEventHandler.run() done, defined at /usr/local/lib/python3.11/dist-packages/wyoming/server.py:31> exception=BrokenPipeError(32, 'Broken pipe')>
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 48, in handle_event
    return await self._handle_event(event)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 114, in _handle_event
    await self.write_event(
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 29, in write_event
    await async_write_event(event, self.writer)
  File "/usr/local/lib/python3.11/dist-packages/wyoming/event.py", line 131, in async_write_event
    await writer.drain()
  File "/usr/lib/python3.11/asyncio/streams.py", line 378, in drain
    await self._protocol._drain_helper()
  File "/usr/lib/python3.11/asyncio/streams.py", line 167, in _drain_helper
    raise ConnectionResetError('Connection lost')
ConnectionResetError: Connection lost
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 41, in run
    if not (await self.handle_event(event)):
            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 50, in handle_event
    await self.write_event(
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 29, in write_event
    await async_write_event(event, self.writer)
  File "/usr/local/lib/python3.11/dist-packages/wyoming/event.py", line 131, in async_write_event
    await writer.drain()
  File "/usr/lib/python3.11/asyncio/streams.py", line 366, in drain
    raise exc
  File "/usr/lib/python3.11/asyncio/selector_events.py", line 1057, in write
    n = self._sock.send(data)
        ^^^^^^^^^^^^^^^^^^^^^
BrokenPipeError: [Errno 32] Broken pipe

Moltenkore avatar Dec 31 '24 17:12 Moltenkore

Same here with piper version 1.5.2 on HAOS Core 2025.1.2 Supervisor 2024.12.3 Operating System 14.1 Frontend 20250109.0:

ERROR:asyncio:Task exception was never retrieved
future: <Task finished name='wyoming event handler' coro=<AsyncEventHandler.run() done, defined at /usr/local/lib/python3.11/dist-packages/wyoming/server.py:31> exception=BrokenPipeError(32, 'Broken pipe')>
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 48, in handle_event
    return await self._handle_event(event)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 114, in _handle_event
    await self.write_event(
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 29, in write_event
    await async_write_event(event, self.writer)
  File "/usr/local/lib/python3.11/dist-packages/wyoming/event.py", line 131, in async_write_event
    await writer.drain()
  File "/usr/lib/python3.11/asyncio/streams.py", line 378, in drain
    await self._protocol._drain_helper()
  File "/usr/lib/python3.11/asyncio/streams.py", line 167, in _drain_helper
    raise ConnectionResetError('Connection lost')
ConnectionResetError: Connection lost
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 41, in run
    if not (await self.handle_event(event)):
            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 50, in handle_event
    await self.write_event(
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 29, in write_event
    await async_write_event(event, self.writer)
  File "/usr/local/lib/python3.11/dist-packages/wyoming/event.py", line 131, in async_write_event
    await writer.drain()
  File "/usr/lib/python3.11/asyncio/streams.py", line 366, in drain
    raise exc
  File "/usr/lib/python3.11/asyncio/selector_events.py", line 1057, in write
    n = self._sock.send(data)
        ^^^^^^^^^^^^^^^^^^^^^
BrokenPipeError: [Errno 32] Broken pipe

dirtyharryiv avatar Jan 15 '25 18:01 dirtyharryiv

@synesthesiam do we need to re report this because the bot closed it? This is a real problem. But it sort of feels like we are talking to the void here in an issue closed by a bot.

Ramblurr avatar Feb 01 '25 15:02 Ramblurr

Thank you for tagging me, I don't get notified otherwise! I will take a look.

synesthesiam avatar Feb 01 '25 19:02 synesthesiam

Hi, I can confirm the same issue here:

s6-rc: info: service discovery successfully started
s6-rc: info: service legacy-services: starting
s6-rc: info: service legacy-services successfully started
ERROR:asyncio:Task exception was never retrieved
future: <Task finished name='wyoming event handler' coro=<AsyncEventHandler.run() done, defined at /usr/local/lib/python3.11/dist-packages/wyoming/server.py:31> exception=BrokenPipeError(32, 'Broken pipe')>
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 48, in handle_event
    return await self._handle_event(event)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 114, in _handle_event
    await self.write_event(
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 29, in write_event
    await async_write_event(event, self.writer)
  File "/usr/local/lib/python3.11/dist-packages/wyoming/event.py", line 131, in async_write_event
    await writer.drain()
  File "/usr/lib/python3.11/asyncio/streams.py", line 378, in drain
    await self._protocol._drain_helper()
  File "/usr/lib/python3.11/asyncio/streams.py", line 167, in _drain_helper
    raise ConnectionResetError('Connection lost')
ConnectionResetError: Connection lost
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 41, in run
    if not (await self.handle_event(event)):
            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/dist-packages/wyoming_piper/handler.py", line 50, in handle_event
    await self.write_event(
  File "/usr/local/lib/python3.11/dist-packages/wyoming/server.py", line 29, in write_event
    await async_write_event(event, self.writer)
  File "/usr/local/lib/python3.11/dist-packages/wyoming/event.py", line 131, in async_write_event
    await writer.drain()
  File "/usr/lib/python3.11/asyncio/streams.py", line 366, in drain
    raise exc
  File "/usr/lib/python3.11/asyncio/selector_events.py", line 1057, in write
    n = self._sock.send(data)

Saur0o0n avatar Feb 05 '25 13:02 Saur0o0n

There's some useful info over here that might help: https://github.com/esphome/home-assistant-voice-pe/issues/271

Moltenkore avatar Feb 05 '25 23:02 Moltenkore

Same issue here. If I'm using piper in an automation with long text (and non static text, e.g.text is not in cache yet), it fails to speak the text in the first place. If I rerun the automation manually right after it failed, it is working. Cache is set to "true".

RKCKBN avatar Mar 11 '25 18:03 RKCKBN

Same problem

zipzagster avatar Mar 14 '25 12:03 zipzagster

Same issue here. I bought the home assistant voice device and it does not work because piper does not read the responses.

provanguard avatar Mar 14 '25 23:03 provanguard

Same here as a workaround I split messages by sentences and send them one by one. This works most of the time but should not be needed.

jeroenterheerdt avatar Mar 16 '25 15:03 jeroenterheerdt

@synesthesiam it seems this issue is still widespread. I know there's a lot going on, so I am not pressuring for a fix, but could we simply have this issue reopened please?

Ramblurr avatar Mar 17 '25 05:03 Ramblurr

I agree in the age of LLMs this should be fixed but in the mean time here's workaround: https://community.home-assistant.io/t/simple-script-to-handle-multiple-tts-lines-as-a-batch/589926/2

jeroenterheerdt avatar Mar 17 '25 16:03 jeroenterheerdt

Pls reopen this Issue. "Not planned" is an bad joke.

tcs-christian-ulrich avatar Aug 22 '25 07:08 tcs-christian-ulrich

They frankly don't want us to report issues, that's why they have a bot that closes them so fast. I understand they get a lot of reports, too many probably, and they just can't deal with it all. It's understandable, I'm thankful to have HA at all. They have to work at their own pace and maybe one day they will independently rediscover this issue and fix it.

Ramblurr avatar Aug 23 '25 21:08 Ramblurr

@agners Can you reopen this issue please?

synesthesiam avatar Aug 23 '25 21:08 synesthesiam

I had a similar issue before, and when I looked into the piper logs, I found an issue that I fixed: https://github.com/rhasspy/wyoming-piper/pull/33

I didn't have that issue after fixing that anymore

Horschig avatar Oct 01 '25 06:10 Horschig

Hallo, I'm using verions 1.6.4, it works only if the application is connected to the internet. Problem is it is using external url to announce instead of internal url. I want Piper to announce only via internal url. Any suggestions to change the url?

Image

aduplessis-cyber avatar Oct 15 '25 05:10 aduplessis-cyber

Updating to version 2.1.1: https://github.com/home-assistant/addons/pull/4217

synesthesiam avatar Nov 05 '25 21:11 synesthesiam