예제 #1
0
 async def test_start_udp_tunnel_connection(self):
     """Test starting UDP tunnel connection."""
     # without gateway_ip automatic is called
     gateway_ip = "127.0.0.2"
     connection_config = ConnectionConfig(
         connection_type=ConnectionType.TUNNELING, gateway_ip=gateway_ip)
     with patch("xknx.io.KNXIPInterface._start_tunnelling_udp"
                ) as start_tunnelling_udp:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         start_tunnelling_udp.assert_called_once_with(
             gateway_ip=gateway_ip,
             gateway_port=3671,
         )
     with patch("xknx.io.tunnel.UDPTunnel.connect") as connect_udp:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         assert isinstance(interface._interface, UDPTunnel)
         assert interface._interface.local_ip == "127.0.0.1"
         assert interface._interface.local_port == 0
         assert interface._interface.gateway_ip == gateway_ip
         assert interface._interface.gateway_port == 3671
         assert interface._interface.auto_reconnect
         assert interface._interface.auto_reconnect_wait == 3
         assert interface._interface.route_back is False
         assert (  # pylint: disable=comparison-with-callable
             interface._interface.telegram_received_callback ==
             interface.telegram_received)
         connect_udp.assert_called_once_with()
예제 #2
0
    async def test_threaded_send_telegram(self):
        """Test sending telegram with threaded connection."""
        # pylint: disable=attribute-defined-outside-init
        self.main_thread = threading.get_ident()

        def assert_thread(*args, **kwargs):
            """Test threaded connection."""
            assert self.main_thread != threading.get_ident()
            return DEFAULT  # to not disable `return_value` of send_telegram_mock

        local_ip = "127.0.0.1"
        # set local_ip to avoid gateway scanner; use routing as it is the simplest mode
        connection_config = ConnectionConfig(
            connection_type=ConnectionType.ROUTING,
            local_ip=local_ip,
            threaded=True)
        telegram_mock = Mock()
        with patch("xknx.io.routing.Routing.connect",
                   side_effect=assert_thread) as connect_routing_mock, patch(
                       "xknx.io.routing.Routing.send_telegram",
                       side_effect=assert_thread,
                       return_value="test",
                   ) as send_telegram_mock, patch(
                       "xknx.io.routing.Routing.disconnect",
                       side_effect=assert_thread) as disconnect_routing_mock:
            interface = knx_interface_factory(self.xknx, connection_config)
            await interface.start()
            connect_routing_mock.assert_called_once_with()
            assert await interface.send_telegram(telegram_mock) == "test"
            send_telegram_mock.assert_called_once_with(telegram_mock)
            await interface.stop()
            disconnect_routing_mock.assert_called_once_with()
            assert interface._interface is None
예제 #3
0
 async def test_start_routing_connection(self):
     """Test starting routing connection."""
     local_ip = "127.0.0.1"
     # set local_ip to avoid gateway scanner
     connection_config = ConnectionConfig(
         connection_type=ConnectionType.ROUTING, local_ip=local_ip)
     with patch("xknx.io.KNXIPInterface._start_routing") as start_routing:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         start_routing.assert_called_once_with(local_ip=local_ip, )
     with patch("xknx.io.routing.Routing.connect") as connect_routing:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         assert isinstance(interface._interface, Routing)
         assert interface._interface.local_ip == local_ip
         assert (  # pylint: disable=comparison-with-callable
             interface._interface.telegram_received_callback ==
             interface.telegram_received)
         connect_routing.assert_called_once_with()
예제 #4
0
파일: xknx.py 프로젝트: XKNX/xknx
    def __init__(
            self,
            own_address: str | IndividualAddress = DEFAULT_ADDRESS,
            address_format: GroupAddressType = GroupAddressType.LONG,
            telegram_received_cb: Callable[[Telegram], Awaitable[None]]
        | None = None,
            device_updated_cb: Callable[[Device], Awaitable[None]]
        | None = None,
            connection_state_changed_cb: Callable[[XknxConnectionState],
                                                  Awaitable[None]]
        | None = None,
            rate_limit: int = DEFAULT_RATE_LIMIT,
            multicast_group: str = DEFAULT_MCAST_GRP,
            multicast_port: int = DEFAULT_MCAST_PORT,
            log_directory: str | None = None,
            state_updater: TrackerOptionType = False,
            daemon_mode: bool = False,
            connection_config: ConnectionConfig = ConnectionConfig(),
    ) -> None:
        """Initialize XKNX class."""
        self.connection_manager = ConnectionManager()
        self.devices = Devices()
        self.knxip_interface = knx_interface_factory(
            self, connection_config=connection_config)
        self.management = Management(self)
        self.telegrams: asyncio.Queue[Telegram | None] = asyncio.Queue()
        self.telegram_queue = TelegramQueue(self)
        self.state_updater = StateUpdater(self,
                                          default_tracker_option=state_updater)
        self.task_registry = TaskRegistry(self)

        self.current_address = IndividualAddress(0)
        self.daemon_mode = daemon_mode
        self.multicast_group = multicast_group
        self.multicast_port = multicast_port
        self.own_address = IndividualAddress(own_address)
        self.rate_limit = rate_limit
        self.sigint_received = asyncio.Event()
        self.started = asyncio.Event()
        self.version = VERSION

        GroupAddress.address_format = address_format  # for global string representation
        if log_directory is not None:
            self.setup_logging(log_directory)

        if telegram_received_cb is not None:
            self.telegram_queue.register_telegram_received_cb(
                telegram_received_cb)

        if device_updated_cb is not None:
            self.devices.register_device_updated_cb(device_updated_cb)

        if connection_state_changed_cb is not None:
            self.connection_manager.register_connection_state_changed_cb(
                connection_state_changed_cb)
예제 #5
0
 async def test_invalid_user_password(self):
     """Test ip secure."""
     gateway_ip = "192.168.1.1"
     connection_config = ConnectionConfig(
         connection_type=ConnectionType.TUNNELING_TCP_SECURE,
         gateway_ip=gateway_ip,
         secure_config=SecureConfig(user_id=1, ),
     )
     with pytest.raises(InvalidSecureConfiguration):
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
예제 #6
0
 async def test_start_secure_with_manual_passwords(self):
     """Test starting a secure connection from manual passwords."""
     gateway_ip = "192.168.1.1"
     connection_config = ConnectionConfig(
         connection_type=ConnectionType.TUNNELING_TCP_SECURE,
         gateway_ip=gateway_ip,
         secure_config=SecureConfig(
             user_id=3,
             device_authentication_password="******",
             user_password="******",
         ),
     )
     with patch("xknx.io.KNXIPInterface._start_secure_tunnelling_tcp"
                ) as start_secure_tunnel:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         start_secure_tunnel.assert_called_once_with(
             gateway_ip="192.168.1.1",
             gateway_port=3671,
             user_id=3,
             user_password="******",
             device_authentication_password="******",
         )
     with patch("xknx.io.tunnel.SecureTunnel.connect") as connect_secure:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         assert isinstance(interface._interface, SecureTunnel)
         assert interface._interface.gateway_ip == gateway_ip
         assert interface._interface.gateway_port == 3671
         assert interface._interface.auto_reconnect is True
         assert interface._interface.auto_reconnect_wait == 3
         assert interface._interface._user_id == 3
         assert interface._interface._user_password == "user1"
         assert (interface._interface._device_authentication_password ==
                 "authenticationcode")
         assert (  # pylint: disable=comparison-with-callable
             interface._interface.telegram_received_callback ==
             interface.telegram_received)
         connect_secure.assert_called_once_with()
예제 #7
0
 async def test_start_secure_connection_knx_keys_first_interface(self):
     """Test starting a secure connection from a knxkeys file."""
     gateway_ip = "192.168.1.1"
     knxkeys_file = os.path.join(os.path.dirname(__file__),
                                 "resources/testcase.knxkeys")
     connection_config = ConnectionConfig(
         connection_type=ConnectionType.TUNNELING_TCP_SECURE,
         gateway_ip=gateway_ip,
         secure_config=SecureConfig(knxkeys_file_path=knxkeys_file,
                                    knxkeys_password="******"),
     )
     with patch("xknx.io.KNXIPInterface._start_secure_tunnelling_tcp"
                ) as start_secure_tunnel:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         start_secure_tunnel.assert_called_once_with(
             gateway_ip="192.168.1.1",
             gateway_port=3671,
             user_id=3,
             user_password="******",
             device_authentication_password="******",
         )
     with patch("xknx.io.tunnel.SecureTunnel.connect") as connect_secure:
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
         assert isinstance(interface._interface, SecureTunnel)
         assert interface._interface.gateway_ip == gateway_ip
         assert interface._interface.gateway_port == 3671
         assert interface._interface.auto_reconnect is True
         assert interface._interface.auto_reconnect_wait == 3
         assert interface._interface._user_id == 3
         assert interface._interface._user_password == "user1"
         assert (interface._interface._device_authentication_password ==
                 "authenticationcode")
         assert (  # pylint: disable=comparison-with-callable
             interface._interface.telegram_received_callback ==
             interface.telegram_received)
         connect_secure.assert_called_once_with()
예제 #8
0
 async def test_invalid_user_id_secure_error(self):
     """Test ip secure."""
     gateway_ip = "192.168.1.1"
     knxkeys_file = os.path.join(os.path.dirname(__file__),
                                 "resources/testcase.knxkeys")
     connection_config = ConnectionConfig(
         connection_type=ConnectionType.TUNNELING_TCP_SECURE,
         gateway_ip=gateway_ip,
         secure_config=SecureConfig(user_id=12,
                                    knxkeys_file_path=knxkeys_file,
                                    knxkeys_password="******"),
     )
     with pytest.raises(InterfaceWithUserIdNotFound):
         interface = knx_interface_factory(self.xknx, connection_config)
         await interface.start()
예제 #9
0
    async def test_threaded_connection(self):
        """Test starting threaded connection."""
        # pylint: disable=attribute-defined-outside-init
        self.main_thread = threading.get_ident()

        def assert_thread(*args, **kwargs):
            """Test threaded connection."""
            assert self.main_thread != threading.get_ident()

        connection_config = ConnectionConfig(threaded=True)
        assert connection_config.connection_type == ConnectionType.AUTOMATIC
        with patch("xknx.io.KNXIPInterface._start_automatic",
                   side_effect=assert_thread) as start_automatic_mock:
            interface = knx_interface_factory(self.xknx, connection_config)
            await interface.start()
            start_automatic_mock.assert_called_once_with()
예제 #10
0
파일: xknx.py 프로젝트: onkelbeh/xknx
 async def start(self) -> None:
     """Start XKNX module. Connect to KNX/IP devices and start state updater."""
     if self.connection_config.threaded:
         await self.connection_manager.register_loop()
     self.task_registry.start()
     self.knxip_interface = knx_interface_factory(
         xknx=self,
         connection_config=self.connection_config,
     )
     logger.info(
         "XKNX v%s starting %s connection to KNX bus.",
         VERSION,
         self.connection_config.connection_type.name.lower(),
     )
     await self.knxip_interface.start()
     await self.telegram_queue.start()
     self.state_updater.start()
     self.started.set()
     if self.daemon_mode:
         await self.loop_until_sigint()
예제 #11
0
    async def test_start_automatic_connection(self):
        """Test starting automatic connection."""
        connection_config = ConnectionConfig()
        assert connection_config.connection_type == ConnectionType.AUTOMATIC
        interface = knx_interface_factory(self.xknx, connection_config)
        with patch("xknx.io.KNXIPInterface._start_automatic"
                   ) as start_automatic_mock:
            await interface.start()
            start_automatic_mock.assert_called_once_with()
            assert threading.active_count() == 1

        async def gateway_generator_mock(_):
            yield GatewayDescriptor(ip_addr="10.1.2.3",
                                    port=3671,
                                    supports_tunnelling_tcp=True)
            yield GatewayDescriptor(ip_addr="10.1.2.3",
                                    port=3671,
                                    supports_tunnelling=True)
            yield GatewayDescriptor(ip_addr="10.1.2.3",
                                    port=3671,
                                    supports_routing=True)

        with patch(
                "xknx.io.knxip_interface.GatewayScanner.async_scan",
                new=gateway_generator_mock,
        ), patch(
                "xknx.io.KNXIPInterface._start_tunnelling_tcp",
                side_effect=CommunicationError("Error"),
        ) as start_tunnelling_tcp_mock, patch(
                "xknx.io.KNXIPInterface._start_tunnelling_udp",
                side_effect=CommunicationError("Error"),
        ) as start_tunnelling_udp_mock, patch(
                "xknx.io.KNXIPInterface._start_routing",
                side_effect=CommunicationError("Error"),
        ) as start_routing_mock:
            with pytest.raises(CommunicationError):
                await interface.start()
            start_tunnelling_tcp_mock.assert_called_once()
            start_tunnelling_udp_mock.assert_called_once()
            start_routing_mock.assert_called_once()