From f689e36378c55e8cf6805f7f37f4a7f015ca65bb Mon Sep 17 00:00:00 2001 From: netkas Date: Fri, 24 Jan 2025 15:10:20 -0500 Subject: [PATCH] Refactored Peer Information to use InformationFields rather than being hard-coded into the peer record --- .idea/sqldialects.xml | 4 +- src/Socialbox/Classes/Configuration.php | 14 + .../Configuration/PoliciesConfiguration.php | 112 ++++ .../RegistrationConfiguration.php | 48 ++ .../Resources/database/authentication_otp.sql | 2 +- .../Resources/database/captcha_images.sql | 2 +- .../Resources/database/peer_information.sql | 19 + .../Classes/Resources/database/peers.sql | 37 ++ .../Resources/database/registered_peers.sql | 39 -- .../Classes/Resources/database/sessions.sql | 2 +- .../SettingsAddInformationField.php | 147 +++++ .../SettingsDeleteBirthday.php | 38 -- .../SettingsDeleteDisplayName.php | 38 -- .../SettingsDeleteDisplayPicture.php | 38 -- .../SettingsDeleteEmailAddress.php | 38 -- .../SettingsDeleteInformationField.php | 119 ++++ .../SettingsDeletePhoneNumber.php | 38 -- .../SettingsGetInformationFields.php | 32 ++ .../StandardMethods/SettingsSetBirthday.php | 63 --- .../SettingsSetDisplayName.php | 48 -- .../SettingsSetDisplayPicture.php | 65 --- .../SettingsSetEmailAddress.php | 50 -- .../SettingsSetPhoneNumber.php | 49 -- .../SettingsUpdateInformationField.php | 62 +++ .../SettingsUpdateInformationPrivacy.php | 64 +++ src/Socialbox/Enums/DatabaseObjects.php | 6 +- src/Socialbox/Enums/Flags/SessionFlags.php | 18 +- src/Socialbox/Enums/PrivacyState.php | 11 + src/Socialbox/Enums/StandardMethods.php | 144 ++--- .../Enums/Types/InformationFieldName.php | 71 +++ src/Socialbox/Managers/CaptchaManager.php | 26 +- .../Managers/OneTimePasswordManager.php | 30 +- src/Socialbox/Managers/PasswordManager.php | 32 +- .../Managers/PeerInformationManager.php | 282 ++++++++++ .../Managers/RegisteredPeerManager.php | 508 ++---------------- src/Socialbox/Managers/SessionManager.php | 6 +- src/Socialbox/Objects/ClientRequest.php | 6 +- .../Database/PeerInformationFieldRecord.php | 105 ++++ ...egisteredPeerRecord.php => PeerRecord.php} | 89 +-- .../Objects/Standard/InformationField.php | 53 ++ .../Standard/InformationFieldState.php | 62 +++ src/Socialbox/Objects/Standard/SelfUser.php | 8 +- src/Socialbox/SocialClient.php | 125 ++--- src/Socialbox/Socialbox.php | 4 +- tests/Socialbox/SocialClientTest.php | 5 +- 45 files changed, 1422 insertions(+), 1337 deletions(-) create mode 100644 src/Socialbox/Classes/Resources/database/peer_information.sql create mode 100644 src/Socialbox/Classes/Resources/database/peers.sql delete mode 100644 src/Socialbox/Classes/Resources/database/registered_peers.sql create mode 100644 src/Socialbox/Classes/StandardMethods/SettingsAddInformationField.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsDeleteBirthday.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayName.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayPicture.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsDeleteEmailAddress.php create mode 100644 src/Socialbox/Classes/StandardMethods/SettingsDeleteInformationField.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsDeletePhoneNumber.php create mode 100644 src/Socialbox/Classes/StandardMethods/SettingsGetInformationFields.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsSetBirthday.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsSetDisplayName.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsSetDisplayPicture.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsSetEmailAddress.php delete mode 100644 src/Socialbox/Classes/StandardMethods/SettingsSetPhoneNumber.php create mode 100644 src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationField.php create mode 100644 src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationPrivacy.php create mode 100644 src/Socialbox/Enums/PrivacyState.php create mode 100644 src/Socialbox/Enums/Types/InformationFieldName.php create mode 100644 src/Socialbox/Managers/PeerInformationManager.php create mode 100644 src/Socialbox/Objects/Database/PeerInformationFieldRecord.php rename src/Socialbox/Objects/Database/{RegisteredPeerRecord.php => PeerRecord.php} (70%) create mode 100644 src/Socialbox/Objects/Standard/InformationField.php create mode 100644 src/Socialbox/Objects/Standard/InformationFieldState.php diff --git a/.idea/sqldialects.xml b/.idea/sqldialects.xml index 2e3f2ff..f682500 100644 --- a/.idea/sqldialects.xml +++ b/.idea/sqldialects.xml @@ -4,7 +4,8 @@ - + + @@ -12,6 +13,7 @@ + diff --git a/src/Socialbox/Classes/Configuration.php b/src/Socialbox/Classes/Configuration.php index e0823f9..653ab2e 100644 --- a/src/Socialbox/Classes/Configuration.php +++ b/src/Socialbox/Classes/Configuration.php @@ -133,10 +133,14 @@ $config->setDefault('registration.password_required', true); $config->setDefault('registration.otp_required', false); $config->setDefault('registration.display_name_required', true); + $config->setDefault('registration.first_name_required', false); + $config->setDefault('registration.middle_name_required', false); + $config->setDefault('registration.last_name_required', false); $config->setDefault('registration.display_picture_required', false); $config->setDefault('registration.email_address_required', false); $config->setDefault('registration.phone_number_required', false); $config->setDefault('registration.birthday_required', false); + $config->setDefault('registration.url_required', false); $config->setDefault('registration.image_captcha_verification_required', true); // Authentication configuration @@ -162,6 +166,16 @@ // recommendation: 100 $config->setDefault('policies.get_contacts_limit', 100); + // Default privacy states for information fields associated with the peer + $config->setDefault('policies.default_display_picture_privacy', 'PUBLIC'); + $config->setDefault('policies.default_first_name_privacy', 'CONTACTS'); + $config->setDefault('policies.default_middle_name_privacy', 'PRIVATE'); + $config->setDefault('policies.default_last_name_privacy', 'PRIVATE'); + $config->setDefault('policies.default_email_address_privacy', 'CONTACTS'); + $config->setDefault('policies.default_phone_number_privacy', 'CONTACTS'); + $config->setDefault('policies.default_birthday_privacy', 'PRIVATE'); + $config->setDefault('policies.default_url_privacy', 'PUBLIC'); + // Storage configuration $config->setDefault('storage.path', '/etc/socialbox'); // The main path for file storage $config->setDefault('storage.user_display_images_path', 'user_profiles'); // eg; `/etc/socialbox/user_profiles` diff --git a/src/Socialbox/Classes/Configuration/PoliciesConfiguration.php b/src/Socialbox/Classes/Configuration/PoliciesConfiguration.php index 05abe8f..7a11247 100644 --- a/src/Socialbox/Classes/Configuration/PoliciesConfiguration.php +++ b/src/Socialbox/Classes/Configuration/PoliciesConfiguration.php @@ -2,6 +2,8 @@ namespace Socialbox\Classes\Configuration; + use Socialbox\Enums\PrivacyState; + class PoliciesConfiguration { private int $maxSigningKeys; @@ -9,7 +11,29 @@ private int $imageCaptchaExpires; private int $peerSyncInterval; private int $getContactsLimit; + private PrivacyState $defaultDisplayPicturePrivacy; + private PrivacyState $defaultFirstNamePrivacy; + private PrivacyState $defaultMiddleNamePrivacy; + private PrivacyState $defaultLastNamePrivacy; + private PrivacyState $defaultEmailAddressPrivacy; + private PrivacyState $defaultPhoneNumberPrivacy; + private PrivacyState $defaultBirthdayPrivacy; + private PrivacyState $defaultUrlPrivacy; + /** + * Constructor method for initializing the policies configuration + * + * @param array $data An associative array containing the following keys: + * 'max_signing_keys', 'session_inactivity_expires', + * 'image_captcha_expires', 'peer_sync_interval', + * 'get_contacts_limit', 'default_display_picture_privacy', + * 'default_first_name_privacy', 'default_middle_name_privacy', + * 'default_last_name_privacy', 'default_email_address_privacy', + * 'default_phone_number_privacy', 'default_birthday_privacy', + * 'default_url_privacy'. + * + * @return void + */ public function __construct(array $data) { $this->maxSigningKeys = $data['max_signing_keys']; @@ -17,6 +41,14 @@ $this->imageCaptchaExpires = $data['image_captcha_expires']; $this->peerSyncInterval = $data['peer_sync_interval']; $this->getContactsLimit = $data['get_contacts_limit']; + $this->defaultDisplayPicturePrivacy = PrivacyState::tryFrom($data['default_display_picture_privacy']) ?? PrivacyState::PRIVATE; + $this->defaultFirstNamePrivacy = PrivacyState::tryFrom($data['default_first_name_privacy']) ?? PrivacyState::PRIVATE; + $this->defaultMiddleNamePrivacy = PrivacyState::tryFrom($data['default_middle_name_privacy']) ?? PrivacyState::PRIVATE; + $this->defaultLastNamePrivacy = PrivacyState::tryFrom($data['default_last_name_privacy']) ?? PrivacyState::PRIVATE; + $this->defaultEmailAddressPrivacy = PrivacyState::tryFrom($data['default_email_address_privacy']) ?? PrivacyState::PRIVATE; + $this->defaultPhoneNumberPrivacy = PrivacyState::tryFrom($data['default_phone_number_privacy']) ?? PrivacyState::PRIVATE; + $this->defaultBirthdayPrivacy = PrivacyState::tryFrom($data['default_birthday_privacy']) ?? PrivacyState::PRIVATE; + $this->defaultUrlPrivacy = PrivacyState::tryFrom($data['default_url_privacy']) ?? PrivacyState::PRIVATE; } /** @@ -70,4 +102,84 @@ { return $this->getContactsLimit; } + + /** + * Returns the default privacy state for the display picture + * + * @return PrivacyState + */ + public function getDefaultDisplayPicturePrivacy(): PrivacyState + { + return $this->defaultDisplayPicturePrivacy; + } + + /** + * Returns the default privacy state for the first name + * + * @return PrivacyState + */ + public function getDefaultFirstNamePrivacy(): PrivacyState + { + return $this->defaultFirstNamePrivacy; + } + + /** + * Returns the default privacy state for the middle name + * + * @return PrivacyState + */ + public function getDefaultMiddleNamePrivacy(): PrivacyState + { + return $this->defaultMiddleNamePrivacy; + } + + /** + * Returns the default privacy state for the last name + * + * @return PrivacyState + */ + public function getDefaultLastNamePrivacy(): PrivacyState + { + return $this->defaultLastNamePrivacy; + } + + /** + * Returns the default privacy state for the email address + * + * @return PrivacyState + */ + public function getDefaultEmailAddressPrivacy(): PrivacyState + { + return $this->defaultEmailAddressPrivacy; + } + + /** + * Returns the default privacy state for the phone number + * + * @return PrivacyState + */ + public function getDefaultPhoneNumberPrivacy(): PrivacyState + { + return $this->defaultPhoneNumberPrivacy; + } + + /** + * Returns the default privacy state for the birthday + * + * @return PrivacyState + */ + public function getDefaultBirthdayPrivacy(): PrivacyState + { + return $this->defaultBirthdayPrivacy; + } + + /** + * Returns the default privacy state for the URL + * + * @return PrivacyState + */ + public function getDefaultUrlPrivacy(): PrivacyState + { + return $this->defaultUrlPrivacy; + } } \ No newline at end of file diff --git a/src/Socialbox/Classes/Configuration/RegistrationConfiguration.php b/src/Socialbox/Classes/Configuration/RegistrationConfiguration.php index 35fcaf0..6745109 100644 --- a/src/Socialbox/Classes/Configuration/RegistrationConfiguration.php +++ b/src/Socialbox/Classes/Configuration/RegistrationConfiguration.php @@ -17,10 +17,14 @@ private bool $passwordRequired; private bool $otpRequired; private bool $displayNameRequired; + private bool $firstNameRequired; + private bool $middleNameRequired; + private bool $lastNameRequired; private bool $displayPictureRequired; private bool $emailAddressRequired; private bool $phoneNumberRequired; private bool $birthdayRequired; + private bool $urlRequired; private bool $imageCaptchaVerificationRequired; /** @@ -49,10 +53,14 @@ $this->passwordRequired = (bool)$data['password_required']; $this->otpRequired = (bool)$data['otp_required']; $this->displayNameRequired = (bool)$data['display_name_required']; + $this->firstNameRequired = (bool)$data['first_name_required']; + $this->middleNameRequired = (bool)$data['middle_name_required']; + $this->lastNameRequired = (bool)$data['last_name_required']; $this->displayPictureRequired = (bool)$data['display_picture_required']; $this->emailAddressRequired = (bool)$data['email_address_required']; $this->phoneNumberRequired = (bool)$data['phone_number_required']; $this->birthdayRequired = (bool)$data['birthday_required']; + $this->urlRequired = (bool)$data['url_required']; $this->imageCaptchaVerificationRequired = (bool)$data['image_captcha_verification_required']; } @@ -186,6 +194,36 @@ return $this->displayNameRequired; } + /** + * Checks if a first name is required. + * + * @return bool Returns true if a first name is required, false otherwise. + */ + public function isFirstNameRequired(): bool + { + return $this->firstNameRequired; + } + + /** + * Checks if a middle name is required. + * + * @return bool Returns true if a middle name is required, false otherwise. + */ + public function isMiddleNameRequired(): bool + { + return $this->middleNameRequired; + } + + /** + * Checks if a last name is required. + * + * @return bool Returns true if a last name is required, false otherwise. + */ + public function isLastNameRequired(): bool + { + return $this->lastNameRequired; + } + /** * Checks if a display picture is required. * @@ -226,6 +264,16 @@ return $this->birthdayRequired; } + /** + * Determines if a URL is required. + * + * @return bool Returns true if a URL is required, false otherwise. + */ + public function isUrlRequired(): bool + { + return $this->urlRequired; + } + /** * Determines if image CAPTCHA verification is required. * diff --git a/src/Socialbox/Classes/Resources/database/authentication_otp.sql b/src/Socialbox/Classes/Resources/database/authentication_otp.sql index 788e100..4e32763 100644 --- a/src/Socialbox/Classes/Resources/database/authentication_otp.sql +++ b/src/Socialbox/Classes/Resources/database/authentication_otp.sql @@ -7,7 +7,7 @@ create table authentication_otp constraint authentication_otp_peer_uuid_uindex unique (peer_uuid) comment 'The Peer UUID unique Index', constraint authentication_otp_registered_peers_uuid_fk - foreign key (peer_uuid) references registered_peers (uuid) + foreign key (peer_uuid) references peers (uuid) on update cascade on delete cascade ) comment 'Table for housing encrypted OTP secrets for for verification'; diff --git a/src/Socialbox/Classes/Resources/database/captcha_images.sql b/src/Socialbox/Classes/Resources/database/captcha_images.sql index 03336da..1a3958b 100644 --- a/src/Socialbox/Classes/Resources/database/captcha_images.sql +++ b/src/Socialbox/Classes/Resources/database/captcha_images.sql @@ -10,7 +10,7 @@ create table captcha_images constraint captchas_peer_uuid_uindex unique (peer_uuid) comment 'The Primary Unique Index for the peer UUID', constraint captchas_registered_peers_uuid_fk - foreign key (peer_uuid) references registered_peers (uuid) + foreign key (peer_uuid) references peers (uuid) on update cascade on delete cascade ); diff --git a/src/Socialbox/Classes/Resources/database/peer_information.sql b/src/Socialbox/Classes/Resources/database/peer_information.sql new file mode 100644 index 0000000..f650ca7 --- /dev/null +++ b/src/Socialbox/Classes/Resources/database/peer_information.sql @@ -0,0 +1,19 @@ +create table peer_information +( + peer_uuid varchar(36) not null comment 'The Unique Universal Identifier for the peer', + property_name enum ('DISPLAY_NAME', 'DISPLAY_PICTURE', 'FIRST_NAME', 'MIDDLE_NAME', 'LAST_NAME', 'EMAIL_ADDRESS', 'PHONE_NUMBER', 'BIRTHDAY', 'URL') not null comment 'The name of the property', + property_value varchar(256) not null comment 'The value of the property associated with the peer', + privacy_state enum ('PUBLIC', 'PRIVATE', 'CONTACTS', 'TRUSTED') default 'PRIVATE' not null comment 'The privacy setting for the information property', + primary key (property_name, peer_uuid), + constraint peer_information_peer_uuid_property_name_uindex + unique (peer_uuid, property_name) comment 'The Unique Index for the the peer uuid & property name combination', + constraint peer_information_registered_peers_uuid_fk + foreign key (peer_uuid) references peers (uuid) + on update cascade on delete cascade +) + comment 'Table for housing peer information'; + +create index peer_information_peer_uuid_index + on peer_information (peer_uuid) + comment 'The index for the peer uuid'; + diff --git a/src/Socialbox/Classes/Resources/database/peers.sql b/src/Socialbox/Classes/Resources/database/peers.sql new file mode 100644 index 0000000..0d7662c --- /dev/null +++ b/src/Socialbox/Classes/Resources/database/peers.sql @@ -0,0 +1,37 @@ +create table peers +( + uuid varchar(36) default uuid() not null comment 'The Primary index for the peer uuid' + primary key, + username varchar(255) not null comment 'The Unique username associated with the peer', + server varchar(255) default 'host' not null comment 'The server that this peer is registered to', + flags text null comment 'Comma seprted flags associated with the peer', + enabled tinyint(1) default 0 not null comment 'Boolean column to indicate if this account is Enabled, by default it''s Disabled until the account is verified.', + updated timestamp default current_timestamp() not null comment 'The Timestamp for when this record was last updated', + created timestamp default current_timestamp() not null comment 'The Timestamp for when the peer was registered on the network', + constraint registered_peers_server_username_uindex + unique (server, username) comment 'The Unique Username + Server Index Pair', + constraint registered_peers_uuid_uindex + unique (uuid) comment 'The Primary index for the peer uuid' +) + comment 'Table for housing registered peers under this network'; + +create index registered_peers_enabled_index + on peers (enabled) + comment 'The index of the enabled column for registered peers'; + +create index registered_peers_registered_index + on peers (created) + comment 'The Index for the reigstered column of the peer'; + +create index registered_peers_server_index + on peers (server) + comment 'The Index for the peer''s server'; + +create index registered_peers_updated_index + on peers (updated) + comment 'The Index for the update column'; + +create index registered_peers_username_index + on peers (username) + comment 'The index for the registered username'; + diff --git a/src/Socialbox/Classes/Resources/database/registered_peers.sql b/src/Socialbox/Classes/Resources/database/registered_peers.sql deleted file mode 100644 index d0486b0..0000000 --- a/src/Socialbox/Classes/Resources/database/registered_peers.sql +++ /dev/null @@ -1,39 +0,0 @@ -create table registered_peers -( - uuid varchar(36) default uuid() not null comment 'The Primary index for the peer uuid' - primary key, - username varchar(255) not null comment 'The Unique username associated with the peer', - server varchar(255) default 'host' not null comment 'The server that this peer is registered to', - display_name varchar(255) null comment 'Optional. The Non-Unique Display name of the peer', - display_picture varchar(36) null comment 'The UUID of the display picture that is used, null if none is set.', - flags text null comment 'Comma seprted flags associated with the peer', - enabled tinyint(1) default 0 not null comment 'Boolean column to indicate if this account is Enabled, by default it''s Disabled until the account is verified.', - updated timestamp default current_timestamp() not null comment 'The Timestamp for when this record was last updated', - created timestamp default current_timestamp() not null comment 'The Timestamp for when the peer was registered on the network', - constraint registered_peers_server_username_uindex - unique (server, username) comment 'The Unique Username + Server Index Pair', - constraint registered_peers_uuid_uindex - unique (uuid) comment 'The Primary index for the peer uuid' -) - comment 'Table for housing registered peers under this network'; - -create index registered_peers_enabled_index - on registered_peers (enabled) - comment 'The index of the enabled column for registered peers'; - -create index registered_peers_registered_index - on registered_peers (created) - comment 'The Index for the reigstered column of the peer'; - -create index registered_peers_server_index - on registered_peers (server) - comment 'The Index for the peer''s server'; - -create index registered_peers_updated_index - on registered_peers (updated) - comment 'The Index for the update column'; - -create index registered_peers_username_index - on registered_peers (username) - comment 'The index for the registered username'; - diff --git a/src/Socialbox/Classes/Resources/database/sessions.sql b/src/Socialbox/Classes/Resources/database/sessions.sql index dcf4a11..397a44d 100644 --- a/src/Socialbox/Classes/Resources/database/sessions.sql +++ b/src/Socialbox/Classes/Resources/database/sessions.sql @@ -20,7 +20,7 @@ create table sessions constraint sessions_uuid_uindex unique (uuid) comment 'The Unique Primary index for the session UUID', constraint sessions_registered_peers_uuid_fk - foreign key (peer_uuid) references registered_peers (uuid) + foreign key (peer_uuid) references peers (uuid) on update cascade on delete cascade ); diff --git a/src/Socialbox/Classes/StandardMethods/SettingsAddInformationField.php b/src/Socialbox/Classes/StandardMethods/SettingsAddInformationField.php new file mode 100644 index 0000000..782ede0 --- /dev/null +++ b/src/Socialbox/Classes/StandardMethods/SettingsAddInformationField.php @@ -0,0 +1,147 @@ +containsParameter('field')) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The required field parameter is missing'); + } + $fieldName = InformationFieldName::tryFrom(strtoupper($rpcRequest->getParameter('field'))); + if($fieldName === null) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided field parameter is invalid'); + } + + // Value parameter is required + if(!$rpcRequest->containsParameter('value')) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The required value parameter is missing'); + } + $value = $rpcRequest->getParameter('value'); + if(!$fieldName->validate($value)) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided value parameter is invalid'); + } + + // Privacy parameter is optional + $privacy = null; + if($rpcRequest->containsParameter('privacy') && $rpcRequest->getParameter('privacy') !== null) + { + $privacy = PrivacyState::tryFrom(strtoupper($rpcRequest->getParameter('privacy'))); + if($privacy === null) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided privacy parameter is invalid'); + } + } + + try + { + $peer = $request->getPeer(); + } + catch (DatabaseOperationException $e) + { + throw new StandardException('Failed to retrieve current peer information', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + try + { + if (PeerInformationManager::fieldExists($peer, $fieldName)) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided field parameter is already registered, use settingsUpdateInformationField or settingsUpdateInformationPrivacy instead'); + } + + PeerInformationManager::addField($peer, $fieldName, $value, $privacy); + } + catch (DatabaseOperationException $e) + { + throw new StandardException('Failed to add the information field', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + // Update the session flow if necessary + try + { + switch($fieldName) + { + case InformationFieldName::DISPLAY_NAME: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_DISPLAY_NAME]); + break; + + case InformationFieldName::FIRST_NAME: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_FIRST_NAME]); + break; + + case InformationFieldName::MIDDLE_NAME: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_MIDDLE_NAME]); + break; + + case InformationFieldName::LAST_NAME: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_LAST_NAME]); + break; + + case InformationFieldName::BIRTHDAY: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_BIRTHDAY]); + break; + + case InformationFieldName::PHONE_NUMBER: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_PHONE]); + break; + + case InformationFieldName::EMAIL_ADDRESS: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_EMAIL]); + break; + + case InformationFieldName::URL: + SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_URL]); + break; + + default: + break; + } + } + catch (Exception $e) + { + try + { + // Rollback the information field otherwise the peer will be stuck with an incomplete session flow + PeerInformationManager::deleteField($peer, $fieldName); + } + catch (DatabaseOperationException $e) + { + // Something is seriously wrong if we can't roll back the information field + throw new StandardException('Failed to rollback the information field', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + if($e instanceof StandardException) + { + throw $e; + } + + throw new StandardException('Failed to update the session flow', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + + return $rpcRequest->produceResponse(true); + } + } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsDeleteBirthday.php b/src/Socialbox/Classes/StandardMethods/SettingsDeleteBirthday.php deleted file mode 100644 index 8da8fe7..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsDeleteBirthday.php +++ /dev/null @@ -1,38 +0,0 @@ -isBirthdayRequired()) - { - return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A birthday is required for this server'); - } - - try - { - RegisteredPeerManager::deleteBirthday($request->getPeer()); - } - catch(Exception $e) - { - throw new StandardException('Failed to delete birthday ' . $e->getMessage(), StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayName.php b/src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayName.php deleted file mode 100644 index 0e1b443..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayName.php +++ /dev/null @@ -1,38 +0,0 @@ -isDisplayNameRequired()) - { - return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A display name is required for this server'); - } - - try - { - RegisteredPeerManager::deleteDisplayName($request->getPeer()); - } - catch(Exception $e) - { - throw new StandardException('Failed to delete display name due to an internal exception', StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayPicture.php b/src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayPicture.php deleted file mode 100644 index 9d4a95c..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsDeleteDisplayPicture.php +++ /dev/null @@ -1,38 +0,0 @@ -isDisplayPictureRequired()) - { - return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A display picture is required for this server'); - } - - try - { - RegisteredPeerManager::deleteDisplayPicture($request->getPeer()); - } - catch(Exception $e) - { - throw new StandardException('Failed to delete display picture: ' . $e->getMessage(), StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsDeleteEmailAddress.php b/src/Socialbox/Classes/StandardMethods/SettingsDeleteEmailAddress.php deleted file mode 100644 index cb82661..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsDeleteEmailAddress.php +++ /dev/null @@ -1,38 +0,0 @@ -isEmailAddressRequired()) - { - return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A email address is required for this server'); - } - - try - { - RegisteredPeerManager::deleteEmailAddress($request->getPeer()); - } - catch(Exception $e) - { - throw new StandardException('Failed to delete email address: ' . $e->getMessage(), StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsDeleteInformationField.php b/src/Socialbox/Classes/StandardMethods/SettingsDeleteInformationField.php new file mode 100644 index 0000000..92c537c --- /dev/null +++ b/src/Socialbox/Classes/StandardMethods/SettingsDeleteInformationField.php @@ -0,0 +1,119 @@ +containsParameter('field')) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The required field parameter is missing'); + } + $fieldName = InformationFieldName::tryFrom(strtoupper($rpcRequest->getParameter('field'))); + if($fieldName === null) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided field parameter is invalid'); + } + + try + { + if(!PeerInformationManager::fieldExists($request->getPeer(), $fieldName)) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'The information field does not exist'); + } + } + catch(DatabaseOperationException $e) + { + throw new StandardException('Failed to check if the information field exists', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + switch($fieldName) + { + case InformationFieldName::DISPLAY_NAME: + if(Configuration::getRegistrationConfiguration()->isDisplayNameRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A display name is required for this server'); + } + break; + + case InformationFieldName::FIRST_NAME: + if(Configuration::getRegistrationConfiguration()->isFirstNameRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A first name is required for this server'); + } + break; + + case InformationFieldName::MIDDLE_NAME: + if(Configuration::getRegistrationConfiguration()->isMiddleNameRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A middle name is required for this server'); + } + break; + + case InformationFieldName::LAST_NAME: + if(Configuration::getRegistrationConfiguration()->isLastNameRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A last name is required for this server'); + } + break; + + case InformationFieldName::BIRTHDAY: + if(Configuration::getRegistrationConfiguration()->isBirthdayRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A birthday is required for this server'); + } + break; + + case InformationFieldName::PHONE_NUMBER: + if(Configuration::getRegistrationConfiguration()->isPhoneNumberRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A phone number is required for this server'); + } + break; + + case InformationFieldName::EMAIL_ADDRESS: + if(Configuration::getRegistrationConfiguration()->isEmailAddressRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'An email address is required for this server'); + } + break; + + case InformationFieldName::URL: + if(Configuration::getRegistrationConfiguration()->isUrlRequired()) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A URL is required for this server'); + } + break; + + default: + break; + } + + try + { + PeerInformationManager::deleteField($request->getPeer(), $fieldName); + } + catch(DatabaseOperationException $e) + { + throw new StandardException('Failed to delete the information field', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + return $rpcRequest->produceResponse(true); + } + } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsDeletePhoneNumber.php b/src/Socialbox/Classes/StandardMethods/SettingsDeletePhoneNumber.php deleted file mode 100644 index aeb755e..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsDeletePhoneNumber.php +++ /dev/null @@ -1,38 +0,0 @@ -isPhoneNumberRequired()) - { - return $rpcRequest->produceError(StandardError::FORBIDDEN, 'A phone number is required for this server'); - } - - try - { - RegisteredPeerManager::deletePhoneNumber($request->getPeer()); - } - catch(Exception $e) - { - throw new StandardException('Failed to delete phone number: ' . $e->getMessage(), StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsGetInformationFields.php b/src/Socialbox/Classes/StandardMethods/SettingsGetInformationFields.php new file mode 100644 index 0000000..9a90643 --- /dev/null +++ b/src/Socialbox/Classes/StandardMethods/SettingsGetInformationFields.php @@ -0,0 +1,32 @@ +getPeer()); + } + catch(DatabaseOperationException $e) + { + throw new StandardException('Failed to retrieve existing information fields', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + return $rpcRequest->produceResponse(array_map(fn($result) => $result->toInformationFieldState(), $fieldRecords)); + } + } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsSetBirthday.php b/src/Socialbox/Classes/StandardMethods/SettingsSetBirthday.php deleted file mode 100644 index 9af21b4..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsSetBirthday.php +++ /dev/null @@ -1,63 +0,0 @@ -containsParameter('month')) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Missing 'month' parameter"); - } - - if(!$rpcRequest->containsParameter('day')) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Missing 'day' parameter"); - } - - if(!$rpcRequest->containsParameter('year')) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Missing 'year' parameter"); - } - - $month = $rpcRequest->getParameter('month'); - $day = $rpcRequest->getParameter('day'); - $year = $rpcRequest->getParameter('year'); - - if(!Validator::validateDate($month, $day, $year)) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Invalid date provided, must be a valid gregorian calender date."); - } - - try - { - // Set the password - RegisteredPeerManager::updateBirthday($request->getPeer(), $month, $day, $year); - - // Check & update the session flow - SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_BIRTHDAY]); - } - catch(Exception $e) - { - throw new StandardException('Failed to set birthday due to an internal exception', StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsSetDisplayName.php b/src/Socialbox/Classes/StandardMethods/SettingsSetDisplayName.php deleted file mode 100644 index 148e0f8..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsSetDisplayName.php +++ /dev/null @@ -1,48 +0,0 @@ -containsParameter('name')) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Missing 'name' parameter"); - } - - try - { - // Update the display name - RegisteredPeerManager::updateDisplayName($request->getPeer(), $rpcRequest->getParameter('name')); - - // Check & update the session flow - SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_DISPLAY_NAME]); - } - catch(InvalidArgumentException) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'Invalid display name'); - } - catch(Exception $e) - { - throw new StandardException('Failed to set password due to an internal exception', StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsSetDisplayPicture.php b/src/Socialbox/Classes/StandardMethods/SettingsSetDisplayPicture.php deleted file mode 100644 index 6567b26..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsSetDisplayPicture.php +++ /dev/null @@ -1,65 +0,0 @@ -containsParameter('image')) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Missing 'image' parameter"); - } - - if(strlen($rpcRequest->getParameter('image')) > Configuration::getStorageConfiguration()->getUserDisplayImagesMaxSize()) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Image size exceeds the maximum allowed size of " . Configuration::getStorageConfiguration()->getUserDisplayImagesMaxSize() . " bytes"); - } - - try - { - $decodedImage = @base64_decode($rpcRequest->getParameter('image')); - if($decodedImage === false) - { - return $rpcRequest->produceError(StandardError::RPC_BAD_REQUEST, "Failed to decode JPEG image base64 data"); - } - - $sanitizedImage = Utilities::resizeImage(Utilities::sanitizeJpeg($decodedImage), 256, 256); - } - catch(Exception $e) - { - throw new StandardException('Failed to process JPEG image: ' . $e->getMessage(), StandardError::RPC_BAD_REQUEST, $e); - } - - try - { - // Set the password - RegisteredPeerManager::updateDisplayPicture($request->getPeer(), $sanitizedImage); - - // Check & update the session flow - SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_DISPLAY_PICTURE]); - } - catch(Exception $e) - { - throw new StandardException('Failed to update display picture: ' . $e->getMessage(), StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsSetEmailAddress.php b/src/Socialbox/Classes/StandardMethods/SettingsSetEmailAddress.php deleted file mode 100644 index c8fda50..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsSetEmailAddress.php +++ /dev/null @@ -1,50 +0,0 @@ -containsParameter('email_address')) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Missing 'email_address' parameter"); - } - - if(!Validator::validateEmailAddress($rpcRequest->getParameter('email_address'))) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Invalid 'email_address' parameter, must be a valid email address"); - } - - try - { - // Set the password - RegisteredPeerManager::updateEmailAddress($request->getPeer(), $rpcRequest->getParameter('email_address')); - - // Check & update the session flow - SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_EMAIL]); - } - catch(Exception $e) - { - throw new StandardException('Failed to set email address due to an internal exception', StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsSetPhoneNumber.php b/src/Socialbox/Classes/StandardMethods/SettingsSetPhoneNumber.php deleted file mode 100644 index eaa9a4d..0000000 --- a/src/Socialbox/Classes/StandardMethods/SettingsSetPhoneNumber.php +++ /dev/null @@ -1,49 +0,0 @@ -containsParameter('phone_number')) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Missing 'phone_number' parameter"); - } - - if(!Validator::validatePhoneNumber($rpcRequest->getParameter('phone_number'))) - { - return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, "Invalid 'phone_number' parameter, must be a valid phone number"); - } - - try - { - // Set the phone number - RegisteredPeerManager::updatePhoneNumber($request->getPeer(), $rpcRequest->getParameter('phone_number')); - - // Check & update the session flow - SessionManager::updateFlow($request->getSession(), [SessionFlags::SET_PHONE]); - } - catch(Exception $e) - { - throw new StandardException('Failed to set phone number due to an internal exception', StandardError::INTERNAL_SERVER_ERROR, $e); - } - - return $rpcRequest->produceResponse(true); - } - } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationField.php b/src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationField.php new file mode 100644 index 0000000..684fbf2 --- /dev/null +++ b/src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationField.php @@ -0,0 +1,62 @@ +containsParameter('field')) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The required field parameter is missing'); + } + $fieldName = InformationFieldName::tryFrom(strtoupper($rpcRequest->getParameter('field'))); + if($fieldName === null) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided field parameter is invalid'); + } + + // Value parameter is required + if(!$rpcRequest->containsParameter('value')) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The required value parameter is missing'); + } + $value = $rpcRequest->getParameter('value'); + if(!$fieldName->validate($value)) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided value parameter is invalid'); + } + + try + { + $peer = $request->getPeer(); + if(!PeerInformationManager::fieldExists($peer, $fieldName)) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'The information field does not exist'); + } + + PeerInformationManager::updateField($peer, $fieldName, $value); + } + catch(DatabaseOperationException $e) + { + throw new StandardException('Failed to update the information field', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + + return $rpcRequest->produceResponse(true); + } + } \ No newline at end of file diff --git a/src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationPrivacy.php b/src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationPrivacy.php new file mode 100644 index 0000000..a63f494 --- /dev/null +++ b/src/Socialbox/Classes/StandardMethods/SettingsUpdateInformationPrivacy.php @@ -0,0 +1,64 @@ +containsParameter('field')) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The required field parameter is missing'); + } + $fieldName = InformationFieldName::tryFrom(strtoupper($rpcRequest->getParameter('field'))); + if($fieldName === null) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided field parameter is invalid'); + } + + // Privacy parameter is required + $privacy = null; + if(!$rpcRequest->containsParameter('privacy')) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The required privacy parameter is missing'); + } + $privacy = PrivacyState::tryFrom(strtoupper($rpcRequest->getParameter('privacy'))); + if($privacy === null) + { + return $rpcRequest->produceError(StandardError::RPC_INVALID_ARGUMENTS, 'The provided privacy parameter is invalid'); + } + + try + { + $peer = $request->getPeer(); + if(!PeerInformationManager::fieldExists($peer, $fieldName)) + { + return $rpcRequest->produceError(StandardError::FORBIDDEN, 'The information field does not exist'); + } + + PeerInformationManager::updatePrivacyState($peer, $fieldName, $privacy); + } + catch(DatabaseOperationException $e) + { + throw new StandardException('Failed to update the information field', StandardError::INTERNAL_SERVER_ERROR, $e); + } + + + return $rpcRequest->produceResponse(true); + } + } \ No newline at end of file diff --git a/src/Socialbox/Enums/DatabaseObjects.php b/src/Socialbox/Enums/DatabaseObjects.php index 5a30afe..3f8acad 100644 --- a/src/Socialbox/Enums/DatabaseObjects.php +++ b/src/Socialbox/Enums/DatabaseObjects.php @@ -7,8 +7,9 @@ case VARIABLES = 'variables.sql'; case RESOLVED_DNS_RECORDS = 'resolved_dns_records.sql'; - case REGISTERED_PEERS = 'registered_peers.sql'; + case PEERS = 'peers.sql'; + case PEER_INFORMATION = 'peer_information.sql'; case AUTHENTICATION_PASSWORDS = 'authentication_passwords.sql'; case AUTHENTICATION_OTP = 'authentication_otp.sql'; case CAPTCHA_IMAGES = 'captcha_images.sql'; @@ -27,8 +28,9 @@ self::VARIABLES, self::RESOLVED_DNS_RECORDS => 0, - self::REGISTERED_PEERS => 1, + self::PEERS => 1, + self::PEER_INFORMATION, self::AUTHENTICATION_PASSWORDS, self::AUTHENTICATION_OTP, self::CAPTCHA_IMAGES, diff --git a/src/Socialbox/Enums/Flags/SessionFlags.php b/src/Socialbox/Enums/Flags/SessionFlags.php index ae47c2a..1fd021c 100644 --- a/src/Socialbox/Enums/Flags/SessionFlags.php +++ b/src/Socialbox/Enums/Flags/SessionFlags.php @@ -13,11 +13,15 @@ // Verification, require fields case SET_PASSWORD = 'SET_PASSWORD'; // Peer has to set a password case SET_OTP = 'SET_OTP'; // Peer has to set an OTP - case SET_DISPLAY_NAME = 'SET_DISPLAY_NAME'; // Peer has to set a display name - case SET_DISPLAY_PICTURE = 'SET_DISPLAY_PICTURE'; // Peer has to set a display picture - case SET_EMAIL = 'SET_EMAIL'; // Peer has to set an email - case SET_PHONE = 'SET_PHONE'; // Peer has to set a phone number - case SET_BIRTHDAY = 'SET_BIRTHDAY'; // Peer has to set a birthday + case SET_DISPLAY_NAME = 'SET_DISPLAY_NAME'; // Peer has to set a display name to their profile information + case SET_FIRST_NAME = 'SET_FIRST_NAME'; // Peer has to set a first name to their profile information + case SET_MIDDLE_NAME = 'SET_MIDDLE_NAME'; // Peer has to set a middle name to their profile information + case SET_LAST_NAME = 'SET_LAST_NAME'; // Peer has to set a last name to their profile information + case SET_DISPLAY_PICTURE = 'SET_DISPLAY_PICTURE'; // Peer has to set a display picture to their profile information + case SET_EMAIL = 'SET_EMAIL'; // Peer has to set an email to their profile information + case SET_PHONE = 'SET_PHONE'; // Peer has to set a phone number to their profile information + case SET_BIRTHDAY = 'SET_BIRTHDAY'; // Peer has to set a birthday to their profile information + case SET_URL = 'SET_URL'; // Peer has to set an url to their profile information // Verification, verification requirements case VER_PRIVACY_POLICY = 'VER_PRIVACY_POLICY'; // Peer has to accept the privacy policy @@ -37,7 +41,7 @@ case VER_AUTHENTICATION_CODE = 'VER_AUTHENTICATION_CODE'; // Peer has to enter their authentication code // Session Flags - case RATE_LIMITED = 'RATE_LIMITED'; // Peer is temporarily rate limited + case RATE_LIMITED = 'RATE_LIMITED'; // Peer is temporarily rate-limited /** * Retrieves a list of registration-related flags. @@ -83,7 +87,7 @@ * Converts an array of SessionFlags to a comma-separated string of their values. * * @param array $flags An array of SessionFlags objects to be converted. - * @return string A comma-separated string of the values of the provided SessionFlags. + * @return string A comma-separated string of the provided SessionFlags as string values. */ public static function toString(array $flags): string { diff --git a/src/Socialbox/Enums/PrivacyState.php b/src/Socialbox/Enums/PrivacyState.php new file mode 100644 index 0000000..d69c8f3 --- /dev/null +++ b/src/Socialbox/Enums/PrivacyState.php @@ -0,0 +1,11 @@ + SettingsSetPassword::execute($request, $rpcRequest), self::SETTINGS_UPDATE_PASSWORD => SettingsUpdatePassword::execute($request, $rpcRequest), self::SETTINGS_DELETE_PASSWORD => SettingsDeletePassword::execute($request, $rpcRequest), - self::SETTINGS_SET_DISPLAY_NAME => SettingsSetDisplayName::execute($request, $rpcRequest), - self::SETTINGS_DELETE_DISPLAY_NAME => SettingsDeleteDisplayName::execute($request, $rpcRequest), - self::SETTINGS_SET_DISPLAY_PICTURE => SettingsSetDisplayPicture::execute($request, $rpcRequest), - self::SETTINGS_DELETE_DISPLAY_PICTURE => SettingsDeleteDisplayPicture::execute($request, $rpcRequest), - self::SETTINGS_SET_EMAIL => SettingsSetEmailAddress::execute($request, $rpcRequest), - self::SETTINGS_DELETE_EMAIL => SettingsDeleteEmailAddress::execute($request, $rpcRequest), - self::SETTINGS_SET_PHONE => SettingsSetPhoneNumber::execute($request, $rpcRequest), - self::SETTINGS_DELETE_PHONE => SettingsDeletePhoneNumber::execute($request, $rpcRequest), - self::SETTINGS_SET_BIRTHDAY => SettingsSetBirthday::execute($request, $rpcRequest), - self::SETTINGS_DELETE_BIRTHDAY => SettingsDeleteBirthday::execute($request, $rpcRequest), + self::SETTINGS_SET_OTP => SettingsSetOtp::execute($request, $rpcRequest), + self::SETTINGS_DELETE_OTP => SettingsDeleteOtp::execute($request, $rpcRequest), + + self::SETTINGS_ADD_INFORMATION_FIELD => SettingsAddInformationField::execute($request, $rpcRequest), + self::SETTINGS_GET_INFORMATION_FIELDS => SettingsGetInformationFields::execute($request, $rpcRequest), + self::SETTINGS_UPDATE_INFORMATION_FIELD => SettingsUpdateInformationField::execute($request, $rpcRequest), + self::SETTINGS_UPDATE_INFORMATION_PRIVACY => SettingsUpdateInformationPrivacy::execute($request, $rpcRequest), + self::SETTINGS_DELETE_INFORMATION_FIELD => SettingsDeleteInformationField::execute($request, $rpcRequest), self::SETTINGS_ADD_SIGNING_KEY => SettingsAddSigningKey::execute($request, $rpcRequest), self::SETTINGS_GET_SIGNING_KEYS => SettingsGetSigningKeys::execute($request, $rpcRequest), @@ -277,14 +260,14 @@ $methods = [ self::SETTINGS_ADD_SIGNING_KEY, self::SETTINGS_GET_SIGNING_KEYS, - self::SETTINGS_SET_DISPLAY_NAME, - self::SETTINGS_SET_DISPLAY_PICTURE, + self::SETTINGS_ADD_INFORMATION_FIELD, + self::SETTINGS_GET_INFORMATION_FIELDS, + self::SETTINGS_UPDATE_INFORMATION_FIELD, + self::SETTINGS_UPDATE_INFORMATION_PRIVACY, + self::SETTINGS_DELETE_INFORMATION_FIELD, self::SETTINGS_SET_PASSWORD, self::SETTINGS_UPDATE_PASSWORD, self::SETTINGS_SET_OTP, - self::SETTINGS_SET_EMAIL, - self::SETTINGS_SET_PHONE, - self::SETTINGS_SET_BIRTHDAY, self::RESOLVE_PEER, self::ADDRESS_BOOK_ADD_CONTACT, @@ -292,48 +275,6 @@ self::ADDRESS_BOOK_GET_CONTACTS, ]; - // Prevent the user from deleting their display name if it is required - if(!Configuration::getRegistrationConfiguration()->isDisplayNameRequired()) - { - $methods[] = self::SETTINGS_DELETE_DISPLAY_NAME; - } - - // Prevent the user from deleting their password if it is required - if(!Configuration::getRegistrationConfiguration()->isPasswordRequired()) - { - $methods[] = self::SETTINGS_DELETE_PASSWORD; - } - - // Prevent the user from deleting their display picture if it is required - if(!Configuration::getRegistrationConfiguration()->isDisplayPictureRequired()) - { - $methods[] = self::SETTINGS_DELETE_DISPLAY_PICTURE; - } - - // Prevent the user from deleting their OTP if it is required - if(!Configuration::getRegistrationConfiguration()->isOtpRequired()) - { - $methods[] = self::SETTINGS_DELETE_OTP; - } - - // Prevent the user from deleting their Phone Number if it is required - if(!Configuration::getRegistrationConfiguration()->isPhoneNumberRequired()) - { - $methods[] = self::SETTINGS_DELETE_PHONE; - } - - // Prevent the user from deleting their email address if it is required - if(!Configuration::getRegistrationConfiguration()->isEmailAddressRequired()) - { - $methods[] = self::SETTINGS_DELETE_EMAIL; - } - - // Prevent the user from deleting their birthday if it is required - if(!Configuration::getRegistrationConfiguration()->isBirthdayRequired()) - { - $methods[] = self::SETTINGS_DELETE_BIRTHDAY; - } - return $methods; } @@ -391,33 +332,18 @@ } // If the flag `SET_DISPLAY_NAME` is set, then the user has to set a display name - if($session->flagExists(SessionFlags::SET_DISPLAY_NAME)) + if($session->flagExists([ + SessionFlags::SET_DISPLAY_NAME, + SessionFlags::SET_FIRST_NAME, + SessionFlags::SET_MIDDLE_NAME, + SessionFlags::SET_LAST_NAME, + SessionFlags::SET_BIRTHDAY, + SessionFlags::SET_PHONE, + SessionFlags::SET_EMAIL, + SessionFlags::SET_URL + ])) { - $methods[] = self::SETTINGS_SET_DISPLAY_NAME; - } - - // If the flag `SET_DISPLAY_PICTURE` is set, then the user has to set a display picture - if($session->flagExists(SessionFlags::SET_DISPLAY_PICTURE)) - { - $methods[] = self::SETTINGS_SET_DISPLAY_PICTURE; - } - - // If the flag `SET_EMAIL` is set, then the user has to set an email address - if($session->flagExists(SessionFlags::SET_EMAIL)) - { - $methods[] = self::SETTINGS_SET_EMAIL; - } - - // If the flag `SET_PHONE` is set, then the user has to set a phone number - if($session->flagExists(SessionFlags::SET_PHONE)) - { - $methods[] = self::SETTINGS_SET_PHONE; - } - - // If the flag `SET_BIRTHDAY` is set, then the user has to set a birthday - if($session->flagExists(SessionFlags::SET_BIRTHDAY)) - { - $methods[] = self::SETTINGS_SET_BIRTHDAY; + $methods[] = self::SETTINGS_ADD_INFORMATION_FIELD; } return $methods; diff --git a/src/Socialbox/Enums/Types/InformationFieldName.php b/src/Socialbox/Enums/Types/InformationFieldName.php new file mode 100644 index 0000000..54a18b1 --- /dev/null +++ b/src/Socialbox/Enums/Types/InformationFieldName.php @@ -0,0 +1,71 @@ + strlen($value) >= 3 && strlen($value) <= 50, + InformationFieldName::LAST_NAME, InformationFieldName::MIDDLE_NAME, InformationFieldName::FIRST_NAME => strlen($value) >= 2 && strlen($value) <= 50, + InformationFieldName::EMAIL_ADDRESS => filter_var($value, FILTER_VALIDATE_EMAIL), + InformationFieldName::PHONE_NUMBER => preg_match('/^\+?[0-9]{1,3}-?[0-9]{3}-?[0-9]{3}-?[0-9]{4}$/', $value), + InformationFieldName::BIRTHDAY => preg_match('/^[0-9]{4}-[0-9]{2}-[0-9]{2}$/', $value), + InformationFieldName::URL => filter_var($value, FILTER_VALIDATE_URL), + default => true, + }; + } + } diff --git a/src/Socialbox/Managers/CaptchaManager.php b/src/Socialbox/Managers/CaptchaManager.php index 3d599c9..2ccba7e 100644 --- a/src/Socialbox/Managers/CaptchaManager.php +++ b/src/Socialbox/Managers/CaptchaManager.php @@ -10,21 +10,21 @@ use Socialbox\Classes\Utilities; use Socialbox\Enums\Status\CaptchaStatus; use Socialbox\Exceptions\DatabaseOperationException; use Socialbox\Objects\Database\CaptchaRecord; -use Socialbox\Objects\Database\RegisteredPeerRecord; +use Socialbox\Objects\Database\PeerRecord; class CaptchaManager { /** * Creates a new captcha for the given peer UUID. * - * @param string|RegisteredPeerRecord $peer_uuid The UUID of the peer to create the captcha for. + * @param string|PeerRecord $peer_uuid The UUID of the peer to create the captcha for. * @return string The answer to the captcha. * @throws DatabaseOperationException If the operation fails. */ - public static function createCaptcha(string|RegisteredPeerRecord $peer_uuid): string + public static function createCaptcha(string|PeerRecord $peer_uuid): string { // If the peer_uuid is a RegisteredPeerRecord, get the UUID - if($peer_uuid instanceof RegisteredPeerRecord) + if($peer_uuid instanceof PeerRecord) { $peer_uuid = $peer_uuid->getUuid(); } @@ -73,14 +73,14 @@ class CaptchaManager /** * Answers a captcha for the given peer UUID. * - * @param string|RegisteredPeerRecord $peer_uuid The UUID of the peer to answer the captcha for. + * @param string|PeerRecord $peer_uuid The UUID of the peer to answer the captcha for. * @param string $answer The answer to the captcha. * @return bool True if the answer is correct, false otherwise. * @throws DatabaseOperationException If the operation fails. */ - public static function answerCaptcha(string|RegisteredPeerRecord $peer_uuid, string $answer): bool + public static function answerCaptcha(string|PeerRecord $peer_uuid, string $answer): bool { - if($peer_uuid instanceof RegisteredPeerRecord) + if($peer_uuid instanceof PeerRecord) { $peer_uuid = $peer_uuid->getUuid(); } @@ -129,14 +129,14 @@ class CaptchaManager /** * Retrieves the captcha record for the given peer UUID. * - * @param string|RegisteredPeerRecord $peer_uuid The UUID of the peer to retrieve the captcha for. + * @param string|PeerRecord $peer_uuid The UUID of the peer to retrieve the captcha for. * @return CaptchaRecord|null The captcha record. * @throws DatabaseOperationException If the operation fails. */ - public static function getCaptcha(string|RegisteredPeerRecord $peer_uuid): ?CaptchaRecord + public static function getCaptcha(string|PeerRecord $peer_uuid): ?CaptchaRecord { // If the peer_uuid is a RegisteredPeerRecord, get the UUID - if($peer_uuid instanceof RegisteredPeerRecord) + if($peer_uuid instanceof PeerRecord) { $peer_uuid = $peer_uuid->getUuid(); } @@ -166,14 +166,14 @@ class CaptchaManager /** * Checks if a captcha exists for the given peer UUID. * - * @param string|RegisteredPeerRecord $peer_uuid The UUID of the peer to check for a captcha. + * @param string|PeerRecord $peer_uuid The UUID of the peer to check for a captcha. * @return bool True if a captcha exists, false otherwise. * @throws DatabaseOperationException If the operation fails. */ - public static function captchaExists(string|RegisteredPeerRecord $peer_uuid): bool + public static function captchaExists(string|PeerRecord $peer_uuid): bool { // If the peer_uuid is a RegisteredPeerRecord, get the UUID - if($peer_uuid instanceof RegisteredPeerRecord) + if($peer_uuid instanceof PeerRecord) { $peer_uuid = $peer_uuid->getUuid(); } diff --git a/src/Socialbox/Managers/OneTimePasswordManager.php b/src/Socialbox/Managers/OneTimePasswordManager.php index 18c4e26..5210afa 100644 --- a/src/Socialbox/Managers/OneTimePasswordManager.php +++ b/src/Socialbox/Managers/OneTimePasswordManager.php @@ -10,20 +10,20 @@ use Socialbox\Classes\OtpCryptography; use Socialbox\Exceptions\CryptographyException; use Socialbox\Exceptions\DatabaseOperationException; - use Socialbox\Objects\Database\RegisteredPeerRecord; + use Socialbox\Objects\Database\PeerRecord; class OneTimePasswordManager { /** * Checks if a given peer uses OTP for authentication. * - * @param string|RegisteredPeerRecord $peerUuid Either a UUID as a string or a RegisteredPeerRecord object representing the peer. + * @param string|PeerRecord $peerUuid Either a UUID as a string or a RegisteredPeerRecord object representing the peer. * @return bool Returns true if the peer uses OTP, otherwise false. * @throws DatabaseOperationException Thrown when a database error occurs. */ - public static function usesOtp(string|RegisteredPeerRecord $peerUuid): bool + public static function usesOtp(string|PeerRecord $peerUuid): bool { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } @@ -45,12 +45,12 @@ /** * Creates and stores a new OTP (One-Time Password) secret for the specified peer, and generates a key URI. * - * @param string|RegisteredPeerRecord $peer The unique identifier of the peer, either as a string UUID + * @param string|PeerRecord $peer The unique identifier of the peer, either as a string UUID * or an instance of RegisteredPeerRecord. * @return string The generated OTP key URI that can be used for applications like authenticator apps. * @throws DatabaseOperationException If there is an error during the database operation. */ - public static function createOtp(string|RegisteredPeerRecord $peer): string + public static function createOtp(string|PeerRecord $peer): string { if(is_string($peer)) { @@ -84,16 +84,16 @@ /** * Verifies the provided OTP (One-Time Password) against the stored secret associated with the specified peer. * - * @param string|RegisteredPeerRecord $peerUuid The unique identifier of the peer, either as a string UUID + * @param string|PeerRecord $peerUuid The unique identifier of the peer, either as a string UUID * or an instance of RegisteredPeerRecord. * @param string $otp The OTP to be verified. * @return bool Returns true if the OTP is valid; otherwise, false. * @throws DatabaseOperationException If there is an error during the database operation. * @throws CryptographyException If there is a failure in decrypting the stored OTP secret. */ - public static function verifyOtp(string|RegisteredPeerRecord $peerUuid, string $otp): bool + public static function verifyOtp(string|PeerRecord $peerUuid, string $otp): bool { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } @@ -145,13 +145,13 @@ /** * Deletes the OTP record associated with the specified peer. * - * @param string|RegisteredPeerRecord $peerUuid The peer's UUID or an instance of RegisteredPeerRecord whose OTP record needs to be deleted. + * @param string|PeerRecord $peerUuid The peer's UUID or an instance of RegisteredPeerRecord whose OTP record needs to be deleted. * @return void * @throws DatabaseOperationException if the database operation fails. */ - public static function deleteOtp(string|RegisteredPeerRecord $peerUuid): void + public static function deleteOtp(string|PeerRecord $peerUuid): void { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } @@ -171,12 +171,12 @@ /** * Retrieves the last updated timestamp for the OTP record of the specified peer. * - * @param string|RegisteredPeerRecord $peerUuid The peer's UUID or an instance of RegisteredPeerRecord whose OTP record's last updated timestamp needs to be retrieved + * @param string|PeerRecord $peerUuid The peer's UUID or an instance of RegisteredPeerRecord whose OTP record's last updated timestamp needs to be retrieved * @return int The last updated timestamp of the OTP record, or 0 if no such record exists */ - public static function getLastUpdated(string|RegisteredPeerRecord $peerUuid): int + public static function getLastUpdated(string|PeerRecord $peerUuid): int { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } diff --git a/src/Socialbox/Managers/PasswordManager.php b/src/Socialbox/Managers/PasswordManager.php index e9c3b26..f6a0465 100644 --- a/src/Socialbox/Managers/PasswordManager.php +++ b/src/Socialbox/Managers/PasswordManager.php @@ -10,20 +10,20 @@ use Socialbox\Classes\Database; use Socialbox\Exceptions\CryptographyException; use Socialbox\Exceptions\DatabaseOperationException; - use Socialbox\Objects\Database\RegisteredPeerRecord; + use Socialbox\Objects\Database\PeerRecord; class PasswordManager { /** * Checks if the given peer UUID is associated with a password in the database. * - * @param string|RegisteredPeerRecord $peerUuid The UUID of the peer, or an instance of RegisteredPeerRecord from which the UUID will be retrieved. + * @param string|PeerRecord $peerUuid The UUID of the peer, or an instance of RegisteredPeerRecord from which the UUID will be retrieved. * @return bool Returns true if the peer UUID is associated with a password, otherwise false. * @throws DatabaseOperationException If an error occurs while querying the database. */ - public static function usesPassword(string|RegisteredPeerRecord $peerUuid): bool + public static function usesPassword(string|PeerRecord $peerUuid): bool { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } @@ -45,15 +45,15 @@ /** * Sets a secured password for the given peer UUID or registered peer record. * - * @param string|RegisteredPeerRecord $peerUuid The unique identifier or registered peer record of the user. + * @param string|PeerRecord $peerUuid The unique identifier or registered peer record of the user. * @param string $hash The plaintext password to be securely stored. * @return void * @throws DatabaseOperationException If an error occurs while storing the password in the database. * @throws CryptographyException If an error occurs during password encryption or hashing. */ - public static function setPassword(string|RegisteredPeerRecord $peerUuid, string $hash): void + public static function setPassword(string|PeerRecord $peerUuid, string $hash): void { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } @@ -84,15 +84,15 @@ /** * Updates the secured password associated with the given peer UUID. * - * @param string|RegisteredPeerRecord $peerUuid The unique identifier or registered peer record of the user. + * @param string|PeerRecord $peerUuid The unique identifier or registered peer record of the user. * @param string $hash The new password to be stored securely. * @return void * @throws DatabaseOperationException If an error occurs while updating the password in the database. * @throws CryptographyException If an error occurs while encrypting the password or validating the hash. */ - public static function updatePassword(string|RegisteredPeerRecord $peerUuid, string $hash): void + public static function updatePassword(string|PeerRecord $peerUuid, string $hash): void { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } @@ -124,13 +124,13 @@ /** * Deletes the stored password for a specific peer. * - * @param string|RegisteredPeerRecord $peerUuid The unique identifier of the peer, or an instance of RegisteredPeerRecord. + * @param string|PeerRecord $peerUuid The unique identifier of the peer, or an instance of RegisteredPeerRecord. * @return void * @throws DatabaseOperationException If an error occurs during the database operation. */ - public static function deletePassword(string|RegisteredPeerRecord $peerUuid): void + public static function deletePassword(string|PeerRecord $peerUuid): void { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } @@ -150,15 +150,15 @@ /** * Verifies a given password against a stored password hash for a specific peer. * - * @param string|RegisteredPeerRecord $peerUuid The unique identifier of the peer, or an instance of RegisteredPeerRecord. + * @param string|PeerRecord $peerUuid The unique identifier of the peer, or an instance of RegisteredPeerRecord. * @param string $sha512 The SHA-512 hash of the password to be verified. * @return bool Returns true if the password matches the stored hash; false otherwise. * @throws CryptographyException If the password hash is invalid or an error occurs during the cryptographic operation. * @throws DatabaseOperationException If an error occurs during the database operation. */ - public static function verifyPassword(string|RegisteredPeerRecord $peerUuid, string $sha512): bool + public static function verifyPassword(string|PeerRecord $peerUuid, string $sha512): bool { - if($peerUuid instanceof RegisteredPeerRecord) + if($peerUuid instanceof PeerRecord) { $peerUuid = $peerUuid->getUuid(); } diff --git a/src/Socialbox/Managers/PeerInformationManager.php b/src/Socialbox/Managers/PeerInformationManager.php new file mode 100644 index 0000000..d8b0186 --- /dev/null +++ b/src/Socialbox/Managers/PeerInformationManager.php @@ -0,0 +1,282 @@ +getUuid(); + } + + if($privacyState === null) + { + $privacyState = match($property) + { + InformationFieldName::DISPLAY_NAME => Configuration::getPoliciesConfiguration()->getDefaultDisplayPicturePrivacy(), + InformationFieldName::FIRST_NAME => Configuration::getPoliciesConfiguration()->getDefaultFirstNamePrivacy(), + InformationFieldName::MIDDLE_NAME => Configuration::getPoliciesConfiguration()->getDefaultMiddleNamePrivacy(), + InformationFieldName::LAST_NAME => Configuration::getPoliciesConfiguration()->getDefaultLastNamePrivacy(), + InformationFieldName::EMAIL_ADDRESS => Configuration::getPoliciesConfiguration()->getDefaultEmailAddressPrivacy(), + InformationFieldName::PHONE_NUMBER => Configuration::getPoliciesConfiguration()->getDefaultPhoneNumberPrivacy(), + InformationFieldName::BIRTHDAY => Configuration::getPoliciesConfiguration()->getDefaultBirthdayPrivacy(), + InformationFieldName::DISPLAY_PICTURE => COnfiguration::getPoliciesConfiguration()->getDefaultDisplayPicturePrivacy(), + InformationFieldName::URL => Configuration::getPoliciesConfiguration()->getDefaultUrlPrivacy(), + }; + } + + try + { + $stmt = Database::getConnection()->prepare('INSERT INTO peer_information (peer_uuid, property_name, property_value, privacy_state) VALUES (:peer_uuid, :property_name, :property_value, :privacy_state)'); + $stmt->bindValue(':peer_uuid', $peerUuid); + $propertyName = $property->value; + $stmt->bindValue(':property_name', $propertyName); + $stmt->bindValue(':property_value', $value); + $stmt->bindValue(':privacy_state', $privacyState->value); + $stmt->execute(); + } + catch(PDOException $e) + { + throw new DatabaseOperationException(sprintf('Failed to add property for peer %s', $peerUuid), $e); + } + } + + /** + * Updates a property for a peer's information record. + * + * @param string|PeerRecord $peerUuid The UUID of the peer to update the property for. + * @param InformationFieldName $property The name of the property to update. + * @param string $value The new value of the property. + * + * @return void + * + * @throws DatabaseOperationException Thrown if the operation fails. + */ + public static function updateField(string|PeerRecord $peerUuid, InformationFieldName $property, string $value): void + { + if($peerUuid instanceof PeerRecord) + { + $peerUuid = $peerUuid->getUuid(); + } + + if(!self::fieldExists($peerUuid, $property)) + { + throw new DatabaseOperationException(sprintf('Cannot to update property %s for peer %s, property does not exist', $property->value, $peerUuid)); + } + + try + { + $stmt = Database::getConnection()->prepare('UPDATE peer_information SET property_value=:property_value WHERE peer_uuid=:peer_uuid AND property_name=:property_name'); + $stmt->bindValue(':peer_uuid', $peerUuid); + $propertyName = $property->value; + $stmt->bindValue(':property_name', $propertyName); + $stmt->bindValue(':property_value', $value); + $stmt->execute(); + } + catch(PDOException $e) + { + throw new DatabaseOperationException(sprintf('Failed to update property %s for peer %s', $property->value, $peerUuid), $e); + } + } + + /** + * Updates the privacy state for a property in a peer's information record. + * + * @param string|PeerRecord $peerUuid The UUID of the peer to update the privacy state for. + * @param InformationFieldName $property The name of the property to update the privacy state for. + * @param PrivacyState $privacyState The new privacy state of the property. + * + * @return void + * + * @throws DatabaseOperationException Thrown if the operation fails. + */ + public static function updatePrivacyState(string|PeerRecord $peerUuid, InformationFieldName $property, PrivacyState $privacyState): void + { + if($peerUuid instanceof PeerRecord) + { + $peerUuid = $peerUuid->getUuid(); + } + + if(!self::fieldExists($peerUuid, $property)) + { + throw new \InvalidArgumentException(sprintf('Cannot update privacy state, the requested property %s does not exist with %s', $property->value, $peerUuid)); + } + + try + { + $stmt = Database::getConnection()->prepare('UPDATE peer_information SET privacy_state=:privacy_state WHERE peer_uuid=:peer_uuid AND property_name=:property_name'); + $stmt->bindValue(':peer_uuid', $peerUuid); + $propertyName = $property->value; + $stmt->bindValue(':property_name', $propertyName); + $privacyState = $privacyState->value; + $stmt->bindValue(':privacy_state', $privacyState); + $stmt->execute(); + } + catch(PDOException $e) + { + throw new DatabaseOperationException(sprintf('Failed to update privacy state for property %s for peer %s', $property->value, $peerUuid), $e); + } + } + + /** + * Checks if a property exists for a peer. + * + * @param string|PeerRecord $peerUuid The UUID of the peer to check for the property. + * @param InformationFieldName $property The name of the property to check for. + * + * @return bool + * + * @throws DatabaseOperationException Thrown if the operation fails. + */ + public static function fieldExists(string|PeerRecord $peerUuid, InformationFieldName $property): bool + { + if($peerUuid instanceof PeerRecord) + { + $peerUuid = $peerUuid->getUuid(); + } + + try + { + $stmt = Database::getConnection()->prepare('SELECT COUNT(*) FROM peer_information WHERE peer_uuid=:peer_uuid AND property_name=:property_name LIMIT 1'); + $stmt->bindValue(':peer_uuid', $peerUuid); + $propertyName = $property->value; + $stmt->bindValue(':property_name', $propertyName); + $stmt->execute(); + + return $stmt->fetchColumn() > 0; + } + catch(PDOException $e) + { + throw new DatabaseOperationException(sprintf('Failed to check if property exists for peer %s', $peerUuid), $e); + } + } + + /** + * Gets a property from a peer's information record. + * + * @param string|PeerRecord $peerUuid The UUID of the peer to get the property from. + * @param InformationFieldName $property The name of the property to get. + * + * @return PeerInformationFieldRecord + * + * @throws DatabaseOperationException Thrown if the operation fails. + */ + public static function getField(string|PeerRecord $peerUuid, InformationFieldName $property): PeerInformationFieldRecord + { + if($peerUuid instanceof PeerRecord) + { + $peerUuid = $peerUuid->getUuid(); + } + + try + { + $stmt = Database::getConnection()->prepare('SELECT * FROM peer_information WHERE peer_uuid=:peer_uuid AND property_name=:property_name LIMIT 1'); + $stmt->bindValue(':peer_uuid', $peerUuid); + $propertyName = $property->value; + $stmt->bindValue(':property_name', $propertyName); + $stmt->execute(); + + $result = $stmt->fetch(); + if($result === false) + { + throw new DatabaseOperationException(sprintf('Property %s does not exist for peer %s', $property->value, $peerUuid)); + } + + return PeerInformationFieldRecord::fromArray($result); + } + catch(PDOException $e) + { + throw new DatabaseOperationException(sprintf('Failed to get property %s for peer %s', $property->value, $peerUuid), $e); + } + } + + /** + * Gets all properties from a peer's information record. + * + * @param string|PeerRecord $peerUuid The UUID of the peer to get the properties from. + * + * @return PeerInformationFieldRecord[] + * + * @throws DatabaseOperationException Thrown if the operation fails. + */ + public static function getFields(string|PeerRecord $peerUuid): array + { + if($peerUuid instanceof PeerRecord) + { + $peerUuid = $peerUuid->getUuid(); + } + + try + { + $stmt = Database::getConnection()->prepare('SELECT * FROM peer_information WHERE peer_uuid=:peer_uuid'); + $stmt->bindValue(':peer_uuid', $peerUuid); + $stmt->execute(); + $results = $stmt->fetchAll(); + + if(!$results) + { + return []; + } + + return array_map(fn($result) => PeerInformationFieldRecord::fromArray($result), $results); + } + catch(PDOException $e) + { + throw new DatabaseOperationException(sprintf('Failed to get properties for peer %s', $peerUuid), $e); + } + } + + /** + * Deletes a property from a peer's information record. + * + * @param string|PeerRecord $peerUuid The UUID of the peer to delete the property from. + * @param InformationFieldName $property The name of the property to delete. + * + * @return void + * + * @throws DatabaseOperationException Thrown if the operation fails. + */ + public static function deleteField(string|PeerRecord $peerUuid, InformationFieldName $property): void + { + if($peerUuid instanceof PeerRecord) + { + $peerUuid = $peerUuid->getUuid(); + } + + try + { + $stmt = Database::getConnection()->prepare('DELETE FROM peer_information WHERE peer_uuid=:peer_uuid AND property_name=:property_name'); + $stmt->bindValue(':peer_uuid', $peerUuid); + $propertyName = $property->value; + $stmt->bindValue(':property_name', $propertyName); + $stmt->execute(); + } + catch(PDOException $e) + { + throw new DatabaseOperationException(sprintf('Failed to delete property %s for peer %s', $property->value, $peerUuid), $e); + } + } + } \ No newline at end of file diff --git a/src/Socialbox/Managers/RegisteredPeerManager.php b/src/Socialbox/Managers/RegisteredPeerManager.php index 5adebe6..bf20cb9 100644 --- a/src/Socialbox/Managers/RegisteredPeerManager.php +++ b/src/Socialbox/Managers/RegisteredPeerManager.php @@ -10,11 +10,10 @@ use Socialbox\Classes\Configuration; use Socialbox\Classes\Database; use Socialbox\Classes\Logger; - use Socialbox\Classes\Validator; use Socialbox\Enums\Flags\PeerFlags; use Socialbox\Enums\ReservedUsernames; use Socialbox\Exceptions\DatabaseOperationException; - use Socialbox\Objects\Database\RegisteredPeerRecord; + use Socialbox\Objects\Database\PeerRecord; use Socialbox\Objects\PeerAddress; use Socialbox\Objects\Standard\Peer; use Symfony\Component\Uid\Uuid; @@ -34,7 +33,7 @@ try { - $statement = Database::getConnection()->prepare('SELECT COUNT(*) FROM `registered_peers` WHERE username=?'); + $statement = Database::getConnection()->prepare('SELECT COUNT(*) FROM peers WHERE username=?'); $statement->bindParam(1, $username); $statement->execute(); @@ -68,7 +67,7 @@ try { - $statement = Database::getConnection()->prepare('INSERT INTO `registered_peers` (uuid, username, server, enabled) VALUES (?, ?, ?, ?)'); + $statement = Database::getConnection()->prepare('INSERT INTO peers (uuid, username, server, enabled) VALUES (?, ?, ?, ?)'); $statement->bindParam(1, $uuid); $username = $peerAddress->getUsername(); $statement->bindParam(2, $username); @@ -88,13 +87,13 @@ * Deletes a peer from the database based on the given UUID or RegisteredPeerRecord. * WARNING: This operation is cascading and will delete all associated data. * - * @param string|RegisteredPeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer to be deleted. + * @param string|PeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer to be deleted. * @return void * @throws DatabaseOperationException If the operation fails. */ - public static function deletePeer(string|RegisteredPeerRecord $uuid): void + public static function deletePeer(string|PeerRecord $uuid): void { - if($uuid instanceof RegisteredPeerRecord) + if($uuid instanceof PeerRecord) { $uuid = $uuid->getUuid(); } @@ -103,7 +102,7 @@ try { - $statement = Database::getConnection()->prepare('DELETE FROM `registered_peers` WHERE uuid=?'); + $statement = Database::getConnection()->prepare('DELETE FROM peers WHERE uuid=?'); $statement->bindParam(1, $uuid); $statement->execute(); } @@ -116,13 +115,13 @@ /** * Retrieves a registered peer record based on the given unique identifier or RegisteredPeerRecord object. * - * @param string|RegisteredPeerRecord $uuid The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @return RegisteredPeerRecord Returns a RegisteredPeerRecord object containing the peer's information. + * @param string|PeerRecord $uuid The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. + * @return PeerRecord Returns a RegisteredPeerRecord object containing the peer's information. * @throws DatabaseOperationException If there is an error during the database operation. */ - public static function getPeer(string|RegisteredPeerRecord $uuid): RegisteredPeerRecord + public static function getPeer(string|PeerRecord $uuid): PeerRecord { - if($uuid instanceof RegisteredPeerRecord) + if($uuid instanceof PeerRecord) { $uuid = $uuid->getUuid(); } @@ -131,7 +130,7 @@ try { - $statement = Database::getConnection()->prepare('SELECT * FROM `registered_peers` WHERE uuid=?'); + $statement = Database::getConnection()->prepare('SELECT * FROM peers WHERE uuid=?'); $statement->bindParam(1, $uuid); $statement->execute(); @@ -142,7 +141,7 @@ throw new DatabaseOperationException(sprintf("The requested peer '%s' does not exist", $uuid)); } - return new RegisteredPeerRecord($result); + return new PeerRecord($result); } catch(Exception $e) { @@ -154,16 +153,16 @@ * Retrieves a peer record by the given username. * * @param PeerAddress $address The address of the peer to be retrieved. - * @return RegisteredPeerRecord|null The record of the peer associated with the given username. + * @return PeerRecord|null The record of the peer associated with the given username. * @throws DatabaseOperationException If there is an error while querying the database. */ - public static function getPeerByAddress(PeerAddress $address): ?RegisteredPeerRecord + public static function getPeerByAddress(PeerAddress $address): ?PeerRecord { Logger::getLogger()->verbose(sprintf("Retrieving peer %s from the database", $address->getAddress())); try { - $statement = Database::getConnection()->prepare('SELECT * FROM `registered_peers` WHERE username=? AND server=?'); + $statement = Database::getConnection()->prepare('SELECT * FROM peers WHERE username=? AND server=?'); $username = $address->getUsername(); $statement->bindParam(1, $username); $server = $address->getDomain(); @@ -184,7 +183,7 @@ return null; } - return new RegisteredPeerRecord($result); + return new PeerRecord($result); } catch(Exception $e) { @@ -223,13 +222,11 @@ try { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET display_name=?, updated=? WHERE uuid=?'); - $displayName = $peer->getDisplayName(); - $statement->bindParam(1, $displayName); + $statement = Database::getConnection()->prepare('UPDATE peers SET updated=? WHERE uuid=?'); $updated = new DateTime(); - $statement->bindParam(2, $updated); + $statement->bindParam(':updated', $updated); $uuid = $existingPeer->getUuid(); - $statement->bindParam(3, $uuid); + $statement->bindParam(':uuid', $uuid); $statement->execute(); } catch(PDOException $e) @@ -244,14 +241,12 @@ try { - $statement = Database::getConnection()->prepare('INSERT INTO `registered_peers` (uuid, username, server, display_name, enabled) VALUES (:uuid, :username, :server, :display_name, 1)'); + $statement = Database::getConnection()->prepare('INSERT INTO peers (uuid, username, server, enabled) VALUES (:uuid, :username, :server, 1)'); $statement->bindParam(':uuid', $uuid); $username = $peer->getAddress()->getUsername(); $statement->bindParam(':username', $username); $server = $peer->getAddress()->getDomain(); $statement->bindParam(':server', $server); - $displayName = $peer->getDisplayName(); - $statement->bindParam(':display_name', $displayName); $statement->execute(); } @@ -264,13 +259,13 @@ /** * Enables a peer identified by the given UUID or RegisteredPeerRecord. * - * @param string|RegisteredPeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer to be enabled. + * @param string|PeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer to be enabled. * @return void * @throws DatabaseOperationException If there is an error while updating the database. */ - public static function enablePeer(string|RegisteredPeerRecord $uuid): void + public static function enablePeer(string|PeerRecord $uuid): void { - if($uuid instanceof RegisteredPeerRecord) + if($uuid instanceof PeerRecord) { $uuid = $uuid->getUuid(); } @@ -279,7 +274,7 @@ try { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET enabled=1 WHERE uuid=?'); + $statement = Database::getConnection()->prepare('UPDATE peers SET enabled=1 WHERE uuid=?'); $statement->bindParam(1, $uuid); $statement->execute(); } @@ -292,13 +287,13 @@ /** * Disables the peer identified by the given UUID or RegisteredPeerRecord. * - * @param string|RegisteredPeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer. + * @param string|PeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer. * @return void * @throws DatabaseOperationException If there is an error while updating the peer's status in the database. */ - public static function disablePeer(string|RegisteredPeerRecord $uuid): void + public static function disablePeer(string|PeerRecord $uuid): void { - if($uuid instanceof RegisteredPeerRecord) + if($uuid instanceof PeerRecord) { $uuid = $uuid->getUuid(); } @@ -307,7 +302,7 @@ try { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET enabled=0 WHERE uuid=?'); + $statement = Database::getConnection()->prepare('UPDATE peers SET enabled=0 WHERE uuid=?'); $statement->bindParam(1, $uuid); $statement->execute(); } @@ -320,14 +315,14 @@ /** * Adds a specific flag to the peer identified by the given UUID or RegisteredPeerRecord. * - * @param string|RegisteredPeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer. + * @param string|PeerRecord $uuid The UUID or RegisteredPeerRecord instance representing the peer. * @param PeerFlags|array $flags The flag or array of flags to be added to the peer. * @return void * @throws DatabaseOperationException If there is an error while updating the database. */ - public static function addFlag(string|RegisteredPeerRecord $uuid, PeerFlags|array $flags): void + public static function addFlag(string|PeerRecord $uuid, PeerFlags|array $flags): void { - if($uuid instanceof RegisteredPeerRecord) + if($uuid instanceof PeerRecord) { $uuid = $uuid->getUuid(); } @@ -349,7 +344,7 @@ try { $implodedFlags = implode(',', array_map(fn($flag) => $flag->name, $existingFlags)); - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET flags=? WHERE uuid=?'); + $statement = Database::getConnection()->prepare('UPDATE peers SET flags=? WHERE uuid=?'); $statement->bindParam(1, $implodedFlags); $statement->bindParam(2, $uuid); $statement->execute(); @@ -363,12 +358,12 @@ /** * Removes a specific flag from the peer identified by the given UUID or RegisteredPeerRecord. * - * @param string|RegisteredPeerRecord $peer + * @param string|PeerRecord $peer * @param PeerFlags $flag The flag to be removed from the peer. * @return void * @throws DatabaseOperationException If there is an error while updating the database. */ - public static function removeFlag(string|RegisteredPeerRecord $peer, PeerFlags $flag): void + public static function removeFlag(string|PeerRecord $peer, PeerFlags $flag): void { if(is_string($peer)) { @@ -387,7 +382,7 @@ try { $implodedFlags = PeerFlags::toString($peer->getFlags()); - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET flags=? WHERE uuid=?'); + $statement = Database::getConnection()->prepare('UPDATE peers SET flags=? WHERE uuid=?'); $statement->bindParam(1, $implodedFlags); $statement->bindParam(2, $registeredPeer); $statement->execute(); @@ -397,435 +392,4 @@ throw new DatabaseOperationException('Failed to remove the flag from the peer in the database', $e); } } - - /** - * Updates the display name of a registered peer based on the given unique identifier or RegisteredPeerRecord object. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @param string $name The new display name to set to the user - * @throws DatabaseOperationException Thrown if there was an error while trying to update the display name - */ - public static function updateDisplayName(string|RegisteredPeerRecord $peer, string $name): void - { - if(empty($name)) - { - throw new InvalidArgumentException('The display name cannot be empty'); - } - - if(strlen($name) > 256) - { - throw new InvalidArgumentException('The display name cannot exceed 256 characters'); - } - - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot update the display name of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Updating display name of peer %s to %s", $peer->getUuid(), $name)); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET display_name=? WHERE uuid=?'); - $statement->bindParam(1, $name); - $uuid = $peer->getUuid(); - $statement->bindParam(2, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to update the display name of the peer in the database', $e); - } - } - - /** - * Deletes the display name of a registered peer identified by a unique identifier or RegisteredPeerRecord object. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @return void - * @throws InvalidArgumentException If the peer is external and its display name cannot be deleted. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function deleteDisplayName(string|RegisteredPeerRecord $peer): void - { - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot delete the display name of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Deleting display name of peer %s", $peer->getUuid())); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET display_name=NULL WHERE uuid=?'); - $uuid = $peer->getUuid(); - $statement->bindParam(1, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to delete the display name of the peer in the database', $e); - } - } - - /** - * Updates the display picture of a registered peer in the database. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the peer or an instance of RegisteredPeerRecord. - * @param string $displayPictureData The raw jpeg data of the display picture. - * @return void - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function updateDisplayPicture(string|RegisteredPeerRecord $peer, string $displayPictureData): void - { - if(empty($uuid)) - { - throw new InvalidArgumentException('The display picture UUID cannot be empty'); - } - - $uuid = Uuid::v4()->toRfc4122(); - $displayPicturePath = Configuration::getStorageConfiguration()->getUserDisplayImagesPath() . DIRECTORY_SEPARATOR . $uuid . '.jpeg'; - - // Delete the file if it already exists - if(file_exists($displayPicturePath)) - { - unlink($displayPicturePath); - } - - // Write the file contents & set the permissions - file_put_contents($displayPicturePath, $displayPictureData); - chmod($displayPicturePath, 0644); - - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - // TODO: Handle for external peers, needs a way to resolve peers to their external counterparts - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot update the display picture of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Updating display picture of peer %s to %s", $peer->getUuid(), $uuid)); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET display_picture=? WHERE uuid=?'); - $statement->bindParam(1, $uuid); - $peerUuid = $peer->getUuid(); - $statement->bindParam(2, $peerUuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to update the display picture of the peer in the database', $e); - } - } - - /** - * Deletes the display picture of a registered peer based on the given unique identifier or RegisteredPeerRecord object. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @return void - * @throws InvalidArgumentException If the peer is external and its display picture cannot be deleted. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function deleteDisplayPicture(string|RegisteredPeerRecord $peer): void - { - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - // TODO: Implement this - throw new InvalidArgumentException('Cannot delete the display picture of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Deleting display picture of peer %s", $peer->getUuid())); - - // Delete the file if it exists - $displayPicturePath = Configuration::getStorageConfiguration()->getUserDisplayImagesPath() . DIRECTORY_SEPARATOR . $peer->getDisplayPicture() . '.jpeg'; - if(file_exists($displayPicturePath)) - { - unlink($displayPicturePath); - } - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET display_picture=NULL WHERE uuid=?'); - $uuid = $peer->getUuid(); - $statement->bindParam(1, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to delete the display picture of the peer in the database', $e); - } - } - - /** - * Updates the email address of a registered peer. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the peer, or an instance of RegisteredPeerRecord. - * @param string $emailAddress The new email address to be assigned to the peer. - * @return void - * @throws InvalidArgumentException If the email address is empty, exceeds 256 characters, is not a valid email format, or if the peer is external. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function updateEmailAddress(string|RegisteredPeerRecord $peer, string $emailAddress): void - { - if(empty($emailAddress)) - { - throw new InvalidArgumentException('The email address cannot be empty'); - } - - if(strlen($emailAddress) > 256) - { - throw new InvalidArgumentException('The email address cannot exceed 256 characters'); - } - - if(filter_var($emailAddress, FILTER_VALIDATE_EMAIL) === false) - { - throw new InvalidArgumentException('The email address is not valid'); - } - - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot update the email address of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Updating email address of peer %s to %s", $peer->getUuid(), $emailAddress)); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET email_address=? WHERE uuid=?'); - $statement->bindParam(1, $emailAddress); - $uuid = $peer->getUuid(); - $statement->bindParam(2, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to update the email address of the peer in the database', $e); - } - } - - /** - * Deletes the email address of a registered peer identified by either a unique identifier or a RegisteredPeerRecord object. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @return void - * @throws InvalidArgumentException If the peer is external and its email address cannot be deleted. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function deleteEmailAddress(string|RegisteredPeerRecord $peer): void - { - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot delete the email address of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Deleting email address of peer %s", $peer->getUuid())); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET email_address=NULL WHERE uuid=?'); - $uuid = $peer->getUuid(); - $statement->bindParam(1, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to delete the email address of the peer in the database', $e); - } - } - - /** - * Updates the phone number of the specified registered peer. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @param string $phoneNumber The new phone number to be set for the peer. - * @return void - * @throws InvalidArgumentException If the phone number is empty, exceeds 16 characters, is invalid, or if the peer is external. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function updatePhoneNumber(string|RegisteredPeerRecord $peer, string $phoneNumber): void - { - if(empty($phoneNumber)) - { - throw new InvalidArgumentException('The phone number cannot be empty'); - } - - if(strlen($phoneNumber) > 16) - { - throw new InvalidArgumentException('The phone number cannot exceed 16 characters'); - } - - if(!Validator::validatePhoneNumber($phoneNumber)) - { - throw new InvalidArgumentException('The phone number is not valid'); - } - - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot update the phone number of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Updating phone number of peer %s to %s", $peer->getUuid(), $phoneNumber)); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET phone_number=? WHERE uuid=?'); - $statement->bindParam(1, $phoneNumber); - $uuid = $peer->getUuid(); - $statement->bindParam(2, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to update the phone number of the peer in the database', $e); - } - } - - /** - * Deletes the phone number of a registered peer based on the given unique identifier or RegisteredPeerRecord object. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @return void This method does not return a value. - * @throws InvalidArgumentException If the peer is external and its phone number cannot be deleted. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function deletePhoneNumber(string|RegisteredPeerRecord $peer): void - { - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot delete the phone number of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Deleting phone number of peer %s", $peer->getUuid())); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET phone_number=NULL WHERE uuid=?'); - $uuid = $peer->getUuid(); - $statement->bindParam(1, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to delete the phone number of the peer in the database', $e); - } - } - - /** - * Sets the birthday of a registered peer record based on the provided date components. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the peer or an instance of RegisteredPeerRecord. - * @param int $month The month component of the birthday. - * @param int $day The day component of the birthday. - * @param int $year The year component of the birthday. - * @return void - * @throws InvalidArgumentException If the peer is external or the provided date is invalid. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function updateBirthday(string|RegisteredPeerRecord $peer, int $month, int $day, int $year): void - { - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot set the birthday of an external peer'); - } - - if(!Validator::validateDate($month, $day, $year)) - { - throw new InvalidArgumentException('The provided date is not valid'); - } - - Logger::getLogger()->verbose(sprintf("Setting birthday of peer %s to %d-%d-%d", $peer->getUuid(), $year, $month, $day)); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET birthday=? WHERE uuid=?'); - $birthday = (new DateTime())->setDate($year, $month, $day)->format('Y-m-d'); - $statement->bindParam(1, $birthday); - $uuid = $peer->getUuid(); - $statement->bindParam(2, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to set the birthday of the peer in the database', $e); - } - } - - /** - * Deletes the birthday of a registered peer based on the given unique identifier or RegisteredPeerRecord object. - * - * @param string|RegisteredPeerRecord $peer The unique identifier of the registered peer, or an instance of RegisteredPeerRecord. - * @throws InvalidArgumentException If the peer is marked as external and cannot have its birthday deleted. - * @throws DatabaseOperationException If there is an error during the database operation. - */ - public static function deleteBirthday(string|RegisteredPeerRecord $peer): void - { - if(is_string($peer)) - { - $peer = self::getPeer($peer); - } - - if($peer->isExternal()) - { - throw new InvalidArgumentException('Cannot delete the birthday of an external peer'); - } - - Logger::getLogger()->verbose(sprintf("Deleting birthday of peer %s", $peer->getUuid())); - - try - { - $statement = Database::getConnection()->prepare('UPDATE `registered_peers` SET birthday=NULL WHERE uuid=?'); - $uuid = $peer->getUuid(); - $statement->bindParam(1, $uuid); - $statement->execute(); - } - catch(PDOException $e) - { - throw new DatabaseOperationException('Failed to delete the birthday of the peer in the database', $e); - } - } } \ No newline at end of file diff --git a/src/Socialbox/Managers/SessionManager.php b/src/Socialbox/Managers/SessionManager.php index 6bf5071..dc87a4d 100644 --- a/src/Socialbox/Managers/SessionManager.php +++ b/src/Socialbox/Managers/SessionManager.php @@ -16,7 +16,7 @@ use Socialbox\Enums\StandardError; use Socialbox\Exceptions\DatabaseOperationException; use Socialbox\Exceptions\StandardException; - use Socialbox\Objects\Database\RegisteredPeerRecord; + use Socialbox\Objects\Database\PeerRecord; use Socialbox\Objects\Database\SessionRecord; use Socialbox\Objects\KeyPair; use Symfony\Component\Uid\Uuid; @@ -26,7 +26,7 @@ /** * Creates a new session for a given peer and client details, and stores it in the database. * - * @param RegisteredPeerRecord $peer The peer record for which the session is being created. + * @param PeerRecord $peer The peer record for which the session is being created. * @param string $clientName The name of the client application. * @param string $clientVersion The version of the client application. * @param string $clientPublicSigningKey The client's public signing key, which must be a valid Ed25519 key. @@ -36,7 +36,7 @@ * @throws InvalidArgumentException If the provided public signing key or encryption key is invalid. * @throws DatabaseOperationException If there is an error during the session creation in the database. */ - public static function createSession(RegisteredPeerRecord $peer, string $clientName, string $clientVersion, string $clientPublicSigningKey, string $clientPublicEncryptionKey, KeyPair $serverEncryptionKeyPair): string + public static function createSession(PeerRecord $peer, string $clientName, string $clientVersion, string $clientPublicSigningKey, string $clientPublicEncryptionKey, KeyPair $serverEncryptionKeyPair): string { if($clientPublicSigningKey === '' || Cryptography::validatePublicSigningKey($clientPublicSigningKey) === false) { diff --git a/src/Socialbox/Objects/ClientRequest.php b/src/Socialbox/Objects/ClientRequest.php index d9f957a..5d28c4f 100644 --- a/src/Socialbox/Objects/ClientRequest.php +++ b/src/Socialbox/Objects/ClientRequest.php @@ -10,7 +10,7 @@ use Socialbox\Exceptions\RequestException; use Socialbox\Managers\RegisteredPeerManager; use Socialbox\Managers\SessionManager; - use Socialbox\Objects\Database\RegisteredPeerRecord; + use Socialbox\Objects\Database\PeerRecord; use Socialbox\Objects\Database\SessionRecord; class ClientRequest @@ -182,10 +182,10 @@ /** * Retrieves the associated peer for the current session. * - * @return RegisteredPeerRecord|null Returns the associated RegisteredPeerRecord if available, or null if no session exists. + * @return PeerRecord|null Returns the associated RegisteredPeerRecord if available, or null if no session exists. * @throws DatabaseOperationException Thrown if an error occurs while retrieving the peer. */ - public function getPeer(): ?RegisteredPeerRecord + public function getPeer(): ?PeerRecord { $session = $this->getSession(); diff --git a/src/Socialbox/Objects/Database/PeerInformationFieldRecord.php b/src/Socialbox/Objects/Database/PeerInformationFieldRecord.php new file mode 100644 index 0000000..2647476 --- /dev/null +++ b/src/Socialbox/Objects/Database/PeerInformationFieldRecord.php @@ -0,0 +1,105 @@ +peerUuid = $data['peer_uuid']; + $this->propertyName = InformationFieldName::from($data['property_name']); + $this->propertyValue = $data['property_value']; + $this->privacyState = PrivacyState::from($data['privacy_state']); + } + + /** + * @return string + */ + public function getPeerUuid(): string + { + return $this->peerUuid; + } + + /** + * @return InformationFieldName + */ + public function getPropertyName(): InformationFieldName + { + return $this->propertyName; + } + + /** + * @return string + */ + public function getPropertyValue(): string + { + return $this->propertyValue; + } + + /** + * @return PrivacyState + */ + public function getPrivacyState(): PrivacyState + { + return $this->privacyState; + } + + /** + * @inheritDoc + */ + public static function fromArray(array $data): PeerInformationFieldRecord + { + return new self($data); + } + + /** + * @inheritDoc + */ + public function toArray(): array + { + return [ + 'peer_uuid' => $this->peerUuid, + 'property_name' => $this->propertyName->value, + 'property_value' => $this->propertyValue, + 'privacy_state' => $this->privacyState->value + ]; + } + + /** + * Converts the record to a standard InformationField object + * + * @return InformationField + */ + public function toInformationField(): InformationField + { + return new InformationField([ + 'name' => $this->propertyName->value, + 'value' => $this->propertyValue + ]); + } + + /** + * Converts the record to a standard InformationFieldState object + * + * @return InformationFieldState + */ + public function toInformationFieldState(): InformationFieldState + { + return new InformationFieldState([ + 'name' => $this->propertyName->value, + 'value' => $this->propertyValue, + 'privacy_state' => $this->privacyState->value + ]); + } + } \ No newline at end of file diff --git a/src/Socialbox/Objects/Database/RegisteredPeerRecord.php b/src/Socialbox/Objects/Database/PeerRecord.php similarity index 70% rename from src/Socialbox/Objects/Database/RegisteredPeerRecord.php rename to src/Socialbox/Objects/Database/PeerRecord.php index aa69195..6143295 100644 --- a/src/Socialbox/Objects/Database/RegisteredPeerRecord.php +++ b/src/Socialbox/Objects/Database/PeerRecord.php @@ -10,16 +10,11 @@ use Socialbox\Objects\Standard\Peer; use Socialbox\Objects\Standard\SelfUser; - class RegisteredPeerRecord implements SerializableInterface + class PeerRecord implements SerializableInterface { private string $uuid; private string $username; private string $server; - private ?string $displayName; - private ?string $displayPicture; - private ?string $emailAddress; - private ?string $phoneNumber; - private ?DateTime $birthday; /** * @var PeerFlags[] */ @@ -38,31 +33,6 @@ $this->uuid = $data['uuid']; $this->username = $data['username']; $this->server = $data['server']; - $this->displayName = $data['display_name'] ?? null; - $this->displayPicture = $data['display_picture'] ?? null; - $this->emailAddress = $data['email_address'] ?? null; - $this->phoneNumber = $data['phone_number'] ?? null; - - if(!isset($data['birthday'])) - { - $this->birthday = null; - } - elseif(is_int($data['birthday'])) - { - $this->birthday = (new DateTime())->setTimestamp($data['birthday']); - } - elseif(is_string($data['birthday'])) - { - $this->birthday = new DateTime($data['birthday']); - } - elseif($data['birthday'] instanceof DateTime) - { - $this->birthday = $data['birthday']; - } - else - { - throw new InvalidArgumentException("The birthday field must be a valid timestamp or date string."); - } if($data['flags']) { @@ -150,56 +120,6 @@ return sprintf("%s@%s", $this->username, Configuration::getInstanceConfiguration()->getDomain()); } - /** - * Retrieves the display name. - * - * @return string|null The display name if set, or null otherwise. - */ - public function getDisplayName(): ?string - { - return $this->displayName; - } - - /** - * Retrieves the display picture. - * - * @return string|null The display picture if set, or null otherwise. - */ - public function getDisplayPicture(): ?string - { - return $this->displayPicture; - } - - /** - * Retrieves the email address. - * - * @return string|null The email address if set, or null otherwise. - */ - public function getEmailAddress(): ?string - { - return $this->emailAddress; - } - - /** - * Retrieves the phone number. - * - * @return string|null The phone number if set, or null otherwise. - */ - public function getPhoneNumber(): ?string - { - return $this->phoneNumber; - } - - /** - * Retrieves the birthday. - * - * @return DateTime|null The birthday if set, or null otherwise. - */ - public function getBirthday(): ?DateTime - { - return $this->birthday; - } - /** * Retrieves the flags. * @@ -292,9 +212,9 @@ */ public function toStandardPeer(): Peer { + // TODO: TO be updated return Peer::fromArray([ 'address' => $this->getAddress(), - 'display_name' => $this->displayName, 'flags' => array_map(fn(PeerFlags $flag) => $flag->value, $this->flags), 'registered' => $this->created->getTimestamp() ]); @@ -317,11 +237,6 @@ 'uuid' => $this->uuid, 'username' => $this->username, 'server' => $this->server, - 'display_name' => $this->displayName, - 'display_picture' => $this->displayPicture, - 'email_address' => $this->emailAddress, - 'phone_number' => $this->phoneNumber, - 'birthday' => $this->birthday?->getTimestamp(), 'flags' => PeerFlags::toString($this->flags), 'enabled' => $this->enabled, 'created' => $this->created, diff --git a/src/Socialbox/Objects/Standard/InformationField.php b/src/Socialbox/Objects/Standard/InformationField.php new file mode 100644 index 0000000..3cdc949 --- /dev/null +++ b/src/Socialbox/Objects/Standard/InformationField.php @@ -0,0 +1,53 @@ +name = InformationFieldName::from($data['name']); + $this->value = $data['value']; + } + + /** + * @return InformationFieldName + */ + public function getName(): InformationFieldName + { + return $this->name; + } + + /** + * @return string + */ + public function getValue(): string + { + return $this->value; + } + + /** + * @inheritDoc + */ + public static function fromArray(array $data): InformationField + { + return new self($data); + } + + /** + * @inheritDoc + */ + public function toArray(): array + { + return [ + 'name' => $this->name->getValue(), + 'value' => $this->value, + ]; + } + } \ No newline at end of file diff --git a/src/Socialbox/Objects/Standard/InformationFieldState.php b/src/Socialbox/Objects/Standard/InformationFieldState.php new file mode 100644 index 0000000..d95b7e6 --- /dev/null +++ b/src/Socialbox/Objects/Standard/InformationFieldState.php @@ -0,0 +1,62 @@ +name = InformationFieldName::from($data['name']); + $this->value = $data['value']; + $this->privacyState = PrivacyState::from($data['privacy_state']); + } + + /** + * @return InformationFieldName + */ + public function getName(): InformationFieldName + { + return $this->name; + } + + /** + * @return string + */ + public function getValue(): string + { + return $this->value; + } + + public function getPrivacyState(): PrivacyState + { + return $this->privacyState; + } + + /** + * @inheritDoc + */ + public static function fromArray(array $data): InformationFieldState + { + return new self($data); + } + + /** + * @inheritDoc + */ + public function toArray(): array + { + return [ + 'name' => $this->name->value, + 'value' => $this->value, + 'privacy_state' => $this->privacyState->value + ]; + } + } \ No newline at end of file diff --git a/src/Socialbox/Objects/Standard/SelfUser.php b/src/Socialbox/Objects/Standard/SelfUser.php index 443f8dc..1d862bd 100644 --- a/src/Socialbox/Objects/Standard/SelfUser.php +++ b/src/Socialbox/Objects/Standard/SelfUser.php @@ -5,7 +5,7 @@ namespace Socialbox\Objects\Standard; use DateTime; use Socialbox\Enums\Flags\PeerFlags; use Socialbox\Interfaces\SerializableInterface; -use Socialbox\Objects\Database\RegisteredPeerRecord; +use Socialbox\Objects\Database\PeerRecord; class SelfUser implements SerializableInterface { @@ -23,11 +23,11 @@ class SelfUser implements SerializableInterface /** * Constructor for initializing the object with provided data. * - * @param array|RegisteredPeerRecord $data Data array containing initial values for object properties. + * @param array|PeerRecord $data Data array containing initial values for object properties. */ - public function __construct(array|RegisteredPeerRecord $data) + public function __construct(array|PeerRecord $data) { - if($data instanceof RegisteredPeerRecord) + if($data instanceof PeerRecord) { $this->uuid = $data->getUuid(); $this->enabled = $data->isEnabled(); diff --git a/src/Socialbox/SocialClient.php b/src/Socialbox/SocialClient.php index 90e11f1..252b9ee 100644 --- a/src/Socialbox/SocialClient.php +++ b/src/Socialbox/SocialClient.php @@ -7,7 +7,9 @@ use Socialbox\Classes\Cryptography; use Socialbox\Classes\RpcClient; use Socialbox\Classes\Utilities; + use Socialbox\Enums\PrivacyState; use Socialbox\Enums\StandardMethods; + use Socialbox\Enums\Types\InformationFieldName; use Socialbox\Exceptions\CryptographyException; use Socialbox\Exceptions\DatabaseOperationException; use Socialbox\Exceptions\ResolutionException; @@ -15,6 +17,7 @@ use Socialbox\Objects\ExportedSession; use Socialbox\Objects\PeerAddress; use Socialbox\Objects\RpcRequest; + use Socialbox\Objects\Standard\InformationField; use Socialbox\Objects\Standard\Peer; use Socialbox\Objects\Standard\ServerDocument; use Socialbox\Objects\Standard\SessionState; @@ -484,132 +487,66 @@ } /** - * Sets the display name in the settings by sending a remote procedure call request. + * Updates the user's OTP settings by sending a remote procedure call request. * - * @param string $displayName The new display name to be set. - * @return true Returns true upon successful update of the display name. + * @param InformationFieldName $field The field to be updated. + * @param string $value The value to be set. + * @param PrivacyState|null $privacy The privacy state to be set. Default is null. + * @return bool True if the OTP was successfully updated, false otherwise. * @throws RpcException Thrown if the RPC request fails. */ - public function settingsSetDisplayName(string $displayName): true + public function settingsAddInformationField(InformationFieldName $field, string $value, ?PrivacyState $privacy=null): true { return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_SET_DISPLAY_NAME, Utilities::randomCrc32(), [ - 'name' => $displayName - ]) + new RpcRequest(StandardMethods::SETTINGS_ADD_INFORMATION_FIELD, Utilities::randomCrc32(), [ + 'field' => $field->value, + 'value' => $value, + 'privacy' => $privacy?->value + ]), )->getResponse()->getResult(); } /** + * Deletes an information field by sending a remote procedure call request. * - */ - public function settingsDeleteDisplayName(): true - { - return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_DELETE_DISPLAY_NAME, Utilities::randomCrc32()) - )->getResponse()->getResult(); - } - - /** - * Updates the display picture by sending a remote procedure call request with the specified file identifier. - * - * @param string $fileId The identifier of the file to be set as the display picture. - * @return true Returns true upon successful update of the + * @param InformationField $field The field to be deleted. + * @return bool True if the field was successfully deleted, false otherwise. * @throws RpcException Thrown if the RPC request fails. */ - public function settingsSetDisplayPicture(string $fileId): true + public function settingsDeleteInformationField(InformationField $field): true { return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_SET_DISPLAY_PICTURE, Utilities::randomCrc32(), [ - 'file_id' => $fileId - ]) + new RpcRequest(StandardMethods::SETTINGS_DELETE_INFORMATION_FIELD, Utilities::randomCrc32()) )->getResponse()->getResult(); } /** - * Updates the email address for the settings by sending a remote procedure call request. + * Updates an information field by sending a remote procedure call request. * - * @param string $emailAddress The new email address to set. - * @return true Returns true if the email address was successfully updated. + * @param InformationField $field The field to be updated. + * @param string $value The value to be set. + * @return bool True if the field was successfully updated, false otherwise. * @throws RpcException Thrown if the RPC request fails. */ - public function settingsSetEmail(string $emailAddress): true + public function settingsUpdateInformationField(InformationField $field, string $value): true { return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_SET_EMAIL, Utilities::randomCrc32(), [ - 'email_address' => $emailAddress - ]) + new RpcRequest(StandardMethods::SETTINGS_UPDATE_INFORMATION_FIELD, Utilities::randomCrc32()) )->getResponse()->getResult(); } /** - * Deletes the email associated with the user settings by sending a remote procedure call request. + * Updates the privacy of an information field by sending a remote procedure call request. * - * @return true Returns true if the email deletion request is successful. - * @throws RpcException - */ - public function settingsDeleteEmail(): true - { - return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_DELETE_EMAIL, Utilities::randomCrc32()) - )->getResponse()->getResult(); - } - - /** - * Updates the phone number in the settings by sending a remote procedure call request. - * - * @param string $phoneNumber The phone number to be set in the settings. - * @return true Returns true if the operation was successful + * @param InformationField $field The field to be updated. + * @param PrivacyState $privacy The privacy state to be set. + * @return bool True if the privacy was successfully updated, false otherwise. * @throws RpcException Thrown if the RPC request fails. */ - public function settingsSetPhone(string $phoneNumber): true + public function settingsUpdateInformationPrivacy(InformationField $field, PrivacyState $privacy): true { return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_SET_DISPLAY_NAME, Utilities::randomCrc32(), [ - 'phone_number' => $phoneNumber - ]) - )->getResponse()->getResult(); - } - - /** - * - */ - public function settingsDeletePhone(): true - { - return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_DELETE_PHONE, Utilities::randomCrc32()) - )->getResponse()->getResult(); - } - - /** - * Updates the user's birthday by sending a remote procedure call request with the specified date. - * - * @param int $year The year of the user's birthday. - * @param int $month The month of the user's birthday. - * @param int $day The day of the user's birthday. - * @return true Returns true if the birthday was successfully updated. - * @throws RpcException Thrown if the RPC request fails. - */ - public function settingsSetBirthday(int $year, int $month, int $day): true - { - return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_SET_BIRTHDAY, Utilities::randomCrc32(), [ - 'year' => $year, - 'month' => $month, - 'day' => $day - ]) - )->getResponse()->getResult(); - } - - /** - * Deletes the saved birthday setting by sending a remote procedure call request. - * - * @return true Returns true if the birthday deletion request is successful. - * @throws RpcException Thrown if the RPC request fails. - */ - public function deleteBirthday(): true - { - return (bool)$this->sendRequest( - new RpcRequest(StandardMethods::SETTINGS_DELETE_BIRTHDAY, Utilities::randomCrc32()) + new RpcRequest(StandardMethods::SETTINGS_UPDATE_INFORMATION_PRIVACY, Utilities::randomCrc32()) )->getResponse()->getResult(); } diff --git a/src/Socialbox/Socialbox.php b/src/Socialbox/Socialbox.php index 133665d..d4383c9 100644 --- a/src/Socialbox/Socialbox.php +++ b/src/Socialbox/Socialbox.php @@ -27,7 +27,7 @@ use Socialbox\Managers\RegisteredPeerManager; use Socialbox\Managers\SessionManager; use Socialbox\Objects\ClientRequest; - use Socialbox\Objects\Database\RegisteredPeerRecord; + use Socialbox\Objects\Database\PeerRecord; use Socialbox\Objects\PeerAddress; use Socialbox\Objects\Standard\Peer; use Socialbox\Objects\Standard\ServerInformation; @@ -836,7 +836,7 @@ throw new StandardException('The requested peer was not found', StandardError::PEER_NOT_FOUND); } - if($registeredPeer instanceof RegisteredPeerRecord) + if($registeredPeer instanceof PeerRecord) { $registeredPeer = $registeredPeer->toStandardPeer(); } diff --git a/tests/Socialbox/SocialClientTest.php b/tests/Socialbox/SocialClientTest.php index 43d6505..b4e143b 100644 --- a/tests/Socialbox/SocialClientTest.php +++ b/tests/Socialbox/SocialClientTest.php @@ -5,6 +5,7 @@ use PHPUnit\Framework\TestCase; use Socialbox\Classes\ServerResolver; use Socialbox\Enums\Flags\SessionFlags; + use Socialbox\Enums\Types\InformationFieldName; class SocialClientTest extends TestCase { @@ -45,7 +46,7 @@ { $client = new SocialClient(self::generateUsername($domain)); $client->settingsSetPassword("password"); - $client->settingsSetDisplayName("Example User"); + $client->settingsAddInformationField(InformationFieldName::DISPLAY_NAME, "Example User"); return $client; } @@ -62,7 +63,7 @@ // Check progressive session state $this->assertTrue($coffeeClient->settingsSetPassword('coffeePassword')); $this->assertFalse($coffeeClient->getSessionState()->containsFlag(SessionFlags::SET_PASSWORD)); - $this->assertTrue($coffeeClient->settingsSetDisplayName('Coffee User')); + $this->assertTrue($coffeeClient->settingsAddInformationField(InformationFieldName::DISPLAY_NAME, 'Coffee User')); $this->assertFalse($coffeeClient->getSessionState()->containsFlag(SessionFlags::SET_DISPLAY_NAME)); $this->assertFalse($coffeeClient->getSessionState()->containsFlag(SessionFlags::REGISTRATION_REQUIRED));