Commit 878ca8a152800bbb889f6aa5a106a87f8867cf95

Authored by Deepak
1 parent a8c5a7fb6d
Exists in master

added signup form on index route for main site

imports/client/app/routes.js
... ... @@ -37,6 +37,7 @@ import { teachersViewController } from '/imports/client/views/org/admi
37 37 */
38 38 import Signup from '/imports/client/views/nonOrg/enter/SignupView';
39 39 import { NonOrgApp } from '/imports/client/layouts/NonOrgApp';
  40 +import {NonOrgAppModule} from '/imports/client/views/nonOrg/app/module/Index';
40 41  
41 42 /**
42 43 * Invalid Org Components
... ... @@ -73,7 +74,7 @@ const getInvalidOrgRoute = () => (
73 74 const getNonOrgRoutes = () => (
74 75 <Router history={ browserHistory }>
75 76 <Route path="/" component={ NonOrgApp }>
76   - <IndexRoute name="index" component={ Index } />
  77 + <IndexRoute name="index" component={ NonOrgAppModule } />
77 78 <Route name="signup" path="/signup" component={ Signup } />
78 79 <Route path="*" component={ NotFound } />
79 80 </Route>
... ...
imports/client/layouts/NonOrgApp.js
1 1 import React, { Component } from 'react';
2 2 import { Grid } from 'react-bootstrap';
3   -import {AppNavigationController} from '/imports/client/views/nonOrg/app/module/navigation/index';
4 3 /**
5 4 * user based redirection will take place here
6 5 */
7   - export class App extends Component {
  6 + export class NonOrgApp extends Component {
8 7 constructor(props) {
9 8 super(props);
10 9 this.state = {
... ... @@ -14,7 +13,6 @@ import {AppNavigationController} from &#39;/imports/client/views/nonOrg/app/modul
14 13 render(){
15 14 return (
16 15 <div>
17   - <AppNavigationController />
18 16 <Grid>
19 17 { this.props.children }
20 18 </Grid>
... ...
imports/client/views/nonOrg/app/module/AppLayout.js
... ... @@ -0,0 +1,53 @@
  1 +import _ from 'lodash';
  2 +import { Meteor } from 'meteor/meteor';
  3 +import React, { Component } from 'react';
  4 +import { Link } from 'react-router';
  5 +import { Avatar } from '/imports/client/components/Avatar';
  6 +import { Icon } from '/imports/client/components/Icon';
  7 +import classNames from 'classnames';
  8 +
  9 +import { logout } from '/imports/client/app/utils/loginMethods';
  10 +
  11 +import Signup from '/imports/client/views/nonOrg/enter/SignupView';
  12 +import { VerifyModule } from '/imports/client/views/verify/module/index';
  13 +import ReactSVG from 'react-svg'
  14 +
  15 +export class AppLayout extends Component {
  16 + render() {
  17 + const {user, org} = this.props.data;
  18 + console.log(user);
  19 + if(!user) {
  20 + return (
  21 + <Signup
  22 + />
  23 + );
  24 + }
  25 +
  26 + if(!user.isEmailVerified()) {
  27 + return (
  28 + <VerifyModule
  29 + pane = {this.props.location.query.verify}
  30 + location = {this.props.location}
  31 + />
  32 + );
  33 + }
  34 +
  35 +
  36 + return (
  37 + <div className = "appLayout-box">
  38 + <div className = "appLayout-wrapOuter">
  39 + <div className = "appLayout-wrapInner">
  40 + <div className = "appLayout-menuWrap">
  41 + </div>
  42 + <div className = "appLayout-contentWrap">
  43 + <div className = "appLayout-content">
  44 +
  45 + </div>
  46 + </div>
  47 + </div>
  48 + </div>
  49 + </div>
  50 + );
  51 + };
  52 +
  53 +};
... ...
imports/client/views/nonOrg/app/module/Index.js
1   -import React from 'react';
2   -import { Jumbotron } from 'react-bootstrap';
3   -
4   -const Index = () => (
5   - <div className="Index">
6   - <Jumbotron className="text-center">
7   - <h2>Base</h2>
8   - <p>A starting point for Meteor applications.</p>
9   - <p><a className="btn btn-success" href="https://themeteorchef.com/base" role="button">Read the Documentation</a></p>
10   - <p style={ { fontSize: '16px', color: '#aaa' } }>Currently at v4.11.1</p>
11   - </Jumbotron>
12   - </div>
13   -);
14   -
15   -export default Index;
  1 +// import { AppModule } from '/imports/client/views/app/module/index'
  2 +import {
  3 + composeWithTracker,
  4 + compose,
  5 + composeAll
  6 + } from 'react-komposer';
  7 +import { AppLayout } from './AppLayout';
  8 +import { Loading } from '/imports/client/components/Loading';
  9 +
  10 +import { Users } from '/imports/collections/users/index';
  11 +import { Orgs } from '/imports/collections/orgs/index';
  12 +
  13 +
  14 +const meteorTick = (props, onData) => {
  15 +
  16 + const handles = [
  17 + Meteor.subscribe('users.current'),
  18 + Meteor.subscribe('orgs.current'),
  19 + ];
  20 +
  21 + if(_.every(handles, (handle) => (handle.ready()) )) {
  22 + const user = Users.current();
  23 + console.log(user);
  24 + onData(null, {
  25 + data: {
  26 + user: user,
  27 + org: Orgs.current(),
  28 + },
  29 + });
  30 + }
  31 +
  32 + return () => {
  33 + _.each(handles, (handle) => handle.stop() );
  34 + };
  35 +};
  36 +
  37 +
  38 +const reduxTick = (props, onData) => {
  39 + onData(null, {
  40 + location: props.location,
  41 + data: {}
  42 + });
  43 +};
  44 +
  45 +
  46 +export const NonOrgAppModule = composeAll(
  47 + composeWithTracker(meteorTick, Loading),
  48 + compose(reduxTick, Loading),
  49 +)(AppLayout);
... ...
imports/client/views/nonOrg/app/module/navigation/AppNavigation.js
... ... @@ -23,6 +23,7 @@ export class AppNavigation extends Component {
23 23 };
24 24 render() {
25 25 const {user} = this.props.data;
  26 + console.log(user);
26 27 if(user){
27 28 return(
28 29 <AuthenticatedNavigation
... ...
imports/client/views/nonOrg/app/module/navigation/AuthenticatedNavigation.js
... ... @@ -19,11 +19,6 @@ const AuthenticatedNavigation = () =&gt; (
19 19 <NavItem eventKey={ 2 } href="/documents">Documents</NavItem>
20 20 </LinkContainer>
21 21 </Nav>
22   - <Nav pullRight>
23   - <NavDropdown eventKey={ 3 } title={ userName() } id="basic-nav-dropdown">
24   - <MenuItem eventKey={ 3.1 } onClick={ handleLogout }>Logout</MenuItem>
25   - </NavDropdown>
26   - </Nav>
27 22 </div>
28 23 );
29 24  
... ...
imports/client/views/nonOrg/app/module/navigation/index.js
... ... @@ -22,6 +22,7 @@ const meteorTick = (props, onData) =&gt; {
22 22 if(_.every(handles, (handle) => (handle.ready()) )) {
23 23 const user = Users.current();
24 24 const org = Orgs.current();
  25 + console.log(user);
25 26 onData(null, {
26 27 data: {
27 28 user: user,
... ...
imports/client/views/verify/EmailPane.js
... ... @@ -0,0 +1,110 @@
  1 +import React from 'react';
  2 +import { Link } from 'react-router';
  3 +import { If, Case } from '/imports/client/components/Logic';
  4 +import { Bert } from 'meteor/themeteorchef:bert';
  5 +
  6 +import { Row, Col, Alert,ControlLabel,
  7 + FormGroup, FormControl, Button } from 'react-bootstrap';
  8 +
  9 +
  10 +export class EmailPane extends React.Component {
  11 +
  12 + constructor(props) {
  13 + super(props);
  14 +
  15 + this.state = {
  16 + email: props.user.emails[0].address,
  17 + form: false,
  18 + };
  19 + };
  20 +
  21 + onUpdate(key, val) {
  22 + this.setState({[key]: val});
  23 + };
  24 +
  25 + onSetEmail() {
  26 + startEmailVerification.call({email: this.state.email}, (err, res)=>{
  27 + Bert.alert('New verification email sent!', 'success');
  28 +
  29 + });
  30 + this.setState({form: false});
  31 + };
  32 +
  33 + onShowForm() {
  34 + this.setState({form: true});
  35 + };
  36 +
  37 + renderForm() {
  38 + const {user} = this.props;
  39 +
  40 + return (
  41 + <div className = "wizardPane-box">
  42 + <div className = "wizardPane-section">
  43 + <div className="icon-circle icon-lg">
  44 + <i className="icon icon-simple icon-envelope"></i>
  45 + </div>
  46 + <div className = "wizardPane-title">
  47 + Set your email address
  48 + </div>
  49 + <div className = "col-xs-8 horizontalform verifyEmail wizardPane-text">
  50 + <div className="form-row">
  51 + <Col sm={4}>
  52 + Enter email
  53 + </Col>
  54 + <Col sm={8}>
  55 + <input
  56 + type = "text"
  57 + value = {this.state.email}
  58 + onChange = {(evt) => this.onUpdate('email', evt.currentTarget.value)}
  59 + placeholder = "Email"
  60 + />
  61 + </Col>
  62 + </div>
  63 +
  64 + </div>
  65 + </div>
  66 + <div className = "wizardPane-section wizardPane-footer">
  67 + <div
  68 + className = "wizardPane-button btn btn-blue"
  69 + onClick = {() => this.onSetEmail()}
  70 + >
  71 + Send verification email
  72 + </div>
  73 + </div>
  74 + </div>
  75 + );
  76 + };
  77 +
  78 + renderMessage() {
  79 + const {user} = this.props;
  80 +
  81 + return (
  82 + <div className = "wizardPane-box">
  83 + <div className = "wizardPane-section">
  84 +
  85 + <div className = "wizardPane-title">
  86 + <i className="icon-envelope icon"></i>
  87 + <h3>Verify your email</h3>
  88 + </div>
  89 + <div className = "wizardPane-text">
  90 + Check your email โ€“ย we sent a verification link to<br/>
  91 + {user.emails[0].address}
  92 + </div>
  93 + </div>
  94 + <div className = "wizardPane-section wizardPane-footer">
  95 + <div className="btn"
  96 + className = "wizardPane-link"
  97 + onClick = {() => this.onShowForm()}
  98 + >
  99 + Email did not arrive or want to use a different email?
  100 + </div>
  101 + </div>
  102 + </div>
  103 + );
  104 + };
  105 +
  106 + render() {
  107 + return this.state.form ? this.renderForm() : this.renderMessage();
  108 + };
  109 +
  110 +};
... ...
imports/client/views/verify/module/VerifyLayout.js
... ... @@ -0,0 +1,65 @@
  1 +import _ from 'lodash';
  2 +import { Meteor } from 'meteor/meteor';
  3 +
  4 +import React, { Component } from 'react';
  5 +import { Link } from 'react-router';
  6 +import { If, Case } from '/imports/client/components/Logic';
  7 +import { Avatar } from '/imports/client/components/Avatar';
  8 +
  9 +import { logout } from '/imports/client/app/utils/loginMethods';
  10 +
  11 +import { EmailPane } from '/imports/client/views/verify/EmailPane';
  12 +import ReactSVG from 'react-svg'
  13 +
  14 +
  15 +export class VerifyLayout extends Component {
  16 +
  17 + render() {
  18 + const user = this.props.data.user;
  19 +
  20 + return (
  21 + <div className = "wizardLayout-box">
  22 + <div className = "wizardLayout-top">
  23 + <div className="container">
  24 + <div className = "wizardLayout-topSpace logo-space-0">
  25 + <ReactSVG
  26 + path="/files/images/svg/logo--white.svg"
  27 + className="enterPane__logo"
  28 + />
  29 + </div>
  30 + <div className = "wizardLayout-topGroup">
  31 + <div className = "wizardLayout-topItem">
  32 + <Avatar
  33 + user = {user}
  34 + size = {20}
  35 + small = {true}
  36 + />
  37 + &nbsp;
  38 + {user.getFullName()}
  39 + </div>
  40 + <div
  41 + className = "wizardLayout-topItem"
  42 + onClick = {() => logout()}
  43 + >
  44 + <i className="icon icon-simple icon-power"></i>
  45 + </div>
  46 + </div>
  47 + </div>
  48 + </div>
  49 +
  50 + <div className = "wizardLayout-wrap">
  51 + <div className = "wizardLayout-content">
  52 +
  53 + <EmailPane
  54 + user = {user}
  55 + />
  56 +
  57 + </div>
  58 + </div>
  59 + </div>
  60 + );
  61 + };
  62 +
  63 +};
  64 +
  65 +
... ...
imports/client/views/verify/module/index.js
... ... @@ -0,0 +1,50 @@
  1 +// import { VerifyModule } from '/imports/client/views/verify/module/index'
  2 +import {
  3 + composeWithTracker,
  4 + compose,
  5 + composeAll
  6 + } from 'react-komposer';
  7 +import { VerifyLayout } from './VerifyLayout';
  8 +import { Loading } from '/imports/client/components/Loading';
  9 +
  10 +import { Users } from '/imports/collections/users/index';
  11 +
  12 +
  13 +const meteorTick = (props, onData) => {
  14 +
  15 + const handles = [
  16 + Meteor.subscribe('users.current'),
  17 + ];
  18 +
  19 + if(_.every(handles, (handle) => (handle.ready()) )) {
  20 + const user = Users.current();
  21 + onData(null, {
  22 + data: {
  23 + user: user,
  24 + },
  25 + });
  26 + }
  27 +
  28 + return () => {
  29 + _.each(handles, (handle) => handle.stop() );
  30 + };
  31 +};
  32 +
  33 +
  34 +const reduxTick = (props, onData) => {
  35 + onData(null, {
  36 + data: {}
  37 + });
  38 +};
  39 +
  40 +
  41 +export const VerifyModule = composeAll(
  42 + composeWithTracker(meteorTick, Loading),
  43 + compose(reduxTick, Loading),
  44 +)(VerifyLayout);
  45 +
  46 +
  47 +
  48 +
  49 +
  50 +
... ...
imports/server/accounts/creation.js
... ... @@ -12,6 +12,7 @@ Accounts.validateNewUser((user) =&gt; {
12 12 });
13 13  
14 14 Accounts.onCreateUser((options, user) => {
  15 +
15 16 if(options.orgSlug){
16 17 orgId = Orgs.insert({
17 18 slug: options.orgSlug,
... ... @@ -23,11 +24,16 @@ Accounts.onCreateUser((options, user) =&gt; {
23 24 }],
24 25 });
25 26 }
  27 + console.log("options");
  28 + console.log(options);
  29 + console.log("user");
  30 + console.log(user);
26 31 _.assign(user, {
27 32 role: Users.roles.ADMIN,
28 33 orgId: orgId,
29   - firstName: options.profile.firstName,
30   - lastName: options.profile.lastName,
  34 + firstName: options.profile.name.first,
  35 + lastName: options.profile.name.last,
31 36 });
  37 + console.log(user);
32 38 return user;
33 39 });
... ...
imports/server/emails/verifyEmail.js
1 1 import _ from 'lodash';
2 2 import { Accounts } from 'meteor/accounts-base';
  3 +import { Orgs } from '/imports/collections/orgs/index';
3 4  
4 5 Accounts.config({
5 6 sendVerificationEmail: true
... ... @@ -10,22 +11,18 @@ Accounts.emailTemplates.verifyEmail = {
10 11 return '[YoungDesk] Verify Your Email Address';
11 12 },
12 13 text(user, url) {
13   - console.log(user);
14   - if(user.firstName){
15   - const name = user.firstName;
16   - }else{
17   - const name = user.profile.firstName;
18   - }
19 14 const theUrl = Meteor.absoluteUrl(`back/verifyEmail/${_.last(url.split('/'))}`);
  15 + org = Orgs.findOne({"_id":user.orgId});
20 16  
  17 + OrgUrl = theUrl.replace("http://","http://"+org.slug+".");
21 18 return (
22 19 `
23   -Hello, ${name}!
  20 +Hello, ${user.firstName}!
24 21  
25 22  
26 23 To verify your email address, visit the following link:
27 24  
28   -${theUrl}
  25 +${OrgUrl}
29 26  
30 27 If you did not request this verification, please ignore this email.
31 28  
... ...