def clean(self): cleaned_data = super(SignUpForm, self).clean() # Generate username cleaned_data['username'] = self.check_username() cleaned_data['company'] = None if cleaned_data.has_key('join') and cleaned_data['join']: # The form was submitted from the Join Space form, # so skip the company lookup return cleaned_data # Check if an Authorization Code was provided if cleaned_data.has_key('auth_code') and cleaned_data['auth_code']: # Check the validity of the code if not OToken().is_valid(cleaned_data['auth_code']): message = Message().get('invalid_token') raise ValidationError(message) else: # The user is trying to join an existing company # Find the company associated with this email address if cleaned_data.has_key('email'): company = lookup_email(cleaned_data['email']) cleaned_data['company'] = company return cleaned_data
def amenities_request(request, edit=False): if request.method == 'GET': return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Method Not Allowed.' }), mimetype="application/json") data = { 'name': request.POST['name'] if request.POST.has_key('name') else 'N/A', 'description': request.POST['description'] if request.POST.has_key('description') else 'N/A', 'address': request.POST['address'] if request.POST.has_key('address') else 'N/A', 'type': request.POST['type'] if request.POST.has_key('type') else 'N/A', 'link': '{}/supplier/{}'.format(settings.HOST, request.POST['url']) if request.POST.has_key('url') else 'N/A', } # add member details data['member'] = request.user.get_profile().name data['space'] = request.user.get_profile().space.name if edit: subject = 'A member has requested Supplier/Amenity amends' else: subject = 'A member has requested a new Supplier/Amenity' text_content = Message().get('email_supplier_details_text', data) if not settings.DEBUG: html_content = Message().get('email_supplier_details_html', data) else: html_content = None mail_admins(subject, text_content, html_message=html_content) response = HttpResponse(json.dumps({ 'status': '200', 'data': data }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def save(self, commit=True): # Generate random username based on first and last names user = User.objects.create_user(self.cleaned_data["username"], self.cleaned_data["email"], self.cleaned_data["password"]) if commit: user.first_name = self.cleaned_data["first_name"] user.last_name = self.cleaned_data["last_name"] if self.cleaned_data['company']: # The User is a Staff Member joining an existing company user.save() user.groups.add(Group.objects.get(name='Staff')) # Assign it to the Company profile = user.get_profile() profile.company = self.cleaned_data['company'] profile.save() elif self.cleaned_data['auth_code']: # The User is the Owner of a Company # User will be able to create a Business Profile when he confirms his email address user.save() user.groups.add(Group.objects.get(name='Owner')) profile = user.get_profile() if self.cleaned_data.has_key( 'join') and self.cleaned_data['join']: # The form was submitted from the Join Space form # the space will be set by the view pass else: # Assign the token space to the User t = OToken.objects.get(key=self.cleaned_data['auth_code']) t.user = user t.save( ) # we assign the user to the token as well to keep a record of who redeemed it profile.space = t.space profile.status = UserProfile.VERIFIED # activate user profile.save() else: # The user is an unaffiliated member # Unaffiliated members are created as inactive, and sent an activation email user.is_active = False user.save() user.groups.add(Group.objects.get(name='Member')) # Create temporary activation profile activation_key = generate_activation_key(user) activation_link = '{}/member/activate/{}/'.format( settings.HOST, activation_key) registration_profile = RegistrationProfile.objects.create( user=user, activation_key=activation_key) # Send email subject = 'Activate Your Account' data = { 'link': activation_link, 'expiration_days': settings.ACCOUNT_ACTIVATION_DAYS } message = Message().get('email_activation_text', data) user.email_user(subject, message, settings.EMAIL_FROM) return user
def action(request, action): """ Handle public actions. Available through AJAX. POST only allowed. """ if request.method == 'GET': return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Method Not Allowed.' }), mimetype="application/json") # Check email address is valid try: email = request.POST['email'] validate_email(email) except Exception: return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Enter a valid email address.' }), mimetype="application/json") subject = 'Someone registered an interest to join Nirit' text_content = Message().get('email_register_interest_text', {'email': email}) mail_admins(subject, text_content) response = HttpResponse(json.dumps({ 'status': '200', 'action': action }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def invite_company(request, codename): """ Invite Company to join Space. Available through AJAX. POST only allowed. """ if request.method == 'GET': return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Method Not Allowed.' }), mimetype="application/json") # Check the user is active if not request.user.get_profile().status == UserProfile.VERIFIED: raise PermissionDenied # Check email address is valid try: email = request.POST['email'] validate_email(email) except Exception: return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Enter a valid email address.' }), mimetype="application/json") # Create a token for the space, # and assign it the email address token = OToken() token.space = request.user.get_profile().space token.email = email token.save() onwer_profile = request.user.get_profile() subject = 'You are invited to join Nirit' c = { 'name': onwer_profile.name, 'company': onwer_profile.company.name, 'link': '{}/member/sign-up/join?token={}'.format(settings.HOST, token.key), } text_content = Message().get('email_invite_company_text', c) if not settings.DEBUG: html_content = Message().get('email_invite_company_html', c) else: html_content = None from_email = settings.EMAIL_FROM msg = EmailMultiAlternatives(subject, text_content, from_email, [email]) if html_content: msg.attach_alternative(html_content, "text/html") msg.send() response = HttpResponse(json.dumps({ 'status': '200', 'token': token.key }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def invite_staff(request, codename): """ Invite staff to join Company. Available through AJAX. POST only allowed. """ if request.method == 'GET': return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Method Not Allowed.' }), mimetype="application/json") # Check the user is active if not request.user.get_profile().status == UserProfile.VERIFIED: raise PermissionDenied try: company = Organization.objects.get(codename=codename) if request.POST.has_key('list') and request.POST['list']: # emails can be separated by whitespaces, commas or semi-colons cleaned_list = re.sub(r'[,;\s]', ' ', request.POST['list']).split() recipients_list = [] for recipient in cleaned_list: try: validate_email(recipient) except: # skip invalid email addresses continue match = utils.lookup_email(recipient) if not match or match != company: # skip non-company emails, # or emails from a different company continue recipients_list.append(recipient) if recipients_list: subject = 'You are invited to join Nirit' c = { 'name': request.user.get_profile().name, 'company': company.name, 'link': '{}/member/sign-up'.format(settings.HOST), } text_content = Message().get('email_invite_members_text', c) if not settings.DEBUG: html_content = Message().get('email_invite_members_html', c) else: html_content = None from_email = settings.EMAIL_FROM msg = EmailMultiAlternatives(subject, text_content, from_email, recipients_list) if html_content: msg.attach_alternative(html_content, "text/html") msg.send() except Organization.DoesNotExist: return HttpResponseBadRequest(json.dumps({ 'status': '404', 'reason': 'Unknown Company.' }), mimetype="application/json") response = HttpResponse(json.dumps({ 'status': '200', }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def contact(request, codename): if request.method == 'GET': return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Method Not Allowed.' }), mimetype="application/json") # Check the user is active if not request.user.get_profile().status == UserProfile.VERIFIED: raise PermissionDenied try: company = Organization.objects.get(codename=codename) if request.POST.has_key('subject') and request.POST['subject']: subject = 'A member has contacted you' text_content = Message().get( 'email_company_contact_text', { 'name': request.user.get_profile().name, 'company': company.name, 'link': '{}/member/{}'.format(settings.HOST, request.user.get_profile().codename), 'subject': request.POST['subject'] }) if not settings.DEBUG: html_content = Message().get( 'email_company_contact_html', { 'name': request.user.get_profile().name, 'company': company.name, 'link': '{}/member/{}'.format( settings.HOST, request.user.get_profile().codename), 'subject': linebreaks(request.POST['subject']) }) else: html_content = None company.mail_editors(subject, text_content, html_content) except Organization.DoesNotExist: return HttpResponseBadRequest(json.dumps({ 'status': '404', 'reason': 'Unknown Company.' }), mimetype="application/json") response = HttpResponse(json.dumps({ 'status': '200', 'data': { 'subject': request.POST['subject'] if request.POST.has_key('subject') else '', 'company': codename } }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def set_status(request, codename, action): # Check the user is active if not request.user.get_profile().status == UserProfile.VERIFIED: raise PermissionDenied # Check the user is an Editor if not request.user.get_profile().company.is_editor(request.user): raise PermissionDenied # Check action if action not in ('activate', 'ban', 'assign', 'revoke'): return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Unknown Action.' }), mimetype="application/json") try: profile = UserProfile.objects.get(codename=codename) if action == 'activate': profile.status = UserProfile.VERIFIED profile.save() # email user subject = 'Your membership has been approved' text_content = Message().get( 'email_sign_up_activated_text', { 'first_name': profile.name, 'link': '{}/member/{}'.format(settings.HOST, profile.codename) }) if not settings.DEBUG: html_content = Message().get( 'email_sign_up_activated_html', { 'first_name': profile.name, 'link': '{}/member/{}'.format(settings.HOST, profile.codename) }) else: html_content = None profile.mail(subject, text_content, html_content) elif action == 'ban': profile.status = UserProfile.BANNED profile.save() elif action == 'assign': profile.user.groups.remove(Group.objects.get(name='Staff')) profile.user.groups.add(Group.objects.get(name='Rep')) elif action == 'revoke': profile.user.groups.remove(Group.objects.get(name='Rep')) profile.user.groups.add(Group.objects.get(name='Staff')) except UserProfile.DoesNotExist: return HttpResponseBadRequest(json.dumps({ 'status': '404', 'reason': 'Unknown User.' }), mimetype="application/json") response = HttpResponse(json.dumps({ 'status': '200', 'data': { 'codename': codename, 'action': action } }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def contact(request, codename): if request.method == 'GET': return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Method Not Allowed.' }), mimetype="application/json") # Check the user is active if not request.user.get_profile().status == UserProfile.VERIFIED: raise PermissionDenied try: profile = UserProfile.objects.get(codename=codename) if request.POST.has_key('subject') and request.POST['subject']: subject = 'A member has contacted you' text_content = Message().get( 'email_member_contact_text', { 'name': request.user.get_profile().name, 'company': request.user.get_profile().company.name, 'link': '{}/member/{}'.format(settings.HOST, request.user.get_profile().codename), 'subject': request.POST['subject'] }) if not settings.DEBUG: html_content = Message().get( 'email_member_contact_html', { 'name': request.user.get_profile().name, 'company': request.user.get_profile().company.name, 'link': '{}/member/{}'.format( settings.HOST, request.user.get_profile().codename), 'subject': linebreaks(request.POST['subject']) }) else: html_content = None from_email = settings.EMAIL_FROM recipients_list = [profile.user.email] if recipients_list: msg = EmailMultiAlternatives(subject, text_content, from_email, recipients_list) if html_content: msg.attach_alternative(html_content, "text/html") msg.send() except UserProfile.DoesNotExist: return HttpResponseBadRequest(json.dumps({ 'status': '404', 'reason': 'Unknown Member.' }), mimetype="application/json") response = HttpResponse(json.dumps({ 'status': '200', 'data': { 'subject': request.POST['subject'] if request.POST.has_key('subject') else '', 'member': codename } }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def set_unaffiliated_status(request, id, action): profile = request.user.get_profile() # Check the user is active if not profile.status == UserProfile.VERIFIED: raise PermissionDenied # Check the user is a Space Manager if not request.user in profile.space.managers: raise PermissionDenied # Check action if action not in ('activate', 'ban'): return HttpResponseBadRequest(json.dumps({ 'status': '400', 'reason': 'Unknown Action.' }), mimetype="application/json") try: member = UserProfile.objects.get(pk=id) try: membership = Membership.objects.get(space=profile.space, member=member) except Membership.DoesNotExist: raise UserProfile.DoesNotExist else: if action == 'activate': membership.status = Membership.APPROVED membership.save() # email user subject = 'Your membership request has been approved' text_content = Message().get( 'email_approval_receipt_text', { 'first_name': member.name, 'space': profile.space.name, 'link': '{}/member/{}'.format(settings.HOST, member.codename) }) if not settings.DEBUG: html_content = Message().get( 'email_approval_receipt_html', { 'first_name': member.name, 'space': profile.space.name, 'link': '{}/member/{}'.format(settings.HOST, member.codename) }) else: html_content = None member.mail(subject, text_content, html_content) elif action == 'ban': membership.status = Membership.REJECTED membership.save() except UserProfile.DoesNotExist: return HttpResponseBadRequest(json.dumps({ 'status': '404', 'reason': 'Unknown User.' }), mimetype="application/json") response = HttpResponse(json.dumps({ 'status': '200', 'data': { 'id': id, 'action': action } }), mimetype="application/json") response['Content-Type'] = 'application/json; charset=utf-8' return response
def join(request): """ Handles Company (Owners) registration in one single form. The form requires to be sent from a manager in an existing Space. Failing that, the token will not exist. """ form = None company_form = None context = {} if request.GET.has_key('token'): token = request.GET['token'] try: t = OToken.objects.get(key=token) except OToken.DoesNotExist: context['status'] = 'FAILED' else: if t.redeemed: context['status'] = 'REDEEMED' else: # Make sure this token is assigned to an email address if not t.email: context['status'] = 'FAILED' else: # This form allows membership and company creation, # in the same form context['status'] = 'ACTIVATED' context['space'] = t.space context['explanation'] = Message().get('welcome/join') # SignUp and Company Form if request.method == 'POST': form = SignUpForm(request.POST) company_form = CompanyForm(request.POST) if form.is_valid() and company_form.is_valid(): # Create user user = form.save() # Create organization data = company_form.save() company = data['organization'] building = data['building'] if data.has_key( 'building') else None floor = data['floor'] if data.has_key( 'floor') else None # Create a Company Profile on this space CompanyProfile.objects.create(organization=company, space=t.space, building=building, floor=floor) # Assign user to the company and space profile = user.get_profile() profile.company = company profile.space = t.space profile.save() # Flag token as redeemed t.redeemed = True t.save() # Post INTRO notice to board # verification is token-based token = profile.token headers = { 'referer': settings.API_HOST, 'content-type': 'application/json', 'authorization': 'Token {}'.format(token) } data = { 'subject': u'{} has just joined Nirit'.format( company.name), 'body': force_unicode(company.description), 'spaces': [t.space.codename], 'type': '{}'.format(Notice.INTRO), 'official': 'on' } url = "{}/notices/post".format(settings.API_HOST) r = requests.post(url, verify=False, headers=headers, data=json.dumps(data)) # Notify Managers and Admins subject = 'A new Company has just joined Nirit' data = { 'name': company.name, 'link': '{}/member/account'.format(settings.HOST) } text_content = Message().get( 'email_new_company_text', data) if not settings.DEBUG: html_content = Message().get( 'email_new_company_html', data) else: html_content = None mail_admins(subject, text_content, html_message=html_content) t.space.mail_managers(subject, text_content, html_content) # Finally, redirect to company page destination = '/company/{}/{}'.format( company.slug, company.codename) return HttpResponseRedirect(destination) else: form = SignUpForm(initial={ 'email': t.email, 'join': True }) company_form = CompanyForm() else: context['status'] = 'FAILED' if form: context['form'] = form if company_form: context['company_form'] = company_form t = loader.get_template('registration/sign_up_join.html') c = RequestContext(request, context) return HttpResponse(t.render(c))
def sign_up(request): explanation = '' if request.method == 'POST': form = SignUpForm(request.POST) if form.is_valid(): user = form.save() # Handle user role if user.get_profile().company: # Staff User created # Notify company Owner/Rep of new Staff sign-up company = user.get_profile().company subject = 'A new member has just joined {}'.format( company.name) data = { 'name': user.get_full_name(), 'company': company.name, 'link': '{}/company/{}/{}/staff'.format(settings.HOST, company.slug, company.codename) } text_content = Message().get('email_sign_up_success_text', data) if not settings.DEBUG: html_content = Message().get('email_sign_up_success_html', data) else: html_content = None company.mail_editors(subject, text_content, html_content) return HttpResponseRedirect('/member/sign-up/complete') elif user.is_active: # Owner User created # Send activation email subject = 'Activate your Nirit account' from_email = settings.EMAIL_FROM to = form.cleaned_data['email'] data = { 'first_name': form.cleaned_data['first_name'], 'link': '{}/member/sign-up/activate?token={}'.format( settings.HOST, form.cleaned_data['auth_code']) } text_content = Message().get('email_activation_required_text', data) if not settings.DEBUG: html_content = Message().get( 'email_activation_required_html', data) else: html_content = None msg = EmailMultiAlternatives(subject, text_content, from_email, [to]) if html_content: msg.attach_alternative(html_content, "text/html") msg.send() return HttpResponseRedirect( '/member/sign-up/activation-required') else: # Unaffiliated User created. return HttpResponseRedirect( '/member/sign-up/registration-complete') else: form = SignUpForm() explanation = Message().get('welcome') t = loader.get_template('registration/sign_up.html') c = RequestContext(request, {'form': form, 'explanation': explanation}) return HttpResponse(t.render(c))
def activate(request): """ Owner activation page. Provides the form to create a Company Profile when activated successfully. """ form = None context = {} if request.GET.has_key('token'): token = request.GET['token'] try: t = OToken.objects.get(key=token) except OToken.DoesNotExist: context['status'] = 'FAILED' else: if t.redeemed: context['status'] = 'REDEEMED' else: # Make sure this token is assigned to a user user = t.user if not user: raise PermissionDenied # Log the user in user.backend = 'django.contrib.auth.backends.ModelBackend' auth_login(request, user) context['status'] = 'ACTIVATED' context['space'] = t.space # This is the one-time chance for the user to create a company # The Company creation form is a slimmed-down version of the Company Edit form # (only required information is displayed, so that the same form class can be used) if request.method == 'POST': form = CompanyForm(request.POST) if form.is_valid(): data = form.save() company = data['organization'] building = data['building'] if data.has_key( 'building') else None floor = data['floor'] if data.has_key( 'floor') else None # Create a Company Profile on this space CompanyProfile.objects.create(organization=company, space=t.space, building=building, floor=floor) # Assign user to the company profile = user.get_profile() profile.company = company profile.save() # Flag token as redeemed t.redeemed = True t.save() # Post INTRO notice to board # verification is token-based token = profile.token headers = { 'referer': settings.API_HOST, 'content-type': 'application/json', 'authorization': 'Token {}'.format(token) } data = { 'subject': u'{} has just joined Nirit'.format(company.name), 'body': force_unicode(company.description), 'spaces': [t.space.codename], 'type': '{}'.format(Notice.INTRO), 'official': 'on' } url = "{}/notices/post".format(settings.API_HOST) r = requests.post(url, verify=False, headers=headers, data=json.dumps(data)) # Notify Managers and Admins subject = 'A new Company has just joined Nirit' data = { 'name': company.name, 'link': '{}/member/account'.format(settings.HOST) } text_content = Message().get('email_new_company_text', data) if not settings.DEBUG: html_content = Message().get( 'email_new_company_html', data) else: html_content = None mail_admins(subject, text_content, html_message=html_content) t.space.mail_managers(subject, text_content, html_content) # Finally, redirect to company page destination = '/company/{}/{}'.format( company.slug, company.codename) return HttpResponseRedirect(destination) else: form = CompanyForm() else: context['status'] = 'FAILED' if form: context['form'] = form t = loader.get_template('registration/sign_up_activate.html') c = RequestContext(request, context) return HttpResponse(t.render(c))