So you mean that instead of an answer you would like to be able to play an audio file?
Yes, exactly, but on a per-sentence-level.
SSML (Speech Synthesis Markup Language) has a audio tag for this purpose (https://www.w3.org/TR/speech-synthesis/#S3.3.1). So it is possible to use e.g. the sentence
'<audio src="hello_world.wav">hello world</audio>'
which will try to play the audio file and as fallback when the file is not found generate the normal sentence instead.
Rhasspy does not has support for SSML yet, but I am currently working on it
Welcome, @Blade_John! If you’re using Home Assistant, check out my HA example.
If you use the built-in intents through HA, it will automatically respond with text (which Rhasspy will play through your TTS system). So something like “turn on the kitchen light” will have HA turn the light on and respond “turned on kitchen light”.
You can also write a tiny Bash script to do the response, or configure a Node-RED flow
I recommend using Node-Red but it depends on what you like more of course. I use Node-Red for all HA and rhasspy automations (Node-Red triggers the intended service calls to HA for each intent).
Node-Red also sends my answer to the rhasspy. I will post my example tomorrow, maybe it will be helpful for you.
AMAZING answers!! I was in a lot of forums for different things in my life,
but this one is REALLY impressive!!!
Yes this one is NICE !
This was the root cause of this topic.
The HA-autogenerated-respond was a mix of english and german words, spoken with the eSpeak male voice, resulting in really funny audio-outputs.
I managed it using custom Intents: (for german language).
At the moment i can’t use the speak
key in HA, to make rhasspy speak.
I’m using a rest_command service.
configuration.yaml
intent_script:
GetTemperature: # Intent type
action:
data_template:
payload: >-
es sind {{ states("sensor.temperature")|regex_replace(find="\.",
replace=",", ignorecase=False) }} grad
service: rest_command.rhasspy_speak
GetTime: # Intent type
action:
data_template:
payload: 'es ist {{ now().hour }} uhr {{ now().minute }}'
service: rest_command.rhasspy_speak
OUTSTANDING! smells like a game-changer.
If anyone is intrested in the german sentences<–>intent for switches & lights in HA:
Expand
sentences.ini
[rhasspYZTurnOnSwitch]
state_on = (ein | an | einschalten) {state}
\[(kannst | könntest) du] [bitte] [(das | die | den)] ($switches){name} <state_on> [schalten]
[rhasspYZTurnOffSwitch]
state_off = (aus | ausschalten ) {state}
\[(kannst | könntest) du] [bitte] [(das | die | den)] ($switches){name} <state_off> [schalten]
[rhasspYZTurnOnLight]
state_on = (ein | an | einschalten) {state}
\[(kannst | könntest) du] [bitte] [(das | die | den)] ($lights){name} <state_on> [schalten]
[rhasspYZTurnOffLight]
state_off = (aus | ausschalten ) {state}
\[(kannst | könntest) du] [bitte] [(das | die | den)] ($lights){name} <state_off> [schalten]
[rhasspYZSetLightColor]
\[(kannst | könntest) du] [bitte] [das|die|den] ($lights){name} auf ($colors){color} schalten
[rhasspYZSetLightBrightness]
\[(kannst | könntest) du] [bitte] [das|die|den] ($lights){name} auf (0..100){brightness} Prozent
HA-configuration.yaml:
intent_script:
rhasspYZTurnOnSwitch: # Intent type
action:
data_template:
entity_id: >
switch.{{ name }}
service_template: >
switch.turn_on
rhasspYZTurnOffSwitch: # Intent type
action:
data_template:
entity_id: >
switch.{{ name }}
service_template: >
switch.turn_off
rhasspYZTurnOnLight: # Intent type
action:
data_template:
entity_id: >
light.{{ name }}
service_template: >
light.turn_on
rhasspYZTurnOffLight: # Intent type
action:
data_template:
entity_id: >
light.{{ name }}
service_template: >
light.turn_off
rhasspYZSetLightColor: # Intent type
action:
data_template:
entity_id: >
light.{{ name }}
color_name: '{{ color }}'
service_template: >
light.turn_on
rhasspYZSetLightBrightness: # Intent type
action:
data_template:
entity_id: >
light.{{ name }}
brightness: '{{ ( brightness * 255 / 100 ) | int }}'
service_template: >
light.turn_on
I also tried to merge the 4 intents into 1, but that didn’t work:
Summary
[rhasspYZ]
state_on = (ein | an | einschalten) {state}
state_off = (aus | ausschalten ) {state}
new_state = <state_on> | <state_off>
\[(kannst | könntest) du] [bitte] [(das | die | den)] ($lights | $switches){name} (<new_state>){state} [schalten]
in the rhasspy log i can see “entity” and “state”, but it is not accessable in HA-templating.
Boom thx for the example. I don’t know why, but im unable to like node-red yet.
Feels like an unneccessary man-in-the-middle. Please don’t get me wrong, the problem is ME, not the world. At the moment it seems, everything can be done within HA (automations, scripts, intents, events). If at some point I can find some real nice benefits, I might fall to dark-side (i mean the red-side)
Nice one, next world opened. thx
Offtopic: What’s the downside of maryTTS? I tested the online-demo, and it sounds much better than the eSpeak. Maybe perfomance is an issue on a pi 3b+ ?
Thank you for the nice spirit here!!!
Gratefully
Blade
Part of your problem with this sentence is most likely that you got the slot tag behind state_on
and state_off
and a second time behind them in the actual sentence.
You should try this instead:
fixed sentence
[rhasspYZ] state_on = (ein | an | einschalten) state_off = (aus | ausschalten ) new_state = (<state_on> | <state_off>) \[(kannst | könntest) du] [bitte] [(das | die | den)] ($lights | $switches){name} (<new_state>){state} [schalten]
the sentences i use for my `ChangeLightState` intent
[ChangeLightState]
light_name = $lampe {name}
light_state = ((ein|an):ein | (aus|ab):aus | heller | dunkler) {state}
[(schalte | schalt)] [(die | das | den)] <light_name> <light_state>
(((deaktiviere):aus)|((aktiviere):ein)) {state} [(die | das | den)] <light_name>
<light_name> ((ausschalten|deaktiviere|abschalten):aus | (einschalten|anschalten|aktiviere):ein {state}
Nice works, THANKS
My Light intents are:
[rhasspYZSetLightColor]
\[(kannst | könntest) du] [bitte] [das|die|den] ($lights){name} auf ($colors){color} schalten
[rhasspYZSetLightBrightness]
\[(kannst | könntest) du] [bitte] [das|die|den] ($lights){name} auf (0..100){brightness} Prozent
I’m using automations.yaml to compose my voice responses in Home Assistant. Where I’ve run into a bit of difficulty is obtaining the slots rawValue for any given slot. Below is the example JSON returned from the Rhasspy event where I’d like to obtain the rawValue data for the slot where slotName = “light”. It should be “brass lamp”.
What I have tried is shown here, but alas, neither are working.
{{ trigger.event.data._intent.slots["light"].rawValue }}
{{ trigger.event.data._intent.slots.light.rawValue }}
So exactly how should I specify a slot by name?
{
"event_type": "rhasspy_ChangeLightState",
"data": {
"light": "switch.brass_lamp",
"state": "off",
"_text": "switch.brass_lamp off",
"_raw_text": "brass lamp off",
"_intent": {
"input": "switch.brass_lamp off",
"intent": {
"intentName": "ChangeLightState",
"confidenceScore": 1
},
"siteId": "Listener1",
"id": null,
"slots": [
{
"entity": "light",
"value": {
"kind": "Unknown",
"value": "switch.brass_lamp"
},
"slotName": "light",
"rawValue": "brass lamp",
"confidence": 1,
"range": {
"start": 0,
"end": 17,
"rawStart": 0,
"rawEnd": 10
}
},
{
"entity": "state_on_off",
"value": {
"kind": "Unknown",
"value": "off"
},
"slotName": "state",
"rawValue": "off",
"confidence": 1,
"range": {
"start": 18,
"end": 21,
"rawStart": 11,
"rawEnd": 14
}
}
],
"sessionId": "Listener1-porcupine-1ed92005-9da1-433a-8d7d-671cd79390de",
"customData": null,
"asrTokens": [
[
{
"value": "switch.brass_lamp",
"confidence": 1,
"rangeStart": 0,
"rangeEnd": 17,
"time": null
},
{
"value": "off",
"confidence": 1,
"rangeStart": 18,
"rangeEnd": 21,
"time": null
}
]
],
"asrConfidence": null,
"rawInput": "brass lamp off",
"wakewordId": "porcupine",
"lang": null
}
},
"origin": "REMOTE",
"time_fired": "2020-07-05T18:15:43.376664+00:00",
"context": {
"id": "278fc19a54f349f7948dfa12882e2913",
"parent_id": null,
"user_id": "26ec3060f78f4880a6a70e903924eb1f"
}
}
I’ve never used Snips before! The good news is, I’ve figured out that because the light is always Slots[0] I can use that notation:
{{ trigger.event.data._intent.slots[0].rawValue }}
@FredTheFrog maybe this will work:
{{ trigger.event.data._intent.slots[0].rawValue }}
This will only work if light is the first slot returned.
slots is an array containing objects.
seems like you already figured it out.
Take a look at
It is completely compatible with Rhasspy since Rhasspy 2.5 respect the Hermes protocol.
It greatly simplify the intent handling with Home Assistant.
Hope this helps.
@synesthesiam Maybe a Rhasspy Home Assistant integration based on the Snips one can be proposed to the HA guys…
@moqart and @fastjack Thank you both for your very timely and helpful replies. I’ve just placed my first 2.5.0/voltron rhasspy unit into ‘Production’ mode. I had to learn the newer configuration syntax for sentences and slots first. I’m still using HA events to respond using HA automations. Maybe I’ll learn to use Snips/hermes next.
Proposing that to the HA developers is an EXCELLENT idea. My concern is they might soon deprecate the Snips interface, since Snips went closed-source.
Or just use Node-Red and get rid of that awful YAML scripting
@FredTheFrog
you might find this simpler.
At the top of your event data, i can see you are using ‘light’ and ‘state’ as your tag/ property in Rhasspy. These can be accessed in a more straightforward fashion:-
{% set var2 = trigger.event.data.light %}
{% set var3 = trigger.event.data.state %}
We actually sort of got this already with the “intent” HTTP endpoint
If you just add intent:
to your HA configuration YAML and switch Rhasspy from “event” to “intent” mode for HA, Rhasspy will trigger intents directly in HA. This works with the built-in intents as well as intent_script
ones.
Thank you, @Gfawkes. While simpler it doesn’t provide the correct text for voice confirmation.
state is simply “on” or “off” which does translate directly/correctly.
light is actually “switch.brass_lamp” which I don’t want spoken. I just want “brass lamp” which is in trigger.event.data._intent.slots[0].rawValue
{
"event_type": "rhasspy_ChangeLightState",
"data": {
"light": "switch.brass_lamp",
"state": "on",
"_text": "switch.brass_lamp on",
"_raw_text": "brass lamp on",
"_intent": {
"input": "switch.brass_lamp on",
"intent": {
"intentName": "ChangeLightState",
"confidenceScore": 1
},
"siteId": "Listener1",
"id": null,
"slots": [
{
"entity": "light",
"value": {
"kind": "Unknown",
"value": "switch.brass_lamp"
},
"slotName": "light",
"rawValue": "brass lamp",
"confidence": 1,
"range": {
"start": 0,
"end": 17,
"rawStart": 0,
"rawEnd": 10
}
},
I guess what I’m really asking is, how to update this sentence definition to send the value of <light> in the HA event? Bonus points if it defines three distinct values: lightSwitch, lightName, lightState.
[ChangeLightState]
light=$light
state=$state_on_off
<light>{light} <state>{state}
(turn | switch | cut) [the] <light>{light} <state>{state}