Skip to content

Commit c66dce3

Browse files
IonBazanstayallive
andauthored
Guess inverse relationship name if not provided (#2)
Co-authored-by: Alex Bouma <[email protected]>
1 parent 15a5806 commit c66dce3

File tree

9 files changed

+57
-5
lines changed

9 files changed

+57
-5
lines changed

.github/workflows/ci.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ jobs:
1818
strategy:
1919
fail-fast: false
2020
matrix:
21-
php: [ "8.3", "8.2", "8.1", "8.0", "7.4", "7.3" ]
21+
php: [ "8.4", "8.3", "8.2", "8.1", "8.0", "7.4", "7.3" ]
2222

2323
name: phpunit (PHP:${{ matrix.php }})
2424

src/HasHasManyWithInverseRelation.php

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,16 @@
22

33
namespace Stayallive\Laravel\Eloquent\Relations;
44

5+
use Illuminate\Support\Str;
6+
57
trait HasHasManyWithInverseRelation
68
{
7-
public function hasManyWithInverse($related, $inverse, $foreignKey = null, $localKey = null): HasManyWithInverseRelation
9+
public function hasManyWithInverse($related, $inverse = null, $foreignKey = null, $localKey = null): HasManyWithInverseRelation
810
{
911
/** @var \Illuminate\Database\Eloquent\Model $this */
10-
$instance = $this->newRelatedInstance($related);
12+
$instance = $this->newRelatedInstance($related);
13+
14+
$inverse = $inverse ?: Str::camel(class_basename($this));
1115
$localKey = $localKey ?: $this->getKeyName();
1216
$foreignKey = $foreignKey ?: $this->getForeignKey();
1317

src/HasHasOneWithInverseRelation.php

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,16 @@
22

33
namespace Stayallive\Laravel\Eloquent\Relations;
44

5+
use Illuminate\Support\Str;
6+
57
trait HasHasOneWithInverseRelation
68
{
7-
public function hasOneWithInverse($related, $inverse, $foreignKey = null, $localKey = null): HasOneWithInverseRelation
9+
public function hasOneWithInverse($related, $inverse = null, $foreignKey = null, $localKey = null): HasOneWithInverseRelation
810
{
911
/** @var \Illuminate\Database\Eloquent\Model $this */
10-
$instance = $this->newRelatedInstance($related);
12+
$instance = $this->newRelatedInstance($related);
13+
14+
$inverse = $inverse ?: Str::camel(class_basename($this));
1115
$localKey = $localKey ?: $this->getKeyName();
1216
$foreignKey = $foreignKey ?: $this->getForeignKey();
1317

tests/Stubs/HasManyWithInverse/ChildModel.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,4 +16,9 @@ public function parent(): BelongsTo
1616
{
1717
return $this->belongsTo(ParentModel::class, 'parent_id');
1818
}
19+
20+
public function parentModel(): BelongsTo
21+
{
22+
return $this->belongsTo(ParentModel::class, 'parent_id');
23+
}
1924
}

tests/Stubs/HasManyWithInverse/ParentModel.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
/**
1010
* @property int $id
1111
* @property \Illuminate\Database\Eloquent\Collection $children
12+
* @property \Illuminate\Database\Eloquent\Collection $childrenDefaultInverse
1213
*/
1314
class ParentModel extends Model
1415
{
@@ -24,4 +25,9 @@ public function children(): HasMany
2425
// The `parent` argument (second) is the name of the inverse relationship as defined in the ChildModel
2526
return $this->hasManyWithInverse(ChildModel::class, 'parent', 'parent_id');
2627
}
28+
29+
public function childrenDefaultInverse(): HasMany
30+
{
31+
return $this->hasManyWithInverse(ChildModel::class, null, 'parent_id');
32+
}
2733
}

tests/Stubs/HasOneWithInverse/ChildModel.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,4 +16,9 @@ public function parent(): BelongsTo
1616
{
1717
return $this->belongsTo(ParentModel::class, 'parent_id');
1818
}
19+
20+
public function parentModel(): BelongsTo
21+
{
22+
return $this->belongsTo(ParentModel::class, 'parent_id');
23+
}
1924
}

tests/Stubs/HasOneWithInverse/ParentModel.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
/**
1010
* @property int $id
1111
* @property \Tests\Stubs\HasOneWithInverse\ChildModel $child
12+
* @property \Tests\Stubs\HasOneWithInverse\ChildModel $childDefaultInverse
1213
*/
1314
class ParentModel extends Model
1415
{
@@ -24,4 +25,9 @@ public function child(): HasOne
2425
// The `parent` argument (second) is the name of the inverse relationship as defined in the ChildModel
2526
return $this->hasOneWithInverse(ChildModel::class, 'parent', 'parent_id');
2627
}
28+
29+
public function childDefaultInverse(): HasOne
30+
{
31+
return $this->hasOneWithInverse(ChildModel::class, null, 'parent_id');
32+
}
2733
}

tests/Unit/HasManyWithInverseTest.php

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,17 @@
1919
});
2020
});
2121

22+
test('inverse relationship name can be automatically guessed if not provided', function () {
23+
/** @var \Tests\Stubs\HasManyWithInverse\ParentModel $parent */
24+
$parent = ParentModel::create([]);
25+
26+
/** @var \Tests\Stubs\HasManyWithInverse\ChildModel $child */
27+
$child = $parent->childrenDefaultInverse()->create([]);
28+
29+
expect($child->relationLoaded('parentModel'))->toBeTrue();
30+
expect($child->getRelations()['parentModel']->id)->toBe($parent->id);
31+
});
32+
2233
test('children have the parent relationship automatically set when being created', function () {
2334
/** @var \Tests\Stubs\HasManyWithInverse\ParentModel $parent */
2435
$parent = ParentModel::create([]);

tests/Unit/HasOneWithInverseTest.php

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,17 @@
1919
});
2020
});
2121

22+
test('inverse relationship name can be automatically guessed if not provided', function () {
23+
/** @var \Tests\Stubs\HasOneWithInverse\ParentModel $parent */
24+
$parent = ParentModel::create([]);
25+
26+
/** @var \Tests\Stubs\HasOneWithInverse\ChildModel $child */
27+
$child = $parent->childDefaultInverse()->create([]);
28+
29+
expect($child->relationLoaded('parentModel'))->toBeTrue();
30+
expect($child->getRelations()['parentModel']->id)->toBe($parent->id);
31+
});
32+
2233
test('child has the parent relationship automatically set when being created', function () {
2334
/** @var \Tests\Stubs\HasOneWithInverse\ParentModel $parent */
2435
$parent = ParentModel::create([]);

0 commit comments

Comments
 (0)