diff --git a/docs/basic-usage.md b/docs/basic-usage.md index afe403f..5622a82 100644 --- a/docs/basic-usage.md +++ b/docs/basic-usage.md @@ -79,6 +79,52 @@ You may be wondering what the `$this->data['message']` variable is all about. We Throwing an exception is a way to let the queue worker know that the job has failed. +#### Using transactions + +If you have to use transactions in your Job - this is a simple schema you can follow. + +!!! note + + Due to the nature of the queue worker, [Strict Mode](https://codeigniter.com/user_guide/database/transactions.html#strict-mode) is automatically disabled for the database connection assigned to the Database handler. That's because queue worker is a long-running process, and we don't want one failed transaction to affect others. + + If you use the same connection group in your Job as defined in the Database handler, then in that case, you don't need to do anything. + + On the other hand, if you are using a different group to connect to the database in your Job, then if you are using transactions, you should disable Strict Mode through the method: `$db->transStrict(false)` or by setting the `transStrict` option to `false` in your connection config group - the last option will disable Strict Mode globally. + +```php +// ... + +class Email extends BaseJob implements JobInterface +{ + /** + * @throws Exception + */ + public function process(string $data): + { + try { + $db = db_connect(); + // Disable Strict Mode + $db->transStrict(false); + $db->transBegin(); + + // Job logic goes here + // Your code should throw an exception on error + + if ($db->transStatus() === false) { + $db->transRollback(); + } else { + $db->transCommit(); + } + } catch (Exception $e) { + $db->transRollback(); + throw $e; + } + } +} +``` + +#### Other options + We can also configure some things on the job level. It's a number of tries, when the job is failing and time after the job will be retried again after failure. We can specify these options by using variables: ```php diff --git a/docs/configuration.md b/docs/configuration.md index a710146..c26eb5c 100644 --- a/docs/configuration.md +++ b/docs/configuration.md @@ -39,6 +39,10 @@ The configuration settings for `database` handler. * `getShared` - Weather to use shared instance. Default value: `true`. * `skipLocked` - Weather to use "skip locked" feature to maintain concurrency calls. Default to `true`. +!!! note + + The [Strict Mode](https://codeigniter.com/user_guide/database/transactions.html#strict-mode) for the given `dbGroup` is automatically disabled - due to the nature of the queue worker. + ### $redis The configuration settings for `redis` handler. You need to have a [ext-redis](https://github.com/phpredis/phpredis) installed to use it. diff --git a/src/Models/QueueJobFailedModel.php b/src/Models/QueueJobFailedModel.php index 0574da6..e98b5f3 100644 --- a/src/Models/QueueJobFailedModel.php +++ b/src/Models/QueueJobFailedModel.php @@ -13,8 +13,12 @@ namespace CodeIgniter\Queue\Models; +use CodeIgniter\Database\BaseConnection; +use CodeIgniter\Database\ConnectionInterface; use CodeIgniter\Model; use CodeIgniter\Queue\Entities\QueueJobFailed; +use CodeIgniter\Validation\ValidationInterface; +use Config\Database; class QueueJobFailedModel extends Model { @@ -37,4 +41,19 @@ class QueueJobFailedModel extends Model // Callbacks protected $allowCallbacks = false; + + public function __construct(?ConnectionInterface $db = null, ?ValidationInterface $validation = null) + { + $this->DBGroup = config('Queue')->database['dbGroup']; + + /** + * @var BaseConnection|null $db + */ + $db ??= Database::connect($this->DBGroup); + + // Turn off the Strict Mode + $db->transStrict(false); + + parent::__construct($db, $validation); + } } diff --git a/src/Models/QueueJobModel.php b/src/Models/QueueJobModel.php index ed7d26f..6aaf910 100644 --- a/src/Models/QueueJobModel.php +++ b/src/Models/QueueJobModel.php @@ -14,10 +14,14 @@ namespace CodeIgniter\Queue\Models; use CodeIgniter\Database\BaseBuilder; +use CodeIgniter\Database\BaseConnection; +use CodeIgniter\Database\ConnectionInterface; use CodeIgniter\I18n\Time; use CodeIgniter\Model; use CodeIgniter\Queue\Entities\QueueJob; use CodeIgniter\Queue\Enums\Status; +use CodeIgniter\Validation\ValidationInterface; +use Config\Database; use ReflectionException; class QueueJobModel extends Model @@ -42,6 +46,21 @@ class QueueJobModel extends Model // Callbacks protected $allowCallbacks = false; + public function __construct(?ConnectionInterface $db = null, ?ValidationInterface $validation = null) + { + $this->DBGroup = config('Queue')->database['dbGroup']; + + /** + * @var BaseConnection|null $db + */ + $db ??= Database::connect($this->DBGroup); + + // Turn off the Strict Mode + $db->transStrict(false); + + parent::__construct($db, $validation); + } + /** * Get the oldest item from the queue. *