Compare commits

..

138 Commits

Author SHA1 Message Date
argirok f427350d71 Merge remote-tracking branch 'origin/develop'
# Conflicts:
#	src/app/openaireLibrary
2024-06-13 11:26:26 +03:00
Argiro Kokogiannaki c265ffc11b Merge pull request 'plugins-functionality' (#10) from plugins-functionality into develop
Reviewed-on: #10
2024-06-13 09:32:43 +02:00
argirok a59f96cdad [plugins-functionality | DONE | Changed ] rename master to main 2024-06-11 14:11:30 +03:00
argirok f03273f40c [plugins-functionality | DONE | Changed ] fix loading when as content source is unselected 2024-06-11 14:10:48 +03:00
argirok 4a4d02d872 [plugins-functionality | DONE | FIXED ] initialize properly display names in the form 2024-06-11 12:19:53 +03:00
argirok 59e9c77e49 [plugins-functionality | DONE | CHANGED ] update the way we manage zenodo communities and master zenodo community 2024-06-10 09:03:55 +03:00
argirok a9945d5da4 [plugins-functionality | DONE | CHANGED ] create validateEnabledPage.component.ts include it in manage pages 2024-06-10 09:03:15 +03:00
argirok 99758d7319 [plugins-functionality | DONE | CHANGED ] add width for organization logos 2024-05-23 12:52:14 +03:00
argirok 9d885d5c84 [plugins-functionality | DONE | ADDED ] add and delete custom plugins, edit plugin in distinct route, add prompt to go back to plugins list 2024-05-22 11:09:18 +03:00
argirok b9f0252392 [plugins-functionality | DONE | CHANGED ] content providers use HTML editor 2024-05-17 10:36:09 +03:00
argirok 6b02ff3ba0 [plugins-functionality | DONE | ADDED ] HTML editor switch 2024-05-16 15:13:03 +03:00
argirok a4a592e248 [plugins-functionality | DONE | CHANGED ] allow add/remove main zenodo community - complete previous commit - add service change 2024-05-16 15:00:44 +03:00
argirok 37f8c73720 [plugins-functionality | DONE | CHANGED ] allow add/remove main zenodo community 2024-05-16 15:00:09 +03:00
argirok 488ac615d4 [plugins-functionality | DONE | ADDED ] add display title and shortitle and use them instead of title/ short title 2024-05-14 14:49:59 +03:00
argirok c7ce678915 [plugins-functionality | DONE | FIXED ] add content providers: fix upper/lower case 2024-04-25 14:30:46 +03:00
argirok ba0bfeb356 [plugins-functionality | DONE | FIXED ] Criteria utils: allow short (3 criteria) or full version (for advanced criteria page) 2024-04-22 10:45:50 +03:00
argirok 30def2150b [plugins-functionality | DONE | CHANGED ] Criteria utils: rename description label to abstract 2024-04-09 13:03:27 +03:00
argirok 99e8f727b0 [plugins-functionality | WIP ] add properties for stats 2024-04-03 10:27:15 +03:00
argirok ce1b87aaa3 [plugins-functionality | DONE | CHANGED ] Change the way the cache is cleared 2024-04-03 10:26:29 +03:00
argirok 5f8d9f32f6 [plugins-functionality | WIP ] Plugins change background when preview in admin 2024-04-01 13:15:52 +03:00
argirok 1114ce4e36 [plugins-functionality | DONE CHANGED ] Edit community info - html editor: remove buttons with css style for text 2024-04-01 11:46:25 +03:00
argirok 6f323f8111 [plugins-functionality | DONE CHANGED ] Criteria: add experimental feature label 2024-04-01 11:44:57 +03:00
argirok c033102dcf Merge branch 'develop' into plugins-functionality 2024-03-28 12:37:27 +02:00
argirok b6e803b56e [plugins-functionality | WIP ] updates and fixes after initial beta release 2024-03-28 12:37:00 +02:00
argirok 75b4328623 [plugins-functionality | DONE | CHANGED] give option to for content, deposit or both, use a common form to edit the options + the criteria 2024-03-15 15:58:15 +02:00
argirok 7a43b29617 [plugins-functionality | WIP] more updates and fixes 2024-03-15 15:56:54 +02:00
argirok b12ce55b20 [plugins-functionality | DONE | FIX] initialize properly view for master zenodo community 2024-03-11 14:08:51 +02:00
argirok ed512f6f05 [plugins-functionality | WIP] add graph info 2024-03-11 13:29:29 +02:00
argirok 2a27c1caf7 [plugins-functionality | WIP] content providers: update methods, add options to select for deposit and add deposition message 2024-02-28 14:46:29 +02:00
argirok a3d67696ad commit libraries 2024-02-15 12:28:43 +02:00
argirok d2384ea07f Merge branch 'develop' 2024-02-15 12:15:18 +02:00
argirok c1e306cff0 [develop | DONE | ADDED ] add again publicationyear in criteria fields, add different list of verbs for numeric values 2024-02-14 11:27:00 +02:00
argirok f2e2edd1f2 [develop | DONE | FIXED ] community status checks 2024-02-14 10:47:03 +02:00
argirok 49e8e56e92 [plugin-functionalities | WIP] : update plugin forms, add reording, filtering by position, create multiple templates per position, etc 2024-02-02 09:33:01 +02:00
argirok 1003382304 [develop | DONE | REMOVED] : criteria-utils: comment out publicationyear option until integer value operators are available 2024-01-19 11:08:08 +02:00
argirok 044d5da78a [plugins-functionality | WIP] : update admn tools API 2024-01-19 11:03:57 +02:00
argirok 1435c5c718 Merge branch 'develop' into plugins-functionality 2024-01-19 11:01:10 +02:00
argirok 4147ffca98 Merge remote-tracking branch 'origin/develop' into develop 2023-11-21 12:59:57 +02:00
argirok f23f75e2d8 [develop | DONE | UPDATED] Community form: remove old visibility statuses 2023-11-21 12:59:46 +02:00
argirok b5c60f85e9 Merge branch 'develop' 2023-11-08 10:38:23 +02:00
argirok a767a1d890 commit libraries 2023-11-08 10:37:50 +02:00
Alex Martzios 7827d23088 [develop | DONE | ADDED] add two new fields in datasources selection criteria & advanced criteria 2023-11-08 09:40:25 +02:00
Konstantinos Triantafyllou b4f01d1fd0 [develop | DONE]: Remove overflow auto from menu_section in customization 2023-11-03 16:56:49 +02:00
Konstantinos Triantafyllou bc201a1ae8 [develop | DONE | FIXED]: Fix sidebar in customization page. 2023-11-03 16:53:39 +02:00
argirok 66a0b038b6 Merge remote-tracking branch 'origin/develop' into develop
# Conflicts:
#	src/environments/environment.beta.ts
#	src/environments/environment.prod.ts
#	src/environments/environment.ts
2023-11-02 09:49:32 +02:00
argirok 2d6b144441 [develop | DONE | UPDATED] properties: use library properties 2023-11-02 09:48:18 +02:00
argirok a02dbded6e [develop | WIP] : properties: add comments what to check 2023-11-02 09:47:36 +02:00
argirok 1b23a25e24 [develop | DONE | UPDATED] :users-managers component add missing attribute to composer function 2023-11-02 09:22:42 +02:00
Konstantinos Triantafyllou e6a5dbc2b4 Merge pull request 'angular-16' (#6) from angular-16 into develop
Reviewed-on: #6
2023-11-01 13:03:17 +01:00
Konstantinos Triantafyllou 24ed9f0690 [angular-16 | FIXED]: Fix width of main content 2023-10-27 17:39:53 +03:00
Konstantinos Triantafyllou 47567e484b Merge pull request '[angular-16-community-projects-availableSince | DONE | UPDATE] : show project link only when it is available before the db update date' (#5) from angular-16-community-projects-availableSince into angular-16
Reviewed-on: #5
2023-10-26 15:48:00 +02:00
Konstantinos Triantafyllou 8f03223bcc Merge pull request '[angular-16-update-zenodo-api | DONE | UPDATE] : update zenodo community API - update method signatures' (#4) from angular-16-update-zenodo-api into angular-16
Reviewed-on: #4
2023-10-26 14:29:01 +02:00
argirok 1c8e46df21 [angular-16-community-projects-availableSince | DONE | UPDATE] : show project link only when it is available before the db update date 2023-10-26 09:49:04 +03:00
Konstantinos Triantafyllou 4ce3080146 [angular-16 | DONE | CHANGED]: Make dashboard-sidebar sticky instead of fixed. 2023-10-25 15:30:50 +03:00
argirok ba9f7db240 [angular-16-update-zenodo-api | DONE | UPDATE] : update zenodo community API - update method signatures 2023-10-23 14:45:27 +03:00
argirok 1907f6f723 beta properties: use new claims service 2023-10-18 15:29:51 +03:00
argirok 9a49371a39 manage plugins of a template 2023-10-17 09:20:16 +03:00
Konstantinos Triantafyllou 6546fd40a1 Merge from develop 2023-10-10 22:50:42 +03:00
Konstantinos Triantafyllou e2122bd14e Update libraries 2023-10-10 22:49:15 +03:00
Konstantinos Triantafyllou 8e27e29605 Enable membership and add condition in users->members 2023-10-10 12:30:47 +03:00
Konstantinos Triantafyllou e5a4472c6d Edit community fix margin in logo section 2023-10-09 17:14:43 +03:00
Konstantinos Triantafyllou 0ffc63ba95 Merge develop into angular-16 2023-10-09 17:07:13 +03:00
argirok 80c6b47c1b Merge branch 'angular-16' into plugins-functionality 2023-10-09 13:56:48 +03:00
argirok 47201b9dff commit libraries 2023-10-09 13:55:30 +03:00
argirok a1754df0b3 Merge branch 'develop' into plugins-functionality 2023-10-06 21:09:55 +03:00
argirok 3c46fb9459 Merge branch 'master' of code-repo.d4science.org:MaDgIK/connect-admin 2023-10-06 21:05:00 +03:00
argirok 63521a83aa commit libraries 2023-10-06 21:04:40 +03:00
argirok 2f9b12c478 Merge branch 'new-community-api' into develop 2023-10-06 21:02:05 +03:00
argirok 0ef15e01cf commit libraries 2023-10-06 21:00:30 +03:00
Konstantina Galouni 5a4e76b0c2 Connect | develop: environments/: Added property swhURL 2023-10-06 15:42:25 +03:00
Konstantinos Triantafyllou 4076f96fb1 Update libraries 2023-10-06 15:28:23 +03:00
argirok 0b703bceec Community projects: add filtering and sorting 2023-10-04 16:04:42 +03:00
argirok b54fa1eaf9 update labels for claimOptions field 2023-10-04 12:17:26 +03:00
argirok 205db8bf10 limit the requests for add projetcs 2023-10-03 10:13:04 +03:00
argirok 78dcc5a208 Merge branch 'develop' into new-community-api 2023-10-02 14:07:48 +03:00
argirok ab85ca7e3c Commit library changes 2023-10-02 14:07:15 +03:00
argirok 703b163803 route for plugins 2023-10-02 12:30:13 +03:00
argirok 10cad849a9 Initial commit for plugins functionality:
Manage Plugin Templates
2023-09-25 11:36:05 +03:00
argirok 7bcab90231 update manage projects page to use paging and search through new communities API 2023-09-19 15:59:37 +03:00
Konstantinos Triantafyllou ef19492aad Remove types/node from package.json 2023-09-14 21:47:48 +03:00
argirok 4dbf21ba48 update remove method on the screen you search and add projects and communities 2023-09-13 14:38:28 +03:00
argirok 7568c668b7 hide membership in edit form until the functionality is ready 2023-09-13 12:13:06 +03:00
Konstantinos Triantafyllou 4365aab4bb Merge from Develop. Resolve (Connect Admin release 30th August 2023 #3) 2023-08-30 13:53:28 +03:00
Konstantinos Triantafyllou 09c04d02b1 Merge from develop 2023-08-29 11:24:05 +03:00
Konstantinos Triantafyllou 93efde0b07 Fix criteria disabled condition because of null in selectionCriteria. 2023-08-29 11:22:27 +03:00
Konstantinos Triantafyllou df4b9be6fc Update uikit to version 3.16.24 2023-08-23 18:37:48 +03:00
Konstantinos Triantafyllou f8a7d0619e Update color picker and fix css of mining 2023-08-04 11:49:19 +03:00
Konstantinos Triantafyllou 2791c7c26b Add mining and update to angular-16 2023-08-04 11:21:30 +03:00
Konstantinos Triantafyllou 2943b496ee Update material to angular 16. 2023-08-04 11:04:31 +03:00
Konstantinos Triantafyllou 247452b860 Update angular to angular 16. 2023-08-04 11:03:37 +03:00
Konstantinos Triantafyllou f11b014248 Update Zone to 0.13.1 2023-08-04 11:01:49 +03:00
Konstantinos Triantafyllou 0dd4fc6717 Update material to angular 15. 2023-08-04 11:00:57 +03:00
Konstantinos Triantafyllou a97bac9e69 Migrate angular core and cli to version 15 and update dependencies to be compatible with the newer version. 2023-08-04 10:58:04 +03:00
Konstantinos Triantafyllou 353fe17126 Update typescript to version 4.9.5 and remove mining until migration ends 2023-08-04 10:56:49 +03:00
Konstantinos Triantafyllou fb6f423273 Update libraries 2023-08-04 10:47:39 +03:00
argirok f63cd1ec60 add fields claim and membership in edit form 2023-07-19 14:26:16 +03:00
argirok d9b0365a1d clean up imports for deleted SearchZenodoCommunitiesService 2023-07-14 15:00:01 +03:00
argirok 3a4203aef8 Merge branch 'develop' into new-community-api 2023-07-14 12:19:21 +03:00
Konstantinos Triantafyllou a79fd13a17 Update piwik with the new methods 2023-07-14 12:12:32 +03:00
argirok 662b514ab5 apply initial changes base odn new community API 2023-07-14 11:43:27 +03:00
Konstantinos Triantafyllou 500dd61f9b Update library. Fix an expression error in advanced-criteria. Add message if there are no subjects in each category. 2023-06-27 12:39:52 +03:00
Konstantinos Triantafyllou 94fc9bda53 Update libraries 2023-06-26 15:10:00 +03:00
Konstantina Galouni 82eec379f2 Updating libraries before prod release 2023-06-23 16:24:48 +03:00
Konstantina Galouni fa6f55e772 Updating openaireLibrary and openaire-theme before beta & prod release 2023-06-23 15:27:08 +03:00
Konstantinos Triantafyllou 946c4f62c4 Update library before release 2023-06-20 09:41:41 +03:00
Konstantinos Triantafyllou 58688d67de Merge pull request 'Connect-Admin release 19th June 2023' (#2) from develop into master
Reviewed-on: #2
2023-06-20 08:37:42 +02:00
argirok 1320fb7a75 Customization configuration: add fontsDarkMode attribute for hero section 2023-06-09 13:58:35 +03:00
argirok b0b277278e fix issue with datasource criteria form #8790 2023-06-08 13:24:46 +03:00
Konstantina Galouni 41d7882e61 Merge remote-tracking branch 'origin/develop' 2023-05-26 15:49:26 +03:00
Konstantina Galouni 6c10e2f397 Updating openaireLibrary before release 2023-05-26 15:48:43 +03:00
Konstantina Galouni 2c9e3e304d [Connect Admin | develop]: connect-admin-customization.component.ts: [Bug fix] Set savingChanges to false when all css are updated and set it to true when purging caches. 2023-05-26 15:33:29 +03:00
Konstantina Galouni 698174e302 [Connect Admin | develop]: app.component.ts: Added in menu "Fields of Science" and "Sustainable Development Goals". 2023-05-26 14:46:53 +03:00
Konstantinos Triantafyllou f98a3e9550 Resolved Connect-Admin release 25th May 2023 #1 2023-05-25 17:37:38 +03:00
Konstantinos Triantafyllou 854656f2ed Merge branch 'develop' of code-repo.d4science.org:MaDgIK/connect-admin into develop 2023-05-25 17:35:50 +03:00
Konstantinos Triantafyllou 508b8120b8 Update library, assets and theme. 2023-05-25 17:35:38 +03:00
Konstantina Galouni 3b6bebc2f1 Updating libraries before beta & prod release 2023-05-24 13:09:58 +03:00
Konstantinos Triantafyllou 07ef246d73 Add icons in manage-communities module. Update library and openaire-theme 2023-05-11 12:32:16 +03:00
Konstantinos Triantafyllou 3b4ea6102c Add message for file size limit in background-upload. 2023-05-03 17:07:39 +03:00
Konstantinos Triantafyllou ced4fe404d Fix margins in subjects 2023-05-03 17:00:14 +03:00
Konstantinos Triantafyllou ffa7ab71a0 Update Uikit to version 3.13.10. Update library 2023-05-02 18:12:18 +03:00
Konstantina Galouni 8712f6cae5 Updating openaireLibrary before beta release 2023-05-02 13:24:06 +03:00
Konstantina Galouni 871523cbbb [Connect Admin | develop]: community.service.ts: Renamed "advancedConstraint" to "advancedConstraints" (coming from community API). 2023-04-26 11:45:54 +03:00
Konstantinos Triantafyllou c174ad17c5 Update uikit to version 3.13.0 2023-04-25 17:08:31 +03:00
Konstantinos Triantafyllou 5123efc8c4 Update libraries before production deployment 2023-04-21 12:35:48 +03:00
Konstantinos Triantafyllou f4b54fa745 Update UIkit to 3.12.2. Add Subjects: Cliking add will add the input value also. 2023-04-04 10:49:59 +03:00
Konstantina Galouni 3f4a4b3501 Updating openaireLibrary - before BETA deploy 2023-03-28 12:08:55 +03:00
Konstantinos Triantafyllou f50525bcef Update libraries 2023-03-27 15:34:27 +03:00
Alex Martzios a3563ad1ef fix wrong condition statement for edit modal 2023-03-15 12:03:16 +02:00
Alex Martzios 070f9d369d add new feature: selection criteria by FoS and SDGs 2023-03-15 11:56:28 +02:00
Alex Martzios 88be699fd2 subjects page: 'enter key' now adds subjects in the list, number of selected SDGs and FoS changes dynamically, 'save' button is enabled/disabled based on overall changes, update submodules 2023-03-13 21:26:31 +02:00
Konstantinos Triantafyllou f2bbf0fb85 Delete header from all pages of communityInfo and users. Add advanced criteria page. 2023-03-10 17:15:26 +02:00
Alex Martzios a83852cffd WIP - add sdg/fos as subjects for community admin dashboards 2023-03-09 16:30:13 +02:00
Konstantinos Triantafyllou d9b4be9a5c Criteria: Change criteria in order to be a generic component. 2023-03-09 00:26:06 +02:00
Konstantinos Triantafyllou 798746e041 Update libraries before make new branches 2023-03-02 16:53:21 +02:00
Konstantinos Triantafyllou 400c0d8dce Remove offcanvas flip from navbar inputs. 2023-03-01 16:40:01 +02:00
Konstantinos Triantafyllou 39aad35c47 Move community info options to sidebar and delete internal tabs 2023-03-01 16:25:54 +02:00
Konstantinos Triantafyllou 83acc14d3b 1. Update library and assets. 2. Add deleteAthorizationLevel for managers with value manager. 2023-02-09 16:31:54 +02:00
Konstantina Galouni f2362b05cd [Connect Admin]: app.component.ts: [Bug fix] Error fixed in Deposit link in menu. 2023-01-18 14:50:37 +02:00
73 changed files with 2290 additions and 1906 deletions

View File

@ -1,7 +1,7 @@
rm -f interactiveminingv3.tgz rm -f interactiveminingv3.tgz
git clone https://code-repo.d4science.org/MaDgIK/interactive-mining.git git clone https://code-repo.d4science.org/MaDgIK/interactive-mining.git
cd interactive-mining/ cd interactive-mining/
git checkout angular-14 git checkout angular-16
cd interactive-mining-angular-frontend/ cd interactive-mining-angular-frontend/
npm install npm install
npm run packagr npm run packagr

View File

@ -17,41 +17,40 @@
}, },
"private": true, "private": true,
"dependencies": { "dependencies": {
"@angular/animations": "^14.2.3", "@angular/animations": "^16.1.8",
"@angular/cdk": "^14.2.2", "@angular/cdk": "^16.1.7",
"@angular/common": "^14.2.3", "@angular/common": "^16.1.8",
"@angular/compiler": "^14.2.3", "@angular/compiler": "^16.1.8",
"@angular/core": "^14.2.3", "@angular/core": "^16.1.8",
"@angular/forms": "^14.2.3", "@angular/forms": "^16.1.8",
"@angular/localize": "^14.2.3", "@angular/localize": "^16.1.8",
"@angular/material": "^14.2.2", "@angular/material": "^16.1.7",
"@angular/platform-browser": "^14.2.3", "@angular/platform-browser": "^16.1.8",
"@angular/platform-browser-dynamic": "^14.2.3", "@angular/platform-browser-dynamic": "^16.1.8",
"@angular/router": "^14.2.3", "@angular/router": "^16.1.8",
"clipboard": "^1.5.16", "clipboard": "^1.5.16",
"core-js": "^2.5.4", "core-js": "^2.5.4",
"express": "^4.15.2", "express": "^4.15.2",
"jquery": "^3.4.1", "jquery": "^3.4.1",
"ng-recaptcha": "^10.0.0", "ng-recaptcha": "^12.0.2",
"ng2-ckeditor": "1.3.7", "ng2-ckeditor": "1.3.7",
"ngx-color-picker": "^8.1.0", "ngx-color-picker": "^14.0.0",
"rxjs": "^6.5.1", "rxjs": "^6.5.1",
"sass-loader": "7.3.1", "sass-loader": "7.3.1",
"ts-md5": "^1.2.0", "ts-md5": "^1.2.0",
"tslib": "^2.0.0", "tslib": "^2.0.0",
"uikit": "3.12.0", "uikit": "3.16.24",
"zone.js": "~0.11.4" "zone.js": "~0.13.1"
}, },
"devDependencies": { "devDependencies": {
"@angular-devkit/build-angular": "^14.2.3", "@angular-devkit/build-angular": "^16.1.7",
"@angular/cli": "^14.2.3", "@angular/cli": "^16.1.7",
"@angular/compiler-cli": "^14.2.3", "@angular/compiler-cli": "^16.1.8",
"@angular/language-service": "^14.2.3", "@angular/language-service": "^16.1.8",
"@types/ckeditor": "^4.9.10",
"@types/express": "^4.17.0", "@types/express": "^4.17.0",
"@types/jasmine": "~3.6.0", "@types/jasmine": "~3.6.0",
"@types/jasminewd2": "~2.0.3", "@types/jasminewd2": "~2.0.3",
"@types/node": "^12.11.1",
"@types/ckeditor": "^4.9.10",
"codelyzer": "^6.0.0", "codelyzer": "^6.0.0",
"jasmine-core": "~3.8.0", "jasmine-core": "~3.8.0",
"jasmine-spec-reporter": "~5.0.0", "jasmine-spec-reporter": "~5.0.0",
@ -62,6 +61,6 @@
"karma-jasmine-html-reporter": "^1.6.0", "karma-jasmine-html-reporter": "^1.6.0",
"protractor": "~7.0.0", "protractor": "~7.0.0",
"ts-node": "~7.0.0", "ts-node": "~7.0.0",
"typescript": "~4.6.4" "typescript": "~4.9.5"
} }
} }

View File

@ -2,16 +2,15 @@
<loading [full]="true"></loading> <loading [full]="true"></loading>
</div> </div>
<div *ngIf="loading == false"> <div *ngIf="loading == false">
<div class="sidebar_main_swipe" [class.sidebar_main_active]="open && hasSidebar" [class.sidebar_mini]="!open && hasSidebar">
<div id="modal-container"></div> <div id="modal-container"></div>
<navbar *ngIf="hasHeader" portal="connect-admin" [header]="menuHeader" [communityId]="community ? community.communityId : null" <navbar *ngIf="hasHeader" portal="connect-admin" [header]="menuHeader" [communityId]="community ? community.communityId : null"
[userMenuItems]=userMenuItems [menuItems]="menuItems" [user]="user" [offCanvasFlip]="true"></navbar> [userMenuItems]=userMenuItems [menuItems]="menuItems" [user]="user"></navbar>
<div> <div class="sidebar_main_swipe uk-flex" [class.sidebar_main_active]="open && (hasSidebar || hasInternalSidebar)" [class.sidebar_mini]="!open && (hasSidebar || hasInternalSidebar)"
<dashboard-sidebar *ngIf="hasSidebar" [items]="sideBarItems" [specialMenuItem]="specialSideBarMenuItem"></dashboard-sidebar> [class.sidebar_hover]="hover">
<main> <dashboard-sidebar *ngIf="hasSidebar && !hasInternalSidebar" [items]="sideBarItems" [backItem]="backItem"></dashboard-sidebar>
<main class="uk-width-1-1">
<router-outlet></router-outlet> <router-outlet></router-outlet>
</main> </main>
</div> </div>
</div>
</div> </div>

View File

@ -28,11 +28,12 @@ export class AppComponent implements OnInit {
params: BehaviorSubject<Params> = new BehaviorSubject<Params>(null); params: BehaviorSubject<Params> = new BehaviorSubject<Params>(null);
data: BehaviorSubject<Data> = new BehaviorSubject<Data>(null); data: BehaviorSubject<Data> = new BehaviorSubject<Data>(null);
hasSidebar: boolean = false; hasSidebar: boolean = false;
hasInternalSidebar: boolean = false;
hasHeader: boolean = true; hasHeader: boolean = true;
hasAdminMenu: boolean = false; hasAdminMenu: boolean = false;
isFrontPage: boolean = false; isFrontPage: boolean = false;
sideBarItems: MenuItem[] = []; sideBarItems: MenuItem[] = [];
specialSideBarMenuItem: MenuItem = null; backItem: MenuItem = null;
menuItems: MenuItem[] = []; menuItems: MenuItem[] = [];
menuHeader: Header = { menuHeader: Header = {
route: "/", route: "/",
@ -81,6 +82,10 @@ export class AppComponent implements OnInit {
this.hasSidebar = hasSidebar; this.hasSidebar = hasSidebar;
this.cdr.detectChanges(); this.cdr.detectChanges();
})); }));
this.subscriptions.push(this.layoutService.hasInternalSidebar.subscribe(hasInternalSidebar => {
this.hasInternalSidebar = hasInternalSidebar;
this.cdr.detectChanges();
}));
this.subscriptions.push(this.layoutService.hasHeader.subscribe(hasHeader => { this.subscriptions.push(this.layoutService.hasHeader.subscribe(hasHeader => {
this.hasHeader = hasHeader; this.hasHeader = hasHeader;
this.cdr.detectChanges(); this.cdr.detectChanges();
@ -126,7 +131,7 @@ export class AppComponent implements OnInit {
this.subscriptions.push(this.data.subscribe(data => { this.subscriptions.push(this.data.subscribe(data => {
if(data && data.portal) { if(data && data.portal) {
this.setProperties(data.portal); this.setProperties(data.portal);
this.configurationService.initCommunityInformation(this.properties, this.properties.adminToolsCommunity); this.configurationService.initPortal(this.properties, this.properties.adminToolsCommunity);
} }
})); }));
this.subscriptions.push(this.userManagementService.getUserInfo().subscribe(user => { this.subscriptions.push(this.userManagementService.getUserInfo().subscribe(user => {
@ -172,13 +177,17 @@ export class AppComponent implements OnInit {
} else { } else {
ConnectHelper.setPortalTypeFromPid(id); ConnectHelper.setPortalTypeFromPid(id);
} }
this.configurationService.initCommunityInformation(this.properties, this.properties.adminToolsCommunity); this.configurationService.initPortal(this.properties, this.properties.adminToolsCommunity);
} }
public get open() { public get open() {
return this.layoutService.open; return this.layoutService.open;
} }
public get hover() {
return this.layoutService.hover;
}
private buildMenu() { private buildMenu() {
this.userMenuItems = []; this.userMenuItems = [];
this.sideBarItems = []; this.sideBarItems = [];
@ -211,14 +220,26 @@ export class AppComponent implements OnInit {
position: 'left', position: 'left',
badge: true badge: true
}; };
this.sideBarItems.push(new MenuItem("community", "Community Info", "", "/" + this.community.communityId, false, [], [], {}, {name: 'badge'}, null, null, "/" + this.community.communityId + "/info")); let communityInfo = new MenuItem("community", "Community Info", "", "/" + this.community.communityId, false, [], [], {}, {name: 'badge'}, null, null, "/" + this.community.communityId + "/info");
communityInfo.items = [
new MenuItem("profile", "Profile", "", "/" + this.community.communityId + "/info/profile", false, [], [], {}, null, null, null, "/" + this.community.communityId + "/info/profile"),
new MenuItem("organizations", "Organizations", "", "/" + this.community.communityId + "/info/organizations", false, [], [], {}, null, null, null, "/" + this.community.communityId + "/info/organizations"),
new MenuItem("projects", OpenaireEntities.PROJECTS, "", "/" + this.community.communityId + "/info/projects", false, [], [], {}, null, null, null, "/" + this.community.communityId + "/info/projects"),
new MenuItem("content-providers", OpenaireEntities.DATASOURCES, "", "/" + this.community.communityId + "/info/content-providers", false, [], [], {}, null, null, null, "/" + this.community.communityId + "/info/content-providers"),
new MenuItem("zenodo-communities", "Zenodo Communities ", "", "/" + this.community.communityId + "/info/zenodo-communities", false, [], [], {}, null, null, null, "/" + this.community.communityId + "/info/zenodo-communities"),
new MenuItem("advanced-criteria", "Advanced Criteria", "", "/" + this.community.communityId + "/info/advanced-criteria", false, [], [], {}, null, null, null, "/" + this.community.communityId + "/info/advanced-criteria")
]
if(this.community.type === 'community') {
communityInfo.items.splice(4, 0, new MenuItem("subjects", "Subjects", "", "/" + this.community.communityId + "/info/subjects", false, [], [], {}, null, null, null, "/" + this.community.communityId + "/info/subjects"))
}
this.sideBarItems.push(communityInfo);
this.sideBarItems.push(new MenuItem("users", "Users", "", "/" + this.community.communityId + "/users", false, [], [], {}, {name: 'group'}, null, null, "/" + this.community.communityId + "/users")); this.sideBarItems.push(new MenuItem("users", "Users", "", "/" + this.community.communityId + "/users", false, [], [], {}, {name: 'group'}, null, null, "/" + this.community.communityId + "/users"));
this.sideBarItems.push(new MenuItem("admin-tools", "Pages & Menus", "", "/" + this.community.communityId + "/admin-tools/pages", false, [], [], {}, {name: 'description'}, null, null, "/" + this.community.communityId + "/admin-tools")); this.sideBarItems.push(new MenuItem("admin-tools", "Pages & Menus", "", "/" + this.community.communityId + "/admin-tools/pages", false, [], [], {}, {name: 'description'}, null, null, "/" + this.community.communityId + "/admin-tools"));
this.sideBarItems.push(new MenuItem("customization", "Customization", "", "/" + this.community.communityId + "/customize-layout", false, [], [], {}, {name: 'brush'})); this.sideBarItems.push(new MenuItem("customization", "Customization", "", "/" + this.community.communityId + "/customize-layout", false, [], [], {}, {name: 'brush'}));
if (this.community.type === 'ri') { if (this.community.type === 'ri') {
this.sideBarItems.push(new MenuItem("mining", "Mining", "", "/" + this.community.communityId + "/mining/manage-profiles", false, [], [], {}, {svg: mining.data}, null, null, "/" + this.community.communityId + "/mining")); this.sideBarItems.push(new MenuItem("mining", "Mining", "", "/" + this.community.communityId + "/mining/manage-profiles", false, [], [], {}, {svg: mining.data}, null, null, "/" + this.community.communityId + "/mining"));
} }
this.specialSideBarMenuItem = new MenuItem("back", "Manage communities", "", "/", false, [], null, {}, {name: 'search', class: 'uk-text-secondary'}); this.backItem = new MenuItem("back", "Manage Communities", "", "/", false, [], null, {}, {name: 'west'});
this.menuItems = []; this.menuItems = [];
this.menuItems.push(new MenuItem("home", "Home", this.menuItems.push(new MenuItem("home", "Home",
@ -226,7 +247,7 @@ export class AppComponent implements OnInit {
, null, null, null, null, "_self") , null, null, null, null, "_self")
); );
this.menuItems.push( this.menuItems.push(
new MenuItem("deposit", "Deposit", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/participate/participate/deposit/learn-how", "", false, [], ['/participate/deposit/learn-how'], null, null, null, null, null, "_self") new MenuItem("deposit", "Deposit", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/participate/deposit/learn-how", "", false, [], ['/participate/deposit/learn-how'], null, null, null, null, null, "_self")
); );
this.menuItems.push( this.menuItems.push(
new MenuItem("link", "Link", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/participate/claim", "", false, [], ['/participate/claim'], null, null, null, null, null, "_self", new MenuItem("link", "Link", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/participate/claim", "", false, [], ['/participate/claim'], null, null, null, null, null, "_self",
@ -256,7 +277,10 @@ export class AppComponent implements OnInit {
new MenuItem("", "Sources and methodology", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/content", "", false, [], ["/content"], null, null, null, null, null, "_self"), new MenuItem("", "Sources and methodology", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/content", "", false, [], ["/content"], null, null, null, null, null, "_self"),
new MenuItem("", "National Bulletins", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/national-bulletins", "", false, [], ["/national-bulletins"], null, null, null, null, null, "_self"), new MenuItem("", "National Bulletins", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/national-bulletins", "", false, [], ["/national-bulletins"], null, null, null, null, null, "_self"),
new MenuItem("", "Subjects", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/subjects", "", false, [], ["/subjects"], null, null, null, null, null, "_self"), new MenuItem("", "Subjects", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/subjects", "", false, [], ["/subjects"], null, null, null, null, null, "_self"),
new MenuItem("", "Projects and funding Opportunities", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/projects", "", false, [], ["/projects"], null, null, null, null, null, "_self") new MenuItem("", "Projects and funding Opportunities", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/projects", "", false, [], ["/projects"], null, null, null, null, null, "_self"),
new MenuItem("", "Fields of Science", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/fields-of-science", "", false, [], ["/fields-of-science"], null, null, null, null, null, "_self"),
new MenuItem("", "Sustainable Development Goals", "https://"+(properties.environment == "beta" ? "beta." : "")+this.community.communityId+".openaire.eu/sdgs", "", false, [], ["/sdgs"], null, null, null, null, null, "_self"),
] ]
) )
); );
@ -306,7 +330,7 @@ export class AppComponent implements OnInit {
this.sideBarItems.push(new MenuItem("connect", "Connect Options", "", "/connect/admin-tools/pages", false, [], [], {}, {name: 'settings'}, null, null, '/connect/admin-tools')); this.sideBarItems.push(new MenuItem("connect", "Connect Options", "", "/connect/admin-tools/pages", false, [], [], {}, {name: 'settings'}, null, null, '/connect/admin-tools'));
this.sideBarItems.push(new MenuItem("explore", "Explore Options", "", "/openaire/admin-tools/pages", false, [], [], {}, {name: 'settings'}, null, null, '/openaire/admin-tools')); this.sideBarItems.push(new MenuItem("explore", "Explore Options", "", "/openaire/admin-tools/pages", false, [], [], {}, {name: 'settings'}, null, null, '/openaire/admin-tools'));
} }
this.specialSideBarMenuItem = null; this.backItem = null;
} }
this.hasSidebar = this.hasSidebar && this.sideBarItems.length > 1; this.hasSidebar = this.hasSidebar && this.sideBarItems.length > 1;
} }

@ -1 +1 @@
Subproject commit acdba43c8bc8244f59e32e450f0dd106bb397037 Subproject commit 2e2a71c3101660480ede67c06edc22aa00faa79d

View File

@ -29,6 +29,16 @@ import {RouterModule} from '@angular/router';
loadChildren: () => import('../../openaireLibrary/dashboard/helpTexts/page-help-content-form.module').then(m => m.PageHelpContentFormModule), loadChildren: () => import('../../openaireLibrary/dashboard/helpTexts/page-help-content-form.module').then(m => m.PageHelpContentFormModule),
pathMatch: 'full' pathMatch: 'full'
}, },
{
path: 'plugins',
loadChildren: () => import('../../openaireLibrary/dashboard/plugins/plugins.module').then(m => m.PluginsModule),
pathMatch: 'full', data: {hasInternalSidebar: false, hasHeader: false}
},
{
path: 'plugins/edit',
loadChildren: () => import('../../openaireLibrary/dashboard/plugins/plugins-form/pluginsForm.module').then(m => m.PluginsFormModule),
pathMatch: 'full', data: {hasInternalSidebar: true, hasHeader: false}
},
{ {
path: 'pages', path: 'pages',
loadChildren: () => import('../../openaireLibrary/dashboard/page/pages.module').then(m => m.PagesModule), loadChildren: () => import('../../openaireLibrary/dashboard/page/pages.module').then(m => m.PagesModule),

View File

@ -5,7 +5,9 @@ import {RouterModule} from "@angular/router";
imports: [RouterModule.forChild([ imports: [RouterModule.forChild([
{path: '', loadChildren: () => import('./admin-tools-routing.module').then(m => m.AdminToolsRoutingModule)}, {path: '', loadChildren: () => import('./admin-tools-routing.module').then(m => m.AdminToolsRoutingModule)},
{path: 'portals', loadChildren: () => import('../../openaireLibrary/dashboard/portal/portals.module').then(m => m.PortalsModule)}, {path: 'portals', loadChildren: () => import('../../openaireLibrary/dashboard/portal/portals.module').then(m => m.PortalsModule)},
{path: 'classes', loadChildren: () => import('../../openaireLibrary/dashboard/divId/divIds.module').then(m => m.DivIdsModule)} {path: 'classes', loadChildren: () => import('../../openaireLibrary/dashboard/divId/divIds.module').then(m => m.DivIdsModule)},
{path: 'templates', loadChildren: () => import('../../openaireLibrary/dashboard/plugins/templates/pluginTemplates.module').then(m => m.PluginTemplatesModule)},
{path: 'templates/plugins', loadChildren: () => import('../../openaireLibrary/dashboard/plugins/plugins.module').then(m => m.PluginsModule)},
])] ])]
}) })
export class PortalAdminToolsRoutingModule { export class PortalAdminToolsRoutingModule {

View File

@ -0,0 +1,120 @@
import {ChangeDetectorRef, Component, OnDestroy, OnInit, ViewChild} from "@angular/core";
import {CommunityService} from "../../openaireLibrary/connect/community/community.service";
import {AdvancedCriteriaService} from "./advanced-criteria.service";
import {Subscription} from "rxjs";
import {SelectionCriteria} from "../../openaireLibrary/utils/entities/contentProvider";
import {
FullScreenModalComponent
} from "../../openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.component";
import {NotificationHandler} from "../../openaireLibrary/utils/notification-handler";
import {CriteriaComponent} from "../content-providers/criteria/criteria.component";
import {CriteriaUtils} from "../content-providers/criteria-utils";
import {CommunityInfo} from "../../openaireLibrary/connect/community/communityInfo";
@Component({
selector: 'advanced-criteria',
template: `
<div page-content>
<div *ngIf="selectionCriteria" actions>
<div class="uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-right@m uk-flex-center">
<button *ngIf="selectionCriteria.criteria.length === 0" (click)="openCriteria()" class="uk-button uk-button-default uk-flex uk-flex-middle">
<icon name="add" [flex]="true"></icon>
<span class="uk-margin-small-left">Add Criteria</span>
</button>
<button *ngIf="selectionCriteria.criteria.length > 0" (click)="openCriteria()" class="uk-button uk-button-default uk-flex uk-flex-middle">
<icon name="edit" [flex]="true"></icon>
<span class="uk-margin-small-left">Edit Criteria</span>
</button>
</div>
</div>
</div>
<div inner>
<div *ngIf="loading" class="uk-position-center">
<loading></loading>
</div>
<div *ngIf="!loading">
<div *ngIf="selectionCriteria?.criteria?.length > 0" class="uk-margin-small-bottom">
<div class="uk-text-meta uk-margin-small-bottom">Criteria</div>
<div [innerHTML]="criteriaUtils.getFiltersAsText(selectionCriteria.criteria,false)"></div>
</div>
<div *ngIf="selectionCriteria?.criteria?.length === 0" class="message">
<h5 class="uk-margin-small-bottom">No criteria yet</h5>
<i class="uk-display-block">
Add multiple constraints in AND to define a criterion: results that satisfy at least one of the criteria will be included in your community.
</i>
</div>
</div>
</div>
</div>
<fs-modal #filtersModal (okEmitter)="saveCriteria()" (cancelEmitter)="criteria.reset()"
[okButtonDisabled]="!criteria || criteria.disabled">
<div *ngIf="selectionCriteria" class="uk-container uk-container-large">
<criteria #criteria [height]="filtersModal.bodyHeight" [entityType]="'criterion'"
[entityTypePlural]="'criteria'" [selectionCriteria]="selectionCriteria">
<div no-criteria>
<h5 class="uk-margin-small-bottom">No Criteria yet</h5>
<i class="uk-display-block">
Add multiple constraints in AND to define a criterion: results that satisfy at least one of the criteria will be included in your community.
</i>
</div>
</criteria>
</div>
</fs-modal>
`
})
export class AdvancedCriteriaComponent implements OnInit, OnDestroy {
public loading = true;
public selectionCriteria: SelectionCriteria;
public community: CommunityInfo;
public criteriaUtils: CriteriaUtils = new CriteriaUtils();
private subscriptions: any[] = [];
@ViewChild('criteria') criteria: CriteriaComponent;
@ViewChild('filtersModal', { static: true }) filtersModal: FullScreenModalComponent;
constructor(private communityService: CommunityService,
private cdr: ChangeDetectorRef,
private advancedCriteriaService: AdvancedCriteriaService) {}
ngOnInit() {
this.loading = true;
this.subscriptions.push(this.communityService.getCommunityAsObservable().subscribe(community => {
this.community = community;
this.selectionCriteria = community.selectionCriteria;
this.loading = false;
}));
}
saveCriteria() {
let callback = (selectionCriteria): void => {
this.advancedCriteriaService.saveAdvancedCriteria(this.community.communityId, selectionCriteria).subscribe(() => {
this.criteria.reset();
this.criteria.loading = false;
NotificationHandler.rise('Filters have been <b>successfully updated</b>');
}, error => {
this.criteria.loading = false;
this.criteria.handeError('An error has been occurred. Try again later!', error);
});
}
this.loading = true;
this.criteria.save(callback);
}
public openCriteria() {
this.criteria.reset();
this.filtersModal.title = 'Criteria';
this.filtersModal.okButtonText = "Save";
this.filtersModal.back = true;
this.filtersModal.okButton = true;
this.filtersModal.open();
this.cdr.detectChanges();
}
ngOnDestroy() {
this.subscriptions.forEach(subscription => {
if(subscription instanceof Subscription) {
subscription.unsubscribe();
}
})
}
}

View File

@ -0,0 +1,18 @@
import {NgModule} from "@angular/core";
import {CommonModule} from "@angular/common";
import {RouterModule} from "@angular/router";
import {AdvancedCriteriaComponent} from "./advanced-criteria.component";
import {PageContentModule} from "../../openaireLibrary/dashboard/sharedComponents/page-content/page-content.module";
import {FullScreenModalModule} from "../../openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.module";
import {CriteriaModule} from "../content-providers/criteria/criteria.module";
import {IconsModule} from "../../openaireLibrary/utils/icons/icons.module";
import {LoadingModule} from "../../openaireLibrary/utils/loading/loading.module";
@NgModule({
imports: [CommonModule, RouterModule.forChild([
{path: '', component: AdvancedCriteriaComponent,}
]), PageContentModule, FullScreenModalModule, CriteriaModule, IconsModule, LoadingModule],
declarations: [AdvancedCriteriaComponent],
exports: [AdvancedCriteriaComponent]
})
export class AdvancedCriteriaModule {}

View File

@ -0,0 +1,25 @@
import {Injectable} from "@angular/core";
import {SelectionCriteria} from "../../openaireLibrary/utils/entities/contentProvider";
import {Observable} from "rxjs";
import {CommunityInfo} from "../../openaireLibrary/connect/community/communityInfo";
import {HttpClient} from "@angular/common/http";
import {properties} from "../../../environments/environment";
import {map} from "rxjs/operators";
import {CommunityService} from "../../openaireLibrary/connect/community/community.service";
@Injectable({
providedIn: 'root'
})
export class AdvancedCriteriaService {
constructor(private httpClient: HttpClient,
private communityService: CommunityService) {
}
public saveAdvancedCriteria(communityId, selectionCriteria: SelectionCriteria): Observable<void> {
return this.httpClient.post(properties.communityAPI + communityId + '/advancedConstraint', selectionCriteria).pipe(map(community => {
this.communityService.updateAdvancedCriteria(this.communityService.parseCommunity(community).selectionCriteria);
}));
}
}

View File

@ -1,21 +1,7 @@
<div page-content> <div page-content>
<div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Organizations
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<community-info tab="organizations"></community-info>
</div>
<div actions> <div actions>
<div class="uk-section-xsmall"> <div class="uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-center uk-flex-right@m"> <div class="uk-flex uk-flex-center uk-flex-right@m">
<button *ngIf="!organizationsEnabled" class="uk-button uk-button-default uk-margin-right" [class.uk-disabled]="loading"
[disabled]="loading"
(click)="enableAffiliations()">Enable Organizations Page
</button>
<button class="uk-button uk-button-default uk-flex uk-flex-middle" <button class="uk-button uk-button-default uk-flex uk-flex-middle"
[disabled]="loading" [class.uk-disabled]="loading" [disabled]="loading" [class.uk-disabled]="loading"
(click)="editAffiliationOpen()"> (click)="editAffiliationOpen()">
@ -30,6 +16,7 @@
<div *ngIf="loading" class="uk-position-center"> <div *ngIf="loading" class="uk-position-center">
<loading></loading> <loading></loading>
</div> </div>
<validate-page-enabled pageRoute="/organizations"></validate-page-enabled>
<div *ngIf="!loading"> <div *ngIf="!loading">
<div *ngIf="affiliations.length == 0" <div *ngIf="affiliations.length == 0"
class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold"> class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold">
@ -45,7 +32,7 @@
<div class="uk-card-body"> <div class="uk-card-body">
<div class="uk-flex uk-flex-middle uk-flex-column"> <div class="uk-flex uk-flex-middle uk-flex-column">
<div class="uk-flex uk-flex-center uk-height-xsmall"> <div class="uk-flex uk-flex-center uk-height-xsmall">
<img class="uk-height-max-xsmall uk-blend-multiply" [src]="affiliation.logo_url | urlPrefix"> <img class="uk-height-max-xsmall uk-blend-multiply uk-width-small" [src]="affiliation.logo_url | urlPrefix">
</div> </div>
<h5>{{affiliation.name}}</h5> <h5>{{affiliation.name}}</h5>
<div class="uk-text-truncate uk-text-small"> <div class="uk-text-truncate uk-text-small">

View File

@ -54,7 +54,6 @@ export class AffiliationsComponent implements OnInit, OnDestroy {
if (this.community) { if (this.community) {
this.title.setTitle(this.community.shortTitle.toUpperCase() + ' | Organizations'); this.title.setTitle(this.community.shortTitle.toUpperCase() + ' | Organizations');
this.getAffiliations(); this.getAffiliations();
this.organizationsPageStatus();
} }
})); }));
} }
@ -81,10 +80,6 @@ export class AffiliationsComponent implements OnInit, OnDestroy {
); );
} }
public get organizationsEnabled(): boolean {
return !this.organizationsPage || this.organizationsPage.isEnabled;
}
editAffiliationOpen(index: number = -1) { editAffiliationOpen(index: number = -1) {
let affiliation: Affiliation; let affiliation: Affiliation;
this.index = index; this.index = index;
@ -113,6 +108,7 @@ export class AffiliationsComponent implements OnInit, OnDestroy {
deleteAffiliationOpen(index: number) { deleteAffiliationOpen(index: number) {
this.index = index; this.index = index;
let affiliation: Affiliation = this.affiliations[index]; let affiliation: Affiliation = this.affiliations[index];
console.log(index, affiliation)
this.removeAffiliationModal.alertTitle = 'Delete Organization'; this.removeAffiliationModal.alertTitle = 'Delete Organization';
this.removeAffiliationModal.message = 'Do you want to remove <b>' + this.removeAffiliationModal.message = 'Do you want to remove <b>' +
affiliation.name + '</b> from Organizations?'; affiliation.name + '</b> from Organizations?';
@ -164,7 +160,8 @@ export class AffiliationsComponent implements OnInit, OnDestroy {
removeAffiliation() { removeAffiliation() {
this.loading = true; this.loading = true;
this.affiliationService.deleteAffiliation(this.properties.communityAPI + this.community.communityId + '/organizations', console.log(this.index, this.affiliations[this.index].id)
this.affiliationService.deleteAffiliation(this.properties.communityAPI + this.community.communityId + '/organizations?organizationName='+this.affiliations[this.index].name,
this.affiliations[this.index].id).subscribe((deleteOK) => { this.affiliations[this.index].id).subscribe((deleteOK) => {
this.affiliations.splice(this.index, 1); this.affiliations.splice(this.index, 1);
if (this.currentPage.length === 0) { if (this.currentPage.length === 0) {
@ -177,13 +174,6 @@ export class AffiliationsComponent implements OnInit, OnDestroy {
this.handleUpdateError('An error has been occurred. Try again later!'); this.handleUpdateError('An error has been occurred. Try again later!');
}); });
} }
private organizationsPageStatus() {
this.helpContentService.getCommunityPagesByRoute(this.community.communityId, '/organizations', this.properties.adminToolsAPIURL).subscribe((page) => {
this.organizationsPage = page;
})
}
handleUpdateError(message: string) { handleUpdateError(message: string) {
NotificationHandler.rise(message, "danger"); NotificationHandler.rise(message, "danger");
this.loading = false; this.loading = false;
@ -194,13 +184,4 @@ export class AffiliationsComponent implements OnInit, OnDestroy {
this.loading = false; this.loading = false;
} }
enableAffiliations() {
this.helpContentService.togglePages(this.community.communityId, [this.organizationsPage._id], true, this.properties.adminToolsAPIURL).subscribe(() => {
this.organizationsPage.isEnabled = true;
this._clearCacheService.purgeBrowserCache("Organizations Page enabled", this.community.communityId);
NotificationHandler.rise('Organizations Page has been <b>enabled successfully</b>');
}, error => {
this.handleUpdateError('An error has been occurred. Try again later!');
});
}
} }

View File

@ -11,18 +11,18 @@ import {AlertModalModule} from '../../openaireLibrary/utils/modal/alertModal.mod
import {UtilitiesService} from '../../openaireLibrary/services/utilities.service'; import {UtilitiesService} from '../../openaireLibrary/services/utilities.service';
import {InputModule} from "../../openaireLibrary/sharedComponents/input/input.module"; import {InputModule} from "../../openaireLibrary/sharedComponents/input/input.module";
import {PageContentModule} from "../../openaireLibrary/dashboard/sharedComponents/page-content/page-content.module"; import {PageContentModule} from "../../openaireLibrary/dashboard/sharedComponents/page-content/page-content.module";
import {CommunityInfoModule} from "../community-info/community-info.module";
import {IconsModule} from "../../openaireLibrary/utils/icons/icons.module"; import {IconsModule} from "../../openaireLibrary/utils/icons/icons.module";
import {NoLoadPaging} from "../../openaireLibrary/searchPages/searchUtils/no-load-paging.module"; import {NoLoadPaging} from "../../openaireLibrary/searchPages/searchUtils/no-load-paging.module";
import {LoadingModule} from "../../openaireLibrary/utils/loading/loading.module"; import {LoadingModule} from "../../openaireLibrary/utils/loading/loading.module";
import {UrlPrefixModule} from "../../openaireLibrary/utils/pipes/url-prefix.module"; import {UrlPrefixModule} from "../../openaireLibrary/utils/pipes/url-prefix.module";
import {HelpContentService} from "../../services/help-content.service"; import {HelpContentService} from "../../services/help-content.service";
import {PagingModule} from "../../openaireLibrary/utils/paging.module"; import {PagingModule} from "../../openaireLibrary/utils/paging.module";
import {ValidateEnabledPageModule} from "../../utils/validateEnabledPage.module";
@NgModule({ @NgModule({
imports: [ imports: [
AffiliationsRoutingModule, CommonModule, FormsModule, RouterModule, AffiliationsRoutingModule, CommonModule, FormsModule, RouterModule,
AlertModalModule, ReactiveFormsModule, InputModule, PageContentModule, CommunityInfoModule, IconsModule, NoLoadPaging, LoadingModule, UrlPrefixModule, PagingModule AlertModalModule, ReactiveFormsModule, InputModule, PageContentModule, IconsModule, NoLoadPaging, LoadingModule, UrlPrefixModule, PagingModule, ValidateEnabledPageModule
], ],
declarations: [ declarations: [
AffiliationsComponent AffiliationsComponent

View File

@ -11,13 +11,6 @@ import {CommunityService} from "../../openaireLibrary/connect/community/communit
template: ` template: `
<div page-content> <div page-content>
<div header> <div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Links
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<users-tabs tab="claims"></users-tabs> <users-tabs tab="claims"></users-tabs>
</div> </div>
<div inner> <div inner>

View File

@ -11,6 +11,7 @@ import {ConnectCommunityGuard} from "../../openaireLibrary/connect/communityGuar
{path: 'projects', loadChildren: () => import('../projects/communityProjects.module').then(m => m.CommunityProjectsModule)}, {path: 'projects', loadChildren: () => import('../projects/communityProjects.module').then(m => m.CommunityProjectsModule)},
{path: 'content-providers', loadChildren: () => import('../content-providers/communityContentProviders.module').then(m => m.CommunityContentProvidersModule)}, {path: 'content-providers', loadChildren: () => import('../content-providers/communityContentProviders.module').then(m => m.CommunityContentProvidersModule)},
{path: 'zenodo-communities', loadChildren: () => import('../zenodo-communities/zenodo-communities.module').then(m => m.ZenodoCommunitiesModule)}, {path: 'zenodo-communities', loadChildren: () => import('../zenodo-communities/zenodo-communities.module').then(m => m.ZenodoCommunitiesModule)},
{path: 'advanced-criteria', loadChildren: () => import('../advanced-criteria/advanced-criteria.module').then(m => m.AdvancedCriteriaModule)},
{path: 'subjects', canActivateChild: [ConnectCommunityGuard], loadChildren: () => import('../subjects/subjects-edit-form/subjects-edit-form.module').then(m => m.SubjectsEditFormModule)}, {path: 'subjects', canActivateChild: [ConnectCommunityGuard], loadChildren: () => import('../subjects/subjects-edit-form/subjects-edit-form.module').then(m => m.SubjectsEditFormModule)},
]) ])
], ],

View File

@ -1,42 +0,0 @@
import {Component, Input, OnInit} from '@angular/core';
import {CommunityInfo} from '../../openaireLibrary/connect/community/communityInfo';
import {CommunityService} from '../../openaireLibrary/connect/community/community.service';
import {Subscription} from 'rxjs';
import {OpenaireEntities} from "../../openaireLibrary/utils/properties/searchFields";
@Component({
selector: 'community-info',
template: `
<ul *ngIf="community" class="uk-tab uk-margin-remove-bottom uk-margin-medium-top uk-flex uk-flex-center uk-flex-left@m" uk-tab>
<li [class.uk-active]="tab === 'profile'"><a routerLink="../profile">Profile</a></li>
<li [class.uk-active]="tab === 'organizations'"><a routerLink="../organizations">Organizations</a></li>
<li [class.uk-active]="tab === 'projects'"><a routerLink="../projects">{{openAIREEntities.PROJECTS}}</a></li>
<li [class.uk-active]="tab === 'content-providers'"><a routerLink="../content-providers">{{openAIREEntities.DATASOURCES}}</a></li>
<li *ngIf="community.type !='ri'" [class.uk-active]="tab === 'subjects'"><a routerLink="../subjects">Subjects</a></li>
<li [class.uk-active]="tab === 'zenodo-communities'"><a routerLink="../zenodo-communities">Zenodo Communities</a></li>
</ul>
`
})
export class CommunityInfoComponent implements OnInit {
@Input()
public type: string;
@Input()
public tab: "profile"| "organizations" | "projects" | "content-providers" | "subjects" | "zenodo-communities" = 'profile';
public community: CommunityInfo;
public openAIREEntities = OpenaireEntities;
private sub;
constructor(private communityService: CommunityService) {
}
ngOnInit() {
this.sub =this.communityService.getCommunityAsObservable().subscribe(community => {
this.community = community;
});
}
ngOnDestroy() {
if (this.sub instanceof Subscription) {
this.sub.unsubscribe();
}
}
}

View File

@ -1,14 +0,0 @@
import {NgModule} from '@angular/core';
import {RouterModule} from "@angular/router";
import {CommonModule} from "@angular/common";
import {CommunityInfoComponent} from "./community-info.component";
@NgModule({
imports: [
CommonModule, RouterModule
],
declarations: [CommunityInfoComponent],
exports: [CommunityInfoComponent]
})
export class CommunityInfoModule {
}

View File

@ -20,11 +20,19 @@ import {ClearCacheService} from "../../../../openaireLibrary/services/clear-cach
<div class="uk-grid uk-grid-large" uk-grid> <div class="uk-grid uk-grid-large" uk-grid>
<div class="uk-width-1-2@m"> <div class="uk-width-1-2@m">
<div input id="name" [formInput]="communityFb.get('name')" <div input id="name" [formInput]="communityFb.get('name')"
placeholder="Name of the community profile."></div> placeholder="Index name of the community."></div>
</div> </div>
<div class="uk-width-1-2@m"> <div class="uk-width-1-2@m">
<div input [formInput]="communityFb.get('shortName')" <div input [formInput]="communityFb.get('shortName')"
placeholder="Short name of the community."></div> placeholder="Index short name of the community."></div>
</div>
<div class="uk-width-1-2@m">
<div input id="name" [formInput]="communityFb.get('displayName')"
placeholder="Display name of the community."></div>
</div>
<div class="uk-width-1-2@m">
<div input [formInput]="communityFb.get('displayShortName')"
placeholder="Display short name of the community."></div>
</div> </div>
<div class="uk-width-1-1"> <div class="uk-width-1-1">
<div class="uk-text-bold uk-margin-bottom uk-form-hint">Description of the community</div> <div class="uk-text-bold uk-margin-bottom uk-form-hint">Description of the community</div>
@ -35,14 +43,14 @@ import {ClearCacheService} from "../../../../openaireLibrary/services/clear-cach
removeButtons: 'Save,NewPage,DocProps,Preview,Print,' + removeButtons: 'Save,NewPage,DocProps,Preview,Print,' +
'Form,Checkbox,Radio,TextField,Textarea,Select,Button,ImageButton,HiddenField,' + 'Form,Checkbox,Radio,TextField,Textarea,Select,Button,ImageButton,HiddenField,' +
'CreateDiv,Flash,PageBreak,' + 'CreateDiv,Flash,PageBreak,' +
'Subscript,Superscript,Anchor,Smiley,Iframe,Styles,Font,About,Language', 'Subscript,Superscript,Anchor,Smiley,Iframe,Styles,Font,About,Language,JustifyLeft,JustifyRight,JustifyCenter,JustifyBlock,FontSize,TextColor,BGColor',
extraPlugins: 'divarea'}"> extraPlugins: 'divarea'}">
</ckeditor> </ckeditor>
</div> </div>
<div class="uk-width-1-1"> <div class="uk-width-1-1">
<input #file id="photo" type="file" class="uk-hidden" (change)="fileChangeEvent($event)"/> <input #file id="photo" type="file" class="uk-hidden" (change)="fileChangeEvent($event)"/>
<div *ngIf="!communityFb.get('isUpload').value" class="uk-grid uk-grid-column-large" uk-grid> <div *ngIf="!communityFb.get('isUpload').value" class="uk-grid uk-grid-column-large" uk-grid>
<div class="uk-margin-top uk-width-auto@l uk-width-1-1"> <div class="uk-margin-xsmall-top uk-width-auto@l uk-width-1-1">
<div class="uk-grid uk-grid-column-large uk-flex-middle" uk-grid> <div class="uk-grid uk-grid-column-large uk-flex-middle" uk-grid>
<div class="uk-width-auto@l uk-width-1-1 uk-flex uk-flex-center"> <div class="uk-width-auto@l uk-width-1-1 uk-flex uk-flex-center">
<button class="uk-button uk-button-primary uk-flex uk-flex-middle uk-flex-wrap" <button class="uk-button uk-button-primary uk-flex uk-flex-middle uk-flex-wrap"
@ -77,11 +85,21 @@ import {ClearCacheService} from "../../../../openaireLibrary/services/clear-cach
<!-- Full width error message --> <!-- Full width error message -->
<div *ngIf="uploadError" class="uk-text-danger uk-margin-small-top uk-width-1-1">{{uploadError}}</div> <div *ngIf="uploadError" class="uk-text-danger uk-margin-small-top uk-width-1-1">{{uploadError}}</div>
</div> </div>
<div class="uk-width-1-2@m"> <div class="uk-width-1-3@m">
<div input [formInput]="communityFb.get('status')" <div input [formInput]="communityFb.get('status')"
placeholder="Visibility status for your community's profile." placeholder="Visibility status for your community's profile."
[options]="statuses" type="select"></div> [options]="statuses" type="select"></div>
</div> </div>
<div class="uk-width-1-3@m">
<div input [formInput]="communityFb.get('claim')"
placeholder="Who can create links for your community"
[options]="claimOptions" type="select"></div>
</div>
<div class="uk-width-1-3@m">
<div input [formInput]="communityFb.get('membership')"
placeholder="Who can join"
[options]="membershipOptions" type="select"></div>
</div>
</div> </div>
</form> </form>
`, `,
@ -90,10 +108,22 @@ import {ClearCacheService} from "../../../../openaireLibrary/services/clear-cach
export class EditCommunityComponent { export class EditCommunityComponent {
public communityFb: UntypedFormGroup; public communityFb: UntypedFormGroup;
public statuses: Option[] = [ public statuses: Option[] = [
{label: 'Visible', value: 'all'}, // {label: 'Visible', value: 'all'},
{label: 'Visible to managers', value: 'manager'}, {label: 'Visible', value: 'PUBLIC'},
// {label: 'Visible to managers', value: 'manager'},
{label: 'Visible to managers', value: 'RESTRICTED'},
{label: 'Hidden', value: 'hidden'} {label: 'Hidden', value: 'hidden'}
] ]
public claimOptions: Option[] = [
{label: 'Logged in users', value: 'all'},
{label: 'Members only', value: 'membersOnly'},
{label: 'Managers only', value: 'managersOnly'}
]
public membershipOptions: Option[] = [
{label: 'Anyone can join', value: 'open'},
{label: 'By invitation', value: 'byInvitation'}
]
public community: CommunityInfo; public community: CommunityInfo;
public isNew: boolean; public isNew: boolean;
public properties: EnvProperties = properties public properties: EnvProperties = properties
@ -131,8 +161,12 @@ export class EditCommunityComponent {
communityId: this.fb.control(this.community.communityId), communityId: this.fb.control(this.community.communityId),
name: this.fb.control(this.community.title, Validators.required), name: this.fb.control(this.community.title, Validators.required),
shortName: this.fb.control(this.community.shortTitle, Validators.required), shortName: this.fb.control(this.community.shortTitle, Validators.required),
displayName: this.fb.control(this.community.displayTitle, Validators.required),
displayShortName: this.fb.control(this.community.displayShortTitle, Validators.required),
description: this.fb.control(this.community.description), description: this.fb.control(this.community.description),
status: this.fb.control(this.community.status), status: this.fb.control(this.community.status),
claim: this.fb.control(this.community.claim),
membership: this.fb.control(this.community.membership),
managers: this.fb.control(this.community.managers), managers: this.fb.control(this.community.managers),
isUpload: this.fb.control(this.community.isUpload), isUpload: this.fb.control(this.community.isUpload),
logoUrl: this.fb.control(this.community.logoUrl) logoUrl: this.fb.control(this.community.logoUrl)
@ -158,6 +192,7 @@ export class EditCommunityComponent {
if (!this.isAdmin) { if (!this.isAdmin) {
setTimeout(() => { setTimeout(() => {
this.communityFb.get('shortName').disable(); this.communityFb.get('shortName').disable();
this.communityFb.get('name').disable();
}, 0); }, 0);
} }
} }
@ -166,7 +201,7 @@ export class EditCommunityComponent {
} }
public get isAdmin() { public get isAdmin() {
return Session.isPortalAdministrator(this.user); return Session.isPortalAdministrator(this.user) || Session.isCommunityCurator(this.user);
} }
public get disabled(): boolean { public get disabled(): boolean {
@ -213,8 +248,7 @@ export class EditCommunityComponent {
this.removePhoto(); this.removePhoto();
this.subscriptions.push(this.communityService.updateCommunity( this.subscriptions.push(this.communityService.updateCommunity(
this.properties.communityAPI + this.community.communityId, this.communityFb.getRawValue()).subscribe(() => { this.properties.communityAPI + this.community.communityId, this.communityFb.getRawValue()).subscribe(() => {
this._clearCacheService.clearCache("Community saved"); this._clearCacheService.clearCacheInRoute("Community saved",this.community.communityId,"/");
this._clearCacheService.purgeBrowserCache("Community saved", this.community.communityId);
this.communityService.getCommunity(this.community.communityId, true).subscribe(community => { this.communityService.getCommunity(this.community.communityId, true).subscribe(community => {
NotificationHandler.rise(community.shortTitle + ' has been <b>successfully created</b>'); NotificationHandler.rise(community.shortTitle + ' has been <b>successfully created</b>');
callback(community); callback(community);
@ -227,8 +261,7 @@ export class EditCommunityComponent {
})); }));
} else { } else {
this.subscriptions.push(this.communityService.updateCommunity(this.properties.communityAPI + this.community.communityId, this.communityFb.getRawValue()).subscribe(() => { this.subscriptions.push(this.communityService.updateCommunity(this.properties.communityAPI + this.community.communityId, this.communityFb.getRawValue()).subscribe(() => {
this._clearCacheService.clearCache("Community updated"); this._clearCacheService.clearCacheInRoute("Community saved",this.community.communityId,"/");
this._clearCacheService.purgeBrowserCache("Community updated", this.community.communityId);
this.communityService.getCommunity(this.community.communityId, true).subscribe(community => { this.communityService.getCommunity(this.community.communityId, true).subscribe(community => {
NotificationHandler.rise(community.shortTitle + ' has been <b>successfully saved</b>'); NotificationHandler.rise(community.shortTitle + ' has been <b>successfully saved</b>');
callback(community); callback(community);

View File

@ -11,19 +11,8 @@ import {Subscription} from "rxjs";
selector: 'community-profile', selector: 'community-profile',
template: ` template: `
<div page-content> <div page-content>
<div header> <div actions class="uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-middle uk-margin-medium-top info"> <div class="uk-container">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Community
Profile
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<community-info tab="profile"></community-info>
</div>
<div actions>
<div class="uk-container uk-section-xsmall">
<div class="uk-flex uk-flex-center uk-flex-right@m"> <div class="uk-flex uk-flex-center uk-flex-right@m">
<button class="uk-button uk-button-default uk-margin-right" <button class="uk-button uk-button-default uk-margin-right"
(click)="reset()" [class.uk-disabled]="loading || !editCommunityComponent.dirty" (click)="reset()" [class.uk-disabled]="loading || !editCommunityComponent.dirty"

View File

@ -5,7 +5,6 @@ import {PageContentModule} from "../../../openaireLibrary/dashboard/sharedCompon
import {ProfileComponent} from "./profile.component"; import {ProfileComponent} from "./profile.component";
import {EditCommunityModule} from "./edit-community/edit-community.module"; import {EditCommunityModule} from "./edit-community/edit-community.module";
import {LoadingModule} from "../../../openaireLibrary/utils/loading/loading.module"; import {LoadingModule} from "../../../openaireLibrary/utils/loading/loading.module";
import {CommunityInfoModule} from "../community-info.module";
@NgModule({ @NgModule({
imports: [ imports: [
@ -17,8 +16,7 @@ import {CommunityInfoModule} from "../community-info.module";
]), ]),
PageContentModule, PageContentModule,
EditCommunityModule, EditCommunityModule,
LoadingModule, LoadingModule
CommunityInfoModule,
], ],
declarations: [ProfileComponent], declarations: [ProfileComponent],
exports: [ProfileComponent] exports: [ProfileComponent]

View File

@ -31,7 +31,7 @@ import {ConnectRIGuard} from "../openaireLibrary/connect/communityGuard/connectR
{ {
path: 'customize-layout', path: 'customize-layout',
loadChildren: () => import('./customization/customization.module').then(m => m.CustomizationModule), loadChildren: () => import('./customization/customization.module').then(m => m.CustomizationModule),
data: {hasSidebar: true, hasHeader: false} data: {hasInternalSidebar: true, hasHeader: false}
}, },
{ {
path: 'user-info', path: 'user-info',

View File

@ -13,26 +13,31 @@ declare var UIkit;
template: ` template: `
<div page-content> <div page-content>
<div header> <div header>
<div class="uk-flex uk-flex-middle uk-margin-top info">
<img src="assets/common-assets/placeholder.png" class="uk-margin-right">
<div>
<div class="uk-margin-remove uk-text-background uk-text-bold uk-h6">Admin Dashboard - Manage Options</div>
<h1 class="uk-h4 uk-margin-remove">Super Admin</h1>
</div>
</div>
<admin-tabs tab="customization" portal="connect"></admin-tabs> <admin-tabs tab="customization" portal="connect"></admin-tabs>
</div> </div>
<div inner> <div inner>
<div>
<div class="uk-alert uk-alert-warning uk-margin-top "> <div class="uk-alert uk-alert-warning uk-margin-top ">
<div class="uk-text-large">Use only after connect deployment. And only if there are css updates!</div> <div class="uk-text-large">Use only after connect deployment. And only if there are css updates!</div>
Press the following button to update the timestamp in the saved layouts and recreate the css files. Press the following button to update the timestamp in the saved layouts and recreate the css files.
</div> </div>
<button (click)="updateCss()" class="uk-button uk-button-danger" [class.uk-disabled]="savingChanges"> Update CSS</button> <button (click)="updateCss()" class="uk-button uk-button-danger" [class.uk-disabled]="savingChanges"> Update CSS</button>
<button (click)="purgeBrowserCache()" class="uk-button uk-button-danger uk-margin-left" [class.uk-disabled]="savingChanges"> Purge Browser Cache</button> <hr>
</div>
<div class="uk-margin-medium-top">
<div>Purge ICM cache for all communities</div>
<ng-container *ngIf="properties.domain != 'production'"> <button (click)="purgeBrowserCache()" class="uk-button uk-button-danger uk-margin-top" [class.uk-disabled]="savingChanges"> Purge Browser Cache</button>
<hr>
</div>
<div class="uk-margin-medium-top">
<div>Reload cache requests either per community or for all communities</div>
<div input [(value)]="community" [placeholder]="'e.g. galaxy'" class="uk-width-1-2 uk-margin-top"></div>
<div input [(value)]="route" [placeholder]="'Route e.g. /'" class="uk-width-1-2 uk-margin-top"></div>
<button (click)="forceReloadCache()" class="uk-button uk-button-danger uk-margin-top" [class.uk-disabled]="savingChanges"> Reload Cache</button>
</div>
<!--<ng-container *ngIf="properties.domain != 'production'">
<hr> <hr>
<div class="uk-alert uk-alert-danger uk-margin-top "> <div class="uk-alert uk-alert-danger uk-margin-top ">
Delete after next deployment Delete after next deployment
@ -42,7 +47,7 @@ declare var UIkit;
</div> </div>
<div input [(value)]="community" [placeholder]="'e.g. galaxy'"></div> <div input [(value)]="community" [placeholder]="'e.g. galaxy'"></div>
<button (click)="deleteLayout()" class="uk-button uk-button-danger" [class.uk-disabled]="!community"> Delete layout</button> <button (click)="deleteLayout()" class="uk-button uk-button-danger" [class.uk-disabled]="!community"> Delete layout</button>
</ng-container> </ng-container>-->
</div> </div>
</div> </div>
@ -51,7 +56,10 @@ declare var UIkit;
export class ConnectAdminCustomizationComponent implements OnInit { export class ConnectAdminCustomizationComponent implements OnInit {
private subscriptions: any[] = []; private subscriptions: any[] = [];
savingChanges = false; savingChanges = false;
cssCreated: number = 0;
totalLayouts: number = 0;
community; community;
route;
properties = properties; properties = properties;
constructor( private customizationService: CustomizationService, private _clearCacheService: ClearCacheService, constructor( private customizationService: CustomizationService, private _clearCacheService: ClearCacheService,
@ -75,6 +83,7 @@ export class ConnectAdminCustomizationComponent implements OnInit {
let defaultCssIsSaved = false; let defaultCssIsSaved = false;
this.subscriptions.push(this.customizationService.getLayouts(properties, ).subscribe(layouts => { this.subscriptions.push(this.customizationService.getLayouts(properties, ).subscribe(layouts => {
this.totalLayouts = layouts ? layouts.length : 0;
for(let layout of layouts){ for(let layout of layouts){
layout.date = date; layout.date = date;
if(layout.portalPid == 'connect'){ if(layout.portalPid == 'connect'){
@ -88,11 +97,13 @@ export class ConnectAdminCustomizationComponent implements OnInit {
} }
} }
if(!connectCssIsSaved){ if(!connectCssIsSaved){
this.totalLayouts++;
let layout = new Layout("connect", null); let layout = new Layout("connect", null);
layout.date = date; layout.date = date;
this.callSaveAndCreate(layout, "connect") this.callSaveAndCreate(layout, "connect")
} }
if(!defaultCssIsSaved){ if(!defaultCssIsSaved){
this.totalLayouts++;
let layout = new Layout("default", null); let layout = new Layout("default", null);
layout.date = date; layout.date = date;
this.callSaveAndCreate(layout, "connect") this.callSaveAndCreate(layout, "connect")
@ -109,16 +120,22 @@ export class ConnectAdminCustomizationComponent implements OnInit {
pos: 'bottom-right' pos: 'bottom-right'
}); });
this.cssCreated++;
if(this.cssCreated == this.totalLayouts) {
this.savingChanges = false;
}
})); }));
})); }));
} }
purgeBrowserCache() { purgeBrowserCache() {
this.savingChanges = true;
this.subscriptions.push(this.communitiesService.getCommunities(this.properties, this.properties.communityAPI + 'communities').subscribe( this.subscriptions.push(this.communitiesService.getCommunities(this.properties, this.properties.communityAPI + 'communities').subscribe(
communities => { communities => {
communities.forEach(community => { communities.forEach(community => {
this._clearCacheService.purgeBrowserCache("Layout added/ updated", community.communityId); this._clearCacheService.purgeBrowserCache("Layout added/ updated", community.communityId);
}); });
this.savingChanges = false;
} }
)); ));
this._clearCacheService.purgeBrowserCache("Layout added/ updated", "connect"); this._clearCacheService.purgeBrowserCache("Layout added/ updated", "connect");
@ -131,4 +148,20 @@ export class ConnectAdminCustomizationComponent implements OnInit {
})); }));
} }
} }
forceReloadCache() {
if (this.community) {
this._clearCacheService.clearCacheInRoute("Clear cache", this.community, this.route ? this.route : "/")
} else {
this.savingChanges = true;
this.subscriptions.push(this.communitiesService.getCommunities(this.properties, this.properties.communityAPI + 'communities').subscribe(
communities => {
communities.forEach(community => {
this._clearCacheService.clearCacheInRoute("Clear cache for "+ community.communityId, community.communityId, this.route ? this.route : "/")
});
this.savingChanges = false;
}
));
}
}
} }

View File

@ -36,12 +36,21 @@
<div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid> <div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid>
<div *ngIf="!getCommunityContentProvider(result)"> <div *ngIf="!getCommunityContentProvider(result)">
<div class="uk-padding-small uk-padding-remove-horizontal"> <div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="addContentProvider(result)" class="uk-button uk-button-link uk-flex uk-flex-middle"> <a class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="add" [flex]="true"></icon> <icon name="add" [flex]="true"></icon>
<span class="uk-margin-small-left"> <span class="uk-margin-small-left">
Add Add
</span> </span>
</a> </a>
<div uk-dropdown="mode:click">
<ul class="uk-nav uk-dropdown-nav">
<li class="uk-nav-header uk-margin-left">Add</li>
<li><a (click)="addContentProvider(result,true, false)"> as content source</a></li>
<li ><a (click)="addContentProvider(result,false, true)">as suggestion for deposit</a></li>
<li ><a (click)="addContentProvider(result,true, true)"> both</a></li>
</ul>
</div>
</div> </div>
</div> </div>
<div *ngIf="getCommunityContentProvider(result)"> <div *ngIf="getCommunityContentProvider(result)">

View File

@ -102,8 +102,8 @@ export class AddContentProvidersComponent implements OnInit {
"</div>" "</div>"
} }
public addContentProvider(contentProvider: SearchResult) { public addContentProvider(contentProvider: SearchResult, content = true, deposit =false) {
this.subscriptions.push(this.manageCommunityContentProvidersService.addContentProvider(this.properties, this.community.communityId, contentProvider).subscribe( this.subscriptions.push(this.manageCommunityContentProvidersService.addContentProvider(this.properties, this.community.communityId, contentProvider, content, deposit).subscribe(
data => { data => {
this.communityContentProviders.push(data); this.communityContentProviders.push(data);
this._clearCacheService.purgeBrowserCache(this.openAIREEntities.DATASOURCE+" added", this.community.communityId); this._clearCacheService.purgeBrowserCache(this.openAIREEntities.DATASOURCE+" added", this.community.communityId);
@ -120,7 +120,7 @@ export class AddContentProvidersComponent implements OnInit {
public removeContentProvider(contentProvider) { public removeContentProvider(contentProvider) {
let communityContentProvider = this.getCommunityContentProvider(contentProvider); let communityContentProvider = this.getCommunityContentProvider(contentProvider);
let contentProviderId: string = communityContentProvider['id']; let contentProviderId: string = communityContentProvider['openaireId'];
this.subscriptions.push(this.manageCommunityContentProvidersService.removeContentProvider(this.properties, this.community.communityId, contentProviderId).subscribe( this.subscriptions.push(this.manageCommunityContentProvidersService.removeContentProvider(this.properties, this.community.communityId, contentProviderId).subscribe(
data => { data => {
let index = this.communityContentProviders.indexOf(communityContentProvider); let index = this.communityContentProviders.indexOf(communityContentProvider);

View File

@ -10,7 +10,6 @@ import {ErrorMessagesModule} from '../../openaireLibrary/utils/errorMessages.mod
import {AlertModalModule} from '../../openaireLibrary/utils/modal/alertModal.module'; import {AlertModalModule} from '../../openaireLibrary/utils/modal/alertModal.module';
import {CommonModule} from '@angular/common'; import {CommonModule} from '@angular/common';
import {PageContentModule} from "../../openaireLibrary/dashboard/sharedComponents/page-content/page-content.module"; import {PageContentModule} from "../../openaireLibrary/dashboard/sharedComponents/page-content/page-content.module";
import {CommunityInfoModule} from "../community-info/community-info.module";
import {InputModule} from "../../openaireLibrary/sharedComponents/input/input.module"; import {InputModule} from "../../openaireLibrary/sharedComponents/input/input.module";
import {SearchInputModule} from "../../openaireLibrary/sharedComponents/search-input/search-input.module"; import {SearchInputModule} from "../../openaireLibrary/sharedComponents/search-input/search-input.module";
import {NoLoadPaging} from "../../openaireLibrary/searchPages/searchUtils/no-load-paging.module"; import {NoLoadPaging} from "../../openaireLibrary/searchPages/searchUtils/no-load-paging.module";
@ -29,6 +28,9 @@ import {AddContentProvidersComponent} from "./add-content-providers.component";
import {ManageCommunityContentProvidersService} from "../../services/manageContentProviders.service"; import {ManageCommunityContentProvidersService} from "../../services/manageContentProviders.service";
import {SearchDataprovidersService} from "../../openaireLibrary/services/searchDataproviders.service"; import {SearchDataprovidersService} from "../../openaireLibrary/services/searchDataproviders.service";
import {CriteriaModule} from "./criteria/criteria.module"; import {CriteriaModule} from "./criteria/criteria.module";
import {MatSlideToggleModule} from "@angular/material/slide-toggle";
import {CKEditorModule} from "ng2-ckeditor";
import {ValidateEnabledPageModule} from "../../utils/validateEnabledPage.module";
@NgModule({ @NgModule({
imports: [ imports: [
@ -42,7 +44,6 @@ import {CriteriaModule} from "./criteria/criteria.module";
AlertModalModule, AlertModalModule,
SearchDataprovidersServiceModule, SearchDataprovidersServiceModule,
PageContentModule, PageContentModule,
CommunityInfoModule,
InputModule, InputModule,
SearchInputModule, SearchInputModule,
RouterModule.forChild([ RouterModule.forChild([
@ -50,7 +51,7 @@ import {CriteriaModule} from "./criteria/criteria.module";
path: '', component: ManageContentProvidersComponent path: '', component: ManageContentProvidersComponent
} }
]), ]),
NoLoadPaging, LoadingModule, IconsModule, FullScreenModalModule, ResultPreviewModule, CriteriaModule NoLoadPaging, LoadingModule, IconsModule, FullScreenModalModule, ResultPreviewModule, CriteriaModule, MatSlideToggleModule, CKEditorModule, ReactiveFormsModule, ValidateEnabledPageModule
], ],
declarations: [ declarations: [
ManageContentProvidersComponent, ManageContentProvidersComponent,

View File

@ -1,18 +1,46 @@
import {Option} from "../../openaireLibrary/sharedComponents/input/input.component"; import {Option} from "../../openaireLibrary/sharedComponents/input/input.component";
import {Criteria} from "../../openaireLibrary/utils/entities/contentProvider";
export class CriteriaUtils { export class CriteriaUtils {
public static readonly fields: Option[] = [ public readonly fields: Option[] = [
{value: 'title', label: 'Title'},
{value: 'author', label: 'Author\'s name'}, {value: 'author', label: 'Author\'s name'},
{value: 'title', label: 'Title'},
{value: 'orcid', label: 'Author\'s ORCID'}, {value: 'orcid', label: 'Author\'s ORCID'},
{value: 'contributor', label: 'Contributor'}, {value: 'contributor', label: 'Contributor'},
{value: 'description', label: 'Description'} {value: 'description', label: 'Abstract'},
{value: 'subject', label: 'Subject'},
{value: 'fos', label: 'Field of Science'},
{value: 'sdg', label: 'SDG'},
{value: 'publisher', label: 'Publisher'},
{value: 'publicationyear', label: 'Publication Year'}
] ]
public readonly numericFields: string[] = ['publicationyear'];
public static readonly verbs: Option[] = [ public readonly verbs: Option[] = [
{value: 'contains', label: 'contains'}, {value: 'contains', label: 'contains'},
{value: 'equals', label: 'equals'}, {value: 'equals', label: 'equals'},
{value: 'not_contains', label: 'not contains'}, {value: 'not_contains', label: 'not contains'},
{value: 'not_equals', label: 'not equals'} {value: 'not_equals', label: 'not equals'},
{value: 'starts_with', label: 'starts with'}
] ]
public readonly verbsForNumbers: Option[] = [
{value: 'equals', label: 'equals'},
{value: 'lesser_than', label: 'lesser than'},
{value: 'greater_than', label: 'greater than'}
]
public getFiltersAsText(criteria: Criteria[], shortVersion=true): string {
let text = criteria.slice(0, shortVersion?3:criteria.length).map((criterion, index) => (index + 1) + ". " + criterion.constraint.map(constraint => {
let field = this.fields.find(field => field.value === constraint.field)?.label;
let matchCase = false;
if (!constraint.verb.includes('_caseinsensitive')) {
matchCase = true;
}
let verb = [...this.verbs,...this.verbsForNumbers].find(verb => verb.value === constraint.verb.replace("_caseinsensitive", "")).label;
let value = '"' + constraint.value + '"' + (matchCase ? " (Match case)" : "");
let expFeature = field =='Publisher' || field == 'Publication Year'? `<span *ngIf="constraint.get('field').value == 'publisher' || constraint.get('field').value == 'publicationyear'" class="
uk-margin-xsmall-left uk-padding-remove-vertical uk-label uk-label-warning uk-text-lowercase uk-padding-xsmall">experimental feature</span>`:''
return field + " " + verb + " " + value + expFeature;
}).join(" <b>and</b> "));
return text.join("<br>");
}
} }

View File

@ -1,33 +1,21 @@
<div class="uk-section uk-position-relative" style="min-height: 60vh"> <div class="uk-position-relative" [style]=" height == -1?'': 'min-height:60vh'">
<div *ngIf="loading" class="uk-position-center"> <div *ngIf="loading" class="uk-position-center">
<loading></loading> <loading></loading>
</div> </div>
<ng-container *ngIf="!loading"> <ng-container *ngIf="!loading">
<div class="uk-flex uk-flex-center uk-margin-medium-bottom"> <div class="criteria uk-overflow-auto uk-position-relative" [ngStyle]="{'height.px': criteriaHeight?criteriaHeight:null}">
<a (click)="addCriteria()" class="uk-flex uk-flex-middle uk-button uk-button-primary" <div *ngIf="criteria.length == 0" class="uk-text-center uk-position-center">
uk-tooltip="<div>Add filter to limit research results.<br>Results which satisfy any of the selected filters will be included in your community.</div>"> <ng-content select="[no-criteria]"></ng-content>
<icon name="add" [flex]="true"></icon>
<span class="uk-margin-small-left">Add filter</span>
</a>
</div> </div>
<div *ngIf="criteria.length == 0" class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold"> <form *ngIf="criteria.length > 0" [formGroup]="selectionCriteriaForm">
<div *ngIf="dataProvider">No filters for {{dataProvider.officialname}}.</div>
<div>If no filters are specified, all {{openaireEntities.RESULTS | lowercase}} of this {{openaireEntities.DATASOURCE | lowercase}} will be included in your
{{openaireEntities.COMMUNITY | lowercase}}.
</div>
</div>
<form *ngIf="criteria.length > 0" [formGroup]="selectionCriteria">
<div formArrayName="criteria" class="uk-margin-bottom"> <div formArrayName="criteria" class="uk-margin-bottom">
<no-load-paging (pageChange)="updatePage($event)" [page]="page" [totalResults]="criteria.length"
[pageSize]="pageSize" [type]="'filter' + (criteria.length > 1?'s':'')">
</no-load-paging>
<ul class="uk-list uk-list-xlarge uk-margin-top uk-margin-bottom"> <ul class="uk-list uk-list-xlarge uk-margin-top uk-margin-bottom">
<li *ngFor="let criterion of currentPage; let i=index"> <li *ngFor="let criterion of criteria.controls; let i=index">
<div [formGroupName]="getIndex(i).toString()" class="uk-flex"> <div [id]="'criterion-' + i.toString()" [formGroupName]="i.toString()" class="uk-flex">
<h3 class="uk-padding uk-margin-remove-bottom uk-margin-top"> <h3 class="uk-padding uk-margin-remove-bottom uk-margin-top">
{{getIndex(i) + 1}} {{i + 1}}
</h3> </h3>
<div class="uk-width-expand uk-padding-small criterion" formArrayName="constraint"> <div class="uk-width-expand uk-padding-small uk-border uk-border-rounded" formArrayName="constraint">
<div class="uk-flex-middle uk-grid uk-margin-small-bottom uk-visible@l" uk-grid> <div class="uk-flex-middle uk-grid uk-margin-small-bottom uk-visible@l" uk-grid>
<div class="uk-width-1-4"> <div class="uk-width-1-4">
<label class="uk-text-uppercase uk-text-bold">Field</label> <label class="uk-text-uppercase uk-text-bold">Field</label>
@ -42,21 +30,27 @@
<label class="uk-text-bold uk-text-uppercase">Match Case</label> <label class="uk-text-bold uk-text-uppercase">Match Case</label>
</div> </div>
</div> </div>
<div *ngFor="let constraint of getConstraint(getIndex(i)).controls; let j=index" [formGroupName]="j.toString()" <div *ngFor="let constraint of getConstraint(i).controls; let j=index" [formGroupName]="j.toString()"
class="uk-margin-bottom uk-hidden@l"> class="uk-margin-bottom uk-hidden@l">
<span *ngIf="constraint.get('field').value == 'publisher' || constraint.get('field').value == 'publicationyear'" class="
uk-padding-remove-vertical uk-label uk-label-warning uk-text-lowercase uk-float-left uk-padding-xsmall">experimental feature</span>
<div class="uk-flex-middle uk-grid-small uk-margin-medium-bottom" uk-grid> <div class="uk-flex-middle uk-grid-small uk-margin-medium-bottom" uk-grid>
<div class="uk-flex uk-flex-right uk-width-1-1"> <div class="uk-flex uk-flex-right uk-width-1-1">
<button class="uk-close uk-icon" (click)="removeConstraint(getIndex(i), j)"> <button class="uk-close uk-icon" (click)="removeConstraint(i, j)">
<icon name="close" ratio="1.5" [flex]="true" <icon name="close" ratio="1.5" [flex]="true"
[attr.uk-tooltip]="(getConstraint(getIndex(i)).length === 1?'By removing this constraint, the filter will be removed too':null)"></icon> [attr.uk-tooltip]="(getConstraint(i).length === 1?'By removing this constraint, the ' + entityType + ' will be removed too':null)"></icon>
</button> </button>
</div> </div>
<div class="uk-width-1-1" input type="select" inputClass="border-bottom" [placeholder]="{static: true, label: 'Choose a field'}" <div class="uk-width-1-1" input type="select" inputClass="border-bottom" [placeholder]="{static: true, label: 'Choose a field'}"
[options]="fields" [formInput]="constraint.get('field')"> [options]="criteriaUtils.fields" [formInput]="constraint.get('field')" (valueChange)="resetFieldWhenValueChange(constraint)">
<label class="uk-text-uppercase uk-text-bold uk-width-1-3 uk-text-truncate">Field:</label> <label class="uk-text-uppercase uk-text-bold uk-width-1-3 uk-text-truncate">Field:</label>
</div> </div>
<div class="uk-width-1-1" input type="select" inputClass="border-bottom" <div *ngIf="criteriaUtils.numericFields.indexOf(constraint.get('field').value) == -1" class="uk-width-1-1" input type="select" inputClass="border-bottom"
[options]="verbs" [formInput]="constraint.get('verb')"> [options]="criteriaUtils.verbs" [formInput]="constraint.get('verb')">
<label class="uk-text-uppercase uk-text-bold uk-width-1-3 uk-text-truncate">Operator:</label>
</div>
<div *ngIf="criteriaUtils.numericFields.indexOf(constraint.get('field').value) != -1" class="uk-width-1-1" input type="select" inputClass="border-bottom"
[options]="criteriaUtils.verbsForNumbers" [formInput]="constraint.get('verb')">
<label class="uk-text-uppercase uk-text-bold uk-width-1-3 uk-text-truncate">Operator:</label> <label class="uk-text-uppercase uk-text-bold uk-width-1-3 uk-text-truncate">Operator:</label>
</div> </div>
<div class="uk-width-1-1" input [placeholder]="{static: true, label: 'Type a keyword'}" <div class="uk-width-1-1" input [placeholder]="{static: true, label: 'Type a keyword'}"
@ -76,15 +70,23 @@
</div> </div>
</div> </div>
</div> </div>
<div *ngFor="let constraint of getConstraint(getIndex(i)).controls; let j=index" <div *ngFor="let constraint of getConstraint(i).controls; let j=index"
[formGroupName]="j.toString()" class="uk-margin-bottom uk-visible@l"> [formGroupName]="j.toString()" class="uk-margin-bottom uk-visible@l">
<span *ngIf="constraint.get('field').value == 'publisher' || constraint.get('field').value == 'publicationyear'" class="
uk-padding-remove-vertical uk-label uk-label-warning uk-text-lowercase uk-padding-xsmall">experimental feature</span>
<div class="uk-flex uk-flex-middle uk-grid" uk-grid> <div class="uk-flex uk-flex-middle uk-grid" uk-grid>
<div class="uk-width-1-4" input type="select" inputClass="border-bottom" [placeholder]="{static: true, label: 'Choose a field'}" <div class="uk-width-1-4" input type="select" inputClass="border-bottom" [placeholder]="{static: true, label: 'Choose a field'}"
[options]="fields" [formInput]="constraint.get('field')"></div> [options]="criteriaUtils.fields" [formInput]="constraint.get('field')"></div>
<div class="uk-width-1-4" input type="select" inputClass="border-bottom" <div *ngIf="criteriaUtils.numericFields.indexOf(constraint.get('field').value) == -1" class="uk-width-1-4" input type="select" inputClass="border-bottom"
[options]="verbs" [formInput]="constraint.get('verb')"></div> [options]="criteriaUtils.verbs" [formInput]="constraint.get('verb')"></div>
<div class="uk-width-1-4" input [placeholder]="{static: true, label: 'Type a keyword'}" <div *ngIf="criteriaUtils.numericFields.indexOf(constraint.get('field').value) != -1" class="uk-width-1-4" input type="select" inputClass="border-bottom"
[options]="criteriaUtils.verbsForNumbers" [formInput]="constraint.get('verb')"></div>
<div *ngIf="constraint.get('field').value !== 'fos' && constraint.get('field').value !== 'sdg'" class="uk-width-1-4" inputClass="flat small" input [placeholder]="{static: true, label: 'Type a keyword'}"
[formInput]="constraint.get('value')"></div> [formInput]="constraint.get('value')"></div>
<div *ngIf="constraint.get('field').value === 'fos'" class="uk-width-1-4" inputClass="flat small" input [placeholder]="{static: true, label: 'Choose a FoS'}"
[formInput]="constraint.get('value')" type="select" [options]="fos"></div>
<div *ngIf="constraint.get('field').value === 'sdg'" class="uk-width-1-4" inputClass="flat small" input [placeholder]="{static: true, label: 'Choose a FoS'}"
[formInput]="constraint.get('value')" type="select" [options]="sdg"></div>
<div class="uk-width-expand"> <div class="uk-width-expand">
<mat-slide-toggle [checked]="constraint.get('verb_suffix').value === ''" class="uk-margin-left" <mat-slide-toggle [checked]="constraint.get('verb_suffix').value === ''" class="uk-margin-left"
[attr.uk-tooltip]="(constraint.get('verb_suffix').value === ''?('Only \'\'' + constraint.get('value').value + '\'\' matches'): [attr.uk-tooltip]="(constraint.get('verb_suffix').value === ''?('Only \'\'' + constraint.get('value').value + '\'\' matches'):
@ -92,15 +94,15 @@
(change)="caseSensitive($event, constraint)"></mat-slide-toggle> (change)="caseSensitive($event, constraint)"></mat-slide-toggle>
</div> </div>
<div class="uk-flex uk-flex-center"> <div class="uk-flex uk-flex-center">
<button class="uk-close uk-icon" (click)="removeConstraint(getIndex(i), j)"> <button class="uk-close uk-icon" (click)="removeConstraint(i, j)">
<icon name="close" ratio="1.5" [flex]="true" <icon name="close" ratio="1.5" [flex]="true"
[attr.uk-tooltip]="(getConstraint(getIndex(i)).length === 1?'By removing this constraint, the filter will be removed too':null)"></icon> [attr.uk-tooltip]="(getConstraint(i).length === 1?'By removing this constraint, the ' + entityType + ' will be removed too':null)"></icon>
</button> </button>
</div> </div>
</div> </div>
</div> </div>
<div class="uk-margin-top uk-width-1-1 uk-flex uk-flex-center uk-flex-left@l"> <div class="uk-margin-top uk-width-1-1 uk-flex uk-flex-center uk-flex-left@l">
<a (click)="addConstraint(getIndex(i))" class="uk-flex uk-flex-middle uk-button uk-button-link"> <a (click)="addConstraint(i)" class="uk-flex uk-flex-middle uk-button uk-button-link">
<icon name="add" [flex]="true"></icon> <icon name="add" [flex]="true"></icon>
<span class="uk-margin-small-left">Add Constraint</span> <span class="uk-margin-small-left">Add Constraint</span>
</a> </a>
@ -109,12 +111,15 @@
</div> </div>
</li> </li>
</ul> </ul>
<div class="uk-margin-small-top">
<paging-no-load [currentPage]="page" [totalResults]="criteria.length" [size]="pageSize"
(pageChange)="updatePage($event)" customClasses="uk-flex-right@m uk-flex-center">
</paging-no-load>
</div>
</div> </div>
</form> </form>
</div>
<div class="uk-flex uk-flex-center uk-margin-top">
<a (click)="addCriteria()" class="uk-flex uk-flex-middle uk-button uk-button-primary"
[attr.uk-tooltip]="'<div>Add a ' + entityType + ' to limit research results.<br>Results which satisfy any of the selected ' + entityTypePlural + ' will be included in your ' + openaireEntities.COMMUNITY + '.</div>'">
<icon name="add" [flex]="true"></icon>
<span class="uk-margin-small-left">Add {{entityType}}</span>
</a>
</div>
</ng-container> </ng-container>
</div> </div>

View File

@ -1,8 +1,3 @@
@import (reference) "~src/assets/openaire-theme/less/_import-variables.less"; .criteria {
padding-right: 20px;
.criterion {
border: @global-border solid @global-border-width;
border-radius: @global-border-radius;
max-height: 400px;
overflow: auto;
} }

View File

@ -1,58 +1,99 @@
import {ChangeDetectorRef, Component, Input, OnInit} from '@angular/core';
import {EnvProperties} from '../../../openaireLibrary/utils/properties/env-properties';
import { import {
Constraint, AfterViewInit,
ContentProvider, ChangeDetectorRef,
Criteria, Component,
SelectionCriteria Input,
} from '../../../openaireLibrary/utils/entities/contentProvider'; OnChanges,
OnDestroy,
OnInit,
SimpleChanges
} from '@angular/core';
import {EnvProperties} from '../../../openaireLibrary/utils/properties/env-properties';
import {Constraint, Criteria, SelectionCriteria} from '../../../openaireLibrary/utils/entities/contentProvider';
import {AbstractControl, UntypedFormArray, UntypedFormBuilder, UntypedFormGroup, Validators} from '@angular/forms'; import {AbstractControl, UntypedFormArray, UntypedFormBuilder, UntypedFormGroup, Validators} from '@angular/forms';
import {ManageCommunityContentProvidersService} from '../../../services/manageContentProviders.service';
import {properties} from "../../../../environments/environment"; import {properties} from "../../../../environments/environment";
import {Option} from "../../../openaireLibrary/sharedComponents/input/input.component";
import {MatSlideToggleChange} from "@angular/material/slide-toggle"; import {MatSlideToggleChange} from "@angular/material/slide-toggle";
import {HelperFunctions} from "../../../openaireLibrary/utils/HelperFunctions.class"; import {HelperFunctions} from "../../../openaireLibrary/utils/HelperFunctions.class";
import {CriteriaUtils} from "../criteria-utils"; import {CriteriaUtils} from "../criteria-utils";
import {NotificationHandler} from "../../../openaireLibrary/utils/notification-handler"; import {NotificationHandler} from "../../../openaireLibrary/utils/notification-handler";
import {OpenaireEntities} from "../../../openaireLibrary/utils/properties/searchFields"; import {OpenaireEntities} from "../../../openaireLibrary/utils/properties/searchFields";
import {ISVocabulariesService} from "../../../openaireLibrary/utils/staticAutoComplete/ISVocabularies.service";
import {Subscription} from "rxjs";
@Component({ @Component({
selector: 'criteria', selector: 'criteria',
templateUrl: 'criteria.component.html', templateUrl: 'criteria.component.html',
styleUrls: ['criteria.component.less'] styleUrls: ['criteria.component.less']
}) })
export class CriteriaComponent implements OnInit { export class CriteriaComponent implements OnInit, OnChanges, AfterViewInit, OnDestroy {
@Input() @Input()
public dataProvider: ContentProvider; public entityType: string = 'filter';
public selectionCriteria: UntypedFormGroup; @Input()
public entityTypePlural: string = 'filters';
@Input()
public selectionCriteria: SelectionCriteria;
@Input()
public height: number = 0;
public criteriaHeight: number = 0;
public selectionCriteriaForm: UntypedFormGroup;
public properties: EnvProperties = properties; public properties: EnvProperties = properties;
public fields: Option[] = CriteriaUtils.fields; public criteriaUtils: CriteriaUtils = new CriteriaUtils();
public verbs: Option[] = CriteriaUtils.verbs; public fos: string[] = [];
public sdg: string[] = [];
public loading = true; public loading = true;
/** Paging */
public page: number = 1;
public pageSize: number = 5;
public openaireEntities = OpenaireEntities; public openaireEntities = OpenaireEntities;
private subscriptions: any[] = [];
constructor(private manageCommunityContentProvidersService: ManageCommunityContentProvidersService, constructor(private cdr: ChangeDetectorRef, private vocabulariesService: ISVocabulariesService,
private cdr: ChangeDetectorRef,
private fb: UntypedFormBuilder) { private fb: UntypedFormBuilder) {
} }
ngOnInit() { ngOnInit() {
this.reset();
this.loading = false; this.loading = false;
this.subscriptions.push(this.vocabulariesService.getVocabularyByType('fos', null, properties).subscribe((fos: any[]) => {
this.fos = fos.map(element => element.id);
}));
this.subscriptions.push(this.vocabulariesService.getVocabularyByType('sdg', null, properties).subscribe((sdg: any[]) => {
this.sdg = sdg.map(element => element.id);
}));
}
ngOnChanges(changes: SimpleChanges) {
if(changes.selectionCriteria){
this.reset();
}
this.calculateMaxHeight();
}
ngAfterViewInit() {
this.calculateMaxHeight();
}
ngOnDestroy() {
this.subscriptions.forEach(subscription => {
if (subscription instanceof Subscription) {
subscription.unsubscribe();
}
});
}
calculateMaxHeight() {
if(this.height) {
if(this.height > 0) {
/* Element height - margins(20 + 20) - button height(42) */
this.criteriaHeight = this.height - 40 - 42;
this.cdr.detectChanges();
}
}
} }
reset() { reset() {
this.page = 1; this.selectionCriteriaForm = this.fb.group({
if (this.dataProvider) {
this.selectionCriteria = this.fb.group({
criteria: this.fb.array([]) criteria: this.fb.array([])
}); });
let selectionCriteria = this.dataProvider.selectioncriteria; if (this.selectionCriteria?.criteria) {
if (selectionCriteria) {
selectionCriteria.criteria.forEach(criterion => { this.selectionCriteria.criteria.forEach(criterion => {
let constraintArray: UntypedFormArray = this.fb.array([]); let constraintArray: UntypedFormArray = this.fb.array([]);
criterion.constraint.forEach(constraint => { criterion.constraint.forEach(constraint => {
constraintArray.push(this.fb.group({ constraintArray.push(this.fb.group({
@ -68,26 +109,13 @@ export class CriteriaComponent implements OnInit {
}); });
} }
} }
}
get disabled() { get disabled() {
return this.loading || !this.dirty || this.selectionCriteria.invalid; return this.loading || !this.dirty || this.selectionCriteriaForm.invalid;
}
get currentPage(): AbstractControl[] {
if (this.criteria) {
return this.criteria.controls.slice((this.page - 1) * this.pageSize, this.page * this.pageSize);
} else {
return [];
}
}
getIndex(index: number): number {
return (this.page - 1)*this.pageSize + index;
} }
public get criteria(): UntypedFormArray { public get criteria(): UntypedFormArray {
return this.selectionCriteria.get('criteria') as UntypedFormArray; return this.selectionCriteriaForm.get('criteria') as UntypedFormArray;
} }
public getConstraint(i: number): UntypedFormArray { public getConstraint(i: number): UntypedFormArray {
@ -103,11 +131,9 @@ export class CriteriaComponent implements OnInit {
verb_suffix: this.fb.control('_caseinsensitive') verb_suffix: this.fb.control('_caseinsensitive')
}) })
]); ]);
this.criteria.insert(0, this.fb.group({ this.criteria.push(this.fb.group({constraint: constraintArray}));
constraint: constraintArray
}));
this.page = 1;
this.cdr.detectChanges(); this.cdr.detectChanges();
document.getElementById('criterion-' + (this.criteria.length - 1).toString()).scrollIntoView({behavior: 'smooth'});
} }
public addConstraint(i: number) { public addConstraint(i: number) {
@ -126,25 +152,22 @@ export class CriteriaComponent implements OnInit {
constraintArray.removeAt(j); constraintArray.removeAt(j);
if (constraintArray.length === 0) { if (constraintArray.length === 0) {
this.criteria.removeAt(i); this.criteria.removeAt(i);
while(this.currentPage.length === 0 && this.page > 0) {
this.page--;
}
} }
this.cdr.detectChanges(); this.cdr.detectChanges();
} }
get dataProviderCriteria(): Criteria[] { get criteriaArray(): Criteria[] {
return (this.dataProvider && this.dataProvider.selectioncriteria && this.dataProvider.selectioncriteria.criteria)?this.dataProvider.selectioncriteria.criteria:[]; return (this.selectionCriteria?.criteria) ? this.selectionCriteria?.criteria : [];
} }
get dirty() { get dirty() {
if(!this.dataProvider || !this.criteria) { if (!this.selectionCriteria && !this.criteria) {
return false; return false;
} else if(this.criteria.length !== this.dataProviderCriteria.length) { } else if (this.criteria.length !== this.criteriaArray.length) {
return true; return true;
} else { } else {
return this.dataProviderCriteria.filter((criterion, i) => { return this.criteriaArray.filter((criterion, i) => {
if(criterion.constraint.length !== this.getConstraint(i).length) { if (criterion.constraint.length !== this.getConstraint(i).length) {
return true; return true;
} else { } else {
let temp = this.getConstraint(i).value; let temp = this.getConstraint(i).value;
@ -156,23 +179,10 @@ export class CriteriaComponent implements OnInit {
} }
} }
save(callback: Function = null) { save(callback: (selectionCriteria) => void = null) {
if (this.selectionCriteria.valid) { if (this.selectionCriteriaForm.valid) {
this.loading = true; this.loading = true;
this.dataProvider.selectioncriteria = this.parseForm(this.selectionCriteria.value); callback(this.parseForm(this.selectionCriteriaForm.value));
this.manageCommunityContentProvidersService.saveContentProvider(this.properties, this.dataProvider).subscribe(() => {
this.reset();
if(callback) {
callback();
}
this.loading = false;
NotificationHandler.rise('Filters have been <b>successfully updated</b>');
}, error => {
this.loading = false;
this.handeError('An error has been occurred. Try again later!', error);
});
} else {
this.handeError('An error has been occurred. Try again later!');
} }
} }
@ -182,7 +192,7 @@ export class CriteriaComponent implements OnInit {
} }
caseSensitive(event: MatSlideToggleChange, constraint: AbstractControl) { caseSensitive(event: MatSlideToggleChange, constraint: AbstractControl) {
if(event.checked) { if (event.checked) {
constraint.get('verb_suffix').setValue(''); constraint.get('verb_suffix').setValue('');
} else { } else {
constraint.get('verb_suffix').setValue('_caseinsensitive'); constraint.get('verb_suffix').setValue('_caseinsensitive');
@ -194,7 +204,7 @@ export class CriteriaComponent implements OnInit {
} }
getSuffix(verb: string) { getSuffix(verb: string) {
if(verb.includes('_caseinsensitive')) { if (verb.includes('_caseinsensitive')) {
return '_caseinsensitive'; return '_caseinsensitive';
} else { } else {
return ''; return '';
@ -216,8 +226,13 @@ export class CriteriaComponent implements OnInit {
return selectionCriteria; return selectionCriteria;
} }
public updatePage(event) { resetFieldWhenValueChange(constraint){
this.page = event.value; // if field not numeric, but verb is numeric clear the verb
HelperFunctions.scroll(); if(this.criteriaUtils.numericFields.indexOf(constraint.get('field').value) == -1 && this.criteriaUtils.verbs.indexOf(constraint.get('verb').value)){
constraint.get('verb').setValue(this.criteriaUtils.verbs[0].value);
}
if(this.criteriaUtils.numericFields.indexOf(constraint.get('field').value) != -1 && this.criteriaUtils.numericFields.indexOf(constraint.get('verb').value)){
constraint.get('verb').setValue(this.criteriaUtils.verbsForNumbers[0].value);
}
} }
} }

View File

@ -1,4 +1,4 @@
import {Component, OnInit, ViewChild} from '@angular/core'; import {ChangeDetectorRef, Component, OnInit, SimpleChanges, ViewChild} from '@angular/core';
import {RemoveContentProvidersComponent} from './remove-content-providers.component'; import {RemoveContentProvidersComponent} from './remove-content-providers.component';
import {Title} from '@angular/platform-browser'; import {Title} from '@angular/platform-browser';
import { import {
@ -13,6 +13,9 @@ import {CommunityService} from "../../openaireLibrary/connect/community/communit
import {ContentProvider} from "../../openaireLibrary/utils/entities/contentProvider"; import {ContentProvider} from "../../openaireLibrary/utils/entities/contentProvider";
import {OpenaireEntities} from "../../openaireLibrary/utils/properties/searchFields"; import {OpenaireEntities} from "../../openaireLibrary/utils/properties/searchFields";
import {CriteriaComponent} from "./criteria/criteria.component"; import {CriteriaComponent} from "./criteria/criteria.component";
import {NotificationHandler} from "../../openaireLibrary/utils/notification-handler";
import {ManageCommunityContentProvidersService} from "../../services/manageContentProviders.service";
import {UntypedFormBuilder} from "@angular/forms";
@Component({ @Component({
selector: 'manage-content-providers', selector: 'manage-content-providers',
@ -21,15 +24,57 @@ import {CriteriaComponent} from "./criteria/criteria.component";
[communityContentProviders]="communityContentProviders" [communityContentProviders]="communityContentProviders"
[loading]="showLoadingInRemove" [community]="community" [loading]="showLoadingInRemove" [community]="community"
(editCriteria)="openCriteria($event)" (editCriteria)="openCriteria($event)"
(communityContentProvidersChanged)="communityContentProvidersChanged($event)"> (communityContentProvidersChanged)="communityContentProvidersChanged($event)">
</remove-content-providers> </remove-content-providers>
<fs-modal #addContentProvidersModal> <fs-modal #addContentProvidersModal>
<add-content-providers #addContentProviders [communityContentProviders]="communityContentProviders" [community]="community" <add-content-providers #addContentProviders [communityContentProviders]="communityContentProviders"
[community]="community"
(communityContentProvidersChanged)="communityContentProvidersChanged($event)"></add-content-providers> (communityContentProvidersChanged)="communityContentProvidersChanged($event)"></add-content-providers>
</fs-modal> </fs-modal>
<fs-modal #filtersModal (okEmitter)="saveCriteria()" (cancelEmitter)="criteria.reset()" [okButtonDisabled]="criteria && criteria.disabled"> <fs-modal #filtersModal (okEmitter)="saveCriteria()" (cancelEmitter)="criteria.reset(); depositReset();"
<div class="uk-container"> [okButtonDisabled]="(criteria && criteria.disabled && !depositInfoChanged)">
<criteria #criteria *ngIf="contentProvider" [dataProvider]="contentProvider"></criteria> <div class="uk-container uk-container-large">
<div *ngIf="dataProvider" class="uk-text-large">{{dataProvider.officialname}}</div>
<div class="uk-flex uk-flex-center">
<div>
<mat-slide-toggle [checked]="enabled" (change)="enabled = !enabled; depositInfoChanged = true;"></mat-slide-toggle>
<label class="uk-margin-medium-top uk-margin-small-left ">Content source</label>
</div>
<div class="uk-margin-small-left">
<mat-slide-toggle [checked]="deposit" (change)="deposit = !deposit; depositInfoChanged = true;"></mat-slide-toggle>
<label class="uk-margin-medium-top uk-margin-small-left ">Suggest for deposit</label>
</div>
</div>
<div class="uk-hr" [class.uk-hidden]="!enabled">
<div class="uk-text-center uk-text-bold uk-text-large uk-margin-top ">Content filters</div>
<criteria #criteria *ngIf="dataProvider" [height]="'-1'"
[selectionCriteria]="dataProvider.selectioncriteria">
<div no-criteria>
<h5 class="uk-margin-small-bottom">No Filters for {{dataProvider.officialname}} yet</h5>
<i class="uk-display-block">If no Filters are specified, all {{openaireEntities.RESULTS | lowercase}} of this {{openaireEntities.DATASOURCE | lowercase}} will be included in your
{{openaireEntities.COMMUNITY | lowercase}}.
</i>
</div>
</criteria>
</div>
<div *ngIf="deposit" class="uk-hr">
<!--<div class="uk-width-1-1 uk-margin-medium-top" input placeholder="Type a message or instruction for researchers about deposition in this datasource"
[value]="message" (valueChange)="message=$event; depositInfoChanged = true;">
</div>-->
<div class="uk-margin-top uk-text-meta">Type a message or instruction for researchers about deposition in this datasource</div>
<ckeditor [readonly]="false"
debounce="500"
[formControl]="messageForm" (change)="messageChanged()"
[config]="{ extraAllowedContent: '* [uk-*](*) ; span', disallowedContent: 'script; *[on*]',
removeButtons: 'Save,NewPage,DocProps,Preview,Print,' +
'Form,Checkbox,Radio,TextField,Textarea,Select,Button,ImageButton,HiddenField,' +
'CreateDiv,Flash,PageBreak,' +
'Subscript,Superscript,Anchor,Smiley,Iframe,Styles,Font,About,Language,JustifyLeft,JustifyRight,JustifyCenter,JustifyBlock,FontSize,TextColor,BGColor',
extraPlugins: 'divarea'}">
</ckeditor>
</div>
</div> </div>
</fs-modal> </fs-modal>
` `
@ -41,15 +86,24 @@ export class ManageContentProvidersComponent implements OnInit {
@ViewChild('criteria') criteria: CriteriaComponent; @ViewChild('criteria') criteria: CriteriaComponent;
@ViewChild('addContentProvidersModal', { static: true }) addContentProvidersModal: FullScreenModalComponent; @ViewChild('addContentProvidersModal', { static: true }) addContentProvidersModal: FullScreenModalComponent;
@ViewChild('filtersModal', { static: true }) filtersModal: FullScreenModalComponent; @ViewChild('filtersModal', { static: true }) filtersModal: FullScreenModalComponent;
@ViewChild('depositModal', { static: true }) depositModal: FullScreenModalComponent;
private subscriptions: any[] = []; private subscriptions: any[] = [];
public showLoadingInRemove: boolean = true; public showLoadingInRemove: boolean = true;
public body: string = "Send from page"; public body: string = "Send from page";
public properties: EnvProperties = properties; public properties: EnvProperties = properties;
public openaireEntities = OpenaireEntities;
public community: CommunityInfo; public community: CommunityInfo;
public contentProvider: ContentProvider; public dataProvider: ContentProvider;
message = "";
deposit= false;
enabled = false;
depositInfoChanged =false;
messageForm = this.fb.control("");
constructor(private title: Title, constructor(private title: Title,
private communityService: CommunityService) { private cdr: ChangeDetectorRef,
private communityService: CommunityService,
private manageCommunityContentProvidersService: ManageCommunityContentProvidersService,
private fb: UntypedFormBuilder) {
} }
ngOnInit() { ngOnInit() {
@ -80,19 +134,39 @@ export class ManageContentProvidersComponent implements OnInit {
} }
public openCriteria(contentProvider: ContentProvider) { public openCriteria(contentProvider: ContentProvider) {
this.contentProvider = contentProvider; this.dataProvider = contentProvider;
this.filtersModal.title = 'Filters'; this.deposit = this.dataProvider.deposit;
this.message = this.dataProvider.message;
this.enabled = this.dataProvider.enabled;
this.messageForm = this.fb.control(this.message);
this.depositInfoChanged = false;
this.filtersModal.title = 'Edit datasource options';
this.filtersModal.okButtonText = "Save"; this.filtersModal.okButtonText = "Save";
this.filtersModal.back = true; this.filtersModal.back = true;
this.filtersModal.okButton = true; this.filtersModal.okButton = true;
this.filtersModal.open();
}
this.filtersModal.open();
this.cdr.detectChanges();
}
public saveCriteria() { public saveCriteria() {
let callback: Function = () => { let callback = (selectionCriteria): void => {
this.dataProvider.selectioncriteria = selectionCriteria;
this.dataProvider.deposit = this.deposit;
this.dataProvider.message = this.message;
this.dataProvider.enabled = this.enabled;
console.log(this.dataProvider)
this.manageCommunityContentProvidersService.saveContentProvider(this.properties, this.dataProvider).subscribe(() => {
this.criteria.reset();
this.removeContentProvidersComponent.getCommunityContentProviders(); this.removeContentProvidersComponent.getCommunityContentProviders();
this.criteria.loading = false;
NotificationHandler.rise('Filters have been <b>successfully updated</b>');
}, error => {
this.criteria.loading = false;
this.criteria.handeError('An error has been occurred. Try again later!', error);
});
} }
this.removeContentProvidersComponent.loading = true; this.removeContentProvidersComponent.loading = true;
console.log()
this.criteria.save(callback); this.criteria.save(callback);
} }
@ -103,4 +177,17 @@ export class ManageContentProvidersComponent implements OnInit {
this.removeContentProvidersComponent.applyFilters(); this.removeContentProvidersComponent.applyFilters();
} }
} }
depositReset(){
this.message = this.dataProvider.message;
this.messageForm.setValue(this.message);
this.deposit = this.dataProvider.deposit;
this.enabled = this.dataProvider.enabled;
}
messageChanged(){
this.message = this.messageForm.value;
this.depositInfoChanged = true;
}
} }

View File

@ -1,16 +1,6 @@
<div page-content> <div page-content>
<div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage <span class="uk-text-capitalize">{{openAIREEntities.DATASOURCES}}</span>
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<community-info tab="content-providers"></community-info>
</div>
<div actions> <div actions>
<div class="uk-section-xsmall"> <div class="uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-right@m uk-flex-center uk-flex-middle uk-grid" uk-grid> <div class="uk-flex uk-flex-right@m uk-flex-center uk-flex-middle uk-grid" uk-grid>
<div search-input [expandable]="true" [searchControl]="filterForm.get('keyword')" searchInputClass="outer" <div search-input [expandable]="true" [searchControl]="filterForm.get('keyword')" searchInputClass="outer"
[placeholder]="'Search ' + openAIREEntities.DATASOURCES" [disabled]="loading" [placeholder]="'Search ' + openAIREEntities.DATASOURCES" [disabled]="loading"
@ -32,6 +22,8 @@
<loading></loading> <loading></loading>
</div> </div>
<div *ngIf="!loading"> <div *ngIf="!loading">
<validate-page-enabled pageRoute="/search/find/dataproviders"></validate-page-enabled>
<validate-page-enabled pageRoute="/participate/deposit/suggested"></validate-page-enabled>
<div *ngIf="previewCommunityContentProviders.length == 0" <div *ngIf="previewCommunityContentProviders.length == 0"
class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold"> class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold">
<div>No <span class="uk-text-lowercase">{{openAIREEntities.DATASOURCES}} </span> <div>No <span class="uk-text-lowercase">{{openAIREEntities.DATASOURCES}} </span>
@ -64,9 +56,15 @@
<span *ngIf="!item.officialname && !item.name">[no title available]</span> <span *ngIf="!item.officialname && !item.name">[no title available]</span>
</span> </span>
</h6> </h6>
<div *ngIf="item.selectioncriteria?.criteria?.length > 0" class="uk-margin-small-bottom uk-text-small"> <div *ngIf="item.enabled" class="uk-label uk-text-primary uk-margin-small-right uk-padding-xsmall ">Content source</div>
<div *ngIf="item.deposit" class="uk-label uk-label-success uk-padding-xsmall">Suggested for deposit</div>
<div *ngIf="item.deposit && item.message" class=" uk-text-small uk-margin-top">
<div class="uk-text-muted uk-text-xsmall">Deposit info:</div>
<div [innerHTML]="item.message"></div>
</div>
<div *ngIf="item.selectioncriteria?.criteria?.length > 0" class="uk-margin-small-bottom uk-margin-small-top uk-text-small">
<div class="uk-text-meta uk-margin-small-bottom">Filters</div> <div class="uk-text-meta uk-margin-small-bottom">Filters</div>
<div [innerHTML]="getFiltersAsText(item.selectioncriteria.criteria)"></div> <div [innerHTML]="criteriaUtils.getFiltersAsText(item.selectioncriteria.criteria)"></div>
<div *ngIf="item.selectioncriteria.criteria.length > 3" class="uk-margin-small-top"> <div *ngIf="item.selectioncriteria.criteria.length > 3" class="uk-margin-small-top">
<a class="uk-link view-more-less-link" (click)="openCriteria(item)">View all {{item.selectioncriteria.criteria.length}} filters</a> <a class="uk-link view-more-less-link" (click)="openCriteria(item)">View all {{item.selectioncriteria.criteria.length}} filters</a>
</div> </div>
@ -74,17 +72,23 @@
</div> </div>
<div class="uk-card-footer uk-padding-remove-vertical"> <div class="uk-card-footer uk-padding-remove-vertical">
<div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid> <div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid>
<div>
</div>
<div> <div>
<div class="uk-padding-small uk-padding-remove-horizontal"> <div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="openCriteria(item)" class="uk-button uk-button-link uk-flex uk-flex-middle"> <a (click)="openCriteria(item)" class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="filters" [flex]="true"></icon> <icon name="edit" [flex]="true"></icon>
<span *ngIf="item.selectioncriteria?.criteria?.length > 0" class="uk-margin-small-left" <!--<span *ngIf="item.selectioncriteria?.criteria?.length > 0" class="uk-margin-small-left"
uk-tooltip="<div>Edit filters to limit research results.<br>Results which satisfy any of the selected filters will be included in your community.</div>"> uk-tooltip="<div>Edit filters to limit research results.<br>Results which satisfy any of the selected filters will be included in your community.</div>">
Edit filters Edit filters
</span> </span>
<span *ngIf="!(item.selectioncriteria?.criteria?.length > 0)" class="uk-margin-small-left" <span *ngIf="!(item.selectioncriteria?.criteria?.length > 0)" class="uk-margin-small-left"
uk-tooltip="<div>Add filter to limit research results.<br>Results which satisfy any of the selected filters will be included in your community.</div>"> uk-tooltip="<div>Add filter to limit research results.<br>Results which satisfy any of the selected filters will be included in your community.</div>">
Add filters Add filters
</span>-->
<span class="uk-margin-small-left"
uk-tooltip="<div>Select datasource as content source and/or suggest for deposit. Add filters to limit research results.<br>Results which satisfy any of the selected filters will be included in your community.</div>">
Edit Options
</span> </span>
</a> </a>
</div> </div>

View File

@ -38,8 +38,7 @@ export class RemoveContentProvidersComponent implements OnInit {
private selectedCommunityContentProvider: any; private selectedCommunityContentProvider: any;
@ViewChild('deleteModal') deleteModal: AlertModal; @ViewChild('deleteModal') deleteModal: AlertModal;
/** Criteria */ /** Criteria */
private fields = CriteriaUtils.fields; public criteriaUtils: CriteriaUtils = new CriteriaUtils();
private verbs = CriteriaUtils.verbs;
/** Paging */ /** Paging */
page: number = 1; page: number = 1;
resultsPerPage: number = properties.resultsPerPage; resultsPerPage: number = properties.resultsPerPage;
@ -81,26 +80,14 @@ export class RemoveContentProvidersComponent implements OnInit {
}); });
} }
getFiltersAsText(criteria: Criteria[]): string {
let text = criteria.slice(0, 3).map((criterion, index) => (index + 1) + ". " + criterion.constraint.map(constraint => {
let field = this.fields.find(field => field.value === constraint.field)?.label;
let matchCase = false;
if (!constraint.verb.includes('_caseinsensitive')) {
matchCase = true;
}
let verb = this.verbs.find(verb => verb.value === constraint.verb.replace("_caseinsensitive", "")).label;
let value = '"' + constraint.value + '"' + (matchCase ? " (Match case)" : "");
return field + " " + verb + " " + value;
}).join(" <b>and</b> "));
return text.join("<br>");
}
public confirmedDeleteContentProvider() { public confirmedDeleteContentProvider() {
this.subscriptions.push(this._manageCommunityContentProvidersService.removeContentProvider(this.properties, this.community.communityId, this.selectedCommunityContentProvider.id).subscribe( console.log(this.selectedCommunityContentProvider)
this.subscriptions.push(this._manageCommunityContentProvidersService.removeContentProvider(this.properties, this.community.communityId, this.selectedCommunityContentProvider.openaireId).subscribe(
() => { () => {
let index = this.communityContentProviders.indexOf(this.selectedCommunityContentProvider); let index = this.communityContentProviders.indexOf(this.selectedCommunityContentProvider);
this.communityContentProviders.splice(index, 1); this.communityContentProviders.splice(index, 1);
this.applyFilters(); this.applyFilters();
this._clearCacheService.clearCacheInRoute(this.openAIREEntities.DATASOURCE+" removed", this.community.communityId)
this._clearCacheService.purgeBrowserCache(this.openAIREEntities.DATASOURCE+" removed", this.community.communityId); this._clearCacheService.purgeBrowserCache(this.openAIREEntities.DATASOURCE+" removed", this.community.communityId);
this.handleSuccess(this.openAIREEntities.DATASOURCE + ' successfully removed!') this.handleSuccess(this.openAIREEntities.DATASOURCE + ' successfully removed!')
this.communityContentProvidersChanged.emit({ this.communityContentProvidersChanged.emit({
@ -197,4 +184,5 @@ export class RemoveContentProvidersComponent implements OnInit {
openCriteria(contentProvider: ContentProvider) { openCriteria(contentProvider: ContentProvider) {
this.editCriteria.emit(contentProvider); this.editCriteria.emit(contentProvider);
} }
} }

View File

@ -9,7 +9,8 @@ declare var UIkit;
selector: 'background-upload', selector: 'background-upload',
template: ` template: `
<input #file id="photo" type="file" class="uk-hidden" (change)="fileChangeEvent($event)"/> <input #file id="photo" type="file" class="uk-hidden" (change)="fileChangeEvent($event)"/>
<div *ngIf="!background.imageFile" class=" upload uk-text-center uk-height-small uk-flex uk-flex-middle uk-flex-center uk-text-uppercase"> <div *ngIf="!background.imageFile"
class=" upload uk-text-center uk-height-small uk-flex uk-flex-middle uk-flex-center uk-text-uppercase">
<span uk-icon="icon: cloud-upload"></span> <span uk-icon="icon: cloud-upload"></span>
<div uk-form-custom> <div uk-form-custom>
<span class="uk-link uk-margin-small-left" (click)="file.click()">upload image</span> <span class="uk-link uk-margin-small-left" (click)="file.click()">upload image</span>
@ -17,38 +18,41 @@ declare var UIkit;
</div> </div>
<div *ngIf="background.imageFile" class="uk-width-1-1 uk-flex uk-flex-middle "> <div *ngIf="background.imageFile" class="uk-width-1-1 uk-flex uk-flex-middle ">
<div class="uk-width-1-1 uk-height-small" style = "background-size:cover" <div class="uk-width-1-1 uk-height-small" style="background-size:cover"
[style.background-image]=" getUrl()"> [style.background-image]=" getUrl()">
<a (click)="removePhoto()" uk-tooltip="Remove" class="uk-float-right uk-border-rounded uk-margin-top uk-margin-right uk-background-muted uk-button uk-button-link"> <a (click)="removePhoto()" uk-tooltip="Remove"
class="uk-float-right uk-border-rounded uk-margin-top uk-margin-right uk-background-muted uk-button uk-button-link">
<icon name="delete" [defaultSize]="true" [flex]="true"></icon> <icon name="delete" [defaultSize]="true" [flex]="true"></icon>
</a> </a>
<div class="uk-text-small uk-margin-large-top uk-text-center" [class.uk-light]="!light">Lorem ipsum dolor sit amet...</div>
</div> </div>
</div> </div>
<div *ngIf="background.imageFile" class="uk-margin-top"> <div *ngIf="background.imageFile" class="uk-margin-top">
<div class="uk-text-bold uk-text-uppercase uk-text-meta uk-margin-small-bottom uk-margin-large-top">position</div> <div class="uk-text-bold uk-text-uppercase uk-text-meta uk-margin-small-bottom uk-margin-large-top">position</div>
<div class="uk-width-expand uk-padding-remove-left" input type="select" inputClass="flat x-small" [(value)]="background.position" <div class="uk-width-expand uk-padding-remove-left" input type="select" inputClass="flat x-small"
[options]="['top','center','bottom']" > [(value)]="background.position"
[options]="['top','center','bottom']">
</div> </div>
</div> </div>
`, `,
styles:[` styles: [`
.upload{ .upload {
border: 1px dotted grey; border: 1px dotted grey;
} }
`] `]
}) })
export class BackgroundUploadComponent implements OnInit { export class BackgroundUploadComponent implements OnInit {
@Input() label:string = ""; @Input() label: string = "";
@Input() background; @Input() background;
@Input() oldBackground; @Input() oldBackground;
// @Input() light:boolean; // @Input() light:boolean;
@Input() communityId:string = ""; @Input() communityId: string = "";
@Input() light:boolean; //fonts mode
public file: File; public file: File;
// public photo: string | ArrayBuffer; // public photo: string | ArrayBuffer;
private maxsize: number = 2000 * 1024; private maxsize: number = 2000 * 1024;
@ -63,6 +67,7 @@ export class BackgroundUploadComponent implements OnInit {
ngOnInit() { ngOnInit() {
this.properties = properties; this.properties = properties;
} }
ngOnDestroy() { ngOnDestroy() {
this.subscriptions.forEach(subscription => { this.subscriptions.forEach(subscription => {
if (subscription instanceof Subscription) { if (subscription instanceof Subscription) {
@ -78,7 +83,7 @@ export class BackgroundUploadComponent implements OnInit {
} }
// this.initPhoto(); // this.initPhoto();
console.log(this.background.imageFile + " " + this.oldBackground.imageFile) console.log(this.background.imageFile + " " + this.oldBackground.imageFile)
if(this.background.imageFile != this.oldBackground.imageFile){ if (this.background.imageFile != this.oldBackground.imageFile) {
this.deletePhoto(); this.deletePhoto();
} }
this.background.imageFile = null; this.background.imageFile = null;
@ -87,10 +92,9 @@ export class BackgroundUploadComponent implements OnInit {
} }
public deletePhoto() { public deletePhoto() {
if (this.background.imageFile) { if (this.background.imageFile) {
this.subscriptions.push(this.utilsService.deletePhoto(properties.utilsService + '/delete/community/' + this.communityId + "/" +this.background.imageFile).subscribe()); this.subscriptions.push(this.utilsService.deletePhoto(properties.utilsService + '/delete/community/' + this.communityId + "/" + this.background.imageFile).subscribe());
} }
} }
@ -105,7 +109,7 @@ export class BackgroundUploadComponent implements OnInit {
}); });
this.removePhoto(); this.removePhoto();
} else if (this.file.size > this.maxsize) { } else if (this.file.size > this.maxsize) {
UIkit.notification('File exceeds size\'s limit ('+this.maxsize/1024+'KB)! ', { UIkit.notification('File exceeds size\'s limit (' + this.maxsize / 1024 + 'KB)! ', {
status: 'danger', status: 'danger',
timeout: 6000, timeout: 6000,
pos: 'bottom-right' pos: 'bottom-right'
@ -125,24 +129,31 @@ export class BackgroundUploadComponent implements OnInit {
public save() { public save() {
if (this.file) { if (this.file) {
this.subscriptions.push(this.utilsService.uploadPhoto(this.properties.utilsService + "/upload/community/"+ this.communityId + "/" + encodeURIComponent(this.communityId+"-"+this.label)+"?big=1", this.file).subscribe(res => { this.subscriptions.push(this.utilsService.uploadPhoto(this.properties.utilsService + "/upload/community/" + this.communityId + "/" + encodeURIComponent(this.communityId + "-" + this.label) + "?big=1", this.file).subscribe(res => {
this.deletePhoto(); this.deletePhoto();
this.removePhoto(); this.removePhoto();
this.background.imageFile = res.filename; this.background.imageFile = res.filename;
}, error => { }, error => {
if (error.error.message) {
UIkit.notification('The maximum size of an image is 1MB, please check if your file exceeds this limit.', {
status: 'danger',
timeout: 6000,
pos: 'bottom-right'
});
} else {
UIkit.notification("An error has been occurred during upload your image. Try again later", { UIkit.notification("An error has been occurred during upload your image. Try again later", {
status: 'danger', status: 'danger',
timeout: 6000, timeout: 6000,
pos: 'bottom-right' pos: 'bottom-right'
}); });
}
})); }));
} }
} }
getUrl() getUrl() {
{ return "url('" + (this.background.imageFile.indexOf('data:') == -1 ? (this.properties.utilsService +
return "url('" +(this.background.imageFile.indexOf('data:')==-1?(this.properties.utilsService + '/download/' + this.background.imageFile) : this.background.imageFile) + "')";
'/download/'+this.background.imageFile):this.background.imageFile) +"')";
} }
} }

View File

@ -17,7 +17,7 @@ import {CustomizationOptions} from '../../openaireLibrary/connect/community/Cust
</div> </div>
</div> </div>
<div class="uk-text-warning uk-text-xsmall uk-margin-small-left" *ngIf="warningForContrast(color)">Contrast ratio may be too low.</div> <div class="uk-text-warning uk-text-xsmall uk-margin-small-left" [class.uk-invisible]="!warningForContrast(color)">Contrast ratio may be too low.</div>
`, `,
styles:[ styles:[
` `

View File

@ -1,19 +1,18 @@
<aside *ngIf="draftCustomizationOptions" id="sidebar_main"> <div *ngIf="draftCustomizationOptions" class="uk-flex">
<div id="sidebar_content"> <aside id="sidebar_main" class="uk-sticky" uk-sticky="start: 0; end: .sidebar_main_swipe">
<div class="menu_section uk-margin-large-top"> <div sidebar-content>
<a (click)="close()" class="uk-button uk-button-link uk-margin-left"> <div class="back">
<h6 class="uk-margin-remove-bottom uk-flex uk-flex-middle uk-flex-center"> <a (click)="close()" class="uk-flex uk-flex-middle uk-flex-center">
<div class="uk-width-auto"> <div class="uk-width-auto">
<icon *ngIf="menuSelected.id != 'home'" class="menu-icon" name="west" ratio="1.5" <icon *ngIf="menuSelected.id != 'home'" name="west" ratio="1.3"
[flex]="true"></icon> [flex]="true"></icon>
<icon *ngIf="menuSelected.id == 'home'" class="menu-icon" name="close" ratio="2" <icon *ngIf="menuSelected.id == 'home'" name="close" ratio="1.3"
[flex]="true"></icon> [flex]="true"></icon>
</div> </div>
<span class="uk-width-expand uk-text-truncate uk-margin-small-left">{{menuSelected.name}}</span> <span class="uk-width-expand uk-text-truncate uk-margin-left hide-on-close">{{menuSelected.name}}</span>
</h6>
</a> </a>
</div> </div>
<div class="menu_section uk-margin-large-top uk-overflow-auto" style="max-height: 75vh"> <div class="menu_section uk-margin-large-top">
<ul *ngIf="menuSelected.id == 'home'" class="uk-list uk-nav uk-nav-default" uk-nav> <ul *ngIf="menuSelected.id == 'home'" class="uk-list uk-nav uk-nav-default" uk-nav>
<ng-template ngFor [ngForOf]="sidebarItems" let-item let-i="index"> <ng-template ngFor [ngForOf]="sidebarItems" let-item let-i="index">
<li class="uk-visible-toggle" [class.uk-active]="menuSelected.id == item.id"> <li class="uk-visible-toggle" [class.uk-active]="menuSelected.id == item.id">
@ -23,20 +22,15 @@
<div *ngIf="item.icon" class="uk-width-auto"> <div *ngIf="item.icon" class="uk-width-auto">
<icon class="menu-icon" [name]="item.icon" [flex]="true"></icon> <icon class="menu-icon" [name]="item.icon" [flex]="true"></icon>
</div> </div>
<span <span class="uk-width-expand uk-text-truncate uk-margin-small-left hide-on-close">
class="uk-width-expand uk-text-truncate uk-margin-small-left">
{{item.name}} {{item.name}}
</span> </span>
<span uk-icon="triangle-right"></span> <span uk-icon="triangle-right"></span>
</div> </div>
</a> </a>
</li> </li>
</ng-template> </ng-template>
</ul> </ul>
<ng-container *ngIf="menuSelected.id == 'identity'"> <ng-container *ngIf="menuSelected.id == 'identity'">
<ng-container <ng-container
*ngTemplateOutlet="identityOptions ; context: { }"></ng-container> *ngTemplateOutlet="identityOptions ; context: { }"></ng-container>
@ -50,10 +44,9 @@
*ngTemplateOutlet="buttonOptions ; context: { }"></ng-container> *ngTemplateOutlet="buttonOptions ; context: { }"></ng-container>
</ng-container> </ng-container>
</div> </div>
</div> </div>
</aside> </aside>
<div *ngIf="draftCustomizationOptions" page-content> <div page-content class="uk-width-1-1">
<div actions> <div actions>
<div class="uk-section-small"> <div class="uk-section-small">
<ng-container *ngTemplateOutlet="applyResetButtons;"></ng-container> <ng-container *ngTemplateOutlet="applyResetButtons;"></ng-container>
@ -142,7 +135,9 @@
</div> </div>
</div> </div>
</div> </div>
</div>
</div> </div>
<ng-template #identityOptions> <ng-template #identityOptions>
<div class="functionalities-container uk-text-small"> <div class="functionalities-container uk-text-small">
<div class="uk-margin-top"> <div class="uk-margin-top">
@ -213,12 +208,36 @@
[light]="false"></background> [light]="false"></background>
<background label="Light" [background]="draftCustomizationOptions.backgrounds.light" <background label="Light" [background]="draftCustomizationOptions.backgrounds.light"
[light]="true"></background> [light]="true"></background>
<background label="Hero section" [background]="draftCustomizationOptions.backgrounds.form" <background label="Custom section" [background]="draftCustomizationOptions.backgrounds.form"
[light]="true" [light]="draftCustomizationOptions.backgrounds.form.fontsDarkMode"
[oldBackground]="publishedCustomizationOptions.backgrounds.form" [oldBackground]="publishedCustomizationOptions.backgrounds.form"
[communityId]="communityId" description="The area under menu"></background> [communityId]="communityId"></background>
<div class="uk-margin-xsmall-bottom uk-text-uppercase uk-text-meta uk-text-bold uk-margin-large-top uk-flex uk-flex-middle"> <div class="uk-margin-xsmall-bottom uk-text-uppercase uk-text-meta uk-text-bold uk-margin-large-top uk-flex uk-flex-middle uk-heading-divider">
Hero section image Custom section
</div>
<div class="uk-margin-xsmall-bottom uk-text-uppercase uk-text-meta uk-text-bold uk-margin-medium-top uk-flex uk-flex-middle">
Fonts
<a *ngIf="( publishedCustomizationOptions.backgrounds.form.fontsDarkMode != draftCustomizationOptions.backgrounds.form.fontsDarkMode )
&& draftCustomizationOptions.backgroundsIsCustom"
(click)="draftCustomizationOptions.backgrounds.form.fontsDarkMode=publishedCustomizationOptions.backgrounds.form.fontsDarkMode;" class="uk-margin-small-left uk-button-link"
uk-tooltip="title:<div class='uk-width-large'>Reset to previously saved options</div>">
<icon name="settings_backup_restore" flex="true"></icon>
</a>
</div>
<div class="uk-margin-small-top">
<span>Dark mode </span>
<span>
<mat-slide-toggle class="uk-margin-large-left"
[checked]="draftCustomizationOptions.backgrounds.form.fontsDarkMode"
(change)="draftCustomizationOptions.backgrounds.form.fontsDarkMode=!draftCustomizationOptions.backgrounds.form.fontsDarkMode;"
[attr.uk-tooltip]="'title:<div class=\'uk-width-large\'>' +
(draftCustomizationOptions.backgrounds.form.fontsDarkMode?'Change to light color mode if the custom section background is dark':'Change to dark mode if the custom section background is light')+'</div>'"
>
</mat-slide-toggle>
</span>
</div>
<div class="uk-margin-xsmall-bottom uk-text-uppercase uk-text-meta uk-text-bold uk-margin-medium-top uk-flex uk-flex-middle">
Image
<a *ngIf="(formHasChanges(publishedCustomizationOptions, draftCustomizationOptions) ) <a *ngIf="(formHasChanges(publishedCustomizationOptions, draftCustomizationOptions) )
&& draftCustomizationOptions.backgroundsIsCustom" && draftCustomizationOptions.backgroundsIsCustom"
(click)="resetImageTo(publishedCustomizationOptions.backgrounds);" class="uk-margin-small-left uk-button-link" (click)="resetImageTo(publishedCustomizationOptions.backgrounds);" class="uk-margin-small-left uk-button-link"
@ -229,7 +248,7 @@
<div class="uk-margin-medium-bottom"> <div class="uk-margin-medium-bottom">
<background-upload label="Form" [background]="draftCustomizationOptions.backgrounds.form" <background-upload label="Form" [background]="draftCustomizationOptions.backgrounds.form"
[oldBackground]="publishedCustomizationOptions.backgrounds.form" [oldBackground]="publishedCustomizationOptions.backgrounds.form"
[communityId]="communityId"></background-upload> [communityId]="communityId" [light]="draftCustomizationOptions.backgrounds.form.fontsDarkMode" ></background-upload>
</div> </div>
</div> </div>
</div> </div>

View File

@ -164,11 +164,6 @@ sidebarItems = [{name:"Identity", id : "identity", icon: "desktop_windows" },
return JSON.stringify(object1) != JSON.stringify(object2); return JSON.stringify(object1) != JSON.stringify(object2);
} }
saveLayout() { saveLayout() {
if (!Session.isLoggedIn()) {
this._router.navigate(['/user-info'], {
queryParams: {'errorCode': LoginErrorCodes.NOT_VALID, 'redirectUrl': this._router.url}
});
}
this.publishedLayout.layoutOptions = this.copyObject(this.draftCustomizationOptions); this.publishedLayout.layoutOptions = this.copyObject(this.draftCustomizationOptions);
this.publishedCustomizationOptions = this.copyObject(this.publishedLayout.layoutOptions) this.publishedCustomizationOptions = this.copyObject(this.publishedLayout.layoutOptions)
this.publishedLayout.date = new Date(); this.publishedLayout.date = new Date();

View File

@ -20,14 +20,6 @@ type Tab = 'all' | 'communities' | 'ris';
template: ` template: `
<div page-content [id]="tab"> <div page-content [id]="tab">
<div header> <div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">
Admin Dashboard - Manage Communities
</div>
<h1 class="uk-h6 uk-margin-remove">Research Communities & Initiatives</h1>
</div>
</div>
<ul class="uk-tab uk-margin-medium-top" uk-tab> <ul class="uk-tab uk-margin-medium-top" uk-tab>
<li [class.uk-active]="tab === 'all'"><a (click)="tab = 'all'"><span class="title">All</span></a></li> <li [class.uk-active]="tab === 'all'"><a (click)="tab = 'all'"><span class="title">All</span></a></li>
<li [class.uk-active]="tab === 'communities'"><a (click)="tab = 'communities'"><span class="title">Research Communities</span></a> <li [class.uk-active]="tab === 'communities'"><a (click)="tab = 'communities'"><span class="title">Research Communities</span></a>
@ -91,7 +83,7 @@ type Tab = 'all' | 'communities' | 'ris';
<div class="uk-card uk-card-default uk-card-body uk-position-relative"> <div class="uk-card uk-card-default uk-card-body uk-position-relative">
<div class="uk-position-top-right uk-margin-small-right uk-margin-small-top"> <div class="uk-position-top-right uk-margin-small-right uk-margin-small-top">
<div class="uk-flex uk-flex-middle"> <div class="uk-flex uk-flex-middle">
<icon [flex]="true" [name]="community.status == 'all'?'earth':(community.status == 'manager'?'restricted':'incognito')" ratio="0.6"></icon> <icon [flex]="true" [name]="community.isPublic()?'earth':(community.isRestricted()?'restricted':'incognito')" ratio="0.6"></icon>
</div> </div>
</div> </div>
<a class="uk-display-block uk-text-center uk-link-reset" [routerLink]="community.communityId"> <a class="uk-display-block uk-text-center uk-link-reset" [routerLink]="community.communityId">

View File

@ -10,7 +10,7 @@ import {UrlPrefixModule} from '../../openaireLibrary/utils/pipes/url-prefix.modu
import {CommunitiesService} from '../../openaireLibrary/connect/communities/communities.service'; import {CommunitiesService} from '../../openaireLibrary/connect/communities/communities.service';
import {IconsModule} from '../../openaireLibrary/utils/icons/icons.module'; import {IconsModule} from '../../openaireLibrary/utils/icons/icons.module';
import {IconsService} from '../../openaireLibrary/utils/icons/icons.service'; import {IconsService} from '../../openaireLibrary/utils/icons/icons.service';
import {earth} from '../../openaireLibrary/utils/icons/icons'; import {earth, incognito, restricted} from '../../openaireLibrary/utils/icons/icons';
import {LogoUrlPipeModule} from "../../openaireLibrary/utils/pipes/logoUrlPipe.module"; import {LogoUrlPipeModule} from "../../openaireLibrary/utils/pipes/logoUrlPipe.module";
import {SearchInputModule} from '../../openaireLibrary/sharedComponents/search-input/search-input.module'; import {SearchInputModule} from '../../openaireLibrary/sharedComponents/search-input/search-input.module';
@ -24,6 +24,6 @@ import {SearchInputModule} from '../../openaireLibrary/sharedComponents/search-i
}) })
export class ManageCommunitiesModule { export class ManageCommunitiesModule {
constructor(private iconsService: IconsService) { constructor(private iconsService: IconsService) {
this.iconsService.registerIcons([earth]); this.iconsService.registerIcons([earth, restricted, incognito]);
} }
} }

View File

@ -94,12 +94,12 @@
<div class="uk-card-body"> <div class="uk-card-body">
<result-preview [properties]="properties" [showOrganizations]="true" <result-preview [properties]="properties" [showOrganizations]="true"
[showSubjects]="true" [result]="getResultPreview(result)" [showSubjects]="true" [result]="getResultPreview(result)"
[externalUrl]="projectUrl"> [externalUrl]="projectUrl" [hasLink]="false">
</result-preview> </result-preview>
</div> </div>
<div class="uk-card-footer uk-padding-remove-vertical"> <div class="uk-card-footer uk-padding-remove-vertical">
<div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid> <div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid>
<div *ngIf="!getCommunityProject(result)"> <div *ngIf="!result['isPart']">
<div class="uk-padding-small uk-padding-remove-horizontal"> <div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="addProject(result)" class="uk-button uk-button-link uk-flex uk-flex-middle"> <a (click)="addProject(result)" class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="add" [flex]="true"></icon> <icon name="add" [flex]="true"></icon>
@ -109,7 +109,7 @@
</a> </a>
</div> </div>
</div> </div>
<div *ngIf="getCommunityProject(result)"> <div *ngIf="result['isPart']">
<div class="uk-padding-small uk-padding-remove-horizontal"> <div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="removeProject(result)" <a (click)="removeProject(result)"
class="uk-button uk-button-link uk-flex uk-flex-middle"> class="uk-button uk-button-link uk-flex uk-flex-middle">

View File

@ -19,6 +19,7 @@ import {CommunityInfo} from "../../openaireLibrary/connect/community/communityIn
import {OpenaireEntities} from "../../openaireLibrary/utils/properties/searchFields"; import {OpenaireEntities} from "../../openaireLibrary/utils/properties/searchFields";
import {Filter, Value} from "../../openaireLibrary/searchPages/searchUtils/searchHelperClasses.class"; import {Filter, Value} from "../../openaireLibrary/searchPages/searchUtils/searchHelperClasses.class";
import {ClearCacheService} from "../../openaireLibrary/services/clear-cache.service"; import {ClearCacheService} from "../../openaireLibrary/services/clear-cache.service";
import {SearchCommunityProjectsService} from "../../openaireLibrary/connect/projects/searchProjects.service";
declare var UIkit; declare var UIkit;
@ -38,7 +39,7 @@ export class AddProjectsComponent implements OnInit {
public errorCodes: ErrorCodes; public errorCodes: ErrorCodes;
public openaireSearchUtils: SearchUtilsClass = new SearchUtilsClass(); public openaireSearchUtils: SearchUtilsClass = new SearchUtilsClass();
@Output() communityProjectsChanged = new EventEmitter(); @Output() communityProjectsChanged = new EventEmitter();
@Input() communityProjects = []; // @Input() communityProjects = [];
public openaireProjects = []; public openaireProjects = [];
public queryParameters: string = ""; public queryParameters: string = "";
@ -58,7 +59,7 @@ export class AddProjectsComponent implements OnInit {
constructor(private route: ActivatedRoute, private _router: Router, private _searchProjectsService: SearchProjectsService, constructor(private route: ActivatedRoute, private _router: Router, private _searchProjectsService: SearchProjectsService,
private _manageCommunityProjectsService: ManageCommunityProjectsService, private _manageCommunityProjectsService: ManageCommunityProjectsService,
private _clearCacheService: ClearCacheService, private _clearCacheService: ClearCacheService, private _searchCommunityProjectsService: SearchCommunityProjectsService,
private _fb: UntypedFormBuilder) { private _fb: UntypedFormBuilder) {
this.errorCodes = new ErrorCodes(); this.errorCodes = new ErrorCodes();
this.openaireSearchUtils.status = this.errorCodes.LOADING; this.openaireSearchUtils.status = this.errorCodes.LOADING;
@ -121,15 +122,18 @@ export class AddProjectsComponent implements OnInit {
public addProject(project: SearchResult) { public addProject(project: SearchResult) {
this.subscriptions.push(this._manageCommunityProjectsService.addProject(this.properties, this.community.communityId, project).subscribe( this.subscriptions.push(this._manageCommunityProjectsService.addProject(this.properties, this.community.communityId, project).subscribe(
data => { data => {
this.communityProjects.push(data); // this.communityProjects.push(data);
this._clearCacheService.clearCacheInRoute(this.openaireEntities.PROJECT+" added", this.community.communityId);
this._clearCacheService.purgeBrowserCache(this.openaireEntities.PROJECT+" added", this.community.communityId); this._clearCacheService.purgeBrowserCache(this.openaireEntities.PROJECT+" added", this.community.communityId);
UIkit.notification(this.openaireEntities.PROJECT+' successfully added!', { UIkit.notification(this.openaireEntities.PROJECT+' successfully added!', {
status: 'success', status: 'success',
timeout: 6000, timeout: 6000,
pos: 'bottom-right' pos: 'bottom-right'
}); });
project["isPart"] = true;
this.communityProjectsChanged.emit({ this.communityProjectsChanged.emit({
value: this.communityProjects, value: project,
}); });
}, },
err => { err => {
@ -140,20 +144,20 @@ export class AddProjectsComponent implements OnInit {
} }
public removeProject(project: any) { public removeProject(project: any) {
let communityProject = this.getCommunityProject(project); // let communityProject = this.getCommunityProject(project);
let projectId: string = communityProject['id']; this.subscriptions.push(this._manageCommunityProjectsService.removeProject(this.properties, this.community.communityId, project['id']).subscribe(
this.subscriptions.push(this._manageCommunityProjectsService.removeProject(this.properties, this.community.communityId, projectId).subscribe(
data => { data => {
let index = this.communityProjects.indexOf(communityProject); // let index = this.communityProjects.indexOf(communityProject);
this.communityProjects.splice(index, 1); // this.communityProjects.splice(index, 1);
this._clearCacheService.purgeBrowserCache(this.openaireEntities.PROJECT+" removed", this.community.communityId); this._clearCacheService.purgeBrowserCache(this.openaireEntities.PROJECT+" removed", this.community.communityId);
UIkit.notification(this.openaireEntities.PROJECT+' successfully removed!', { UIkit.notification(this.openaireEntities.PROJECT+' successfully removed!', {
status: 'success', status: 'success',
timeout: 6000, timeout: 6000,
pos: 'bottom-right' pos: 'bottom-right'
}); });
project["isPart"] = false;
this.communityProjectsChanged.emit({ this.communityProjectsChanged.emit({
value: this.communityProjects, value: project,
}); });
}, },
err => { err => {
@ -163,16 +167,19 @@ export class AddProjectsComponent implements OnInit {
)); ));
} }
public getCommunityProject(project: any): string { public getCommunityProject(project: any) {
let index: number = 0; this.subscriptions.push(this._searchCommunityProjectsService.searchProjectsWithPaging(this.properties, this.community.communityId, 1, this.resultsPerPage, project.id, null).subscribe(
for (let communityProject of this.communityProjects) { data => {
if (communityProject.openaireId == project.id || if(data.totalElements > 0){
(project.code == communityProject.grantId && project.funderShortname == communityProject.funder)) { project["isPart"] = true;
return communityProject;
} }
index++; },
err => {
console.error(err);
//TODO check erros (service not available, bad request)
} }
return ""; ));
} }
getFunders() { getFunders() {
@ -217,7 +224,9 @@ export class AddProjectsComponent implements OnInit {
data => { data => {
this.openaireSearchUtils.totalResults = data[0]; this.openaireSearchUtils.totalResults = data[0];
this.openaireProjects = data[1]; this.openaireProjects = data[1];
for(let project of this.openaireProjects){
this.getCommunityProject(project);
}
this.openaireSearchUtils.status = this.errorCodes.DONE; this.openaireSearchUtils.status = this.errorCodes.DONE;
if (this.openaireSearchUtils.totalResults == 0) { if (this.openaireSearchUtils.totalResults == 0) {
this.openaireSearchUtils.status = this.errorCodes.NONE; this.openaireSearchUtils.status = this.errorCodes.NONE;

View File

@ -14,7 +14,6 @@ import {SearchPagingModule} from '../../openaireLibrary/searchPages/searchUtils/
import {AlertModalModule} from '../../openaireLibrary/utils/modal/alertModal.module'; import {AlertModalModule} from '../../openaireLibrary/utils/modal/alertModal.module';
import {CommonModule} from '@angular/common'; import {CommonModule} from '@angular/common';
import {PageContentModule} from "../../openaireLibrary/dashboard/sharedComponents/page-content/page-content.module"; import {PageContentModule} from "../../openaireLibrary/dashboard/sharedComponents/page-content/page-content.module";
import {CommunityInfoModule} from "../community-info/community-info.module";
import {InputModule} from "../../openaireLibrary/sharedComponents/input/input.module"; import {InputModule} from "../../openaireLibrary/sharedComponents/input/input.module";
import {SearchInputModule} from "../../openaireLibrary/sharedComponents/search-input/search-input.module"; import {SearchInputModule} from "../../openaireLibrary/sharedComponents/search-input/search-input.module";
import {NoLoadPaging} from "../../openaireLibrary/searchPages/searchUtils/no-load-paging.module"; import {NoLoadPaging} from "../../openaireLibrary/searchPages/searchUtils/no-load-paging.module";
@ -25,6 +24,7 @@ import {ResultPreviewModule} from "../../openaireLibrary/utils/result-preview/re
import {ErrorMessagesModule} from "../../openaireLibrary/utils/errorMessages.module"; import {ErrorMessagesModule} from "../../openaireLibrary/utils/errorMessages.module";
import {DropdownFilterModule} from "../../openaireLibrary/utils/dropdown-filter/dropdown-filter.module"; import {DropdownFilterModule} from "../../openaireLibrary/utils/dropdown-filter/dropdown-filter.module";
import {SearchFilterModule} from "../../openaireLibrary/searchPages/searchUtils/searchFilter.module"; import {SearchFilterModule} from "../../openaireLibrary/searchPages/searchUtils/searchFilter.module";
import {ValidateEnabledPageModule} from "../../utils/validateEnabledPage.module";
@NgModule({ @NgModule({
imports: [ imports: [
@ -38,7 +38,6 @@ import {SearchFilterModule} from "../../openaireLibrary/searchPages/searchUtils/
AlertModalModule, AlertModalModule,
SearchProjectsServiceModule, SearchProjectsServiceModule,
PageContentModule, PageContentModule,
CommunityInfoModule,
InputModule, InputModule,
SearchInputModule, SearchInputModule,
RouterModule.forChild([ RouterModule.forChild([
@ -46,7 +45,7 @@ import {SearchFilterModule} from "../../openaireLibrary/searchPages/searchUtils/
path: '', component: ManageProjectsComponent path: '', component: ManageProjectsComponent
} }
]), ]),
NoLoadPaging, LoadingModule, IconsModule, FullScreenModalModule, ResultPreviewModule, DropdownFilterModule, SearchFilterModule NoLoadPaging, LoadingModule, IconsModule, FullScreenModalModule, ResultPreviewModule, DropdownFilterModule, SearchFilterModule, ValidateEnabledPageModule
], ],
declarations: [ declarations: [
ManageProjectsComponent, ManageProjectsComponent,

View File

@ -16,12 +16,11 @@ import {CommunityService} from "../../openaireLibrary/connect/community/communit
@Component({ @Component({
selector: 'manage-projects', selector: 'manage-projects',
template: ` template: `
<remove-projects #removeProjectsComponent (addProjects)="openAddProjects()" [communityProjects]="communityProjects" <remove-projects #removeProjectsComponent (addProjects)="openAddProjects()"
[loading]="showLoadingInRemove" [community]="community" [loading]="showLoadingInRemove" [community]="community">
(communityProjectsChanged)="communityProjectsChanged($event)">
</remove-projects> </remove-projects>
<fs-modal #fsModalProjects> <fs-modal #fsModalProjects>
<add-projects #addProjects [communityProjects]="communityProjects" [community]="community" <add-projects *ngIf="modalIsOpen" #addProjects [community]="community"
(communityProjectsChanged)="communityProjectsChanged($event)"></add-projects> (communityProjectsChanged)="communityProjectsChanged($event)"></add-projects>
</fs-modal> </fs-modal>
` `
@ -36,6 +35,7 @@ export class ManageProjectsComponent implements OnInit {
public body: string = "Send from page"; public body: string = "Send from page";
public properties: EnvProperties = properties; public properties: EnvProperties = properties;
public community: CommunityInfo = null; public community: CommunityInfo = null;
modalIsOpen = false;
constructor(private element: ElementRef, constructor(private element: ElementRef,
private title: Title, private title: Title,
@ -68,15 +68,17 @@ export class ManageProjectsComponent implements OnInit {
this.fullscreen.back = true; this.fullscreen.back = true;
this.fullscreen.okButton = true; this.fullscreen.okButton = true;
this.fullscreen.open(); this.fullscreen.open();
this.modalIsOpen = true;
} }
public communityProjectsChanged($event) { public communityProjectsChanged($event) {
this.communityProjects = $event.value; /* this.communityProjects = $event.value;
this.showLoadingInRemove = false; this.showLoadingInRemove = false;
if (this.fullscreen.isOpen) { if (this.fullscreen.isOpen) {
this.removeProjectsComponent.applyFilters(); this.removeProjectsComponent.applyFilters();
this.removeProjectsComponent.createFunderFilter(); this.removeProjectsComponent.createFunderFilter();
} }*/
this.removeProjectsComponent.getCommunityProjects();
} }
} }

View File

@ -1,16 +1,6 @@
<div page-content> <div page-content>
<div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage {{openaireEntiites.PROJECTS}}
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<community-info tab="projects"></community-info>
</div>
<div actions> <div actions>
<div class="uk-section-xsmall"> <div class="uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-middle"> <div class="uk-flex uk-flex-middle">
<div class="uk-width-expand@m uk-width-1-1 uk-grid uk-flex-middle uk-flex-right@m uk-flex-center uk-margin-remove-left" uk-grid> <div class="uk-width-expand@m uk-width-1-1 uk-grid uk-flex-middle uk-flex-right@m uk-flex-center uk-margin-remove-left" uk-grid>
<div search-input [expandable]="true" [searchControl]="filterForm.get('keyword')" searchInputClass="outer" <div search-input [expandable]="true" [searchControl]="filterForm.get('keyword')" searchInputClass="outer"
@ -34,20 +24,21 @@
</div> </div>
<div inner> <div inner>
<div class="uk-margin-top"> <div class="uk-margin-top">
<results-and-pages [type]="openaireEntiites.PROJECTS | lowercase" [page]="page" [pageSize]="resultsPerPage" <results-and-pages [type]="openaireEntiites.PROJECTS | lowercase" [page]="communitySearchUtils.page" [pageSize]="resultsPerPage"
[totalResults]="previewCommunityProjects.length"></results-and-pages> [totalResults]="communitySearchUtils.totalResults"></results-and-pages>
</div> </div>
<div class="uk-grid uk-flex-middle uk-margin-medium-top" uk-grid> <div class="uk-grid uk-flex-middle uk-margin-medium-top" uk-grid>
<div *ngIf="allOptions.length > 0"> <div *ngIf="allFunderOptions.length > 0">
<dropdown-filter #dropdownFilter dropdownClass="uk-width-medium uk-padding-small" <dropdown-filter #dropdownFilter dropdownClass="uk-width-medium uk-padding-small"
name="Filter by Funder" [count]="filterForm.get('funder').value.length"> name="Filter by Funder" [count]="filterForm.get('funder').value?1:null">
<h6 class="uk-margin-remove-bottom" title="Filter by Funder">Funder</h6> <h6 class="uk-margin-remove-bottom" title="Filter by Funder">Funder</h6>
<ul class="uk-list uk-margin-remove-bottom"> <ul class="uk-list uk-margin-remove-bottom">
<li *ngFor="let option of allOptions">
<a class="uk-link-text"> <li *ngFor="let option of previewFunderOptions">
<label (click)="select(option.value, $event, dropdownFilter)" class="uk-flex uk-flex-middle"> <a class="uk-link-text" >
<label (click)="select(option, $event, dropdownFilter)" class="uk-flex uk-flex-middle">
<input class="uk-checkbox" <input class="uk-checkbox"
type="checkbox" [checked]="isSelected(option.value)"> type="checkbox" [checked]="isSelected(option.value.id)">
<span class="uk-margin-small-left">{{option.label}}</span> <span class="uk-margin-small-left">{{option.label}}</span>
</label> </label>
</a> </a>
@ -65,9 +56,9 @@
</div> </div>
<!-- </div>--> <!-- </div>-->
<div class="uk-width-expand@l uk-width-1-1 uk-flex uk-flex-right@m uk-flex-center"> <div class="uk-width-expand@l uk-width-1-1 uk-flex uk-flex-right@m uk-flex-center">
<paging-no-load *ngIf="previewCommunityProjects.length > 0" <paging-no-load *ngIf="communitySearchUtils.totalResults> 0" [currentPage]="communitySearchUtils.page"
(pageChange)="updatePage($event)" [size]="resultsPerPage" (pageChange)="updatePage($event)" [size]="resultsPerPage"
[totalResults]="previewCommunityProjects.length" customClasses="uk-flex-right"> [totalResults]="communitySearchUtils.totalResults" customClasses="uk-flex-right">
</paging-no-load> </paging-no-load>
</div> </div>
</div> </div>
@ -76,30 +67,30 @@
<div *ngIf="loading" class="uk-position-center"> <div *ngIf="loading" class="uk-position-center">
<loading></loading> <loading></loading>
</div> </div>
<validate-page-enabled pageRoute="/search/find/projects"></validate-page-enabled>
<div *ngIf="!loading"> <div *ngIf="!loading">
<div class="uk-margin-medium-bottom"> <div class="uk-margin-medium-bottom">
<div *ngIf="previewCommunityProjects.length == 0" <div *ngIf="previewCommunityProjects.length == 0"
class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold"> class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold">
<div>No {{openaireEntiites.PROJECTS | lowercase}} <div>No {{openaireEntiites.PROJECTS | lowercase}}
<span *ngIf="communityProjects.length == 0; else: notFound">for {{community.shortTitle}}</span> <span *ngIf="communitySearchUtils.totalResults == 0; else: notFound">for {{community.shortTitle}}</span>
<ng-template #notFound>found</ng-template> <ng-template #notFound>found</ng-template>
</div> </div>
</div> </div>
<div *ngIf="previewCommunityProjects.length > 0" <div *ngIf="previewCommunityProjects.length > 0"
class="uk-grid uk-grid-large uk-child-width-1-1 uk-child-width-1-2@m uk-margin-bottom" uk-grid uk-height-match="target: .uk-card-body"> class="uk-grid uk-grid-large uk-child-width-1-1 uk-child-width-1-2@m uk-margin-bottom" uk-grid uk-height-match="target: .uk-card-body">
<div *ngFor="let item of previewCommunityProjects.slice((page - 1)*resultsPerPage, page*resultsPerPage); let i=index"> <div *ngFor="let item of previewCommunityProjects; let i=index">
<div class="uk-card uk-card-default"> <div class="uk-card uk-card-default">
<div class="uk-card-body"> <div class="uk-card-body">
<h6 class="uk-margin-bottom"> <h6 class="uk-margin-bottom">
<a *ngIf="item.openaireId || (item.grantId && item.funder)" <a *ngIf="(item.openaireId || (item.grantId && item.funder)) && (!item['availableSince'] || !lastDBLoadDate || item['availableSince']<lastDBLoadDate)"
target="_blank" class="custom-external uk-link-text" target="_blank" class="custom-external uk-link-text"
[href]="projectUrl+'?' + ((item.openaireId) ? 'projectId='+item.openaireId : 'grantId='+item.grantId+'&funder='+item.funder)"> [href]="projectUrl+'?' + ((item.openaireId) ? 'projectId='+item.openaireId : 'grantId='+item.grantId+'&funder='+item.funder)">
<span *ngIf="item.name">{{item.name}}</span> <span *ngIf="item.name">{{item.name}}</span>
<span *ngIf="item.name && item.acronym"> (</span><span *ngIf="item.acronym">{{item.acronym}}</span><span *ngIf="item.name && item.acronym">)</span> <span *ngIf="item.name && item.acronym"> (</span><span *ngIf="item.acronym">{{item.acronym}}</span><span *ngIf="item.name && item.acronym">)</span>
<span *ngIf="!item.name && !item.acronym">[no title available]</span> <span *ngIf="!item.name && !item.acronym">[no title available]</span>
</a> </a>
<span *ngIf="!item.openaireId && !(item.grantId && item.funder)"> <span *ngIf="(!item.openaireId && !(item.grantId && item.funder) || (item['availableSince'] && lastDBLoadDate && item['availableSince'] >= lastDBLoadDate))">
<span *ngIf="item.name">{{item.name}}</span> <span *ngIf="item.name">{{item.name}}</span>
<span *ngIf="item.name && item.acronym"> (</span><span *ngIf="item.acronym">{{item.acronym}}</span><span *ngIf="item.name && item.acronym">)</span> <span *ngIf="item.name && item.acronym"> (</span><span *ngIf="item.acronym">{{item.acronym}}</span><span *ngIf="item.name && item.acronym">)</span>
<span *ngIf="!item.name && !item.acronym">[no title available]</span> <span *ngIf="!item.name && !item.acronym">[no title available]</span>
@ -134,7 +125,7 @@
</div> </div>
<div class="uk-margin-small-top"> <div class="uk-margin-small-top">
<paging-no-load [currentPage]="page" <paging-no-load [currentPage]="page"
[totalResults]="previewCommunityProjects.length" [size]="resultsPerPage" [totalResults]="communitySearchUtils.totalResults" [size]="resultsPerPage"
(pageChange)="updatePage($event)" customClasses="uk-flex-right@m uk-flex-center"> (pageChange)="updatePage($event)" customClasses="uk-flex-right@m uk-flex-center">
</paging-no-load> </paging-no-load>
</div> </div>

View File

@ -19,6 +19,8 @@ import {CommunityInfo} from "../../openaireLibrary/connect/community/communityIn
import {HelperFunctions} from "../../openaireLibrary/utils/HelperFunctions.class"; import {HelperFunctions} from "../../openaireLibrary/utils/HelperFunctions.class";
import {NotificationHandler} from "../../openaireLibrary/utils/notification-handler"; import {NotificationHandler} from "../../openaireLibrary/utils/notification-handler";
import {ClearCacheService} from "../../openaireLibrary/services/clear-cache.service"; import {ClearCacheService} from "../../openaireLibrary/services/clear-cache.service";
import {debounceTime, distinctUntilChanged} from "rxjs/operators";
import {IndexInfoService} from "../../openaireLibrary/utils/indexInfo.service";
@Component({ @Component({
selector: 'remove-projects', selector: 'remove-projects',
@ -35,7 +37,7 @@ export class RemoveProjectsComponent implements OnInit {
public projectUrl = "https://" + ((properties.environment == "beta" || properties.environment == "development") ? "beta." : "") + "explore.openaire.eu" + properties.searchLinkToProject.split("?")[0]; public projectUrl = "https://" + ((properties.environment == "beta" || properties.environment == "development") ? "beta." : "") + "explore.openaire.eu" + properties.searchLinkToProject.split("?")[0];
@Output() communityProjectsChanged = new EventEmitter(); @Output() communityProjectsChanged = new EventEmitter();
@Input() public communityProjects = []; // @Input() public communityProjects = [];
public previewCommunityProjects = []; public previewCommunityProjects = [];
public communitySearchUtils: SearchUtilsClass = new SearchUtilsClass(); public communitySearchUtils: SearchUtilsClass = new SearchUtilsClass();
public errorCodes: ErrorCodes; public errorCodes: ErrorCodes;
@ -51,56 +53,49 @@ export class RemoveProjectsComponent implements OnInit {
/* Search */ /* Search */
@ViewChild('searchInputComponent') searchInputComponent: SearchInputComponent; @ViewChild('searchInputComponent') searchInputComponent: SearchInputComponent;
filterForm: UntypedFormGroup; filterForm: UntypedFormGroup;
public fundersCtrl: UntypedFormArray;
private searchText: RegExp = new RegExp(''); private searchText: RegExp = new RegExp('');
public keyword: string = ''; public keyword: string = '';
selectedFunders: string[] = []; allFunderOptions: Option[] = [];
allOptions: Option[] = []; previewFunderOptions: Option[] = [];
sortOptions: Option[] = [ sortOptions: Option[] = [
//{label:"Title (desc) ", value:{ sort: "title",descending: true }}, {label: "Title ", value: {sort: "name", descending: false}},
{label: "Title ", value: {sort: "title", descending: false}}, {label: "Grant ID ", value: {sort: "grantId", descending: false}},
//{label:"Grant ID (desc) ", value:{ sort: "grant",descending: true }},
{label: "Grant ID ", value: {sort: "grant", descending: false}},
//{label:"Funder (desc) ", value:{ sort: "funder",descending: true }},
{label: "Funder ", value: {sort: "funder", descending: false}} {label: "Funder ", value: {sort: "funder", descending: false}}
]; ];
public openaireEntiites = OpenaireEntities; public openaireEntiites = OpenaireEntities;
lastDBLoadDate = null;
constructor(private route: ActivatedRoute, private _router: Router, constructor(private route: ActivatedRoute, private _router: Router,
private _fb: UntypedFormBuilder, private _fb: UntypedFormBuilder,
private communityService: CommunityService, private communityService: CommunityService,
private _manageCommunityProjectsService: ManageCommunityProjectsService, private _manageCommunityProjectsService: ManageCommunityProjectsService,
private _searchCommunityProjectsService: SearchCommunityProjectsService, private _searchCommunityProjectsService: SearchCommunityProjectsService,
private _clearCacheService: ClearCacheService) { private _clearCacheService: ClearCacheService, private indexInfoService: IndexInfoService) {
this.errorCodes = new ErrorCodes(); this.errorCodes = new ErrorCodes();
this.communitySearchUtils.status = this.errorCodes.LOADING; this.communitySearchUtils.status = this.errorCodes.LOADING;
} }
ngOnInit() { ngOnInit() {
this.subscriptions.push(this.indexInfoService.getDBLoadLastDate(this.properties).subscribe(res => {
this.lastDBLoadDate = res;
}));
this.communitySearchUtils.keyword = ""; this.communitySearchUtils.keyword = "";
this.fundersCtrl = this._fb.array([]);
this.filterForm = this._fb.group({ this.filterForm = this._fb.group({
keyword: [''], keyword: [''],
funder: this.fundersCtrl, funder: this._fb.control(null),
sort: this._fb.control(this.sortOptions[0].value) sort: this._fb.control(this.sortOptions[0].value)
}); });
this.subscriptions.push(this.filterForm.get('keyword').valueChanges.subscribe(value => { this.subscriptions.push(this.filterForm.get('keyword').valueChanges.pipe(debounceTime(500), distinctUntilChanged()).subscribe(value => {
this.searchText = new RegExp(value, 'i');
this.page = 1; this.page = 1;
this.applyFilters(); this._getCommunityProjects(this.page, this.filterForm.get('keyword').value,(this.filterForm.get("funder").value? this.filterForm.get("funder").value.id:null),
})); this.filterForm.get("sort").value.sort );
this.subscriptions.push(this.filterForm.get('funder').valueChanges.subscribe(value => {
this.page = 1;
this.applyFilters();
})); }));
this.subscriptions.push(this.filterForm.get('sort').valueChanges.subscribe(value => { this.subscriptions.push(this.filterForm.get('sort').valueChanges.subscribe(value => {
this.page = 1; this.page = 1;
this.sort(); this._getCommunityProjects(this.page, this.filterForm.get('keyword').value, this.filterForm.get("funder").value? this.filterForm.get("funder").value.id:null, this.filterForm.get("sort").value.sort );
})); }));
this.subscriptions.push(this.communityService.getCommunityAsObservable().subscribe(community => { this.subscriptions.push(this.communityService.getCommunityAsObservable().subscribe(community => {
@ -111,7 +106,8 @@ export class RemoveProjectsComponent implements OnInit {
+ this.community.communityId + ".openaire.eu" + this.properties.searchLinkToProject.split("?")[0]; + this.community.communityId + ".openaire.eu" + this.properties.searchLinkToProject.split("?")[0];
this.keyword = ''; this.keyword = '';
this._getCommunityProjects(); this._getCommunityFunders();
this._getCommunityProjects(1,this.keyword, null);
} }
})); }));
} }
@ -133,18 +129,13 @@ export class RemoveProjectsComponent implements OnInit {
} }
public confirmedDeleteProject(data: any) { public confirmedDeleteProject(data: any) {
this.subscriptions.push(this._manageCommunityProjectsService.removeProject(this.properties, this.community.communityId, this.selectedCommunityProject.id).subscribe( this.subscriptions.push(this._manageCommunityProjectsService.removeProject(this.properties, this.community.communityId, this.selectedCommunityProject.openaireId).subscribe(
data => { data => {
let index = this.communityProjects.indexOf(this.selectedCommunityProject); this._clearCacheService.clearCacheInRoute(this.openaireEntiites.PROJECT+" removed", this.community.communityId);
this.communityProjects.splice(index, 1);
this.applyFilters();
this._clearCacheService.purgeBrowserCache(this.openaireEntiites.PROJECT+" removed", this.community.communityId); this._clearCacheService.purgeBrowserCache(this.openaireEntiites.PROJECT+" removed", this.community.communityId);
NotificationHandler.rise(OpenaireEntities.PROJECT+' successfully removed!'); NotificationHandler.rise(OpenaireEntities.PROJECT+' successfully removed!');
this.communityProjectsChanged.emit({ this._getCommunityProjects(this.communitySearchUtils.page, this.keyword,null);
value: this.communityProjects,
});
this.communitySearchUtils.totalResults--;
this.communitySearchUtils.page = 1;
}, },
err => { err => {
this.handleError('An error has been occurred. Try again later!'); this.handleError('An error has been occurred. Try again later!');
@ -179,29 +170,21 @@ export class RemoveProjectsComponent implements OnInit {
this.alertModalDeleteCommunity.okButtonText = "Yes"; this.alertModalDeleteCommunity.okButtonText = "Yes";
this.alertModalDeleteCommunity.open(); this.alertModalDeleteCommunity.open();
} }
public getCommunityProjects() {
public _getCommunityProjects() { this._getCommunityProjects(this.communitySearchUtils.page, this.keyword,null );
}
public _getCommunityProjects(page, keyword, funder, orderBy = "name" ) {
this.communitySearchUtils.status = this.errorCodes.LOADING; this.communitySearchUtils.status = this.errorCodes.LOADING;
this.communityProjects = []; this.communitySearchUtils.page = page;
this.communitySearchUtils.totalResults = 0; this.communitySearchUtils.keyword = keyword;
this.communitySearchUtils.page = 1; this.subscriptions.push(this._searchCommunityProjectsService.searchProjectsWithPaging(this.properties, this.community.communityId, this.communitySearchUtils.page, this.resultsPerPage, this.communitySearchUtils.keyword, funder, orderBy).subscribe(
this.communitySearchUtils.keyword = "";
this.subscriptions.push(this._searchCommunityProjectsService.searchProjects(this.properties, this.community.communityId).subscribe(
data => { data => {
this.communityProjects = data; this.previewCommunityProjects = data.content;
this.previewCommunityProjects = this.communityProjects; this.communitySearchUtils.totalResults = data.totalElements;
this.sort();
this.communitySearchUtils.totalResults = data.length;
this.communitySearchUtils.status = this.errorCodes.DONE; this.communitySearchUtils.status = this.errorCodes.DONE;
this.communityProjectsChanged.emit({ this.communityProjectsChanged.emit({
value: this.communityProjects, value: this.communitySearchUtils.totalResults
}); });
this.createFunderFilter();
this.loading = false; this.loading = false;
}, },
err => { err => {
@ -215,90 +198,33 @@ export class RemoveProjectsComponent implements OnInit {
} else { } else {
this.communitySearchUtils.status = this.errorCodes.NOT_AVAILABLE; this.communitySearchUtils.status = this.errorCodes.NOT_AVAILABLE;
} }
this.loading = false; this.loading = false;
} }
)); ));
} }
public _getCommunityFunders() {
public createFunderFilter(): void { this.subscriptions.push(this._searchCommunityProjectsService.getProjectFunders(this.properties, this.community.communityId).subscribe(
let funders: Set<string> = new Set<string>(); data => {
this.allOptions = []; for (let funder of data) {
let i; this.allFunderOptions.push({label: funder, value: {id: funder, label: funder}});
for (i = 0; i < this.communityProjects.length; i++) {
let funder = this.communityProjects[i].funder;
if (funder && !funders.has(funder)) {
funders.add(funder);
this.allOptions.push({label: funder, value: {id: funder, label: funder}});
} }
this.previewFunderOptions =[...this.allFunderOptions];
},
err => {
} }
));
} }
public updatePage($event) { public updatePage($event) {
HelperFunctions.scroll(); HelperFunctions.scroll();
this.page = $event.value; this.page = $event.value;
this._getCommunityProjects(this.page, this.filterForm.get('keyword').value, null);
} }
addNew() { addNew() {
this.addProjects.emit(); this.addProjects.emit();
} }
public applyFilters() {
this.previewCommunityProjects = this.communityProjects.filter(project => {
return (this.filterCommunityProjectByKeyword(project) && this.filterCommunityProjectByFunder(project));
});
// check paging here!!!
if (this.previewCommunityProjects.slice((this.page - 1) * this.resultsPerPage, this.page * this.resultsPerPage).length == 0) {
this.page = 1;
}
this.sort();
}
public filterCommunityProjectByKeyword(project): boolean {
return this.searchText.toString() === ''
|| ((project.name + " " + project.acronym + " " + project.grantId + " " + project.funder)).match(this.searchText) != null;
}
public filterCommunityProjectByFunder(project): boolean {
if (this.fundersCtrl.getRawValue().length == 0) {
return true;
}
for (let funder of this.fundersCtrl.getRawValue()) {
if (project.funder.toLowerCase().indexOf(funder.label.toLowerCase()) != -1) {
return true;
}
}
return false;
}
private sort() {
let sortOption: { sort: string, descending: boolean } = this.filterForm.get('sort').value;
this.previewCommunityProjects.sort((left, right): number => {
if (sortOption.sort == "title") {
if ((left.name + left.acronym) > (right.name + right.acronym)) {
return sortOption.descending ? -1 : 1;
} else if ((left.name + left.acronym) < (right.name + right.acronym)) {
return sortOption.descending ? 1 : -1;
}
} else if (sortOption.sort == "grant") {
if (left.grantId > right.grantId) {
return sortOption.descending ? -1 : 1;
} else if (left.grantId < right.grantId) {
return sortOption.descending ? 1 : -1;
}
} else if (sortOption.sort == "funder") {
if (left.funder > right.funder) {
return sortOption.descending ? -1 : 1;
} else if (left.funder < right.funder) {
return sortOption.descending ? 1 : -1;
}
}
return 0;
});
}
public onSearchClose() { public onSearchClose() {
this.communitySearchUtils.keyword = this.filterForm.get('keyword').value; this.communitySearchUtils.keyword = this.filterForm.get('keyword').value;
@ -313,23 +239,25 @@ export class RemoveProjectsComponent implements OnInit {
NotificationHandler.rise(message, 'danger'); NotificationHandler.rise(message, 'danger');
} }
select(value: string, event, dropdownFilter: DropdownFilterComponent) { select(option, event, dropdownFilter: DropdownFilterComponent) {
console.log(option)
if(event.target instanceof HTMLInputElement) { if(event.target instanceof HTMLInputElement) {
dropdownFilter.closeDropdown(); dropdownFilter.closeDropdown();
if(event.target.checked && !this.selectedFunders.find(entity => value === entity)) { if(event.target.checked) {
this.selectedFunders.push(value); this.filterForm.get("funder").setValue(option.value);
this.fundersCtrl.setControl(this.fundersCtrl.value.length, this._fb.control(value)); this._getCommunityProjects(1, this.filterForm.get('keyword').value, this.filterForm.get('funder').value.id );
this.previewFunderOptions =[option];
} else if(!event.target.checked) { } else if(!event.target.checked) {
let index = this.selectedFunders.indexOf(value); this.filterForm.get("funder").setValue(null);
if(index !== -1) { this._getCommunityProjects(1, this.filterForm.get('keyword').value,null);
this.selectedFunders.splice(index, 1); this.previewFunderOptions =[...this.allFunderOptions];
this.fundersCtrl.removeAt(index);
}
} }
} }
} }
isSelected(value: string) { isSelected(value: string) {
return this.filterForm && this.filterForm.get('funder').value.find(funder => funder === value) return this.filterForm && this.filterForm.get('funder').value && this.filterForm.get('funder').value.id === value;
} }
} }

View File

@ -133,7 +133,7 @@ export class StatsComponent implements OnInit {
this._router.navigate(['/user-info'], { queryParams: { "errorCode": LoginErrorCodes.NOT_VALID, "redirectUrl": this._router.url} }); this._router.navigate(['/user-info'], { queryParams: { "errorCode": LoginErrorCodes.NOT_VALID, "redirectUrl": this._router.url} });
} else { } else {
//console.log(`calling ${this.properties.adminToolsAPIURL}/communityFull/${this.communityId}`); //console.log(`calling ${this.properties.adminToolsAPIURL}/communityFull/${this.communityId}`);
this.configService.communityInformationState.subscribe( this.configService.portalAsObservable.subscribe(
res => { res => {
console.debug(res); console.debug(res);
if(res) { if(res) {

View File

@ -1,32 +1,16 @@
<div page-content> <div page-content>
<div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Subjects
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<community-info tab="subjects"></community-info>
</div>
<div actions> <div actions>
<div class="uk-section-xsmall"> <div class="uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-right@m uk-flex-center uk-flex-middle uk-grid uk-margin-top" uk-grid> <div class="uk-flex uk-flex-right@m uk-flex-center uk-flex-middle uk-grid" uk-grid>
<div [disabled]="showLoading" search-input class="uk-width-1-3@xl uk-width-2-5@l uk-width-1-2@m uk-width-1-1" <div [disabled]="loading" search-input class="uk-width-1-3@xl uk-width-2-5@l uk-width-1-2@m uk-width-1-1"
[searchControl]="filterForm" [expandable]="true" placeholder="Search Subjects" searchInputClass="outer"> [searchControl]="filterForm" [expandable]="true" placeholder="Search Subjects" searchInputClass="outer">
</div> </div>
<!-- <a *ngIf="!subjectsEnabled" (click)="enablePage()" class="uk-link-heading uk-text-small uk-text-uppercase"
uk-tooltip="title:<div class='uk-padding-small'>This information will be visible in <b>Subjects page</b> of Research Community Dashboard, which is <b>disabled</b>. <br> Click to enable id.</div>">
<span class="uk-text-secondary"><icon name="check_circle_outlined"></icon></span>
Enable page
</a>-->
<div> <div>
<button class="uk-button uk-button-default uk-flex uk-flex-middle" <button class="uk-button uk-button-default uk-flex uk-flex-middle"
[disabled]="showLoading" [class.uk-disabled]="showLoading" [disabled]="loading" [class.uk-disabled]="loading"
(click)="newSubject()" (click)="editAllSubjects()"
uk-tooltip="title:<div><div class='uk-margin-small-bottom uk-text-bold'>Add new subjects</div> All the research results associated to the subjects specified here will be automatically linked to the community dashboard in the next run of OpenAIRE workflows.</div>"> uk-tooltip="title:<div><div class='uk-margin-small-bottom uk-text-bold'>Add or edit subjects</div> All the research results associated to the subjects specified here will be automatically linked to the community dashboard in the next run of OpenAIRE workflows.</div>">
<icon name="add" [flex]="true"></icon> <span>Add/Edit Subjects</span>
<span class="uk-margin-small-left">New Subject</span>
</button> </button>
</div> </div>
</div> </div>
@ -34,95 +18,321 @@
</div> </div>
<div inner> <div inner>
<div class="uk-section uk-section-small uk-position-relative" style="min-height: 60vh"> <div class="uk-section uk-section-small uk-position-relative" style="min-height: 60vh">
<div *ngIf="showLoading" class="uk-position-center"> <div *ngIf="loading" class="uk-position-center">
<loading></loading> <loading></loading>
</div> </div>
<div *ngIf="!showLoading"> <validate-page-enabled pageRoute="/subjects"></validate-page-enabled>
<div *ngIf="community.subjects.length == 0" <div *ngIf="!loading">
<div *ngIf="displayedSubjects?.length == 0 && displayedSdg?.length == 0 && displayedFos?.length == 0"
class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold"> class="uk-card uk-card-default uk-padding-large uk-text-center uk-margin-bottom uk-text-bold">
<div>No subjects <div>No subjects</div>
<span *ngIf="originalSubjects.length == 0; else: notFound">for {{community.shortTitle}}</span>
<ng-template #notFound>found</ng-template>
</div> </div>
</div> <div *ngIf="displayedSubjects?.length > 0 || displayedSdg?.length > 0 || displayedFos?.length > 0">
<div *ngIf="community.subjects.length > 0"> <ul uk-tab class="uk-tab uk-margin-bottom uk-flex uk-flex-center uk-flex-left@m">
<no-load-paging *ngIf="community.subjects.length > 0" [type]="'Subjects'" <li class="uk-active" *ngIf="displayedAllSubjects?.length" (click)="groupSubjects(displayedAllSubjects, 'all')">
[page]="page" [pageSize]="size" (pageChange)="updatePage($event)" <a>All ({{displayedAllSubjects.length}})</a>
[totalResults]="community.subjects.length"> </li>
</no-load-paging> <li (click)="groupSubjects(displayedSubjects, 'freeText')">
<div class="uk-grid uk-grid-large uk-grid-match uk-child-width-1-1 uk-child-width-1-2@m uk-margin-top uk-margin-bottom" uk-grid> <a>Free Text ({{displayedSubjects.length}})</a>
<div *ngFor='let subject of currentPage; let i = index;'> </li>
<div class="uk-card uk-card-default"> <li (click)="groupSubjects(displayedSdg, 'sdg')">
<div class="uk-card-body"> <a>SDGs ({{displayedSdg.length}})</a>
<h6 uk-tooltip="title:All the research results associated to this subjects will be automatically linked to the community dashboard." </li>
class="uk-display-inline-block"> <li (click)="groupSubjects(displayedFos, 'fos')">
{{subject}} <a>Fields of Science ({{displayedFos.length}})</a>
</h6> </li>
</div> </ul>
<div class="uk-card-footer uk-padding-remove-vertical"> <ul class="uk-switcher">
<div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid> <li>
<ng-container *ngIf="displayedAllSubjects?.length">
<div> <div>
<div class="uk-padding-small uk-padding-remove-horizontal"> <ul class="uk-nav uk-nav-default uk-flex uk-flex-wrap">
<a (click)="editSubject(subject)" <li *ngFor="let item of groupedAllSubjects; let i = index;" class="uk-margin-right" [class.uk-margin-left]="i != 0"
class="uk-button uk-button-link uk-flex uk-flex-middle"> [class]="indexAll == i ? 'uk-active':''" (click)="changeDisplayedSubjects(i, item)">
<icon name="edit" [flex]="true"></icon> <a class="uk-padding-remove">{{item.group}}</a>
<span class="uk-margin-xsmall-left">Edit</span> </li>
</ul>
</div>
<!-- View for 'All' -->
<div *ngIf="indexAll == 0 && groupedAllSubjects.length > 1" class="uk-margin-large-top uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let item of groupedAllSubjects.slice(1); let i = index;">
<div>
<h6>{{item.group}}</h6>
<div *ngFor="let subItem of item.data.slice(0, subjectsLimit)" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
<div *ngIf="item.data.length > subjectsLimit">
<a (click)="changeDisplayedSubjects(i+1, item)" class="view-more-less-link">
View all
</a> </a>
</div> </div>
</div> </div>
</div>
</div>
<!-- View for a single group -->
<div *ngIf="indexAll != 0 || groupedAllSubjects.length == 1" class="uk-margin-large-top">
<div> <div>
<div class="uk-padding-small uk-padding-remove-horizontal"> <div>
<button class="uk-button uk-button-link uk-flex uk-flex-middle" <h6>{{groupedAllSubjects[indexAll].group}}</h6>
(click)="removeModalOpen(subject, i)"> <ng-container *ngIf="subjectsColumns?.length == 0; else elseBlock">
<icon name="delete" [flex]="true"></icon> <div *ngFor="let subItem of groupedAllSubjects[indexAll].data" class="uk-margin-small-bottom">
<span class="uk-margin-xsmall-left">Delete</span> <span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
</button> {{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
</ng-container>
<ng-template #elseBlock>
<div class="uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let group of subjectsColumns">
<div *ngFor="let subItem of group" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
</div>
</div>
</ng-template>
</div>
</div>
</div>
</ng-container>
<ng-container *ngIf="displayedAllSubjects?.length === 0">
<div class="uk-position-relative uk-height-medium">
<h6 class="uk-position-center uk-margin-remove">There are no subjects yet</h6>
</div>
</ng-container>
</li>
<li>
<ng-container *ngIf="displayedSubjects?.length">
<div>
<ul class="uk-nav uk-nav-default uk-flex uk-flex-wrap">
<li *ngFor="let item of groupedSubjects; let i = index;" class="uk-margin-right" [class.uk-margin-left]="i != 0"
[class]="indexSubjects == i ? 'uk-active':''" (click)="changeDisplayedSubjects(i, item)">
<a class="uk-padding-remove">{{item.group}}</a>
</li>
</ul>
</div>
<!-- View for 'All' -->
<div *ngIf="indexSubjects == 0 && groupedSubjects.length > 1" class="uk-margin-large-top uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let item of groupedSubjects.slice(1); let i = index;">
<div>
<h6>{{item.group}}</h6>
<div *ngFor="let subItem of item.data.slice(0, subjectsLimit)" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
<div *ngIf="item.data.length > subjectsLimit">
<a (click)="changeDisplayedSubjects(i+1, item)" class="view-more-less-link">
View all
</a>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
<!-- View for a single group -->
<div *ngIf="indexSubjects != 0 || groupedSubjects.length == 1" class="uk-margin-large-top">
<div>
<div>
<h6>{{groupedSubjects[indexSubjects]?.group}}</h6>
<ng-container *ngIf="subjectsColumns?.length == 0; else elseBlock">
<div *ngFor="let subItem of groupedSubjects[indexSubjects]?.data" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
</ng-container>
<ng-template #elseBlock>
<div class="uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let group of subjectsColumns">
<div *ngFor="let subItem of group" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div> </div>
</div> </div>
</div> </div>
<div class="uk-margin-small-top"> </ng-template>
<paging-no-load [currentPage]="page" [totalResults]="community.subjects.length" [size]="size"
(pageChange)="updatePage($event)" customClasses="uk-flex-right@m uk-flex-center">
</paging-no-load>
</div> </div>
</div> </div>
</div> </div>
</ng-container>
<ng-container *ngIf="displayedSubjects?.length === 0">
<div class="uk-position-relative uk-height-medium">
<h6 class="uk-position-center uk-margin-remove">There are no subjects yet</h6>
</div>
</ng-container>
</li>
<li>
<ng-container *ngIf="displayedSdg?.length">
<div>
<ul class="uk-nav uk-nav-default uk-flex uk-flex-wrap">
<li *ngFor="let item of groupedSdg; let i = index;" class="uk-margin-right" [class.uk-margin-left]="i != 0"
[class]="indexSdg == i ? 'uk-active':''" (click)="changeDisplayedSubjects(i, item)">
<a class="uk-padding-remove">{{item.group}}</a>
</li>
</ul>
</div>
<!-- View for 'All' -->
<div *ngIf="indexSdg == 0 && groupedSdg.length > 1" class="uk-margin-large-top uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let item of groupedSdg.slice(1); let i = index;">
<div>
<h6>{{item.group}}</h6>
<div *ngFor="let subItem of item.data.slice(0, subjectsLimit)" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
<div *ngIf="item.data.length > subjectsLimit">
<a (click)="changeDisplayedSubjects(i+1, item)" class="view-more-less-link">
View all
</a>
</div>
</div>
</div>
</div>
<!-- View for a single group -->
<div *ngIf="indexSdg != 0 || groupedSdg.length == 1" class="uk-margin-large-top">
<div>
<div>
<h6>{{groupedSdg[indexSdg].group}}</h6>
<ng-container *ngIf="subjectsColumns?.length == 0; else elseBlock">
<div *ngFor="let subItem of groupedSdg[indexSdg].data" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
</ng-container>
<ng-template #elseBlock>
<div class="uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let group of subjectsColumns">
<div *ngFor="let subItem of group" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
</div>
</div>
</ng-template>
</div>
</div>
</div>
</ng-container>
<ng-container *ngIf="displayedSdg?.length === 0">
<div class="uk-position-relative uk-height-medium">
<h6 class="uk-position-center uk-margin-remove">There are no subjects yet</h6>
</div>
</ng-container>
</li>
<li>
<ng-container *ngIf="displayedFos?.length">
<div>
<ul class="uk-nav uk-nav-default uk-flex uk-flex-wrap">
<li *ngFor="let item of groupedFos; let i = index;" class="uk-margin-right" [class.uk-margin-left]="i != 0"
[class]="indexFos == i ? 'uk-active':''" (click)="changeDisplayedSubjects(i, item)">
<a class="uk-padding-remove">{{item.group}}</a>
</li>
</ul>
</div>
<!-- View for 'All' -->
<div *ngIf="indexFos == 0 && groupedFos.length > 1" class="uk-margin-large-top uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let item of groupedFos.slice(1); let i = index;">
<div>
<h6>{{item.group}}</h6>
<div *ngFor="let subItem of item.data.slice(0, subjectsLimit)" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
<div *ngIf="item.data.length > subjectsLimit">
<a (click)="changeDisplayedSubjects(i+1, item)" class="view-more-less-link">
View all
</a>
</div>
</div>
</div>
</div>
<!-- View for a single group -->
<div *ngIf="indexFos != 0 || groupedFos.length == 1" class="uk-margin-large-top">
<div>
<div>
<h6>{{groupedFos[indexFos].group}}</h6>
<ng-container *ngIf="subjectsColumns?.length == 0; else elseBlock">
<div *ngFor="let subItem of groupedFos[indexFos].data" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
</ng-container>
<ng-template #elseBlock>
<div class="uk-grid uk-child-width-1-4@m" uk-grid>
<div *ngFor="let group of subjectsColumns">
<div *ngFor="let subItem of group" class="uk-margin-small-bottom">
<span [attr.uk-tooltip]="subItem.length > maxCharacters ? 'cls: uk-active' : 'cls: uk-invisible'" [title]="subItem">
{{subItem.length > maxCharacters ? subItem.substring(0,maxCharacters)+'...' : subItem}}
</span>
</div>
</div>
</div>
</ng-template>
</div>
</div>
</div>
</ng-container>
<ng-container *ngIf="displayedFos?.length === 0">
<div class="uk-position-relative uk-height-medium">
<h6 class="uk-position-center uk-margin-remove">There are no subjects yet</h6>
</div>
</ng-container>
</li>
</ul>
</div>
</div>
</div> </div>
</div> </div>
</div> </div>
<modal-alert #deleteModal (alertOutput)="saveSubjects()" [overflowBody]="false" classTitle="uk-background-primary uk-light"></modal-alert> <fs-modal #fsModal classBody="uk-container-large" (okEmitter)="saveAllSubjects()" [okButtonDisabled]="!hasChanges && !sdgSelection.hasChanges && !fosSelection.hasChanges">
<fs-modal #fsModal classBody="uk-container-small" (okEmitter)="saveSubjects()" [okButtonDisabled]="myForm && (myForm.invalid || !myForm.dirty)"> <div>
<form *ngIf="myForm"> <ul uk-tab #modalTabs class="uk-tab uk-margin-top uk-margin-large-bottom uk-flex uk-flex-center uk-flex-left@m">
<div class="uk-margin-top uk-flex-center uk-flex uk-margin-medium-bottom"> <li class="uk-active">
<a *ngIf="!isEditModal" (click)="addSubjectInForm()"> <a>Free Text ({{displayedSubjects.length}})</a>
<button class="uk-button uk-button-primary uk-flex uk-flex-middle"> </li>
<icon name="add" [flex]="true"></icon> <li>
<span class="uk-margin-xsmall-left">Add Subject</span> <a>SDGs ({{sdgSelection.getSelectedSubjects().length}})<span *ngIf="sdgSelection.hasChanges">*</span></a>
</li>
<li>
<a>Fields of Science ({{fosSelection.getSelectedSubjects().length}})<span *ngIf="fosSelection.hasChanges">*</span></a>
</li>
</ul>
<ul class="uk-switcher">
<li *ngIf="subjectsForm">
<div #addSubjectsInput input [type]="'chips'" [formInput]="subjectsForm" [inputClass]="'flat small'" [extendEnter]="onEnter"
[separators]="[',', 'enter']" [visibleChips]="3" class="uk-width-1-1 uk-width-xlarge@m"
[placeholder]="{static: true, label: 'Type subjects as free text keywords'}">
<div tools class="uk-flex uk-flex-right">
<button (click)="addSubjectsIntoList()" class="uk-button uk-button-link uk-margin-xsmall-left uk-margin-right">add</button>
</div>
<div note class="uk-text-xsmall">Separate subjects with commas</div>
</div>
<div class="uk-margin-large-top">
<span *ngFor="let subject of displayedSubjects; let i = index;"
class="uk-label uk-label-primary uk-flex-inline uk-flex-middle uk-margin-right uk-margin-bottom">
<span class="uk-margin-small-right uk-text-truncate">{{subject}}</span>
<button (click)="removeSubjectFromList(i)" class="uk-close uk-icon">
<icon name="close" flex="true" ratio="0.7"></icon>
</button> </button>
</a> </span>
</div> </div>
<div class="uk-grid uk-child-width-1-1" uk-grid> </li>
<div *ngFor=" let control of myForm.controls; index as i" class="uk-flex uk-flex-middle"> <li>
<div input [formInput]="myForm.controls[i]" type="text" <sdg-selection #sdgSelection [subjects]="displayedSdg" [isFeedback]="false"></sdg-selection>
placeholder="Type subjects as free text keywords" class="uk-width-expand"></div> </li>
<div *ngIf="!isEditModal" class="uk-width-auto uk-flex uk-flex-center uk-margin-left"> <li>
<button class="uk-close uk-icon" [class.uk-invisible]="myForm.length === 1" <fos-selection #fosSelection [subjects]="displayedFos" [inModal]="true"></fos-selection>
(click)="removeSubjectInForm(i)"> </li>
<icon name="close" [flex]="true" [ratio]="1.5"></icon> </ul>
</button>
</div> </div>
</div>
</div>
</form>
</fs-modal> </fs-modal>
<!--<modal-alert #enablePageModal (alertOutput)="enablePage()">
<div class="uk-padding uk-padding-remove-horizontal">
This information will be visible in <span class="uk-text-bold">Subjects page</span> of Research Community
Dashboard, which is <span class="uk-text-bold">disabled</span>.
Do you want to <span class="uk-text-bold">enable</span> it now?
</div>
</modal-alert>-->

View File

@ -1,6 +1,6 @@
import {Component, ElementRef, OnInit, ViewChild} from '@angular/core'; import {Component, ElementRef, OnInit, ViewChild} from '@angular/core';
import {UntypedFormArray, UntypedFormBuilder, UntypedFormControl} from '@angular/forms'; import {UntypedFormArray, UntypedFormBuilder, UntypedFormControl} from '@angular/forms';
import {ActivatedRoute, Router} from '@angular/router'; import {ActivatedRoute} from '@angular/router';
import {CommunityService} from '../../../openaireLibrary/connect/community/community.service'; import {CommunityService} from '../../../openaireLibrary/connect/community/community.service';
import {SubjectsService} from '../subjects.service'; import {SubjectsService} from '../subjects.service';
import {EnvProperties} from '../../../openaireLibrary/utils/properties/env-properties'; import {EnvProperties} from '../../../openaireLibrary/utils/properties/env-properties';
@ -8,67 +8,106 @@ import {Title} from '@angular/platform-browser';
import {properties} from '../../../../environments/environment'; import {properties} from '../../../../environments/environment';
import {AlertModal} from '../../../openaireLibrary/utils/modal/alert'; import {AlertModal} from '../../../openaireLibrary/utils/modal/alert';
import {SearchInputComponent} from '../../../openaireLibrary/sharedComponents/search-input/search-input.component'; import {SearchInputComponent} from '../../../openaireLibrary/sharedComponents/search-input/search-input.component';
import {Subscription} from 'rxjs'; import {forkJoin, Subscription} from 'rxjs';
import {CommunityInfo} from '../../../openaireLibrary/connect/community/communityInfo'; import {CommunityInfo} from '../../../openaireLibrary/connect/community/communityInfo';
import {FullScreenModalComponent} from 'src/app/openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.component'; import {
FullScreenModalComponent
} from 'src/app/openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.component';
import {HelperFunctions} from 'src/app/openaireLibrary/utils/HelperFunctions.class'; import {HelperFunctions} from 'src/app/openaireLibrary/utils/HelperFunctions.class';
import {NotificationHandler} from "../../../openaireLibrary/utils/notification-handler"; import {NotificationHandler} from "../../../openaireLibrary/utils/notification-handler";
import {ClearCacheService} from "../../../openaireLibrary/services/clear-cache.service"; import {ClearCacheService} from "../../../openaireLibrary/services/clear-cache.service";
import {SdgSelectionComponent} from '../../../openaireLibrary/sdg/sdg-selection/sdg-selection.component';
import {FosSelectionComponent} from '../../../openaireLibrary/fos/fos-selection/fos-selection.component';
import {InputComponent} from "../../../openaireLibrary/sharedComponents/input/input.component";
declare var UIkit: any;
@Component({ @Component({
selector: 'subjects-edit-form', selector: 'subjects-edit-form',
templateUrl: './subjects-edit-form.component.html', templateUrl: './subjects-edit-form.component.html',
}) })
export class SubjectsEditFormComponent implements OnInit { export class SubjectsEditFormComponent implements OnInit {
myForm = new UntypedFormArray([new UntypedFormControl({subject: ''})]); properties: EnvProperties = properties;
public showLoading = true; communityId: string = null;
public res = []; community: CommunityInfo = null;
loading = true;
params: any; params: any;
public communityId: string = null; private subscriptions: any[] = [];
public community: CommunityInfo = null;
public properties: EnvProperties = properties; filterForm: UntypedFormControl;
public edit = null; subjectsForm = new UntypedFormArray([]);
public originalSubjects = []; hasChanges: boolean = false;
originalAllSubjects = [];
originalSubjects = [];
originalSdg = [];
originalFos = [];
displayedAllSubjects = [];
displayedSubjects = [];
displayedSdg = [];
displayedFos = [];
groupedAllSubjects = [];
groupedSubjects = [];
groupedSdg = [];
groupedFos = [];
subjectsColumns = [];
subjectsLimit: number = 6;
maxCharacters: number = 25;
activeTab: 'all' | 'freeText' | 'sdg' | 'fos' = 'all';
indexAll: number = 0;
indexSubjects: number = 0;
indexSdg: number = 0;
indexFos: number = 0;
@ViewChild('addSubjectsInput') addSubjectsInput: InputComponent;
@ViewChild('editModal') editModal: AlertModal; @ViewChild('editModal') editModal: AlertModal;
@ViewChild('deleteModal') deleteModal: AlertModal; @ViewChild('deleteModal') deleteModal: AlertModal;
@ViewChild('fsModal', {static: true}) fullscreen: FullScreenModalComponent; @ViewChild('fsModal', {static: true}) fullscreen: FullScreenModalComponent;
page = 1; @ViewChild('modalTabs') modalTabs: ElementRef;
size = 10; @ViewChild('sdgSelection') sdgSelection: SdgSelectionComponent;
selectedSubjects = []; @ViewChild('fosSelection') fosSelection: FosSelectionComponent;
isEditModal: boolean = false;
public selectedKeyword: string; onEnter: () => void = () => {
@ViewChild('searchInputComponent') searchInputComponent: SearchInputComponent; this.addSubjectsIntoList();
public filterForm: UntypedFormControl;
private subscriptions: any[] = [];
/*//Check again functionality to enable page
subjectsPage;
@ViewChild('enablePageModal') enablePageModal: AlertModal;*/
constructor(private element: ElementRef,
private route: ActivatedRoute,
private _router: Router,
public _fb: UntypedFormBuilder,
private title: Title,
// private _helpContentService: HelpContentService,
private _communityService: CommunityService,
private _subjectsService: SubjectsService,
private _clearCacheService: ClearCacheService
) {
} }
constructor(private route: ActivatedRoute,
public _fb: UntypedFormBuilder,
private title: Title,
private _communityService: CommunityService,
private _subjectsService: SubjectsService,
private _clearCacheService: ClearCacheService) {
}
ngOnInit() { ngOnInit() {
this.filterForm = this._fb.control(''); this.filterForm = this._fb.control('');
this.subscriptions.push(this.filterForm.valueChanges.subscribe(value => { this.subscriptions.push(this.filterForm.valueChanges.subscribe(value => {
this.page = 1; this.displayedAllSubjects = this.originalAllSubjects.filter(subject => {
this.community.subjects = this.originalSubjects.filter(subject => {
return !value || subject.toLowerCase().indexOf(value.toLowerCase()) != -1 return !value || subject.toLowerCase().indexOf(value.toLowerCase()) != -1
}); });
this.displayedSubjects = this.originalSubjects.filter(subject => {
return !value || subject.toLowerCase().indexOf(value.toLowerCase()) != -1
});
this.displayedSdg = this.originalSdg.filter(subject => {
return !value || subject.toLowerCase().indexOf(value.toLowerCase()) != -1
});
this.displayedFos = this.originalFos.filter(subject => {
return !value || subject.toLowerCase().indexOf(value.toLowerCase()) != -1
});
if (this.activeTab === 'all') {
this.groupSubjects(this.displayedAllSubjects, 'all');
} else if (this.activeTab === 'freeText') {
this.groupSubjects(this.displayedSubjects, 'freeText');
} else if (this.activeTab === 'sdg') {
this.groupSubjects(this.displayedSdg, 'sdg');
} else if (this.activeTab === 'fos') {
this.groupSubjects(this.displayedFos, 'fos');
}
})); }));
this.subscriptions.push(this.route.params.subscribe( this.subscriptions.push(this.route.params.subscribe(
params => { params => {
this.communityId = params['community']; this.communityId = params['community'];
this.title.setTitle(this.communityId.toUpperCase() + ' | Subjects'); this.title.setTitle(this.communityId.toUpperCase() + ' | Subjects');
this.showLoading = true; this.loading = true;
this.subscriptions.push(this._communityService.getCommunityAsObservable().subscribe( this.subscriptions.push(this._communityService.getCommunityAsObservable().subscribe(
community => { community => {
this.community = community; this.community = community;
@ -76,7 +115,7 @@ export class SubjectsEditFormComponent implements OnInit {
community: encodeURIComponent( community: encodeURIComponent(
'"' + community.queryId + '"') '"' + community.queryId + '"')
}; };
this.community.subjects.sort((n1,n2)=> { this.community.subjects.sort((n1, n2) => {
if (n1.toLowerCase() > n2.toLowerCase()) { if (n1.toLowerCase() > n2.toLowerCase()) {
return 1; return 1;
} }
@ -85,19 +124,19 @@ export class SubjectsEditFormComponent implements OnInit {
} }
return 0; return 0;
}); });
this.displayedSubjects = HelperFunctions.copy(this.community.subjects);
this.originalSubjects = []; this.displayedSdg = this.community.sdg;
for (let i = 0; i < this.community.subjects.length; i++) { this.displayedFos = this.community.fos;
this.originalSubjects.push(this.community.subjects[i]); this.displayedAllSubjects = [...this.displayedSubjects, ...this.displayedSdg, ...this.displayedFos];
} this.groupSubjects(this.displayedAllSubjects, 'all');
if (this.community.subjects.length === 0) { this.originalAllSubjects = HelperFunctions.copy(this.displayedAllSubjects);
this.community.subjects.push(''); this.originalSubjects = HelperFunctions.copy(this.displayedSubjects);
} this.originalSdg = HelperFunctions.copy(this.displayedSdg);
this.showLoading = false; this.originalFos = HelperFunctions.copy(this.displayedFos);
this.loading = false;
}, },
error => this.handleUpdateError('System error retrieving community profile', error) error => this.handleUpdateError('System error retrieving community profile', error)
)); ));
// this.getSubjectsPageStatus();
})); }));
} }
@ -110,18 +149,108 @@ export class SubjectsEditFormComponent implements OnInit {
}); });
} }
private removeModalOpen(subject: string, i: any) { public groupSubjects(subjects: string[], type: string) {
this.selectedSubjects = [subject]; if (subjects.length === 0) {
this.reset(['']); return [];
this.deleteModal.cancelButton = true; }
this.deleteModal.okButton = true; subjects.sort((a, b) => a.localeCompare(b));
this.deleteModal.alertTitle = 'Delete Subject'; if (type === 'all') {
this.deleteModal.message = 'Are you sure you want to delete this subject?'; this.indexAll = 0;
this.deleteModal.okButtonText = 'Yes'; this.activeTab = 'all';
this.deleteModal.cancelButtonText = 'No'; this.groupedAllSubjects = Object.values(
this.deleteModal.open(); subjects.reduce((acc, subject) => {
let firstLetter = subject[0].toLocaleUpperCase();
if (!acc[firstLetter]) {
acc[firstLetter] = {group: firstLetter, data: [subject]};
} else {
acc[firstLetter].data.push(subject);
}
return acc;
}, {})
)
if (subjects.length > 1) {
this.groupedAllSubjects.unshift({group: 'All', data: subjects});
}
}
if (type === 'freeText') {
this.indexSubjects = 0;
this.activeTab = 'freeText';
this.groupedSubjects = Object.values(
subjects.reduce((acc, subject) => {
let firstLetter = subject[0].toLocaleUpperCase();
if (!acc[firstLetter]) {
acc[firstLetter] = {group: firstLetter, data: [subject]};
} else {
acc[firstLetter].data.push(subject);
}
return acc;
}, {})
)
if (subjects.length > 1) {
this.groupedSubjects.unshift({group: 'All', data: subjects});
}
}
if (type === 'sdg') {
this.indexSdg = 0;
this.activeTab = 'sdg';
this.groupedSdg = Object.values(
subjects.reduce((acc, subject) => {
let firstLetter = subject[0].toLocaleUpperCase();
if (!acc[firstLetter]) {
acc[firstLetter] = {group: firstLetter, data: [subject]};
} else {
acc[firstLetter].data.push(subject);
}
return acc;
}, {})
)
if (subjects.length > 1) {
this.groupedSdg.unshift({group: 'All', data: subjects});
}
}
if (type === 'fos') {
this.indexFos = 0;
this.activeTab = 'fos';
this.groupedFos = Object.values(
subjects.reduce((acc, subject) => {
let key = subject.substring(0, 2).toLocaleUpperCase();
if (!acc[key]) {
acc[key] = {group: key, data: [subject]};
} else {
acc[key].data.push(subject);
}
return acc;
}, {})
)
if (subjects.length > 1) {
this.groupedFos.unshift({group: 'All', data: subjects});
}
}
} }
public changeDisplayedSubjects(i, group) {
this.subjectsColumns = [];
if (this.activeTab === 'all') {
this.indexAll = i;
} else if (this.activeTab === 'freeText') {
this.indexSubjects = i;
} else if (this.activeTab === 'sdg') {
this.indexSdg = i;
} else if (this.activeTab === 'fos') {
this.indexFos = i;
}
if (group.data.length > this.subjectsLimit && group.group != 'All') {
this.divideSubjects(group);
}
}
public divideSubjects(group) {
let columns = [];
for (let i = 0; i < (group.data.length / this.subjectsLimit); i++) {
columns.push(group.data.slice(i * this.subjectsLimit, ((i + 1) * this.subjectsLimit)));
}
this.subjectsColumns = columns;
}
public getSubjectsExistOnlyInFirst(firstArray: string[], secondArray: string[]): string[] { public getSubjectsExistOnlyInFirst(firstArray: string[], secondArray: string[]): string[] {
const difference = []; const difference = [];
@ -129,75 +258,96 @@ export class SubjectsEditFormComponent implements OnInit {
if (secondArray.indexOf(firstArray[i]) === -1) { if (secondArray.indexOf(firstArray[i]) === -1) {
difference.push(firstArray[i]); difference.push(firstArray[i]);
} }
} }
return difference; return difference;
} }
public saveSubjects() { public editAllSubjects() {
UIkit.tab(this.modalTabs.nativeElement).show(0);
this.displayedSubjects = HelperFunctions.copy(this.community.subjects);
this.sdgSelection.reset();
this.sdgSelection.sdgs.markAsPristine();
this.fosSelection.reset();
this.fosSelection.fosOptions.markAsPristine();
this.fullscreen.title = "Add/Edit Subjects";
this.fullscreen.okButtonText = "Save";
this.fullscreen.back = true;
this.fullscreen.okButton = true;
this.fullscreen.open();
}
public addSubjectsIntoList() {
if (this.addSubjectsInput.searchControl.getRawValue()) {
this.addSubjectsInput.add(null, true);
}
this.subjectsForm.getRawValue().forEach(element => {
this.displayedSubjects.unshift(element);
});
this.subjectsForm.clear();
this.hasChanges = true;
}
public removeSubjectFromList(i) {
this.displayedSubjects.splice(i, 1);
this.hasChanges = true;
}
public saveAllSubjects() {
let selectedSdg = this.sdgSelection.getSelectedSubjects().map(a => a.id);
let selectedFos = this.fosSelection.getSelectedSubjects().map(a => a.id);
let requests = [
...this.saveSubjects(this.community.subjects, this.displayedSubjects, 'subjects'),
...this.saveSubjects(this.community.sdg, selectedSdg, 'sdg'),
...this.saveSubjects(this.community.fos, selectedFos, 'fos')
];
this.subscriptions.push(forkJoin(requests).subscribe(res => {
this.afterUpdateActions(res, "updated");
}));
}
public saveSubjects(subjects, displayedSubjects, type: string) {
if (this.communityId != null && this.communityId !== '') { if (this.communityId != null && this.communityId !== '') {
this.showLoading = true; this.loading = true;
const subjectsToDeleteAr = this.getSubjectsExistOnlyInFirst(this.selectedSubjects, this.myForm.getRawValue()); const subjectsToDeleteAr = this.getSubjectsExistOnlyInFirst(subjects, displayedSubjects);
const subjectsToAddAr = this.getSubjectsExistOnlyInFirst(this.myForm.getRawValue(), this.selectedSubjects); const subjectsToAddAr = this.getSubjectsExistOnlyInFirst(displayedSubjects, subjects);
const subjectsToDelete = this.getNonEmptyItems(subjectsToDeleteAr); const subjectsToDelete = this.getNonEmptyItems(subjectsToDeleteAr);
const subjectsToAdd = this.getNonEmptyItems(subjectsToAddAr); const subjectsToAdd = this.getNonEmptyItems(subjectsToAddAr);
if (subjectsToAdd.length > 0 && subjectsToDelete.length > 0) { let requests = [];
this.subscriptions.push(this._subjectsService.removeSubjects( if (subjectsToDelete.length > 0) {
this.properties.communityAPI + this.communityId + '/subjects', subjectsToDelete).subscribe(res =>{ requests.push(this._subjectsService.removeSubjects(
this.subscriptions.push(this._subjectsService.addSubjects( this.properties.communityAPI + this.communityId + '/' + type, subjectsToDelete))
this.properties.communityAPI + this.communityId + '/subjects', subjectsToAdd).subscribe(res => {
this.afterUpdateActions(res, "added");
}));
}));
} else if (subjectsToAdd.length > 0) {
this.subscriptions.push(this._subjectsService.addSubjects(
this.properties.communityAPI + this.communityId + '/subjects', subjectsToAdd).subscribe(res => {
this.afterUpdateActions(res, "added");
},
error => this.handleUpdateError('System error updating subjects', error)
));
} else if (subjectsToDelete.length > 0) {
this.subscriptions.push(this._subjectsService.removeSubjects(
this.properties.communityAPI + this.communityId + '/subjects', subjectsToDelete).subscribe(res => {
this.afterUpdateActions(res, "deleted");
},
error => this.handleUpdateError('System error updating subjects', error)
));
} }
if (subjectsToAdd.length > 0) {
requests.push(this._subjectsService.addSubjects(
this.properties.communityAPI + this.communityId + '/' + type, subjectsToAdd))
}
return requests;
} }
} }
handleUpdateError(message: string, error = null) { handleUpdateError(message: string, error = null) {
if(error) { if (error) {
console.error(error) console.error(error)
} }
NotificationHandler.rise(message, 'danger'); NotificationHandler.rise(message, 'danger');
this.showLoading = false; this.loading = false;
} }
afterUpdateActions(res, message: string) { afterUpdateActions(response, message: string) {
this._communityService.setCommunity(this._communityService.parseCommunity(res)); response.forEach(res => {
this.community.subjects = res['subjects']; if (res.subjects) {
this.originalSubjects = []; this.community.subjects = res.subjects;
for (let i = 0; i < this.community.subjects.length; i++) { } else if (res.sdg) {
this.originalSubjects.push(this.community.subjects[i]); this.community.sdg = res.sdg;
} else if (res.fos) {
this.community.fos = res.fos;
} }
this.originalSubjects.sort((n1,n2)=> {
if (n1.toLowerCase() > n2.toLowerCase()) {
return 1;
}
if (n1.toLowerCase() < n2.toLowerCase()) {
return -1;
}
return 0;
}); });
this.page = 1; this._communityService.updateSubjects(this.community.subjects, this.community.fos, this.community.sdg);
this.community.subjects = this.originalSubjects.filter(subject => { this._clearCacheService.clearCacheInRoute("Subjects " + message, this.communityId);
return !this.filterForm.value || subject.toLowerCase().indexOf(this.filterForm.value.toLowerCase()) != -1 this._clearCacheService.purgeBrowserCache("Subjects " + message, this.communityId);
}).sort(); NotificationHandler.rise('Subjects successfully ' + message + '!')
this._clearCacheService.purgeBrowserCache("Subject "+message, this.communityId); this.loading = false;
NotificationHandler.rise('Subject successfully ' + message + '!')
this.showLoading = false;
} }
@ -231,111 +381,4 @@ export class SubjectsEditFormComponent implements OnInit {
return false; return false;
} }
} }
public addSubjectInForm() {
this.myForm.push(new UntypedFormControl(''));
}
public removeSubjectInForm(i: number) {
this.myForm.removeAt(i);
}
public reset(subjects: string[]) {
this.myForm = new UntypedFormArray([]);
for (let subject in subjects) {
this.myForm.push(new UntypedFormControl(''));
}
this.myForm.patchValue(subjects);
}
newSubject() {
this.isEditModal = false;
this.selectedSubjects = [];
this.reset([""]);
this.fullscreen.title = "Add Subject";
this.fullscreen.okButtonText = "Save";
this.fullscreen.back = true;
this.fullscreen.okButton = true;
this.fullscreen.open();
}
get currentPage() {
if(this.community.subjects) {
return this.community.subjects.slice((this.page - 1) * this.size, this.page * this.size);
} else {
return [];
}
}
public updatePage(event) {
this.page = event.value;
HelperFunctions.scroll();
}
public editSubject(subject: string) {
this.isEditModal = true;
this.selectedSubjects = [subject];
this.reset([subject]);
this.fullscreen.title = "Edit Subject";
this.fullscreen.okButtonText = "Save";
this.fullscreen.back = true;
this.fullscreen.okButton = true;
this.fullscreen.open();
}
private formModalOpen(title: string, yesBtn: string) {
this.editModal.okButtonLeft = false;
this.editModal.cancelButton = true;
this.editModal.okButton = true;
this.editModal.alertTitle = title;
this.editModal.okButtonText = yesBtn;
this.editModal.open();
}
public onSearchClose() {
this.selectedKeyword = this.filterForm.value;
}
public resetInput() {
this.selectedKeyword = null;
this.searchInputComponent.reset()
}
/*
//Check again functionality to enable page
private getSubjectsPageStatus() {
this._helpContentService.getCommunityPagesByRoute(this.communityId, '/subjects', this.properties.adminToolsAPIURL).subscribe((page) => {
this.subjectsPage = page;
});
}
public get subjectsEnabled(): boolean {
return !this.subjectsPage || this.subjectsPage.isEnabled;
}
enablePage() {
this._helpContentService.togglePages(this.communityId, [this.subjectsPage._id], true, this.properties.adminToolsAPIURL).subscribe(() => {
this.subjectsPage.isEnabled = true;
UIkit.notification('Curators Page has been <b>enabled successfully</b>', {
status: 'success',
timeout: 6000,
pos: 'bottom-right'
});
},error => {
this.subjectsPage.isEnabled = false;
UIkit.notification('An error occured', {
status: 'danger',
timeout: 6000,
pos: 'bottom-right'
});
});
}
private curatorsEnabledOpen() {
this.enablePageModal.okButtonLeft = false;
this.enablePageModal.alertTitle = 'Enable Subjects Page';
this.enablePageModal.okButtonText = 'Yes';
this.enablePageModal.cancelButtonText = 'No';
this.enablePageModal.open();
}*/
} }

View File

@ -13,14 +13,18 @@ import {AlertModalModule} from '../../../openaireLibrary/utils/modal/alertModal.
import {NoLoadPaging} from '../../../openaireLibrary/searchPages/searchUtils/no-load-paging.module'; import {NoLoadPaging} from '../../../openaireLibrary/searchPages/searchUtils/no-load-paging.module';
import {LoadingModule} from '../../../openaireLibrary/utils/loading/loading.module'; import {LoadingModule} from '../../../openaireLibrary/utils/loading/loading.module';
import {InputModule} from '../../../openaireLibrary/sharedComponents/input/input.module'; import {InputModule} from '../../../openaireLibrary/sharedComponents/input/input.module';
import {CommunityInfoModule} from '../../community-info/community-info.module';
import {SearchInputModule} from '../../../openaireLibrary/sharedComponents/search-input/search-input.module'; import {SearchInputModule} from '../../../openaireLibrary/sharedComponents/search-input/search-input.module';
import {FullScreenModalModule} from 'src/app/openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.module'; import {FullScreenModalModule} from 'src/app/openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.module';
import {PagingModule} from "../../../openaireLibrary/utils/paging.module"; import {PagingModule} from "../../../openaireLibrary/utils/paging.module";
import {SdgSelectionModule} from '../../../openaireLibrary/sdg/sdg-selection/sdg-selection.module';
import {FosSelectionModule} from '../../../openaireLibrary/fos/fos-selection/fos-selection.module';
import {ValidateEnabledPageModule} from "../../../utils/validateEnabledPage.module";
@NgModule({ @NgModule({
imports: [ imports: [
SubjectsEditFormRoutingModule, CommonModule, FormsModule, RouterModule, PageContentModule, IconsModule, AlertModalModule, NoLoadPaging, LoadingModule, InputModule, CommunityInfoModule, SearchInputModule, FullScreenModalModule, PagingModule SubjectsEditFormRoutingModule, CommonModule, FormsModule, RouterModule,
PageContentModule, IconsModule, AlertModalModule, NoLoadPaging, LoadingModule, InputModule,
SearchInputModule, FullScreenModalModule, PagingModule, SdgSelectionModule, FosSelectionModule, ValidateEnabledPageModule
], ],
declarations: [ declarations: [
SubjectsEditFormComponent SubjectsEditFormComponent

View File

@ -1,11 +1,5 @@
<div page-content> <div page-content>
<div header> <div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Notification Settings</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<users-tabs tab="notifications"></users-tabs> <users-tabs tab="notifications"></users-tabs>
</div> </div>
<div actions> <div actions>

View File

@ -25,18 +25,10 @@ declare var UIkit;
template: ` template: `
<div page-content> <div page-content>
<div header> <div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Personal Info &
Affiliations
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<users-tabs tab="personal"></users-tabs> <users-tabs tab="personal"></users-tabs>
</div> </div>
<div actions> <div actions>
<div class="uk-container uk-section-xsmall"> <div class="uk-container uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-middle uk-flex-center uk-flex-right@m"> <div class="uk-flex uk-flex-middle uk-flex-center uk-flex-right@m">
<button class="uk-button uk-button-secondary" [class.uk-disabled]="!hasChanged || loading" <button class="uk-button uk-button-secondary" [class.uk-disabled]="!hasChanged || loading"
[disabled]="!hasChanged || loading" [disabled]="!hasChanged || loading"

View File

@ -12,13 +12,8 @@ import {CommunityInfo} from "../../../openaireLibrary/connect/community/communit
selector: 'users-managers', selector: 'users-managers',
template: ` template: `
<role-users [id]="community.communityId" [type]="community.type" [name]="community.shortTitle" [inviteDisableMessage]="inviteDisableMessage" <role-users [id]="community.communityId" [type]="community.type" [name]="community.shortTitle" [inviteDisableMessage]="inviteDisableMessage"
[link]="link" [role]="'manager'" [message]="message" [emailComposer]="emailComposer"> [link]="link" [role]="'manager'" [deleteAuthorizationLevel]="'manager'"
<div class="uk-flex uk-flex-middle uk-margin-medium-top info"> [message]="message" [emailComposer]="emailComposer">
<div>
<div class="uk-margin-remove uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Users</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<users-tabs tab="manager"></users-tabs> <users-tabs tab="manager"></users-tabs>
</role-users> </role-users>
` `
@ -30,12 +25,11 @@ export class UsersManagersComponent implements OnInit {
public message: string; public message: string;
public inviteDisableMessage: string; public inviteDisableMessage: string;
public emailComposer: Function = (name, recipient, role):Email => { public emailComposer: Function = (name, recipient, role):Email => {
return Composer.composeEmailForCommunityDashboard(name, recipient); return Composer.composeEmailForCommunityDashboard(name, role, recipient);
} }
private subscriptions: any[] = []; private subscriptions: any[] = [];
constructor(private communityService: CommunityService, constructor(private communityService: CommunityService,
private route: ActivatedRoute,
private title: Title) { private title: Title) {
} }
@ -48,7 +42,7 @@ export class UsersManagersComponent implements OnInit {
this.link = this.getURL(this.community.communityId); this.link = this.getURL(this.community.communityId);
this.message = 'A manager has the right to access the administration part of Research Community Dashboard, ' + this.message = 'A manager has the right to access the administration part of Research Community Dashboard, ' +
'where he is able to customize and manage the content, invite other users as managers or members.'; 'where he is able to customize and manage the content, invite other users as managers or members.';
if(community.status === "hidden") { if(community.isPrivate()) {
this.inviteDisableMessage = "Community's status is Hidden and invitation to manage the Research community dashboard is disabled. Update the community status to enable invitations." this.inviteDisableMessage = "Community's status is Hidden and invitation to manage the Research community dashboard is disabled. Update the community status to enable invitations."
} }
this.loading = false; this.loading = false;

View File

@ -4,30 +4,36 @@ import {ActivatedRoute} from "@angular/router";
import {CommunityService} from "../../../openaireLibrary/connect/community/community.service"; import {CommunityService} from "../../../openaireLibrary/connect/community/community.service";
import {Subscriber} from "rxjs"; import {Subscriber} from "rxjs";
import {CommunityInfo} from "../../../openaireLibrary/connect/community/communityInfo"; import {CommunityInfo} from "../../../openaireLibrary/connect/community/communityInfo";
import {Email} from "../../../openaireLibrary/utils/email/email";
import {Composer} from "../../../openaireLibrary/utils/email/composer";
import {properties} from "../../../../environments/environment";
@Component({ @Component({
selector: 'users-subscribers', selector: 'users-subscribers',
template: ` template: `
<subscribers [id]="community.communityId" [type]="'community'" [name]="community.shortTitle" <subscribers *ngIf="community.isOpen()" [id]="community.communityId" [type]="'community'" [name]="community.shortTitle"
[inviteDisableMessage]="inviteDisableMessage"> [inviteDisableMessage]="inviteDisableMessage">
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Users</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<users-tabs tab="member"></users-tabs> <users-tabs tab="member"></users-tabs>
</subscribers> </subscribers>
<role-users *ngIf="!community.isOpen()" [id]="community.communityId" [type]="community.type" [name]="community.shortTitle" [inviteDisableMessage]="inviteDisableMessage"
[link]="link" [role]="'member'"
[message]="message" [emailComposer]="emailComposer">
<users-tabs tab="member"></users-tabs>
</role-users>
` `
}) })
export class UsersSubscribersComponent implements OnInit { export class UsersSubscribersComponent implements OnInit {
public community: CommunityInfo; public community: CommunityInfo;
public link: string;
public loading: boolean; public loading: boolean;
public message: string;
public inviteDisableMessage: string; public inviteDisableMessage: string;
public emailComposer: Function = (name, recipient, role):Email => {
return Composer.composeEmailForCommunityDashboard(name, role, recipient);
}
private subscriptions: any[] = []; private subscriptions: any[] = [];
constructor(private communityService: CommunityService, constructor(private communityService: CommunityService,
private route: ActivatedRoute,
private title: Title) { private title: Title) {
} }
@ -36,9 +42,12 @@ export class UsersSubscribersComponent implements OnInit {
this.subscriptions.push(this.communityService.getCommunityAsObservable().subscribe(community => { this.subscriptions.push(this.communityService.getCommunityAsObservable().subscribe(community => {
if(community) { if(community) {
this.community = community; this.community = community;
this.title.setTitle(this.community.shortTitle.toUpperCase() + " | Subscribers"); this.title.setTitle(this.community.shortTitle.toUpperCase() + " | Members");
if(community.status !== "all") { this.link = this.getURL(this.community.communityId);
this.inviteDisableMessage = "Community's status is " + (community.status === 'manager'?'Visible to managers':'Hidden') + " and invitation to join the Research community dashboard is disabled. Update the community status to enable invitations." this.message = 'A member can access the community dashboard and link research results with projects, ' +
'communities and other research projects.';
if(!community.isPublic()) {
this.inviteDisableMessage = "Community's status is " + (community.isRestricted()?'Visible to managers':'Hidden') + " and invitation to join the Research community dashboard is disabled. Update the community status to enable invitations."
} }
this.loading = false; this.loading = false;
} }
@ -52,4 +61,8 @@ export class UsersSubscribersComponent implements OnInit {
} }
}); });
} }
private getURL(id: string): string {
return 'https://' + (properties.environment !== "production"?'beta.':'') + id + ".openaire.eu?verify=";
}
} }

View File

@ -5,11 +5,12 @@ import {LoadingModule} from "../../../openaireLibrary/utils/loading/loading.modu
import {RouterModule} from "@angular/router"; import {RouterModule} from "@angular/router";
import {SubscribersModule} from "../../../openaireLibrary/dashboard/users/subscribers/subscribers.module"; import {SubscribersModule} from "../../../openaireLibrary/dashboard/users/subscribers/subscribers.module";
import {UsersTabsModule} from '../users-tabs.module'; import {UsersTabsModule} from '../users-tabs.module';
import {RoleUsersModule} from "../../../openaireLibrary/dashboard/users/role-users/role-users.module";
@NgModule({ @NgModule({
imports: [CommonModule, LoadingModule, RouterModule.forChild([ imports: [CommonModule, LoadingModule, RouterModule.forChild([
{path: '', component: UsersSubscribersComponent} {path: '', component: UsersSubscribersComponent}
]), SubscribersModule, UsersTabsModule], ]), SubscribersModule, UsersTabsModule, RoleUsersModule],
declarations: [UsersSubscribersComponent], declarations: [UsersSubscribersComponent],
exports: [UsersSubscribersComponent] exports: [UsersSubscribersComponent]
}) })

View File

@ -22,9 +22,27 @@
<div class="uk-card-body"> <div class="uk-card-body">
<preview-zenodo-community [item]="item" [master]="masterCommunity && item.id==masterCommunity.id"></preview-zenodo-community> <preview-zenodo-community [item]="item" [master]="masterCommunity && item.id==masterCommunity.id"></preview-zenodo-community>
</div> </div>
<div *ngIf="!masterCommunity || item.id!==masterCommunity.id" class="uk-card-footer uk-padding-remove-vertical"> <div class="uk-card-footer uk-padding-remove-vertical">
<div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid> <div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid>
<div *ngIf="!inThelist(item, selectedCommunities) && !(masterCommunity && item.id==masterCommunity.id)"> <div *ngIf="inThelist(item, selectedCommunities) && !(masterCommunity && item.id==masterCommunity.id)">
<div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="removeCommunity(item)"
class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="remove" [flex]="true"></icon>
<span class="uk-margin-small-left">Remove</span>
</a>
</div>
</div>
<div *ngIf="(masterCommunity && item.id==masterCommunity.id)">
<div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="removeCommunity(item, true)"
class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="remove" [flex]="true"></icon>
<span class="uk-margin-small-left">Remove as Main</span>
</a>
</div>
</div>
<div *ngIf="!inThelist(item, selectedCommunities)">
<div class="uk-padding-small uk-padding-remove-horizontal"> <div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="addCommunity(item)" class="uk-button uk-button-link uk-flex uk-flex-middle"> <a (click)="addCommunity(item)" class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="add" [flex]="true"></icon> <icon name="add" [flex]="true"></icon>
@ -34,15 +52,17 @@
</a> </a>
</div> </div>
</div> </div>
<div *ngIf="inThelist(item, selectedCommunities)"> <div *ngIf="!(masterCommunity)">
<div class="uk-padding-small uk-padding-remove-horizontal"> <div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="removeCommunity(item)" <a (click)="addCommunity(item,true)" class="uk-button uk-button-link uk-flex uk-flex-middle">
class="uk-button uk-button-link uk-flex uk-flex-middle"> <icon name="add" [flex]="true"></icon>
<icon name="remove" [flex]="true"></icon> <span class="uk-margin-small-left">
<span class="uk-margin-small-left">Remove</span> Add as Main
</span>
</a> </a>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>

View File

@ -11,6 +11,8 @@ import {Subject, Subscription} from 'rxjs';
import {debounceTime, distinctUntilChanged} from 'rxjs/operators'; import {debounceTime, distinctUntilChanged} from 'rxjs/operators';
import {CommunityInfo} from "../../openaireLibrary/connect/community/communityInfo"; import {CommunityInfo} from "../../openaireLibrary/connect/community/communityInfo";
import {HelperFunctions} from "../../openaireLibrary/utils/HelperFunctions.class"; import {HelperFunctions} from "../../openaireLibrary/utils/HelperFunctions.class";
import {CommunityService} from "../../openaireLibrary/connect/community/community.service";
import {NotificationHandler} from "../../openaireLibrary/utils/notification-handler";
declare var UIkit; declare var UIkit;
@ -39,7 +41,8 @@ export class AddZenodoCommunitiesComponent implements OnInit {
private _router: Router, private _router: Router,
public _fb: UntypedFormBuilder, public _fb: UntypedFormBuilder,
private _zenodoCommunitieService: ZenodoCommunitiesService, private _zenodoCommunitieService: ZenodoCommunitiesService,
private _manageZenodoCommunitiesService: ManageZenodoCommunitiesService) { private _manageZenodoCommunitiesService: ManageZenodoCommunitiesService,
private _communityService: CommunityService) {
this.errorCodes = new ErrorCodes(); this.errorCodes = new ErrorCodes();
this.zenodoCommunitySearchUtils.status = this.errorCodes.LOADING; this.zenodoCommunitySearchUtils.status = this.errorCodes.LOADING;
@ -130,18 +133,26 @@ export class AddZenodoCommunitiesComponent implements OnInit {
} }
public addCommunity(community) { public addCommunity(community, master:boolean = false) {
this.subscriptions.push(this._manageZenodoCommunitiesService.addZCommunity(this.properties, this.community.communityId, community.id).subscribe( if(master && this.getPosition(community) == -1 ){
this.addCommunity(community, false);
}
this.subscriptions.push(this._manageZenodoCommunitiesService.addZenodoCommunity(this.properties, this.community.communityId, community.id, master).subscribe(
data => { data => {
community["openaireId"] = data.id; // this._communityService.setCommunity(this._communityService.parseCommunity(data));
if(master){
this.masterCommunity = community;
}else {
this.selectedCommunities.push(community); this.selectedCommunities.push(community);
UIkit.notification('Community successfully added!', { }
UIkit.notification('Community successfully added' + (master?" as master!":"!"), {
status: 'success', status: 'success',
timeout: 6000, timeout: 6000,
pos: 'bottom-right' pos: 'bottom-right'
}); });
this.zenodoCommunitiesChanged.emit({ this.zenodoCommunitiesChanged.emit({
value: this.selectedCommunities, communities: this.selectedCommunities,
main:this.masterCommunity
}); });
}, },
err => { err => {
@ -151,10 +162,19 @@ export class AddZenodoCommunitiesComponent implements OnInit {
)); ));
} }
public removeCommunity(comm) { public removeCommunity(comm, master:boolean = false) {
var openaireId = this.getOpenaireId(comm); var openaireId = this.getOpenaireId(comm);
this.subscriptions.push(this._manageZenodoCommunitiesService.removeZCommunity(this.properties, this.community.communityId, openaireId,).subscribe( this.subscriptions.push(this._manageZenodoCommunitiesService.removeZenodoCommunity(this.properties, this.community.communityId, openaireId, master).subscribe(
data => { data => {
this.afterRemoveActions(comm, master);
},
err => {
this.handleError('An error has been occurred. Try again later!');
console.log(err.status);
}
));
}
getPosition(comm){
var pos = -1; var pos = -1;
for (var i = 0; i < this.selectedCommunities.length; i++) { for (var i = 0; i < this.selectedCommunities.length; i++) {
if (this.selectedCommunities[i].id == comm.id) { if (this.selectedCommunities[i].id == comm.id) {
@ -162,26 +182,24 @@ export class AddZenodoCommunitiesComponent implements OnInit {
break; break;
} }
} }
return pos;
}
afterRemoveActions(comm, master:boolean = false){
if(master){
this.masterCommunity = null;
NotificationHandler.rise('Community has been <b>removed from master</b>!')
}else {
var pos = this.getPosition(comm)
if (pos != -1) { if (pos != -1) {
this.selectedCommunities.splice(pos, 1); this.selectedCommunities.splice(pos, 1);
} }
}
UIkit.notification('Community successfully removed!', { NotificationHandler.rise('Community has been <b>removed</b>!')
status: 'success',
timeout: 6000,
pos: 'bottom-right'
});
this.zenodoCommunitiesChanged.emit({ this.zenodoCommunitiesChanged.emit({
value: this.selectedCommunities, communities: this.selectedCommunities,
main: this.masterCommunity
}); });
},
err => {
this.handleError('An error has been occurred. Try again later!');
console.log(err.status);
} }
));
}
public inThelist(community: any, list): any { public inThelist(community: any, list): any {
for (let com of list) { for (let com of list) {
if (com.id == community.id) { if (com.id == community.id) {
@ -194,7 +212,7 @@ export class AddZenodoCommunitiesComponent implements OnInit {
public getOpenaireId(community: any): string { public getOpenaireId(community: any): string {
for (let com of this.selectedCommunities) { for (let com of this.selectedCommunities) {
if (com.id == community.id) { if (com.id == community.id) {
return com.openaireId; return com.id;
} }
} }
return null; return null;

View File

@ -1,158 +0,0 @@
import {
ChangeDetectorRef,
Component,
EventEmitter,
Input,
OnDestroy,
OnInit,
Output,
ViewChild,
ViewEncapsulation
} from '@angular/core';
import {UntypedFormBuilder, UntypedFormControl} from '@angular/forms';
import {ActivatedRoute, Router} from '@angular/router';
import {EnvProperties} from '../../openaireLibrary/utils/properties/env-properties';
import {properties} from "../../../environments/environment";
import {ErrorCodes} from '../../openaireLibrary/utils/properties/errorCodes';
import {SearchUtilsClass} from '../../openaireLibrary/searchPages/searchUtils/searchUtils.class';
import {ManageZenodoCommunitiesService} from '../../services/manageZenodoCommunities.service';
import {SearchInputComponent} from '../../openaireLibrary/sharedComponents/search-input/search-input.component';
import {Subscription} from 'rxjs';
import {CommunityInfo} from "../../openaireLibrary/connect/community/communityInfo";
import {HelperFunctions} from "../../openaireLibrary/utils/HelperFunctions.class";
import {NotificationHandler} from "../../openaireLibrary/utils/notification-handler";
@Component({
selector: 'manage-zenodo-communities',
templateUrl: './manage-zenodo-communities.component.html'
})
export class ManageZenodoCommunitiesComponent implements OnInit, OnDestroy {
properties: EnvProperties = properties;
@Input() community: CommunityInfo = null;
@Input() public loading: boolean = true;
@Input() searchUtils: SearchUtilsClass = null;
errorCodes: ErrorCodes;
public rowsOnPage = 10;
@Input() masterCommunity = null;
@Input() selectedCommunities = [];
previewCommunities = [];
@ViewChild('AlertModalDeleteCommunity') alertModalDeleteCommunity;
selectedToDelete = null;
@Output() addZenodoCommunity: EventEmitter<any> = new EventEmitter();
@Output() zenodoCommunitiesChanged = new EventEmitter();
page = 1;
size = 10;
@ViewChild('searchInputComponent') searchInputComponent: SearchInputComponent;
public filterForm: UntypedFormControl;
private subscriptions: any[] = [];
constructor(private route: ActivatedRoute,
private _router: Router,
public _fb: UntypedFormBuilder,
private cdr: ChangeDetectorRef,
private _manageZenodoCommunitiesService: ManageZenodoCommunitiesService) {
this.errorCodes = new ErrorCodes();
}
ngOnInit() {
this.init();
}
ngOnDestroy() {
this.subscriptions.forEach(subscription => {
if (subscription instanceof Subscription) {
subscription.unsubscribe();
}
});
}
private init() {
this.filterForm = this._fb.control('');
this.filterPreviewCommunities("");
this.subscriptions.push(this.filterForm.valueChanges.subscribe(value => {
this.page = 1;
this.filterPreviewCommunities(value);
}));
this.searchUtils.keyword = "";
this.searchUtils.totalResults = this.selectedCommunities.length;
}
public filterPreviewCommunities(value: string) {
this.previewCommunities = this.selectedCommunities.filter(community => {
return !value || community.title.toLowerCase().indexOf(value.toLowerCase()) != -1
});
if (this.previewCommunities.slice((this.page - 1) * this.rowsOnPage, this.page * this.rowsOnPage).length == 0) {
this.page = 1;
}
this.cdr.detectChanges();
}
public confirmedDeleteCommunity(data: any) {
this.subscriptions.push(this._manageZenodoCommunitiesService.removeZCommunity(this.properties, this.community.communityId, this.selectedToDelete.openaireId).subscribe(
data => {
var pos = -1;
for (var i = 0; i < this.selectedCommunities.length; i++) {
if (this.selectedCommunities[i].id == this.selectedToDelete.id) {
pos = i;
break;
}
}
if (pos != -1) {
this.selectedCommunities.splice(pos, 1);
this.searchUtils.totalResults = this.selectedCommunities.length;
}
this.searchUtils.totalResults = this.selectedCommunities.length;
this.filterPreviewCommunities(this.filterForm.value);
NotificationHandler.rise('Community has been <b>successfully removed</b>!')
this.zenodoCommunitiesChanged.emit({
value: this.selectedCommunities,
});
},
err => {
this.handleError('An error has been occurred. Try again later!');
console.log(err.status);
}
));
}
public removeCommunity(comm) {
this.selectedToDelete = comm;
this.alertModalDeleteCommunity.cancelButton = true;
this.alertModalDeleteCommunity.okButton = true;
this.alertModalDeleteCommunity.alertTitle = "Remove zenodo community";
let title = "";
if (comm.title) {
title = comm.title;
}
this.alertModalDeleteCommunity.message = "Zenodo community";
if (title) {
this.alertModalDeleteCommunity.message += " '" + title + "' ";
}
this.alertModalDeleteCommunity.message += "will be removed from your community. Are you sure?";
this.alertModalDeleteCommunity.okButtonText = "Yes";
this.alertModalDeleteCommunity.open();
}
totalPages(): number {
let totalPages: any = this.searchUtils.totalResults / (this.rowsOnPage);
if (!(Number.isInteger(totalPages))) {
totalPages = (parseInt(totalPages, 10) + 1);
}
return totalPages;
}
public updatePage($event) {
HelperFunctions.scroll();
this.page = $event.value;
}
addNew() {
this.addZenodoCommunity.emit();
}
handleError(message: string) {
NotificationHandler.rise(message, 'danger');
}
}

View File

@ -8,7 +8,7 @@ import {Component, Input} from '@angular/core';
<a target="_blank" [href]="item.link"> <a target="_blank" [href]="item.link">
<img *ngIf="item.logoUrl" <img *ngIf="item.logoUrl"
src="{{item.logoUrl}}" width="80" height="80" src="{{item.logoUrl}}" width="80" height="80"
alt="{{item.title}}"> alt="">
</a> </a>
</div> </div>
<div class="uk-width-expand"> <div class="uk-width-expand">

View File

@ -1,22 +1,12 @@
<div page-content> <div page-content *ngIf="community && searchUtils">
<div header>
<div class="uk-flex uk-flex-middle uk-margin-medium-top info">
<div>
<div class="uk-text-background uk-text-bold uk-text-small">Admin Dashboard - Manage Zenodo Communities
</div>
<h1 class="uk-h6 uk-margin-remove">{{community.shortTitle}}</h1>
</div>
</div>
<community-info tab="zenodo-communities"></community-info>
</div>
<div actions> <div actions>
<div class="uk-section-xsmall"> <div class="uk-section-xsmall uk-margin-top">
<div class="uk-flex uk-flex-right@m uk-flex-center uk-flex-middle uk-grid" uk-grid> <div class="uk-flex uk-flex-right@m uk-flex-center uk-flex-middle uk-grid" uk-grid>
<div search-input [expandable]="true" [searchControl]="filterForm" searchInputClass="outer" <div search-input [expandable]="true" [searchControl]="filterForm" searchInputClass="outer"
placeholder="Search Zenodo Community" [disabled]="searchUtils.status === errorCodes.LOADING" placeholder="Search Zenodo Community" [disabled]="searchUtils.status === errorCodes.LOADING"
class="uk-width-1-3@xl uk-width-2-5@l uk-width-1-2@m uk-width-1-1"></div> class="uk-width-1-3@xl uk-width-2-5@l uk-width-1-2@m uk-width-1-1"></div>
<div> <div>
<button class="uk-button uk-button-default uk-flex uk-flex-middle" (click)="addNew()" <button class="uk-button uk-button-default uk-flex uk-flex-middle" (click)="openAddZenodoCommunites()"
uk-tooltip="title:<div class='uk-text-bold'> Search and add more Zenodo Communities</div><div>The research results of a Zenodo community specified here will be automatically linked to your community dashboard.</div>" uk-tooltip="title:<div class='uk-text-bold'> Search and add more Zenodo Communities</div><div>The research results of a Zenodo community specified here will be automatically linked to your community dashboard.</div>"
[disabled]="searchUtils.status === errorCodes.LOADING" [disabled]="searchUtils.status === errorCodes.LOADING"
[class.uk-disabled]="searchUtils.status === errorCodes.LOADING"> [class.uk-disabled]="searchUtils.status === errorCodes.LOADING">
@ -29,6 +19,7 @@
</div> </div>
<div inner> <div inner>
<div class="uk-section uk-section-small uk-position-relative" style="min-height: 60vh"> <div class="uk-section uk-section-small uk-position-relative" style="min-height: 60vh">
<validate-page-enabled pageRoute="/participate/deposit/zenodo"></validate-page-enabled>
<div *ngIf="searchUtils.status == errorCodes.LOADING" class="uk-position-center"> <div *ngIf="searchUtils.status == errorCodes.LOADING" class="uk-position-center">
<loading></loading> <loading></loading>
</div> </div>
@ -46,16 +37,16 @@
[page]="page" [pageSize]="size" [page]="page" [pageSize]="size"
[totalResults]="previewCommunities.length"> [totalResults]="previewCommunities.length">
</no-load-paging> </no-load-paging>
<!-- <ul class="uk-margin-medium-top uk-margin-bottom uk-list uk-list-xlarge">--> <!-- <ul class="uk-margin-medium-top uk-margin-bottom uk-list uk-list-xlarge">-->
<div class="uk-grid uk-grid-large uk-child-width-1-1 uk-margin-medium-top uk-margin-bottom" uk-grid> <div class="uk-grid uk-grid-large uk-child-width-1-1 uk-margin-medium-top uk-margin-bottom" uk-grid>
<div *ngFor="let item of previewCommunities.slice((this.page - 1)*this.size, this.page*this.size); let i=index"> <div *ngFor="let item of previewCommunities.slice((this.page - 1)*this.size, this.page*this.size); let i=index">
<div class="uk-card uk-card-default"> <div class="uk-card uk-card-default">
<div class="uk-card-body"> <div class="uk-card-body">
<preview-zenodo-community [item]="item" [master]="masterCommunity && item.id==masterCommunity.id"></preview-zenodo-community> <preview-zenodo-community [item]="item" [master]="masterCommunity && item.id==masterCommunity.id"></preview-zenodo-community>
</div> </div>
<div *ngIf="!masterCommunity || item.id!==masterCommunity.id" class="uk-card-footer uk-padding-remove-vertical"> <div class="uk-card-footer uk-padding-remove-vertical">
<div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid> <div class="uk-grid uk-grid-small uk-flex-nowrap uk-grid-divider uk-flex-right" uk-grid>
<div> <div *ngIf="item.id!==masterZenodoCommunityId" >
<div class="uk-padding-small uk-padding-remove-horizontal"> <div class="uk-padding-small uk-padding-remove-horizontal">
<button class="uk-button uk-button-link uk-flex uk-flex-middle" <button class="uk-button uk-button-link uk-flex uk-flex-middle"
(click)="removeCommunity(item)"> (click)="removeCommunity(item)">
@ -64,12 +55,31 @@
</button> </button>
</div> </div>
</div> </div>
<div *ngIf="(item.id==masterZenodoCommunityId)">
<div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="removeFromMasterCommunity(item)"
class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="remove" [flex]="true"></icon>
<span class="uk-margin-small-left">Remove as Main</span>
</a>
</div>
</div>
<div *ngIf="(!masterZenodoCommunityId)">
<div class="uk-padding-small uk-padding-remove-horizontal">
<a (click)="addAsMasterCommunity(item)"
class="uk-button uk-button-link uk-flex uk-flex-middle">
<icon name="add" [flex]="true"></icon>
<span class="uk-margin-small-left">Add as Main</span>
</a>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
<!-- </ul>--> </div>
</div>
<!-- </ul>-->
<div class="uk-margin-small-top"> <div class="uk-margin-small-top">
<paging-no-load [currentPage]="page" <paging-no-load [currentPage]="page"
[totalResults]="previewCommunities.length" [size]="size" [totalResults]="previewCommunities.length" [size]="size"
@ -82,3 +92,9 @@
</div> </div>
</div> </div>
<modal-alert #AlertModalDeleteCommunity (alertOutput)="confirmedDeleteCommunity($event)" [overflowBody]="false"></modal-alert> <modal-alert #AlertModalDeleteCommunity (alertOutput)="confirmedDeleteCommunity($event)" [overflowBody]="false"></modal-alert>
<fs-modal #fsModal>
<add-zenodo-communities *ngIf="community" [masterCommunity]=masterCommunity
[selectedCommunities]=selectedCommunities
[community]="community" (zenodoCommunitiesChanged)="zenodoCommunitiesChanged($event)"></add-zenodo-communities>
</fs-modal>

View File

@ -1,10 +1,18 @@
import {Component, ElementRef, Input, OnDestroy, OnInit, ViewChild} from '@angular/core'; import {
ChangeDetectorRef,
Component,
ElementRef,
EventEmitter,
Input,
OnDestroy,
OnInit,
Output,
ViewChild
} from '@angular/core';
import {ActivatedRoute, Router} from '@angular/router'; import {ActivatedRoute, Router} from '@angular/router';
import {EnvProperties} from '../../openaireLibrary/utils/properties/env-properties'; import {EnvProperties} from '../../openaireLibrary/utils/properties/env-properties';
import {ZenodoCommunitiesService} from '../../openaireLibrary/connect/zenodoCommunities/zenodo-communities.service'; import {ZenodoCommunitiesService} from '../../openaireLibrary/connect/zenodoCommunities/zenodo-communities.service';
import {SearchZenodoCommunitiesService} from '../../openaireLibrary/connect/zenodoCommunities/searchZenodoCommunities.service';
import {CommunityService} from '../../openaireLibrary/connect/community/community.service'; import {CommunityService} from '../../openaireLibrary/connect/community/community.service';
import {CommunityInfo} from '../../openaireLibrary/connect/community/communityInfo'; import {CommunityInfo} from '../../openaireLibrary/connect/community/communityInfo';
import {ZenodoCommunityInfo} from '../../openaireLibrary/connect/zenodoCommunities/zenodoCommunityInfo'; import {ZenodoCommunityInfo} from '../../openaireLibrary/connect/zenodoCommunities/zenodoCommunityInfo';
@ -14,95 +22,74 @@ import {Title} from '@angular/platform-browser';
import {properties} from '../../../environments/environment'; import {properties} from '../../../environments/environment';
import {Subscription} from 'rxjs'; import {Subscription} from 'rxjs';
import {FullScreenModalComponent} from '../../openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.component'; import {FullScreenModalComponent} from '../../openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.component';
import {ManageZenodoCommunitiesComponent} from './manage-zenodo-communities.component'; import {NotificationHandler} from "../../openaireLibrary/utils/notification-handler";
import {HelperFunctions} from "../../openaireLibrary/utils/HelperFunctions.class";
import {SearchInputComponent} from "../../openaireLibrary/sharedComponents/search-input/search-input.component";
import {UntypedFormBuilder, UntypedFormControl} from "@angular/forms";
import {ManageZenodoCommunitiesService} from "../../services/manageZenodoCommunities.service";
@Component({ @Component({
selector: 'zenodo-communities', selector: 'zenodo-communities',
template: ` templateUrl: 'zenodo-communities.component.html'
<manage-zenodo-communities #manage *ngIf="community && zenodoSearchUtils"
[loading]="showLoadingInRemove"
[masterCommunity]=masterZenodoCommunity [selectedCommunities]=selectedCommunities
[community]="community" [searchUtils]=zenodoSearchUtils (addZenodoCommunity)="openAddZenodoCommunites()"
(zenodoCommunitiesChanged)="zenodoCommunitiesChanged($event)"></manage-zenodo-communities>
<fs-modal #fsModal>
<add-zenodo-communities [masterCommunity]=masterZenodoCommunity
[selectedCommunities]=selectedCommunities
[community]="community" (zenodoCommunitiesChanged)="zenodoCommunitiesChanged($event)"></add-zenodo-communities>
</fs-modal>
`
}) })
export class ZenodoCommunitiesComponent implements OnInit, OnDestroy { export class ZenodoCommunitiesComponent implements OnInit, OnDestroy {
public community: CommunityInfo = null; public community: CommunityInfo = null;
public toggle = false; public toggle = false;
public pageTitle = 'Manage zenodo communities'; public pageTitle = 'Manage zenodo communities';
masterZenodoCommunityId = null; masterZenodoCommunityId = null;
masterZenodoCommunity = null; masterCommunity = null;
public properties: EnvProperties = null; public properties: EnvProperties = null;
selectedCommunityIds = null; selectedCommunityIds = null;
selectedCommunities = []; selectedCommunities = null;
zenodocommunitiesloadedCount = 0; zenodocommunitiesloadedCount = 0;
zenodoSearchUtils: SearchUtilsClass = new SearchUtilsClass();
public errorCodes: ErrorCodes = new ErrorCodes(); public errorCodes: ErrorCodes = new ErrorCodes();
subscriptions = []; subscriptions = [];
@ViewChild('fsModal', { static: true }) fullscreen: FullScreenModalComponent; @ViewChild('fsModal', {static: true}) fullscreen: FullScreenModalComponent;
@ViewChild(ManageZenodoCommunitiesComponent) manage: ManageZenodoCommunitiesComponent;
public showLoadingInRemove: boolean = true; public showLoadingInRemove: boolean = true;
@Input() public loading: boolean = true;
@Input() searchUtils: SearchUtilsClass = new SearchUtilsClass();
public rowsOnPage = 10;
previewCommunities = [];
@ViewChild('AlertModalDeleteCommunity') alertModalDeleteCommunity;
selectedToDelete = null;
@Output() addZenodoCommunity: EventEmitter<any> = new EventEmitter();
page = 1;
size = 10;
@ViewChild('searchInputComponent') searchInputComponent: SearchInputComponent;
public filterForm: UntypedFormControl;
deleteMaster = false;
constructor(private element: ElementRef, private route: ActivatedRoute, private _router: Router, constructor(private element: ElementRef, private route: ActivatedRoute, private _router: Router,
private _zenodoCommunitieService: ZenodoCommunitiesService, private title: Title, private _zenodoCommunitieService: ZenodoCommunitiesService, private title: Title,
private _communityService: CommunityService, private _communityService: CommunityService,
private _searchZenodoCommunitiesService: SearchZenodoCommunitiesService) { public _fb: UntypedFormBuilder,
private cdr: ChangeDetectorRef,
private _manageZenodoCommunitiesService: ManageZenodoCommunitiesService) {
} }
ngOnInit() { ngOnInit() {
this.zenodoSearchUtils.status = this.errorCodes.LOADING; this.searchUtils.status = this.errorCodes.LOADING;
this.properties = properties; this.properties = properties;
this.subscriptions.push(this.route.params.subscribe(params => {
this.subscriptions.push(this._communityService.getCommunityAsObservable().subscribe( //use this method to ensure that get the lattest version of the community and the updated information for the list of zenodo communities
this.subscriptions.push(this._communityService.getCommunity(params['community'],true).subscribe(
community => { community => {
this.community = community; this.community = community;
this.title.setTitle(this.community.shortTitle.toUpperCase() + ' | Zenodo Communities'); this.title.setTitle(this.community.shortTitle.toUpperCase() + ' | Zenodo Communities');
this.masterZenodoCommunityId = this.community.zenodoCommunity; this.masterZenodoCommunityId = this.community.zenodoCommunity;
if (this.masterZenodoCommunityId) { this.selectedCommunities = [];
this.subscriptions.push(this._zenodoCommunitieService.getZenodoCommunityById(this.properties, this.searchUtils.status = this.errorCodes.LOADING;
this.properties.zenodoCommunities + this.masterZenodoCommunityId, this.selectedCommunityIds = this.community.otherZenodoCommunities;
null).subscribe( this.searchUtils.totalResults = this.selectedCommunityIds.length;
result => {
this.masterZenodoCommunity = result;
this.selectedCommunities.unshift(this.masterZenodoCommunity);
},
error => {
const emptyCommunity: ZenodoCommunityInfo = new ZenodoCommunityInfo();
emptyCommunity.id = this.masterZenodoCommunityId;
emptyCommunity.title = this.masterZenodoCommunityId;
this.masterZenodoCommunity = emptyCommunity;
}
));
}
this.zenodoSearchUtils.status = this.errorCodes.LOADING;
this.zenodoSearchUtils.status = this.errorCodes.LOADING;
this._searchZenodoCommunitiesService.searchZCommunities(this.properties, this.community.communityId).subscribe(
result => {
this.selectedCommunityIds = result;
this.zenodoSearchUtils.totalResults = this.selectedCommunityIds.length;
if (this.selectedCommunityIds.length === 0) { if (this.selectedCommunityIds.length === 0) {
this.zenodoSearchUtils.status = this.errorCodes.NONE; this.searchUtils.status = this.errorCodes.NONE;
} }
for (let i = 0; i < this.selectedCommunityIds.length; i++) { for (let i = 0; i < this.selectedCommunityIds.length; i++) {
this.getZenodoCommunityById( this.getZenodoCommunityById(this.selectedCommunityIds[i]);
this.selectedCommunityIds[i]['zenodoid'],
this.selectedCommunityIds[i]['id']);
} }
this.init();
},
error => {
console.log('list of zenodo communities couldn\'t be loaded');
this.zenodoSearchUtils.status = this.errorCodes.DONE;
}
);
}) })
); );
}));
this.fullscreen.title = "Search and Add Zenodo Communities"; this.fullscreen.title = "Search and Add Zenodo Communities";
this.fullscreen.okButtonText = "Done"; this.fullscreen.okButtonText = "Done";
this.fullscreen.okButton = true; this.fullscreen.okButton = true;
@ -116,27 +103,31 @@ export class ZenodoCommunitiesComponent implements OnInit, OnDestroy {
}); });
} }
getZenodoCommunityById(zenodoid, openaireId) { getZenodoCommunityById(zenodoid) {
this.subscriptions.push(this._zenodoCommunitieService.getZenodoCommunityById(this.properties, this.subscriptions.push(this._zenodoCommunitieService.getZenodoCommunityById(this.properties,
this.properties.zenodoCommunities + zenodoid, openaireId).subscribe( zenodoid).subscribe(
result => { result => {
if(zenodoid == this.masterZenodoCommunityId){
this.masterCommunity = result;
result.master = true;
this.selectedCommunities.unshift(result);
}else {
this.selectedCommunities.push(result); this.selectedCommunities.push(result);
}
this.zenodocommunitiesloadedCount++; this.zenodocommunitiesloadedCount++;
if (this.zenodocommunitiesloadedCount >= this.selectedCommunityIds.length) { if (this.zenodocommunitiesloadedCount >= this.selectedCommunityIds.length) {
this.zenodoSearchUtils.status = this.errorCodes.DONE; this.searchUtils.status = this.errorCodes.DONE;
} }
}, },
error => { error => {
const emptyCommunity: ZenodoCommunityInfo = new ZenodoCommunityInfo(); const emptyCommunity: ZenodoCommunityInfo = new ZenodoCommunityInfo();
emptyCommunity.id = zenodoid; emptyCommunity.id = zenodoid;
emptyCommunity.openaireId = openaireId;
emptyCommunity.title = zenodoid; emptyCommunity.title = zenodoid;
this.selectedCommunities.push(emptyCommunity); this.selectedCommunities.push(emptyCommunity);
this.zenodocommunitiesloadedCount++; this.zenodocommunitiesloadedCount++;
if (this.zenodocommunitiesloadedCount >= this.selectedCommunityIds.length) { if (this.zenodocommunitiesloadedCount >= this.selectedCommunityIds.length) {
this.zenodoSearchUtils.status = this.errorCodes.DONE; this.searchUtils.status = this.errorCodes.DONE;
} }
console.log('Zenodo community\'' + zenodoid + '\' couldn\'t be loaded'); console.log('Zenodo community\'' + zenodoid + '\' couldn\'t be loaded');
} }
@ -153,11 +144,150 @@ export class ZenodoCommunitiesComponent implements OnInit, OnDestroy {
} }
public zenodoCommunitiesChanged($event) { public zenodoCommunitiesChanged($event) {
this.selectedCommunities = $event.value; this.selectedCommunities = $event.communities;
this.masterCommunity = $event.main;
if(!this.masterZenodoCommunityId && $event.main){
this.selectedCommunityIds.unshift($event.main.id)
this.selectedCommunities.unshift($event.main);
}
this.masterZenodoCommunityId = $event.main?$event.main.id:null;
this.showLoadingInRemove = false; this.showLoadingInRemove = false;
if (this.fullscreen.isOpen) { if (this.fullscreen.isOpen) {
this.manage.filterPreviewCommunities(this.manage.filterForm.value); this.filterPreviewCommunities(this.filterForm.value);
}
this.filterPreviewCommunities(this.searchUtils.keyword);
}
private init() {
this.filterForm = this._fb.control('');
this.filterPreviewCommunities("");
this.subscriptions.push(this.filterForm.valueChanges.subscribe(value => {
this.page = 1;
this.filterPreviewCommunities(value);
}));
this.searchUtils.keyword = "";
this.searchUtils.totalResults = this.selectedCommunities.length;
}
public filterPreviewCommunities(value: string) {
this.previewCommunities = this.selectedCommunities.filter(community => {
return !value || community.title.toLowerCase().indexOf(value.toLowerCase()) != -1
});
if (this.previewCommunities.slice((this.page - 1) * this.rowsOnPage, this.page * this.rowsOnPage).length == 0) {
this.page = 1;
}
this.cdr.detectChanges();
}
public confirmedDeleteCommunity(data: any) {
if(this.deleteMaster){
this.subscriptions.push(this._manageZenodoCommunitiesService.removeZenodoCommunity(this.properties, this.community.communityId, this.selectedToDelete.id, true).subscribe(
data => {
this.afterRemoveActions();
}
));
}else {
this.subscriptions.push(this._manageZenodoCommunitiesService.removeZenodoCommunity(this.properties, this.community.communityId, this.selectedToDelete.id).subscribe(
data => {
this.afterRemoveActions();
}
));
} }
} }
afterRemoveActions(){
if(this.deleteMaster){
this.masterCommunity = null;
this.masterZenodoCommunityId = null
NotificationHandler.rise('Community has been <b>removed from master</b>!')
}else {
var pos = -1;
for (var i = 0; i < this.selectedCommunities.length; i++) {
if (this.selectedCommunities[i].id == this.selectedToDelete.id) {
pos = i;
break;
}
}
if (pos != -1) {
this.selectedCommunities.splice(pos, 1);
this.selectedCommunityIds.splice(pos,1)
this.searchUtils.totalResults = this.selectedCommunities.length;
}
this.searchUtils.totalResults = this.selectedCommunities.length;
this.filterPreviewCommunities(this.filterForm.value);
NotificationHandler.rise('Community has been <b>successfully removed</b>!')
}
}
public removeCommunity(comm) {
this.deleteMaster = false;
this.selectedToDelete = comm;
this.alertModalDeleteCommunity.cancelButton = true;
this.alertModalDeleteCommunity.okButton = true;
this.alertModalDeleteCommunity.alertTitle = "Remove zenodo community";
let title = "";
if (comm.title) {
title = comm.title;
}
this.alertModalDeleteCommunity.message = "Zenodo community";
if (title) {
this.alertModalDeleteCommunity.message += " '" + title + "' ";
}
this.alertModalDeleteCommunity.message += "will be removed from your community. Are you sure?";
this.alertModalDeleteCommunity.okButtonText = "Yes";
this.alertModalDeleteCommunity.open();
}
public removeFromMasterCommunity(comm) {
this.deleteMaster = true;
this.selectedToDelete = comm;
this.alertModalDeleteCommunity.cancelButton = true;
this.alertModalDeleteCommunity.okButton = true;
this.alertModalDeleteCommunity.alertTitle = "Remove master zenodo community";
let title = "";
if (comm.title) {
title = comm.title;
}
this.alertModalDeleteCommunity.message = "Zenodo community";
if (title) {
this.alertModalDeleteCommunity.message += " '" + title + "' ";
}
this.alertModalDeleteCommunity.message += "will be removed as master from your community, but will remain in the list of the related communities. Do you want to proceed?";
this.alertModalDeleteCommunity.okButtonText = "Yes";
this.alertModalDeleteCommunity.open();
}
totalPages(): number {
let totalPages: any = this.searchUtils.totalResults / (this.rowsOnPage);
if (!(Number.isInteger(totalPages))) {
totalPages = (parseInt(totalPages, 10) + 1);
}
return totalPages;
}
public updatePage($event) {
HelperFunctions.scroll();
this.page = $event.value;
}
addNew() {
this.addZenodoCommunity.emit();
}
handleError(message: string) {
NotificationHandler.rise(message, 'danger');
}
public addAsMasterCommunity(community) {
this.subscriptions.push(this._manageZenodoCommunitiesService.addZenodoCommunity(this.properties ,this.community.communityId,community.id, true).subscribe(
data => {
this.masterCommunity = community;
this.masterZenodoCommunityId = community.id
},
err => {
this.handleError('An error has been occurred. Try again later!');
console.log(err.status);
}
));
}
} }

View File

@ -2,15 +2,12 @@ import {NgModule} from '@angular/core';
import {CommonModule} from '@angular/common'; import {CommonModule} from '@angular/common';
import {FormsModule} from '@angular/forms'; import {FormsModule} from '@angular/forms';
import {RouterModule} from '@angular/router'; import {RouterModule} from '@angular/router';
import {ManageZenodoCommunitiesComponent} from './manage-zenodo-communities.component';
import {AddZenodoCommunitiesComponent} from './add-zenodo-communities.component'; import {AddZenodoCommunitiesComponent} from './add-zenodo-communities.component';
import {ZenodoCommunitiesComponent} from './zenodo-communities.component'; import {ZenodoCommunitiesComponent} from './zenodo-communities.component';
import {SearchZenodoCommunitiesServiceModule} from '../../openaireLibrary/connect/zenodoCommunities/searchZenodoCommunitiesService.module';
import {ManageZenodoCommunitiesService} from '../../services/manageZenodoCommunities.service'; import {ManageZenodoCommunitiesService} from '../../services/manageZenodoCommunities.service';
import {ZenodoCommunitiesServiceModule} from '../../openaireLibrary/connect/zenodoCommunities/zenodo-communitiesService.module'; import {ZenodoCommunitiesServiceModule} from '../../openaireLibrary/connect/zenodoCommunities/zenodo-communitiesService.module';
import {AlertModalModule} from '../../openaireLibrary/utils/modal/alertModal.module'; import {AlertModalModule} from '../../openaireLibrary/utils/modal/alertModal.module';
import {ZenodoCommunitiesRoutingModule} from './zenodo-communities-routing.module'; import {ZenodoCommunitiesRoutingModule} from './zenodo-communities-routing.module';
import {CommunityInfoModule} from '../community-info/community-info.module';
import {SearchInputModule} from '../../openaireLibrary/sharedComponents/search-input/search-input.module'; import {SearchInputModule} from '../../openaireLibrary/sharedComponents/search-input/search-input.module';
import {IconsModule} from '../../openaireLibrary/utils/icons/icons.module'; import {IconsModule} from '../../openaireLibrary/utils/icons/icons.module';
import {NoLoadPaging} from '../../openaireLibrary/searchPages/searchUtils/no-load-paging.module'; import {NoLoadPaging} from '../../openaireLibrary/searchPages/searchUtils/no-load-paging.module';
@ -20,14 +17,15 @@ import {PageContentModule} from '../../openaireLibrary/dashboard/sharedComponent
import {FullScreenModalModule} from '../../openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.module'; import {FullScreenModalModule} from '../../openaireLibrary/utils/modal/full-screen-modal/full-screen-modal.module';
import {HTMLToStringPipeModule} from '../../openaireLibrary/utils/pipes/HTMLToStringPipe.module'; import {HTMLToStringPipeModule} from '../../openaireLibrary/utils/pipes/HTMLToStringPipe.module';
import {PagingModule} from "../../openaireLibrary/utils/paging.module"; import {PagingModule} from "../../openaireLibrary/utils/paging.module";
import {ValidateEnabledPageModule} from "../../utils/validateEnabledPage.module";
@NgModule({ @NgModule({
imports: [ imports: [
CommonModule, FormsModule, RouterModule, SearchZenodoCommunitiesServiceModule, ZenodoCommunitiesServiceModule, CommonModule, FormsModule, RouterModule, ZenodoCommunitiesServiceModule,
AlertModalModule, ZenodoCommunitiesRoutingModule, CommunityInfoModule, PageContentModule, SearchInputModule, IconsModule, NoLoadPaging, LoadingModule, FullScreenModalModule, HTMLToStringPipeModule, PagingModule AlertModalModule, ZenodoCommunitiesRoutingModule, PageContentModule, SearchInputModule, IconsModule, NoLoadPaging, LoadingModule, FullScreenModalModule, HTMLToStringPipeModule, PagingModule, ValidateEnabledPageModule
], ],
declarations: [ declarations: [
ManageZenodoCommunitiesComponent, ZenodoCommunitiesComponent, AddZenodoCommunitiesComponent, PreviewZenodoCommunityComponent ZenodoCommunitiesComponent, AddZenodoCommunitiesComponent, PreviewZenodoCommunityComponent
], ],
providers: [ providers: [
ManageZenodoCommunitiesService ManageZenodoCommunitiesService

View File

@ -11,27 +11,29 @@ export class ManageCommunityContentProvidersService {
removeContentProvider(properties: EnvProperties, pid: string, id: string): any { removeContentProvider(properties: EnvProperties, pid: string, id: string): any {
let headers = new HttpHeaders({'Content-Type': 'application/json', 'accept': 'application/json'}); let headers = new HttpHeaders({'Content-Type': 'application/json', 'accept': 'application/json'});
let url = properties.communityAPI + pid + '/contentproviders'; let url = properties.communityAPI + pid + '/datasources?dsId=' +id;
return this.http.request('delete', url, {body: id, headers: headers}); return this.http.request('delete', url, {body: id, headers: headers});
} }
addContentProvider(properties: EnvProperties, pid: string, contentProvider: any): Observable<ContentProvider> { addContentProvider(properties: EnvProperties, pid: string, contentProvider: any, content:boolean, deposit:boolean): Observable<ContentProvider> {
let url = properties.communityAPI + pid + '/contentproviders'; let url = properties.communityAPI + pid + '/datasources';
let communityContentProvider = this.convertSearchContentProviderToCommunityContentProvider(contentProvider, pid); let communityContentProvider = this.convertSearchContentProviderToCommunityContentProvider(contentProvider, pid, content, deposit);
return this.http.post<ContentProvider>(url, communityContentProvider); return this.http.post<ContentProvider>(url, communityContentProvider);
} }
saveContentProvider(properties: EnvProperties, contentProvider: ContentProvider): Observable<ContentProvider> { saveContentProvider(properties: EnvProperties, contentProvider: ContentProvider): Observable<ContentProvider> {
let url = properties.communityAPI + contentProvider.communityId + '/contentproviders'; let url = properties.communityAPI + contentProvider.communityId + '/datasources';
return this.http.post<ContentProvider>(url, contentProvider); return this.http.post<ContentProvider>(url, contentProvider);
} }
convertSearchContentProviderToCommunityContentProvider(contentProvider: any, community: string): ContentProvider { convertSearchContentProviderToCommunityContentProvider(contentProvider: any, community: string, content:boolean, deposit:boolean): ContentProvider {
let communityContentProvider: ContentProvider = new ContentProvider(); let communityContentProvider: ContentProvider = new ContentProvider();
communityContentProvider.communityId = community; communityContentProvider.communityId = community;
communityContentProvider.officialname = contentProvider.title.name; communityContentProvider.officialname = contentProvider.title.name;
communityContentProvider.name = contentProvider.englishname; communityContentProvider.name = contentProvider.englishname;
communityContentProvider.openaireId = contentProvider.id; communityContentProvider.openaireId = contentProvider.id;
communityContentProvider.enabled = content;
communityContentProvider.deposit = deposit;
return communityContentProvider; return communityContentProvider;
} }

View File

@ -12,9 +12,9 @@ export class ManageCommunityProjectsService {
let headers = new HttpHeaders({'Content-Type': 'application/json', 'accept': 'application/json'}); let headers = new HttpHeaders({'Content-Type': 'application/json', 'accept': 'application/json'});
let url = properties.communityAPI+pid+"/projects"; let url = properties.communityAPI+pid+"/projects?projectId="+id;
//return this.http.delete(url, options) //return this.http.delete(url, options)
return this.http.request('delete', url, { body: id, headers: headers}) return this.http.request('delete', url, { headers: headers})
} }
addProject(properties:EnvProperties, pid: string, project: any) { addProject(properties:EnvProperties, pid: string, project: any) {

View File

@ -5,35 +5,25 @@ import{EnvProperties} from '../openaireLibrary/utils/properties/env-properties';
@Injectable() @Injectable()
export class ManageZenodoCommunitiesService { export class ManageZenodoCommunitiesService {
constructor(private http: HttpClient ) {} constructor(private http: HttpClient ) {}
removeZenodoCommunity(properties:EnvProperties, pid: string,zenodoid: string, main:boolean = false) {
removeZCommunity (properties: EnvProperties, pid: string,id: string):any { const options = {
//let headers = new Headers({'Content-Type': 'application/json', 'accept': 'application/json'}); headers: new HttpHeaders({
//let options = new RequestOptions({headers: headers, body: id}); 'Content-Type': 'application/json',
})
let headers = new HttpHeaders({'Content-Type': 'application/json', 'accept': 'application/json'});
let url = properties.communityAPI + pid + "/zenodocommunities";
//return this.http.delete(url, options);
return this.http.request('delete', url, { body: id, headers: headers})
}
addZCommunity(properties:EnvProperties, pid: string,zenodoid: string) {
//let headers = new Headers({'Content-Type': 'application/json'});
//let options = new RequestOptions({headers: headers});
let headers = new HttpHeaders({'Content-Type': 'application/json'});
let url = properties.communityAPI+pid+"/zenodocommunities";
var zCommunity: any = {
"communityId": pid,
"zenodoid": zenodoid
}; };
return this.http.post<any>(url, JSON.stringify(zCommunity), {headers: headers}); let url = properties.communityAPI+pid+"/zenodocommunities?zenodocommunity="+zenodoid + "&main=" + main;
//.map(res => <any> res.json()) return this.http.delete<any>(url, options);
} }
addZenodoCommunity(properties:EnvProperties, pid: string,zenodoid: string, main:boolean = false) {
const options = {
headers: new HttpHeaders({
'Content-Type': 'application/json',
})
};
let url = properties.communityAPI+pid+"/zenodocommunities?zenodocommunity="+zenodoid + "&main=" + main;
return this.http.post<any>(url, options);
}
} }

View File

@ -0,0 +1,93 @@
import {Component, Input, OnDestroy, OnInit, ViewChild} from "@angular/core";
import {EnvProperties} from "../openaireLibrary/utils/properties/env-properties";
import {UntypedFormBuilder} from "@angular/forms";
import {CommunityInfo} from "../openaireLibrary/connect/community/communityInfo";
import {Page} from "../openaireLibrary/utils/entities/adminTool/page";
import {AlertModal} from "../openaireLibrary/utils/modal/alert";
import {ActivatedRoute, Router} from "@angular/router";
import {Title} from "@angular/platform-browser";
import {CommunityService} from "../openaireLibrary/connect/community/community.service";
import {AffiliationService} from "../openaireLibrary/connect/affiliations/affiliation.service";
import {HelpContentService} from "../services/help-content.service";
import {ClearCacheService} from "../openaireLibrary/services/clear-cache.service";
import {Subscription} from "rxjs";
import {HelperFunctions} from "../openaireLibrary/utils/HelperFunctions.class";
import {NotificationHandler} from "../openaireLibrary/utils/notification-handler";
import {properties} from "src/environments/environment";
@Component({
selector: 'validate-page-enabled',
template: `
<div *ngIf="page && !pageEnabled" class="uk-width-1-1 uk-alert uk-alert-warning">
<b>{{page.name}}</b> page is not enabled. Manage pages <a [href]="community.communityId + '/admin-tools/pages'" target="_blank">here</a> or
<a *ngIf="!pageEnabled" class=" uk-margin-right" [class.uk-disabled]="loading" [disabled]="loading"
(click)="enablePage()">enable it now</a>
</div>
`
})
export class ValidateEnabledPageComponent implements OnInit, OnDestroy {
@Input() pageRoute:string;
public properties: EnvProperties = properties;
public community: CommunityInfo;
public page: Page;
loading;
private subs: any[] = [];
@ViewChild('affiliationModal') affiliationModal: AlertModal;
@ViewChild('removeAffiliationModal') removeAffiliationModal: AlertModal;
constructor(private route: ActivatedRoute,
private router: Router,
private title: Title,
private fb: UntypedFormBuilder,
private communityService: CommunityService,
private helpContentService: HelpContentService,
private _clearCacheService: ClearCacheService) {
}
ngOnInit() {
this.subs.push(this.communityService.getCommunityAsObservable().subscribe( community => {
this.community = community;
this.getPageStatus();
}));
}
ngOnDestroy() {
this.subs.forEach(sub => {
if (sub instanceof Subscription) {
sub.unsubscribe();
}
})
}
public get pageEnabled(): boolean {
return !this.page || this.page.isEnabled;
}
public updatePage(event) {
HelperFunctions.scroll();
this.page = event.value;
}
private getPageStatus() {
this.helpContentService.getCommunityPagesByRoute(this.community.communityId, this.pageRoute, this.properties.adminToolsAPIURL).subscribe((page) => {
this.page = page;
})
}
enablePage() {
this.loading = true;
this.helpContentService.togglePages(this.community.communityId, [this.page._id], true, this.properties.adminToolsAPIURL).subscribe(() => {
this.page.isEnabled = true;
this._clearCacheService.purgeBrowserCache("Page enabled", this.community.communityId);
NotificationHandler.rise(this.page.name + ' has been <b>enabled successfully</b>');
this.loading = false;
}, error => {
});
}
}

View File

@ -0,0 +1,17 @@
import {NgModule} from '@angular/core';
import {CommonModule} from '@angular/common';
import {RouterModule} from "@angular/router";
import {ValidateEnabledPageComponent} from "./validateEnabledPage.component";
import {AdminToolServiceModule} from "../openaireLibrary/services/adminToolService.module";
import {HelpContentService} from "../services/help-content.service";
@NgModule({
declarations: [ValidateEnabledPageComponent],
imports: [
CommonModule, RouterModule, AdminToolServiceModule
],
exports:[ValidateEnabledPageComponent],
providers:[HelpContentService]
})
export class ValidateEnabledPageModule {
}

@ -1 +1 @@
Subproject commit fdcbc17b88deb76cee2cd4432282468be9f56b7e Subproject commit 3b437aafda7a716a0a89785a106456cbe520dce3

@ -1 +1 @@
Subproject commit 201ff990c0b2532951a796b10799ab95cb40c0b0 Subproject commit 99ab54cdd7b973a2ba047f0a6b37667270b58439

View File

@ -1,91 +1,14 @@
import {EnvProperties} from '../app/openaireLibrary/utils/properties/env-properties'; import {EnvProperties} from '../app/openaireLibrary/utils/properties/env-properties';
import {common, commonBeta, commonProd} from "../app/openaireLibrary/utils/properties/environments/environment";
export let properties: EnvProperties = { let props: EnvProperties = {
environment: "beta",
dashboard: 'connect',
isDashboard: true, isDashboard: true,
adminToolsPortalType: "community",
enablePiwikTrack: false, enablePiwikTrack: false,
useCache: false, useCache: false,
framesAPIURL: "https://beta.openaire.eu/stats3/", domain:'https://beta.admin.connect.openaire.eu',
claimsAPIURL: "https://beta.services.openaire.eu/claims/rest/claimsService/", monitorStatsFrameUrl:"https://beta.services.openaire.eu/stats-tool/"
statisticsAPIURL: "https://beta.services.openaire.eu/stats-api/",
statisticsFrameAPIURL: "https://beta.openaire.eu/stats/",
statisticsFrameNewAPIURL: "https://stats.madgik.di.uoa.gr/stats-api/",
useNewStatistisTool: true,
searchAPIURLLAst: "https://beta.services.openaire.eu/search/v2/api/",
searchResourcesAPIURL: "https://beta.services.openaire.eu/search/v2/api/resources",
openCitationsAPIURL: "https://services.openaire.eu/opencitations/getCitations?id=",
csvAPIURL: "https://beta.services.openaire.eu/search/v2/api/reports",
searchCrossrefAPIURL: "https://api.crossref.org/works",
searchDataciteAPIURL: "https://api.datacite.org/works",
searchOrcidURL: "https://pub.orcid.org/",
orcidURL: "https://orcid.org/",
doiURL: "https://dx.doi.org/",
cordisURL: "http://cordis.europa.eu/projects/",
openDoarURL: "http://v2.sherpa.ac.uk/id/repository/",
r3DataURL: "http://service.re3data.org/repository/",
sherpaURL: "http://www.sherpa.ac.uk/romeo/search.php?issn=",
zenodo: "https://zenodo.org/",
zenodoCommunities: "https://zenodo.org/api/communities/",
openAccess: "https://www.openaire.eu/support/faq#article-id-234",
openAccessRepo: "https://www.openaire.eu/support/faq#article-id-310",
fp7Guidlines: "https://www.openaire.eu/open-access-in-fp7-seventh-research-framework-programme",
h2020Guidlines: "https://www.openaire.eu/oa-publications/h2020/open-access-in-horizon-2020",
ercGuidlines: "http://erc.europa.eu/sites/default/files/document/file/ERC_Open_Access_Guidelines-revised_2014.pdf",
helpdesk: "https://www.openaire.eu/support/helpdesk",
helpdeskEmail: "helpdesk@openaire.eu",
utilsService: "https://demo.openaire.eu/utils-service",
vocabulariesAPI: "https://beta.services.openaire.eu/provision/mvc/vocabularies/",
piwikBaseUrl: " https://analytics.openaire.eu/piwik.php?idsite=6",
registryUrl: 'https://beta.services.openaire.eu/uoa-user-management/api/registry/',
loginUrl: "https://beta.services.openaire.eu/login-service/openid_connect_login",
userInfoUrl: "https://beta.services.openaire.eu/login-service/userInfo",
logoutUrl: "https://beta.services.openaire.eu/login-service/openid_logout",
cookieDomain: ".openaire.eu",
feedbackmail: "feedback@openaire.eu",
feedbackmailForMissingEntities: "feedback@openaire.eu",
cacheUrl: "https://demo.openaire.eu/cache/get?url=",
deleteCacheUrl: 'https://demo.openaire.eu/cache/clear',
deleteBrowserCacheUrl: 'https://beta.services.openaire.eu/uoa-admin-tools/cache',
adminToolsAPIURL: "https://beta.services.openaire.eu/uoa-admin-tools/",
adminToolsCommunity: "openaire",
communityAPI: "https://beta.services.openaire.eu/openaire/community/",
miningBackendURL: "https://beta.services.openaire.eu/interactive-mining",
csvLimit: 2000,
pagingLimit: 20,
resultsPerPage: 10,
baseLink: "",
domain: "https://beta.admin.connect.openaire.eu/",
baseOpenaireLink: "https://beta.explore.openaire.eu",
searchLinkToPublication: "/search/publication?articleId=",
searchLinkToProject: "/search/project?projectId=",
searchLinkToDataProvider: "/search/dataprovider?datasourceId=",
searchLinkToDataset: "/search/dataset?datasetId=",
searchLinkToOrganization: "/search/organization?organizationId=",
searchLinkToPublications: "/search/find/publications",
searchLinkToDataProviders: "/search/find/dataproviders",
searchLinkToProjects: "/search/find/projects",
searchLinkToDatasets: "/search/find/datasets",
searchLinkToSoftware: "/search/find/software",
searchLinkToOrganizations: "/search/find/organizations",
searchLinkToCompatibleDataProviders: "/search/content-providers",
searchLinkToEntityRegistriesDataProviders: "/search/entity-registries",
searchLinkToJournals: "/search/journals",
searchLinkToAdvancedPublications: "/search/advanced/publications",
searchLinkToAdvancedProjects: "/search/advanced/projects",
searchLinkToAdvancedDatasets: "/search/advanced/datasets",
searchLinkToAdvancedSoftware: "/search/advanced/software",
searchLinkToAdvancedDataProviders: "/search/advanced/dataproviders",
searchLinkToAdvancedOrganizations: "/search/advanced/organizations",
lastIndexInformationLink: "https://beta.openaire.eu/aggregation-and-content-provision-workflows",
showLastIndexInformationLink: false,
widgetLink: "https://beta.openaire.eu/index.php?option=com_openaire&view=widget&format=raw&projectId=",
claimsInformationLink: "https://beta.openaire.eu/linking",
lastIndexUpdate: "2020-05-06",
indexInfoAPI: "https://beta.services.openaire.eu/openaire/info/",
admins: ["rcd@openaire.eu"],
adminPortalURL: "https://beta.admin.connect.openaire.eu",
errorLink: '/error',
connectPortalUrl: 'https://beta.connect.openaire.eu'
}; };
export let properties: EnvProperties = {
...common, ...commonBeta, ...props
}

View File

@ -1,91 +1,16 @@
import {EnvProperties} from '../app/openaireLibrary/utils/properties/env-properties'; import {EnvProperties} from '../app/openaireLibrary/utils/properties/env-properties';
import {common, commonProd} from "../app/openaireLibrary/utils/properties/environments/environment";
let props: EnvProperties = {
export let properties: EnvProperties = {
environment:"production",
dashboard: 'connect',
isDashboard: true, isDashboard: true,
adminToolsPortalType: "community",
enablePiwikTrack: false, enablePiwikTrack: false,
useCache: false, useCache: false,
framesAPIURL: "https://www.openaire.eu/stats3/", domain:'https://admin.connect.openaire.eu',
claimsAPIURL: "https://services.openaire.eu/claims/rest/claimsService/", monitorStatsFrameUrl:"https://services.openaire.eu/stats-tool/"
statisticsAPIURL: "https://beta.services.openaire.eu/stats-api/",
statisticsFrameAPIURL:"https://www.openaire.eu/stats/",
statisticsFrameNewAPIURL: "http://marilyn.athenarc.gr:8080/stats-api/",
useNewStatistisTool:false,
searchAPIURLLAst: "https://services.openaire.eu/search/v2/api/",
searchResourcesAPIURL: "https://services.openaire.eu/search/v2/api/resources",
openCitationsAPIURL: "https://services.openaire.eu/opencitations/getCitations?id=",
csvAPIURL: "https://services.openaire.eu/search/v2/api/reports",
searchCrossrefAPIURL: "https://api.crossref.org/works",
searchDataciteAPIURL: "https://api.datacite.org/works",
searchOrcidURL: "https://pub.orcid.org/",
orcidURL: "https://orcid.org/",
doiURL: "https://dx.doi.org/",
cordisURL: "http://cordis.europa.eu/projects/",
openDoarURL: "http://v2.sherpa.ac.uk/id/repository/",
r3DataURL: "http://service.re3data.org/repository/",
sherpaURL: "http://www.sherpa.ac.uk/romeo/search.php?issn=",
zenodo: "https://zenodo.org/",
zenodoCommunities: "https://zenodo.org/api/communities/",
openAccess: "https://www.openaire.eu/support/faq#article-id-234",
openAccessRepo: "https://www.openaire.eu/support/faq#article-id-310",
fp7Guidlines: "https://www.openaire.eu/open-access-in-fp7-seventh-research-framework-programme",
h2020Guidlines: "https://www.openaire.eu/oa-publications/h2020/open-access-in-horizon-2020",
ercGuidlines: "http://erc.europa.eu/sites/default/files/document/file/ERC_Open_Access_Guidelines-revised_2014.pdf",
helpdesk: "https://www.openaire.eu/support/helpdesk",
helpdeskEmail: "helpdesk@openaire.eu",
utilsService: "https://explore.openaire.eu/utils-service",
vocabulariesAPI:"https://services.openaire.eu/provision/mvc/vocabularies/",
piwikBaseUrl:" https://analytics.openaire.eu/piwik.php?idsite=6",
loginUrl: "https://services.openaire.eu/login-service/openid_connect_login",
registryUrl: 'https://services.openaire.eu/uoa-user-management/api/registry/',
userInfoUrl: "https://services.openaire.eu/login-service/userInfo",
logoutUrl: "https://services.openaire.eu/login-service/openid_logout",
cookieDomain:".openaire.eu",
feedbackmail:"openaire.test@gmail.com",
feedbackmailForMissingEntities: "feedback@openaire.eu",
cacheUrl:"https://explore.openaire.eu/cache/get?url=",
deleteCacheUrl: 'https://explore.openaire.eu/cache/clear',
deleteBrowserCacheUrl: 'https://services.openaire.eu/uoa-admin-tools/cache',
adminToolsAPIURL:"https://services.openaire.eu/uoa-admin-tools/",
adminToolsCommunity:"openaire",
communityAPI: "https://services.openaire.eu/openaire/community/",
miningBackendURL: "https://beta.services.openaire.eu/interactive-mining",
csvLimit: 2000,
pagingLimit: 20,
resultsPerPage: 10,
baseLink: "",
domain: "https://admin.explore.openaire.eu/",
baseOpenaireLink: "https://explore.openaire.eu",
searchLinkToPublication: "/search/publication?articleId=",
searchLinkToProject: "/search/project?projectId=",
searchLinkToDataProvider: "/search/dataprovider?datasourceId=",
searchLinkToDataset: "/search/dataset?datasetId=",
searchLinkToOrganization: "/search/organization?organizationId=",
searchLinkToPublications: "/search/find/publications",
searchLinkToDataProviders: "/search/find/dataproviders",
searchLinkToProjects: "/search/find/projects",
searchLinkToDatasets: "/search/find/datasets",
searchLinkToSoftware: "/search/find/software",
searchLinkToOrganizations: "/search/find/organizations",
searchLinkToCompatibleDataProviders: "/search/content-providers",
searchLinkToEntityRegistriesDataProviders: "/search/entity-registries",
searchLinkToJournals: "/search/journals",
searchLinkToAdvancedPublications: "/search/advanced/publications",
searchLinkToAdvancedProjects: "/search/advanced/projects",
searchLinkToAdvancedDatasets: "/search/advanced/datasets",
searchLinkToAdvancedSoftware: "/search/advanced/software",
searchLinkToAdvancedDataProviders: "/search/advanced/dataproviders",
searchLinkToAdvancedOrganizations: "/search/advanced/organizations",
lastIndexInformationLink: "https://www.openaire.eu/aggregation-and-content-provision-workflows",
showLastIndexInformationLink: false,
widgetLink: "https://www.openaire.eu/index.php?option=com_openaire&view=widget&format=raw&projectId=",
claimsInformationLink: "https://www.openaire.eu/linking",
lastIndexUpdate: "2020-12-17",
indexInfoAPI: "https://services.openaire.eu/openaire/info/",
admins: ["rcd@openaire.eu"],
adminPortalURL: "https://admin.connect.openaire.eu",
errorLink: '/error',
connectPortalUrl: 'https://connect.openaire.eu'
}; };
export let properties: EnvProperties = {
...common, ...commonProd, ...props
}

View File

@ -4,93 +4,23 @@
// The list of which env maps to which file can be found in `.angular-cli.json`. // The list of which env maps to which file can be found in `.angular-cli.json`.
import {EnvProperties} from '../app/openaireLibrary/utils/properties/env-properties'; import {EnvProperties} from '../app/openaireLibrary/utils/properties/env-properties';
import {common, commonDev, commonProd} from "../app/openaireLibrary/utils/properties/environments/environment";
let props: EnvProperties = {
export let properties: EnvProperties = {
environment: 'development',
dashboard: 'connect',
isDashboard: true, isDashboard: true,
adminToolsPortalType: "community",
enablePiwikTrack: false, enablePiwikTrack: false,
useCache: false, useCache: false,
framesAPIURL: 'https://beta.openaire.eu/stats3/', connectPortalUrl: 'http://scoobydoo.di.uoa.gr:4200',
claimsAPIURL: 'http://scoobydoo.di.uoa.gr:8080/dnet-claims-service-2.0.0-SNAPSHOT/rest/claimsService/',
statisticsAPIURL: 'https://beta.services.openaire.eu/stats-api/',
statisticsFrameAPIURL: 'https://beta.openaire.eu/stats/',
statisticsFrameNewAPIURL: "https://stats.madgik.di.uoa.gr/stats-api/",
useNewStatistisTool: true,
searchAPIURLLAst: 'https://beta.services.openaire.eu/search/v2/api/',
searchResourcesAPIURL: 'https://beta.services.openaire.eu/search/v2/api/resources',
openCitationsAPIURL: 'https://services.openaire.eu/opencitations/getCitations?id=',
csvAPIURL: 'http://rudie.di.uoa.gr:8080/dnet-functionality-services-2.0.0-SNAPSHOT/rest/v2/reports',
searchCrossrefAPIURL: 'https://api.crossref.org/works',
searchDataciteAPIURL: 'https://api.datacite.org/works',
searchOrcidURL: 'https://pub.orcid.org/',
orcidURL: 'https://orcid.org/',
doiURL: 'https://dx.doi.org/',
cordisURL: 'http://cordis.europa.eu/projects/',
openDoarURL: 'http://v2.sherpa.ac.uk/id/repository/',
r3DataURL: 'http://service.re3data.org/repository/',
sherpaURL: 'http://www.sherpa.ac.uk/romeo/search.php?issn=',
zenodo: 'https://zenodo.org/',
zenodoCommunities: 'https://zenodo.org/api/communities/',
openAccess: 'https://www.openaire.eu/support/faq#article-id-234',
openAccessRepo: 'https://www.openaire.eu/support/faq#article-id-310',
fp7Guidlines: 'https://www.openaire.eu/open-access-in-fp7-seventh-research-framework-programme',
h2020Guidlines: 'https://www.openaire.eu/oa-publications/h2020/open-access-in-horizon-2020',
ercGuidlines: 'http://erc.europa.eu/sites/default/files/document/file/ERC_Open_Access_Guidelines-revised_2014.pdf',
helpdesk: 'https://www.openaire.eu/support/helpdesk',
helpdeskEmail: 'helpdesk@openaire.eu',
utilsService: 'http://mpagasas.di.uoa.gr:8000',
vocabulariesAPI: 'https://beta.services.openaire.eu/provision/mvc/vocabularies/',
piwikBaseUrl: ' https://analytics.openaire.eu/piwik.php?idsite=6',
registryUrl: 'http://mpagasas.di.uoa.gr:8080/dnet-openaire-users-1.0.0-SNAPSHOT/api/registry/',
loginUrl: "http://mpagasas.di.uoa.gr:19080/login-service/openid_connect_login",
userInfoUrl: "http://mpagasas.di.uoa.gr:19080/login-service/userInfo",
logoutUrl: "http://mpagasas.di.uoa.gr:19080/login-service/openid_logout",
cookieDomain: '.di.uoa.gr',
feedbackmail: 'openaire.test@gmail.com',
feedbackmailForMissingEntities: 'feedback@openaire.eu',
cacheUrl: 'http://scoobydoo.di.uoa.gr:3000/get?url=',
// deleteCacheUrl: 'http://duffy.di.uoa.gr:3000/clear',
// deleteBrowserCacheUrl: 'http://duffy.di.uoa.gr:19280/uoa-admin-tools/cache',
adminToolsAPIURL: 'http://duffy.di.uoa.gr:19280/uoa-admin-tools/',
adminToolsCommunity: 'openaire',
communityAPI: 'https://dev-openaire.d4science.org/openaire/community/',
miningBackendURL: 'https://beta.services.openaire.eu/interactive-mining',
csvLimit: 2000,
pagingLimit: 20,
resultsPerPage: 10,
baseLink: "",
domain:'https://beta.admin.connect.openaire.eu', domain:'https://beta.admin.connect.openaire.eu',
baseOpenaireLink: 'https://beta.explore.openaire.eu', adminToolsAPIURL: 'http://scoobydoo.di.uoa.gr:8880/uoa-admin-tools/',
searchLinkToPublication: '/search/publication?articleId=', utilsService: "http://scoobydoo.di.uoa.gr:8000",
searchLinkToProject: '/search/project?projectId=',
searchLinkToDataProvider: '/search/dataprovider?datasourceId=', monitorStatsFrameUrl:"https://stats.madgik.di.uoa.gr/stats-api/",
searchLinkToDataset: '/search/dataset?datasetId=', // disableFrameLoad : true
searchLinkToOrganization: '/search/organization?organizationId=',
searchLinkToPublications: '/search/find/publications',
searchLinkToDataProviders: '/search/find/dataproviders',
searchLinkToProjects: '/search/find/projects',
searchLinkToDatasets: '/search/find/datasets',
searchLinkToSoftware: '/search/find/software',
searchLinkToOrganizations: '/search/find/organizations',
searchLinkToCompatibleDataProviders: '/search/content-providers',
searchLinkToEntityRegistriesDataProviders: '/search/entity-registries',
searchLinkToJournals: '/search/journals',
searchLinkToAdvancedPublications: '/search/advanced/publications',
searchLinkToAdvancedProjects: '/search/advanced/projects',
searchLinkToAdvancedDatasets: '/search/advanced/datasets',
searchLinkToAdvancedSoftware: '/search/advanced/software',
searchLinkToAdvancedDataProviders: '/search/advanced/dataproviders',
searchLinkToAdvancedOrganizations: '/search/advanced/organizations',
lastIndexInformationLink: 'https://www.openaire.eu/aggregation-and-content-provision-workflows',
showLastIndexInformationLink: false,
widgetLink: 'https://beta.openaire.eu/index.php?option=com_openaire&view=widget&format=raw&projectId=',
claimsInformationLink: 'https://www.openaire.eu/linking-beta',
lastIndexUpdate: '2019-05-16',
indexInfoAPI: 'http://beta.services.openaire.eu/openaire/info/',
admins: ['kostis30fylloy@gmail.com'],
adminPortalURL: 'https://beta.admin.connect.openaire.eu',
errorLink: '/error',
connectPortalUrl: 'http://scoobydoo.di.uoa.gr:4200'
}; };
export let properties: EnvProperties = {
...common, ...commonDev, ...props
}

View File

@ -1,5 +1,5 @@
@use "sass:meta"; @use "sass:meta";
@import "~interactiveminingv3/assets/css/variables.css"; @import "node_modules/interactiveminingv3/assets/css/variables.css";
.mining { .mining {

View File

@ -7,8 +7,6 @@ import {
platformBrowserDynamicTesting platformBrowserDynamicTesting
} from '@angular/platform-browser-dynamic/testing'; } from '@angular/platform-browser-dynamic/testing';
declare const require: any;
// First, initialize the Angular testing environment. // First, initialize the Angular testing environment.
getTestBed().initTestEnvironment( getTestBed().initTestEnvironment(
BrowserDynamicTestingModule, BrowserDynamicTestingModule,
@ -16,7 +14,3 @@ getTestBed().initTestEnvironment(
teardown: { destroyAfterEach: false } teardown: { destroyAfterEach: false }
} }
); );
// Then we find all the tests.
const context = require.context('./', true, /\.spec\.ts$/);
// And load the modules.
context.keys().map(context);

View File

@ -10,13 +10,14 @@
"moduleResolution": "node", "moduleResolution": "node",
"experimentalDecorators": true, "experimentalDecorators": true,
"importHelpers": true, "importHelpers": true,
"target": "es2020", "target": "ES2022",
"typeRoots": [ "typeRoots": [
"node_modules/@types" "node_modules/@types"
], ],
"lib": [ "lib": [
"es2018", "es2018",
"dom" "dom"
] ],
"useDefineForClassFields": false
} }
} }