diff --git a/app/Http/Controllers/Api/Client/AccountController.php b/app/Http/Controllers/Api/Client/AccountController.php new file mode 100644 index 000000000..e683d3a0b --- /dev/null +++ b/app/Http/Controllers/Api/Client/AccountController.php @@ -0,0 +1,16 @@ +fractal->item($request->user()) + ->transformWith($this->getTransformer(AccountTransformer::class)) + ->toArray(); + } +} diff --git a/app/Http/Controllers/Auth/AbstractLoginController.php b/app/Http/Controllers/Auth/AbstractLoginController.php index 150841fab..58a48dfe2 100644 --- a/app/Http/Controllers/Auth/AbstractLoginController.php +++ b/app/Http/Controllers/Auth/AbstractLoginController.php @@ -2,7 +2,6 @@ namespace Pterodactyl\Http\Controllers\Auth; -use Cake\Chronos\Chronos; use Lcobucci\JWT\Builder; use Illuminate\Http\Request; use Pterodactyl\Models\User; @@ -16,6 +15,7 @@ use Illuminate\Contracts\Auth\Authenticatable; use Illuminate\Contracts\Encryption\Encrypter; use Illuminate\Foundation\Auth\AuthenticatesUsers; use Pterodactyl\Traits\Helpers\ProvidesJWTServices; +use Pterodactyl\Transformers\Api\Client\AccountTransformer; use Illuminate\Contracts\Cache\Repository as CacheRepository; use Pterodactyl\Contracts\Repository\UserRepositoryInterface; @@ -137,24 +137,18 @@ abstract class AbstractLoginController extends Controller $request->session()->regenerate(); $this->clearLoginAttempts($request); - $token = $this->builder->setIssuer(config('app.url')) - ->setAudience(config('app.url')) - ->setId(str_random(12), true) - ->setIssuedAt(Chronos::now()->getTimestamp()) - ->setNotBefore(Chronos::now()->getTimestamp()) - ->setExpiration(Chronos::now()->addSeconds(config('session.lifetime'))->getTimestamp()) - ->set('user', $user->only([ - 'id', 'uuid', 'username', 'email', 'name_first', 'name_last', 'language', 'root_admin', - ])) - ->sign($this->getJWTSigner(), $this->getJWTSigningKey()) - ->getToken(); - $this->auth->guard()->login($user, true); + debug($request->cookies->all()); + return response()->json([ 'complete' => true, 'intended' => $this->redirectPath(), - 'token' => $token->__toString(), + 'cookie' => [ + 'name' => config('session.cookie'), + 'value' => $this->encrypter->encrypt($request->cookie(config('session.cookie'))), + ], + 'user' => (new AccountTransformer())->transform($user), ]); } diff --git a/app/Transformers/Api/Client/AccountTransformer.php b/app/Transformers/Api/Client/AccountTransformer.php new file mode 100644 index 000000000..30bed0d24 --- /dev/null +++ b/app/Transformers/Api/Client/AccountTransformer.php @@ -0,0 +1,36 @@ + $model->root_admin, + 'username' => $model->username, + 'email' => $model->email, + 'first_name' => $model->name_first, + 'last_name' => $model->name_last, + 'language' => $model->language, + ]; + } +} diff --git a/resources/assets/scripts/store.js b/resources/assets/scripts/_store.js similarity index 100% rename from resources/assets/scripts/store.js rename to resources/assets/scripts/_store.js diff --git a/resources/assets/scripts/app.js b/resources/assets/scripts/app.js index 204ae6e1c..a8f012a68 100644 --- a/resources/assets/scripts/app.js +++ b/resources/assets/scripts/app.js @@ -8,16 +8,17 @@ import { Ziggy } from './helpers/ziggy'; import Locales from './../../../resources/lang/locales'; import { flash } from './mixins/flash'; import { routes } from './routes'; -import { storeData } from './store'; +import storeData from './store/index.js'; window.events = new Vue; window.Ziggy = Ziggy; +Vue.config.productionTip = false; Vue.use(Vuex); + const store = new Vuex.Store(storeData); const route = require('./../../../vendor/tightenco/ziggy/src/js/route').default; -Vue.config.productionTip = false; Vue.mixin({ methods: { route } }); Vue.mixin(flash); diff --git a/resources/assets/scripts/components/auth/LoginForm.vue b/resources/assets/scripts/components/auth/LoginForm.vue index 39708ec2e..af63c101c 100644 --- a/resources/assets/scripts/components/auth/LoginForm.vue +++ b/resources/assets/scripts/components/auth/LoginForm.vue @@ -77,32 +77,21 @@ this.$data.showSpinner = true; this.clearFlashes(); - axios.post(this.route('auth.login'), { - user: this.$props.user.email, - password: this.$props.user.password, - }) - .then(function (response) { - // If there is a 302 redirect or some other odd behavior (basically, response that isnt - // in JSON format) throw an error and don't try to continue with the login. - if (!(response.data instanceof Object)) { - throw new Error('An error was encountered while processing this request.'); + this.$store.dispatch('auth/login', { user: this.$props.user.email, password: this.$props.user.password }) + .then(response => { + if (response.complete) { + return window.location = response.intended; } - if (response.data.complete) { - localStorage.setItem('token', response.data.token); - self.$store.dispatch('login'); - return window.location = response.data.intended; - } - - self.$props.user.password = ''; - self.$data.showSpinner = false; - self.$router.push({name: 'checkpoint', query: {token: response.data.login_token}}); + this.$props.user.password = ''; + this.$data.showSpinner = false; + this.$router.push({name: 'checkpoint', query: {token: response.login_token}}); }) - .catch(function (err) { - self.$props.user.password = ''; - self.$data.showSpinner = false; - self.$refs.password.focus(); - self.$store.dispatch('logout'); + .catch(err => { + this.$props.user.password = ''; + this.$data.showSpinner = false; + this.$refs.password.focus(); + this.$store.dispatch('auth/logout'); if (!err.response) { return console.error(err); diff --git a/resources/assets/scripts/components/dashboard/Dashboard.vue b/resources/assets/scripts/components/dashboard/Dashboard.vue index 59b1bdb0f..a34060438 100644 --- a/resources/assets/scripts/components/dashboard/Dashboard.vue +++ b/resources/assets/scripts/components/dashboard/Dashboard.vue @@ -29,7 +29,7 @@