diff --git a/lib/Db/CommentMapper.php b/lib/Db/CommentMapper.php index a934aa51f..f22887435 100644 --- a/lib/Db/CommentMapper.php +++ b/lib/Db/CommentMapper.php @@ -53,12 +53,17 @@ public function findByPoll(int $pollId, bool $getDeleted = false): array { /** * @return void */ - public function renameUserId(string $userId, string $replacementName): void { + public function renameUserId(string $userId, string $replacementId, int|null $pollId = null): void { $query = $this->db->getQueryBuilder(); $query->update($this->getTableName(), self::TABLE) - ->set('user_id', $query->createNamedParameter($replacementName)) - ->where($query->expr()->eq('user_id', $query->createNamedParameter($userId))) - ->executeStatement(); + ->set('user_id', $query->createNamedParameter($replacementId)) + ->where($query->expr()->eq('user_id', $query->createNamedParameter($userId))); + + if ($pollId !== null) { + $query->andWhere($query->expr()->eq('poll_id', $query->createNamedParameter($pollId, IQueryBuilder::PARAM_INT))); + } + + $query->executeStatement(); } public function purgeDeletedComments(int $offset): void { diff --git a/lib/Db/OptionMapper.php b/lib/Db/OptionMapper.php index 80ee3b4cf..a4e72573c 100644 --- a/lib/Db/OptionMapper.php +++ b/lib/Db/OptionMapper.php @@ -128,12 +128,17 @@ public function findOptionsWithDuration(): array { return $this->findEntities($qb); } - public function renameUserId(string $userId, string $replacementName): void { + public function renameUserId(string $userId, string $replacementName, int|null $pollId = null): void { $query = $this->db->getQueryBuilder(); $query->update($this->getTableName()) ->set('owner', $query->createNamedParameter($replacementName)) - ->where($query->expr()->eq('owner', $query->createNamedParameter($userId))) - ->executeStatement(); + ->where($query->expr()->eq('owner', $query->createNamedParameter($userId))); + + if ($pollId !== null) { + $query->andWhere($query->expr()->eq('poll_id', $query->createNamedParameter($pollId, IQueryBuilder::PARAM_INT))); + } + + $query->executeStatement(); } public function purgeDeletedOptions(int $offset): void { diff --git a/lib/Db/VoteMapper.php b/lib/Db/VoteMapper.php index c4b0fcb26..5b231a898 100644 --- a/lib/Db/VoteMapper.php +++ b/lib/Db/VoteMapper.php @@ -115,12 +115,17 @@ public function deleteByPollAndUserId(int $pollId, string $userId): void { $qb->executeStatement(); } - public function renameUserId(string $userId, string $replacementName): void { + public function renameUserId(string $userId, string $replacementId, int|null $pollId = null): void { $query = $this->db->getQueryBuilder(); $query->update($this->getTableName()) - ->set('user_id', $query->createNamedParameter($replacementName)) - ->where($query->expr()->eq('user_id', $query->createNamedParameter($userId))) - ->executeStatement(); + ->set('user_id', $query->createNamedParameter($replacementId)) + ->where($query->expr()->eq('user_id', $query->createNamedParameter($userId))); + + if ($pollId !== null) { + $query->andWhere($query->expr()->eq('poll_id', $query->createNamedParameter($pollId, IQueryBuilder::PARAM_INT))); + } + + $query->executeStatement(); } public function fixVoteOptionText(int $pollId, int $optionId, string $searchOptionText, string $replaceOptionText): void { diff --git a/lib/Service/ShareService.php b/lib/Service/ShareService.php index 16c4b4784..cab9b0de9 100644 --- a/lib/Service/ShareService.php +++ b/lib/Service/ShareService.php @@ -8,11 +8,14 @@ namespace OCA\Polls\Service; +use OCA\Polls\Db\CommentMapper; +use OCA\Polls\Db\OptionMapper; use OCA\Polls\Db\Poll; use OCA\Polls\Db\PollMapper; use OCA\Polls\Db\Share; use OCA\Polls\Db\ShareMapper; use OCA\Polls\Db\UserMapper; +use OCA\Polls\Db\VoteMapper; use OCA\Polls\Event\ShareChangedDisplayNameEvent; use OCA\Polls\Event\ShareChangedEmailEvent; use OCA\Polls\Event\ShareChangedLabelEvent; @@ -36,7 +39,6 @@ use OCP\DB\Exception; use OCP\EventDispatcher\IEventDispatcher; use OCP\Security\ISecureRandom; -use phpDocumentor\Reflection\Types\This; use Psr\Log\LoggerInterface; class ShareService { @@ -64,6 +66,9 @@ public function __construct( private PollMapper $pollMapper, private UserMapper $userMapper, private UserSession $userSession, + private VoteMapper $voteMapper, + private OptionMapper $optionMapper, + private CommentMapper $commentMapper, ) { $this->shares = []; } @@ -304,6 +309,7 @@ private function convertPersonalPublicShareToExternalShare( return; } + $initialUserId = $this->share->getUserId(); $this->share->setUserId($userId ?? $this->generatePublicUserId()); $this->share->setDisplayName($displayName ?? $this->share->getDisplayName()); $this->share->setTimeZoneName($timeZone ?? $this->share->getTimeZoneName()); @@ -322,6 +328,24 @@ private function convertPersonalPublicShareToExternalShare( // remove personal information from user id $this->share->setUserId($this->generatePublicUserId()); $this->share = $this->shareMapper->update($this->share); + $this->convertDependingObjects($initialUserId, $this->share->getUserId(), $this->share->getPollId()); + } + + /** + * Rename userId as a follow up on renaming share's userId + * This methods covers the situation, where a userId of a share + * is changed, but there are already existing votes or options + * belonging to the renamed user + * + * This situation could occur, if a user already registered before the update to 7.2.4 and + * already voted, commented or suggested an option and reenters the poll with an email or contact share + * + * added in Polls 7.2.4 (can be removed later) + */ + private function convertDependingObjects(string $userId, string $replacementId, int $pollId) { + $this->voteMapper->renameUserId($userId, $replacementId, $pollId); + $this->optionMapper->renameUserId($userId, $replacementId, $pollId); + $this->commentMapper->renameUserId($userId, $replacementId, $pollId); } /**