1 | {{extend 'layout.html'}}
|
---|
2 | <h2><span style="color:#139FD7">python</span>anywhere {{=T('Deployment Interface')}}</h2>
|
---|
3 |
|
---|
4 |
|
---|
5 | <div id="register_form">
|
---|
6 | <h3>{{=T('Login/Register')}}</h3>
|
---|
7 | <form class="form-horizontal" id="palogin">
|
---|
8 |
|
---|
9 | <div class="control-group" id="username__row">
|
---|
10 | <label class="control-label" for="username">{{=T('Username')}}</label>
|
---|
11 | <div class="controls">
|
---|
12 | <input type="text" name="username" id="username"><span class="help-inline">*</span>
|
---|
13 | <span class="help-block"></span>
|
---|
14 | </div>
|
---|
15 | </div>
|
---|
16 |
|
---|
17 | <div class="control-group" id="email_address__row">
|
---|
18 | <label class="control-label" for="email_address">{{=T('Email Address')}}</label>
|
---|
19 | <div class="controls">
|
---|
20 | <input type="text" name="email_address" id="email_address">
|
---|
21 | <span class="help-block"></span>
|
---|
22 | </div>
|
---|
23 | </div>
|
---|
24 |
|
---|
25 | <div class="control-group" id="pythonanywhere_password__row">
|
---|
26 | <label class="control-label" for="pythonanywhere_password">{{=T('PythonAnywhere Password')}}</label>
|
---|
27 | <div class="controls">
|
---|
28 | <input type="password" name="pythonanywhere_password" id="pythonanywhere_password">
|
---|
29 | <span class="help-block"></span>
|
---|
30 | </div>
|
---|
31 | </div>
|
---|
32 |
|
---|
33 | <div class="control-group" id="web2py_admin_password__row">
|
---|
34 | <label class="control-label" for="web2py_admin_password">{{=T('web2py Admin Password')}}</label>
|
---|
35 | <div class="controls">
|
---|
36 | <input type="password" name="web2py_admin_password" id="web2py_admin_password"><span class="help-inline">*</span>
|
---|
37 | <span class="help-block"></span>
|
---|
38 | </div>
|
---|
39 | </div>
|
---|
40 |
|
---|
41 | <div class="control-group" id="accepts_terms__row">
|
---|
42 | <div class="controls">
|
---|
43 | <label class="checkbox">
|
---|
44 | <input type="checkbox" name="accepts_terms" id="accepts_terms"><a target="_blank" href="https://www.pythonanywhere.com/terms/">{{=T('Accept Terms')}}</a>
|
---|
45 | </label>
|
---|
46 | <span class="help-block"></span>
|
---|
47 | </div>
|
---|
48 | </div>
|
---|
49 |
|
---|
50 | <div class="control-group">
|
---|
51 | <div class="controls">
|
---|
52 | <button type="submit" class="btn btn-primary" id="submit_palogin">{{=T('Submit')}}</button>
|
---|
53 | </div>
|
---|
54 | </div>
|
---|
55 |
|
---|
56 | </form>
|
---|
57 | <p>* {{=T('You only need these if you have already registered')}}</p>
|
---|
58 | </div>
|
---|
59 |
|
---|
60 | <div class="row-fluid" id="app_manager" style="display:none;">
|
---|
61 | <div class="span6">
|
---|
62 | <h3>{{=T('Local Apps')}}</h3>
|
---|
63 | <form id="apppicker">
|
---|
64 | <select name="apps" class="form-control" id="local" multiple>
|
---|
65 | <option>{{=T('Loading...')}}</option>
|
---|
66 | </select>
|
---|
67 | <input type="submit" value="Deploy" id="deploy_button" class="btn btn-primary">
|
---|
68 | </form>
|
---|
69 |
|
---|
70 | <div class="alert alert-info">
|
---|
71 | <strong>{{=T('Warning!')}}</strong> {{=T('if your application uses a database other than sqlite you will then have to configure its DAL in pythonanywhere.')}}
|
---|
72 | </div>
|
---|
73 | </div>
|
---|
74 | <div class="span6">
|
---|
75 | <h3>{{=T('PythonAnywhere Apps')}}</h3>
|
---|
76 | <ul id="pythonanywhere">
|
---|
77 | <li>{{=T('Loading...')}}</li>
|
---|
78 | </ul>
|
---|
79 | </div>
|
---|
80 | </div>
|
---|
81 |
|
---|
82 | <script>
|
---|
83 |
|
---|
84 | $(document).ready(function() {
|
---|
85 |
|
---|
86 | $('#palogin').off('submit');
|
---|
87 | $('#palogin').submit(function(event) {
|
---|
88 | var data = $('#palogin').serialize();
|
---|
89 | $.web2py.disableElement($('#submit_palogin'));
|
---|
90 | $.web2py.disableFormElements($('#palogin'));
|
---|
91 | $.ajax({
|
---|
92 | url: '{{=URL("pythonanywhere", "create_account")}}',
|
---|
93 | type: 'POST',
|
---|
94 | data: data,
|
---|
95 | dataType: 'json',
|
---|
96 | }).done(function(data, textStatus, jqXHR) {
|
---|
97 | $('#palogin .error').removeClass('error');
|
---|
98 | $('#palogin .help-block').text('');
|
---|
99 | if(data.status == 'error') {
|
---|
100 | for(var error in data.errors) {
|
---|
101 | $('#' + error + '__row').addClass('error');
|
---|
102 | $('#' + error + '__row .help-block').text(data.errors[error][0]);
|
---|
103 | }
|
---|
104 | $.web2py.enableElement($('#submit_palogin'));
|
---|
105 | $.web2py.enableFormElements($('#palogin'));
|
---|
106 | $.web2py.flash("{{=T('Form has errors')}}");
|
---|
107 | } else {
|
---|
108 | $.web2py.flash("{{=T('Login successful')}}");
|
---|
109 | $('#register_form').hide();
|
---|
110 | $('#app_manager').show();
|
---|
111 | refresh_apps();
|
---|
112 | }
|
---|
113 | }).fail(function(){
|
---|
114 | $.web2py.flash("{{=T('Something went wrong please wait a few minutes before retrying')}}");
|
---|
115 | $.web2py.enableElement($('#submit_palogin'));
|
---|
116 | $.web2py.enableFormElements($('#palogin'));
|
---|
117 | });
|
---|
118 | event.preventDefault();
|
---|
119 | });
|
---|
120 |
|
---|
121 | $('#apppicker').off('submit');
|
---|
122 | $('#apppicker').submit(function(event) {
|
---|
123 | var data = $('#apppicker').serialize();
|
---|
124 | $.web2py.disableElement($('#deploy_button'));
|
---|
125 | $.ajax({
|
---|
126 | url: '{{=URL("pythonanywhere", "bulk_install")}}',
|
---|
127 | type: 'POST',
|
---|
128 | data: {username: $('#username').val(), password: $('#web2py_admin_password').val(), apps: $('#local').val()},
|
---|
129 | dataType: 'json',
|
---|
130 | }).done(function(data, textStatus, jqXHR) {
|
---|
131 | refresh_apps();
|
---|
132 | $.web2py.enableElement($('#deploy_button'));
|
---|
133 | }).fail(function(){
|
---|
134 | $.web2py.flash("{{=T('Something went wrong please wait a few minutes before retrying')}}");
|
---|
135 | $.web2py.enableElement($('#deploy_button'));
|
---|
136 | });
|
---|
137 | event.preventDefault();
|
---|
138 | });
|
---|
139 | });
|
---|
140 |
|
---|
141 | function refresh_apps() {
|
---|
142 | // Refresh List of Apps
|
---|
143 | $('#deploy_button').prop('disabled', true);
|
---|
144 | $.ajax({
|
---|
145 | url: '{{=URL("pythonanywhere", "list_apps")}}',
|
---|
146 | type: 'GET',
|
---|
147 | data: {username: $('#username').val(), password: $('#web2py_admin_password').val()},
|
---|
148 | dataType: 'json',
|
---|
149 | }).done(function(data, textStatus, jqXHR) {
|
---|
150 | var i = 0;
|
---|
151 | $('#local').html('')
|
---|
152 | for(i = 0; i < data.local.length; i++) {
|
---|
153 | $('#local').append($('<option>', {
|
---|
154 | value: data.local[i],
|
---|
155 | text: data.local[i]
|
---|
156 | }));
|
---|
157 | }
|
---|
158 | $('#local').multiSelect('refresh');
|
---|
159 | $('#pythonanywhere').html('')
|
---|
160 | for(i = 0; i < data.pythonanywhere.length; i++) {
|
---|
161 | $('#pythonanywhere').append($('<li>', {
|
---|
162 | text: data.pythonanywhere[i]
|
---|
163 | }));
|
---|
164 | }
|
---|
165 | $('#deploy_button').prop('disabled', false);
|
---|
166 | $.web2py.hide_flash();
|
---|
167 | }).fail(function(){
|
---|
168 | // Mostly this happens if it's a new account, just waiting a bit should be enough.
|
---|
169 | $.get('http://' + $('#username').val() + '.pythonanywhere.com'); // Kickstart the instance
|
---|
170 | $.web2py.flash("{{=T('Please wait, giving pythonanywhere a moment...')}}");
|
---|
171 | setTimeout(refresh_apps, 30000);
|
---|
172 | });
|
---|
173 | }
|
---|
174 |
|
---|
175 | </script>
|
---|
176 |
|
---|