python-swidget 1.2.2__tar.gz → 1.2.3__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: python-swidget
3
- Version: 1.2.2
3
+ Version: 1.2.3
4
4
  Summary: Python API for Swidget smart devices
5
5
  Home-page: https://github.com/swidget/python-swidget
6
6
  License: GPL-3.0-or-later
@@ -52,3 +52,4 @@ A library to manage Swidget smart devices
52
52
  dev.turn_on()
53
53
  dev.close()
54
54
  ```
55
+
@@ -18,4 +18,4 @@ A library to manage Swidget smart devices
18
18
  dev.update()
19
19
  dev.turn_on()
20
20
  dev.close()
21
- ```
21
+ ```
@@ -1,6 +1,6 @@
1
1
  [tool.poetry]
2
2
  name = "python-swidget"
3
- version = "1.2.2"
3
+ version = "1.2.3"
4
4
  description = "Python API for Swidget smart devices"
5
5
  license = "GPL-3.0-or-later"
6
6
  authors = ["Swidget"]
@@ -11,25 +11,30 @@ For device type specific actions `SwidgetDimmer`, `SwidgetOutlet`, or `SwidgetSw
11
11
  Module-specific errors are raised as `SwidgetException` and are expected
12
12
  to be handled by the user of the library.
13
13
  """
14
+
14
15
  from importlib_metadata import version # type: ignore
15
16
 
16
- from swidget.discovery import discover_devices, discover_single, SwidgetDiscoveredDevice
17
+ from swidget.discovery import SwidgetDiscoveredDevice, discover_devices, discover_single
17
18
  from swidget.exceptions import SwidgetException
18
19
  from swidget.provision import provision_wifi
19
- from swidget.swidgetdevice import DeviceType, SwidgetAssembly, SwidgetDevice, SwidgetComponent
20
+ from swidget.swidgetdevice import (
21
+ DeviceType,
22
+ SwidgetAssembly,
23
+ SwidgetComponent,
24
+ SwidgetDevice,
25
+ )
20
26
  from swidget.swidgetdimmer import SwidgetDimmer
21
27
  from swidget.swidgetoutlet import SwidgetOutlet
22
28
  from swidget.swidgetswitch import SwidgetSwitch
23
29
  from swidget.swidgettimerswitch import SwidgetTimerSwitch
24
30
 
25
-
26
31
  __version__ = version("python-swidget")
27
32
 
28
33
 
29
34
  __all__ = [
30
35
  "discover_devices",
31
36
  "discover_single",
32
- "provision_wifi"
37
+ "provision_wifi",
33
38
  "SwidgetDiscoveredDevice",
34
39
  "SwidgetException",
35
40
  "DeviceType",
@@ -40,4 +45,4 @@ __all__ = [
40
45
  "SwidgetOutlet",
41
46
  "SwidgetSwitch",
42
47
  "SwidgetTimerSwitch",
43
- ]
48
+ ]
@@ -1,28 +1,29 @@
1
1
  """python-swidget cli tool."""
2
+
2
3
  import logging
3
4
  import sys
4
- from typing import Any, cast
5
+ from contextlib import asynccontextmanager
5
6
  from pprint import pformat as pf
7
+ from typing import Any, cast
6
8
 
7
9
  import asyncclick as click
8
- from contextlib import asynccontextmanager
9
10
 
10
11
  from swidget import (
11
- discover_devices,
12
- discover_single,
13
- provision_wifi,
14
12
  SwidgetDevice,
15
13
  SwidgetDimmer,
16
- SwidgetSwitch,
17
14
  SwidgetOutlet,
18
- SwidgetTimerSwitch
15
+ SwidgetSwitch,
16
+ SwidgetTimerSwitch,
17
+ discover_devices,
18
+ discover_single,
19
+ provision_wifi,
19
20
  )
20
21
 
21
22
  TYPE_TO_CLASS = {
22
23
  "dimmer": SwidgetDimmer,
23
24
  "switch": SwidgetSwitch,
24
25
  "outlet": SwidgetOutlet,
25
- "pana_switch": SwidgetTimerSwitch
26
+ "pana_switch": SwidgetTimerSwitch,
26
27
  }
27
28
 
28
29
 
@@ -30,24 +31,23 @@ pass_dev = click.make_pass_decorator(SwidgetDevice)
30
31
 
31
32
 
32
33
  @click.group(invoke_without_command=True)
33
- @click.option("--host",
34
+ @click.option(
35
+ "--host",
34
36
  envvar="SWIDGET_HOST",
35
37
  required=False,
36
38
  help="The host name or IP address of the device to connect to.",
37
39
  )
38
- @click.option("-p", "--password",
40
+ @click.option(
41
+ "-p",
42
+ "--password",
39
43
  envvar="SWIDGET_PASSWORD",
40
44
  required=False,
41
45
  help="The password of the device to connect to.",
42
46
  )
43
- @click.option("-d", "--debug",
44
- envvar="SWIDGET_DEBUG",
45
- default=False,
46
- is_flag=True)
47
- @click.option("--http_only",
48
- envvar="SWIDGET_HTTP_ONLY",
49
- default=True,
50
- is_flag=True)
47
+ @click.option("-d", "--debug", envvar="SWIDGET_DEBUG", default=False, is_flag=True)
48
+ @click.option(
49
+ "-ho", "--http_only", envvar="SWIDGET_HTTP_ONLY", default=True, is_flag=True
50
+ )
51
51
  @click.option(
52
52
  "--type",
53
53
  envvar="SWIDGET_TYPE",
@@ -74,18 +74,22 @@ async def cli(ctx, host, password, debug, http_only, type):
74
74
  await ctx.invoke(discover)
75
75
  return
76
76
  if type is not None:
77
- dev = TYPE_TO_CLASS[type](host=host,
78
- token_name='x-secret-key',
79
- secret_key=password,
80
- use_https=http_only,
81
- use_websockets=False)
77
+ dev = TYPE_TO_CLASS[type](
78
+ host=host,
79
+ token_name="x-secret-key",
80
+ secret_key=password,
81
+ use_https=http_only,
82
+ use_websockets=False,
83
+ )
82
84
  else:
83
85
  click.echo("No --type defined, discovering...")
84
- dev = await discover_single(host=host,
85
- token_name='x-secret-key',
86
- password=password,
87
- use_https=http_only,
88
- use_websockets=False)
86
+ dev = await discover_single(
87
+ host=host,
88
+ token_name="x-secret-key",
89
+ password=password,
90
+ use_https=http_only,
91
+ use_websockets=False,
92
+ )
89
93
  await dev.update()
90
94
 
91
95
  @asynccontextmanager
@@ -113,11 +117,15 @@ def wifi():
113
117
  @click.option("--friendly_name", prompt=True, hide_input=False)
114
118
  def join(ssid, network_password, secret_key, friendly_name):
115
119
  """Join the given wifi network."""
116
- confirmation = click.prompt(f"Are you connected to a wifi network that stars with the name 'Swidget-' (y/n)")
120
+ confirmation = click.prompt(
121
+ "Are you connected to a wifi network that stars with the name 'Swidget-' (y/n)"
122
+ )
117
123
  if confirmation == "y":
118
124
  click.echo(f"Asking the device to connect to network {ssid}..")
119
125
  provision_wifi(friendly_name, ssid, network_password, secret_key)
120
- click.echo(f"Disconnect from the `swidget` network and connect back your main WiFi network")
126
+ click.echo(
127
+ "Disconnect from the 'swidget' network and connect back your main WiFi network"
128
+ )
121
129
  return True
122
130
  else:
123
131
  click.echo("Not provisioning wifi")
@@ -135,6 +143,7 @@ async def discover(ctx, timeout):
135
143
  for device in devices.values():
136
144
  click.echo(f"{device.host}[{device.mac}] - {device.friendly_name}")
137
145
 
146
+
138
147
  @cli.command()
139
148
  @pass_dev
140
149
  async def hwinfo(dev):
@@ -149,7 +158,7 @@ async def hwinfo(dev):
149
158
  async def state(dev: SwidgetDevice):
150
159
  """Print out device state and versions."""
151
160
  click.echo(click.style(f"== {dev.friendly_name} - {dev.model} ==", bold=True))
152
- click.echo(f"\tFriendly Name: {dev.friendly_name}")
161
+ click.echo(f"\tFriendly Name: {dev.friendly_name}")
153
162
  click.echo(f"\tHost: {dev.ip_address}")
154
163
  click.echo(
155
164
  click.style(
@@ -159,9 +168,9 @@ async def state(dev: SwidgetDevice):
159
168
  )
160
169
 
161
170
  click.echo(click.style("\t== Generic information ==", bold=True))
162
- click.echo(f"\tHardware: {dev.hw_info['model']}")
163
- click.echo(f"\tSoftware: {dev.hw_info['version']}")
164
- click.echo(f"\tMAC (rssi): {dev.mac_address} ({dev.rssi})")
171
+ click.echo(f"\tHardware: {dev.hw_info['model']}")
172
+ click.echo(f"\tSoftware: {dev.hw_info['version']}")
173
+ click.echo(f"\tMAC (rssi): {dev.mac_address} ({dev.rssi})")
165
174
 
166
175
  click.echo(click.style("\n\t== Current State ==", bold=True))
167
176
  realtime_values = dev.realtime_values
@@ -177,7 +186,6 @@ async def state(dev: SwidgetDevice):
177
186
  for function in dev.host_features:
178
187
  click.echo(click.style(f"\t+ {function}", fg="green"))
179
188
 
180
-
181
189
  click.echo(click.style("\n\t== Insert Features ==", bold=True))
182
190
  for function in dev.insert_features:
183
191
  click.echo(click.style(f"\t+ {function}", fg="green"))
@@ -198,7 +206,8 @@ async def raw_command(dev: SwidgetDevice, assembly, component, function, command
198
206
  @cli.command()
199
207
  @click.argument("brightness", type=click.IntRange(0, 100), default=None, required=False)
200
208
  @pass_dev
201
- async def brightness(dev: SwidgetDevice, brightness: Any=None):
209
+ async def brightness(dev: SwidgetDevice, brightness: Any = None):
210
+ """Get or set the brightness of a dimmer device."""
202
211
  dimmer_dev = cast(SwidgetDimmer, dev)
203
212
  """Get or set brightness."""
204
213
  if not dimmer_dev.is_dimmer:
@@ -215,25 +224,26 @@ async def brightness(dev: SwidgetDevice, brightness: Any=None):
215
224
  @cli.command()
216
225
  @pass_dev
217
226
  async def blink(dev):
218
- """Set the device insert to blink"""
219
- click.echo(f"Requesting the device to blink")
227
+ """Set the device insert to blink."""
228
+ click.echo("Requesting the device to blink")
220
229
  return await dev.blink()
221
230
 
222
231
 
223
232
  @cli.command()
224
233
  @pass_dev
225
234
  async def ping(dev):
226
- """Ping the device"""
227
- click.echo(f"Pinging the device")
235
+ """Ping the device."""
236
+ click.echo("Pinging the device")
228
237
  try:
229
238
  result = await dev.ping()
230
239
  if result == 200:
231
240
  click.echo("Successfully pinged device")
232
241
  else:
233
242
  click.echo(result.status_code)
234
- except:
243
+ except Exception:
235
244
  click.echo("Unable to ping device")
236
245
 
246
+
237
247
  @cli.command()
238
248
  @pass_dev
239
249
  async def on(dev: SwidgetDevice):
@@ -253,14 +263,15 @@ async def off(dev: SwidgetDevice):
253
263
  @cli.command()
254
264
  @pass_dev
255
265
  async def enable_debug_server(dev: SwidgetDevice):
256
- """Enable Debug Server"""
257
- click.echo(f"Enabling debug server")
266
+ """Enable Debug Server."""
267
+ click.echo("Enabling debug server")
258
268
  return await dev.enable_debug_server()
259
269
 
260
270
 
261
271
  @cli.command()
262
272
  @pass_dev
263
273
  async def check_for_updates(dev: SwidgetDevice):
274
+ """Connect to Swidget Cloud to see if there are any updates available for the insert."""
264
275
  click.echo("Contacting Swidget servers to fetch for updates...")
265
276
  available_updates = await dev.check_for_updates()
266
277
  if len(available_updates) == 0:
@@ -275,6 +286,7 @@ async def check_for_updates(dev: SwidgetDevice):
275
286
  @click.option("--version", required=False)
276
287
  @pass_dev
277
288
  async def upgrade(dev: SwidgetDevice, version: str):
289
+ """Update the device to a newer version."""
278
290
  if version is None:
279
291
  click.echo("Contacting Swidget servers to fetch for latest version")
280
292
  available_updates = await dev.check_for_updates()
@@ -1,3 +1,4 @@
1
+ """Module to discover Swidget devices."""
1
2
  import asyncio
2
3
  import logging
3
4
  import socket
@@ -7,11 +8,12 @@ from urllib.parse import urlparse
7
8
  import ssdp # type: ignore
8
9
 
9
10
  from swidget.swidgetdevice import DeviceType, SwidgetDevice
11
+
12
+ from .exceptions import SwidgetException
10
13
  from .swidgetdimmer import SwidgetDimmer
11
14
  from .swidgetoutlet import SwidgetOutlet
12
15
  from .swidgetswitch import SwidgetSwitch
13
16
  from .swidgettimerswitch import SwidgetTimerSwitch
14
- from .exceptions import SwidgetException
15
17
 
16
18
  RESPONSE_SEC = 5
17
19
  SWIDGET_ST = "urn:swidget:pico:1"
@@ -20,16 +22,28 @@ devices = dict()
20
22
 
21
23
 
22
24
  class SwidgetDiscoveredDevice:
23
- def __init__(self, mac: str, host: str, friendly_name: str = "Swidget Discovered Device"):
25
+ """Stub class to capture details about discovered devices."""
26
+
27
+ def __init__(
28
+ self,
29
+ mac: str,
30
+ host: str,
31
+ host_type: str,
32
+ insert_type: str,
33
+ friendly_name: str = "Swidget Discovered Device",
34
+ ):
24
35
  self.mac = mac
25
36
  self.host = host
26
37
  self.friendly_name = friendly_name
38
+ self.host_type = host_type
39
+ self.insert_type = insert_type
27
40
 
28
41
 
29
42
  class SwidgetProtocol(ssdp.SimpleServiceDiscoveryProtocol):
30
43
  """Protocol to handle responses and requests."""
44
+
31
45
  def response_received(self, response: ssdp.SSDPResponse, addr: tuple):
32
- "Handle an incoming response."
46
+ """Handle an incoming response."""
33
47
  headers = {h[0]: h[1] for h in response.headers}
34
48
  mac_address = headers["USN"].split("-")[-1]
35
49
  ip_address = urlparse(headers["LOCATION"]).hostname
@@ -37,11 +51,20 @@ class SwidgetProtocol(ssdp.SimpleServiceDiscoveryProtocol):
37
51
  device_type = headers["SERVER"].split(" ")[1].split("+")[0]
38
52
  insert_type = headers["SERVER"].split(" ")[1].split("+")[1].split("/")[0]
39
53
  friendly_name = headers["SERVER"].split("/")[2].strip('"')
40
- devices[mac_address] = SwidgetDiscoveredDevice(mac_address, ip_address, friendly_name)
41
- _LOGGER.debug(f"Swidget device '{friendly_name}' at {ip_address}. {device_type}/{insert_type}")
54
+ devices[mac_address] = SwidgetDiscoveredDevice(
55
+ mac=mac_address,
56
+ host=ip_address,
57
+ friendly_name=friendly_name,
58
+ host_type=device_type,
59
+ insert_type=insert_type,
60
+ )
61
+ _LOGGER.debug(
62
+ f"Swidget device '{friendly_name}' at {ip_address}. {device_type}/{insert_type}"
63
+ )
42
64
 
43
65
 
44
66
  async def discover_devices(timeout=RESPONSE_SEC):
67
+ """Discover devices via SSDP."""
45
68
  global devices
46
69
  loop = asyncio.get_event_loop()
47
70
  devices = dict()
@@ -64,7 +87,9 @@ async def discover_devices(timeout=RESPONSE_SEC):
64
87
  return devices
65
88
 
66
89
 
67
- async def discover_single(host: str, token_name: str, password: str, use_https: bool, use_websockets: bool) -> Any:
90
+ async def discover_single(
91
+ host: str, token_name: str, password: str, use_https: bool, use_websockets: bool
92
+ ) -> Any:
68
93
  """Discover a single device by the given IP address.
69
94
 
70
95
  :param host: Hostname of device to query
@@ -72,7 +97,9 @@ async def discover_single(host: str, token_name: str, password: str, use_https:
72
97
  :return: Object for querying/controlling found device.
73
98
  """
74
99
  _LOGGER.debug(f"Checking for device at {host}")
75
- swidget_device = SwidgetDevice(host, token_name, password, use_https, use_websockets=False)
100
+ swidget_device = SwidgetDevice(
101
+ host, token_name, password, use_https, use_websockets=False
102
+ )
76
103
  _LOGGER.debug(f"Asking {host} for summary data")
77
104
  await swidget_device.get_summary()
78
105
  device_type = swidget_device.device_type
@@ -95,7 +122,7 @@ def _get_device_class(device_type: DeviceType) -> Type[SwidgetDevice]:
95
122
  return SwidgetSwitch
96
123
  elif device_type == DeviceType.Dimmer:
97
124
  return SwidgetDimmer
98
- elif device_type == DeviceType.TimerSwitch: # This is the timer switch
125
+ elif device_type == DeviceType.TimerSwitch: # This is the timer switch
99
126
  return SwidgetTimerSwitch
100
127
  elif device_type == DeviceType.RelaySwitch:
101
128
  return SwidgetSwitch
@@ -1,42 +1,48 @@
1
- from enum import Enum
1
+ """Provision the Swidget device in local-only mode."""
2
2
  import time
3
+ from enum import Enum
3
4
 
4
- import requests
5
+ import requests # type: ignore
5
6
  import urllib3
6
7
 
7
8
  urllib3.disable_warnings()
8
9
 
9
10
 
10
11
  class DeviceConnectionResult(str, Enum):
11
- NoStarted = "NotInitiated",
12
- InProgress ="AttemptingConnect",
13
- Success = "Success",
14
- AuthenticationFailure = "AuthFail",
15
- SSIDNotFound = "SSIDNotFound",
16
- NoIp = "NoIpReceived",
12
+ """Enum class for provisioning results."""
13
+
14
+ NoStarted = ("NotInitiated",)
15
+ InProgress = ("AttemptingConnect",)
16
+ Success = ("Success",)
17
+ AuthenticationFailure = ("AuthFail",)
18
+ SSIDNotFound = ("SSIDNotFound",)
19
+ NoIp = ("NoIpReceived",)
17
20
  ConnectionFailure = "FailedToConnect"
18
21
 
19
22
 
20
23
  def send_credentials(device_name, ssid, network_password, secret_key):
21
- payload = {"name": device_name,
22
- "ssid": ssid,
23
- "password": network_password,
24
- "secretKey": secret_key}
24
+ """Send the credentials to the Swidget device."""
25
+ payload = {
26
+ "name": device_name,
27
+ "ssid": ssid,
28
+ "password": network_password,
29
+ "secretKey": secret_key,
30
+ }
25
31
  url = "https://10.123.45.1/network"
26
32
  sentProvisionRequestAttempts = 0
27
33
 
28
34
  while True:
29
35
  print(f"Provision Attempt: {sentProvisionRequestAttempts}")
30
36
  if sentProvisionRequestAttempts >= 5:
31
- print(f"Provision failed, Ensure you're connected to the device's hotspot.")
37
+ print("Provision failed, Ensure you're connected to the device's hotspot.")
32
38
  return False, None
33
39
  try:
34
40
  initial_provision = requests.post(url, json=payload, verify=False)
35
41
  if initial_provision.status_code == 200:
36
- print(f"Provision Success")
42
+ print("Provision Success")
37
43
  return True, initial_provision.json()["secretKey"]
38
44
  else:
39
- print(f"Provision Failed: {initial_provision.json()}")
45
+ print("Provision Failed: {initial_provision.json()}")
40
46
  return False, None
41
47
  except Exception as e:
42
48
  print("Error", e)
@@ -45,61 +51,73 @@ def send_credentials(device_name, ssid, network_password, secret_key):
45
51
 
46
52
 
47
53
  def verify_connect_result(key):
48
- headers = {'x-secret-key': key}
49
- connect_success = False
54
+ """Function to query the device and verify if the device is successfully provisioned."""
55
+ headers = {"x-secret-key": key}
50
56
  connect_verification_attempts = 0
51
- while not connect_success:
57
+ while connect_verification_attempts < 5:
52
58
  url = "https://10.123.45.1/network"
53
- if connect_verification_attempts >= 5:
54
- return False, None, None, "Failed to connect to device"
55
59
  try:
56
60
  verify_connection = requests.get(url, headers=headers, verify=False)
57
61
  print(f"Verify Response: {verify_connection.json()}")
58
62
  if verify_connection.status_code == 200:
59
63
  print(f"Verification request success: {verify_connection.json()}")
60
64
  connect_status = verify_connection.json()["status"]
61
- if connect_status == DeviceConnectionResult.Success:
62
- return True, verify_connection.json()["ip"], verify_connection.json()["mac"], None
63
- elif connect_status == DeviceConnectionResult.InProgress:
64
- pass
65
+ if connect_status == "Success":
66
+ return (
67
+ True,
68
+ verify_connection.json()["ip"],
69
+ verify_connection.json()["mac"],
70
+ None,
71
+ )
72
+ elif connect_status == "InProgress":
73
+ time.sleep(5)
74
+ connect_verification_attempts += 1
75
+ continue
65
76
  else:
66
77
  return False, None, None, connect_status
67
78
  else:
68
79
  print(f"Verification request failure: {verify_connection.json()}")
80
+ time.sleep(5)
81
+ except Exception as e:
82
+ print(e)
69
83
  time.sleep(5)
70
- except:
71
- time.sleep(5)
72
- connect_verification_attempts += 1
84
+ connect_verification_attempts += 1
85
+ return False, None, None, "Internal server error"
73
86
 
74
87
 
75
88
  def provision_wifi(device_name, ssid, network_password, secret_key):
89
+ """Main function to provision credentials to the Swidget device."""
76
90
  print(f"Device_name: {device_name}")
77
91
  print(f"SSID: {ssid}")
78
- print(f"Network Password: <redacted>")
79
- print(f"Swidget Secret Key: <redacted>")
92
+ print("Network Password: <redacted>")
93
+ print("Swidget Secret Key: <redacted>")
80
94
 
81
- send_success, key = send_credentials(device_name, ssid, network_password, secret_key)
95
+ send_success, key = send_credentials(
96
+ device_name, ssid, network_password, secret_key
97
+ )
82
98
  if not send_success:
83
99
  return False
84
- secret_key = key # we set the key to whatever was returned from the device. this handles the case of an empty string (which causes insert to generate a key)
100
+ secret_key = key # we set the key to whatever was returned from the device. this handles the case of an empty string (which causes insert to generate a key)
85
101
 
86
102
  verify_success, ip, mac, errorMessage = verify_connect_result(secret_key)
87
103
  if not verify_success:
88
104
  print(f"Verify Error: {errorMessage}")
89
105
  return False
90
106
  print(f"Verified Connection: {ip} {mac}")
91
- headers = {'x-secret-key': secret_key}
107
+ headers = {"x-secret-key": secret_key}
92
108
  # the device will remain in AP mode for 60 seconds before switching over to control mode. This is to allow time to send requests to update the device
93
109
  # without swiching networks.
94
110
 
95
111
  # issuing the setup_complete request will skip the 60s time
96
- complete_setup = requests.get("https://10.123.45.1/setup_complete", headers=headers, verify=False)
112
+ complete_setup = requests.get(
113
+ "https://10.123.45.1/setup_complete", headers=headers, verify=False
114
+ )
97
115
  if complete_setup.status_code == 200:
98
116
  print("Setup complete, enabled control server")
99
117
  else:
100
118
  return False
101
119
 
102
- #alternatively, sleep for some time
120
+ # alternatively, sleep for some time
103
121
  print("Device has been configured, switch your wifi network off `Swidget-` now")
104
122
  time.sleep(30)
105
123
 
@@ -109,8 +127,10 @@ def provision_wifi(device_name, ssid, network_password, secret_key):
109
127
  try:
110
128
  url = f"https://{ip}/api/v1/name"
111
129
  verify_name = requests.get(url, headers=headers, verify=False).json()
112
- print(f"Verifying device name has been set: {verify_name}. Provisioning complete")
130
+ print(
131
+ f"Verifying device name has been set: {verify_name}. Provisioning complete"
132
+ )
113
133
  return True
114
- except:
134
+ except Exception:
115
135
  print("Connect to provided network")
116
- time.sleep(5)
136
+ time.sleep(5)