From b3f1408739a00d9e683fbb97ceb5cefc4f292dbc Mon Sep 17 00:00:00 2001 From: Zamil Majdy <z.majdy1996@gmail.com> Date: Sun, 9 Apr 2017 16:56:26 +0700 Subject: [PATCH] Implement JS fetch for upload from library --- assets/js/Dashboard.jsx | 2 +- assets/js/VacancyPage.jsx | 40 +++++++++++++------------- assets/js/components/RegisterModal.jsx | 25 ++++------------ assets/js/index.jsx | 8 ++++-- assets/js/lib/Server.jsx | 31 ++++++++++++++------ assets/js/lib/Storage.jsx | 17 +++++++++-- core/serializers/accounts.py | 10 +++---- core/views/accounts.py | 14 ++++----- 8 files changed, 80 insertions(+), 67 deletions(-) diff --git a/assets/js/Dashboard.jsx b/assets/js/Dashboard.jsx index 513a5b8c..634fdefa 100755 --- a/assets/js/Dashboard.jsx +++ b/assets/js/Dashboard.jsx @@ -11,7 +11,7 @@ export default class Dashboard extends React.Component { render = () => ( <div> - <TopMenu /> + <TopMenu /> {this.props.children} </div> ) diff --git a/assets/js/VacancyPage.jsx b/assets/js/VacancyPage.jsx index 27abae5b..cb25fd82 100644 --- a/assets/js/VacancyPage.jsx +++ b/assets/js/VacancyPage.jsx @@ -14,30 +14,30 @@ export default class VacancyPage extends React.Component { password: '', errorFlag: false, vacancies: [], + student: false, }; + Storage.getUserData().then(r => this.setState({ student: r.student })); + this.handleItemClick = this.handleItemClick.bind(this); } handleItemClick = (e, { name }) => this.setState({ activeItem: name }); - render() { - const student = Storage.get('user-data').student; - return ( - <div className="halamanLowongan"> - <Tabs selected={0}> - <Pane label="Semua Lowongan" > - <VacancyList key={1} studentId={student.id} url="/vacancies/" /> - </Pane> - <Pane label="Lamaran saya" > - <VacancyList key={2} status="Batal" studentId={student.id} url={`/students/${student.id}/applied-vacancies/`} /> - </Pane> - <Pane label="Lamaran Ditandai" > - <VacancyList key={3} studentId={student.id} url={`/students/${student.id}/bookmarked-vacancies/`} /> - </Pane> - </Tabs> - - </div> - - ); - } + render = () => ( + this.state.student && ( + <div className="halamanLowongan"> + <Tabs selected={0}> + <Pane label="Semua Lowongan" > + <VacancyList key={1} studentId={this.state.student.id} url="/vacancies/" /> + </Pane> + <Pane label="Lamaran saya" > + <VacancyList key={2} status="Batal" studentId={this.state.student.id} url={`/students/${this.state.student.id}/applied-vacancies/`} /> + </Pane> + <Pane label="Lamaran Ditandai" > + <VacancyList key={3} studentId={this.state.student.id} url={`/students/${this.state.student.id}/bookmarked-vacancies/`} /> + </Pane> + </Tabs> + </div> + ) + ); } diff --git a/assets/js/components/RegisterModal.jsx b/assets/js/components/RegisterModal.jsx index 06d91044..43631df1 100644 --- a/assets/js/components/RegisterModal.jsx +++ b/assets/js/components/RegisterModal.jsx @@ -32,27 +32,12 @@ export default class RegisterModal extends React.Component { handleSubmit = (e) => { e.preventDefault(); - const form = new FormData(); - Object.keys(this.state).map(k => form.append(k, this.state[k])); - const data = { - 'X-CSRFToken': Server.getCookie('csrftoken'), - mode: 'no-cors', - method: 'POST', - body: form, - credentials: 'same-origin', - }; - - fetch('/api/register/', data) - .then((response) => { - if (response.status < 200 || response.status > 399) throw response.json(); - else return response.json(); - }) - .then((response) => { - alert('Akun berhasil dibuat :)'); - Storage.set('user-data', response); - browserHistory.push('/home'); - }, error => error.then(r => alert(JSON.stringify(r)))); + Server.submit('/register/', this.state).then((response) => { + alert('Akun berhasil dibuat :)'); + Storage.set('user-data', response); + browserHistory.push('/home'); + }, error => error.then(r => alert(JSON.stringify(r)))); }; render = () => ( diff --git a/assets/js/index.jsx b/assets/js/index.jsx index cc866085..18cb7f6a 100644 --- a/assets/js/index.jsx +++ b/assets/js/index.jsx @@ -28,9 +28,12 @@ export default class App extends React.Component { Server.isLoggedIn() || replace({ pathname: '/login' }) ); - handleHome= (nextState, replace) => { + handleHome= (nextState, replace, cb) => { if (Server.isLoggedIn()) { - Storage.get('user-data').student ? replace({pathname: '/lowongan'}) : replace({pathname: '/profile'}); + Storage.getUserData().then((data) => { + const next = data.student ? '/lowongan' : '/profile'; + replace({ pathname: next }); cb(); + }); } else { replace({ pathname: '/login' }); } @@ -40,7 +43,6 @@ export default class App extends React.Component { <Router history={browserHistory}> <Route path="/login" component={Login} /> <Route component={Dashboard} onEnter={this.handleAuth}> - <Route path="/" component={VacancyPage} /> <Route path="/profile" component={Profile} /> <Route path="/lowongan" component={VacancyPage} /> <Route path="/users" component={Profile} /> diff --git a/assets/js/lib/Server.jsx b/assets/js/lib/Server.jsx index b9c7e142..6f912c84 100644 --- a/assets/js/lib/Server.jsx +++ b/assets/js/lib/Server.jsx @@ -17,8 +17,23 @@ export default class Server { return null; } + static submit(path, data, method = 'POST', useCache = false) { + const form = new FormData(); + /* istanbul ignore next */ + Object.keys(data).map(k => form.append(k, this.state[k])); + + const requestData = { + 'X-CSRFToken': Server.getCookie('csrftoken'), + mode: 'no-cors', + method: 'POST', + body: form, + credentials: 'same-origin', + }; + + return this.handleFetchRequest(requestData, path, useCache); + } + static sendRequest(path, method, data, useCache = false) { - const url = `/api${path}`; const csrftoken = this.getCookie('csrftoken'); const headers = { 'content-type': 'application/json', @@ -32,7 +47,11 @@ export default class Server { credentials: 'same-origin', }; - // noinspection JSUnresolvedFunction + return this.handleFetchRequest(requestData, path, useCache); + } + + static handleFetchRequest(requestData, path, useCache) { + const url = `/api${path}`; const request = fetch(url, requestData); /* istanbul ignore next */ @@ -43,12 +62,8 @@ export default class Server { const contentType = response.headers.get('content-type'); const result = contentType && contentType.indexOf('application/json') !== -1 ? response.json() : response.text(); - if (response.status < 200 || response.status > 399) { - throw result; - } - else { - return result; - } + if (response.status < 200 || response.status > 399) throw result; + else return result; }); /* istanbul ignore next */ diff --git a/assets/js/lib/Storage.jsx b/assets/js/lib/Storage.jsx index 0e28781e..cb2a24ce 100644 --- a/assets/js/lib/Storage.jsx +++ b/assets/js/lib/Storage.jsx @@ -1,3 +1,5 @@ +import Server from './../lib/Server'; + /** Session Storage Polyfill */ /* eslint-disable */ @@ -120,14 +122,23 @@ polyfil(); export default class Storage { static get(key) { - return JSON.parse(sessionStorage.getItem(key)); + return JSON.parse(localStorage.getItem(key)); } static set(key, value) { - return sessionStorage.setItem(key, JSON.stringify(value)); + return localStorage.setItem(key, JSON.stringify(value)); } static clear() { - return sessionStorage.clear(); + return localStorage.clear(); + } + + static getUserData() { + const data = Storage.get('user-data'); + /* istanbul ignore next */ + return (data != null) ? Promise.resolve(data) : Server.get('/users/me/').then((response) => { + Storage.set(('user-data'), response); + return response; + }); } } diff --git a/core/serializers/accounts.py b/core/serializers/accounts.py index 986f4c4f..63f67d1a 100644 --- a/core/serializers/accounts.py +++ b/core/serializers/accounts.py @@ -4,14 +4,14 @@ from rest_framework import serializers from core.models.accounts import Supervisor, Company, Student -class UserSerializer(serializers.HyperlinkedModelSerializer): +class BasicUserSerializer(serializers.HyperlinkedModelSerializer): class Meta: model = User fields = ('url', 'username', 'email', 'is_staff') class StudentSerializer(serializers.ModelSerializer): - user = UserSerializer() + user = BasicUserSerializer() name = serializers.ReadOnlyField() class Meta: @@ -20,7 +20,7 @@ class StudentSerializer(serializers.ModelSerializer): class CompanySerializer(serializers.ModelSerializer): - user = UserSerializer() + user = BasicUserSerializer() name = serializers.ReadOnlyField() class Meta: @@ -29,7 +29,7 @@ class CompanySerializer(serializers.ModelSerializer): class SupervisorSerializer(serializers.ModelSerializer): - user = UserSerializer() + user = BasicUserSerializer() name = serializers.ReadOnlyField() class Meta: @@ -37,7 +37,7 @@ class SupervisorSerializer(serializers.ModelSerializer): fields = '__all__' -class LoginSerializer(serializers.HyperlinkedModelSerializer): +class UserSerializer(serializers.HyperlinkedModelSerializer): company = CompanySerializer() supervisor = SupervisorSerializer() student = StudentSerializer() diff --git a/core/views/accounts.py b/core/views/accounts.py index 4afa426a..3f75bb29 100644 --- a/core/views/accounts.py +++ b/core/views/accounts.py @@ -11,8 +11,8 @@ from rest_framework.status import HTTP_400_BAD_REQUEST, HTTP_409_CONFLICT from core.lib.permissions import IsAdminOrStudent, IsAdminOrSelfOrReadOnly, IsAdminOrCompany, IsAdminOrSupervisor from core.models.accounts import Student, Company, Supervisor -from core.serializers.accounts import UserSerializer, StudentSerializer, CompanySerializer, SupervisorSerializer, \ - LoginSerializer, RegisterSerializer +from core.serializers.accounts import BasicUserSerializer, StudentSerializer, CompanySerializer, SupervisorSerializer, \ + UserSerializer, RegisterSerializer class UserViewSet(viewsets.ModelViewSet): @@ -26,7 +26,7 @@ class UserViewSet(viewsets.ModelViewSet): Get current user's details """ user = self.request.user - serializer = UserSerializer(user, context={"request": request}) + serializer = BasicUserSerializer(user, context={"request": request}) return Response(serializer.data) def get_permissions(self): @@ -62,7 +62,7 @@ class SupervisorViewSet(viewsets.ModelViewSet): class LoginViewSet(viewsets.GenericViewSet): permission_classes = (AllowAny, ) - serializer_class = LoginSerializer + serializer_class = UserSerializer queryset = User.objects.all() def create(self, request): @@ -115,9 +115,9 @@ class LoginViewSet(viewsets.GenericViewSet): nip=resp.get("kodeidentitas") ) supervisor.save() - serializer = LoginSerializer(user, context={'request': request}) + serializer = UserSerializer(user, context={'request': request}) return Response(serializer.data, status=status.HTTP_201_CREATED) - serializer = LoginSerializer(user, context={'request': request}) + serializer = UserSerializer(user, context={'request': request}) return Response(serializer.data, status=status.HTTP_200_OK) else: return Response(status=status.HTTP_401_UNAUTHORIZED) @@ -125,7 +125,7 @@ class LoginViewSet(viewsets.GenericViewSet): user = authenticate(username = username, password = password) if user is not None: login(request, user) - serializer = LoginSerializer(user, context={'request': request}) + serializer = UserSerializer(user, context={'request': request}) return Response(serializer.data, status=status.HTTP_200_OK) else: return Response(status=status.HTTP_401_UNAUTHORIZED) -- GitLab