@girder/core 5.0.0-beta.1 → 5.0.0-beta.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (239) hide show
  1. package/dist-lib/Girder_Favicon.png +0 -0
  2. package/dist-lib/Girder_Mark.png +0 -0
  3. package/dist-lib/girder-core.js +48560 -0
  4. package/dist-lib/girder-core.js.map +1 -0
  5. package/dist-lib/girder-core.umd.cjs +630 -0
  6. package/dist-lib/girder-core.umd.cjs.map +1 -0
  7. package/dist-lib/index.d.ts +1 -0
  8. package/dist-lib/src/auth.js +112 -0
  9. package/dist-lib/src/collections/ApiKeyCollection.js +9 -0
  10. package/dist-lib/src/collections/AssetstoreCollection.js +9 -0
  11. package/dist-lib/src/collections/Collection.js +295 -0
  12. package/dist-lib/src/collections/CollectionCollection.js +9 -0
  13. package/dist-lib/src/collections/FileCollection.js +11 -0
  14. package/dist-lib/src/collections/FolderCollection.js +11 -0
  15. package/dist-lib/src/collections/GroupCollection.js +9 -0
  16. package/dist-lib/src/collections/ItemCollection.js +11 -0
  17. package/dist-lib/src/collections/UserCollection.js +24 -0
  18. package/dist-lib/src/collections/index.js +21 -0
  19. package/dist-lib/src/constants.js +32 -0
  20. package/dist-lib/src/dialog.js +128 -0
  21. package/dist-lib/src/events.js +6 -0
  22. package/dist-lib/src/index.d.ts +23 -0
  23. package/dist-lib/src/index.ts +80 -0
  24. package/dist-lib/src/main.ts +45 -0
  25. package/dist-lib/src/misc.js +260 -0
  26. package/dist-lib/src/models/AccessControlledModel.js +76 -0
  27. package/dist-lib/src/models/ApiKeyModel.js +31 -0
  28. package/dist-lib/src/models/AssetstoreModel.js +43 -0
  29. package/dist-lib/src/models/CollectionCreationPolicyModel.js +20 -0
  30. package/dist-lib/src/models/CollectionModel.js +12 -0
  31. package/dist-lib/src/models/FileModel.js +310 -0
  32. package/dist-lib/src/models/FolderModel.js +33 -0
  33. package/dist-lib/src/models/GroupModel.js +197 -0
  34. package/dist-lib/src/models/ItemModel.js +72 -0
  35. package/dist-lib/src/models/MetadataMixin.js +88 -0
  36. package/dist-lib/src/models/Model.js +187 -0
  37. package/dist-lib/src/models/UserModel.js +189 -0
  38. package/dist-lib/src/models/index.js +25 -0
  39. package/dist-lib/src/pluginUtils.js +11 -0
  40. package/dist-lib/src/rest.js +221 -0
  41. package/dist-lib/src/router.js +58 -0
  42. package/dist-lib/src/routes.js +229 -0
  43. package/dist-lib/src/stylesheets/apidocs/apidocs.styl +50 -0
  44. package/dist-lib/src/stylesheets/body/adminConsole.styl +21 -0
  45. package/dist-lib/src/stylesheets/body/assetstores.styl +46 -0
  46. package/dist-lib/src/stylesheets/body/collectionList.styl +39 -0
  47. package/dist-lib/src/stylesheets/body/collectionPage.styl +6 -0
  48. package/dist-lib/src/stylesheets/body/frontPage.styl +48 -0
  49. package/dist-lib/src/stylesheets/body/groupList.styl +43 -0
  50. package/dist-lib/src/stylesheets/body/groupPage.styl +116 -0
  51. package/dist-lib/src/stylesheets/body/itemPage.styl +81 -0
  52. package/dist-lib/src/stylesheets/body/plugins.styl +61 -0
  53. package/dist-lib/src/stylesheets/body/searchResultsList.styl +51 -0
  54. package/dist-lib/src/stylesheets/body/systemConfig.styl +56 -0
  55. package/dist-lib/src/stylesheets/body/userAccount.styl +57 -0
  56. package/dist-lib/src/stylesheets/body/userList.styl +79 -0
  57. package/dist-lib/src/stylesheets/body/userPage.styl +6 -0
  58. package/dist-lib/src/stylesheets/layout/footer.styl +19 -0
  59. package/dist-lib/src/stylesheets/layout/global.styl +154 -0
  60. package/dist-lib/src/stylesheets/layout/globalNav.styl +89 -0
  61. package/dist-lib/src/stylesheets/layout/header.styl +29 -0
  62. package/dist-lib/src/stylesheets/layout/headerUser.styl +33 -0
  63. package/dist-lib/src/stylesheets/layout/layout.styl +75 -0
  64. package/dist-lib/src/stylesheets/layout/layoutVars.styl +9 -0
  65. package/dist-lib/src/stylesheets/layout/loading.styl +37 -0
  66. package/dist-lib/src/stylesheets/layout/progressArea.styl +17 -0
  67. package/dist-lib/src/stylesheets/widgets/accessWidget.styl +106 -0
  68. package/dist-lib/src/stylesheets/widgets/browserWidget.styl +9 -0
  69. package/dist-lib/src/stylesheets/widgets/hierarchyWidget.styl +188 -0
  70. package/dist-lib/src/stylesheets/widgets/markdownWidget.styl +92 -0
  71. package/dist-lib/src/stylesheets/widgets/metadataWidget.styl +92 -0
  72. package/dist-lib/src/stylesheets/widgets/searchFieldWidget.styl +70 -0
  73. package/dist-lib/src/stylesheets/widgets/taskProgress.styl +41 -0
  74. package/dist-lib/src/stylesheets/widgets/timelineWidget.styl +41 -0
  75. package/dist-lib/src/stylesheets/widgets/uploadWidget.styl +43 -0
  76. package/dist-lib/src/stylesheets/widgets/userOtpManagementWidget.styl +159 -0
  77. package/dist-lib/src/templates/body/adminConsole.pug +13 -0
  78. package/dist-lib/src/templates/body/assetstores.pug +83 -0
  79. package/dist-lib/src/templates/body/collectionList.pug +40 -0
  80. package/dist-lib/src/templates/body/collectionPage.pug +36 -0
  81. package/dist-lib/src/templates/body/filesystemImport.pug +41 -0
  82. package/dist-lib/src/templates/body/frontPage.pug +84 -0
  83. package/dist-lib/src/templates/body/groupList.pug +30 -0
  84. package/dist-lib/src/templates/body/groupPage.pug +116 -0
  85. package/dist-lib/src/templates/body/itemPage.pug +61 -0
  86. package/dist-lib/src/templates/body/plugins.pug +20 -0
  87. package/dist-lib/src/templates/body/s3Import.pug +35 -0
  88. package/dist-lib/src/templates/body/searchResults.pug +15 -0
  89. package/dist-lib/src/templates/body/searchResultsType.pug +13 -0
  90. package/dist-lib/src/templates/body/systemConfiguration.pug +199 -0
  91. package/dist-lib/src/templates/body/userAccount.pug +83 -0
  92. package/dist-lib/src/templates/body/userList.pug +43 -0
  93. package/dist-lib/src/templates/body/userPage.pug +40 -0
  94. package/dist-lib/src/templates/layout/alert.pug +5 -0
  95. package/dist-lib/src/templates/layout/layout.pug +12 -0
  96. package/dist-lib/src/templates/layout/layoutFooter.pug +11 -0
  97. package/dist-lib/src/templates/layout/layoutGlobalNav.pug +7 -0
  98. package/dist-lib/src/templates/layout/layoutHeader.pug +8 -0
  99. package/dist-lib/src/templates/layout/layoutHeaderUser.pug +26 -0
  100. package/dist-lib/src/templates/layout/layoutProgressArea.pug +1 -0
  101. package/dist-lib/src/templates/layout/loginDialog.pug +30 -0
  102. package/dist-lib/src/templates/layout/registerDialog.pug +35 -0
  103. package/dist-lib/src/templates/layout/resetPasswordDialog.pug +25 -0
  104. package/dist-lib/src/templates/widgets/accessEditor.pug +23 -0
  105. package/dist-lib/src/templates/widgets/accessEditorMixins.pug +57 -0
  106. package/dist-lib/src/templates/widgets/accessEditorNonModal.pug +11 -0
  107. package/dist-lib/src/templates/widgets/accessEntry.pug +32 -0
  108. package/dist-lib/src/templates/widgets/apiKeyList.pug +50 -0
  109. package/dist-lib/src/templates/widgets/browserWidget.pug +32 -0
  110. package/dist-lib/src/templates/widgets/checkedActionsMenu.pug +46 -0
  111. package/dist-lib/src/templates/widgets/collectionInfoDialog.pug +37 -0
  112. package/dist-lib/src/templates/widgets/confirmDialog.pug +14 -0
  113. package/dist-lib/src/templates/widgets/dateTimeRangeWidget.pug +20 -0
  114. package/dist-lib/src/templates/widgets/dateTimeWidget.pug +8 -0
  115. package/dist-lib/src/templates/widgets/editApiKeyWidget.pug +43 -0
  116. package/dist-lib/src/templates/widgets/editAssetstoreWidget.pug +66 -0
  117. package/dist-lib/src/templates/widgets/editCollectionWidget.pug +27 -0
  118. package/dist-lib/src/templates/widgets/editFileWidget.pug +21 -0
  119. package/dist-lib/src/templates/widgets/editFolderWidget.pug +27 -0
  120. package/dist-lib/src/templates/widgets/editGroupWidget.pug +54 -0
  121. package/dist-lib/src/templates/widgets/editItemWidget.pug +27 -0
  122. package/dist-lib/src/templates/widgets/fileInfoDialog.pug +33 -0
  123. package/dist-lib/src/templates/widgets/fileList.pug +33 -0
  124. package/dist-lib/src/templates/widgets/folderInfoDialog.pug +42 -0
  125. package/dist-lib/src/templates/widgets/folderList.pug +21 -0
  126. package/dist-lib/src/templates/widgets/groupAdminList.pug +33 -0
  127. package/dist-lib/src/templates/widgets/groupInviteDialog.pug +76 -0
  128. package/dist-lib/src/templates/widgets/groupInviteList.pug +14 -0
  129. package/dist-lib/src/templates/widgets/groupMemberList.pug +39 -0
  130. package/dist-lib/src/templates/widgets/groupModList.pug +23 -0
  131. package/dist-lib/src/templates/widgets/hierarchyBreadcrumb.pug +37 -0
  132. package/dist-lib/src/templates/widgets/hierarchyPaginated.pug +19 -0
  133. package/dist-lib/src/templates/widgets/hierarchyWidget.pug +96 -0
  134. package/dist-lib/src/templates/widgets/itemBreadcrumb.pug +16 -0
  135. package/dist-lib/src/templates/widgets/itemList.pug +27 -0
  136. package/dist-lib/src/templates/widgets/jsonMetadatumEditWidget.pug +13 -0
  137. package/dist-lib/src/templates/widgets/jsonMetadatumView.pug +6 -0
  138. package/dist-lib/src/templates/widgets/loadingAnimation.pug +4 -0
  139. package/dist-lib/src/templates/widgets/markdownWidget.pug +34 -0
  140. package/dist-lib/src/templates/widgets/metadataWidget.pug +16 -0
  141. package/dist-lib/src/templates/widgets/metadatumEditWidget.pug +15 -0
  142. package/dist-lib/src/templates/widgets/metadatumView.pug +5 -0
  143. package/dist-lib/src/templates/widgets/newAssetstore.pug +83 -0
  144. package/dist-lib/src/templates/widgets/paginateWidget.pug +7 -0
  145. package/dist-lib/src/templates/widgets/pluginConfigBreadcrumb.pug +13 -0
  146. package/dist-lib/src/templates/widgets/rootSelectorWidget.pug +13 -0
  147. package/dist-lib/src/templates/widgets/searchField.pug +10 -0
  148. package/dist-lib/src/templates/widgets/searchHelp.pug +12 -0
  149. package/dist-lib/src/templates/widgets/searchModeSelect.pug +9 -0
  150. package/dist-lib/src/templates/widgets/searchResults.pug +14 -0
  151. package/dist-lib/src/templates/widgets/sortCollectionWidget.pug +14 -0
  152. package/dist-lib/src/templates/widgets/taskProgress.pug +16 -0
  153. package/dist-lib/src/templates/widgets/timeline.pug +15 -0
  154. package/dist-lib/src/templates/widgets/uploadWidget.pug +15 -0
  155. package/dist-lib/src/templates/widgets/uploadWidgetMixins.pug +31 -0
  156. package/dist-lib/src/templates/widgets/uploadWidgetNonModal.pug +10 -0
  157. package/dist-lib/src/templates/widgets/userOtpBegin.pug +4 -0
  158. package/dist-lib/src/templates/widgets/userOtpDisable.pug +6 -0
  159. package/dist-lib/src/templates/widgets/userOtpEnable.pug +44 -0
  160. package/dist-lib/src/utilities/EventStream.js +177 -0
  161. package/dist-lib/src/utilities/PluginUtils.js +36 -0
  162. package/dist-lib/src/utilities/S3UploadHandler.js +303 -0
  163. package/dist-lib/src/utilities/index.js +9 -0
  164. package/dist-lib/src/utilities/jquery/girderEnable.js +19 -0
  165. package/dist-lib/src/utilities/jquery/girderModal.js +48 -0
  166. package/dist-lib/src/version.js +6 -0
  167. package/dist-lib/src/views/App.js +359 -0
  168. package/dist-lib/src/views/View.js +79 -0
  169. package/dist-lib/src/views/body/AdminView.js +29 -0
  170. package/dist-lib/src/views/body/AssetstoresView.js +234 -0
  171. package/dist-lib/src/views/body/CollectionView.js +188 -0
  172. package/dist-lib/src/views/body/CollectionsView.js +120 -0
  173. package/dist-lib/src/views/body/FilesystemImportView.js +83 -0
  174. package/dist-lib/src/views/body/FolderView.js +54 -0
  175. package/dist-lib/src/views/body/FrontPageView.js +47 -0
  176. package/dist-lib/src/views/body/GroupView.js +336 -0
  177. package/dist-lib/src/views/body/GroupsView.js +106 -0
  178. package/dist-lib/src/views/body/ItemView.js +177 -0
  179. package/dist-lib/src/views/body/PluginsView.js +73 -0
  180. package/dist-lib/src/views/body/S3ImportView.js +80 -0
  181. package/dist-lib/src/views/body/SearchResultsView.js +162 -0
  182. package/dist-lib/src/views/body/SystemConfigurationView.js +182 -0
  183. package/dist-lib/src/views/body/UserAccountView.js +179 -0
  184. package/dist-lib/src/views/body/UserView.js +165 -0
  185. package/dist-lib/src/views/body/UsersView.js +124 -0
  186. package/dist-lib/src/views/body/index.js +37 -0
  187. package/dist-lib/src/views/index.js +13 -0
  188. package/dist-lib/src/views/layout/FooterView.js +29 -0
  189. package/dist-lib/src/views/layout/GlobalNavView.js +103 -0
  190. package/dist-lib/src/views/layout/HeaderUserView.js +45 -0
  191. package/dist-lib/src/views/layout/HeaderView.js +83 -0
  192. package/dist-lib/src/views/layout/LoginView.js +100 -0
  193. package/dist-lib/src/views/layout/ProgressListView.js +70 -0
  194. package/dist-lib/src/views/layout/RegisterView.js +101 -0
  195. package/dist-lib/src/views/layout/ResetPasswordView.js +70 -0
  196. package/dist-lib/src/views/layout/index.js +19 -0
  197. package/dist-lib/src/views/widgets/AccessWidget.js +427 -0
  198. package/dist-lib/src/views/widgets/ApiKeyListWidget.js +140 -0
  199. package/dist-lib/src/views/widgets/BrowserWidget.js +317 -0
  200. package/dist-lib/src/views/widgets/CheckedMenuWidget.js +68 -0
  201. package/dist-lib/src/views/widgets/CollectionInfoWidget.js +40 -0
  202. package/dist-lib/src/views/widgets/DateTimeRangeWidget.js +180 -0
  203. package/dist-lib/src/views/widgets/DateTimeWidget.js +110 -0
  204. package/dist-lib/src/views/widgets/EditApiKeyWidget.js +122 -0
  205. package/dist-lib/src/views/widgets/EditAssetstoreWidget.js +133 -0
  206. package/dist-lib/src/views/widgets/EditCollectionWidget.js +93 -0
  207. package/dist-lib/src/views/widgets/EditFileWidget.js +56 -0
  208. package/dist-lib/src/views/widgets/EditFolderWidget.js +116 -0
  209. package/dist-lib/src/views/widgets/EditGroupWidget.js +125 -0
  210. package/dist-lib/src/views/widgets/EditItemWidget.js +110 -0
  211. package/dist-lib/src/views/widgets/FileInfoWidget.js +26 -0
  212. package/dist-lib/src/views/widgets/FileListWidget.js +151 -0
  213. package/dist-lib/src/views/widgets/FolderInfoWidget.js +39 -0
  214. package/dist-lib/src/views/widgets/FolderListWidget.js +106 -0
  215. package/dist-lib/src/views/widgets/GroupAdminsWidget.js +88 -0
  216. package/dist-lib/src/views/widgets/GroupInvitesWidget.js +56 -0
  217. package/dist-lib/src/views/widgets/GroupMembersWidget.js +185 -0
  218. package/dist-lib/src/views/widgets/GroupModsWidget.js +77 -0
  219. package/dist-lib/src/views/widgets/HierarchyWidget.js +1097 -0
  220. package/dist-lib/src/views/widgets/ItemBreadcrumbWidget.js +38 -0
  221. package/dist-lib/src/views/widgets/ItemListWidget.js +345 -0
  222. package/dist-lib/src/views/widgets/LoadingAnimation.js +17 -0
  223. package/dist-lib/src/views/widgets/MarkdownWidget.js +217 -0
  224. package/dist-lib/src/views/widgets/MetadataWidget.js +508 -0
  225. package/dist-lib/src/views/widgets/NewAssetstoreWidget.js +71 -0
  226. package/dist-lib/src/views/widgets/PaginateWidget.js +37 -0
  227. package/dist-lib/src/views/widgets/PluginConfigBreadcrumbWidget.js +33 -0
  228. package/dist-lib/src/views/widgets/RootSelectorWidget.js +192 -0
  229. package/dist-lib/src/views/widgets/SearchFieldWidget.js +365 -0
  230. package/dist-lib/src/views/widgets/SearchPaginateWidget.js +149 -0
  231. package/dist-lib/src/views/widgets/SortCollectionWidget.js +53 -0
  232. package/dist-lib/src/views/widgets/TaskProgressWidget.js +91 -0
  233. package/dist-lib/src/views/widgets/TimelineWidget.js +155 -0
  234. package/dist-lib/src/views/widgets/UploadWidget.js +340 -0
  235. package/dist-lib/src/views/widgets/UserOtpManagementWidget.js +105 -0
  236. package/dist-lib/src/views/widgets/index.js +75 -0
  237. package/dist-lib/src/vite-env.d.ts +5 -0
  238. package/dist-lib/style.css +16 -0
  239. package/package.json +1 -1
@@ -0,0 +1,359 @@
1
+ import $ from 'jquery';
2
+ import _ from 'underscore';
3
+ import Backbone from 'backbone';
4
+ import 'typeface-open-sans';
5
+ import 'bootstrap/dist/css/bootstrap.css';
6
+ import 'bootstrap/js/alert';
7
+ import '@girder/fontello/dist/css/animation.css';
8
+ import '@girder/fontello/dist/css/fontello.css';
9
+
10
+ import '@girder/core/utilities/jquery/girderModal';
11
+
12
+ import events from '@girder/core/events';
13
+ import eventStream from '@girder/core/utilities/EventStream';
14
+ import LayoutFooterView from '@girder/core/views/layout/FooterView';
15
+ import LayoutGlobalNavView from '@girder/core/views/layout/GlobalNavView';
16
+ import LayoutHeaderView from '@girder/core/views/layout/HeaderView';
17
+ import LoginView from '@girder/core/views/layout/LoginView';
18
+ import ProgressListView from '@girder/core/views/layout/ProgressListView';
19
+ import RegisterView from '@girder/core/views/layout/RegisterView';
20
+ import ResetPasswordView from '@girder/core/views/layout/ResetPasswordView';
21
+ import router from '@girder/core/router';
22
+ import UserModel from '@girder/core/models/UserModel';
23
+ import View from '@girder/core/views/View';
24
+ import { fetchCurrentUser, setCurrentUser, getCurrentUser } from '@girder/core/auth';
25
+ import { Layout } from '@girder/core/constants';
26
+ import { splitRoute } from '@girder/core/misc';
27
+
28
+ import AlertTemplate from '@girder/core/templates/layout/alert.pug';
29
+ import LayoutTemplate from '@girder/core/templates/layout/layout.pug';
30
+
31
+ import '@girder/core/routes';
32
+
33
+ import '@girder/core/stylesheets/layout/global.styl';
34
+ import '@girder/core/stylesheets/layout/layout.styl';
35
+
36
+ var App = View.extend({
37
+ /**
38
+ * @param {object} [settings]
39
+ * @param {bool} [settings.start=true] Run start after initialization
40
+ */
41
+ initialize: function (settings) {
42
+ this._started = false;
43
+ settings = settings || {};
44
+ this.contactEmail = settings.contactEmail || null;
45
+ this.privacyNoticeHref = settings.privacyNoticeHref || null;
46
+ this.brandName = settings.brandName || null;
47
+ this.bannerColor = settings.bannerColor || null;
48
+ this.registrationPolicy = settings.registrationPolicy || null;
49
+ this.enablePasswordLogin = _.has(settings, 'enablePasswordLogin') ? settings.enablePasswordLogin : true;
50
+
51
+ if (settings.start === undefined || settings.start) {
52
+ this.start();
53
+ }
54
+ },
55
+
56
+ /**
57
+ * Start the application with optional components.
58
+ * @param {object} [settings]
59
+ * @param {bool} [settings.fetch=true] Fetch the current user modal
60
+ * @param {bool} [settings.render=true] Render the layout after starting
61
+ * @param {bool} [settings.history=true] Start backbone's history api
62
+ * @returns {$.Deferred} A promise-like object that resolves when the app is ready
63
+ */
64
+ start: function (settings) {
65
+ // start is a noop if the app is already running
66
+ var promise = new $.Deferred().resolve(null).promise();
67
+ if (this._started) {
68
+ return promise;
69
+ }
70
+
71
+ // set defaults
72
+ settings = _.defaults(settings || {}, {
73
+ fetch: true,
74
+ render: true,
75
+ history: true
76
+ });
77
+
78
+ // define a function to be run after fetching the user model
79
+ var afterFetch = (user) => {
80
+ this._createLayout();
81
+
82
+ if (user) {
83
+ setCurrentUser(new UserModel(user));
84
+ eventStream.open();
85
+ }
86
+
87
+ this._started = true;
88
+
89
+ if (settings.render) {
90
+ this.render();
91
+ }
92
+
93
+ if (settings.history) {
94
+ Backbone.history.stop();
95
+ Backbone.history.start({
96
+ pushState: false
97
+ });
98
+ }
99
+ };
100
+
101
+ // If fetching the user from the server then we return the jqxhr object
102
+ // from the request, otherwise just call the callback.
103
+ if (settings.fetch) {
104
+ promise = fetchCurrentUser()
105
+ .done(afterFetch);
106
+ } else {
107
+ afterFetch(null);
108
+ }
109
+
110
+ this.bindGirderEvents();
111
+ return promise;
112
+ },
113
+
114
+ /**
115
+ * Bind the application to the global event object.
116
+ */
117
+ bindGirderEvents: function () {
118
+ // Unbind any current handlers in case this happens to be called twice.
119
+ events.off(null, null, this);
120
+
121
+ events.on('g:navigateTo', this.navigateTo, this);
122
+ events.on('g:loginUi', this.loginDialog, this);
123
+ events.on('g:registerUi', this.registerDialog, this);
124
+ events.on('g:resetPasswordUi', this.resetPasswordDialog, this);
125
+ events.on('g:alert', this.alert, this);
126
+ events.on('g:login', this.login, this);
127
+ },
128
+
129
+ /**
130
+ * Create the main layout views.
131
+ * @private
132
+ */
133
+ _createLayout: function () {
134
+ this.headerView = new LayoutHeaderView({
135
+ parentView: this,
136
+ brandName: this.brandName,
137
+ bannerColor: this.bannerColor,
138
+ registrationPolicy: this.registrationPolicy
139
+ });
140
+
141
+ this.globalNavView = new LayoutGlobalNavView({
142
+ parentView: this
143
+ });
144
+
145
+ this.footerView = new LayoutFooterView({
146
+ parentView: this,
147
+ contactEmail: this.contactEmail,
148
+ privacyNoticeHref: this.privacyNoticeHref
149
+ });
150
+
151
+ this.progressListView = new ProgressListView({
152
+ eventStream: eventStream,
153
+ parentView: this
154
+ });
155
+
156
+ this.layoutRenderMap = {};
157
+ this.layoutRenderMap[Layout.DEFAULT] = this._defaultLayout;
158
+ this.layoutRenderMap[Layout.EMPTY] = this._emptyLayout;
159
+ },
160
+
161
+ _layout: 'default',
162
+
163
+ _defaultLayout: {
164
+ show: function () {
165
+ this.$('#g-app-header-container,#g-global-nav-container,#g-app-footer-container').show();
166
+ this.$('#g-app-body-container').addClass('g-default-layout');
167
+ },
168
+
169
+ hide: function () {
170
+ this.$('#g-app-header-container,#g-global-nav-container,#g-app-footer-container').hide();
171
+ this.$('#g-app-body-container').removeClass('g-default-layout');
172
+ }
173
+ },
174
+
175
+ _emptyLayout: {
176
+ show: function () {
177
+ this.$('#g-app-body-container').addClass('g-empty-layout');
178
+ },
179
+
180
+ hide: function () {
181
+ this.$('#g-app-body-container').removeClass('g-empty-layout');
182
+ }
183
+ },
184
+
185
+ render: function () {
186
+ if (!this._started) {
187
+ return;
188
+ }
189
+ this.$el.html(LayoutTemplate());
190
+
191
+ this.globalNavView.setElement(this.$('#g-global-nav-container')).render();
192
+ this.headerView.setElement(this.$('#g-app-header-container')).render();
193
+ this.footerView.setElement(this.$('#g-app-footer-container')).render();
194
+ this.progressListView.setElement(this.$('#g-app-progress-container')).render();
195
+
196
+ return this;
197
+ },
198
+
199
+ /**
200
+ * Changes the current body view to the view class specified by view.
201
+ * @param view The view to display in the body.
202
+ * @param [settings={}] Settings to pass to the view initialize() method.
203
+ * @param opts Additional options for navigateTo, if any.
204
+ */
205
+ navigateTo: function (view, settings, opts) {
206
+ this.globalNavView.deactivateAll();
207
+
208
+ settings = settings || {};
209
+ opts = opts || {};
210
+
211
+ if (opts.layout) {
212
+ if (this._layout !== opts.layout) {
213
+ if (_.has(this.layoutRenderMap, opts.layout)) {
214
+ // set a layout if opts specifies one different from current
215
+ this.layoutRenderMap[this._layout].hide.call(this, opts);
216
+ this._layout = opts.layout;
217
+ this.layoutRenderMap[this._layout].show.call(this, opts);
218
+ } else {
219
+ console.error('Attempting to set unknown layout type: ' + opts.layout);
220
+ }
221
+ }
222
+ } else if (this._layout !== Layout.DEFAULT) {
223
+ // reset to default as needed when nothing specified in opts
224
+ this.layoutRenderMap[this._layout].hide.call(this, opts);
225
+ this._layout = Layout.DEFAULT;
226
+ this.layoutRenderMap[this._layout].show.call(this, opts);
227
+ }
228
+
229
+ if (view) {
230
+ if (this.bodyView) {
231
+ this.bodyView.destroy();
232
+ }
233
+
234
+ settings = _.extend(settings, {
235
+ el: this.$('#g-app-body-container'),
236
+ parentView: this,
237
+ brandName: this.brandName
238
+ });
239
+
240
+ /* We let the view be created in this way even though it is
241
+ * normally against convention.
242
+ */
243
+ this.bodyView = new view(settings); // eslint-disable-line new-cap
244
+
245
+ if (opts.renderNow) {
246
+ this.bodyView.render();
247
+ }
248
+ } else {
249
+ console.error('Undefined page.');
250
+ }
251
+ return this;
252
+ },
253
+
254
+ /**
255
+ * Close any open dialog if we are already logged in.
256
+ * :returns: true if we have a current user.
257
+ */
258
+ closeDialogIfUser: function () {
259
+ if (getCurrentUser()) {
260
+ $('.modal').girderModal('close');
261
+ return true;
262
+ }
263
+ return false;
264
+ },
265
+
266
+ /**
267
+ * Show a dialog allowing a user to login or register.
268
+ */
269
+ loginDialog: function () {
270
+ if (this.closeDialogIfUser()) {
271
+ return;
272
+ }
273
+ if (!this.loginView) {
274
+ this.loginView = new LoginView({
275
+ el: this.$('#g-dialog-container'),
276
+ parentView: this,
277
+ registrationPolicy: this.registrationPolicy,
278
+ enablePasswordLogin: this.enablePasswordLogin
279
+ });
280
+ }
281
+ this.loginView.render();
282
+ },
283
+
284
+ registerDialog: function () {
285
+ if (this.closeDialogIfUser()) {
286
+ return;
287
+ }
288
+ if (!this.registerView) {
289
+ this.registerView = new RegisterView({
290
+ el: this.$('#g-dialog-container'),
291
+ parentView: this
292
+ });
293
+ }
294
+ this.registerView.render();
295
+ },
296
+
297
+ resetPasswordDialog: function () {
298
+ if (this.closeDialogIfUser()) {
299
+ return;
300
+ }
301
+ if (!this.resetPasswordView) {
302
+ this.resetPasswordView = new ResetPasswordView({
303
+ el: this.$('#g-dialog-container'),
304
+ parentView: this,
305
+ registrationPolicy: this.registrationPolicy
306
+ });
307
+ }
308
+ this.resetPasswordView.render();
309
+ },
310
+
311
+ /**
312
+ * Display a brief alert on the screen with the following options:
313
+ * - text: The text to be displayed
314
+ * - [type]: The alert class ('info', 'warning', 'success', 'danger').
315
+ * Default is 'info'.
316
+ * - [icon]: An optional icon to display in the alert.
317
+ * - [timeout]: How long before the alert should automatically disappear.
318
+ * Default is 6000ms. Set to <= 0 to have no timeout.
319
+ */
320
+ alert: function (options) {
321
+ var el = $(AlertTemplate({
322
+ text: options.text,
323
+ type: options.type || 'info',
324
+ icon: options.icon
325
+ }));
326
+ $('#g-alerts-container').append(el);
327
+ el.fadeIn(500);
328
+
329
+ if (options.timeout === undefined) {
330
+ options.timeout = 6000;
331
+ }
332
+ if (options.timeout > 0) {
333
+ window.setTimeout(function () {
334
+ el.fadeOut(750, function () {
335
+ $(this).remove();
336
+ });
337
+ }, options.timeout);
338
+ }
339
+ },
340
+
341
+ /**
342
+ * On login we re-render the current body view; whereas on
343
+ * logout, we redirect to the front page.
344
+ */
345
+ login: function () {
346
+ var route = splitRoute(Backbone.history.fragment).base;
347
+ Backbone.history.fragment = null;
348
+ eventStream.close();
349
+
350
+ if (getCurrentUser()) {
351
+ eventStream.open();
352
+ router.navigate(route, { trigger: true });
353
+ } else {
354
+ router.navigate('/', { trigger: true });
355
+ }
356
+ }
357
+ });
358
+
359
+ export default App;
@@ -0,0 +1,79 @@
1
+ import _ from 'underscore';
2
+ import Backbone from 'backbone';
3
+
4
+ import events from '@girder/core/events';
5
+ import eventStream from '@girder/core/utilities/EventStream';
6
+
7
+ var View = Backbone.View.extend({
8
+ // eslint-disable-next-line backbone/no-constructor
9
+ constructor: function (opts) {
10
+ if (opts && _.has(opts, 'parentView')) {
11
+ if (opts.parentView) {
12
+ opts.parentView.registerChildView(this);
13
+ this.parentView = opts.parentView;
14
+ }
15
+ } else {
16
+ console.error('View created with no parentView property set. ' +
17
+ 'This view may not be garbage collected.');
18
+ }
19
+ Backbone.View.prototype.constructor.apply(this, arguments);
20
+ },
21
+
22
+ /**
23
+ * Remove a view, unbinding its events and removing its listeners on
24
+ * events so that it can be garbage collected.
25
+ */
26
+ destroy: function () {
27
+ _.each(this._childViews, function (child) {
28
+ child.destroy();
29
+ });
30
+ this._childViews = null;
31
+
32
+ this.undelegateEvents();
33
+ this.stopListening();
34
+ this.off();
35
+ events.off(null, null, this);
36
+ eventStream.off(null, null, this);
37
+
38
+ if (this.parentView) {
39
+ this.parentView.unregisterChildView(this);
40
+ }
41
+
42
+ // Modal views need special cleanup.
43
+ if (this.$el.is('.modal')) {
44
+ var el = this.$el;
45
+ if (el.data('bs.modal') && el.data('bs.modal').isShown) {
46
+ el.on('hidden.bs.modal', function () {
47
+ el.empty().off().removeData();
48
+ }).modal('hide');
49
+ el.modal('removeBackdrop');
50
+ } else {
51
+ el.modal('hideModal');
52
+ el.modal('removeBackdrop');
53
+ el.empty().off().removeData();
54
+ }
55
+ } else {
56
+ this.$el.empty().off().removeData();
57
+ }
58
+ },
59
+
60
+ /**
61
+ * It's typically not necessary to call this directly. Instead, instantiate
62
+ * child views with the "parentView" field.
63
+ */
64
+ registerChildView: function (child) {
65
+ this._childViews = this._childViews || [];
66
+ this._childViews.push(child);
67
+ },
68
+
69
+ /**
70
+ * Typically, you will not need to call this method directly. Calling
71
+ * destroy on a child element will automatically unregister it from its
72
+ * parent view if the parent view was specified.
73
+ */
74
+ unregisterChildView: function (child) {
75
+ this._childViews = _.without(this._childViews, child);
76
+ }
77
+ });
78
+
79
+ export default View;
@@ -0,0 +1,29 @@
1
+ import View from '@girder/core/views/View';
2
+ import { cancelRestRequests } from '@girder/core/rest';
3
+ import { getCurrentUser } from '@girder/core/auth';
4
+
5
+ import AdminConsoleTemplate from '@girder/core/templates/body/adminConsole.pug';
6
+
7
+ import '@girder/core/stylesheets/body/adminConsole.styl';
8
+
9
+ /**
10
+ * This view shows the admin console, which links to all available admin pages.
11
+ */
12
+ var AdminView = View.extend({
13
+ initialize: function () {
14
+ cancelRestRequests('fetch');
15
+ this.render();
16
+ },
17
+
18
+ render: function () {
19
+ if (!getCurrentUser() || !getCurrentUser().get('admin')) {
20
+ this.$el.text('Must be logged in as admin to view this page.');
21
+ return;
22
+ }
23
+ this.$el.html(AdminConsoleTemplate());
24
+
25
+ return this;
26
+ }
27
+ });
28
+
29
+ export default AdminView;
@@ -0,0 +1,234 @@
1
+ import $ from 'jquery';
2
+ import _ from 'underscore';
3
+
4
+ import AssetstoreCollection from '@girder/core/collections/AssetstoreCollection';
5
+ import AssetstoreModel from '@girder/core/models/AssetstoreModel';
6
+ import EditAssetstoreWidget from '@girder/core/views/widgets/EditAssetstoreWidget';
7
+ import NewAssetstoreWidget from '@girder/core/views/widgets/NewAssetstoreWidget';
8
+ import View from '@girder/core/views/View';
9
+ import { AssetstoreType } from '@girder/core/constants';
10
+ import { cancelRestRequests } from '@girder/core/rest';
11
+ import { confirm } from '@girder/core/dialog';
12
+ import events from '@girder/core/events';
13
+ import { formatSize } from '@girder/core/misc';
14
+ import { getCurrentUser } from '@girder/core/auth';
15
+
16
+ import AssetstoresTemplate from '@girder/core/templates/body/assetstores.pug';
17
+
18
+ import '@girder/core/stylesheets/body/assetstores.styl';
19
+
20
+ import 'as-jqplot/dist/jquery.jqplot.js';
21
+ import 'as-jqplot/dist/jquery.jqplot.css'; // jquery.jqplot.min.css
22
+ import 'as-jqplot/dist/plugins/jqplot.pieRenderer.js';
23
+
24
+ /**
25
+ * This private data structure is a dynamic way to map assetstore types to the views
26
+ * that should be rendered to import data into them.
27
+ */
28
+ import FilesystemImportView from '@girder/core/views/body/FilesystemImportView';
29
+ import S3ImportView from '@girder/core/views/body/S3ImportView';
30
+ var assetstoreImportViewMap = {};
31
+ assetstoreImportViewMap[AssetstoreType.FILESYSTEM] = FilesystemImportView;
32
+ assetstoreImportViewMap[AssetstoreType.S3] = S3ImportView;
33
+
34
+ /**
35
+ * This view shows the admin console, which links to all available admin pages.
36
+ */
37
+ var AssetstoresView = View.extend({
38
+ events: {
39
+ 'click .g-set-current': 'setCurrentAssetstore',
40
+ 'click .g-delete-assetstore': 'deleteAssetstore',
41
+ 'click .g-edit-assetstore': 'editAssetstore'
42
+ },
43
+
44
+ initialize: function (settings) {
45
+ cancelRestRequests('fetch');
46
+ this.plots = [];
47
+ this.assetstoreEdit = settings.assetstoreEdit || false;
48
+ this.importableTypes = [
49
+ AssetstoreType.FILESYSTEM,
50
+ AssetstoreType.S3
51
+ ].concat(settings.importableTypes || []);
52
+
53
+ this.newAssetstoreWidget = new NewAssetstoreWidget({
54
+ parentView: this
55
+ }).on('g:created', this.addAssetstore, this);
56
+
57
+ // Fetch all of the current assetstores
58
+ this.collection = new AssetstoreCollection();
59
+ this.collection.on('g:changed', function () {
60
+ this.render();
61
+ }, this).fetch();
62
+ },
63
+
64
+ destroy: function () {
65
+ this._destroyPlots();
66
+ View.prototype.destroy.call(this);
67
+ },
68
+
69
+ _destroyPlots: function () {
70
+ for (const plot of this.plots) {
71
+ plot.data('jqplot').destroy();
72
+ }
73
+ this.plots = [];
74
+ },
75
+
76
+ render: function () {
77
+ if (!getCurrentUser() || !getCurrentUser().get('admin')) {
78
+ this.$el.text('Must be logged in as admin to view this page.');
79
+ return;
80
+ }
81
+ this._destroyPlots();
82
+ this.$el.html(AssetstoresTemplate({
83
+ assetstores: this.collection.toArray(),
84
+ types: AssetstoreType,
85
+ importableTypes: this.importableTypes,
86
+ getAssetstoreImportRoute: this.getAssetstoreImportRoute
87
+ }));
88
+
89
+ this.newAssetstoreWidget.setElement(this.$('#g-new-assetstore-container')).render();
90
+
91
+ _.each(this.$('.g-assetstore-capacity-chart'),
92
+ this.capacityChart, this);
93
+
94
+ if (this.assetstoreEdit) {
95
+ this.editAssetstoreDialog(this.assetstoreEdit);
96
+ this.assetstoreEdit = false;
97
+ }
98
+
99
+ return this;
100
+ },
101
+
102
+ addAssetstore: function (assetstore) {
103
+ this.collection.add(assetstore);
104
+ this.render();
105
+ },
106
+
107
+ /**
108
+ * Renders the capacities of the assetstores in a pie chart using Chart.js.
109
+ * @param el The canvas element to render in.
110
+ */
111
+ capacityChart: function (el) {
112
+ var assetstore = this.collection.get($(el).attr('cid'));
113
+ var capacity = assetstore.get('capacity');
114
+ var used = capacity.total - capacity.free;
115
+ var data = [
116
+ ['Used (' + formatSize(used) + ')', used],
117
+ ['Free (' + formatSize(capacity.free) + ')', capacity.free]
118
+ ];
119
+ var plot = $(el).jqplot([data], {
120
+ seriesDefaults: {
121
+ renderer: $.jqplot.PieRenderer,
122
+ rendererOptions: {
123
+ sliceMargin: 2,
124
+ shadow: false,
125
+ highlightMouseOver: false,
126
+ showDataLabels: true,
127
+ padding: 5,
128
+ startAngle: 180
129
+ }
130
+ },
131
+ legend: {
132
+ show: true,
133
+ location: 'e',
134
+ background: 'transparent',
135
+ border: 'none'
136
+ },
137
+ grid: {
138
+ background: 'transparent',
139
+ border: 'none',
140
+ borderWidth: 0,
141
+ shadow: false
142
+ },
143
+ gridPadding: { top: 10, right: 10, bottom: 10, left: 10 }
144
+ });
145
+ this.plots.push(plot);
146
+ },
147
+
148
+ setCurrentAssetstore: function (evt) {
149
+ var el = $(evt.currentTarget);
150
+ var assetstore = this.collection.get(el.attr('cid'));
151
+ assetstore.set({ current: true });
152
+ assetstore.off('g:saved').on('g:saved', function () {
153
+ events.trigger('g:alert', {
154
+ icon: 'ok',
155
+ text: 'Changed current assetstore.',
156
+ type: 'success',
157
+ timeout: 4000
158
+ });
159
+ this.collection.fetch({}, true);
160
+ }, this).off('g:error').on('g:error', function (err) {
161
+ events.trigger('g:alert', {
162
+ icon: 'cancel',
163
+ text: err.responseJSON.message,
164
+ type: 'danger'
165
+ });
166
+ }).save();
167
+ },
168
+
169
+ deleteAssetstore: function (evt) {
170
+ var el = $(evt.currentTarget);
171
+ var assetstore = this.collection.get(el.attr('cid'));
172
+
173
+ confirm({
174
+ text: 'Are you sure you want to delete the assetstore <b>' +
175
+ assetstore.escape('name') + '</b>? There are no files ' +
176
+ 'stored in it, and no data will be lost.',
177
+ escapedHtml: true,
178
+ yesText: 'Delete',
179
+ confirmCallback: () => {
180
+ assetstore.on('g:deleted', function () {
181
+ events.trigger('g:alert', {
182
+ icon: 'ok',
183
+ text: 'Assetstore deleted.',
184
+ type: 'success',
185
+ timeout: 4000
186
+ });
187
+ this.collection.fetch({}, true);
188
+ }, this).off('g:error').on('g:error', function (resp) {
189
+ events.trigger('g:alert', {
190
+ icon: 'attention',
191
+ text: resp.responseJSON.message,
192
+ type: 'danger',
193
+ timeout: 4000
194
+ });
195
+ }, this).destroy();
196
+ }
197
+ });
198
+ },
199
+
200
+ editAssetstore: function (evt) {
201
+ var cid = $(evt.currentTarget).attr('cid');
202
+ this.editAssetstoreDialog(cid);
203
+ },
204
+
205
+ editAssetstoreDialog: function (cid) {
206
+ var assetstore = this.collection.get(cid);
207
+ var container = $('#g-dialog-container');
208
+
209
+ var editAssetstoreWidget = new EditAssetstoreWidget({
210
+ el: container,
211
+ model: assetstore,
212
+ parentView: this
213
+ }).off('g:saved').on('g:saved', function () {
214
+ this.render();
215
+ }, this);
216
+ editAssetstoreWidget.render();
217
+ }
218
+ }, {
219
+ import: function (assetstoreId) {
220
+ var assetstore = new AssetstoreModel({ _id: assetstoreId });
221
+ assetstore.once('g:fetched', function () {
222
+ var View = assetstoreImportViewMap[assetstore.get('type')];
223
+ if (View) {
224
+ events.trigger('g:navigateTo', View, {
225
+ assetstore: assetstore
226
+ });
227
+ } else {
228
+ throw new Error('No such view');
229
+ }
230
+ }).fetch();
231
+ }
232
+ });
233
+
234
+ export default AssetstoresView;