Skip to content

Commit

Permalink
Added Fixed #167
Browse files Browse the repository at this point in the history
  • Loading branch information
overtrue committed Apr 6, 2022
1 parent 23740fc commit 1a539df
Show file tree
Hide file tree
Showing 7 changed files with 98 additions and 11 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -6,3 +6,4 @@ composer.lock
.phpunit.result.cache
cghooks.lock

.php-cs-fixer.cache
13 changes: 13 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -76,12 +76,16 @@ $user1->areFollowingEachOther($user2);

```php
$user->followings;
$user->approvedFollowings;
$user->notApprovedFollowings;
```

#### Get followers:

```php
$user->followers;
$user->approvedFollowers;
$user->notApprovedFollowers;
```

### Follow Requests
Expand All @@ -101,22 +105,31 @@ public function needsToApproveFollowRequests()
```php
// followings count
$user->followings()->count();
$user->approvedFollowings()->count();
$user->notApprovedFollowings()->count();

// with query where
$user->followings()->where('gender', 'female')->count();

// followers count
$user->followers()->count();
$user->approvedFollowers()->count();
$user->notApprovedFollowers()->count();
```

List with `*_count` attribute:

```php
$users = User::withCount(['followings', 'followers'])->get();
// or
$users = User::withCount(['approvedFollowings', 'approvedFollowers'])->get();

foreach($users as $user) {
// $user->followings_count;
// $user->followers_count;
// or
// $user->approved_followings_count;
// $user->approved_followers_count;
}
```

Expand Down
38 changes: 30 additions & 8 deletions src/Followable.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,12 @@
namespace Overtrue\LaravelFollow;

use Illuminate\Contracts\Pagination\Paginator;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Pagination\CursorPaginator;
use Illuminate\Pagination\LengthAwarePaginator;
use Illuminate\Support\Collection;
use Overtrue\LaravelFavorite\Traits\Favoriteable;
use Illuminate\Support\Enumerable;
use Illuminate\Support\LazyCollection;

/**
* @property \Illuminate\Database\Eloquent\Collection $followings
Expand All @@ -29,6 +31,7 @@ public function needsToApproveFollowRequests(): bool
*/
public function follow($user): array
{
/** @var \Illuminate\Database\Eloquent\Model|\Overtrue\LaravelFollow\Followable $user */
$isPending = $user->needsToApproveFollowRequests() ?: false;

$this->followings()->attach($user, [
Expand Down Expand Up @@ -80,7 +83,6 @@ public function hasRequestedToFollow($user): bool
$user = $user->getKey();
}

/* @var \Illuminate\Database\Eloquent\Model $this */
if ($this->relationLoaded('followings')) {
return $this->followings
->where('pivot.accepted_at', '===', null)
Expand All @@ -102,7 +104,6 @@ public function isFollowing($user): bool
$user = $user->getKey();
}

/* @var \Illuminate\Database\Eloquent\Model $this */
if ($this->relationLoaded('followings')) {
return $this->followings
->where('pivot.accepted_at', '!==', null)
Expand All @@ -124,7 +125,6 @@ public function isFollowedBy($user): bool
$user = $user->getKey();
}

/* @var \Illuminate\Database\Eloquent\Model $this */
if ($this->relationLoaded('followers')) {
return $this->followers
->where('pivot.accepted_at', '!==', null)
Expand Down Expand Up @@ -163,7 +163,6 @@ public function scopeOrderByFollowersCountAsc($query)

public function followers(): \Illuminate\Database\Eloquent\Relations\BelongsToMany
{
/* @var \Illuminate\Database\Eloquent\Model $this */
return $this->belongsToMany(
__CLASS__,
\config('follow.relation_table', 'user_follower'),
Expand All @@ -174,7 +173,6 @@ public function followers(): \Illuminate\Database\Eloquent\Relations\BelongsToMa

public function followings(): \Illuminate\Database\Eloquent\Relations\BelongsToMany
{
/* @var \Illuminate\Database\Eloquent\Model $this */
return $this->belongsToMany(
__CLASS__,
\config('follow.relation_table', 'user_follower'),
Expand All @@ -183,6 +181,26 @@ public function followings(): \Illuminate\Database\Eloquent\Relations\BelongsToM
)->withPivot('accepted_at')->withTimestamps()->using(UserFollower::class);
}

public function scopeApprovedFollowers(Builder $query): \Illuminate\Database\Eloquent\Relations\BelongsToMany
{
return $this->followers()->wherePivotNotNull('accepted_at');
}

public function scopeNotApprovedFollowers(Builder $query): \Illuminate\Database\Eloquent\Relations\BelongsToMany
{
return $this->followers()->wherePivotNull('accepted_at');
}

public function scopeApprovedFollowings(Builder $query): \Illuminate\Database\Eloquent\Relations\BelongsToMany
{
return $this->followings()->wherePivotNotNull('accepted_at');
}

public function scopeNotApprovedFollowings(Builder $query): \Illuminate\Database\Eloquent\Relations\BelongsToMany
{
return $this->followings()->wherePivotNull('accepted_at');
}

public function attachFollowStatus($followables, callable $resolver = null)
{
$returnFirst = false;
Expand All @@ -196,14 +214,18 @@ public function attachFollowStatus($followables, callable $resolver = null)
$followables = $followables->getCollection();
break;
case $followables instanceof Paginator:
case $followables instanceof CursorPaginator:
$followables = \collect($followables->items());
break;
case $followables instanceof LazyCollection:
$followables = \collect(\iterator_to_array($followables->getIterator()));
break;
case \is_array($followables):
$followables = \collect($followables);
break;
}

\abort_if(!($followables instanceof Collection), 422, 'Invalid $followables type.');
\abort_if(!($followables instanceof Enumerable), 422, 'Invalid $followables type.');

$followed = UserFollower::where('follower_id', $this->getKey())->get();

Expand Down
1 change: 1 addition & 0 deletions src/UserFollower.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace Overtrue\LaravelFollow;

use Illuminate\Database\Eloquent\Builder;
use Illuminate\Database\Eloquent\Relations\Pivot;
use Overtrue\LaravelFollow\Events\Followed;
use Overtrue\LaravelFollow\Events\Unfollowed;
Expand Down
29 changes: 27 additions & 2 deletions tests/FeatureTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,9 @@
namespace Tests;

use Illuminate\Support\Carbon;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Event;
use Overtrue\LaravelFollow\Events\Followed;
use Overtrue\LaravelFollow\Events\Unfollowed;
use Overtrue\LaravelFollow\UserFollower;

class FeatureTest extends TestCase
{
Expand Down Expand Up @@ -214,6 +212,33 @@ function () use ($user1, $users) {
$this->assertTrue($users[2]->has_followed);
$this->assertTrue($users[3]->has_followed);

// paginator
$users = User::paginate();
$user1->attachFollowStatus($users);

$users = $users->toArray()['data'];
$this->assertFalse($users[0]['has_followed']);
$this->assertTrue($users[1]['has_followed']);
$this->assertTrue($users[2]['has_followed']);
$this->assertTrue($users[3]['has_followed']);

// cursor paginator
$users = User::cursorPaginate();
$user1->attachFollowStatus($users);

$users = $users->toArray()['data'];
$this->assertFalse($users[0]['has_followed']);
$this->assertTrue($users[1]['has_followed']);
$this->assertTrue($users[2]['has_followed']);
$this->assertTrue($users[3]['has_followed']);

// cursor
$users = User::cursor();
$users = $user1->attachFollowStatus($users)->toArray();
$this->assertFalse($users[0]['has_followed']);
$this->assertTrue($users[1]['has_followed']);
$this->assertTrue($users[2]['has_followed']);
$this->assertTrue($users[3]['has_followed']);

// with custom resolver
$users = \collect(['creator' => $user2], ['creator' => $user3], ['creator' => $user4]);
Expand Down
25 changes: 25 additions & 0 deletions tests/PrivacyTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -64,4 +64,29 @@ public function test_following_private_user_sets_request_pending_with_eager_load
$this->assertTrue($user1->hasRequestedToFollow($user2));
$this->assertFalse($user2->isFollowedBy($user1));
}

public function test_approved_scopes()
{
$user1 = User::create(['name' => 'user1']);
$user2 = User::create(['name' => 'user2', 'private' => true]);

$user1->follow($user2);

$this->assertCount(1, $user1->followings()->get());
$this->assertCount(0, $user1->approvedFollowings()->get());
$this->assertCount(1, $user1->notApprovedFollowings()->get());

$this->assertCount(1, $user2->followers()->get());
$this->assertCount(0, $user2->approvedFollowers()->get());
$this->assertCount(1, $user2->notApprovedFollowers()->get());

$user2->acceptFollowRequestFrom($user1);

$this->assertCount(1, $user1->followings()->get());
$this->assertCount(1, $user1->approvedFollowings()->get());
$this->assertCount(0, $user1->notApprovedFollowings()->get());
$this->assertCount(1, $user2->followers()->get());
$this->assertCount(1, $user2->approvedFollowers()->get());
$this->assertCount(0, $user2->notApprovedFollowers()->get());
}
}
2 changes: 1 addition & 1 deletion tests/User.php
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ class User extends Model
/**
* @return bool
*/
public function needsToApproveFollowRequests()
public function needsToApproveFollowRequests(): bool
{
return $this->private ?? false;
}
Expand Down

0 comments on commit 1a539df

Please sign in to comment.