external-accounts.html 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308
  1. {% extends '../layout/2column.html' %}
  2. {% block html_title %}{{ t('Password Settings') }} · {{ path }}{% endblock %}
  3. {% block content_head %}
  4. <div class="header-wrap">
  5. <header id="page-header">
  6. <h1 class="title" id="">{{ t('User Settings') }}</h1>
  7. </header>
  8. </div>
  9. {% endblock %}
  10. {% block content_main %}
  11. <div class="content-main">
  12. <ul class="nav nav-tabs">
  13. <li><a href="/me"><i class="fa fa-gears"></i> {{ t('User Information') }}</a></li>
  14. <li class="active"><a href="/me/external-accounts"><i class="fa fa-user-plus"></i> {{ t('External Accounts') }}</a></li>
  15. <li><a href="/me/password"><i class="fa fa-key"></i> {{ t('Password Settings') }}</a></li>
  16. <li><a href="/me/apiToken"><i class="fa fa-rocket"></i> {{ t('API Settings') }}</a></li>
  17. </ul>
  18. <div class="tab-content">
  19. {% set error = req.flash('errorMessage') %}
  20. {% if error.length %}
  21. {% for e in error %}
  22. <div class="alert alert-danger">
  23. <b>Server Error occured:</b><br>
  24. {{ e }}
  25. </div>
  26. {% endfor %}
  27. {% endif %}
  28. {% set warn = req.flash('warningMessage') %}
  29. {% if warn.length %}
  30. {% for w in warn %}
  31. <div class="alert alert-warning">
  32. {{ w }}
  33. </div>
  34. {% endfor %}
  35. {% endif %}
  36. {% set message = req.flash('successMessage') %}
  37. {% if message.length %}
  38. <div class="alert alert-success">
  39. <b>{{ message }}</b>
  40. </div>
  41. {% endif %}
  42. <legend style="line-height: 1.7em;">
  43. <button class="btn btn-default btn-sm pull-right" data-target="#create-external-account" data-toggle="modal">
  44. <i class="fa fa-plus-circle" aria-hidden="true"></i>
  45. Add
  46. </button>
  47. {{ t('External Accounts') }}
  48. </legend>
  49. <div class="row">
  50. <div class="col-md-12">
  51. <table class="table table-hover table-striped table-bordered table-user-list">
  52. <thead>
  53. <tr>
  54. <th width="120px">Authentication Provider</th>
  55. <th>
  56. <code>accountId</code>
  57. </th>
  58. <th width="200px">{{ t('Created') }}</th>
  59. <th width="150px">{{ t('Admin') }}</th>
  60. </tr>
  61. </thead>
  62. <tbody>
  63. {% for account in externalAccounts %}
  64. <tr>
  65. <td>{{ account.providerType }}</td>
  66. <td>
  67. <strong>{{ account.accountId }}</strong>
  68. </td>
  69. <td>{{ account.createdAt|date('Y-m-d', account.createdAt.getTimezoneOffset()) }}</td>
  70. <td class="text-center">
  71. <button class="btn btn-default btn-sm btn-danger"
  72. data-toggle="modal" data-target="#diassociate-external-account" data-provider-type="{{ account.providerType }}" data-account-id="{{ account.accountId }}">
  73. <i class="fa fa-unlink"></i>
  74. {{ t('Diassociate') }}
  75. </button>
  76. </td>
  77. </tr>
  78. {% endfor %}
  79. </tbody>
  80. </table>
  81. </div>
  82. </div>
  83. {# modal #}
  84. <style>
  85. .modal.create-external-account .modal-dialog {
  86. width: 750px;
  87. }
  88. </style>
  89. <div class="modal create-external-account" id="create-external-account">
  90. <div class="modal-dialog">
  91. <div class="modal-content">
  92. <div class="modal-header">
  93. <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
  94. <h4 class="modal-title">{{ t('Create External Account') }}</h4>
  95. </div>
  96. <div class="modal-body">
  97. <ul class="nav nav-tabs passport-settings" role="tablist">
  98. <li class="active">
  99. <a href="#passport-ldap" data-toggle="tab" role="tab"><i class="fa fa-sitemap"></i> LDAP</a>
  100. </li>
  101. <li>
  102. <a href="#passport-google-oauth" data-toggle="tab" role="tab"><i class="fa fa-google"></i> Google OAuth</a>
  103. </li>
  104. <li>
  105. <a href="#passport-facebook" data-toggle="tab" role="tab"><i class="fa fa-facebook"></i> Facebook</a>
  106. </li>
  107. <li>
  108. <a href="#passport-twitter" data-toggle="tab" role="tab"><i class="fa fa-twitter"></i> Twitter</a>
  109. </li>
  110. <li>
  111. <a href="#passport-github" data-toggle="tab" role="tab"><i class="fa fa-github"></i> Github</a>
  112. </li>
  113. </ul>
  114. <div class="tab-content passport-settings">
  115. <div id="passport-ldap" class="tab-pane active" role="tabpanel" >
  116. <div id="form-box">
  117. <form id="formLdapAssociation" method="post" class="form-horizontal" role="form">
  118. <fieldset>
  119. <div class="form-group">
  120. <label for="username" class="col-xs-3 control-label">{{ t('Username') }}</label>
  121. <div class="col-xs-6">
  122. <input class="form-control" name="loginForm[username]">
  123. </div>
  124. </div>
  125. <div class="form-group">
  126. <label for="password" class="col-xs-3 control-label">{{ t('Password') }}</label>
  127. <div class="col-xs-6">
  128. <input class="form-control col-xs-4" type="password" name="loginForm[password]">
  129. </div>
  130. </div>
  131. <div class="form-group">
  132. <div class="col-xs-12 text-right">
  133. <button type="button" class="btn btn-default" onclick="testAssociateLdap()">{{ t('Test') }}</button>
  134. <button type="button" class="btn btn-primary" onclick="associateLdap()">{{ t('Add') }}</button>
  135. </div>
  136. </div>
  137. </fieldset>
  138. </form>
  139. </div>
  140. </div>
  141. <div id="passport-google-oauth" class="tab-pane" role="tabpanel">
  142. (TBD)
  143. </div>
  144. <div id="passport-facebook" class="tab-pane" role="tabpanel">
  145. (TBD)
  146. </div>
  147. <div id="passport-twitter" class="tab-pane" role="tabpanel">
  148. (TBD)
  149. </div>
  150. <div id="passport-github" class="tab-pane" role="tabpanel">
  151. (TBD)
  152. </div>
  153. </div><!-- /.tab-content -->
  154. </div><!-- /.modal-body -->
  155. </div><!-- /.modal-content -->
  156. </div><!-- /.modal-dialog -->
  157. <script>
  158. /**
  159. * associate (submit the form)
  160. */
  161. function associateLdap() {
  162. var $form = $('#formLdapAssociation');
  163. var $action = '/me/external-accounts/associateLdap';
  164. $form.attr('action', $action);
  165. $form.submit();
  166. }
  167. /**
  168. * test association (ajax)
  169. */
  170. function testAssociateLdap() {
  171. function showMessage(formId, msg, status) {
  172. $('#' + formId + ' > .alert').remove();
  173. var $message = $('<p class="alert"></p>');
  174. $message.addClass('alert-' + status);
  175. $message.html(msg.replace('\n', '<br>'));
  176. $message.insertBefore('#' + formId);
  177. if (status == 'success') {
  178. setTimeout(function()
  179. {
  180. $message.fadeOut({
  181. complete: function() {
  182. $message.remove();
  183. }
  184. });
  185. }, 5000);
  186. }
  187. }
  188. var $form = $('#formLdapAssociation');
  189. var $action = '/_api/me/external-accounts/testAssociateLdap';
  190. var $id = $form.attr('id');
  191. var $button = $('button', this);
  192. $button.attr('disabled', 'disabled');
  193. var jqxhr = $.post($action, $form.serialize(), function(data)
  194. {
  195. if (!data.status) {
  196. showMessage($id, 'data.status not found', 'danger');
  197. }
  198. else {
  199. showMessage($id, data.message, data.status);
  200. }
  201. })
  202. .fail(function() {
  203. showMessage($id, 'エラーが発生しました', 'danger');
  204. })
  205. .always(function() {
  206. $button.prop('disabled', false);
  207. });
  208. return false;
  209. }
  210. </script>
  211. </div><!-- /.modal -->
  212. <div class="modal diassociate-external-account" id="diassociate-external-account">
  213. <div class="modal-dialog">
  214. <div class="modal-content">
  215. <div class="modal-header">
  216. <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
  217. <h4 class="modal-title">{{ t('Diassociate External Account') }}</h4>
  218. </div>
  219. <div class="modal-body">
  220. <div class="row">
  221. <div class="col-md-12">
  222. <p><b>
  223. Are you sure to diassociate the
  224. <span class="diassociate-provider-type"></span> account
  225. <code class="diassociate-account-id"></code>?
  226. </b></p>
  227. </div>
  228. </div>
  229. </div>
  230. <div class="modal-footer">
  231. <form action="/me/external-accounts/disassociate" method="post">
  232. <input type="hidden" name="_csrf" value="{{ csrf() }}">
  233. <input type="hidden" name="providerType">
  234. <input type="hidden" name="accountId">
  235. <button type="button" class="btn btn-sm btn-default" data-dismiss="modal">
  236. {{ t('Cancel') }}
  237. </button>
  238. <button type="submit" class="btn btn-sm btn-danger">
  239. <i class="fa fa-unlink"></i>
  240. {{ t('Diassociate') }}
  241. </button>
  242. </form>
  243. </div>
  244. </div><!-- /.modal-content -->
  245. </div><!-- /.modal-dialog -->
  246. <script>
  247. $('#diassociate-external-account').on('show.bs.modal', function (event) {
  248. var modal = $(this);
  249. var button = $(event.relatedTarget); // Button that triggered the modal
  250. // get data-*
  251. var providerType = button.data('provider-type');
  252. var accountId = button.data('account-id');
  253. // set labels
  254. modal.find('.diassociate-provider-type').text(providerType);
  255. modal.find('.diassociate-account-id').text(accountId);
  256. // set hidden inputs
  257. modal.find('input:hidden[name="providerType"]').val(providerType);
  258. modal.find('input:hidden[name="accountId"]').val(accountId);
  259. })
  260. </script>
  261. </div><!-- /.modal -->
  262. </div>
  263. {% endblock content_main %}
  264. {% block content_footer %}
  265. {% endblock %}
  266. {% block footer %}
  267. {% endblock %}