Add more events and filters
This commit is contained in:
parent
9ccb620fe4
commit
3fc176e07a
|
|
@ -11,9 +11,12 @@ use Session;
|
|||
use Carbon\Carbon;
|
||||
use App\Models\User;
|
||||
use App\Models\Texture;
|
||||
use App\Services\Filter;
|
||||
use App\Services\Rejection;
|
||||
use Illuminate\Http\Request;
|
||||
use App\Mail\EmailVerification;
|
||||
use App\Events\UserProfileUpdated;
|
||||
use Illuminate\Contracts\Events\Dispatcher;
|
||||
|
||||
class UserController extends Controller
|
||||
{
|
||||
|
|
@ -205,10 +208,18 @@ class UserController extends Controller
|
|||
]);
|
||||
}
|
||||
|
||||
public function handleProfile(Request $request, User $users)
|
||||
public function handleProfile(Request $request, Filter $filter, Dispatcher $dispatcher)
|
||||
{
|
||||
$action = $request->input('action', '');
|
||||
$user = Auth::user();
|
||||
$addition = $request->except('action');
|
||||
|
||||
$can = $filter->apply('user_can_edit_profile', true, [$action, $addition]);
|
||||
if ($can instanceof Rejection) {
|
||||
return json($can->getReason(), 1);
|
||||
}
|
||||
|
||||
$dispatcher->dispatch('user.profile.updating', [$user, $action, $addition]);
|
||||
|
||||
switch ($action) {
|
||||
case 'nickname':
|
||||
|
|
@ -223,6 +234,8 @@ class UserController extends Controller
|
|||
$nickname = $request->input('new_nickname');
|
||||
$user->nickname = $nickname;
|
||||
$user->save();
|
||||
|
||||
$dispatcher->dispatch('user.profile.updated', [$user, $action, $addition]);
|
||||
event(new UserProfileUpdated($action, $user));
|
||||
|
||||
return json(trans('user.profile.nickname.success', ['nickname' => $nickname]), 0);
|
||||
|
|
@ -238,6 +251,7 @@ class UserController extends Controller
|
|||
}
|
||||
|
||||
if ($user->changePassword($request->input('new_password'))) {
|
||||
$dispatcher->dispatch('user.profile.updated', [$user, $action, $addition]);
|
||||
event(new UserProfileUpdated($action, $user));
|
||||
|
||||
Auth::logout();
|
||||
|
|
@ -265,6 +279,7 @@ class UserController extends Controller
|
|||
$user->verified = false;
|
||||
$user->save();
|
||||
|
||||
$dispatcher->dispatch('user.profile.updated', [$user, $action, $addition]);
|
||||
event(new UserProfileUpdated($action, $user));
|
||||
|
||||
Auth::logout();
|
||||
|
|
@ -286,7 +301,10 @@ class UserController extends Controller
|
|||
|
||||
Auth::logout();
|
||||
|
||||
$dispatcher->dispatch('user.deleting', [$user]);
|
||||
|
||||
if ($user->delete()) {
|
||||
$dispatcher->dispatch('user.deleted', [$user]);
|
||||
session()->flush();
|
||||
|
||||
return json(trans('user.profile.delete.success'), 0);
|
||||
|
|
@ -302,35 +320,39 @@ class UserController extends Controller
|
|||
|
||||
// @codeCoverageIgnore
|
||||
|
||||
/**
|
||||
* Set user avatar.
|
||||
*
|
||||
* @param Request $request
|
||||
*/
|
||||
public function setAvatar(Request $request)
|
||||
public function setAvatar(Request $request, Filter $filter, Dispatcher $dispatcher)
|
||||
{
|
||||
$this->validate($request, [
|
||||
'tid' => 'required|integer',
|
||||
]);
|
||||
$this->validate($request, ['tid' => 'required|integer']);
|
||||
$tid = $request->input('tid');
|
||||
$user = auth()->user();
|
||||
|
||||
$can = $filter->apply('user_can_update_avatar', true, [$user, $tid]);
|
||||
if ($can instanceof Rejection) {
|
||||
return json($can->getReason(), 1);
|
||||
}
|
||||
|
||||
$dispatcher->dispatch('user.avatar.updating', [$user, $tid]);
|
||||
|
||||
if ($tid == 0) {
|
||||
$user->avatar = 0;
|
||||
$user->save();
|
||||
|
||||
$dispatcher->dispatch('user.avatar.updated', [$user, $tid]);
|
||||
|
||||
return json(trans('user.profile.avatar.success'), 0);
|
||||
}
|
||||
|
||||
$result = Texture::find($tid);
|
||||
if ($result) {
|
||||
if ($result->type == 'cape') {
|
||||
$texture = Texture::find($tid);
|
||||
if ($texture) {
|
||||
if ($texture->type == 'cape') {
|
||||
return json(trans('user.profile.avatar.wrong-type'), 1);
|
||||
}
|
||||
|
||||
$user->avatar = $tid;
|
||||
$user->save();
|
||||
|
||||
$dispatcher->dispatch('user.avatar.updated', [$user, $tid]);
|
||||
|
||||
return json(trans('user.profile.avatar.success'), 0);
|
||||
} else {
|
||||
return json(trans('skinlib.non-existent'), 1);
|
||||
|
|
|
|||
|
|
@ -7,6 +7,8 @@ use Parsedown;
|
|||
use App\Events;
|
||||
use App\Models\User;
|
||||
use App\Notifications;
|
||||
use App\Services\Filter;
|
||||
use App\Services\Rejection;
|
||||
use Illuminate\Support\Str;
|
||||
use App\Mail\EmailVerification;
|
||||
use Illuminate\Support\Facades\Mail;
|
||||
|
|
@ -224,6 +226,19 @@ class UserControllerTest extends TestCase
|
|||
Event::fake();
|
||||
$user = factory(User::class)->create();
|
||||
$user->changePassword('12345678');
|
||||
$uid = $user->uid;
|
||||
|
||||
// Rejected by filter
|
||||
$filter = resolve(Filter::class);
|
||||
$filter->add('user_can_edit_profile', function ($can, $action, $addition) {
|
||||
$this->assertEquals('nope', $action);
|
||||
$this->assertEquals([], $addition);
|
||||
return new Rejection('rejected');
|
||||
});
|
||||
$this->actingAs($user)
|
||||
->postJson('/user/profile', ['action' => 'nope'])
|
||||
->assertJson(['code' => 1, 'message' => 'rejected']);
|
||||
$filter->remove('user_can_edit_profile');
|
||||
|
||||
// Invalid action
|
||||
$this->actingAs($user)
|
||||
|
|
@ -232,6 +247,13 @@ class UserControllerTest extends TestCase
|
|||
'code' => 1,
|
||||
'message' => trans('general.illegal-parameters'),
|
||||
]);
|
||||
Event::assertDispatched('user.profile.updating', function ($eventName, $payload) use ($uid) {
|
||||
[$user, $action, $addition] = $payload;
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals('', $action);
|
||||
$this->assertEquals([], $addition);
|
||||
return true;
|
||||
});
|
||||
|
||||
// Change nickname without `new_nickname` field
|
||||
$this->postJson('/user/profile', ['action' => 'nickname'])
|
||||
|
|
@ -265,7 +287,15 @@ class UserControllerTest extends TestCase
|
|||
'message' => trans('user.profile.nickname.success', ['nickname' => 'nickname']),
|
||||
]);
|
||||
$this->assertEquals('nickname', User::find($user->uid)->nickname);
|
||||
Event::assertDispatched('user.profile.updated', function ($eventName, $payload) use ($uid) {
|
||||
[$user, $action, $addition] = $payload;
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals('nickname', $action);
|
||||
$this->assertEquals(['new_nickname' => 'nickname'], $addition);
|
||||
return true;
|
||||
});
|
||||
Event::assertDispatched(Events\UserProfileUpdated::class);
|
||||
Event::fake();
|
||||
|
||||
// Change password without `current_password` field
|
||||
$this->postJson('/user/profile', ['action' => 'password'])
|
||||
|
|
@ -318,10 +348,21 @@ class UserControllerTest extends TestCase
|
|||
'code' => 0,
|
||||
'message' => trans('user.profile.password.success'),
|
||||
]);
|
||||
Event::assertDispatched('user.profile.updated', function ($eventName, $payload) use ($uid) {
|
||||
[$user, $action, $addition] = $payload;
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals('password', $action);
|
||||
$this->assertEquals([
|
||||
'current_password' => '12345678',
|
||||
'new_password' => '87654321',
|
||||
], $addition);
|
||||
return true;
|
||||
});
|
||||
Event::assertDispatched(Events\EncryptUserPassword::class);
|
||||
$this->assertTrue(User::find($user->uid)->verifyPassword('87654321'));
|
||||
// After changed password, user should re-login.
|
||||
$this->assertGuest();
|
||||
Event::fake();
|
||||
|
||||
$user = User::find($user->uid);
|
||||
// Change email without `new_email` field
|
||||
|
|
@ -381,10 +422,21 @@ class UserControllerTest extends TestCase
|
|||
'code' => 0,
|
||||
'message' => trans('user.profile.email.success'),
|
||||
]);
|
||||
Event::assertDispatched('user.profile.updated', function ($eventName, $payload) use ($uid) {
|
||||
[$user, $action, $addition] = $payload;
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals('email', $action);
|
||||
$this->assertEquals([
|
||||
'new_email' => 'a@b.c',
|
||||
'password' => '87654321',
|
||||
], $addition);
|
||||
return true;
|
||||
});
|
||||
$this->assertEquals('a@b.c', User::find($user->uid)->email);
|
||||
$this->assertEquals(0, User::find($user->uid)->verified);
|
||||
// After changed email, user should re-login.
|
||||
$this->assertGuest();
|
||||
Event::fake();
|
||||
|
||||
$user = User::find($user->uid);
|
||||
$user->verified = true;
|
||||
|
|
@ -426,6 +478,14 @@ class UserControllerTest extends TestCase
|
|||
'code' => 0,
|
||||
'message' => trans('user.profile.delete.success'),
|
||||
]);
|
||||
Event::assertDispatched('user.deleting', function ($eventName, $payload) use ($uid) {
|
||||
$this->assertEquals($uid, $payload[0]->uid);
|
||||
return true;
|
||||
});
|
||||
Event::assertDispatched('user.deleted', function ($eventName, $payload) use ($uid) {
|
||||
$this->assertEquals($uid, $payload[0]->uid);
|
||||
return true;
|
||||
});
|
||||
$this->assertNull(User::find($user->uid));
|
||||
|
||||
// Administrator cannot be deleted
|
||||
|
|
@ -442,6 +502,7 @@ class UserControllerTest extends TestCase
|
|||
public function testSetAvatar()
|
||||
{
|
||||
$user = factory(User::class)->create();
|
||||
$uid = $user->uid;
|
||||
$steve = factory(\App\Models\Texture::class)->create();
|
||||
$cape = factory(\App\Models\Texture::class, 'cape')->create();
|
||||
|
||||
|
|
@ -457,9 +518,7 @@ class UserControllerTest extends TestCase
|
|||
|
||||
// Texture cannot be found
|
||||
$this->actingAs($user)
|
||||
->postJson('/user/profile/avatar', [
|
||||
'tid' => -1,
|
||||
])
|
||||
->postJson('/user/profile/avatar', ['tid' => -1])
|
||||
->assertJson([
|
||||
'code' => 1,
|
||||
'message' => trans('skinlib.non-existent'),
|
||||
|
|
@ -467,29 +526,65 @@ class UserControllerTest extends TestCase
|
|||
|
||||
// Use cape
|
||||
$this->actingAs($user)
|
||||
->postJson('/user/profile/avatar', [
|
||||
'tid' => $cape->tid,
|
||||
])
|
||||
->postJson('/user/profile/avatar', ['tid' => $cape->tid])
|
||||
->assertJson([
|
||||
'code' => 1,
|
||||
'message' => trans('user.profile.avatar.wrong-type'),
|
||||
]);
|
||||
|
||||
// Success
|
||||
Event::fake();
|
||||
$this->actingAs($user)
|
||||
->postJson('/user/profile/avatar', [
|
||||
'tid' => $steve->tid,
|
||||
])
|
||||
->postJson('/user/profile/avatar', ['tid' => $steve->tid])
|
||||
->assertJson([
|
||||
'code' => 0,
|
||||
'message' => trans('user.profile.avatar.success'),
|
||||
]);
|
||||
$this->assertEquals($steve->tid, User::find($user->uid)->avatar);
|
||||
Event::assertDispatched(
|
||||
'user.avatar.updating',
|
||||
function ($eventName, $payload) use ($uid, $steve) {
|
||||
[$user, $tid] = $payload;
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals($steve->tid, $tid);
|
||||
return true;
|
||||
}
|
||||
);
|
||||
Event::assertDispatched(
|
||||
'user.avatar.updated',
|
||||
function ($eventName, $payload) use ($uid, $steve) {
|
||||
[$user, $tid] = $payload;
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals($steve->tid, $tid);
|
||||
return true;
|
||||
}
|
||||
);
|
||||
|
||||
// Reset avatar
|
||||
Event::fake();
|
||||
$this->postJson('/user/profile/avatar', ['tid' => 0])
|
||||
->assertJson(['code' => 0]);
|
||||
$this->assertEquals(0, User::find($user->uid)->avatar);
|
||||
Event::assertDispatched(
|
||||
'user.avatar.updated',
|
||||
function ($eventName, $payload) use ($uid) {
|
||||
[$user, $tid] = $payload;
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals(0, $tid);
|
||||
return true;
|
||||
}
|
||||
);
|
||||
|
||||
// Rejected by filter
|
||||
$filter = resolve(Filter::class);
|
||||
$filter->add('user_can_update_avatar', function ($can, $user, $tid) use ($uid, $steve) {
|
||||
$this->assertEquals($uid, $user->uid);
|
||||
$this->assertEquals($steve->tid, $tid);
|
||||
return new Rejection('rejected');
|
||||
});
|
||||
$this->actingAs($user)
|
||||
->postJson('/user/profile/avatar', ['tid' => $steve->tid])
|
||||
->assertJson(['code' => 1, 'message' => 'rejected']);
|
||||
}
|
||||
|
||||
public function testReadNotification()
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user