Skip to content

Commit

Permalink
update if changed and delete if equal to fallback
Browse files Browse the repository at this point in the history
  • Loading branch information
denisdulici committed Apr 23, 2021
1 parent 6faedfe commit b6a2041
Show file tree
Hide file tree
Showing 2 changed files with 50 additions and 10 deletions.
13 changes: 13 additions & 0 deletions src/Contracts/Driver.php
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,19 @@ public function getFallback($key, $default = null)
return Arr::get((array) config('setting.fallback'), $key);
}

/**
* Check if the given value is same as fallback.
*
* @param string $key
* @param string $value
*
* @return bool
*/
public function isEqualToFallback($key, $value)
{
return (string) $this->getFallback($key) == (string) $value;
}

/**
* Determine if a key exists in the settings data.
*
Expand Down
47 changes: 37 additions & 10 deletions src/Drivers/Database.php
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ class Database extends Driver
*
* @var string
*/
protected $encryptedKeys;
protected $encrypted_keys;

/**
* Any query constraints that should be applied.
Expand All @@ -64,13 +64,13 @@ class Database extends Driver
* @param \Illuminate\Database\Connection $connection
* @param string $table
*/
public function __construct(Connection $connection, $table = null, $key = null, $value = null, $encryptedKeys = [])
public function __construct(Connection $connection, $table = null, $key = null, $value = null, $encrypted_keys = [])
{
$this->connection = $connection;
$this->table = $table ?: 'settings';
$this->key = $key ?: 'key';
$this->value = $value ?: 'value';
$this->encryptedKeys = $encryptedKeys ?: [];
$this->encrypted_keys = $encrypted_keys ?: [];
}

/**
Expand Down Expand Up @@ -166,16 +166,35 @@ public function forget($key)
*/
protected function write(array $data)
{
$keys = $this->newQuery()->pluck($this->key);
// Get current data
$db_data = $this->newQuery()->get([$this->key, $this->value])->toArray();

$insert_data = LaravelArr::dot($data);
$update_data = [];
$delete_keys = [];

foreach ($keys as $key) {
foreach ($db_data as $db_row) {
$key = $db_row->key;
$value = $db_row->value;

$is_in_insert = $is_different_in_db = $is_same_as_fallback = false;

if (isset($insert_data[$key])) {
$update_data[$key] = $insert_data[$key];
$is_in_insert = true;
$is_different_in_db = (string) $insert_data[$key] != (string) $value;
$is_same_as_fallback = $this->isEqualToFallback($key, $insert_data[$key]);
}

if ($is_in_insert) {
if ($is_same_as_fallback) {
// Delete if new data is same as fallback
$delete_keys[] = $key;
} elseif ($is_different_in_db) {
// Update if new data is different from db
$update_data[$key] = $insert_data[$key];
}
} else {
// Delete if current db not available in new data
$delete_keys[] = $key;
}

Expand Down Expand Up @@ -219,6 +238,11 @@ protected function prepareInsertData(array $data)
foreach ($data as $key => $value) {
$value = $this->prepareValue($key, $value);

// Don't insert if same as fallback
if ($this->isEqualToFallback($key, $value)) {
continue;
}

$db_data[] = array_merge(
$this->getExtraColumns(),
[$this->key => $key, $this->value => $value]
Expand All @@ -228,6 +252,11 @@ protected function prepareInsertData(array $data)
foreach ($data as $key => $value) {
$value = $this->prepareValue($key, $value);

// Don't insert if same as fallback
if ($this->isEqualToFallback($key, $value)) {
continue;
}

$db_data[] = [$this->key => $key, $this->value => $value];
}
}
Expand All @@ -247,9 +276,8 @@ protected function prepareInsertData(array $data)
*/
protected function prepareValue(string $key, $value)
{

// Check if key should be encrypted
if (in_array($key, $this->encryptedKeys)) {
if (in_array($key, $this->encrypted_keys)) {
// Cast to string to avoid error when a user passes a boolean value
return Crypt::encryptString((string) $value);
}
Expand All @@ -268,9 +296,8 @@ protected function prepareValue(string $key, $value)
*/
protected function unpackValue(string $key, $value)
{

// Check if key should be encrypted
if (in_array($key, $this->encryptedKeys)) {
if (in_array($key, $this->encrypted_keys)) {
// Cast to string to avoid error when a user passes a boolean value
return Crypt::decryptString((string) $value);
}
Expand Down

0 comments on commit b6a2041

Please sign in to comment.