]> git.basschouten.com Git - openhab-addons.git/blob
34b6f49e1316e1342090c3a49285195fd263b1a1
[openhab-addons.git] /
1 /**
2  * Copyright (c) 2010-2023 Contributors to the openHAB project
3  *
4  * See the NOTICE file(s) distributed with this work for additional
5  * information.
6  *
7  * This program and the accompanying materials are made available under the
8  * terms of the Eclipse Public License 2.0 which is available at
9  * http://www.eclipse.org/legal/epl-2.0
10  *
11  * SPDX-License-Identifier: EPL-2.0
12  */
13 package org.openhab.binding.tr064.internal.util;
14
15 import java.util.ArrayList;
16 import java.util.HashMap;
17 import java.util.List;
18 import java.util.Map;
19 import java.util.Optional;
20 import java.util.stream.Collectors;
21 import java.util.stream.Stream;
22
23 import org.eclipse.jdt.annotation.NonNullByDefault;
24 import org.eclipse.jetty.client.HttpClient;
25 import org.openhab.binding.tr064.internal.SCPDException;
26 import org.openhab.binding.tr064.internal.dto.scpd.root.SCPDDeviceType;
27 import org.openhab.binding.tr064.internal.dto.scpd.root.SCPDRootType;
28 import org.openhab.binding.tr064.internal.dto.scpd.root.SCPDServiceType;
29 import org.openhab.binding.tr064.internal.dto.scpd.service.SCPDScpdType;
30
31 /**
32  * The {@link SCPDUtil} is responsible for handling commands, which are
33  * sent to one of the channels.
34  *
35  * @author Jan N. Klug - Initial contribution
36  */
37 @NonNullByDefault
38 public class SCPDUtil {
39     private SCPDRootType scpdRoot;
40     private final List<SCPDDeviceType> scpdDevicesList = new ArrayList<>();
41     private final Map<String, SCPDScpdType> serviceMap = new HashMap<>();
42
43     public SCPDUtil(HttpClient httpClient, String endpoint) throws SCPDException {
44         SCPDRootType scpdRoot = Util.getAndUnmarshalXML(httpClient, endpoint + "/tr64desc.xml", SCPDRootType.class);
45         if (scpdRoot == null) {
46             throw new SCPDException("could not get SCPD root");
47         }
48         this.scpdRoot = scpdRoot;
49
50         scpdDevicesList.addAll(flatDeviceList(scpdRoot.getDevice()).collect(Collectors.toList()));
51         for (SCPDDeviceType device : scpdDevicesList) {
52             for (SCPDServiceType service : device.getServiceList()) {
53                 SCPDScpdType scpd = serviceMap.computeIfAbsent(service.getServiceId(), serviceId -> Util
54                         .getAndUnmarshalXML(httpClient, endpoint + service.getSCPDURL(), SCPDScpdType.class));
55                 if (scpd == null) {
56                     throw new SCPDException("could not get SCPD service");
57                 }
58             }
59         }
60     }
61
62     /**
63      * recursively flatten the device tree to a stream
64      *
65      * @param device a device
66      * @return stream of sub-devices
67      */
68     private Stream<SCPDDeviceType> flatDeviceList(SCPDDeviceType device) {
69         return Stream.concat(Stream.of(device), device.getDeviceList().stream().flatMap(this::flatDeviceList));
70     }
71
72     /**
73      * get a list of all sub-devices (root device not included)
74      *
75      * @return the device list
76      */
77     public List<SCPDDeviceType> getAllSubDevices() {
78         return scpdDevicesList.stream().filter(device -> !device.getUDN().equals(scpdRoot.getDevice().getUDN()))
79                 .collect(Collectors.toList());
80     }
81
82     /**
83      * get a single device by it's UDN
84      *
85      * @param udn the device UDN
86      * @return the device
87      */
88     public Optional<SCPDDeviceType> getDevice(String udn) {
89         if (udn.isEmpty()) {
90             return Optional.of(scpdRoot.getDevice());
91         } else {
92             return getAllSubDevices().stream().filter(device -> udn.equals(device.getUDN())).findFirst();
93         }
94     }
95
96     /**
97      * get a single service by it's serviceId
98      *
99      * @param serviceId the service id
100      * @return the service
101      */
102     public Optional<SCPDScpdType> getService(String serviceId) {
103         return Optional.ofNullable(serviceMap.get(serviceId));
104     }
105 }