Skip to content

Commit 68848b4

Browse files
Handle selector for Multiple entities (specifically for media_player.join (#929)
1 parent ecf8c2e commit 68848b4

File tree

3 files changed

+74
-2
lines changed

3 files changed

+74
-2
lines changed

src/HassModel/NetDaemon.HassModel.CodeGenerator/MetaData/ServicesMetaData/HassServiceArgumentMapper.cs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ public static ServiceArgument Map(HassServiceField field)
1414
}
1515
private static Type GetClrTypeFromSelector(Selector? selectorObject)
1616
{
17-
return selectorObject switch
17+
var clrType = selectorObject switch
1818
{
1919
null => typeof(object),
2020
NumberSelector s when (s.Step ?? 1) % 1 != 0 => typeof(double),
@@ -31,5 +31,7 @@ NumberSelector s when (s.Step ?? 1) % 1 != 0 => typeof(double),
3131
_ => typeof(object)
3232
},
3333
};
34+
35+
return selectorObject?.Multiple ?? false ? typeof(IEnumerable<>).MakeGenericType(clrType) : clrType;
3436
}
3537
}

src/HassModel/NetDaemon.HassModel.CodeGenerator/MetaData/ServicesMetaData/Selectors.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ namespace NetDaemon.HassModel.CodeGenerator.Model;
55

66
internal record Selector()
77
{
8+
public bool Multiple { get; init; }
9+
810
public string? Type { get; init; }
911
}
1012

src/HassModel/NetDaemon.HassModel.Tests/CodeGenerator/ServicesGeneratorTest.cs

Lines changed: 69 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
using System.Collections.Generic;
2+
using System.Text.Json;
13
using NetDaemon.Client.HomeAssistant.Model;
24
using NetDaemon.HassModel.CodeGenerator;
35
using NetDaemon.HassModel.CodeGenerator.Model;
@@ -227,6 +229,72 @@ public void Run(Entities entities, Services services)
227229
""";
228230

229231
CodeGenTestHelper.AssertCodeCompiles(code.ToString(), appCode);
230-
}
232+
}
233+
234+
[Fact]
235+
public void MultpileEntitySelector_ShouldGenerateArray()
236+
{
237+
var states = new HassState[] {
238+
new() { EntityId = "media_player.group1" },
239+
};
240+
241+
var serviceMetaData = """
242+
{
243+
"media_player": {
244+
"join": {
245+
"name": "Join",
246+
"description": "Group players together. Only works on platforms with support for player groups.",
247+
"fields": {
248+
"group_members": {
249+
"name": "Group members",
250+
"description": "The players which will be synced with the target player.",
251+
"required": true,
252+
"example": "- media_player.multiroom_player2\n- media_player.multiroom_player3\n",
253+
"selector": {
254+
"entity": {
255+
"multiple": true,
256+
"domain": "media_player"
257+
}
258+
}
259+
}
260+
},
261+
"target": {
262+
"entity": {
263+
"domain": "media_player"
264+
}
265+
}
266+
}
267+
}
268+
}
269+
""";
270+
271+
var appCode = """
272+
using NetDaemon.HassModel;
273+
using NetDaemon.HassModel.Entities;
274+
using RootNameSpace;
275+
276+
public class Root
277+
{
278+
public void Run(Entities entities, Services services)
279+
{
280+
entities.MediaPlayer.Group1.Join(groupMembers: new string [] {"media_player.multiroom_player1", "media_player.multiroom_player2"});
281+
services.MediaPlayer.Join(new ServiceTarget(), groupMembers: new string [] {"media_player.multiroom_player1", "media_player.multiroom_player2"});
282+
}
283+
}
284+
""";
285+
286+
var hassServiceDomains = Parse(serviceMetaData);
287+
288+
// Act:
289+
var code = CodeGenTestHelper.GenerateCompilationUnit(_settings, states, hassServiceDomains);
290+
291+
CodeGenTestHelper.AssertCodeCompiles(code.ToString(), appCode);
292+
}
293+
294+
private static IReadOnlyCollection<HassServiceDomain> Parse(string sample)
295+
{
296+
var element = JsonDocument.Parse(sample).RootElement;
297+
return ServiceMetaDataParser.Parse(element);
298+
}
231299
}
232300

0 commit comments

Comments
 (0)