Commit 925ffa9d3440ccc682cf66edfe66357ee262e27e
1 parent
52c4c75dfb
Exists in
master
changed teachers to staff
Showing
30 changed files
with
1211 additions
and
1676 deletions
Show diff stats
imports/client/app/routes.js
1 | /* eslint-disable max-len */ | 1 | /* eslint-disable max-len */ |
2 | 2 | ||
3 | import React from 'react'; | 3 | import React from 'react'; |
4 | import { render } from 'react-dom'; | 4 | import { render } from 'react-dom'; |
5 | import { Router, Route, | 5 | import { Router, Route, |
6 | IndexRoute, browserHistory } from 'react-router'; | 6 | IndexRoute, browserHistory } from 'react-router'; |
7 | import { Meteor } from 'meteor/meteor'; | 7 | import { Meteor } from 'meteor/meteor'; |
8 | 8 | ||
9 | /** | 9 | /** |
10 | * General Components | 10 | * General Components |
11 | */ | 11 | */ |
12 | import Index from '/imports/client/views/app/module/Index'; | 12 | import Index from '/imports/client/views/app/module/Index'; |
13 | import NotFound from '/imports/client/views/org/NotFound'; | 13 | import NotFound from '/imports/client/views/org/NotFound'; |
14 | 14 | ||
15 | /** | 15 | /** |
16 | * Org Components | 16 | * Org Components |
17 | */ | 17 | */ |
18 | 18 | ||
19 | import { App } from '/imports/client/layouts/OrgApp'; | 19 | import { App } from '/imports/client/layouts/OrgApp'; |
20 | import { AppModule } from '/imports/client/views/org/app/module/Index'; | 20 | import { AppModule } from '/imports/client/views/org/app/module/Index'; |
21 | import { Orgs } from '/imports/collections/orgs/index'; | 21 | import { Orgs } from '/imports/collections/orgs/index'; |
22 | import { importCsvController } from '/imports/client/views/org/importCsv/index' | 22 | import { importCsvController } from '/imports/client/views/org/importCsv/index' |
23 | 23 | ||
24 | //admin | 24 | //admin |
25 | import { StudentDataController } from '/imports/client/views/org/admin/students/index' | 25 | import { StudentDataController } from '/imports/client/views/org/admin/students/index' |
26 | import { teachersViewController } from '/imports/client/views/org/admin/teachers/index' | 26 | import { staffViewController } from '/imports/client/views/org/admin/staff/index' |
27 | //students | 27 | //students |
28 | 28 | ||
29 | //teachers | 29 | //teachers |
30 | 30 | ||
31 | //parents | 31 | //parents |
32 | 32 | ||
33 | 33 | ||
34 | 34 | ||
35 | /** | 35 | /** |
36 | * NonOrg Components | 36 | * NonOrg Components |
37 | */ | 37 | */ |
38 | import Signup from '/imports/client/views/nonOrg/enter/SignupView'; | 38 | import Signup from '/imports/client/views/nonOrg/enter/SignupView'; |
39 | import { NonOrgApp } from '/imports/client/layouts/NonOrgApp'; | 39 | import { NonOrgApp } from '/imports/client/layouts/NonOrgApp'; |
40 | import {NonOrgAppModule} from '/imports/client/views/nonOrg/app/module/Index'; | 40 | import {NonOrgAppModule} from '/imports/client/views/nonOrg/app/module/Index'; |
41 | 41 | ||
42 | /** | 42 | /** |
43 | * Invalid Org Components | 43 | * Invalid Org Components |
44 | */ | 44 | */ |
45 | 45 | ||
46 | /** | 46 | /** |
47 | There are three types of routes | 47 | There are three types of routes |
48 | 1)getOrgRoutes: all the routes that should be present for a registered org | 48 | 1)getOrgRoutes: all the routes that should be present for a registered org |
49 | 2)getInvalidOrgRoute: all the routes where someone tries to enter a subdomain which hasn't been registered yet (404 mostly :D) | 49 | 2)getInvalidOrgRoute: all the routes where someone tries to enter a subdomain which hasn't been registered yet (404 mostly :D) |
50 | 3)getNonOrgRoutes: all routes linked to normal site, ie signing up a new org. CHeking out demo and everything internal | 50 | 3)getNonOrgRoutes: all routes linked to normal site, ie signing up a new org. CHeking out demo and everything internal |
51 | **/ | 51 | **/ |
52 | const getOrgRoutes = () => ( | 52 | const getOrgRoutes = () => ( |
53 | <Router history={ browserHistory }> | 53 | <Router history={ browserHistory }> |
54 | <Route path="/" component={ App }> | 54 | <Route path="/" component={ App }> |
55 | <IndexRoute name="index" component={ AppModule } /> | 55 | <IndexRoute name="index" component={ AppModule } /> |
56 | <Route name="import" path="/import" component={ importCsvController } /> | 56 | <Route name="import" path="/import" component={ importCsvController } /> |
57 | <Route name="student" path="/students" component={ StudentDataController } /> | 57 | <Route name="student" path="/students" component={ StudentDataController } /> |
58 | <Route name="teachers" path="/teachers" component={ teachersViewController } /> | 58 | <Route name="staff" path="/staff" component={ staffViewController } /> |
59 | <Route path="*" component={ NotFound } /> | 59 | <Route path="*" component={ NotFound } /> |
60 | </Route> | 60 | </Route> |
61 | </Router> | 61 | </Router> |
62 | ) | 62 | ) |
63 | 63 | ||
64 | 64 | ||
65 | const getInvalidOrgRoute = () => ( | 65 | const getInvalidOrgRoute = () => ( |
66 | <Router history={ browserHistory }> | 66 | <Router history={ browserHistory }> |
67 | <Route path="/" component={ App }> | 67 | <Route path="/" component={ App }> |
68 | <IndexRoute name="index" component={ NotFound } /> | 68 | <IndexRoute name="index" component={ NotFound } /> |
69 | <Route path="*" component={ NotFound } /> | 69 | <Route path="*" component={ NotFound } /> |
70 | </Route> | 70 | </Route> |
71 | </Router> | 71 | </Router> |
72 | ) | 72 | ) |
73 | 73 | ||
74 | const getNonOrgRoutes = () => ( | 74 | const getNonOrgRoutes = () => ( |
75 | <Router history={ browserHistory }> | 75 | <Router history={ browserHistory }> |
76 | <Route path="/" component={ NonOrgApp }> | 76 | <Route path="/" component={ NonOrgApp }> |
77 | <IndexRoute name="index" component={ NonOrgAppModule } /> | 77 | <IndexRoute name="index" component={ NonOrgAppModule } /> |
78 | <Route name="signup" path="/signup" component={ Signup } /> | 78 | <Route name="signup" path="/signup" component={ Signup } /> |
79 | <Route path="*" component={ NotFound } /> | 79 | <Route path="*" component={ NotFound } /> |
80 | </Route> | 80 | </Route> |
81 | </Router> | 81 | </Router> |
82 | ) | 82 | ) |
83 | 83 | ||
84 | //Authenticate function to give access to users only | 84 | //Authenticate function to give access to users only |
85 | const authenticate = (nextState, replace) => { | 85 | const authenticate = (nextState, replace) => { |
86 | if (!Meteor.loggingIn() && !Meteor.userId()) { | 86 | if (!Meteor.loggingIn() && !Meteor.userId()) { |
87 | replace({ | 87 | replace({ |
88 | pathname: '/login', | 88 | pathname: '/login', |
89 | state: { nextPathname: nextState.location.pathname }, | 89 | state: { nextPathname: nextState.location.pathname }, |
90 | }); | 90 | }); |
91 | } | 91 | } |
92 | }; | 92 | }; |
93 | 93 | ||
94 | 94 | ||
95 | /** | 95 | /** |
96 | 96 | ||
97 | **/ | 97 | **/ |
98 | const detectOrg = () => { | 98 | const detectOrg = () => { |
99 | orgSlug = ""; | 99 | orgSlug = ""; |
100 | var hostnameArray = document.location.hostname.split( "." ); | 100 | var hostnameArray = document.location.hostname.split( "." ); |
101 | if(hostnameArray[0] !== "www"){ | 101 | if(hostnameArray[0] !== "www"){ |
102 | if((hostnameArray[1]==='localhost'||hostnameArray[1]==='ydapp')){ | 102 | if((hostnameArray[1]==='localhost'||hostnameArray[1]==='ydapp')){ |
103 | orgSlug = hostnameArray[0]; | 103 | orgSlug = hostnameArray[0]; |
104 | } | 104 | } |
105 | }else{ | 105 | }else{ |
106 | if((hostnameArray[2]==='localhost'||hostnameArray[2]==='ydapp')){ | 106 | if((hostnameArray[2]==='localhost'||hostnameArray[2]==='ydapp')){ |
107 | orgSlug = hostnameArray[1]; | 107 | orgSlug = hostnameArray[1]; |
108 | } | 108 | } |
109 | } | 109 | } |
110 | 110 | ||
111 | if(orgSlug!==""){ | 111 | if(orgSlug!==""){ |
112 | console.log(orgSlug); | 112 | console.log(orgSlug); |
113 | Meteor.call('checkExistingOrg', {slug:orgSlug}, function(err, res) { | 113 | Meteor.call('checkExistingOrg', {slug:orgSlug}, function(err, res) { |
114 | if(res){ | 114 | if(res){ |
115 | Session.set('orgId', res._id); | 115 | Session.set('orgId', res._id); |
116 | Session.set('orgSlug', orgSlug); | 116 | Session.set('orgSlug', orgSlug); |
117 | render(getOrgRoutes(),document.getElementById('app')); | 117 | render(getOrgRoutes(),document.getElementById('app')); |
118 | }else{ | 118 | }else{ |
119 | render(getInvalidOrgRoute(),document.getElementById('app')); | 119 | render(getInvalidOrgRoute(),document.getElementById('app')); |
120 | } | 120 | } |
121 | }); | 121 | }); |
122 | }else{ | 122 | }else{ |
123 | render(getNonOrgRoutes(),document.getElementById('app')); | 123 | render(getNonOrgRoutes(),document.getElementById('app')); |
124 | } | 124 | } |
125 | } | 125 | } |
126 | const checkSlug = (nextState, replace) => { | 126 | const checkSlug = (nextState, replace) => { |
127 | orgId = Session.get('orgId'); | 127 | orgId = Session.get('orgId'); |
128 | } | 128 | } |
129 | 129 | ||
130 | 130 | ||
131 | Meteor.startup(() => { | 131 | Meteor.startup(() => { |
132 | detectOrg(); | 132 | detectOrg(); |
133 | }); | 133 | }); |
134 | 134 |
imports/client/views/org/admin/AdminLayout.js
1 | import _ from 'lodash'; | 1 | import _ from 'lodash'; |
2 | import { Meteor } from 'meteor/meteor'; | 2 | import { Meteor } from 'meteor/meteor'; |
3 | import React, { Component } from 'react'; | 3 | import React, { Component } from 'react'; |
4 | import { Link } from 'react-router'; | 4 | import { Link } from 'react-router'; |
5 | import { Avatar } from '/imports/client/components/Avatar'; | 5 | import { Avatar } from '/imports/client/components/Avatar'; |
6 | import { Icon } from '/imports/client/components/Icon'; | 6 | import { Icon } from '/imports/client/components/Icon'; |
7 | import classNames from 'classnames'; | 7 | import classNames from 'classnames'; |
8 | import { EnterModule } from '/imports/client/views/org/enter/module/index'; | 8 | import { EnterModule } from '/imports/client/views/org/enter/module/index'; |
9 | import { AdminSidebar } from './Sidebar' | 9 | import { AdminSidebar } from './Sidebar' |
10 | import { AdminBreadcrumb } from './Breadcrumb' | 10 | import { AdminBreadcrumb } from './Breadcrumb' |
11 | // import { VerifyModule } from '/imports/client/views/verify/module/index'; | 11 | // import { VerifyModule } from '/imports/client/views/verify/module/index'; |
12 | import { Navbar,Modal, Nav, NavItem, | 12 | import { Navbar,Modal, Nav, NavItem, |
13 | Glyphicon, Collapse, | 13 | Glyphicon, Collapse, |
14 | NavbarToggler, NavbarBrand, | 14 | NavbarToggler, NavbarBrand, |
15 | NavLink, DropdownItem, DropdownToggle, DropdownMenu, | 15 | NavLink, DropdownItem, DropdownToggle, DropdownMenu, |
16 | NavDropdown, MenuItem, Breadcrumb } from 'react-bootstrap'; | 16 | NavDropdown, MenuItem, Breadcrumb } from 'react-bootstrap'; |
17 | import { VerifyModule } from '/imports/client/views/verify/module/index' | 17 | import { VerifyModule } from '/imports/client/views/verify/module/index' |
18 | 18 | ||
19 | var Accordion = require('react-bootstrap').Accordion; | 19 | var Accordion = require('react-bootstrap').Accordion; |
20 | var Panel = require('react-bootstrap').Panel; | 20 | var Panel = require('react-bootstrap').Panel; |
21 | export class AdminAppLayout extends Component { | 21 | export class AdminAppLayout extends Component { |
22 | render() { | 22 | render() { |
23 | const {user, org} = this.props; | 23 | const {user, org} = this.props; |
24 | return ( | 24 | return ( |
25 | <div className = "appLayout-box"> | 25 | <div className = "appLayout-box"> |
26 | <div className="page-container"> | 26 | <div className="page-container"> |
27 | <div className="page-content"> | 27 | <div className="page-content"> |
28 | <AdminSidebar | 28 | <AdminSidebar |
29 | user = {user} | 29 | user = {user} |
30 | org = {org} | 30 | org = {org} |
31 | /> | 31 | /> |
32 | <div className="content-wrapper"> | 32 | <div className="content-wrapper"> |
33 | <AdminBreadcrumb /> | 33 | <AdminBreadcrumb /> |
34 | <div className="content"> | 34 | <div className="content"> |
35 | <div className="row"> | 35 | <div className="row"> |
36 | <div className="col-lg-3 col-md-6"> | 36 | <div className="col-lg-3 col-md-6"> |
37 | <div className="thumbnail"> | 37 | <div className="thumbnail"> |
38 | <Link to="/students" > | 38 | <Link to="/students" > |
39 | <div className="thumb thumb-rounded"> | 39 | <div className="thumb thumb-rounded"> |
40 | <img src="assets/images/download2.png" alt="" /> | 40 | <img src="assets/images/download2.png" alt="" /> |
41 | </div> | 41 | </div> |
42 | <div className="caption text-center"> | 42 | <div className="caption text-center"> |
43 | <h6 className="text-semibold no-margin">Students <small className="display-block">Click to view</small></h6> | 43 | <h6 className="text-semibold no-margin">Students <small className="display-block">Click to view</small></h6> |
44 | </div> | 44 | </div> |
45 | </Link> | 45 | </Link> |
46 | </div> | 46 | </div> |
47 | </div> | 47 | </div> |
48 | <div className="col-lg-3 col-md-6"> | 48 | <div className="col-lg-3 col-md-6"> |
49 | <div className="thumbnail"> | 49 | <div className="thumbnail"> |
50 | <Link to="/teachers" > | 50 | <Link to="/staff" > |
51 | <div className="thumb thumb-rounded"> | 51 | <div className="thumb thumb-rounded"> |
52 | <img src="assets/images/download3.png" alt=""/> | 52 | <img src="assets/images/download3.png" alt=""/> |
53 | </div> | 53 | </div> |
54 | <div className="caption text-center"> | 54 | <div className="caption text-center"> |
55 | <h6 className="text-semibold no-margin">Teachers <small className="display-block">Click to view</small></h6> | 55 | <h6 className="text-semibold no-margin">Teachers <small className="display-block">Click to view</small></h6> |
56 | </div> | 56 | </div> |
57 | </Link> | 57 | </Link> |
58 | </div> | 58 | </div> |
59 | </div> | 59 | </div> |
60 | 60 | ||
61 | </div> | 61 | </div> |
62 | </div> | 62 | </div> |
63 | </div> | 63 | </div> |
64 | </div> | 64 | </div> |
65 | </div> | 65 | </div> |
66 | 66 | ||
67 | <div className = "appLayout-wrapOuter"> | 67 | <div className = "appLayout-wrapOuter"> |
68 | <div className = "appLayout-wrapInner"> | 68 | <div className = "appLayout-wrapInner"> |
69 | <div className = "appLayout-menuWrap"> | 69 | <div className = "appLayout-menuWrap"> |
70 | 70 | ||
71 | </div> | 71 | </div> |
72 | <div className = "appLayout-contentWrap"> | 72 | <div className = "appLayout-contentWrap"> |
73 | <div className = "appLayout-content"> | 73 | <div className = "appLayout-content"> |
74 | 74 | ||
75 | </div> | 75 | </div> |
76 | </div> | 76 | </div> |
77 | </div> | 77 | </div> |
78 | </div> | 78 | </div> |
79 | </div> | 79 | </div> |
80 | ); | 80 | ); |
81 | }; | 81 | }; |
82 | 82 | ||
83 | }; | 83 | }; |
84 | 84 |
imports/client/views/org/admin/Header.js
1 | import _ from 'lodash'; | 1 | import _ from 'lodash'; |
2 | import { Meteor } from 'meteor/meteor'; | 2 | import { Meteor } from 'meteor/meteor'; |
3 | 3 | ||
4 | import React, { Component } from 'react'; | 4 | import React, { Component } from 'react'; |
5 | import { Link,browserHistory } from 'react-router'; | 5 | import { Link,browserHistory } from 'react-router'; |
6 | import { FormGroup, | 6 | import { FormGroup, |
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | 7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; |
8 | 8 | ||
9 | 9 | ||
10 | export class Header extends Component { | 10 | export class Header extends Component { |
11 | 11 | ||
12 | constructor(props) { | 12 | constructor(props) { |
13 | super(props); | 13 | super(props); |
14 | this.state = { | 14 | this.state = { |
15 | 15 | ||
16 | }; | 16 | }; |
17 | this.onUpdate = this.onUpdate.bind(this); | 17 | this.onUpdate = this.onUpdate.bind(this); |
18 | }; | 18 | }; |
19 | 19 | ||
20 | onUpdate(key, value) { | 20 | onUpdate(key, value) { |
21 | this.setState({[key]: value}); | 21 | this.setState({[key]: value}); |
22 | }; | 22 | }; |
23 | 23 | ||
24 | render() { | 24 | render() { |
25 | return ( | 25 | return ( |
26 | <div className = "enterPane-box"> | 26 | <div className = "enterPane-box"> |
27 | <div className="row"> | 27 | <div className="row"> |
28 | <div className="col-lg-3 col-md-6"> | 28 | <div className="col-lg-3 col-md-6"> |
29 | <div className="thumbnail"> | 29 | <div className="thumbnail"> |
30 | <Link to="/students" > | 30 | <Link to="/students" > |
31 | <div className="thumb thumb-rounded"> | 31 | <div className="thumb thumb-rounded"> |
32 | <img src="assets/images/download2.png" alt="" /> | 32 | <img src="assets/images/download2.png" alt="" /> |
33 | </div> | 33 | </div> |
34 | <div className="caption text-center"> | 34 | <div className="caption text-center"> |
35 | <h6 className="text-semibold no-margin">Students <small className="display-block">Click to view</small></h6> | 35 | <h6 className="text-semibold no-margin">Students <small className="display-block">Click to view</small></h6> |
36 | </div> | 36 | </div> |
37 | </Link> | 37 | </Link> |
38 | </div> | 38 | </div> |
39 | </div> | 39 | </div> |
40 | <div className="col-lg-3 col-md-6"> | 40 | <div className="col-lg-3 col-md-6"> |
41 | <div className="thumbnail"> | 41 | <div className="thumbnail"> |
42 | <Link to="/teachers" > | 42 | <Link to="/staff" > |
43 | <div className="thumb thumb-rounded"> | 43 | <div className="thumb thumb-rounded"> |
44 | <img src="assets/images/download3.png" alt=""/> | 44 | <img src="assets/images/download3.png" alt=""/> |
45 | </div> | 45 | </div> |
46 | <div className="caption text-center"> | 46 | <div className="caption text-center"> |
47 | <h6 className="text-semibold no-margin">Teachers <small className="display-block">Click to view</small></h6> | 47 | <h6 className="text-semibold no-margin">Teachers <small className="display-block">Click to view</small></h6> |
48 | </div> | 48 | </div> |
49 | </Link> | 49 | </Link> |
50 | </div> | 50 | </div> |
51 | </div> | 51 | </div> |
52 | 52 | ||
53 | </div> | 53 | </div> |
54 | </div> | 54 | </div> |
55 | ); | 55 | ); |
56 | }; | 56 | }; |
57 | 57 | ||
58 | }; | 58 | }; |
59 | 59 |
imports/client/views/org/admin/staff/StaffView.js
File was created | 1 | import _ from 'lodash'; | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | |||
4 | import React, { Component } from 'react'; | ||
5 | import { Link,browserHistory } from 'react-router'; | ||
6 | import { FormGroup, | ||
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
8 | import { Header } from '../Header'; | ||
9 | import { AdminSidebar } from '../Sidebar' | ||
10 | import { AdminBreadcrumb } from '../Breadcrumb' | ||
11 | import { StaffTable } from './view/StaffTable' | ||
12 | import { AddTeacher } from './add/addTeacher' | ||
13 | import { UploadCsvTeacher } from './UploadCsvTeacher' | ||
14 | |||
15 | export class StaffView extends Component { | ||
16 | constructor(props) { | ||
17 | super(props); | ||
18 | this.state = { | ||
19 | |||
20 | }; | ||
21 | this.onUpdate = this.onUpdate.bind(this); | ||
22 | }; | ||
23 | |||
24 | onUpdate(key, value) { | ||
25 | this.setState({[key]: value}); | ||
26 | }; | ||
27 | |||
28 | render() { | ||
29 | const {user, org, staff} = this.props.data; | ||
30 | return ( | ||
31 | <div className="appLayout-box"> | ||
32 | <div className="page-container"> | ||
33 | <div className="page-content"> | ||
34 | <AdminSidebar | ||
35 | user = {user} | ||
36 | org = {org} | ||
37 | /> | ||
38 | <div className="content-wrapper"> | ||
39 | <AdminBreadcrumb /> | ||
40 | |||
41 | <div className="content has-detached-left"> | ||
42 | <div className="container-detached"> | ||
43 | <div className="content-detached"> | ||
44 | <Header | ||
45 | user = {user} | ||
46 | org = {org} | ||
47 | /> | ||
48 | <StaffTable | ||
49 | data = {this.props.data} | ||
50 | staff = {staff} | ||
51 | /> | ||
52 | <AddTeacher/> | ||
53 | <UploadCsvTeacher /> | ||
54 | </div> | ||
55 | </div> | ||
56 | <div className="sidebar-detached affix-top"> | ||
57 | <div className="sidebar sidebar-default"> | ||
58 | <div className="sidebar-content"> | ||
59 | |||
60 | <div className="sidebar-category"> | ||
61 | <div className="category-title"> | ||
62 | <span>Advanced Search</span> | ||
63 | <ul className="icons-list"> | ||
64 | <li><a href="#" data-action="collapse"></a></li> | ||
65 | </ul> | ||
66 | </div> | ||
67 | |||
68 | <div className="category-content"> | ||
69 | <form action="#"> | ||
70 | <div className="has-feedback has-feedback-left"> | ||
71 | <input type="search" className="form-control" | ||
72 | value={this.state.firstNameSearch} | ||
73 | onChange={e=>this.onUpdate('firstNameSearch',e.target.value)} | ||
74 | placeholder="First Name" | ||
75 | /> | ||
76 | <div className="form-control-feedback"> | ||
77 | <i className="icon-search4 text-size-base text-muted"></i> | ||
78 | </div> | ||
79 | </div> | ||
80 | </form> | ||
81 | </div> | ||
82 | <div className="category-content"> | ||
83 | <form action="#"> | ||
84 | <div className="has-feedback has-feedback-left"> | ||
85 | <input type="search" className="form-control" | ||
86 | value={this.state.lastNameSearch} | ||
87 | onChange={e=>this.onUpdate('lastNameSearch',e.target.value)} | ||
88 | placeholder="Last Name" /> | ||
89 | <div className="form-control-feedback"> | ||
90 | <i className="icon-search4 text-size-base text-muted"></i> | ||
91 | </div> | ||
92 | </div> | ||
93 | </form> | ||
94 | </div> | ||
95 | </div> | ||
96 | </div> | ||
97 | </div> | ||
98 | </div> | ||
99 | </div> | ||
100 | </div> | ||
101 | </div> | ||
102 | </div> | ||
103 | </div> | ||
104 | ); | ||
105 | }; | ||
106 | |||
107 | }; | ||
108 |
imports/client/views/org/admin/staff/UploadCsvTeacher.js
File was created | 1 | // import {UploadCsv } from '/imports/collections/students/UploadCsv' | |
2 | import _ from 'lodash'; | ||
3 | import { Meteor } from 'meteor/meteor'; | ||
4 | |||
5 | import React, { Component } from 'react'; | ||
6 | import { Link,browserHistory } from 'react-router'; | ||
7 | import { FormGroup,Panel,Table, | ||
8 | ButtonToolbar,Modal,ControlLabel,HelpBlock, | ||
9 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
10 | // import { AddStudentForm } from './addStudentForm'; | ||
11 | import { FilesCollection } from 'meteor/ostrio:files'; | ||
12 | const Papa = this.Papa; | ||
13 | // console.log(this); | ||
14 | const style = { | ||
15 | margin: 12, | ||
16 | }; | ||
17 | function FieldGroup({ id, label, help, ...props }) { | ||
18 | return ( | ||
19 | <FormGroup controlId={id}> | ||
20 | <ControlLabel>{label}</ControlLabel> | ||
21 | <FormControl {...props} /> | ||
22 | {help && <HelpBlock>{help}</HelpBlock>} | ||
23 | </FormGroup> | ||
24 | ); | ||
25 | } | ||
26 | export class UploadCsvTeacher extends Component { | ||
27 | constructor(props) { | ||
28 | super(props); | ||
29 | this.state = { | ||
30 | show: false | ||
31 | }; | ||
32 | this.showModal = this.showModal.bind(this); | ||
33 | this.hideModal = this.hideModal.bind(this); | ||
34 | this.onUpdate = this.onUpdate.bind(this); | ||
35 | }; | ||
36 | |||
37 | showModal() { | ||
38 | this.setState({show: true}); | ||
39 | } | ||
40 | |||
41 | hideModal() { | ||
42 | this.setState({show: false}); | ||
43 | } | ||
44 | onUpdate(key, value) { | ||
45 | this.setState({[key]: value}); | ||
46 | }; | ||
47 | uploadStudentCsv(e){ | ||
48 | e.preventDefault(); | ||
49 | e.persist(); | ||
50 | var file = $('input[type="file"]').prop("files")[0]; | ||
51 | Papa.parse(file, { | ||
52 | header: true, | ||
53 | complete: function(csvData) { | ||
54 | console.log("csvData"); | ||
55 | console.log(csvData); | ||
56 | if(csvData){ | ||
57 | Meteor.call('teachers.uploadCsv', csvData, function (error, result) { | ||
58 | console.log("error"); | ||
59 | console.log(error); | ||
60 | console.log("result"); | ||
61 | console.log(result); | ||
62 | }) | ||
63 | } | ||
64 | } | ||
65 | }); | ||
66 | } | ||
67 | |||
68 | render() { | ||
69 | console.log(this.props); | ||
70 | return ( | ||
71 | <ButtonToolbar> | ||
72 | <Button bsStyle="primary" onClick={this.showModal}> | ||
73 | Upload CSV | ||
74 | </Button> | ||
75 | <Modal | ||
76 | {...this.props} | ||
77 | show={this.state.show} | ||
78 | onHide={this.hideModal} | ||
79 | dialogClassName="custom-modal" | ||
80 | > | ||
81 | <Modal.Header closeButton> | ||
82 | <Modal.Title id="contained-modal-title-lg">Upload Csv</Modal.Title> | ||
83 | </Modal.Header> | ||
84 | <Modal.Body> | ||
85 | <form onSubmit={ (e) => this.uploadStudentCsv(e) } > | ||
86 | <FieldGroup | ||
87 | id="formControlsFile" | ||
88 | type="file" | ||
89 | label="File" | ||
90 | help="Upload you CSV here." | ||
91 | /> | ||
92 | <Button type="submit" bsStyle="default">Upload File</Button> | ||
93 | </form> | ||
94 | </Modal.Body> | ||
95 | <Modal.Footer> | ||
96 | <Button onClick={this.hideModal}>Close</Button> | ||
97 | </Modal.Footer> | ||
98 | </Modal> | ||
99 | </ButtonToolbar> | ||
100 | ); | ||
101 | }; | ||
102 | |||
103 | }; | ||
104 |
imports/client/views/org/admin/staff/add/AddTeacherFormContainer.js
File was created | 1 | import React, { Component } from 'react' | |
2 | import StudentForm from './TeacherForm' | ||
3 | import Form from '/imports/client/views/core/Form' | ||
4 | import Validator from '/imports/client/views/core/Validator' | ||
5 | import { isRequired, isValidEmail } from '/imports/client/views/core/validations' | ||
6 | import { addStudentManually } from '/imports/collections/students/methods'; | ||
7 | |||
8 | export class AddStudentFormContainer extends Component { | ||
9 | |||
10 | constructor(props) { | ||
11 | super(props) | ||
12 | this.state = { currentStep: 0 } | ||
13 | this.handleNextClick = this.handleNextClick.bind(this) | ||
14 | this.handleBackClick = this.handleBackClick.bind(this) | ||
15 | this.handleSubmit = this.handleSubmit.bind(this) | ||
16 | } | ||
17 | |||
18 | handleNextClick() { | ||
19 | this.form.handleSubmit() | ||
20 | if (this.validator.getErrors() && Object.keys(this.validator.getErrors()).length > 0) return | ||
21 | this.setState({ currentStep: this.state.currentStep + 1 }) | ||
22 | this.form.resetSubmitted() | ||
23 | } | ||
24 | |||
25 | handleBackClick() { | ||
26 | this.setState({ currentStep: this.state.currentStep + -1 }) | ||
27 | } | ||
28 | |||
29 | handleSubmit() { | ||
30 | if (this.state.currentStep === 3) { | ||
31 | addStudentManually.call(this.form.state.values) | ||
32 | } | ||
33 | } | ||
34 | |||
35 | //render callback | ||
36 | render() { | ||
37 | return ( | ||
38 | <Form | ||
39 | onSubmit={this.handleSubmit} | ||
40 | ref={form => this.form = form} | ||
41 | initialValues={{ | ||
42 | gender: 'male', | ||
43 | parentGender: 'male', | ||
44 | }} | ||
45 | > | ||
46 | {({ values, setValue, getValue, isSubmitted, isDirty }) => ( | ||
47 | <Validator | ||
48 | values={values} | ||
49 | ref={validator => this.validator = validator} | ||
50 | validations={{ | ||
51 | admissionId: [(value) => isRequired('Admission id', value)], | ||
52 | firstName: [(value) => isRequired('First name', value)], | ||
53 | lastName: [(value) => isRequired('Last name', value)], | ||
54 | email: [(value) => isRequired('Email', value), isValidEmail], | ||
55 | dob: [(value) => isRequired('Date of birth', value)], | ||
56 | gender: [(value) => isRequired('Gender', value)], | ||
57 | rollNo: [(value) => this.state.currentStep === 1 && isRequired('Roll no', value)], | ||
58 | studentClass: [(value) => this.state.currentStep === 1 && isRequired('Class', value)], | ||
59 | section: [(value) => this.state.currentStep === 1 && isRequired('Section', value)], | ||
60 | community: [(value) => this.state.currentStep === 1 && isRequired('Community', value)], | ||
61 | bloodGroup: [(value) => this.state.currentStep === 1 && isRequired('Blood group', value)], | ||
62 | phone: [(value) => this.state.currentStep === 1 && isRequired('Phone', value)], | ||
63 | address: [(value) => this.state.currentStep === 2 && isRequired('Address', value)], | ||
64 | city: [(value) => this.state.currentStep === 2 && isRequired('City', value)], | ||
65 | state: [(value) => this.state.currentStep === 2 && isRequired('State', value)], | ||
66 | parentName: [(value) => this.state.currentStep === 3 && isRequired('Parent name', value)], | ||
67 | parentEmail: [(value) => this.state.currentStep === 3 && isRequired('Parent email', value), (value) => this.state.currentStep === 3 && isValidEmail(value)], | ||
68 | relation: [(value) => this.state.currentStep === 3 && isRequired('Relation', value)], | ||
69 | profession: [(value) => this.state.currentStep === 3 && isRequired('Profession', value)], | ||
70 | parentGender: [(value) => this.state.currentStep === 3 && isRequired('Parent gender', value)], | ||
71 | parentPhone: [(value) => this.state.currentStep === 3 && isRequired('Parent phone', value)], | ||
72 | parentAddress: [(value) => this.state.currentStep === 3 && isRequired('Parent address', value)], | ||
73 | parentCity: [(value) => this.state.currentStep === 3 && isRequired('Parent city', value)], | ||
74 | parentState: [(value) => this.state.currentStep === 3 && isRequired('Parent state', value)], | ||
75 | parentZipcode: [(value) => this.state.currentStep === 3 && isRequired('Parent zip code', value)], | ||
76 | }} | ||
77 | > | ||
78 | {({ errors }) => ( | ||
79 | <StudentForm | ||
80 | isDirty={isDirty} | ||
81 | setValue={setValue} | ||
82 | getValue={getValue} | ||
83 | isSubmitted={isSubmitted} | ||
84 | errors={errors} | ||
85 | onNextClick={this.handleNextClick} | ||
86 | onBackClick={this.handleBackClick} | ||
87 | currentStep={this.state.currentStep} | ||
88 | /> | ||
89 | )} | ||
90 | </Validator> | ||
91 | )} | ||
92 | </Form> | ||
93 | ) | ||
94 | } | ||
95 | } | ||
96 |
imports/client/views/org/admin/staff/add/TeacherForm.js
File was created | 1 | import React, { PropTypes } from 'react' | |
2 | import { | ||
3 | Row, | ||
4 | Col, | ||
5 | FormGroup, | ||
6 | FormControl, | ||
7 | Button | ||
8 | } from 'react-bootstrap' | ||
9 | import DatePicker from '/imports/client/views/core/DatePicker' | ||
10 | import Label from '/imports/client/views/core/Label' | ||
11 | import Stepper from '/imports/client/views/core/Stepper' | ||
12 | import ErrorLabel from '/imports/client/views/core/ErrorLabel' | ||
13 | |||
14 | const StudentForm = props => ( | ||
15 | <div className="stepy-validation"> | ||
16 | <Stepper | ||
17 | steps={[ | ||
18 | { | ||
19 | label: 'Personal data', | ||
20 | active: props.currentStep === 0, | ||
21 | }, | ||
22 | { | ||
23 | label: 'Academic', | ||
24 | active: props.currentStep === 1, | ||
25 | }, | ||
26 | { | ||
27 | label: 'Address', | ||
28 | active: props.currentStep === 2, | ||
29 | }, | ||
30 | { | ||
31 | label: 'Parent info', | ||
32 | active: props.currentStep === 3, | ||
33 | } | ||
34 | ]} | ||
35 | /> | ||
36 | {props.currentStep === 0 && ( | ||
37 | <fieldset title="1"> | ||
38 | <legend className="text-semibold">Personal data</legend> | ||
39 | <Row> | ||
40 | <Col xs={12} sm={4}> | ||
41 | <FormGroup controlId="admissionId"> | ||
42 | <Label required>Employee ID</Label> | ||
43 | <FormControl | ||
44 | type="text" | ||
45 | value={props.getValue('admissionId')} | ||
46 | placeholder="admission Id" | ||
47 | onChange={e => props.setValue('admissionId', e.target.value)} | ||
48 | /> | ||
49 | {props.isSubmitted() && props.errors && props.errors.admissionId && ( | ||
50 | <ErrorLabel> {props.errors.admissionId} </ErrorLabel> | ||
51 | )} | ||
52 | </FormGroup> | ||
53 | </Col> | ||
54 | |||
55 | <Col xs={12} sm={4}> | ||
56 | <FormGroup controlId="firstName"> | ||
57 | <Label required>First Name</Label> | ||
58 | <FormControl | ||
59 | type="text" | ||
60 | value={props.getValue('firstName')} | ||
61 | placeholder="First Name" | ||
62 | onChange={e => props.setValue('firstName', e.target.value)} | ||
63 | /> | ||
64 | {props.isSubmitted() && props.errors && props.errors.firstName && ( | ||
65 | <ErrorLabel> {props.errors.firstName} </ErrorLabel> | ||
66 | )} | ||
67 | </FormGroup> | ||
68 | </Col> | ||
69 | |||
70 | <Col xs={12} sm={4}> | ||
71 | <FormGroup controlId="lastName"> | ||
72 | <Label required>Last Name</Label> | ||
73 | <FormControl | ||
74 | type="text" | ||
75 | value={props.getValue('lastName')} | ||
76 | placeholder="Last Name" | ||
77 | onChange={e => props.setValue('lastName', e.target.value)} | ||
78 | /> | ||
79 | {props.isSubmitted() && props.errors && props.errors.lastName && ( | ||
80 | <ErrorLabel> {props.errors.lastName} </ErrorLabel> | ||
81 | )} | ||
82 | </FormGroup> | ||
83 | </Col> | ||
84 | </Row> | ||
85 | <Row> | ||
86 | <Col xs={12} sm={4}> | ||
87 | <FormGroup controlId="formControlsSelect"> | ||
88 | <Label>Gender</Label> | ||
89 | <FormControl componentClass="select" | ||
90 | placeholder="select" | ||
91 | value={props.getValue('gender')} | ||
92 | onChange={e => props.setValue('gender', e.target.value)} | ||
93 | > | ||
94 | <option value="male">Male</option> | ||
95 | <option value="female">Female</option> | ||
96 | </FormControl> | ||
97 | {props.isSubmitted() && props.errors && props.errors.gender && ( | ||
98 | <ErrorLabel> {props.errors.gender} </ErrorLabel> | ||
99 | )} | ||
100 | </FormGroup> | ||
101 | </Col> | ||
102 | |||
103 | <Col xs={12} sm={4}> | ||
104 | <FormGroup controlId="martialStatus"> | ||
105 | <Label required>Martial Status</Label> | ||
106 | <FormControl | ||
107 | type="text" | ||
108 | value={props.getValue('martialStatus')} | ||
109 | placeholder="Martial Status" | ||
110 | onChange={e => props.setValue('martialStatus', e.target.value)} | ||
111 | /> | ||
112 | {props.isSubmitted() && props.errors && props.errors.martialStatus && ( | ||
113 | <ErrorLabel> {props.errors.martialStatus} </ErrorLabel> | ||
114 | )} | ||
115 | </FormGroup> | ||
116 | </Col> | ||
117 | |||
118 | <Col xs={12} sm={4}> | ||
119 | <FormGroup> | ||
120 | <Label required>Date of birth</Label> | ||
121 | <DatePicker | ||
122 | id="dob" | ||
123 | setValue = {props.setValue} | ||
124 | value={props.getValue('dob')} | ||
125 | onChange={(e) => { | ||
126 | props.setValue('dob', e.target.value) | ||
127 | }} | ||
128 | /> | ||
129 | {props.isSubmitted() && props.errors && props.errors.dob && ( | ||
130 | <ErrorLabel> {props.errors.dob} </ErrorLabel> | ||
131 | )} | ||
132 | </FormGroup> | ||
133 | </Col> | ||
134 | </Row> | ||
135 | <Row> | ||
136 | <Col xs={12} sm={4}> | ||
137 | <FormGroup controlId="email"> | ||
138 | <Label required>Email</Label> | ||
139 | <FormControl | ||
140 | type="email" | ||
141 | value={props.getValue('email')} | ||
142 | placeholder="Email" | ||
143 | onChange={e => props.setValue('email', e.target.value)} | ||
144 | /> | ||
145 | {props.isSubmitted() && props.errors && props.errors.email && ( | ||
146 | <ErrorLabel> {props.errors.email} </ErrorLabel> | ||
147 | )} | ||
148 | </FormGroup> | ||
149 | </Col> | ||
150 | |||
151 | <Col xs={12} sm={4}> | ||
152 | <FormGroup controlId="formControlsSelect"> | ||
153 | <Label>Type</Label> | ||
154 | <FormControl componentClass="select" | ||
155 | placeholder="select" | ||
156 | value={props.getValue('type')} | ||
157 | onChange={e => props.setValue('gender', e.target.value)} | ||
158 | > | ||
159 | <option value="male">Male</option> | ||
160 | <option value="female">Female</option> | ||
161 | </FormControl> | ||
162 | {props.isSubmitted() && props.errors && props.errors.gender && ( | ||
163 | <ErrorLabel> {props.errors.gender} </ErrorLabel> | ||
164 | )} | ||
165 | </FormGroup> | ||
166 | </Col> | ||
167 | |||
168 | </Row> | ||
169 | <Row> | ||
170 | |||
171 | </Row> | ||
172 | </fieldset> | ||
173 | )} | ||
174 | {props.currentStep === 1 && ( | ||
175 | <fieldset title="Academic"> | ||
176 | <legend className="text-semibold">Academic</legend> | ||
177 | <Row> | ||
178 | <Col xs={12} sm={4}> | ||
179 | <FormGroup controlId="rollNo"> | ||
180 | <Label required>Roll No</Label> | ||
181 | <FormControl | ||
182 | type="text" | ||
183 | value={props.getValue('rollNo')} | ||
184 | placeholder="Roll No" | ||
185 | onChange={e => props.setValue('rollNo', e.target.value)} | ||
186 | /> | ||
187 | {props.isSubmitted() && props.errors && props.errors.rollNo && ( | ||
188 | <ErrorLabel> {props.errors.rollNo} </ErrorLabel> | ||
189 | )} | ||
190 | </FormGroup> | ||
191 | </Col> | ||
192 | <Col xs={12} sm={4}> | ||
193 | <FormGroup controlId="class"> | ||
194 | <Label required>Class</Label> | ||
195 | <FormControl | ||
196 | type="text" | ||
197 | value={props.getValue('studentClass')} | ||
198 | placeholder="7" | ||
199 | onChange={e => props.setValue('studentClass', e.target.value)} | ||
200 | /> | ||
201 | {props.isSubmitted() && props.errors && props.errors.studentClass && ( | ||
202 | <ErrorLabel> {props.errors.studentClass} </ErrorLabel> | ||
203 | )} | ||
204 | </FormGroup> | ||
205 | </Col> | ||
206 | </Row> | ||
207 | <Row> | ||
208 | <Col xs={12} sm={4}> | ||
209 | <FormGroup controlId="section"> | ||
210 | <Label required>Section</Label> | ||
211 | <FormControl | ||
212 | type="text" | ||
213 | value={props.getValue('section')} | ||
214 | placeholder="B" | ||
215 | onChange={e => props.setValue('section', e.target.value)} | ||
216 | /> | ||
217 | {props.isSubmitted() && props.errors && props.errors.section && ( | ||
218 | <ErrorLabel> {props.errors.section} </ErrorLabel> | ||
219 | )} | ||
220 | </FormGroup> | ||
221 | </Col> | ||
222 | <Col xs={12} sm={4}> | ||
223 | <FormGroup controlId="community"> | ||
224 | <Label required>Community</Label> | ||
225 | <FormControl | ||
226 | type="text" | ||
227 | value={props.getValue('community')} | ||
228 | placeholder="General" | ||
229 | onChange={e => props.setValue('community', e.target.value)} | ||
230 | /> | ||
231 | {props.isSubmitted() && props.errors && props.errors.community && ( | ||
232 | <ErrorLabel> {props.errors.community} </ErrorLabel> | ||
233 | )} | ||
234 | </FormGroup> | ||
235 | </Col> | ||
236 | </Row> | ||
237 | <Row> | ||
238 | <Col xs={12} sm={4}> | ||
239 | <FormGroup controlId="bloodGroup"> | ||
240 | <Label required>bloodGroup</Label> | ||
241 | <FormControl | ||
242 | type="text" | ||
243 | value={props.getValue('bloodGroup')} | ||
244 | placeholder="B+" | ||
245 | onChange={e => props.setValue('bloodGroup', e.target.value)} | ||
246 | /> | ||
247 | {props.isSubmitted() && props.errors && props.errors.bloodGroup && ( | ||
248 | <ErrorLabel> {props.errors.bloodGroup} </ErrorLabel> | ||
249 | )} | ||
250 | </FormGroup> | ||
251 | </Col> | ||
252 | <Col xs={12} sm={4}> | ||
253 | <FormGroup controlId="phone"> | ||
254 | <Label required>Phone</Label> | ||
255 | <FormControl | ||
256 | type="text" | ||
257 | value={props.getValue('phone')} | ||
258 | placeholder="9999999999" | ||
259 | onChange={e => props.setValue('phone', e.target.value)} | ||
260 | /> | ||
261 | {props.isSubmitted() && props.errors && props.errors.phone && ( | ||
262 | <ErrorLabel> {props.errors.phone} </ErrorLabel> | ||
263 | )} | ||
264 | </FormGroup> | ||
265 | </Col> | ||
266 | </Row> | ||
267 | </fieldset> | ||
268 | )} | ||
269 | {props.currentStep === 2 && ( | ||
270 | <fieldset title="Address"> | ||
271 | <legend className="text-semibold">Address</legend> | ||
272 | <Row> | ||
273 | <Col xs={12} sm={4}> | ||
274 | <FormGroup controlId="address"> | ||
275 | <Label required>Address</Label> | ||
276 | <FormControl | ||
277 | type="text" | ||
278 | value={props.getValue('address')} | ||
279 | placeholder="#876, Street, town" | ||
280 | onChange={e => props.setValue('address', e.target.value)} | ||
281 | /> | ||
282 | {props.isSubmitted() && props.errors && props.errors.address && ( | ||
283 | <ErrorLabel> {props.errors.address} </ErrorLabel> | ||
284 | )} | ||
285 | </FormGroup> | ||
286 | </Col> | ||
287 | <Col xs={12} sm={4}> | ||
288 | <FormGroup controlId="city"> | ||
289 | <Label required>City</Label> | ||
290 | <FormControl | ||
291 | type="text" | ||
292 | value={props.getValue('city')} | ||
293 | placeholder="Chennai" | ||
294 | onChange={e => props.setValue('city', e.target.value)} | ||
295 | /> | ||
296 | {props.isSubmitted() && props.errors && props.errors.city && ( | ||
297 | <ErrorLabel> {props.errors.city} </ErrorLabel> | ||
298 | )} | ||
299 | </FormGroup> | ||
300 | </Col> | ||
301 | </Row> | ||
302 | <Row> | ||
303 | <Col xs={12} sm={4}> | ||
304 | <FormGroup controlId="state"> | ||
305 | <Label required>State</Label> | ||
306 | <FormControl | ||
307 | type="text" | ||
308 | value={props.getValue('state')} | ||
309 | placeholder="Tamilnadu" | ||
310 | onChange={e => props.setValue('state', e.target.value)} | ||
311 | /> | ||
312 | {props.isSubmitted() && props.errors && props.errors.state && ( | ||
313 | <ErrorLabel> {props.errors.state} </ErrorLabel> | ||
314 | )} | ||
315 | </FormGroup> | ||
316 | </Col> | ||
317 | </Row> | ||
318 | </fieldset> | ||
319 | )} | ||
320 | {props.currentStep === 3 && ( | ||
321 | <fieldset title="2"> | ||
322 | <legend className="text-semibold">Parent information</legend> | ||
323 | <Row> | ||
324 | <Col xs={12} sm={4}> | ||
325 | <FormGroup controlId="parentName"> | ||
326 | <Label required>Parent Name</Label> | ||
327 | <FormControl | ||
328 | type="text" | ||
329 | value={props.getValue('parentName')} | ||
330 | placeholder="John" | ||
331 | onChange={e => props.setValue('parentName', e.target.value)} | ||
332 | /> | ||
333 | {props.isSubmitted() && props.errors && props.errors.parentName && ( | ||
334 | <ErrorLabel> {props.errors.parentName} </ErrorLabel> | ||
335 | )} | ||
336 | </FormGroup> | ||
337 | </Col> | ||
338 | <Col xs={12} sm={4}> | ||
339 | <FormGroup controlId="parentEmail"> | ||
340 | <Label required>Parent Email</Label> | ||
341 | <FormControl | ||
342 | type="text" | ||
343 | value={props.getValue('parentEmail')} | ||
344 | placeholder="john@email.com" | ||
345 | onChange={e => props.setValue('parentEmail', e.target.value)} | ||
346 | /> | ||
347 | {props.isSubmitted() && props.errors && props.errors.parentEmail && ( | ||
348 | <ErrorLabel> {props.errors.parentEmail} </ErrorLabel> | ||
349 | )} | ||
350 | </FormGroup> | ||
351 | </Col> | ||
352 | </Row> | ||
353 | <Row> | ||
354 | <Col xs={12} sm={4}> | ||
355 | <FormGroup controlId="relation"> | ||
356 | <Label required>Relation</Label> | ||
357 | <FormControl | ||
358 | type="text" | ||
359 | value={props.getValue('relation')} | ||
360 | placeholder="Father" | ||
361 | onChange={e => props.setValue('relation', e.target.value)} | ||
362 | /> | ||
363 | {props.isSubmitted() && props.errors && props.errors.relation && ( | ||
364 | <ErrorLabel> {props.errors.relation} </ErrorLabel> | ||
365 | )} | ||
366 | </FormGroup> | ||
367 | </Col> | ||
368 | <Col xs={12} sm={4}> | ||
369 | <FormGroup controlId="profession"> | ||
370 | <Label required>Profession</Label> | ||
371 | <FormControl | ||
372 | type="text" | ||
373 | value={props.getValue('profession')} | ||
374 | placeholder="Farmer" | ||
375 | onChange={e => props.setValue('profession', e.target.value)} | ||
376 | /> | ||
377 | {props.isSubmitted() && props.errors && props.errors.profession && ( | ||
378 | <ErrorLabel> {props.errors.profession} </ErrorLabel> | ||
379 | )} | ||
380 | </FormGroup> | ||
381 | </Col> | ||
382 | </Row> | ||
383 | <Row> | ||
384 | <Col xs={12} sm={4}> | ||
385 | <FormGroup controlId="parentGender"> | ||
386 | <Label>Parent Gender</Label> | ||
387 | <FormControl componentClass="select" | ||
388 | placeholder="select" | ||
389 | value={props.getValue('parentGender')} | ||
390 | onChange={e => props.setValue('parentGender', e.target.value)} | ||
391 | > | ||
392 | <option value="male">Male</option> | ||
393 | <option value="female">Female</option> | ||
394 | </FormControl> | ||
395 | {props.isSubmitted() && props.errors && props.errors.parentGender && ( | ||
396 | <ErrorLabel> {props.errors.parentGender} </ErrorLabel> | ||
397 | )} | ||
398 | </FormGroup> | ||
399 | </Col> | ||
400 | <Col xs={12} sm={4}> | ||
401 | <FormGroup controlId="parentPhone"> | ||
402 | <Label required>Parent Phone</Label> | ||
403 | <FormControl | ||
404 | type="text" | ||
405 | value={props.getValue('parentPhone')} | ||
406 | placeholder="9876543210" | ||
407 | onChange={e => props.setValue('parentPhone', e.target.value)} | ||
408 | /> | ||
409 | {props.isSubmitted() && props.errors && props.errors.parentPhone && ( | ||
410 | <ErrorLabel> {props.errors.parentPhone} </ErrorLabel> | ||
411 | )} | ||
412 | </FormGroup> | ||
413 | </Col> | ||
414 | </Row> | ||
415 | <Row> | ||
416 | <Col xs={12} sm={4}> | ||
417 | <FormGroup controlId="parentAddress"> | ||
418 | <Label required>Parent Address</Label> | ||
419 | <FormControl | ||
420 | type="text" | ||
421 | value={props.getValue('parentAddress')} | ||
422 | placeholder="#12, street, town" | ||
423 | onChange={e => props.setValue('parentAddress', e.target.value)} | ||
424 | /> | ||
425 | {props.isSubmitted() && props.errors && props.errors.parentAddress && ( | ||
426 | <ErrorLabel> {props.errors.parentAddress} </ErrorLabel> | ||
427 | )} | ||
428 | </FormGroup> | ||
429 | </Col> | ||
430 | <Col xs={12} sm={4}> | ||
431 | <FormGroup controlId="parentCity"> | ||
432 | <Label required>Parent City</Label> | ||
433 | <FormControl | ||
434 | type="text" | ||
435 | value={props.getValue('parentCity')} | ||
436 | placeholder="Chennai" | ||
437 | onChange={e => props.setValue('parentCity', e.target.value)} | ||
438 | /> | ||
439 | {props.isSubmitted() && props.errors && props.errors.parentCity && ( | ||
440 | <ErrorLabel> {props.errors.parentCity} </ErrorLabel> | ||
441 | )} | ||
442 | </FormGroup> | ||
443 | </Col> | ||
444 | </Row> | ||
445 | <Row> | ||
446 | <Col xs={12} sm={4}> | ||
447 | <FormGroup controlId="parentState"> | ||
448 | <Label required>Parent State</Label> | ||
449 | <FormControl | ||
450 | type="text" | ||
451 | value={props.getValue('parentState')} | ||
452 | placeholder="600031" | ||
453 | onChange={e => props.setValue('parentState', e.target.value)} | ||
454 | /> | ||
455 | {props.isSubmitted() && props.errors && props.errors.parentState && ( | ||
456 | <ErrorLabel> {props.errors.parentState} </ErrorLabel> | ||
457 | )} | ||
458 | </FormGroup> | ||
459 | </Col> | ||
460 | <Col xs={12} sm={4}> | ||
461 | <FormGroup controlId="parentZipcode"> | ||
462 | <Label required>Parent Zipcode</Label> | ||
463 | <FormControl | ||
464 | type="text" | ||
465 | value={props.getValue('parentZipcode')} | ||
466 | placeholder="600031" | ||
467 | onChange={e => props.setValue('parentZipcode', e.target.value)} | ||
468 | /> | ||
469 | {props.isSubmitted() && props.errors && props.errors.parentZipcode && ( | ||
470 | <ErrorLabel> {props.errors.parentZipcode} </ErrorLabel> | ||
471 | )} | ||
472 | </FormGroup> | ||
473 | </Col> | ||
474 | </Row> | ||
475 | </fieldset> | ||
476 | )} | ||
477 | <div style={{ textAlign: 'left' }}> | ||
478 | {props.currentStep > 0 && ( | ||
479 | <div style={{ display: 'inline-block', marginRight: 10 }}> | ||
480 | <Button onClick={props.onBackClick}> | ||
481 | <i className="icon-arrow-left13 position-left"></i> | ||
482 | BACK | ||
483 | </Button> | ||
484 | |||
485 | </div> | ||
486 | )} | ||
487 | {props.currentStep < 3 && ( | ||
488 | <div style={{ display: 'inline-block' }}> | ||
489 | <Button | ||
490 | bsStyle="primary" | ||
491 | onClick={props.onNextClick} | ||
492 | > | ||
493 | NEXT | ||
494 | <i className="icon-arrow-right14 position-right" /> | ||
495 | </Button> | ||
496 | </div> | ||
497 | )} | ||
498 | {props.currentStep === 3 && ( | ||
499 | <div style={{ display: 'inline-block' }}> | ||
500 | <Button | ||
501 | bsStyle="primary" | ||
502 | onClick={props.onNextClick} | ||
503 | > | ||
504 | SAVE | ||
505 | <i className="fa fa-check" /> | ||
506 | </Button> | ||
507 | </div> | ||
508 | )} | ||
509 | </div> | ||
510 | </div> | ||
511 | ) | ||
512 | |||
513 | StudentForm.propTypes = { | ||
514 | currentStep: PropTypes.number.isRequired, | ||
515 | onNextClick: PropTypes.func.isRequired, | ||
516 | onBackClick: PropTypes.func.isRequired, | ||
517 | setValue: PropTypes.func.isRequired, | ||
518 | getValue: PropTypes.func.isRequired, | ||
519 | } | ||
520 | |||
521 | export default StudentForm | ||
522 |
imports/client/views/org/admin/staff/add/addTeacher.js
File was created | 1 | import _ from 'lodash'; | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | import React, { Component } from 'react'; | ||
4 | import { Link,browserHistory } from 'react-router'; | ||
5 | import { FormGroup,Panel,Table, | ||
6 | ButtonToolbar,Modal, | ||
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
8 | import { AddStudentFormContainer } from './AddTeacherFormContainer'; | ||
9 | |||
10 | const style = { | ||
11 | margin: 12, | ||
12 | }; | ||
13 | export class AddTeacher extends Component { | ||
14 | constructor(props) { | ||
15 | super(props); | ||
16 | this.state = { | ||
17 | show: false | ||
18 | }; | ||
19 | this.showModal = this.showModal.bind(this); | ||
20 | this.hideModal = this.hideModal.bind(this); | ||
21 | this.onUpdate = this.onUpdate.bind(this); | ||
22 | }; | ||
23 | |||
24 | showModal() { | ||
25 | this.setState({show: true}); | ||
26 | } | ||
27 | |||
28 | hideModal() { | ||
29 | this.setState({show: false}); | ||
30 | } | ||
31 | onUpdate(key, value) { | ||
32 | this.setState({[key]: value}); | ||
33 | }; | ||
34 | |||
35 | render() { | ||
36 | return ( | ||
37 | <ButtonToolbar> | ||
38 | <Button bsStyle="primary" onClick={this.showModal}> | ||
39 | Add Student | ||
40 | </Button> | ||
41 | <Modal | ||
42 | {...this.props} | ||
43 | show={this.state.show} | ||
44 | onHide={this.hideModal} | ||
45 | dialogClassName="custom-modal" | ||
46 | bsSize="large" | ||
47 | > | ||
48 | <Modal.Header closeButton> | ||
49 | <Modal.Title id="contained-modal-title-lg">Add New Staff</Modal.Title> | ||
50 | </Modal.Header> | ||
51 | <Modal.Body> | ||
52 | <AddStudentFormContainer /> | ||
53 | </Modal.Body> | ||
54 | {/* | ||
55 | <Modal.Footer> | ||
56 | <Button onClick={this.hideModal}>Close</Button> | ||
57 | </Modal.Footer> | ||
58 | */} | ||
59 | </Modal> | ||
60 | </ButtonToolbar> | ||
61 | ); | ||
62 | }; | ||
63 | |||
64 | }; | ||
65 |
imports/client/views/org/admin/staff/index.js
File was created | 1 | // import { InviteSignupController } from '/imports/client/views/invite/signup/index' | |
2 | import _ from 'lodash'; | ||
3 | import { | ||
4 | composeWithTracker, | ||
5 | compose, | ||
6 | composeAll | ||
7 | } from 'react-komposer'; | ||
8 | import { Loading } from '/imports/client/components/Loading'; | ||
9 | |||
10 | import { Orgs } from '/imports/collections/orgs/index'; | ||
11 | import { Users } from '/imports/collections/users/index'; | ||
12 | import { Staffs } from '/imports/collections/staff/index'; | ||
13 | import { StaffView } from './StaffView'; | ||
14 | |||
15 | const meteorTick = (props, onData) => { | ||
16 | |||
17 | const handles = [ | ||
18 | Meteor.subscribe('users.current'), | ||
19 | Meteor.subscribe('orgs.current') | ||
20 | ]; | ||
21 | |||
22 | if(_.every(handles, (handle) => (handle.ready()) )) { | ||
23 | const user = Users.current(); | ||
24 | const org = Orgs.current(); | ||
25 | staff = Users.find({"role":"STAFF"}).fetch() ? Users.find({"role":"TEACHER"}).fetch() : ""; | ||
26 | staffData = Staffs.find().fetch() ? Staffs.find().fetch() : ""; | ||
27 | for(var i=0; i< staff.length; i++){ | ||
28 | for(var j=0; j< staff.length; j++){ | ||
29 | if(staff[i]._id == staffData[j].userId){ | ||
30 | staff[i].class = staffData[j].class; | ||
31 | staff[i].dob = staffData[j].dob; | ||
32 | } | ||
33 | } | ||
34 | } | ||
35 | onData(null, { | ||
36 | data: { | ||
37 | user: user, | ||
38 | org: org, | ||
39 | staff: staff | ||
40 | }, | ||
41 | }); | ||
42 | } | ||
43 | |||
44 | return () => { | ||
45 | _.each(handles, (handle) => handle.stop() ); | ||
46 | }; | ||
47 | }; | ||
48 | |||
49 | |||
50 | const reduxTick = (props, onData) => { | ||
51 | onData(null, { | ||
52 | data: {} | ||
53 | }); | ||
54 | }; | ||
55 | |||
56 | |||
57 | export const staffViewController = composeAll( | ||
58 | composeWithTracker(meteorTick, Loading), | ||
59 | compose(reduxTick, Loading), | ||
60 | )(StaffView); | ||
61 |
imports/client/views/org/admin/staff/view/StaffTable.js
File was created | 1 | import _ from 'lodash'; | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | |||
4 | import React, { Component } from 'react'; | ||
5 | import { Link,browserHistory } from 'react-router'; | ||
6 | import { FormGroup,Panel,Table, | ||
7 | ButtonToolbar,Modal, | ||
8 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
9 | import {moment} from 'meteor/momentjs:moment' | ||
10 | import {TeachersRow} from './TeachersRow' | ||
11 | |||
12 | export class StaffTable extends Component { | ||
13 | |||
14 | constructor(props) { | ||
15 | super(props); | ||
16 | this.state = { | ||
17 | show: false | ||
18 | }; | ||
19 | this.onUpdate = this.onUpdate.bind(this); | ||
20 | }; | ||
21 | onUpdate(key, value) { | ||
22 | this.setState({[key]: value}); | ||
23 | }; | ||
24 | |||
25 | render() { | ||
26 | return ( | ||
27 | <div className="panel panel-flat"> | ||
28 | <div className="panel-heading"> | ||
29 | <h5 className="panel-title">Teachers Details</h5> | ||
30 | <div className="heading-elements"> | ||
31 | <ul className="icons-list"> | ||
32 | <li><a data-action="collapse"></a></li> | ||
33 | <li><a data-action="reload"></a></li> | ||
34 | </ul> | ||
35 | </div> | ||
36 | </div> | ||
37 | <Table striped bordered condensed hover> | ||
38 | <thead> | ||
39 | <tr> | ||
40 | <th>First Name</th> | ||
41 | <th>Last Name</th> | ||
42 | <th>Class</th> | ||
43 | <th>DOB</th> | ||
44 | <th>Status</th> | ||
45 | <th className="text-center">Actions</th> | ||
46 | </tr> | ||
47 | </thead> | ||
48 | <tbody> | ||
49 | { | ||
50 | this.props.staff.map(function(student, i) | ||
51 | { | ||
52 | return( | ||
53 | <TeachersRow | ||
54 | teacher = {teacher} | ||
55 | /> | ||
56 | ) | ||
57 | }) | ||
58 | } | ||
59 | </tbody> | ||
60 | </Table> | ||
61 | </div> | ||
62 | ); | ||
63 | }; | ||
64 | |||
65 | }; | ||
66 |
imports/client/views/org/admin/staff/view/TeachersRow.js
File was created | 1 | import _ from 'lodash'; | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | |||
4 | import React, { Component } from 'react'; | ||
5 | import { Link,browserHistory } from 'react-router'; | ||
6 | import { FormGroup, | ||
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
8 | |||
9 | |||
10 | export class teachersRow extends Component { | ||
11 | |||
12 | constructor(props) { | ||
13 | super(props); | ||
14 | this.state = { | ||
15 | |||
16 | }; | ||
17 | this.onUpdate = this.onUpdate.bind(this); | ||
18 | }; | ||
19 | |||
20 | onUpdate(key, value) { | ||
21 | this.setState({[key]: value}); | ||
22 | }; | ||
23 | |||
24 | render() { | ||
25 | const {student} = this.props; | ||
26 | if(student.firstName){ | ||
27 | return ( | ||
28 | <tr> | ||
29 | <td>{student.firstName}</td> | ||
30 | <td>{student.lastName}</td> | ||
31 | <td>{student.class}</td> | ||
32 | <td>{student.dob? moment(student.dob).format("LL") : <span></span>}</td> | ||
33 | <td><span className="label label-success">Active</span></td> | ||
34 | <td className="text-center"> | ||
35 | <ul className="icons-list"> | ||
36 | <li className="dropdown"> | ||
37 | <a href="#" className="dropdown-toggle" data-toggle="dropdown"> | ||
38 | <i className="icon-menu9"></i> | ||
39 | </a> | ||
40 | <ul className="dropdown-menu dropdown-menu-right"> | ||
41 | <li><a href="#"><i className="icon-file-pdf"></i> Export to .pdf</a></li> | ||
42 | <li><a href="#"><i className="icon-file-excel"></i> Export to .csv</a></li> | ||
43 | <li><a href="#"><i className="icon-file-word"></i> Export to .doc</a></li> | ||
44 | </ul> | ||
45 | </li> | ||
46 | </ul> | ||
47 | </td> | ||
48 | </tr> | ||
49 | ); | ||
50 | }else { | ||
51 | return null; | ||
52 | } | ||
53 | |||
54 | }; | ||
55 | |||
56 | }; | ||
57 |
imports/client/views/org/admin/students/UploadCsv.js
1 | // import {UploadCsv } from '/imports/collections/students/UploadCsv' | 1 | // import {UploadCsv } from '/imports/collections/students/UploadCsv' |
2 | import _ from 'lodash'; | 2 | import _ from 'lodash'; |
3 | import { Meteor } from 'meteor/meteor'; | 3 | import { Meteor } from 'meteor/meteor'; |
4 | 4 | ||
5 | import React, { Component } from 'react'; | 5 | import React, { Component } from 'react'; |
6 | import { Link,browserHistory } from 'react-router'; | 6 | import { Link,browserHistory } from 'react-router'; |
7 | import { FormGroup,Panel,Table, | 7 | import { FormGroup,Panel,Table, |
8 | ButtonToolbar,Modal,ControlLabel,HelpBlock, | 8 | ButtonToolbar,Modal,ControlLabel,HelpBlock, |
9 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | 9 | FormControl,Glyphicon,Button } from 'react-bootstrap'; |
10 | // import { AddStudentForm } from './addStudentForm'; | 10 | // import { AddStudentForm } from './addStudentForm'; |
11 | import { FilesCollection } from 'meteor/ostrio:files'; | 11 | import { FilesCollection } from 'meteor/ostrio:files'; |
12 | const Papa = this.Papa; | 12 | const Papa = this.Papa; |
13 | // console.log(this); | 13 | // console.log(this); |
14 | const style = { | 14 | const style = { |
15 | margin: 12, | 15 | margin: 12, |
16 | }; | 16 | }; |
17 | function FieldGroup({ id, label, help, ...props }) { | 17 | function FieldGroup({ id, label, help, ...props }) { |
18 | return ( | 18 | return ( |
19 | <FormGroup controlId={id}> | 19 | <FormGroup controlId={id}> |
20 | <ControlLabel>{label}</ControlLabel> | 20 | <ControlLabel>{label}</ControlLabel> |
21 | <FormControl {...props} /> | 21 | <FormControl {...props} /> |
22 | {help && <HelpBlock>{help}</HelpBlock>} | 22 | {help && <HelpBlock>{help}</HelpBlock>} |
23 | </FormGroup> | 23 | </FormGroup> |
24 | ); | 24 | ); |
25 | } | 25 | } |
26 | export class UploadCsv extends Component { | 26 | export class UploadCsv extends Component { |
27 | constructor(props) { | 27 | constructor(props) { |
28 | super(props); | 28 | super(props); |
29 | this.state = { | 29 | this.state = { |
30 | show: false | 30 | show: false |
31 | }; | 31 | }; |
32 | this.showModal = this.showModal.bind(this); | 32 | this.showModal = this.showModal.bind(this); |
33 | this.hideModal = this.hideModal.bind(this); | 33 | this.hideModal = this.hideModal.bind(this); |
34 | this.onUpdate = this.onUpdate.bind(this); | 34 | this.onUpdate = this.onUpdate.bind(this); |
35 | }; | 35 | }; |
36 | 36 | ||
37 | showModal() { | 37 | showModal() { |
38 | this.setState({show: true}); | 38 | this.setState({show: true}); |
39 | } | 39 | } |
40 | 40 | ||
41 | hideModal() { | 41 | hideModal() { |
42 | this.setState({show: false}); | 42 | this.setState({show: false}); |
43 | } | 43 | } |
44 | onUpdate(key, value) { | 44 | onUpdate(key, value) { |
45 | this.setState({[key]: value}); | 45 | this.setState({[key]: value}); |
46 | }; | 46 | }; |
47 | uploadStudentCsv(e){ | 47 | uploadStudentCsv(e){ |
48 | e.preventDefault(); | 48 | e.preventDefault(); |
49 | e.persist(); | 49 | e.persist(); |
50 | var file = $('input[type="file"]').prop("files")[0]; | 50 | var file = $('input[type="file"]').prop("files")[0]; |
51 | Papa.parse(file, { | 51 | Papa.parse(file, { |
52 | header: true, | 52 | header: true, |
53 | complete: function(csvData) { | 53 | complete: function(csvData) { |
54 | console.log("csvData"); | 54 | console.log("csvData"); |
55 | console.log(csvData); | 55 | console.log(csvData); |
56 | if(csvData){ | 56 | if(csvData){ |
57 | Meteor.call('student.uploadCsv', csvData, function (error, result) { | 57 | Meteor.call('student.uploadCsv', csvData, function (error, result) { |
58 | console.log("error"); | 58 | console.log("error"); |
59 | console.log(error); | 59 | console.log(error); |
60 | console.log("result"); | 60 | console.log("result"); |
61 | console.log(result); | 61 | console.log(result); |
62 | }) | 62 | }) |
63 | } | 63 | } |
64 | } | 64 | } |
65 | }); | 65 | }); |
66 | } | 66 | } |
67 | 67 | ||
68 | render() { | 68 | render() { |
69 | console.log(this.props); | 69 | console.log(this.props); |
70 | return ( | 70 | return ( |
71 | <ButtonToolbar> | 71 | <ButtonToolbar> |
72 | <Button bsStyle="primary" onClick={this.showModal}> | 72 | <Button bsStyle="primary" onClick={this.showModal}> |
73 | Upload CSV | 73 | Upload CSV |
74 | </Button> | 74 | </Button> |
75 | <Modal | 75 | <Modal |
76 | {...this.props} | 76 | {...this.props} |
77 | show={this.state.show} | 77 | show={this.state.show} |
78 | onHide={this.hideModal} | 78 | onHide={this.hideModal} |
79 | dialogClassName="custom-modal" | 79 | dialogClassName="custom-modal" |
80 | > | 80 | > |
81 | <Modal.Header closeButton> | 81 | <Modal.Header closeButton> |
82 | <Modal.Title id="contained-modal-title-lg">New Student</Modal.Title> | 82 | <Modal.Title id="contained-modal-title-lg">Upload Csv file</Modal.Title> |
83 | </Modal.Header> | 83 | </Modal.Header> |
84 | <Modal.Body> | 84 | <Modal.Body> |
85 | <form onSubmit={ (e) => this.uploadStudentCsv(e) } > | 85 | <form onSubmit={ (e) => this.uploadStudentCsv(e) } > |
86 | <FieldGroup | 86 | <FieldGroup |
87 | id="formControlsFile" | 87 | id="formControlsFile" |
88 | type="file" | 88 | type="file" |
89 | label="File" | 89 | label="File" |
90 | help="Upload you CSV here." | 90 | help="Upload you CSV here." |
91 | /> | 91 | /> |
92 | <Button type="submit" bsStyle="default">Upload File</Button> | 92 | <Button type="submit" bsStyle="default">Upload File</Button> |
93 | </form> | 93 | </form> |
94 | </Modal.Body> | 94 | </Modal.Body> |
95 | <Modal.Footer> | 95 | <Modal.Footer> |
96 | <Button onClick={this.hideModal}>Close</Button> | 96 | <Button onClick={this.hideModal}>Close</Button> |
97 | </Modal.Footer> | 97 | </Modal.Footer> |
98 | </Modal> | 98 | </Modal> |
99 | </ButtonToolbar> | 99 | </ButtonToolbar> |
100 | ); | 100 | ); |
101 | }; | 101 | }; |
102 | 102 | ||
103 | }; | 103 | }; |
104 | 104 |
imports/client/views/org/admin/students/add/addStudent.js
1 | import _ from 'lodash'; | 1 | import _ from 'lodash'; |
2 | import { Meteor } from 'meteor/meteor'; | 2 | import { Meteor } from 'meteor/meteor'; |
3 | import React, { Component } from 'react'; | 3 | import React, { Component } from 'react'; |
4 | import { Link,browserHistory } from 'react-router'; | 4 | import { Link,browserHistory } from 'react-router'; |
5 | import { FormGroup,Panel,Table, | 5 | import { FormGroup,Panel,Table, |
6 | ButtonToolbar,Modal, | 6 | ButtonToolbar,Modal, |
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | 7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; |
8 | import { AddStudentFormContainer } from './AddStudentFormContainer'; | 8 | import { AddStudentFormContainer } from './AddStudentFormContainer'; |
9 | 9 | ||
10 | const style = { | 10 | const style = { |
11 | margin: 12, | 11 | margin: 12, |
12 | }; | 12 | }; |
13 | export class AddStudent extends Component { | 13 | export class AddStudent extends Component { |
14 | constructor(props) { | 14 | constructor(props) { |
15 | super(props); | 15 | super(props); |
16 | this.state = { | 16 | this.state = { |
17 | show: false | 17 | show: false |
18 | }; | 18 | }; |
19 | this.showModal = this.showModal.bind(this); | 19 | this.showModal = this.showModal.bind(this); |
20 | this.hideModal = this.hideModal.bind(this); | 20 | this.hideModal = this.hideModal.bind(this); |
21 | this.onUpdate = this.onUpdate.bind(this); | 21 | this.onUpdate = this.onUpdate.bind(this); |
22 | }; | 22 | }; |
23 | 23 | ||
24 | showModal() { | 24 | showModal() { |
25 | this.setState({show: true}); | 25 | this.setState({show: true}); |
26 | } | 26 | } |
27 | 27 | ||
28 | hideModal() { | 28 | hideModal() { |
29 | this.setState({show: false}); | 29 | this.setState({show: false}); |
30 | } | 30 | } |
31 | onUpdate(key, value) { | 31 | onUpdate(key, value) { |
32 | this.setState({[key]: value}); | 32 | this.setState({[key]: value}); |
33 | }; | 33 | }; |
34 | 34 | ||
35 | render() { | 35 | render() { |
36 | return ( | 36 | return ( |
37 | <ButtonToolbar> | 37 | <ButtonToolbar> |
38 | <Button bsStyle="primary" onClick={this.showModal}> | 38 | <Button bsStyle="primary" onClick={this.showModal}> |
39 | Add Student | 39 | Add Student |
40 | </Button> | 40 | </Button> |
41 | <Modal | 41 | <Modal |
42 | {...this.props} | 42 | {...this.props} |
43 | show={this.state.show} | 43 | show={this.state.show} |
44 | onHide={this.hideModal} | 44 | onHide={this.hideModal} |
45 | dialogClassName="custom-modal" | 45 | dialogClassName="custom-modal" |
46 | > | 46 | > |
47 | <Modal.Header closeButton> | 47 | <Modal.Header closeButton> |
48 | <Modal.Title id="contained-modal-title-lg">New Student</Modal.Title> | 48 | <Modal.Title id="contained-modal-title-lg">Add Student</Modal.Title> |
49 | </Modal.Header> | 49 | </Modal.Header> |
50 | <Modal.Body> | 50 | <Modal.Body> |
51 | <AddStudentFormContainer /> | 51 | <AddStudentFormContainer /> |
52 | </Modal.Body> | 52 | </Modal.Body> |
53 | {/* | 53 | {/* |
54 | <Modal.Footer> | 54 | <Modal.Footer> |
55 | <Button onClick={this.hideModal}>Close</Button> | 55 | <Button onClick={this.hideModal}>Close</Button> |
56 | </Modal.Footer> | 56 | </Modal.Footer> |
57 | */} | 57 | */} |
58 | </Modal> | 58 | </Modal> |
59 | </ButtonToolbar> | 59 | </ButtonToolbar> |
60 | ); | 60 | ); |
61 | }; | 61 | }; |
62 | 62 | ||
63 | }; | 63 | }; |
64 | 64 |
imports/client/views/org/admin/teachers/TeacherView.js
1 | import _ from 'lodash'; | File was deleted | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | |||
4 | import React, { Component } from 'react'; | ||
5 | import { Link,browserHistory } from 'react-router'; | ||
6 | import { FormGroup, | ||
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
8 | import { Header } from '../Header'; | ||
9 | import { AdminSidebar } from '../Sidebar' | ||
10 | import { AdminBreadcrumb } from '../Breadcrumb' | ||
11 | import { TeachersTable } from './view/TeachersTable' | ||
12 | import { AddTeacher } from './add/addTeacher' | ||
13 | import { UploadCsvTeacher } from './UploadCsvTeacher' | ||
14 | |||
15 | export class TeachersView extends Component { | ||
16 | constructor(props) { | ||
17 | super(props); | ||
18 | this.state = { | ||
19 | |||
20 | }; | ||
21 | this.onUpdate = this.onUpdate.bind(this); | ||
22 | }; | ||
23 | |||
24 | onUpdate(key, value) { | ||
25 | this.setState({[key]: value}); | ||
26 | }; | ||
27 | |||
28 | render() { | ||
29 | const {user, org, teachers, teachersData} = this.props.data; | ||
30 | return ( | ||
31 | <div className="appLayout-box"> | ||
32 | <div className="page-container"> | ||
33 | <div className="page-content"> | ||
34 | <AdminSidebar | ||
35 | user = {user} | ||
36 | org = {org} | ||
37 | /> | ||
38 | <div className="content-wrapper"> | ||
39 | <AdminBreadcrumb /> | ||
40 | |||
41 | <div className="content has-detached-left"> | ||
42 | <div className="container-detached"> | ||
43 | <div className="content-detached"> | ||
44 | <Header | ||
45 | user = {user} | ||
46 | org = {org} | ||
47 | /> | ||
48 | <TeachersTable | ||
49 | data = {this.props.data} | ||
50 | teachers = {teachers} | ||
51 | /> | ||
52 | <AddTeacher/> | ||
53 | <UploadCsvTeacher /> | ||
54 | </div> | ||
55 | </div> | ||
56 | <div className="sidebar-detached affix-top"> | ||
57 | <div className="sidebar sidebar-default"> | ||
58 | <div className="sidebar-content"> | ||
59 | |||
60 | <div className="sidebar-category"> | ||
61 | <div className="category-title"> | ||
62 | <span>Advanced Search</span> | ||
63 | <ul className="icons-list"> | ||
64 | <li><a href="#" data-action="collapse"></a></li> | ||
65 | </ul> | ||
66 | </div> | ||
67 | |||
68 | <div className="category-content"> | ||
69 | <form action="#"> | ||
70 | <div className="has-feedback has-feedback-left"> | ||
71 | <input type="search" className="form-control" | ||
72 | value={this.state.firstNameSearch} | ||
73 | onChange={e=>this.onUpdate('firstNameSearch',e.target.value)} | ||
74 | placeholder="First Name" | ||
75 | /> | ||
76 | <div className="form-control-feedback"> | ||
77 | <i className="icon-search4 text-size-base text-muted"></i> | ||
78 | </div> | ||
79 | </div> | ||
80 | </form> | ||
81 | </div> | ||
82 | <div className="category-content"> | ||
83 | <form action="#"> | ||
84 | <div className="has-feedback has-feedback-left"> | ||
85 | <input type="search" className="form-control" | ||
86 | value={this.state.lastNameSearch} | ||
87 | onChange={e=>this.onUpdate('lastNameSearch',e.target.value)} | ||
88 | placeholder="Last Name" /> | ||
89 | <div className="form-control-feedback"> | ||
90 | <i className="icon-search4 text-size-base text-muted"></i> | ||
91 | </div> | ||
92 | </div> | ||
93 | </form> | ||
94 | </div> | ||
95 | </div> | ||
96 | </div> | ||
97 | </div> | ||
98 | </div> | ||
99 | </div> | ||
100 | </div> | ||
101 | </div> | ||
102 | </div> | ||
103 | </div> | ||
104 | ); | ||
105 | }; | ||
106 | |||
107 | }; | ||
108 | 1 | import _ from 'lodash'; |
imports/client/views/org/admin/teachers/UploadCsvTeacher.js
1 | // import {UploadCsv } from '/imports/collections/students/UploadCsv' | File was deleted | |
2 | import _ from 'lodash'; | ||
3 | import { Meteor } from 'meteor/meteor'; | ||
4 | |||
5 | import React, { Component } from 'react'; | ||
6 | import { Link,browserHistory } from 'react-router'; | ||
7 | import { FormGroup,Panel,Table, | ||
8 | ButtonToolbar,Modal,ControlLabel,HelpBlock, | ||
9 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
10 | // import { AddStudentForm } from './addStudentForm'; | ||
11 | import { FilesCollection } from 'meteor/ostrio:files'; | ||
12 | const Papa = this.Papa; | ||
13 | // console.log(this); | ||
14 | const style = { | ||
15 | margin: 12, | ||
16 | }; | ||
17 | function FieldGroup({ id, label, help, ...props }) { | ||
18 | return ( | ||
19 | <FormGroup controlId={id}> | ||
20 | <ControlLabel>{label}</ControlLabel> | ||
21 | <FormControl {...props} /> | ||
22 | {help && <HelpBlock>{help}</HelpBlock>} | ||
23 | </FormGroup> | ||
24 | ); | ||
25 | } | ||
26 | export class UploadCsvTeacher extends Component { | ||
27 | constructor(props) { | ||
28 | super(props); | ||
29 | this.state = { | ||
30 | show: false | ||
31 | }; | ||
32 | this.showModal = this.showModal.bind(this); | ||
33 | this.hideModal = this.hideModal.bind(this); | ||
34 | this.onUpdate = this.onUpdate.bind(this); | ||
35 | }; | ||
36 | |||
37 | showModal() { | ||
38 | this.setState({show: true}); | ||
39 | } | ||
40 | |||
41 | hideModal() { | ||
42 | this.setState({show: false}); | ||
43 | } | ||
44 | onUpdate(key, value) { | ||
45 | this.setState({[key]: value}); | ||
46 | }; | ||
47 | uploadStudentCsv(e){ | ||
48 | e.preventDefault(); | ||
49 | e.persist(); | ||
50 | var file = $('input[type="file"]').prop("files")[0]; | ||
51 | Papa.parse(file, { | ||
52 | header: true, | ||
53 | complete: function(csvData) { | ||
54 | console.log("csvData"); | ||
55 | console.log(csvData); | ||
56 | if(csvData){ | ||
57 | Meteor.call('teachers.uploadCsv', csvData, function (error, result) { | ||
58 | console.log("error"); | ||
59 | console.log(error); | ||
60 | console.log("result"); | ||
61 | console.log(result); | ||
62 | }) | ||
63 | } | ||
64 | } | ||
65 | }); | ||
66 | } | ||
67 | |||
68 | render() { | ||
69 | console.log(this.props); | ||
70 | return ( | ||
71 | <ButtonToolbar> | ||
72 | <Button bsStyle="primary" onClick={this.showModal}> | ||
73 | Upload CSV | ||
74 | </Button> | ||
75 | <Modal | ||
76 | {...this.props} | ||
77 | show={this.state.show} | ||
78 | onHide={this.hideModal} | ||
79 | dialogClassName="custom-modal" | ||
80 | > | ||
81 | <Modal.Header closeButton> | ||
82 | <Modal.Title id="contained-modal-title-lg">New Student</Modal.Title> | ||
83 | </Modal.Header> | ||
84 | <Modal.Body> | ||
85 | <form onSubmit={ (e) => this.uploadStudentCsv(e) } > | ||
86 | <FieldGroup | ||
87 | id="formControlsFile" | ||
88 | type="file" | ||
89 | label="File" | ||
90 | help="Upload you CSV here." | ||
91 | /> | ||
92 | <Button type="submit" bsStyle="default">Upload File</Button> | ||
93 | </form> | ||
94 | </Modal.Body> | ||
95 | <Modal.Footer> | ||
96 | <Button onClick={this.hideModal}>Close</Button> | ||
97 | </Modal.Footer> | ||
98 | </Modal> | ||
99 | </ButtonToolbar> | ||
100 | ); | ||
101 | }; | ||
102 | |||
103 | }; | ||
104 | 1 | // import {UploadCsv } from '/imports/collections/students/UploadCsv' |
imports/client/views/org/admin/teachers/add/AddStudentFormContainer.js
1 | import React, { Component } from 'react' | File was deleted | |
2 | import { AddStudentForm } from './addStudentForm' | ||
3 | import StudentForm from './StudentForm' | ||
4 | import Form from '/imports/client/views/core/Form' | ||
5 | import Validator from '/imports/client/views/core/Validator' | ||
6 | import { isRequired, isValidEmail } from '/imports/client/views/core/validations' | ||
7 | import { addStudentManually } from '/imports/collections/students/methods'; | ||
8 | |||
9 | export class AddStudentFormContainer extends Component { | ||
10 | |||
11 | constructor(props) { | ||
12 | super(props) | ||
13 | this.state = { currentStep: 0 } | ||
14 | this.handleNextClick = this.handleNextClick.bind(this) | ||
15 | this.handleBackClick = this.handleBackClick.bind(this) | ||
16 | this.handleSubmit = this.handleSubmit.bind(this) | ||
17 | } | ||
18 | |||
19 | handleNextClick() { | ||
20 | this.form.handleSubmit() | ||
21 | if (this.validator.getErrors() && Object.keys(this.validator.getErrors()).length > 0) return | ||
22 | this.setState({ currentStep: this.state.currentStep + 1 }) | ||
23 | this.form.resetSubmitted() | ||
24 | } | ||
25 | |||
26 | handleBackClick() { | ||
27 | this.setState({ currentStep: this.state.currentStep + -1 }) | ||
28 | } | ||
29 | |||
30 | handleSubmit() { | ||
31 | if (this.state.currentStep === 3) { | ||
32 | addStudentManually.call(this.form.state.values) | ||
33 | } | ||
34 | } | ||
35 | |||
36 | //render callback | ||
37 | render() { | ||
38 | return ( | ||
39 | <Form | ||
40 | onSubmit={this.handleSubmit} | ||
41 | ref={form => this.form = form} | ||
42 | initialValues={{ | ||
43 | gender: 'male', | ||
44 | parentGender: 'male', | ||
45 | }} | ||
46 | > | ||
47 | {({ values, setValue, getValue, isSubmitted, isDirty }) => ( | ||
48 | <Validator | ||
49 | values={values} | ||
50 | ref={validator => this.validator = validator} | ||
51 | validations={{ | ||
52 | admissionId: [(value) => isRequired('Admission id', value)], | ||
53 | firstName: [(value) => isRequired('First name', value)], | ||
54 | lastName: [(value) => isRequired('Last name', value)], | ||
55 | email: [(value) => isRequired('Email', value), isValidEmail], | ||
56 | dob: [(value) => isRequired('Date of birth', value)], | ||
57 | gender: [(value) => isRequired('Gender', value)], | ||
58 | rollNo: [(value) => this.state.currentStep === 1 && isRequired('Roll no', value)], | ||
59 | studentClass: [(value) => this.state.currentStep === 1 && isRequired('Class', value)], | ||
60 | section: [(value) => this.state.currentStep === 1 && isRequired('Section', value)], | ||
61 | community: [(value) => this.state.currentStep === 1 && isRequired('Community', value)], | ||
62 | bloodGroup: [(value) => this.state.currentStep === 1 && isRequired('Blood group', value)], | ||
63 | phone: [(value) => this.state.currentStep === 1 && isRequired('Phone', value)], | ||
64 | address: [(value) => this.state.currentStep === 2 && isRequired('Address', value)], | ||
65 | city: [(value) => this.state.currentStep === 2 && isRequired('City', value)], | ||
66 | state: [(value) => this.state.currentStep === 2 && isRequired('State', value)], | ||
67 | parentName: [(value) => this.state.currentStep === 3 && isRequired('Parent name', value)], | ||
68 | parentEmail: [(value) => this.state.currentStep === 3 && isRequired('Parent email', value), (value) => this.state.currentStep === 3 && isValidEmail(value)], | ||
69 | relation: [(value) => this.state.currentStep === 3 && isRequired('Relation', value)], | ||
70 | profession: [(value) => this.state.currentStep === 3 && isRequired('Profession', value)], | ||
71 | parentGender: [(value) => this.state.currentStep === 3 && isRequired('Parent gender', value)], | ||
72 | parentPhone: [(value) => this.state.currentStep === 3 && isRequired('Parent phone', value)], | ||
73 | parentAddress: [(value) => this.state.currentStep === 3 && isRequired('Parent address', value)], | ||
74 | parentCity: [(value) => this.state.currentStep === 3 && isRequired('Parent city', value)], | ||
75 | parentState: [(value) => this.state.currentStep === 3 && isRequired('Parent state', value)], | ||
76 | parentZipcode: [(value) => this.state.currentStep === 3 && isRequired('Parent zip code', value)], | ||
77 | }} | ||
78 | > | ||
79 | {({ errors }) => ( | ||
80 | <StudentForm | ||
81 | isDirty={isDirty} | ||
82 | setValue={setValue} | ||
83 | getValue={getValue} | ||
84 | isSubmitted={isSubmitted} | ||
85 | errors={errors} | ||
86 | onNextClick={this.handleNextClick} | ||
87 | onBackClick={this.handleBackClick} | ||
88 | currentStep={this.state.currentStep} | ||
89 | /> | ||
90 | )} | ||
91 | </Validator> | ||
92 | )} | ||
93 | </Form> | ||
94 | ) | ||
95 | } | ||
96 | } | ||
97 | 1 | import React, { Component } from 'react' |
imports/client/views/org/admin/teachers/add/StudentForm.js
1 | import React, { PropTypes } from 'react' | File was deleted | |
2 | import { | ||
3 | Row, | ||
4 | Col, | ||
5 | FormGroup, | ||
6 | FormControl, | ||
7 | Button | ||
8 | } from 'react-bootstrap' | ||
9 | import DatePicker from '/imports/client/views/core/DatePicker' | ||
10 | import Label from '/imports/client/views/core/Label' | ||
11 | import Stepper from '/imports/client/views/core/Stepper' | ||
12 | import ErrorLabel from '/imports/client/views/core/ErrorLabel' | ||
13 | |||
14 | const StudentForm = props => ( | ||
15 | <div className="stepy-validation"> | ||
16 | <Stepper | ||
17 | steps={[ | ||
18 | { | ||
19 | label: 'Personal data', | ||
20 | active: props.currentStep === 0, | ||
21 | }, | ||
22 | { | ||
23 | label: 'Academic', | ||
24 | active: props.currentStep === 1, | ||
25 | }, | ||
26 | { | ||
27 | label: 'Address', | ||
28 | active: props.currentStep === 2, | ||
29 | }, | ||
30 | { | ||
31 | label: 'Parent info', | ||
32 | active: props.currentStep === 3, | ||
33 | } | ||
34 | ]} | ||
35 | /> | ||
36 | {props.currentStep === 0 && ( | ||
37 | <fieldset title="1"> | ||
38 | <legend className="text-semibold">Personal data</legend> | ||
39 | <Row> | ||
40 | <Col xs={12} sm={6}> | ||
41 | <FormGroup controlId="admissionId"> | ||
42 | <Label required>Admission Id</Label> | ||
43 | <FormControl | ||
44 | type="text" | ||
45 | value={props.getValue('admissionId')} | ||
46 | placeholder="admission Id" | ||
47 | onChange={e => props.setValue('admissionId', e.target.value)} | ||
48 | /> | ||
49 | {props.isSubmitted() && props.errors && props.errors.admissionId && ( | ||
50 | <ErrorLabel> {props.errors.admissionId} </ErrorLabel> | ||
51 | )} | ||
52 | </FormGroup> | ||
53 | </Col> | ||
54 | <Col xs={12} sm={6}> | ||
55 | <FormGroup controlId="firstName"> | ||
56 | <Label required>First Name</Label> | ||
57 | <FormControl | ||
58 | type="text" | ||
59 | value={props.getValue('firstName')} | ||
60 | placeholder="First Name" | ||
61 | onChange={e => props.setValue('firstName', e.target.value)} | ||
62 | /> | ||
63 | {props.isSubmitted() && props.errors && props.errors.firstName && ( | ||
64 | <ErrorLabel> {props.errors.firstName} </ErrorLabel> | ||
65 | )} | ||
66 | </FormGroup> | ||
67 | </Col> | ||
68 | </Row> | ||
69 | <Row> | ||
70 | <Col xs={12} sm={6}> | ||
71 | <FormGroup controlId="lastName"> | ||
72 | <Label required>Last Name</Label> | ||
73 | <FormControl | ||
74 | type="text" | ||
75 | value={props.getValue('lastName')} | ||
76 | placeholder="Last Name" | ||
77 | onChange={e => props.setValue('lastName', e.target.value)} | ||
78 | /> | ||
79 | {props.isSubmitted() && props.errors && props.errors.lastName && ( | ||
80 | <ErrorLabel> {props.errors.lastName} </ErrorLabel> | ||
81 | )} | ||
82 | </FormGroup> | ||
83 | </Col> | ||
84 | <Col xs={12} sm={6}> | ||
85 | <FormGroup controlId="formControlsSelect"> | ||
86 | <Label>Gender</Label> | ||
87 | <FormControl componentClass="select" | ||
88 | placeholder="select" | ||
89 | value={props.getValue('gender')} | ||
90 | onChange={e => props.setValue('gender', e.target.value)} | ||
91 | > | ||
92 | <option value="male">Male</option> | ||
93 | <option value="female">Female</option> | ||
94 | </FormControl> | ||
95 | {props.isSubmitted() && props.errors && props.errors.gender && ( | ||
96 | <ErrorLabel> {props.errors.gender} </ErrorLabel> | ||
97 | )} | ||
98 | </FormGroup> | ||
99 | </Col> | ||
100 | </Row> | ||
101 | <Row> | ||
102 | <Col xs={12} sm={6}> | ||
103 | <FormGroup controlId="email"> | ||
104 | <Label required>Email</Label> | ||
105 | <FormControl | ||
106 | type="email" | ||
107 | value={props.getValue('email')} | ||
108 | placeholder="Email" | ||
109 | onChange={e => props.setValue('email', e.target.value)} | ||
110 | /> | ||
111 | {props.isSubmitted() && props.errors && props.errors.email && ( | ||
112 | <ErrorLabel> {props.errors.email} </ErrorLabel> | ||
113 | )} | ||
114 | </FormGroup> | ||
115 | </Col> | ||
116 | <Col xs={12} sm={6}> | ||
117 | <FormGroup> | ||
118 | <Label required>Date of birth</Label> | ||
119 | <DatePicker | ||
120 | id="dob" | ||
121 | setValue = {props.setValue} | ||
122 | value={props.getValue('dob')} | ||
123 | onChange={(e) => { | ||
124 | props.setValue('dob', e.target.value) | ||
125 | }} | ||
126 | /> | ||
127 | {props.isSubmitted() && props.errors && props.errors.dob && ( | ||
128 | <ErrorLabel> {props.errors.dob} </ErrorLabel> | ||
129 | )} | ||
130 | </FormGroup> | ||
131 | </Col> | ||
132 | </Row> | ||
133 | <Row> | ||
134 | |||
135 | </Row> | ||
136 | </fieldset> | ||
137 | )} | ||
138 | {props.currentStep === 1 && ( | ||
139 | <fieldset title="Academic"> | ||
140 | <legend className="text-semibold">Academic</legend> | ||
141 | <Row> | ||
142 | <Col xs={12} sm={6}> | ||
143 | <FormGroup controlId="rollNo"> | ||
144 | <Label required>Roll No</Label> | ||
145 | <FormControl | ||
146 | type="text" | ||
147 | value={props.getValue('rollNo')} | ||
148 | placeholder="Roll No" | ||
149 | onChange={e => props.setValue('rollNo', e.target.value)} | ||
150 | /> | ||
151 | {props.isSubmitted() && props.errors && props.errors.rollNo && ( | ||
152 | <ErrorLabel> {props.errors.rollNo} </ErrorLabel> | ||
153 | )} | ||
154 | </FormGroup> | ||
155 | </Col> | ||
156 | <Col xs={12} sm={6}> | ||
157 | <FormGroup controlId="class"> | ||
158 | <Label required>Class</Label> | ||
159 | <FormControl | ||
160 | type="text" | ||
161 | value={props.getValue('studentClass')} | ||
162 | placeholder="7" | ||
163 | onChange={e => props.setValue('studentClass', e.target.value)} | ||
164 | /> | ||
165 | {props.isSubmitted() && props.errors && props.errors.studentClass && ( | ||
166 | <ErrorLabel> {props.errors.studentClass} </ErrorLabel> | ||
167 | )} | ||
168 | </FormGroup> | ||
169 | </Col> | ||
170 | </Row> | ||
171 | <Row> | ||
172 | <Col xs={12} sm={6}> | ||
173 | <FormGroup controlId="section"> | ||
174 | <Label required>Section</Label> | ||
175 | <FormControl | ||
176 | type="text" | ||
177 | value={props.getValue('section')} | ||
178 | placeholder="B" | ||
179 | onChange={e => props.setValue('section', e.target.value)} | ||
180 | /> | ||
181 | {props.isSubmitted() && props.errors && props.errors.section && ( | ||
182 | <ErrorLabel> {props.errors.section} </ErrorLabel> | ||
183 | )} | ||
184 | </FormGroup> | ||
185 | </Col> | ||
186 | <Col xs={12} sm={6}> | ||
187 | <FormGroup controlId="community"> | ||
188 | <Label required>Community</Label> | ||
189 | <FormControl | ||
190 | type="text" | ||
191 | value={props.getValue('community')} | ||
192 | placeholder="General" | ||
193 | onChange={e => props.setValue('community', e.target.value)} | ||
194 | /> | ||
195 | {props.isSubmitted() && props.errors && props.errors.community && ( | ||
196 | <ErrorLabel> {props.errors.community} </ErrorLabel> | ||
197 | )} | ||
198 | </FormGroup> | ||
199 | </Col> | ||
200 | </Row> | ||
201 | <Row> | ||
202 | <Col xs={12} sm={6}> | ||
203 | <FormGroup controlId="bloodGroup"> | ||
204 | <Label required>bloodGroup</Label> | ||
205 | <FormControl | ||
206 | type="text" | ||
207 | value={props.getValue('bloodGroup')} | ||
208 | placeholder="B+" | ||
209 | onChange={e => props.setValue('bloodGroup', e.target.value)} | ||
210 | /> | ||
211 | {props.isSubmitted() && props.errors && props.errors.bloodGroup && ( | ||
212 | <ErrorLabel> {props.errors.bloodGroup} </ErrorLabel> | ||
213 | )} | ||
214 | </FormGroup> | ||
215 | </Col> | ||
216 | <Col xs={12} sm={6}> | ||
217 | <FormGroup controlId="phone"> | ||
218 | <Label required>Phone</Label> | ||
219 | <FormControl | ||
220 | type="text" | ||
221 | value={props.getValue('phone')} | ||
222 | placeholder="9999999999" | ||
223 | onChange={e => props.setValue('phone', e.target.value)} | ||
224 | /> | ||
225 | {props.isSubmitted() && props.errors && props.errors.phone && ( | ||
226 | <ErrorLabel> {props.errors.phone} </ErrorLabel> | ||
227 | )} | ||
228 | </FormGroup> | ||
229 | </Col> | ||
230 | </Row> | ||
231 | </fieldset> | ||
232 | )} | ||
233 | {props.currentStep === 2 && ( | ||
234 | <fieldset title="Address"> | ||
235 | <legend className="text-semibold">Address</legend> | ||
236 | <Row> | ||
237 | <Col xs={12} sm={6}> | ||
238 | <FormGroup controlId="address"> | ||
239 | <Label required>Address</Label> | ||
240 | <FormControl | ||
241 | type="text" | ||
242 | value={props.getValue('address')} | ||
243 | placeholder="#876, Street, town" | ||
244 | onChange={e => props.setValue('address', e.target.value)} | ||
245 | /> | ||
246 | {props.isSubmitted() && props.errors && props.errors.address && ( | ||
247 | <ErrorLabel> {props.errors.address} </ErrorLabel> | ||
248 | )} | ||
249 | </FormGroup> | ||
250 | </Col> | ||
251 | <Col xs={12} sm={6}> | ||
252 | <FormGroup controlId="city"> | ||
253 | <Label required>City</Label> | ||
254 | <FormControl | ||
255 | type="text" | ||
256 | value={props.getValue('city')} | ||
257 | placeholder="Chennai" | ||
258 | onChange={e => props.setValue('city', e.target.value)} | ||
259 | /> | ||
260 | {props.isSubmitted() && props.errors && props.errors.city && ( | ||
261 | <ErrorLabel> {props.errors.city} </ErrorLabel> | ||
262 | )} | ||
263 | </FormGroup> | ||
264 | </Col> | ||
265 | </Row> | ||
266 | <Row> | ||
267 | <Col xs={12} sm={6}> | ||
268 | <FormGroup controlId="state"> | ||
269 | <Label required>State</Label> | ||
270 | <FormControl | ||
271 | type="text" | ||
272 | value={props.getValue('state')} | ||
273 | placeholder="Tamilnadu" | ||
274 | onChange={e => props.setValue('state', e.target.value)} | ||
275 | /> | ||
276 | {props.isSubmitted() && props.errors && props.errors.state && ( | ||
277 | <ErrorLabel> {props.errors.state} </ErrorLabel> | ||
278 | )} | ||
279 | </FormGroup> | ||
280 | </Col> | ||
281 | </Row> | ||
282 | </fieldset> | ||
283 | )} | ||
284 | {props.currentStep === 3 && ( | ||
285 | <fieldset title="2"> | ||
286 | <legend className="text-semibold">Parent information</legend> | ||
287 | <Row> | ||
288 | <Col xs={12} sm={6}> | ||
289 | <FormGroup controlId="parentName"> | ||
290 | <Label required>Parent Name</Label> | ||
291 | <FormControl | ||
292 | type="text" | ||
293 | value={props.getValue('parentName')} | ||
294 | placeholder="John" | ||
295 | onChange={e => props.setValue('parentName', e.target.value)} | ||
296 | /> | ||
297 | {props.isSubmitted() && props.errors && props.errors.parentName && ( | ||
298 | <ErrorLabel> {props.errors.parentName} </ErrorLabel> | ||
299 | )} | ||
300 | </FormGroup> | ||
301 | </Col> | ||
302 | <Col xs={12} sm={6}> | ||
303 | <FormGroup controlId="parentEmail"> | ||
304 | <Label required>Parent Email</Label> | ||
305 | <FormControl | ||
306 | type="text" | ||
307 | value={props.getValue('parentEmail')} | ||
308 | placeholder="john@email.com" | ||
309 | onChange={e => props.setValue('parentEmail', e.target.value)} | ||
310 | /> | ||
311 | {props.isSubmitted() && props.errors && props.errors.parentEmail && ( | ||
312 | <ErrorLabel> {props.errors.parentEmail} </ErrorLabel> | ||
313 | )} | ||
314 | </FormGroup> | ||
315 | </Col> | ||
316 | </Row> | ||
317 | <Row> | ||
318 | <Col xs={12} sm={6}> | ||
319 | <FormGroup controlId="relation"> | ||
320 | <Label required>Relation</Label> | ||
321 | <FormControl | ||
322 | type="text" | ||
323 | value={props.getValue('relation')} | ||
324 | placeholder="Father" | ||
325 | onChange={e => props.setValue('relation', e.target.value)} | ||
326 | /> | ||
327 | {props.isSubmitted() && props.errors && props.errors.relation && ( | ||
328 | <ErrorLabel> {props.errors.relation} </ErrorLabel> | ||
329 | )} | ||
330 | </FormGroup> | ||
331 | </Col> | ||
332 | <Col xs={12} sm={6}> | ||
333 | <FormGroup controlId="profession"> | ||
334 | <Label required>Profession</Label> | ||
335 | <FormControl | ||
336 | type="text" | ||
337 | value={props.getValue('profession')} | ||
338 | placeholder="Farmer" | ||
339 | onChange={e => props.setValue('profession', e.target.value)} | ||
340 | /> | ||
341 | {props.isSubmitted() && props.errors && props.errors.profession && ( | ||
342 | <ErrorLabel> {props.errors.profession} </ErrorLabel> | ||
343 | )} | ||
344 | </FormGroup> | ||
345 | </Col> | ||
346 | </Row> | ||
347 | <Row> | ||
348 | <Col xs={12} sm={6}> | ||
349 | <FormGroup controlId="parentGender"> | ||
350 | <Label>Parent Gender</Label> | ||
351 | <FormControl componentClass="select" | ||
352 | placeholder="select" | ||
353 | value={props.getValue('parentGender')} | ||
354 | onChange={e => props.setValue('parentGender', e.target.value)} | ||
355 | > | ||
356 | <option value="male">Male</option> | ||
357 | <option value="female">Female</option> | ||
358 | </FormControl> | ||
359 | {props.isSubmitted() && props.errors && props.errors.parentGender && ( | ||
360 | <ErrorLabel> {props.errors.parentGender} </ErrorLabel> | ||
361 | )} | ||
362 | </FormGroup> | ||
363 | </Col> | ||
364 | <Col xs={12} sm={6}> | ||
365 | <FormGroup controlId="parentPhone"> | ||
366 | <Label required>Parent Phone</Label> | ||
367 | <FormControl | ||
368 | type="text" | ||
369 | value={props.getValue('parentPhone')} | ||
370 | placeholder="9876543210" | ||
371 | onChange={e => props.setValue('parentPhone', e.target.value)} | ||
372 | /> | ||
373 | {props.isSubmitted() && props.errors && props.errors.parentPhone && ( | ||
374 | <ErrorLabel> {props.errors.parentPhone} </ErrorLabel> | ||
375 | )} | ||
376 | </FormGroup> | ||
377 | </Col> | ||
378 | </Row> | ||
379 | <Row> | ||
380 | <Col xs={12} sm={6}> | ||
381 | <FormGroup controlId="parentAddress"> | ||
382 | <Label required>Parent Address</Label> | ||
383 | <FormControl | ||
384 | type="text" | ||
385 | value={props.getValue('parentAddress')} | ||
386 | placeholder="#12, street, town" | ||
387 | onChange={e => props.setValue('parentAddress', e.target.value)} | ||
388 | /> | ||
389 | {props.isSubmitted() && props.errors && props.errors.parentAddress && ( | ||
390 | <ErrorLabel> {props.errors.parentAddress} </ErrorLabel> | ||
391 | )} | ||
392 | </FormGroup> | ||
393 | </Col> | ||
394 | <Col xs={12} sm={6}> | ||
395 | <FormGroup controlId="parentCity"> | ||
396 | <Label required>Parent City</Label> | ||
397 | <FormControl | ||
398 | type="text" | ||
399 | value={props.getValue('parentCity')} | ||
400 | placeholder="Chennai" | ||
401 | onChange={e => props.setValue('parentCity', e.target.value)} | ||
402 | /> | ||
403 | {props.isSubmitted() && props.errors && props.errors.parentCity && ( | ||
404 | <ErrorLabel> {props.errors.parentCity} </ErrorLabel> | ||
405 | )} | ||
406 | </FormGroup> | ||
407 | </Col> | ||
408 | </Row> | ||
409 | <Row> | ||
410 | <Col xs={12} sm={6}> | ||
411 | <FormGroup controlId="parentState"> | ||
412 | <Label required>Parent State</Label> | ||
413 | <FormControl | ||
414 | type="text" | ||
415 | value={props.getValue('parentState')} | ||
416 | placeholder="600031" | ||
417 | onChange={e => props.setValue('parentState', e.target.value)} | ||
418 | /> | ||
419 | {props.isSubmitted() && props.errors && props.errors.parentState && ( | ||
420 | <ErrorLabel> {props.errors.parentState} </ErrorLabel> | ||
421 | )} | ||
422 | </FormGroup> | ||
423 | </Col> | ||
424 | <Col xs={12} sm={6}> | ||
425 | <FormGroup controlId="parentZipcode"> | ||
426 | <Label required>Parent Zipcode</Label> | ||
427 | <FormControl | ||
428 | type="text" | ||
429 | value={props.getValue('parentZipcode')} | ||
430 | placeholder="600031" | ||
431 | onChange={e => props.setValue('parentZipcode', e.target.value)} | ||
432 | /> | ||
433 | {props.isSubmitted() && props.errors && props.errors.parentZipcode && ( | ||
434 | <ErrorLabel> {props.errors.parentZipcode} </ErrorLabel> | ||
435 | )} | ||
436 | </FormGroup> | ||
437 | </Col> | ||
438 | </Row> | ||
439 | </fieldset> | ||
440 | )} | ||
441 | <div style={{ textAlign: 'left' }}> | ||
442 | {props.currentStep > 0 && ( | ||
443 | <div style={{ display: 'inline-block', marginRight: 10 }}> | ||
444 | <Button onClick={props.onBackClick}> | ||
445 | <i className="icon-arrow-left13 position-left"></i> | ||
446 | BACK | ||
447 | </Button> | ||
448 | |||
449 | </div> | ||
450 | )} | ||
451 | {props.currentStep < 3 && ( | ||
452 | <div style={{ display: 'inline-block' }}> | ||
453 | <Button | ||
454 | bsStyle="primary" | ||
455 | onClick={props.onNextClick} | ||
456 | > | ||
457 | NEXT | ||
458 | <i className="icon-arrow-right14 position-right" /> | ||
459 | </Button> | ||
460 | </div> | ||
461 | )} | ||
462 | {props.currentStep === 3 && ( | ||
463 | <div style={{ display: 'inline-block' }}> | ||
464 | <Button | ||
465 | bsStyle="primary" | ||
466 | onClick={props.onNextClick} | ||
467 | > | ||
468 | SAVE | ||
469 | <i className="fa fa-check" /> | ||
470 | </Button> | ||
471 | </div> | ||
472 | )} | ||
473 | </div> | ||
474 | </div> | ||
475 | ) | ||
476 | |||
477 | StudentForm.propTypes = { | ||
478 | currentStep: PropTypes.number.isRequired, | ||
479 | onNextClick: PropTypes.func.isRequired, | ||
480 | onBackClick: PropTypes.func.isRequired, | ||
481 | setValue: PropTypes.func.isRequired, | ||
482 | getValue: PropTypes.func.isRequired, | ||
483 | } | ||
484 | |||
485 | export default StudentForm | ||
486 | 1 | import React, { PropTypes } from 'react' |
imports/client/views/org/admin/teachers/add/addStudentForm.js
1 | import _ from 'lodash'; | File was deleted | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | |||
4 | import React, { Component } from 'react'; | ||
5 | import { Link,browserHistory } from 'react-router'; | ||
6 | import { Form, FormGroup,InputGroup, | ||
7 | DropdownButton,MenuItem,ControlLabel, | ||
8 | SplitButton, | ||
9 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
10 | import DatePicker from 'react-bootstrap-date-picker' | ||
11 | import {addStudentManually} from '/imports/collections/students/methods'; | ||
12 | |||
13 | export class AddStudentForm extends Component { | ||
14 | |||
15 | constructor(props) { | ||
16 | super(props); | ||
17 | this.state = { | ||
18 | admissionId: "123", | ||
19 | firstName: "first", | ||
20 | lastName: "last", | ||
21 | middleName: "middle", | ||
22 | email: "deepak125.dk+21@gmail.com", | ||
23 | dob: "", | ||
24 | formattedDob: "", | ||
25 | gender: "male", | ||
26 | rollNo: "1", | ||
27 | class: "2", | ||
28 | section: "B", | ||
29 | community: "SC", | ||
30 | bloodGroup: "B+", | ||
31 | phone: "9876543321", | ||
32 | address: "address", | ||
33 | city: "chennai", | ||
34 | state: "tn", | ||
35 | parentName: "parentName", | ||
36 | parentEmail: "deepak125.dk+41@gmail.com", | ||
37 | relation: "father", | ||
38 | profession: "farmer", | ||
39 | parentGender: "male", | ||
40 | parentPhone: "987655412", | ||
41 | parentAddress: "parentAddress", | ||
42 | parentCity: "parentCity", | ||
43 | parentState: "parentState", | ||
44 | parentZipcode: "parentZipcode", | ||
45 | }; | ||
46 | this.onUpdate = this.onUpdate.bind(this); | ||
47 | this.handleDob = this.handleDob.bind(this); | ||
48 | }; | ||
49 | |||
50 | onUpdate(key, value) { | ||
51 | this.setState({[key]: value}); | ||
52 | }; | ||
53 | |||
54 | handleDob(value, formattedValue) { | ||
55 | this.setState({ | ||
56 | dob: value, // ISO String, ex: "2016-11-19T12:00:00.000Z" | ||
57 | formattedDob: formattedValue // Formatted String, ex: "11/19/2016" | ||
58 | }); | ||
59 | } | ||
60 | addStudent(e){ | ||
61 | e.preventDefault(); | ||
62 | e.persist(); | ||
63 | const firstName = this.state.firstName; | ||
64 | const middleName = this.state.middleName; | ||
65 | const lastName = this.state.lastName; | ||
66 | const admissionId = this.state.admissionId; | ||
67 | const email = this.state.email; | ||
68 | const dob = this.state.dob; | ||
69 | const formattedDob = this.state.formattedDob; | ||
70 | const gender = this.state.gender; | ||
71 | const rollNo = this.state.rollNo; | ||
72 | const studentclass = this.state.class; | ||
73 | const section = this.state.section; | ||
74 | const community = this.state.community; | ||
75 | const bloodGroup = this.state.bloodGroup; | ||
76 | const phone = this.state.phone; | ||
77 | const address = this.state.address; | ||
78 | const city = this.state.city; | ||
79 | const state = this.state.state; | ||
80 | const parentName = this.state.parentName; | ||
81 | const parentEmail = this.state.parentEmail; | ||
82 | const relation = this.state.relation; | ||
83 | const profession = this.state.profession; | ||
84 | const parentGender = this.state.parentGender; | ||
85 | const parentPhone = this.state.parentPhone; | ||
86 | const parentAddress = this.state.parentAddress; | ||
87 | const parentCity = this.state.parentCity; | ||
88 | const parentState = this.state.parentState; | ||
89 | const parentZipcode = this.state.parentZipcode; | ||
90 | if(admissionId==""){ | ||
91 | Bert.alert('Enter Admission Id!', 'danger'); | ||
92 | }else if(firstName==""){ | ||
93 | Bert.alert('Enter Fist Name', 'danger'); | ||
94 | } else if(middleName==""){ | ||
95 | Bert.alert('Enter Middle name!', 'danger'); | ||
96 | }else if(lastName==""){ | ||
97 | Bert.alert('Enter Last name!', 'danger'); | ||
98 | }else if(email==""){ | ||
99 | Bert.alert('Enter email!', 'danger'); | ||
100 | }else if(dob==""){ | ||
101 | Bert.alert('Enter DOB!', 'danger'); | ||
102 | }else if(gender==""){ | ||
103 | Bert.alert('Enter Student Gender!', 'danger'); | ||
104 | }else if(studentclass==""){ | ||
105 | Bert.alert('Enter Class!', 'danger'); | ||
106 | }else if(section==""){ | ||
107 | Bert.alert('Enter Section!', 'danger'); | ||
108 | }else if(community==""){ | ||
109 | Bert.alert('Enter Section!', 'danger'); | ||
110 | }else if(bloodGroup==""){ | ||
111 | Bert.alert('Enter Blood Group!', 'danger'); | ||
112 | }else if(phone==""){ | ||
113 | Bert.alert('Enter phone!', 'danger'); | ||
114 | }else if(address==""){ | ||
115 | Bert.alert('Enter address!', 'danger'); | ||
116 | }else if(city==""){ | ||
117 | Bert.alert('Enter city!', 'danger'); | ||
118 | }else if(state==""){ | ||
119 | Bert.alert('Enter state!', 'danger'); | ||
120 | }else if(parentName==""){ | ||
121 | Bert.alert('Enter Parent name!', 'danger'); | ||
122 | }else if(parentEmail==""){ | ||
123 | Bert.alert('Enter Parent Email!', 'danger'); | ||
124 | }else if(relation==""){ | ||
125 | Bert.alert('Enter relation!', 'danger'); | ||
126 | }else if(profession==""){ | ||
127 | Bert.alert('Enter parent profession!', 'danger'); | ||
128 | }else if(parentGender==""){ | ||
129 | Bert.alert("Enter Parent's Gender!", 'danger'); | ||
130 | }else if(parentPhone==""){ | ||
131 | Bert.alert("Enter Parent's Phone!", 'danger'); | ||
132 | }else if(parentAddress==""){ | ||
133 | Bert.alert("Enter Parent's Address!", 'danger'); | ||
134 | }else if(parentCity==""){ | ||
135 | Bert.alert("Enter Parent's City!", 'danger'); | ||
136 | }else if(parentState==""){ | ||
137 | Bert.alert("Enter Parent's State!", 'danger'); | ||
138 | }else if(parentZipcode==""){ | ||
139 | Bert.alert("Enter Parent's zipcode!", 'danger'); | ||
140 | }else{ | ||
141 | addStudentManually.call({ | ||
142 | admissionId, | ||
143 | firstName, | ||
144 | middleName, | ||
145 | lastName, | ||
146 | email, | ||
147 | dob, | ||
148 | formattedDob, | ||
149 | gender, | ||
150 | rollNo, | ||
151 | studentclass, | ||
152 | section, | ||
153 | community, | ||
154 | bloodGroup, | ||
155 | phone, | ||
156 | address, | ||
157 | city, | ||
158 | state, | ||
159 | parentName, | ||
160 | parentEmail, | ||
161 | relation, | ||
162 | profession, | ||
163 | parentGender, | ||
164 | parentPhone, | ||
165 | parentAddress, | ||
166 | parentCity, | ||
167 | parentState, | ||
168 | parentZipcode | ||
169 | }, function (error, result) { | ||
170 | console.log(error); | ||
171 | console.log(result); | ||
172 | }); | ||
173 | } | ||
174 | } | ||
175 | render() { | ||
176 | return ( | ||
177 | <Form className="steps-validation wizard clearfix" onSubmit={ (e) => this.addStudent(e) } inline> | ||
178 | <div className="steps clearfix"> | ||
179 | <ul role="tablist"> | ||
180 | <li role="tab" className="first current" aria-disabled="false" aria-selected="true"> | ||
181 | <a id="steps-uid-4-t-0" href="#steps-uid-4-h-0" aria-controls="steps-uid-4-p-0"> | ||
182 | <span className="current-info audible">current step: </span><span className="number">1</span> Personal data | ||
183 | </a> | ||
184 | </li> | ||
185 | <li role="tab" className="disabled" aria-disabled="true"> | ||
186 | <a id="steps-uid-4-t-1" href="#steps-uid-4-h-1" aria-controls="steps-uid-4-p-1"> | ||
187 | <span className="number">2</span> Your education\n\ | ||
188 | </a> | ||
189 | </li> | ||
190 | <li role="tab" className="disabled" aria-disabled="true"> | ||
191 | <a id="steps-uid-4-t-2" href="#steps-uid-4-h-2" aria-controls="steps-uid-4-p-2"> | ||
192 | <span className="number">3</span> Your experience | ||
193 | </a> | ||
194 | </li> | ||
195 | <li role="tab" className="disabled last" aria-disabled="true"> | ||
196 | <a id="steps-uid-4-t-3" href="#steps-uid-4-h-3" aria-controls="steps-uid-4-p-3"> | ||
197 | <span className="number">4</span> Additional info | ||
198 | </a> | ||
199 | </li> | ||
200 | </ul> | ||
201 | </div> | ||
202 | <div className="content clearfix"> | ||
203 | <h6 id="steps-uid-4-h-0" tabindex="-1" className="title current">Personal data</h6> | ||
204 | <div id="steps-uid-4-p-0" role="tabpanel" aria-labelledby="steps-uid-4-h-0" className="body current"> | ||
205 | <div className="row"> | ||
206 | <div className="col-md-6"> | ||
207 | |||
208 | <FormGroup controlId="admissionId"> | ||
209 | <ControlLabel>Admission Id</ControlLabel> | ||
210 | <FormControl | ||
211 | type="text" | ||
212 | value={this.state.admissionId} | ||
213 | placeholder="admission Id" | ||
214 | onChange={e=>this.onUpdate('admissionId',e.target.value)} | ||
215 | /> | ||
216 | </FormGroup> | ||
217 | |||
218 | </div> | ||
219 | |||
220 | <div className="col-md-6"> | ||
221 | |||
222 | <FormGroup controlId="firstName"> | ||
223 | <ControlLabel>First Name</ControlLabel> | ||
224 | <FormControl | ||
225 | type="text" | ||
226 | value={this.state.firstName} | ||
227 | placeholder="First Name" | ||
228 | onChange={e=>this.onUpdate('firstName',e.target.value)} | ||
229 | /> | ||
230 | </FormGroup> | ||
231 | |||
232 | </div> | ||
233 | </div> | ||
234 | </div> | ||
235 | </div> | ||
236 | |||
237 | |||
238 | <FormGroup controlId="admissionId"> | ||
239 | <ControlLabel>Admission Id</ControlLabel> | ||
240 | <FormControl | ||
241 | type="text" | ||
242 | value={this.state.admissionId} | ||
243 | placeholder="admission Id" | ||
244 | onChange={e=>this.onUpdate('admissionId',e.target.value)} | ||
245 | /> | ||
246 | </FormGroup> | ||
247 | |||
248 | <FormGroup controlId="firstName"> | ||
249 | <ControlLabel>First Name</ControlLabel> | ||
250 | <FormControl | ||
251 | type="text" | ||
252 | value={this.state.firstName} | ||
253 | placeholder="First Name" | ||
254 | onChange={e=>this.onUpdate('firstName',e.target.value)} | ||
255 | /> | ||
256 | </FormGroup> | ||
257 | <FormGroup controlId="middleName"> | ||
258 | <ControlLabel>Middle Name</ControlLabel> | ||
259 | <FormControl | ||
260 | type="text" | ||
261 | value={this.state.middleName} | ||
262 | placeholder="Middle Name" | ||
263 | onChange={e=>this.onUpdate('middleName',e.target.value)} | ||
264 | /> | ||
265 | </FormGroup> | ||
266 | |||
267 | <FormGroup controlId="lastName"> | ||
268 | <ControlLabel>Last Name</ControlLabel> | ||
269 | <FormControl | ||
270 | type="text" | ||
271 | value={this.state.lastName} | ||
272 | placeholder="Last Name" | ||
273 | onChange={e=>this.onUpdate('lastName',e.target.value)} | ||
274 | /> | ||
275 | |||
276 | </FormGroup> | ||
277 | <FormGroup controlId="email"> | ||
278 | <ControlLabel>Email</ControlLabel> | ||
279 | <FormControl | ||
280 | type="email" | ||
281 | value={this.state.email} | ||
282 | placeholder="Email" | ||
283 | onChange={e=>this.onUpdate('email',e.target.value)} | ||
284 | /> | ||
285 | </FormGroup> | ||
286 | <FormGroup> | ||
287 | <ControlLabel>Date of birth</ControlLabel> | ||
288 | <DatePicker id="dob" | ||
289 | value={this.state.dob} | ||
290 | onChange={this.handleDob} | ||
291 | /> | ||
292 | </FormGroup> | ||
293 | |||
294 | <FormGroup controlId="formControlsSelect"> | ||
295 | <ControlLabel>Gender</ControlLabel> | ||
296 | <FormControl componentClass="select" | ||
297 | placeholder="select" | ||
298 | value={this.state.gender} | ||
299 | onChange={e=>this.onUpdate('gender',e.target.value)} | ||
300 | > | ||
301 | <option value="male">Male</option> | ||
302 | <option value="female">Female</option> | ||
303 | </FormControl> | ||
304 | </FormGroup> | ||
305 | |||
306 | <FormGroup controlId="rollNo"> | ||
307 | <ControlLabel>Roll No</ControlLabel> | ||
308 | <FormControl | ||
309 | type="text" | ||
310 | value={this.state.rollNo} | ||
311 | placeholder="Roll No" | ||
312 | onChange={e=>this.onUpdate('rollNo',e.target.value)} | ||
313 | /> | ||
314 | </FormGroup> | ||
315 | <FormGroup controlId="class"> | ||
316 | <ControlLabel>Class</ControlLabel> | ||
317 | <FormControl | ||
318 | type="text" | ||
319 | value={this.state.class} | ||
320 | placeholder="7" | ||
321 | onChange={e=>this.onUpdate('class',e.target.value)} | ||
322 | /> | ||
323 | </FormGroup> | ||
324 | <FormGroup controlId="section"> | ||
325 | <ControlLabel>Section</ControlLabel> | ||
326 | <FormControl | ||
327 | type="text" | ||
328 | value={this.state.section} | ||
329 | placeholder="B" | ||
330 | onChange={e=>this.onUpdate('section',e.target.value)} | ||
331 | /> | ||
332 | </FormGroup> | ||
333 | |||
334 | <FormGroup controlId="community"> | ||
335 | <ControlLabel>Community</ControlLabel> | ||
336 | <FormControl | ||
337 | type="text" | ||
338 | value={this.state.community} | ||
339 | placeholder="General" | ||
340 | onChange={e=>this.onUpdate('community',e.target.value)} | ||
341 | /> | ||
342 | </FormGroup> | ||
343 | |||
344 | <FormGroup controlId="bloodGroup"> | ||
345 | <ControlLabel>bloodGroup</ControlLabel> | ||
346 | <FormControl | ||
347 | type="text" | ||
348 | value={this.state.bloodGroup} | ||
349 | placeholder="B+" | ||
350 | onChange={e=>this.onUpdate('bloodGroup',e.target.value)} | ||
351 | /> | ||
352 | </FormGroup> | ||
353 | |||
354 | <FormGroup controlId="phone"> | ||
355 | <ControlLabel>Phone</ControlLabel> | ||
356 | <FormControl | ||
357 | type="text" | ||
358 | value={this.state.phone} | ||
359 | placeholder="9999999999" | ||
360 | onChange={e=>this.onUpdate('phone',e.target.value)} | ||
361 | /> | ||
362 | </FormGroup> | ||
363 | |||
364 | <FormGroup controlId="address"> | ||
365 | <ControlLabel>Address</ControlLabel> | ||
366 | <FormControl | ||
367 | type="text" | ||
368 | value={this.state.address} | ||
369 | placeholder="#876, Street, town" | ||
370 | onChange={e=>this.onUpdate('address',e.target.value)} | ||
371 | /> | ||
372 | </FormGroup> | ||
373 | |||
374 | <FormGroup controlId="city"> | ||
375 | <ControlLabel>City</ControlLabel> | ||
376 | <FormControl | ||
377 | type="text" | ||
378 | value={this.state.city} | ||
379 | placeholder="Chennai" | ||
380 | onChange={e=>this.onUpdate('city',e.target.value)} | ||
381 | /> | ||
382 | </FormGroup> | ||
383 | |||
384 | <FormGroup controlId="state"> | ||
385 | <ControlLabel>State</ControlLabel> | ||
386 | <FormControl | ||
387 | type="text" | ||
388 | value={this.state.state} | ||
389 | placeholder="Tamilnadu" | ||
390 | onChange={e=>this.onUpdate('state',e.target.value)} | ||
391 | /> | ||
392 | </FormGroup> | ||
393 | |||
394 | <FormGroup controlId="parentName"> | ||
395 | <ControlLabel>Parent Name</ControlLabel> | ||
396 | <FormControl | ||
397 | type="text" | ||
398 | value={this.state.parentName} | ||
399 | placeholder="John" | ||
400 | onChange={e=>this.onUpdate('parentName',e.target.value)} | ||
401 | /> | ||
402 | </FormGroup> | ||
403 | |||
404 | <FormGroup controlId="parentEmail"> | ||
405 | <ControlLabel>Parent Email</ControlLabel> | ||
406 | <FormControl | ||
407 | type="text" | ||
408 | value={this.state.parentEmail} | ||
409 | placeholder="john@email.com" | ||
410 | onChange={e=>this.onUpdate('parentEmail',e.target.value)} | ||
411 | /> | ||
412 | </FormGroup> | ||
413 | |||
414 | <FormGroup controlId="relation"> | ||
415 | <ControlLabel>Relation</ControlLabel> | ||
416 | <FormControl | ||
417 | type="text" | ||
418 | value={this.state.relation} | ||
419 | placeholder="Father" | ||
420 | onChange={e=>this.onUpdate('relation',e.target.value)} | ||
421 | /> | ||
422 | </FormGroup> | ||
423 | |||
424 | <FormGroup controlId="profession"> | ||
425 | <ControlLabel>Profession</ControlLabel> | ||
426 | <FormControl | ||
427 | type="text" | ||
428 | value={this.state.profession} | ||
429 | placeholder="Farmer" | ||
430 | onChange={e=>this.onUpdate('profession',e.target.value)} | ||
431 | /> | ||
432 | </FormGroup> | ||
433 | |||
434 | <FormGroup controlId="parentGender"> | ||
435 | <ControlLabel>Parent Gender</ControlLabel> | ||
436 | <FormControl componentClass="select" | ||
437 | placeholder="select" | ||
438 | value={this.state.parentGender} | ||
439 | onChange={e=>this.onUpdate('parentGender',e.target.value)} | ||
440 | > | ||
441 | <option value="male">Male</option> | ||
442 | <option value="female">Female</option> | ||
443 | </FormControl> | ||
444 | </FormGroup> | ||
445 | |||
446 | <FormGroup controlId="parentPhone"> | ||
447 | <ControlLabel>Parent Phone</ControlLabel> | ||
448 | <FormControl | ||
449 | type="text" | ||
450 | value={this.state.parentPhone} | ||
451 | placeholder="9876543210" | ||
452 | onChange={e=>this.onUpdate('parentPhone',e.target.value)} | ||
453 | /> | ||
454 | </FormGroup> | ||
455 | |||
456 | <FormGroup controlId="parentAddress"> | ||
457 | <ControlLabel>Parent Address</ControlLabel> | ||
458 | <FormControl | ||
459 | type="text" | ||
460 | value={this.state.parentAddress} | ||
461 | placeholder="#12, street, town" | ||
462 | onChange={e=>this.onUpdate('parentAddress',e.target.value)} | ||
463 | /> | ||
464 | </FormGroup> | ||
465 | |||
466 | <FormGroup controlId="parentCity"> | ||
467 | <ControlLabel>Parent City</ControlLabel> | ||
468 | <FormControl | ||
469 | type="text" | ||
470 | value={this.state.parentCity} | ||
471 | placeholder="Chennai" | ||
472 | onChange={e=>this.onUpdate('parentCity',e.target.value)} | ||
473 | /> | ||
474 | </FormGroup> | ||
475 | |||
476 | <FormGroup controlId="parentState"> | ||
477 | <ControlLabel>Parent State</ControlLabel> | ||
478 | <FormControl | ||
479 | type="text" | ||
480 | value={this.state.parentState} | ||
481 | placeholder="Tamilnadu" | ||
482 | onChange={e=>this.onUpdate('parentState',e.target.value)} | ||
483 | /> | ||
484 | </FormGroup> | ||
485 | |||
486 | <FormGroup controlId="parentZipcode"> | ||
487 | <ControlLabel>Parent Zipcode</ControlLabel> | ||
488 | <FormControl | ||
489 | type="text" | ||
490 | value={this.state.parentZipcode} | ||
491 | placeholder="600031" | ||
492 | onChange={e=>this.onUpdate('parentZipcode',e.target.value)} | ||
493 | /> | ||
494 | </FormGroup> | ||
495 | <Button type="submit" bsStyle="default">Add Student</Button> | ||
496 | </Form> | ||
497 | ); | ||
498 | }; | ||
499 | |||
500 | }; | ||
501 | 1 | import _ from 'lodash'; |
imports/client/views/org/admin/teachers/add/addTeacher.js
1 | import _ from 'lodash'; | File was deleted | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | import React, { Component } from 'react'; | ||
4 | import { Link,browserHistory } from 'react-router'; | ||
5 | import { FormGroup,Panel,Table, | ||
6 | ButtonToolbar,Modal, | ||
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
8 | import { AddStudentFormContainer } from './AddStudentFormContainer'; | ||
9 | |||
10 | const style = { | ||
11 | margin: 12, | ||
12 | }; | ||
13 | export class AddTeacher extends Component { | ||
14 | constructor(props) { | ||
15 | super(props); | ||
16 | this.state = { | ||
17 | show: false | ||
18 | }; | ||
19 | this.showModal = this.showModal.bind(this); | ||
20 | this.hideModal = this.hideModal.bind(this); | ||
21 | this.onUpdate = this.onUpdate.bind(this); | ||
22 | }; | ||
23 | |||
24 | showModal() { | ||
25 | this.setState({show: true}); | ||
26 | } | ||
27 | |||
28 | hideModal() { | ||
29 | this.setState({show: false}); | ||
30 | } | ||
31 | onUpdate(key, value) { | ||
32 | this.setState({[key]: value}); | ||
33 | }; | ||
34 | |||
35 | render() { | ||
36 | return ( | ||
37 | <ButtonToolbar> | ||
38 | <Button bsStyle="primary" onClick={this.showModal}> | ||
39 | Add Student | ||
40 | </Button> | ||
41 | <Modal | ||
42 | {...this.props} | ||
43 | show={this.state.show} | ||
44 | onHide={this.hideModal} | ||
45 | dialogClassName="custom-modal" | ||
46 | > | ||
47 | <Modal.Header closeButton> | ||
48 | <Modal.Title id="contained-modal-title-lg">New Student</Modal.Title> | ||
49 | </Modal.Header> | ||
50 | <Modal.Body> | ||
51 | <AddStudentFormContainer /> | ||
52 | </Modal.Body> | ||
53 | {/* | ||
54 | <Modal.Footer> | ||
55 | <Button onClick={this.hideModal}>Close</Button> | ||
56 | </Modal.Footer> | ||
57 | */} | ||
58 | </Modal> | ||
59 | </ButtonToolbar> | ||
60 | ); | ||
61 | }; | ||
62 | |||
63 | }; | ||
64 | 1 | import _ from 'lodash'; |
imports/client/views/org/admin/teachers/index.js
1 | // import { InviteSignupController } from '/imports/client/views/invite/signup/index' | File was deleted | |
2 | import _ from 'lodash'; | ||
3 | import { | ||
4 | composeWithTracker, | ||
5 | compose, | ||
6 | composeAll | ||
7 | } from 'react-komposer'; | ||
8 | import { Loading } from '/imports/client/components/Loading'; | ||
9 | |||
10 | import { Orgs } from '/imports/collections/orgs/index'; | ||
11 | import { Users } from '/imports/collections/users/index'; | ||
12 | import { Teachers } from '/imports/collections/teachers/index'; | ||
13 | import { TeachersView } from './TeacherView'; | ||
14 | |||
15 | const meteorTick = (props, onData) => { | ||
16 | |||
17 | const handles = [ | ||
18 | Meteor.subscribe('users.current'), | ||
19 | Meteor.subscribe('orgs.current') | ||
20 | ]; | ||
21 | |||
22 | if(_.every(handles, (handle) => (handle.ready()) )) { | ||
23 | const user = Users.current(); | ||
24 | const org = Orgs.current(); | ||
25 | teachers = Users.find({"role":"TEACHER"}).fetch() ? Users.find({"role":"TEACHER"}).fetch() : ""; | ||
26 | teachersData = Teachers.find().fetch() ? Teachers.find().fetch() : ""; | ||
27 | for(var i=0; i< teachers.length; i++){ | ||
28 | for(var j=0; j< teachers.length; j++){ | ||
29 | if(teachers[i]._id == teachersData[j].userId){ | ||
30 | teachers[i].class = teachersData[j].class; | ||
31 | teachers[i].dob = teachersData[j].dob; | ||
32 | } | ||
33 | } | ||
34 | } | ||
35 | onData(null, { | ||
36 | data: { | ||
37 | user: user, | ||
38 | org: org, | ||
39 | teachersData: teachersData, | ||
40 | teachers: teachers | ||
41 | }, | ||
42 | }); | ||
43 | } | ||
44 | |||
45 | return () => { | ||
46 | _.each(handles, (handle) => handle.stop() ); | ||
47 | }; | ||
48 | }; | ||
49 | |||
50 | |||
51 | const reduxTick = (props, onData) => { | ||
52 | onData(null, { | ||
53 | data: {} | ||
54 | }); | ||
55 | }; | ||
56 | |||
57 | |||
58 | export const teachersViewController = composeAll( | ||
59 | composeWithTracker(meteorTick, Loading), | ||
60 | compose(reduxTick, Loading), | ||
61 | )(TeachersView); | ||
62 | 1 | // import { InviteSignupController } from '/imports/client/views/invite/signup/index' |
imports/client/views/org/admin/teachers/view/TeachersRow.js
1 | import _ from 'lodash'; | File was deleted | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | |||
4 | import React, { Component } from 'react'; | ||
5 | import { Link,browserHistory } from 'react-router'; | ||
6 | import { FormGroup, | ||
7 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
8 | |||
9 | |||
10 | export class teachersRow extends Component { | ||
11 | |||
12 | constructor(props) { | ||
13 | super(props); | ||
14 | this.state = { | ||
15 | |||
16 | }; | ||
17 | this.onUpdate = this.onUpdate.bind(this); | ||
18 | }; | ||
19 | |||
20 | onUpdate(key, value) { | ||
21 | this.setState({[key]: value}); | ||
22 | }; | ||
23 | |||
24 | render() { | ||
25 | const {student} = this.props; | ||
26 | if(student.firstName){ | ||
27 | return ( | ||
28 | <tr> | ||
29 | <td>{student.firstName}</td> | ||
30 | <td>{student.lastName}</td> | ||
31 | <td>{student.class}</td> | ||
32 | <td>{student.dob? moment(student.dob).format("LL") : <span></span>}</td> | ||
33 | <td><span className="label label-success">Active</span></td> | ||
34 | <td className="text-center"> | ||
35 | <ul className="icons-list"> | ||
36 | <li className="dropdown"> | ||
37 | <a href="#" className="dropdown-toggle" data-toggle="dropdown"> | ||
38 | <i className="icon-menu9"></i> | ||
39 | </a> | ||
40 | <ul className="dropdown-menu dropdown-menu-right"> | ||
41 | <li><a href="#"><i className="icon-file-pdf"></i> Export to .pdf</a></li> | ||
42 | <li><a href="#"><i className="icon-file-excel"></i> Export to .csv</a></li> | ||
43 | <li><a href="#"><i className="icon-file-word"></i> Export to .doc</a></li> | ||
44 | </ul> | ||
45 | </li> | ||
46 | </ul> | ||
47 | </td> | ||
48 | </tr> | ||
49 | ); | ||
50 | }else { | ||
51 | return null; | ||
52 | } | ||
53 | |||
54 | }; | ||
55 | |||
56 | }; | ||
57 | 1 | import _ from 'lodash'; |
imports/client/views/org/admin/teachers/view/TeachersTable.js
1 | import _ from 'lodash'; | File was deleted | |
2 | import { Meteor } from 'meteor/meteor'; | ||
3 | |||
4 | import React, { Component } from 'react'; | ||
5 | import { Link,browserHistory } from 'react-router'; | ||
6 | import { FormGroup,Panel,Table, | ||
7 | ButtonToolbar,Modal, | ||
8 | FormControl,Glyphicon,Button } from 'react-bootstrap'; | ||
9 | import {moment} from 'meteor/momentjs:moment' | ||
10 | import {TeachersRow} from './TeachersRow' | ||
11 | |||
12 | export class TeachersTable extends Component { | ||
13 | |||
14 | constructor(props) { | ||
15 | super(props); | ||
16 | this.state = { | ||
17 | show: false | ||
18 | }; | ||
19 | this.onUpdate = this.onUpdate.bind(this); | ||
20 | }; | ||
21 | onUpdate(key, value) { | ||
22 | this.setState({[key]: value}); | ||
23 | }; | ||
24 | |||
25 | render() { | ||
26 | return ( | ||
27 | <div className="panel panel-flat"> | ||
28 | <div className="panel-heading"> | ||
29 | <h5 className="panel-title">Teachers Details</h5> | ||
30 | <div className="heading-elements"> | ||
31 | <ul className="icons-list"> | ||
32 | <li><a data-action="collapse"></a></li> | ||
33 | <li><a data-action="reload"></a></li> | ||
34 | </ul> | ||
35 | </div> | ||
36 | </div> | ||
37 | <Table striped bordered condensed hover> | ||
38 | <thead> | ||
39 | <tr> | ||
40 | <th>First Name</th> | ||
41 | <th>Last Name</th> | ||
42 | <th>Class</th> | ||
43 | <th>DOB</th> | ||
44 | <th>Status</th> | ||
45 | <th className="text-center">Actions</th> | ||
46 | </tr> | ||
47 | </thead> | ||
48 | <tbody> | ||
49 | { | ||
50 | this.props.teachers.map(function(student, i) | ||
51 | { | ||
52 | return( | ||
53 | <TeachersRow | ||
54 | teacher = {teacher} | ||
55 | /> | ||
56 | ) | ||
57 | }) | ||
58 | } | ||
59 | </tbody> | ||
60 | </Table> | ||
61 | </div> | ||
62 | ); | ||
63 | }; | ||
64 | |||
65 | }; | ||
66 | 1 | import _ from 'lodash'; |
imports/collections/staff/index.js
File was created | 1 | // import {Staffs } from '/imports/collections/staff/index' | |
2 | |||
3 | import _ from 'lodash'; | ||
4 | import { Meteor } from 'meteor/meteor'; | ||
5 | import { Mongo } from 'meteor/mongo'; | ||
6 | import { SimpleSchema } from 'meteor/aldeed:simple-schema'; | ||
7 | |||
8 | import { Orgs } from '/imports/collections/orgs/index'; | ||
9 | import { Users } from '/imports/collections/users/index'; | ||
10 | |||
11 | class Staff { | ||
12 | constructor(doc) { | ||
13 | _.assign(this, doc); | ||
14 | }; | ||
15 | |||
16 | getUserIds() { | ||
17 | return _.filter(_.map(this.users, 'userId')); | ||
18 | }; | ||
19 | }; | ||
20 | export { Staff }; | ||
21 | |||
22 | class StaffsCollection extends Mongo.Collection { | ||
23 | insert(item, callback) { | ||
24 | _.assign(item, { | ||
25 | createdAt: new Date().getTime(), | ||
26 | }); | ||
27 | return super.insert(item, callback); | ||
28 | }; | ||
29 | }; | ||
30 | |||
31 | export const Staffs = new StaffsCollection('Teachers', { | ||
32 | transform: (item) => { | ||
33 | return new Staff(item); | ||
34 | }, | ||
35 | }); | ||
36 | |||
37 | _.assign(Staffs, { | ||
38 | allStaffs: () => { | ||
39 | const user = Users.current(); | ||
40 | if(!user) return null; | ||
41 | return Orgs.find({'users.userId': user._id}); | ||
42 | }, | ||
43 | current: () => { | ||
44 | const user = Users.current(); | ||
45 | if(!user) return null; | ||
46 | return Orgs.findOne({_id: user.orgId}); | ||
47 | }, | ||
48 | currentOrgUsers: () => { | ||
49 | const OrgsArr = Orgs.current(); | ||
50 | if(!OrgsArr) return null; | ||
51 | return OrgsArr.users; | ||
52 | }, | ||
53 | |||
54 | }); | ||
55 | |||
56 | Staffs.deny({ | ||
57 | insert() { return true; }, | ||
58 | update() { return true; }, | ||
59 | remove() { return true; }, | ||
60 | }); | ||
61 | |||
62 | |||
63 | Staffs.schema = new SimpleSchema({ | ||
64 | userId: { type: String }, | ||
65 | orgId: { type: String }, | ||
66 | type: { type: String }, | ||
67 | gender: { type: String, optional: true }, | ||
68 | services: { | ||
69 | type: Object, | ||
70 | optional: true, | ||
71 | blackbox: true, | ||
72 | }, | ||
73 | |||
74 | isMetaUser: { type: Boolean, optional: true }, | ||
75 | |||
76 | createdAt: { type: Date, autoValue: function(){return new Date();}} | ||
77 | |||
78 | }); | ||
79 | |||
80 | Staffs.attachSchema(Staffs.schema); | ||
81 | |||
82 | Staffs.privateFields = { | ||
83 | orgId: 1, | ||
84 | address: 1, | ||
85 | |||
86 | isMetaUser: 1, | ||
87 | createdAt: 1, | ||
88 | }; | ||
89 | |||
90 | Staffs.publicFields = { | ||
91 | firstName: 1, | ||
92 | lastName: 1, | ||
93 | emails: 1, | ||
94 | |||
95 | createdAt: 1, | ||
96 | }; | ||
97 |
imports/collections/staff/methods.js
File was created | 1 | // import {Parents } from '/imports/collections/parents/methods' | |
2 | import _ from 'lodash'; | ||
3 | import { Meteor } from 'meteor/meteor'; | ||
4 | import { ValidatedMethod } from 'meteor/mdg:validated-method'; | ||
5 | import { SimpleSchema } from 'meteor/aldeed:simple-schema'; | ||
6 | import { DDPRateLimiter } from 'meteor/ddp-rate-limiter'; | ||
7 | import { Bert } from 'meteor/themeteorchef:bert'; | ||
8 | import { Users } from '/imports/collections/users/index'; | ||
9 | import { Teachers } from '/imports/collections/staff/index'; | ||
10 | import { Orgs } from '/imports/collections/orgs/index'; | ||
11 | export const teachersMethods = new ValidatedMethod({ | ||
12 | name: 'teachers.method', | ||
13 | |||
14 | validate: new SimpleSchema({ | ||
15 | itemId: { type: String }, | ||
16 | }).validator(), | ||
17 | |||
18 | run({itemId}) { | ||
19 | return {}; | ||
20 | }, | ||
21 | |||
22 | }); | ||
23 |
imports/collections/staff/publications.js
File was created | 1 | import { Meteor } from 'meteor/meteor'; | |
2 | import { check, Match } from 'meteor/check' | ||
3 | |||
4 | import { Orgs } from '/imports/collections/orgs/index'; | ||
5 | import { Users } from '/imports/collections/users/index'; | ||
6 | import { Teachers } from '/imports/collections/staff/index'; | ||
7 | |||
8 | Meteor.publish('teachers.forMyOrg', function () { | ||
9 | const user = Users.findOne({_id: this.userId}); | ||
10 | if(!user) return []; | ||
11 | return Teachers.find({orgId: user.orgId}); | ||
12 | }); | ||
13 |
imports/collections/teachers/index.js
1 | // import {Parents } from '/imports/collections/parents/index' | File was deleted | |
2 | |||
3 | import _ from 'lodash'; | ||
4 | import { Meteor } from 'meteor/meteor'; | ||
5 | import { Mongo } from 'meteor/mongo'; | ||
6 | import { SimpleSchema } from 'meteor/aldeed:simple-schema'; | ||
7 | |||
8 | import { Orgs } from '/imports/collections/orgs/index'; | ||
9 | import { Users } from '/imports/collections/users/index'; | ||
10 | |||
11 | class Teacher { | ||
12 | constructor(doc) { | ||
13 | _.assign(this, doc); | ||
14 | }; | ||
15 | |||
16 | getUserIds() { | ||
17 | return _.filter(_.map(this.users, 'userId')); | ||
18 | }; | ||
19 | }; | ||
20 | export { Teacher }; | ||
21 | |||
22 | class TeachersCollection extends Mongo.Collection { | ||
23 | insert(item, callback) { | ||
24 | _.assign(item, { | ||
25 | createdAt: new Date().getTime(), | ||
26 | }); | ||
27 | return super.insert(item, callback); | ||
28 | }; | ||
29 | }; | ||
30 | |||
31 | export const Teachers = new TeachersCollection('Teachers', { | ||
32 | transform: (item) => { | ||
33 | return new Teacher(item); | ||
34 | }, | ||
35 | }); | ||
36 | |||
37 | _.assign(Teachers, { | ||
38 | allStudents: () => { | ||
39 | const user = Users.current(); | ||
40 | if(!user) return null; | ||
41 | return Orgs.find({'users.userId': user._id}); | ||
42 | }, | ||
43 | current: () => { | ||
44 | const user = Users.current(); | ||
45 | if(!user) return null; | ||
46 | return Orgs.findOne({_id: user.orgId}); | ||
47 | }, | ||
48 | currentOrgUsers: () => { | ||
49 | const OrgsArr = Orgs.current(); | ||
50 | if(!OrgsArr) return null; | ||
51 | return OrgsArr.users; | ||
52 | }, | ||
53 | |||
54 | }); | ||
55 | |||
56 | Teachers.deny({ | ||
57 | insert() { return true; }, | ||
58 | update() { return true; }, | ||
59 | remove() { return true; }, | ||
60 | }); | ||
61 | |||
62 | |||
63 | Teachers.schema = new SimpleSchema({ | ||
64 | userId: { type: String }, | ||
65 | orgId: { type: String }, | ||
66 | type: { type: String }, | ||
67 | gender: { type: String, optional: true }, | ||
68 | services: { | ||
69 | type: Object, | ||
70 | optional: true, | ||
71 | blackbox: true, | ||
72 | }, | ||
73 | |||
74 | isMetaUser: { type: Boolean, optional: true }, | ||
75 | |||
76 | createdAt: { type: Date, autoValue: function(){return new Date();}} | ||
77 | |||
78 | }); | ||
79 | |||
80 | Teachers.attachSchema(Teachers.schema); | ||
81 | |||
82 | Teachers.privateFields = { | ||
83 | orgId: 1, | ||
84 | address: 1, | ||
85 | |||
86 | isMetaUser: 1, | ||
87 | createdAt: 1, | ||
88 | }; | ||
89 | |||
90 | Teachers.publicFields = { | ||
91 | firstName: 1, | ||
92 | lastName: 1, | ||
93 | emails: 1, | ||
94 | |||
95 | createdAt: 1, | ||
96 | }; | ||
97 | 1 | // import {Parents } from '/imports/collections/parents/index' |
imports/collections/teachers/methods.js
1 | // import {Parents } from '/imports/collections/parents/methods' | File was deleted | |
2 | import _ from 'lodash'; | ||
3 | import { Meteor } from 'meteor/meteor'; | ||
4 | import { ValidatedMethod } from 'meteor/mdg:validated-method'; | ||
5 | import { SimpleSchema } from 'meteor/aldeed:simple-schema'; | ||
6 | import { DDPRateLimiter } from 'meteor/ddp-rate-limiter'; | ||
7 | import { Bert } from 'meteor/themeteorchef:bert'; | ||
8 | import { Users } from '/imports/collections/users/index'; | ||
9 | import { Teachers } from '/imports/collections/teachers/index'; | ||
10 | import { Orgs } from '/imports/collections/orgs/index'; | ||
11 | export const teachersMethods = new ValidatedMethod({ | ||
12 | name: 'teachers.method', | ||
13 | |||
14 | validate: new SimpleSchema({ | ||
15 | itemId: { type: String }, | ||
16 | }).validator(), | ||
17 | |||
18 | run({itemId}) { | ||
19 | return {}; | ||
20 | }, | ||
21 | |||
22 | }); | ||
23 | 1 | // import {Parents } from '/imports/collections/parents/methods' |
imports/collections/teachers/publications.js
1 | import { Meteor } from 'meteor/meteor'; | File was deleted | |
2 | import { check, Match } from 'meteor/check' | ||
3 | |||
4 | import { Orgs } from '/imports/collections/orgs/index'; | ||
5 | import { Users } from '/imports/collections/users/index'; | ||
6 | import { Teachers } from '/imports/collections/teachers/index'; | ||
7 | |||
8 | Meteor.publish('teachers.forMyOrg', function () { | ||
9 | const user = Users.findOne({_id: this.userId}); | ||
10 | if(!user) return []; | ||
11 | return Teachers.find({orgId: user.orgId}); | ||
12 | }); | ||
13 | 1 | import { Meteor } from 'meteor/meteor'; |
imports/collections/users/index.js
1 | // import { Users } from '/imports/collections/users/index'; | 1 | // import { Users } from '/imports/collections/users/index'; |
2 | // import { Users } from '/imports/collections/users/index'; | 2 | // import { Users } from '/imports/collections/users/index'; |
3 | 3 | ||
4 | import _ from 'lodash'; | 4 | import _ from 'lodash'; |
5 | import { Meteor } from 'meteor/meteor'; | 5 | import { Meteor } from 'meteor/meteor'; |
6 | import { Mongo } from 'meteor/mongo'; | 6 | import { Mongo } from 'meteor/mongo'; |
7 | import { SimpleSchema } from 'meteor/aldeed:simple-schema'; | 7 | import { SimpleSchema } from 'meteor/aldeed:simple-schema'; |
8 | 8 | ||
9 | import { Orgs } from '/imports/collections/orgs/index'; | 9 | import { Orgs } from '/imports/collections/orgs/index'; |
10 | 10 | ||
11 | class User { | 11 | class User { |
12 | 12 | ||
13 | constructor(doc) { | 13 | constructor(doc) { |
14 | _.assign(this, doc); | 14 | _.assign(this, doc); |
15 | }; | 15 | }; |
16 | 16 | ||
17 | isEmailVerified() { | 17 | isEmailVerified() { |
18 | return !! _.find(this.emails, x => x.verified); | 18 | return !! _.find(this.emails, x => x.verified); |
19 | }; | 19 | }; |
20 | 20 | ||
21 | isPhoneVerified() { | 21 | isPhoneVerified() { |
22 | return !! _.find(this.phones, x => x.verified); | 22 | return !! _.find(this.phones, x => x.verified); |
23 | }; | 23 | }; |
24 | 24 | ||
25 | isIdentityVerified() { | 25 | isIdentityVerified() { |
26 | return !! _.find(this.identities, x => x.verified); | 26 | return !! _.find(this.identities, x => x.verified); |
27 | }; | 27 | }; |
28 | 28 | ||
29 | getRole() { | 29 | getRole() { |
30 | const org = Orgs.findOne({_id: this.orgId}); | 30 | const org = Orgs.findOne({_id: this.orgId}); |
31 | if(!org) return null; | 31 | if(!org) return null; |
32 | const connection = _.find(org.users, {userId: this._id}); | 32 | const connection = _.find(org.users, {userId: this._id}); |
33 | if(!connection) return null; | 33 | if(!connection) return null; |
34 | return connection.role; | 34 | return connection.role; |
35 | }; | 35 | }; |
36 | 36 | ||
37 | getFullName() { | 37 | getFullName() { |
38 | return `${this.firstName} ${this.lastName}`; | 38 | return `${this.firstName} ${this.lastName}`; |
39 | }; | 39 | }; |
40 | getFirstName() { | 40 | getFirstName() { |
41 | return `${this.firstName}`; | 41 | return `${this.firstName}`; |
42 | }; | 42 | }; |
43 | getLastName() { | 43 | getLastName() { |
44 | return `${this.lastName}`; | 44 | return `${this.lastName}`; |
45 | }; | 45 | }; |
46 | getEmail() { | 46 | getEmail() { |
47 | return `${this.emails[0].address}`; | 47 | return `${this.emails[0].address}`; |
48 | }; | 48 | }; |
49 | getOrganization(){ | 49 | getOrganization(){ |
50 | return `${this.orgId}`; | 50 | return `${this.orgId}`; |
51 | }; | 51 | }; |
52 | 52 | ||
53 | getNameByUserId(userId){ | 53 | getNameByUserId(userId){ |
54 | var user = Users.findOne({"_id":userId}); | 54 | var user = Users.findOne({"_id":userId}); |
55 | return user.firstName + " " + user.lastName; | 55 | return user.firstName + " " + user.lastName; |
56 | } | 56 | } |
57 | getAvatarUrl() { | 57 | getAvatarUrl() { |
58 | let random = parseInt(this._id.substr(0, 4), 36); | 58 | let random = parseInt(this._id.substr(0, 4), 36); |
59 | random = '' + (random % 32); | 59 | random = '' + (random % 32); |
60 | while(random.length < 3) random = '0' + random; | 60 | while(random.length < 3) random = '0' + random; |
61 | return `/files/random/random${ random }.png`; | 61 | return `/files/random/random${ random }.png`; |
62 | }; | 62 | }; |
63 | }; | 63 | }; |
64 | 64 | ||
65 | export { User }; | 65 | export { User }; |
66 | 66 | ||
67 | 67 | ||
68 | const transform = function(doc) { | 68 | const transform = function(doc) { |
69 | return new User(doc); | 69 | return new User(doc); |
70 | }; | 70 | }; |
71 | 71 | ||
72 | export const Users = { | 72 | export const Users = { |
73 | 73 | ||
74 | current: function() { | 74 | current: function() { |
75 | return Meteor.users.findOne({_id: Meteor.userId()}, _.extend({transform: transform})); | 75 | return Meteor.users.findOne({_id: Meteor.userId()}, _.extend({transform: transform})); |
76 | }, | 76 | }, |
77 | 77 | ||
78 | find: function(selector, options) { | 78 | find: function(selector, options) { |
79 | return Meteor.users.find(selector || {}, _.extend({transform: transform}, options)); | 79 | return Meteor.users.find(selector || {}, _.extend({transform: transform}, options)); |
80 | }, | 80 | }, |
81 | 81 | ||
82 | findOne: function(selector, options) { | 82 | findOne: function(selector, options) { |
83 | return Meteor.users.findOne(selector || {}, _.extend({transform: transform}, options)); | 83 | return Meteor.users.findOne(selector || {}, _.extend({transform: transform}, options)); |
84 | }, | 84 | }, |
85 | 85 | ||
86 | insert: _.bind(Meteor.users.insert, Meteor.users), | 86 | insert: _.bind(Meteor.users.insert, Meteor.users), |
87 | update: _.bind(Meteor.users.update, Meteor.users), | 87 | update: _.bind(Meteor.users.update, Meteor.users), |
88 | remove: _.bind(Meteor.users.remove, Meteor.users), | 88 | remove: _.bind(Meteor.users.remove, Meteor.users), |
89 | allow: _.bind(Meteor.users.allow, Meteor.users), | 89 | allow: _.bind(Meteor.users.allow, Meteor.users), |
90 | deny: _.bind(Meteor.users.deny, Meteor.users), | 90 | deny: _.bind(Meteor.users.deny, Meteor.users), |
91 | attachSchema: _.bind(Meteor.users.attachSchema, Meteor.users), | 91 | attachSchema: _.bind(Meteor.users.attachSchema, Meteor.users), |
92 | 92 | ||
93 | }; | 93 | }; |
94 | 94 | ||
95 | 95 | ||
96 | Users.deny({ | 96 | Users.deny({ |
97 | insert() { return true; }, | 97 | insert() { return true; }, |
98 | update() { return true; }, | 98 | update() { return true; }, |
99 | remove() { return true; }, | 99 | remove() { return true; }, |
100 | }); | 100 | }); |
101 | 101 | ||
102 | Users.roles = { | 102 | Users.roles = { |
103 | 'STUDENT': 'STUDENT', | 103 | 'STUDENT': 'STUDENT', |
104 | 'TEACHER': 'TEACHER', | 104 | 'STAFF': 'STAFF', |
105 | 'ADMIN': 'ADMIN', | 105 | 'ADMIN': 'ADMIN', |
106 | 'PARENT': 'PARENT' | 106 | 'PARENT': 'PARENT' |
107 | }; | 107 | }; |
108 | 108 | ||
109 | 109 | ||
110 | Users.schema = new SimpleSchema({ | 110 | Users.schema = new SimpleSchema({ |
111 | role: { type: String }, | 111 | role: { type: String }, |
112 | orgId: { type: String }, | 112 | orgId: { type: String }, |
113 | username: { type: String, optional: true }, | 113 | username: { type: String, optional: true }, |
114 | prefix: { type: String, optional: true }, | 114 | prefix: { type: String, optional: true }, |
115 | firstName: { type: String, optional: true }, | 115 | firstName: { type: String, optional: true }, |
116 | middlename: { type: String, optional: true }, | 116 | middlename: { type: String, optional: true }, |
117 | lastName: { type: String, optional: true }, | 117 | lastName: { type: String, optional: true }, |
118 | gender: { type: String, optional: true }, | 118 | gender: { type: String, optional: true }, |
119 | dob: { type: String, optional: true }, | 119 | dob: { type: String, optional: true }, |
120 | emails: { | 120 | emails: { |
121 | type: [new SimpleSchema({ | 121 | type: [new SimpleSchema({ |
122 | address: { type: String, }, | 122 | address: { type: String, }, |
123 | verified: { type: Boolean, }, | 123 | verified: { type: Boolean, }, |
124 | })], | 124 | })], |
125 | optional: true | 125 | optional: true |
126 | }, | 126 | }, |
127 | phones: { | 127 | phones: { |
128 | type: [new SimpleSchema({ | 128 | type: [new SimpleSchema({ |
129 | country: { type: String, }, | 129 | country: { type: String, }, |
130 | prefix: { type: String, }, | 130 | prefix: { type: String, }, |
131 | number: { type: String, }, | 131 | number: { type: String, }, |
132 | verified: { type: Boolean, }, | 132 | verified: { type: Boolean, }, |
133 | })], | 133 | })], |
134 | optional: true | 134 | optional: true |
135 | }, | 135 | }, |
136 | 136 | ||
137 | services: { | 137 | services: { |
138 | type: Object, | 138 | type: Object, |
139 | optional: true, | 139 | optional: true, |
140 | blackbox: true, | 140 | blackbox: true, |
141 | }, | 141 | }, |
142 | 142 | ||
143 | isMetaUser: { type: Boolean, optional: true }, | 143 | isMetaUser: { type: Boolean, optional: true }, |
144 | 144 | ||
145 | createdAt: { type: Date, autoValue: function(){return new Date();}} | 145 | createdAt: { type: Date, autoValue: function(){return new Date();}} |
146 | 146 | ||
147 | }); | 147 | }); |
148 | 148 | ||
149 | Users.attachSchema(Users.schema); | 149 | Users.attachSchema(Users.schema); |
150 | 150 | ||
151 | Users.privateFields = { | 151 | Users.privateFields = { |
152 | orgId: 1, | 152 | orgId: 1, |
153 | address: 1, | 153 | address: 1, |
154 | 154 | ||
155 | firstName: 1, | 155 | firstName: 1, |
156 | lastName: 1, | 156 | lastName: 1, |
157 | emails: 1, | 157 | emails: 1, |
158 | phones: 1, | 158 | phones: 1, |
159 | 159 | ||
160 | isMetaUser: 1, | 160 | isMetaUser: 1, |
161 | createdAt: 1, | 161 | createdAt: 1, |
162 | }; | 162 | }; |
163 | 163 | ||
164 | Users.publicFields = { | 164 | Users.publicFields = { |
165 | firstName: 1, | 165 | firstName: 1, |
166 | lastName: 1, | 166 | lastName: 1, |
167 | emails: 1, | 167 | emails: 1, |
168 | 168 | ||
169 | createdAt: 1, | 169 | createdAt: 1, |
170 | }; | 170 | }; |
171 | 171 |
imports/server/collections.js
1 | import '/imports/collections/orgs/publications' | 1 | import '/imports/collections/orgs/publications' |
2 | import '/imports/collections/orgs/methods'; | 2 | import '/imports/collections/orgs/methods'; |
3 | 3 | ||
4 | import '/imports/collections/users/publications'; | 4 | import '/imports/collections/users/publications'; |
5 | 5 | ||
6 | import '/imports/collections/students/methods'; | 6 | import '/imports/collections/students/methods'; |
7 | import '/imports/collections/students/publications'; | 7 | import '/imports/collections/students/publications'; |
8 | import '/imports/collections/students/serverCsvUpload'; | 8 | import '/imports/collections/students/serverCsvUpload'; |
9 | 9 | ||
10 | import '/imports/collections/teachers/methods'; | 10 | import '/imports/collections/staff/methods'; |
11 | import '/imports/collections/teachers/publications'; | 11 | import '/imports/collections/staff/publications'; |
12 | 12 |