This commit is contained in:
emdee@macaw.me 2023-12-14 20:46:56 +00:00
parent b934928fe3
commit 012c7ea56e
8 changed files with 388 additions and 286 deletions

File diff suppressed because it is too large Load diff

View file

@ -11,6 +11,7 @@ try:
except:
from libtox import LibToxAV
import toxav_enums as enum
class ToxError(RuntimeError): pass
def LOG_ERROR(a: str) -> None: print('EROR> '+a)
def LOG_WARN(a: str) -> None: print('WARN> '+a)
@ -91,7 +92,7 @@ class ToxAV:
# Call setup
def call(self, friend_number: int, audio_bit_rate: int, video_bit_rate: int) -> None:
def call(self, friend_number: int, audio_bit_rate: int, video_bit_rate: int) -> bool:
"""
Call a friend. This will start ringing the friend.
@ -111,22 +112,22 @@ class ToxAV:
toxav_err_call = toxav_err_call.value
if toxav_err_call == enum.TOXAV_ERR_CALL['OK']:
return bool(result)
elif toxav_err_call == enum.TOXAV_ERR_CALL['MALLOC']:
if toxav_err_call == enum.TOXAV_ERR_CALL['MALLOC']:
raise MemoryError('A resource allocation error occurred while trying to create the structures required for '
'the call.')
elif toxav_err_call == enum.TOXAV_ERR_CALL['SYNC']:
if toxav_err_call == enum.TOXAV_ERR_CALL['SYNC']:
raise RuntimeError('Synchronization error occurred.')
elif toxav_err_call == enum.TOXAV_ERR_CALL['FRIEND_NOT_FOUND']:
if toxav_err_call == enum.TOXAV_ERR_CALL['FRIEND_NOT_FOUND']:
raise ArgumentError('The friend number did not designate a valid friend.')
elif toxav_err_call == enum.TOXAV_ERR_CALL['FRIEND_NOT_CONNECTED']:
if toxav_err_call == enum.TOXAV_ERR_CALL['FRIEND_NOT_CONNECTED']:
raise ArgumentError('The friend was valid, but not currently connected.')
elif toxav_err_call == enum.TOXAV_ERR_CALL['FRIEND_ALREADY_IN_CALL']:
if toxav_err_call == enum.TOXAV_ERR_CALL['FRIEND_ALREADY_IN_CALL']:
raise ArgumentError('Attempted to call a friend while already in an audio or video call with them.')
elif toxav_err_call == enum.TOXAV_ERR_CALL['INVALID_BIT_RATE']:
if toxav_err_call == enum.TOXAV_ERR_CALL['INVALID_BIT_RATE']:
raise ArgumentError('Audio or video bit rate is invalid.')
raise ArgumentError('The function did not return OK')
def callback_call(self, callback: Callable, user_data) -> None:
def callback_call(self, callback: Union[Callable,None], user_data) -> None:
"""
Set the callback for the `call` event. Pass None to unset.
@ -148,7 +149,7 @@ class ToxAV:
self.call_cb = c_callback(callback)
self.libtoxav.toxav_callback_call(self._toxav_pointer, self.call_cb, user_data)
def answer(self, friend_number: int, audio_bit_rate: int, video_bit_rate: int) -> None:
def answer(self, friend_number: int, audio_bit_rate: int, video_bit_rate: int) -> bool:
"""
Accept an incoming call.
@ -186,7 +187,7 @@ class ToxAV:
# Call state graph
def callback_call_state(self, callback: Callable, user_data) -> None:
def callback_call_state(self, callback: Union[Callable,None], user_data) -> None:
"""
Set the callback for the `call_state` event. Pass None to unset.
@ -211,7 +212,7 @@ class ToxAV:
# Call control
def call_control(self, friend_number: int, control: int) -> None:
def call_control(self, friend_number: int, control: int) -> bool:
"""
Sends a call control command to a friend.
@ -221,8 +222,10 @@ class ToxAV:
"""
toxav_err_call_control = c_int()
LOG_DEBUG(f"call_control")
result = self.libtoxav.toxav_call_control(self._toxav_pointer, c_uint32(friend_number), c_int(control),
byref(toxav_err_call_control))
result = self.libtoxav.toxav_call_control(self._toxav_pointer,
c_uint32(friend_number),
c_int(control),
byref(toxav_err_call_control))
toxav_err_call_control = toxav_err_call_control.value
if toxav_err_call_control == enum.TOXAV_ERR_CALL_CONTROL['OK']:
return bool(result)
@ -242,7 +245,7 @@ class ToxAV:
# A/V sending
def audio_send_frame(self, friend_number: int, pcm, sample_count: int, channels: int, sampling_rate: int) -> None:
def audio_send_frame(self, friend_number: int, pcm, sample_count: int, channels: int, sampling_rate: int) -> bool:
"""
Send an audio frame to a friend.
@ -288,7 +291,7 @@ class ToxAV:
RuntimeError('Failed to push frame through rtp interface.')
raise ToxError('The function did not return OK.')
def video_send_frame(self, friend_number: int, width: int, height: int, y, u, v) -> None:
def video_send_frame(self, friend_number: int, width: int, height: int, y, u, v) -> bool:
"""
Send a video frame to a friend.
@ -316,26 +319,27 @@ class ToxAV:
toxav_err_send_frame = toxav_err_send_frame.value
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['OK']:
return bool(result)
elif toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['NULL']:
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['NULL']:
raise ArgumentError('One of Y, U, or V was NULL.')
elif toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['FRIEND_NOT_FOUND']:
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['FRIEND_NOT_FOUND']:
raise ArgumentError('The friend_number passed did not designate a valid friend.')
elif toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['FRIEND_NOT_IN_CALL']:
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['FRIEND_NOT_IN_CALL']:
raise RuntimeError('This client is currently not in a call with the friend.')
elif toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['SYNC']:
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['SYNC']:
raise RuntimeError('Synchronization error occurred.')
elif toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['INVALID']:
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['INVALID']:
raise ArgumentError('One of the frame parameters was invalid. E.g. the resolution may be too small or too '
'large, or the audio sampling rate may be unsupported.')
elif toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['PAYLOAD_TYPE_DISABLED']:
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['PAYLOAD_TYPE_DISABLED']:
raise RuntimeError('Either friend turned off audio or video receiving or we turned off sending for the said'
'payload.')
elif toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['RTP_FAILED']:
if toxav_err_send_frame == enum.TOXAV_ERR_SEND_FRAME['RTP_FAILED']:
RuntimeError('Failed to push frame through rtp interface.')
raise ToxError('The function did not return OK.')
# A/V receiving
def callback_audio_receive_frame(self, callback: Callable, user_data) -> None:
def callback_audio_receive_frame(self, callback: Union[Callable,None], user_data) -> None:
"""
Set the callback for the `audio_receive_frame` event. Pass None to unset.
@ -364,7 +368,7 @@ class ToxAV:
self.audio_receive_frame_cb = c_callback(callback)
self.libtoxav.toxav_callback_audio_receive_frame(self._toxav_pointer, self.audio_receive_frame_cb, user_data)
def callback_video_receive_frame(self, callback: Callable, user_data) -> None:
def callback_video_receive_frame(self, callback: Union[Callable,None], user_data) -> None:
"""
Set the callback for the `video_receive_frame` event. Pass None to unset.

View file

@ -27,7 +27,7 @@ class ToxEncryptSave:
result = func(c_char_p(bytes(data)))
return bool(result)
def pass_encrypt(self, data: bytes, password: str) -> bytes:
def pass_encrypt(self, data: bytes, password: Union[str,bytes]) -> bytes:
"""
Encrypts the given data with the given password.
@ -35,6 +35,7 @@ class ToxEncryptSave:
"""
out = create_string_buffer(len(data) + enum.TOX_PASS_ENCRYPTION_EXTRA_LENGTH)
tox_err_encryption = c_int()
assert password
if type(password) != bytes:
password = bytes(password, 'utf-8')
self.libtoxencryptsave.tox_pass_encrypt(c_char_p(data),
@ -45,7 +46,7 @@ class ToxEncryptSave:
byref(tox_err_encryption))
tox_err_encryption = tox_err_encryption.value
if tox_err_encryption == enum.TOX_ERR_ENCRYPTION['OK']:
return out[:]
return bytes(out[:])
if tox_err_encryption == enum.TOX_ERR_ENCRYPTION['NULL']:
raise ArgumentError('Some input data, or maybe the output pointer, was null.')
if tox_err_encryption == enum.TOX_ERR_ENCRYPTION['KEY_DERIVATION_FAILED']:
@ -55,7 +56,7 @@ class ToxEncryptSave:
raise RuntimeError('The encryption itself failed.')
raise ToxError('The function did not return OK.')
def pass_decrypt(self, data: bytes, password: str) -> bytes:
def pass_decrypt(self, data: bytes, password: Union[str,bytes]) -> bytes:
"""
Decrypts the given data with the given password.
@ -63,6 +64,7 @@ class ToxEncryptSave:
"""
out = create_string_buffer(len(data) - enum.TOX_PASS_ENCRYPTION_EXTRA_LENGTH)
tox_err_decryption = c_int()
assert password
if type(password) != bytes:
password = bytes(password, 'utf-8')
self.libtoxencryptsave.tox_pass_decrypt(c_char_p(bytes(data)),
@ -74,16 +76,17 @@ class ToxEncryptSave:
tox_err_decryption = tox_err_decryption.value
if tox_err_decryption == enum.TOX_ERR_DECRYPTION['OK']:
return bytes(out[:])
elif tox_err_decryption == enum.TOX_ERR_DECRYPTION['NULL']:
if tox_err_decryption == enum.TOX_ERR_DECRYPTION['NULL']:
raise ArgumentError('Some input data, or maybe the output pointer, was null.')
elif tox_err_decryption == enum.TOX_ERR_DECRYPTION['INVALID_LENGTH']:
if tox_err_decryption == enum.TOX_ERR_DECRYPTION['INVALID_LENGTH']:
raise ArgumentError('The input data was shorter than TOX_PASS_ENCRYPTION_EXTRA_LENGTH bytes')
elif tox_err_decryption == enum.TOX_ERR_DECRYPTION['BAD_FORMAT']:
if tox_err_decryption == enum.TOX_ERR_DECRYPTION['BAD_FORMAT']:
raise ArgumentError('The input data is missing the magic number (i.e. wasn\'t created by this module, or is'
' corrupted)')
elif tox_err_decryption == enum.TOX_ERR_DECRYPTION['KEY_DERIVATION_FAILED']:
if tox_err_decryption == enum.TOX_ERR_DECRYPTION['KEY_DERIVATION_FAILED']:
raise RuntimeError('The crypto lib was unable to derive a key from the given passphrase, which is usually a'
' lack of memory issue. The functions accepting keys do not produce this error.')
elif tox_err_decryption == enum.TOX_ERR_DECRYPTION['FAILED']:
if tox_err_decryption == enum.TOX_ERR_DECRYPTION['FAILED']:
raise RuntimeError('The encrypted byte array could not be decrypted. Either the data was corrupt or the '
'password/key was incorrect.')
raise ToxError('The function did not return OK.')

View file

@ -29,7 +29,7 @@ def LOG_info(a): print('INFO_ '+a)
def LOG_debug(a): print('DBUG_ '+a)
def LOG_trace(a): pass # print('TRAC_ '+a)
import wrapper
from wrapper import tox
import wrapper.toxcore_enums_and_consts as enums
from wrapper.tox import Tox, UINT32_MAX
from wrapper.toxcore_enums_and_consts import TOX_CONNECTION, TOX_USER_STATUS, \
@ -69,7 +69,7 @@ iDHT_TRY = 0
if not bHAVE_AV:
class AV(): pass
else:
class AV(wrapper.tox.ToxAV):
class AV(tox.ToxAV):
def __init__(self, core):
super(AV, self).__init__(core)
self.core = self.get_tox()
@ -147,7 +147,7 @@ class EchoBot():
message_data_size,
*largs) -> None:
key = ''.join(chr(x) for x in public_key[:TOX_PUBLIC_KEY_SIZE])
sPk = wrapper.tox.bin_to_string(key, TOX_PUBLIC_KEY_SIZE)
sPk = tox.bin_to_string(key, TOX_PUBLIC_KEY_SIZE)
sMd = str(message_data, 'UTF-8')
LOG.debug('on_friend_request ' +sPk +' ' +sMd)
self.on_friend_request(sPk, sMd)