Skip to content

Commit

Permalink
Merge pull request #7140 from Automattic/add/create-table-version-on-…
Browse files Browse the repository at this point in the history
…save

Create tables-based versions of student progress and quiz data when saving of their comment based versions
  • Loading branch information
merkushin authored Sep 4, 2023
2 parents 164ea6e + eb0bfa3 commit 7f1925d
Show file tree
Hide file tree
Showing 16 changed files with 473 additions and 249 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -89,10 +89,8 @@ public function create( Submission $submission, int $question_id, string $value
$answer = $this->comments_based_repository->create( $submission, $question_id, $value );

if ( $this->use_tables ) {
$tables_based_submission = $this->get_tables_based_submission( $submission );
if ( $tables_based_submission ) {
$this->tables_based_repository->create( $tables_based_submission, $question_id, $value );
}
$tables_based_submission = $this->get_or_create_tables_based_submission( $submission );
$this->tables_based_repository->create( $tables_based_submission, $question_id, $value );
}

return $answer;
Expand Down Expand Up @@ -122,21 +120,23 @@ public function delete_all( Submission $submission ): void {
$this->comments_based_repository->delete_all( $submission );

if ( $this->use_tables ) {
$tables_based_submission = $this->get_tables_based_submission( $submission );
if ( $tables_based_submission ) {
$this->tables_based_repository->delete_all( $tables_based_submission );
}
$tables_based_submission = $this->get_or_create_tables_based_submission( $submission );
$this->tables_based_repository->delete_all( $tables_based_submission );
}
}

/**
* Get the tables based submission for a given submission.
* Get the tables based submission for a given submission or create if not exists.
*
* @param Submission $submission The submission.
*
* @return Submission|null The tables based submission or null if it does not exist.
* @return Submission The tables based submission or null if it does not exist.
*/
private function get_tables_based_submission( Submission $submission ): ?Submission {
return $this->tables_based_submission_repository->get( $submission->get_quiz_id(), $submission->get_user_id() );
private function get_or_create_tables_based_submission( Submission $submission ): Submission {
return $this->tables_based_submission_repository->get_or_create(
$submission->get_quiz_id(),
$submission->get_user_id(),
$submission->get_final_grade()
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,10 @@

use DateTimeImmutable;
use Sensei\Internal\Quiz_Submission\Answer\Models\Answer;
use Sensei\Internal\Quiz_Submission\Answer\Repositories\Comments_Based_Answer_Repository;
use Sensei\Internal\Quiz_Submission\Answer\Repositories\Tables_Based_Answer_Repository;
use Sensei\Internal\Quiz_Submission\Grade\Models\Grade;
use Sensei\Internal\Quiz_Submission\Submission\Models\Submission;
use Sensei\Internal\Quiz_Submission\Submission\Repositories\Comments_Based_Submission_Repository;
use Sensei\Internal\Quiz_Submission\Submission\Repositories\Tables_Based_Submission_Repository;

if ( ! defined( 'ABSPATH' ) ) {
Expand Down Expand Up @@ -56,6 +56,14 @@ class Aggregate_Grade_Repository implements Grade_Repository_Interface {
*/
private $tables_based_answer_repository;


/**
* Comments based answer repository.
*
* @var Comments_Based_Answer_Repository
*/
private $comments_based_answer_repository;

/**
* The flag if the tables based implementation is available for use.
*
Expand All @@ -72,19 +80,22 @@ class Aggregate_Grade_Repository implements Grade_Repository_Interface {
* @param Tables_Based_Grade_Repository $tables_based_repository Tables based quiz answer repository implementation.
* @param Tables_Based_Submission_Repository $tables_based_submission_repository Tables based quiz submission repository implementation.
* @param Tables_Based_Answer_Repository $tables_based_answer_repository Tables based quiz answer repository implementation.
* @param Comments_Based_Answer_Repository $comments_based_answer_repository Comments based quiz answer repository implementation.
* @param bool $use_tables The flag if the tables based implementation is available for use.
*/
public function __construct(
Comments_Based_Grade_Repository $comments_based_repository,
Tables_Based_Grade_Repository $tables_based_repository,
Tables_Based_Submission_Repository $tables_based_submission_repository,
Tables_Based_Answer_Repository $tables_based_answer_repository,
Comments_Based_Answer_Repository $comments_based_answer_repository,
bool $use_tables
) {
$this->comments_based_repository = $comments_based_repository;
$this->tables_based_repository = $tables_based_repository;
$this->tables_based_submission_repository = $tables_based_submission_repository;
$this->tables_based_answer_repository = $tables_based_answer_repository;
$this->comments_based_answer_repository = $comments_based_answer_repository;
$this->use_tables = $use_tables;
}

Expand All @@ -105,25 +116,52 @@ public function create( Submission $submission, int $answer_id, int $question_id
$grade = $this->comments_based_repository->create( $submission, $answer_id, $question_id, $points, $feedback );

if ( $this->use_tables ) {
$tables_based_submission = $this->tables_based_submission_repository->get( $submission->get_quiz_id(), $submission->get_user_id() );
if ( $tables_based_submission ) {
$answers = $this->tables_based_answer_repository->get_all( $tables_based_submission->get_id() );
$filtered = array_filter(
$answers,
function( Answer $answer ) use ( $question_id ) {
return $answer->get_question_id() === $question_id;
}
);
if ( count( $filtered ) === 1 ) {
$answer = array_shift( $filtered );
$this->tables_based_repository->create( $tables_based_submission, $answer->get_id(), $question_id, $points, $feedback );
}
$tables_based_submission = $this->get_or_create_tables_based_submission( $submission );

$answers = $this->get_or_create_tables_based_answers( $submission, $tables_based_submission );
$answer = $answers[ $question_id ] ?? null;

if ( $answer ) {
$this->tables_based_repository->create( $tables_based_submission, $answer->get_id(), $question_id, $points, $feedback );
}
}

return $grade;
}

/**
* Get or create all answers for the table based submission.
*
* @param Submission $comments_based_submission The comments based submission.
* @param Submission $tables_based_submission The tables based submission.
* @return Answer[] The answers.
*/
public function get_or_create_tables_based_answers( $comments_based_submission, $tables_based_submission ): array {
$comments_based_answers = $this->comments_based_answer_repository->get_all( $comments_based_submission->get_id() );
$tables_based_answers = $this->tables_based_answer_repository->get_all( $tables_based_submission->get_id() );
$result = array();
foreach ( $comments_based_answers as $comments_based_answer ) {
$filtered = array_filter(
$tables_based_answers,
function( Answer $answer ) use ( $comments_based_answer ) {
return $answer->get_question_id() === $comments_based_answer->get_question_id();
}
);
if ( count( $filtered ) === 1 ) {
$answer = array_shift( $filtered );
$result[ $answer->get_question_id() ] = $answer;
} else {
$result[ $comments_based_answer->get_question_id() ] = $this->tables_based_answer_repository->create(
$tables_based_submission,
$comments_based_answer->get_question_id(),
$comments_based_answer->get_value()
);
}
}

return $result;
}

/**
* Get all grades for a quiz submission.
*
Expand All @@ -149,41 +187,86 @@ public function save_many( Submission $submission, array $grades ): void {
$this->comments_based_repository->save_many( $submission, $grades );

if ( $this->use_tables ) {
$grades_to_save = [];
$tables_based_submission = $this->tables_based_submission_repository->get( $submission->get_quiz_id(), $submission->get_user_id() );
if ( $tables_based_submission ) {
$tables_based_grades = $this->tables_based_repository->get_all( $tables_based_submission->get_id() );
foreach ( $grades as $grade ) {
$filtered = array_filter(
$tables_based_grades,
function( Grade $tables_based_grade ) use ( $grade ) {
return $tables_based_grade->get_question_id() === $grade->get_question_id();
}
);
if ( count( $filtered ) !== 1 ) {
continue;
}
$tables_based_grade = array_shift( $filtered );

$created_at = new DateTimeImmutable( '@' . $grade->get_created_at()->getTimestamp() );
$updated_at = new DateTimeImmutable( '@' . $grade->get_updated_at()->getTimestamp() );

$grades_to_save[] = new Grade(
$tables_based_grade->get_id(),
$tables_based_grade->get_answer_id(),
$tables_based_grade->get_question_id(),
$grade->get_points(),
$grade->get_feedback(),
$created_at,
$updated_at
);
$tables_based_submission = $this->get_or_create_tables_based_submission( $submission );
$tables_based_grades = $this->get_or_create_tables_based_grades_for_save(
$submission,
$tables_based_submission,
$grades
);

$grades_to_save = [];
foreach ( $grades as $grade ) {
$tables_based_grade = $tables_based_grades[ $grade->get_question_id() ] ?? null;
if ( null === $tables_based_grade ) {
continue;
}

$this->tables_based_repository->save_many( $tables_based_submission, $grades_to_save );
$created_at = new DateTimeImmutable( '@' . $grade->get_created_at()->getTimestamp() );
$updated_at = new DateTimeImmutable( '@' . $grade->get_updated_at()->getTimestamp() );

$grades_to_save[] = new Grade(
$tables_based_grade->get_id(),
$tables_based_grade->get_answer_id(),
$tables_based_grade->get_question_id(),
$grade->get_points(),
$grade->get_feedback(),
$created_at,
$updated_at
);
}

$this->tables_based_repository->save_many( $tables_based_submission, $grades_to_save );
}
}

/**
* Get or create all grades for the table based submission.
*
* @param Submission $comments_based_submission The comments based submission.
* @param Submission $tables_based_submission The tables based submission.
* @param Grade[] $comments_based_grades The comments based grades.
* @return Grade[] The tables based grades.
*/
private function get_or_create_tables_based_grades_for_save(
Submission $comments_based_submission,
Submission $tables_based_submission,
array $comments_based_grades
): array {
$tables_based_answers = $this->get_or_create_tables_based_answers(
$comments_based_submission,
$tables_based_submission
);
$tables_based_grades = $this->tables_based_repository->get_all( $tables_based_submission->get_id() );
$result = array();
foreach ( $comments_based_grades as $comments_based_grade ) {
$filtered = array_filter(
$tables_based_grades,
function( Grade $grade ) use ( $comments_based_grade ) {
return $grade->get_question_id() === $comments_based_grade->get_question_id();
}
);
if ( count( $filtered ) === 1 ) {
$grade = array_shift( $filtered );
$result[ $grade->get_question_id() ] = $grade;
} else {
$answer = $tables_based_answers[ $comments_based_grade->get_question_id() ] ?? null;
if ( ! $answer ) {
continue;
}

$result[ $comments_based_grade->get_question_id() ] = $this->tables_based_repository->create(
$tables_based_submission,
$answer->get_id(),
$comments_based_grade->get_question_id(),
$comments_based_grade->get_points(),
$comments_based_grade->get_feedback()
);
}
}

return $result;
}

/**
* Delete all grades for a submission.
*
Expand All @@ -195,10 +278,23 @@ public function delete_all( Submission $submission ): void {
$this->comments_based_repository->delete_all( $submission );

if ( $this->use_tables ) {
$tables_based_submission = $this->tables_based_submission_repository->get( $submission->get_quiz_id(), $submission->get_user_id() );
if ( $tables_based_submission ) {
$this->tables_based_repository->delete_all( $tables_based_submission );
}
$tables_based_submission = $this->get_or_create_tables_based_submission( $submission );
$this->tables_based_repository->delete_all( $tables_based_submission );
}
}

/**
* Get the tables based submission for a given submission or create if not exists.
*
* @param Submission $submission The submission.
*
* @return Submission The tables based submission.
*/
private function get_or_create_tables_based_submission( Submission $submission ): Submission {
return $this->tables_based_submission_repository->get_or_create(
$submission->get_quiz_id(),
$submission->get_user_id(),
$submission->get_final_grade()
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

namespace Sensei\Internal\Quiz_Submission\Grade\Repositories;

use Sensei\Internal\Quiz_Submission\Answer\Repositories\Comments_Based_Answer_Repository;
use Sensei\Internal\Quiz_Submission\Answer\Repositories\Tables_Based_Answer_Repository;
use Sensei\Internal\Quiz_Submission\Submission\Repositories\Tables_Based_Submission_Repository;

Expand Down Expand Up @@ -56,6 +57,7 @@ public function create(): Grade_Repository_Interface {
new Tables_Based_Grade_Repository( $wpdb ),
new Tables_Based_Submission_Repository( $wpdb ),
new Tables_Based_Answer_Repository( $wpdb ),
new Comments_Based_Answer_Repository(),
$this->use_tables
);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -91,13 +91,7 @@ public function create( int $quiz_id, int $user_id, float $final_grade = null ):
* @return Submission The quiz submission.
*/
public function get_or_create( int $quiz_id, int $user_id, float $final_grade = null ): Submission {
$submission = $this->get( $quiz_id, $user_id );

if ( $submission ) {
return $submission;
}

return $this->create( $quiz_id, $user_id, $final_grade );
return $this->comments_based_repository->get_or_create( $quiz_id, $user_id, $final_grade );
}

/**
Expand Down Expand Up @@ -138,24 +132,26 @@ public function save( Submission $submission ): void {
$this->comments_based_repository->save( $submission );

if ( $this->use_tables ) {
$tables_based_submission = $this->tables_based_repository->get( $submission->get_quiz_id(), $submission->get_user_id() );

if ( $tables_based_submission ) {
// Make sure the dates are in UTC.
$created_at = new DateTimeImmutable( '@' . $submission->get_created_at()->getTimestamp() );
$updated_at = new DateTimeImmutable( '@' . $submission->get_updated_at()->getTimestamp() );

$submission_to_save = new Submission(
$tables_based_submission->get_id(),
$submission->get_quiz_id(),
$submission->get_user_id(),
$submission->get_final_grade(),
$created_at,
$updated_at
);

$this->tables_based_repository->save( $submission_to_save );
}
$tables_based_submission = $this->tables_based_repository->get_or_create(
$submission->get_quiz_id(),
$submission->get_user_id(),
$submission->get_final_grade()
);

// Make sure the dates are in UTC.
$created_at = new DateTimeImmutable( '@' . $submission->get_created_at()->getTimestamp() );
$updated_at = new DateTimeImmutable( '@' . $submission->get_updated_at()->getTimestamp() );

$submission_to_save = new Submission(
$tables_based_submission->get_id(),
$submission->get_quiz_id(),
$submission->get_user_id(),
$submission->get_final_grade(),
$created_at,
$updated_at
);

$this->tables_based_repository->save( $submission_to_save );
}
}

Expand Down
Loading

0 comments on commit 7f1925d

Please sign in to comment.