diff --git a/app/Http/Controllers/MagicController.php b/app/Http/Controllers/MagicController.php index f8cf94ee1..66dcf5549 100644 --- a/app/Http/Controllers/MagicController.php +++ b/app/Http/Controllers/MagicController.php @@ -6,6 +6,7 @@ use App\Http\Livewire\Server\PrivateKey; use App\Models\Environment; use App\Models\Project; use App\Models\Server; +use App\Models\Team; class MagicController extends Controller { @@ -53,4 +54,16 @@ class MagicController extends Controller 'environment_name' => $environment->name, ]); } + public function newTeam() + { + $team = Team::create( + [ + 'name' => request()->query('name') ?? generate_random_name(), + 'personal_team' => false, + ], + ); + auth()->user()->teams()->attach($team, ['role' => 'admin']); + session(['currentTeam' => $team]); + return redirect(request()->header('Referer')); + } } diff --git a/app/Http/Livewire/Team/Create.php b/app/Http/Livewire/Team/Create.php new file mode 100644 index 000000000..5aa07bc94 --- /dev/null +++ b/app/Http/Livewire/Team/Create.php @@ -0,0 +1,37 @@ + 'required|min:3|max:255', + 'description' => 'nullable|min:3|max:255', + ]; + protected $validationAttributes = [ + 'name' => 'name', + 'description' => 'description', + ]; + public function submit() + { + $this->validate(); + try { + $team = Team::create([ + 'name' => $this->name, + 'description' => $this->description, + 'personal_team' => false, + ]); + auth()->user()->teams()->attach($team, ['role' => 'admin']); + session(['currentTeam' => $team]); + return redirect()->route('team.show'); + } catch (\Throwable $th) { + return general_error_handler($th, $this); + } + } +} diff --git a/app/Http/Livewire/Team/Form.php b/app/Http/Livewire/Team/Form.php new file mode 100644 index 000000000..f60f72523 --- /dev/null +++ b/app/Http/Livewire/Team/Form.php @@ -0,0 +1,35 @@ + 'required|min:3|max:255', + 'team.description' => 'nullable|min:3|max:255', + ]; + protected $validationAttributes = [ + 'team.name' => 'name', + 'team.description' => 'description', + ]; + public function mount() + { + $this->team = session('currentTeam'); + } + public function submit() + { + $this->validate(); + try { + $this->team->save(); + session(['currentTeam' => $this->team]); + $this->emit('reloadWindow'); + } catch (\Throwable $th) { + return general_error_handler($th, $this); + } + } +} diff --git a/app/Models/Team.php b/app/Models/Team.php index 02660e90f..b1c93c4ac 100644 --- a/app/Models/Team.php +++ b/app/Models/Team.php @@ -20,6 +20,7 @@ class Team extends Model implements SendsDiscord, SendsEmail protected $fillable = [ 'id', 'name', + 'description', 'personal_team', 'extra_attributes', ]; diff --git a/database/migrations/2023_03_20_112811_create_teams_table.php b/database/migrations/2023_03_20_112811_create_teams_table.php index 6c59b184a..83347563a 100644 --- a/database/migrations/2023_03_20_112811_create_teams_table.php +++ b/database/migrations/2023_03_20_112811_create_teams_table.php @@ -14,6 +14,7 @@ return new class extends Migration Schema::create('teams', function (Blueprint $table) { $table->id(); $table->string('name'); + $table->string('description')->nullable(); $table->boolean('personal_team')->default(false); $table->schemalessAttributes('extra_attributes'); $table->timestamps(); diff --git a/database/seeders/TeamSeeder.php b/database/seeders/TeamSeeder.php index c2bab6ac5..d1b41a42e 100644 --- a/database/seeders/TeamSeeder.php +++ b/database/seeders/TeamSeeder.php @@ -5,7 +5,6 @@ namespace Database\Seeders; use App\Models\Team; use App\Models\User; use Illuminate\Database\Seeder; -use Illuminate\Support\Facades\DB; class TeamSeeder extends Seeder { @@ -13,6 +12,8 @@ class TeamSeeder extends Seeder { $normal_user_in_root_team = User::find(1); $root_user_personal_team = Team::find(0); + $root_user_personal_team->description = 'The root team'; + $root_user_personal_team->save(); $normal_user_in_root_team->teams()->attach($root_user_personal_team); diff --git a/resources/js/components/MagicBar.vue b/resources/js/components/MagicBar.vue index c8274ccbf..d93e4cf0d 100644 --- a/resources/js/components/MagicBar.vue +++ b/resources/js/components/MagicBar.vue @@ -293,75 +293,82 @@ const magicActions = [{ new: true, sequence: ['main', 'server', 'redirect'] }, + { id: 8, + name: 'Create: Team', + icon: '/', + sequence: ['main', 'redirect'] +}, +{ + id: 9, name: 'Goto: Dashboard', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 9, + id: 10, name: 'Goto: Servers', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 10, + id: 11, name: 'Goto: Private Keys', tags: 'destination,docker,network,new,create', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 11, + id: 12, name: 'Goto: Projects', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 12, + id: 13, name: 'Goto: Sources', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 13, + id: 14, name: 'Goto: Destinations', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 14, + id: 15, name: 'Goto: Settings', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 15, + id: 16, name: 'Goto: Command Center', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 16, + id: 17, name: 'Goto: Notifications', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 17, + id: 18, name: 'Goto: Profile', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 18, + id: 19, name: 'Goto: Teams', icon: 'goto', sequence: ['main', 'redirect'] }, { - id: 19, + id: 20, name: 'Goto: Switch Teams', icon: 'goto', sequence: ['main', 'redirect'] @@ -546,40 +553,43 @@ async function redirect() { targetUrl.searchParams.append('server', server) break; case 8: - targetUrl.pathname = `/` + targetUrl.pathname = `/team/new` break; case 9: - targetUrl.pathname = `/servers` + targetUrl.pathname = `/` break; case 10: - targetUrl.pathname = `/private-keys` + targetUrl.pathname = `/servers` break; case 11: - targetUrl.pathname = `/projects` + targetUrl.pathname = `/private-keys` break; case 12: - targetUrl.pathname = `/sources` + targetUrl.pathname = `/projects` break; case 13: - targetUrl.pathname = `/destinations` + targetUrl.pathname = `/sources` break; case 14: - targetUrl.pathname = `/settings` + targetUrl.pathname = `/destinations` break; case 15: - targetUrl.pathname = `/command-center` + targetUrl.pathname = `/settings` break; case 16: - targetUrl.pathname = `/profile/team/notifications` + targetUrl.pathname = `/command-center` break; case 17: - targetUrl.pathname = `/profile` + targetUrl.pathname = `/team/notifications` break; case 18: - targetUrl.pathname = `/profile/team` + targetUrl.pathname = `/profile` break; case 19: - targetUrl.pathname = `/profile/team` + targetUrl.pathname = `/team` + break; + case 20: + targetUrl.pathname = `/team` break; } window.location.href = targetUrl; diff --git a/resources/views/components/navbar.blade.php b/resources/views/components/navbar.blade.php index 865ca5bda..257589db7 100644 --- a/resources/views/components/navbar.blade.php +++ b/resources/views/components/navbar.blade.php @@ -100,7 +100,8 @@
  • - + @@ -117,7 +118,7 @@
  • @csrf - + diff --git a/resources/views/livewire/team/create.blade.php b/resources/views/livewire/team/create.blade.php new file mode 100644 index 000000000..f50e360f7 --- /dev/null +++ b/resources/views/livewire/team/create.blade.php @@ -0,0 +1,7 @@ +
    + + + + Save Team + + diff --git a/resources/views/livewire/team/form.blade.php b/resources/views/livewire/team/form.blade.php new file mode 100644 index 000000000..c8f7b849a --- /dev/null +++ b/resources/views/livewire/team/form.blade.php @@ -0,0 +1,12 @@ +
    +
    +

    General

    + + Save + +
    +
    + + +
    +
    diff --git a/resources/views/team/create.blade.php b/resources/views/team/create.blade.php new file mode 100644 index 000000000..6dae7ec02 --- /dev/null +++ b/resources/views/team/create.blade.php @@ -0,0 +1,5 @@ + +

    New Team

    +
    Add a new team
    + +
    diff --git a/resources/views/team/show.blade.php b/resources/views/team/show.blade.php index bffe026ae..2657ec5b3 100644 --- a/resources/views/team/show.blade.php +++ b/resources/views/team/show.blade.php @@ -1,7 +1,8 @@ -

    Members

    -
    + +

    Members

    +
    diff --git a/routes/web.php b/routes/web.php index 1375fe480..be1075fc5 100644 --- a/routes/web.php +++ b/routes/web.php @@ -90,8 +90,9 @@ Route::middleware(['auth'])->group(function () { Route::get('/settings', [Controller::class, 'settings'])->name('settings.configuration'); Route::get('/settings/emails', [Controller::class, 'emails'])->name('settings.emails'); Route::get('/profile', fn () => view('profile', ['request' => request()]))->name('profile'); - Route::get('/profile/team', [Controller::class, 'team'])->name('team.show'); - Route::get('/profile/team/notifications', fn () => view('team.notifications'))->name('team.notifications'); + Route::get('/team', [Controller::class, 'team'])->name('team.show'); + Route::get('/team/new', fn () => view('team.create'))->name('team.create'); + Route::get('/team/notifications', fn () => view('team.notifications'))->name('team.notifications'); Route::get('/command-center', fn () => view('command-center', ['servers' => Server::validated()->get()]))->name('command-center'); Route::get('/invitations/{uuid}', [Controller::class, 'acceptInvitation'])->name('team.invitation.accept'); Route::get('/invitations/{uuid}/revoke', [Controller::class, 'revokeInvitation'])->name('team.invitation.revoke');