Compare commits
	
		
			76 Commits
		
	
	
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| 04494d2a2a | |||
| e2d6fbb513 | |||
| 477c650f3f | |||
| fc15c68cba | |||
| 32b5f5420b | |||
| ee87f82799 | |||
| 7c08f522aa | |||
| e211554579 | |||
| 7ba890dfd7 | |||
| 68b4309164 | |||
| d803f3d490 | |||
| 5468766d87 | |||
| e967d8d20c | |||
| ad4db882f0 | |||
| 84aa846b87 | |||
| 3532968b33 | |||
| 6bb49db4ee | |||
| 38fb111f7a | |||
| a50447f457 | |||
| b1a2044631 | |||
| c883920caa | |||
| 21453ef272 | |||
| 10182433f8 | |||
| b338f33a63 | |||
| cb82200481 | |||
| 9abf74d6d2 | |||
| 50e81a6cb5 | |||
| 8fae1fb6b3 | |||
| 372fa110ec | |||
| 35bec9fe58 | |||
| 93d67bdba9 | |||
| a5e72a18e3 | |||
| 91d2f46b93 | |||
| c60bae4533 | |||
| 43ac878d44 | |||
| ceabd06a43 | |||
| 9bfc0c5338 | |||
| fb8206ff13 | |||
| dceb0ef461 | |||
| 88bc1982ca | |||
| e741a9d7e7 | |||
| 65f1d22205 | |||
| d867c08aba | |||
| 6193eff38e | |||
| f1929e7cf9 | |||
| 373484c242 | |||
| f77460bb0c | |||
| 574e0dcb05 | |||
| 7b19a0aa08 | |||
| 08642d7618 | |||
| c3e9c27cd3 | |||
| 29a2854671 | |||
| 8e6786e722 | |||
| 6ad40564e3 | |||
| 776973bfe9 | |||
| 6025e43baa | |||
| d9a47f882c | |||
| 4235758a6d | |||
| 59fe2dfabb | |||
| 6364536dcd | |||
| a8a771114d | |||
| 4e0a2c8301 | |||
| b6fed92a17 | |||
| 97b57aeb0c | |||
| e25ed1fff9 | |||
| a2ff5b8a14 | |||
| 0284f18beb | |||
| 803d64c78c | |||
| dacb2f8ace | |||
| b7a53960e5 | |||
| 66f1e6b4fe | |||
| 33166bfafc | |||
| b2648645e8 | |||
| 53e3ddb751 | |||
| edc2dcab92 | |||
| d49f545d94 | 
| @@ -1,2 +1,4 @@ | ||||
| public/env.sample.js | ||||
| .pnpm-store | ||||
| .yarn | ||||
| .pnp.* | ||||
							
								
								
									
										101
									
								
								.drone.yml
									
									
									
									
									
								
							
							
						
						
									
										101
									
								
								.drone.yml
									
									
									
									
									
								
							| @@ -1,101 +0,0 @@ | ||||
| --- | ||||
| kind: secret | ||||
| name: docker_username | ||||
| get: | ||||
|   path: odit-registry-builder | ||||
|   name: username | ||||
|  | ||||
| --- | ||||
| kind: secret | ||||
| name: docker_password | ||||
| get: | ||||
|   path: odit-registry-builder | ||||
|   name: password | ||||
|  | ||||
| --- | ||||
| kind: secret | ||||
| name: git_ssh | ||||
| get: | ||||
|   path: odit-git-bot | ||||
|   name: sshkey | ||||
|  | ||||
| --- | ||||
| kind: secret | ||||
| name: npm_url | ||||
| get: | ||||
|   path: odit-npm-cache | ||||
|   name: url | ||||
|  | ||||
| --- | ||||
| kind: pipeline | ||||
| type: kubernetes | ||||
| name: build:dev | ||||
|  | ||||
| steps: | ||||
|   - name: run full license export | ||||
|     depends_on: ["clone"] | ||||
|     image: registry.odit.services/hub/library/node:19.7.0-alpine3.16 | ||||
|     commands: | ||||
|       - npm config set registry $NPM_REGISTRY_URL && npm i -g pnpm@8 | ||||
|       - pnpm i | ||||
|       - pnpm licenses:export | ||||
|     environment: | ||||
|       NPM_REGISTRY_URL: | ||||
|         from_secret: npm_url | ||||
|   - name: push new licenses file to repo | ||||
|     depends_on: ["run full license export"] | ||||
|     image: appleboy/drone-git-push | ||||
|     settings: | ||||
|       branch: dev | ||||
|       commit: true | ||||
|       commit_message: new license file version [CI SKIP] | ||||
|       author_email: bot@odit.services | ||||
|       remote: git@git.odit.services:lfk/frontend.git | ||||
|       ssh_key: | ||||
|         from_secret: git_ssh | ||||
|   - name: build dev | ||||
|     depends_on: ["clone"] | ||||
|     image: registry.odit.services/library/drone-kaniko | ||||
|     settings: | ||||
|       username: | ||||
|         from_secret: docker_username | ||||
|       password: | ||||
|         from_secret: docker_password | ||||
|       build_args: | ||||
|         - NPM_REGISTRY_URL: | ||||
|           from_secret: npm_url | ||||
|       repo: lfk/frontend | ||||
|       tags: | ||||
|         - dev | ||||
|       cache: true | ||||
|       registry: registry.odit.services | ||||
| trigger: | ||||
|   branch: | ||||
|     - dev | ||||
|   event: | ||||
|     - push | ||||
|  | ||||
| --- | ||||
| kind: pipeline | ||||
| type: kubernetes | ||||
| name: build:tags | ||||
| steps: | ||||
|   - name: build $DRONE_TAG | ||||
|     depends_on: ["clone"] | ||||
|     image: registry.odit.services/library/drone-kaniko | ||||
|     settings: | ||||
|       username: | ||||
|         from_secret: docker_username | ||||
|       password: | ||||
|         from_secret: docker_password | ||||
|       build_args: | ||||
|         - NPM_REGISTRY_URL: | ||||
|           from_secret: npm_url | ||||
|       repo: lfk/frontend | ||||
|       tags: | ||||
|         - "${DRONE_TAG}" | ||||
|       cache: true | ||||
|       registry: registry.odit.services | ||||
| trigger: | ||||
|   event: | ||||
|     - tag | ||||
							
								
								
									
										2
									
								
								.gitignore
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										2
									
								
								.gitignore
									
									
									
									
										vendored
									
									
								
							| @@ -4,3 +4,5 @@ public/env.js | ||||
| public/index.html | ||||
| /dist | ||||
| .pnpm-store | ||||
| .yarn | ||||
| .pnp.* | ||||
							
								
								
									
										26
									
								
								.woodpecker/build.yml
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										26
									
								
								.woodpecker/build.yml
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,26 @@ | ||||
| steps: | ||||
|   - name: run full license export | ||||
|     image: registry.odit.services/hub/library/node:19.7.0-alpine3.16 | ||||
|     commands: | ||||
|       - npm i -g pnpm@8 | ||||
|       - pnpm i | ||||
|       - pnpm licenses:export | ||||
|   - name: build dev | ||||
|     image: woodpeckerci/plugin-docker-buildx | ||||
|     settings: | ||||
|       repo: registry.odit.services/lfk/frontend | ||||
|       tags: | ||||
|         - dev | ||||
|         - latest | ||||
|       registry: registry.odit.services | ||||
|       platforms: linux/amd64,linux/arm64 | ||||
|       cache_from: registry.odit.services/lfk/frontend:dev | ||||
|       username: | ||||
|         from_secret: odit-registry-builder-username | ||||
|       password: | ||||
|         from_secret: odit-registry-builder-password | ||||
| when: | ||||
|   event: | ||||
|     - push | ||||
|   branch: | ||||
|     - dev | ||||
							
								
								
									
										17
									
								
								.woodpecker/release.yml
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										17
									
								
								.woodpecker/release.yml
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,17 @@ | ||||
| steps: | ||||
|   - name: build tag | ||||
|     image: woodpeckerci/plugin-docker-buildx | ||||
|     settings: | ||||
|       repo: registry.odit.services/lfk/frontend | ||||
|       tags: | ||||
|         - "${CI_COMMIT_TAG}" | ||||
|       registry: registry.odit.services | ||||
|       platforms: linux/amd64,linux/arm64 | ||||
|       cache_from: registry.odit.services/lfk/frontend:latest | ||||
|       username: | ||||
|         from_secret: odit-registry-builder-username | ||||
|       password: | ||||
|         from_secret: odit-registry-builder-password | ||||
| when: | ||||
|   event: | ||||
|     - tag | ||||
							
								
								
									
										152
									
								
								CHANGELOG.md
									
									
									
									
									
								
							
							
						
						
									
										152
									
								
								CHANGELOG.md
									
									
									
									
									
								
							| @@ -2,8 +2,160 @@ | ||||
|  | ||||
| All notable changes to this project will be documented in this file. Dates are displayed in UTC. | ||||
|  | ||||
| #### [1.5.3](https://git.odit.services/lfk/frontend/compare/1.5.2...1.5.3) | ||||
|  | ||||
| - feat(dx): Yarn support [`fc15c68`](https://git.odit.services/lfk/frontend/commit/fc15c68cba0d1986563eaf63da3a68784a685a9e) | ||||
| - feat(about): cleanup ui [`84aa846`](https://git.odit.services/lfk/frontend/commit/84aa846b87186b52a2f8632724d4f2cb70af062b) | ||||
| - feat(dashboard): reorder menu items [`e967d8d`](https://git.odit.services/lfk/frontend/commit/e967d8d20c6972b64b0096594a09043553e9c7e5) | ||||
| - fix: unexpected/ missing props [`d803f3d`](https://git.odit.services/lfk/frontend/commit/d803f3d4905d6f792b77d17025467ac13c29068b) | ||||
| - chore(deps): bump some [`68b4309`](https://git.odit.services/lfk/frontend/commit/68b4309164eac40b6fda969b60a7e238985d49f8) | ||||
| - fix(ci): Switch over to new woodpecker version [`7ba890d`](https://git.odit.services/lfk/frontend/commit/7ba890dfd7ba908ebef0338f6faa5e7d804cb5ef) | ||||
| - refactor(ci): Only build licences, don't export [`32b5f54`](https://git.odit.services/lfk/frontend/commit/32b5f5420bf9ff656b713d61b3a0113b9d6cb69f) | ||||
| - feat: cleanup random page toasts [`ad4db88`](https://git.odit.services/lfk/frontend/commit/ad4db882f0f4d00a80ae5e0072e09c071c07ffa2) | ||||
| - fix(ci): Update git pushb settings [`ee87f82`](https://git.odit.services/lfk/frontend/commit/ee87f82799ce559fd43d671ab412f2643eafeac6) | ||||
| - fix(ci): Update relase machanism [`7c08f52`](https://git.odit.services/lfk/frontend/commit/7c08f522aa4b2986544a4c0e5d3261c4c7296121) | ||||
| - fix(ci): Install pnpm [`e211554`](https://git.odit.services/lfk/frontend/commit/e211554579b1f27d13194eff4aad76f6f030141e) | ||||
| - fix(orgs): ImportRunnerModal props [`5468766`](https://git.odit.services/lfk/frontend/commit/5468766d875a6278f01ed1fd9573688374befdd5) | ||||
|  | ||||
| #### [1.5.2](https://git.odit.services/lfk/frontend/compare/1.5.1...1.5.2) | ||||
|  | ||||
| > 21 November 2024 | ||||
|  | ||||
| - feat: improved dashboard titles ui + a11y [`21453ef`](https://git.odit.services/lfk/frontend/commit/21453ef272665c0b7c7b04009b7b74e110fbd988) | ||||
| - feat: improved dashboard titles ui + a11y [`c883920`](https://git.odit.services/lfk/frontend/commit/c883920caaaaef30a8e54dd0e7eecd68943f3041) | ||||
| - feat(dashboard): improved a11y of active sidebar menu item [`a50447f`](https://git.odit.services/lfk/frontend/commit/a50447f457ecc045995efb7b952b07ea09c91373) | ||||
| - feat: improved mobile buttons + search ui [`38fb111`](https://git.odit.services/lfk/frontend/commit/38fb111f7a2b5a1a01b17b00e89ee081e4b91bd9) | ||||
| - feat(i18n/de): rename "Track" to "Laufstrecke" [`1018243`](https://git.odit.services/lfk/frontend/commit/10182433f825968ee55298399b231173698a795c) | ||||
| - 🚀RELEASE v1.5.2 [`3532968`](https://git.odit.services/lfk/frontend/commit/3532968b3399b985b1ed28ba6b89a13f35f9289b) | ||||
| - feat(dashboard): improved mobile ui hamburger button [`b338f33`](https://git.odit.services/lfk/frontend/commit/b338f33a63ad8e98ab44deff2f80dbd5fe2a0fc2) | ||||
| - feat(dashboard): match greeting style with rest of titles [`b1a2044`](https://git.odit.services/lfk/frontend/commit/b1a20446314d1b25e9f653bd2767b072fd629f97) | ||||
| - feat(dashboard): add lfk icon and app name to mobile nav bar [`6bb49db`](https://git.odit.services/lfk/frontend/commit/6bb49db4eee95486f5a947d708b80a7a94d36933) | ||||
| - feat(users/UsersOverview): improve ui by adding borders to badges [`cb82200`](https://git.odit.services/lfk/frontend/commit/cb82200481c629a0dd8b235821115ae4276948ca) | ||||
|  | ||||
| #### [1.5.1](https://git.odit.services/lfk/frontend/compare/1.5.0...1.5.1) | ||||
|  | ||||
| > 21 November 2024 | ||||
|  | ||||
| - chore(deps): pnpm@9 [`35bec9f`](https://git.odit.services/lfk/frontend/commit/35bec9fe584b93cd52e8bab4e469713468a67f70) | ||||
| - chore(deps): bump some [`8fae1fb`](https://git.odit.services/lfk/frontend/commit/8fae1fb6b3e033f789d2568cbd2640c0d163dc53) | ||||
| - fix(scanstations): CopyScanStationTokenModal open after create [`372fa11`](https://git.odit.services/lfk/frontend/commit/372fa110ec402dae166a302f2209c79353983148) | ||||
| - 🚀RELEASE v1.5.1 [`9abf74d`](https://git.odit.services/lfk/frontend/commit/9abf74d6d217e7745c1055bdbfbe97de7b14572f) | ||||
| - fix(config): add explicit window.config [`91d2f46`](https://git.odit.services/lfk/frontend/commit/91d2f46b934bcba1429bd1d96e772c25c42a3e28) | ||||
| - fix(dockerfile): AS casing [`50e81a6`](https://git.odit.services/lfk/frontend/commit/50e81a6cb5773381e153cbec3bed7db820ced84a) | ||||
| - refactor(scanstations/CopyScanStationTokenModal): drop dispatch [`a5e72a1`](https://git.odit.services/lfk/frontend/commit/a5e72a18e368b5a7ee7b4e1894de613ecb767f28) | ||||
| - chore(deps): node:23.2.0 [`93d67bd`](https://git.odit.services/lfk/frontend/commit/93d67bdba90a67b45d8895d9facaf66e908d53d6) | ||||
| - fix(tracks/AddTrackModal): i18n [`c60bae4`](https://git.odit.services/lfk/frontend/commit/c60bae45334c2aa90d8931da07691c196469da46) | ||||
| - fix: tailwind config [`43ac878`](https://git.odit.services/lfk/frontend/commit/43ac878d44b556c6d7811610f6fe0c9a5eff305f) | ||||
|  | ||||
| #### [1.5.0](https://git.odit.services/lfk/frontend/compare/1.4.13...1.5.0) | ||||
|  | ||||
| > 20 November 2024 | ||||
|  | ||||
| - feat(ci)!: Switch to woodpecker [`fb8206f`](https://git.odit.services/lfk/frontend/commit/fb8206ff130f4f65dcf619a2a786e7d5895b77a1) | ||||
| - 🚀RELEASE v1.5.0 [`ceabd06`](https://git.odit.services/lfk/frontend/commit/ceabd06a4319c3c9ffab680f909730d5bd789540) | ||||
| - fix(components): Add missing toast imports [`9bfc0c5`](https://git.odit.services/lfk/frontend/commit/9bfc0c5338933e832d5df50457c7978c026d8df6) | ||||
|  | ||||
| #### [1.4.13](https://git.odit.services/lfk/frontend/compare/1.4.12...1.4.13) | ||||
|  | ||||
| > 31 July 2023 | ||||
|  | ||||
| - 🚀RELEASE v1.4.13 [`dceb0ef`](https://git.odit.services/lfk/frontend/commit/dceb0ef46197dc56e29c5f52a5bd8f9fe9b70b27) | ||||
| - Show donations as euro in export [`88bc198`](https://git.odit.services/lfk/frontend/commit/88bc1982cab4481e2e9245f81eff27e095b66a0f) | ||||
| - new license file version [CI SKIP] [`6193eff`](https://git.odit.services/lfk/frontend/commit/6193eff38e1a9d5726bc7d572ab36b921de843d0) | ||||
|  | ||||
| #### [1.4.12](https://git.odit.services/lfk/frontend/compare/1.4.11...1.4.12) | ||||
|  | ||||
| > 18 May 2023 | ||||
|  | ||||
| - 🚀RELEASE v1.4.12 [`65f1d22`](https://git.odit.services/lfk/frontend/commit/65f1d222050b0dec81fc847c1921b6135a55ce50) | ||||
| - fix(donation/payment): Funny javascript number to float conversion where integers were needed [`d867c08`](https://git.odit.services/lfk/frontend/commit/d867c08aba234d3a7fe9e2311d37dc5e96fc2afc) | ||||
| - new license file version [CI SKIP] [`08642d7`](https://git.odit.services/lfk/frontend/commit/08642d7618faeae31f0acfe776642c9fa156e5ff) | ||||
|  | ||||
| #### [1.4.11](https://git.odit.services/lfk/frontend/compare/1.4.10...1.4.11) | ||||
|  | ||||
| > 10 May 2023 | ||||
|  | ||||
| - chore(deps): Lockfile [`f77460b`](https://git.odit.services/lfk/frontend/commit/f77460bb0c8ce6d0f3d83a077017d5fc7bf55af7) | ||||
| - 🚀RELEASE v1.4.11 [`373484c`](https://git.odit.services/lfk/frontend/commit/373484c2424bea7ae0d70d342e0ae2076aab1b6a) | ||||
| - feat(orgs): Show total distance [`574e0dc`](https://git.odit.services/lfk/frontend/commit/574e0dcb051305bde2fc76d8456a35baec0cf309) | ||||
| - chore(deps): More bumps [`7b19a0a`](https://git.odit.services/lfk/frontend/commit/7b19a0aa08bb6c89c51d27c0d05777e8fcfdad17) | ||||
|  | ||||
| #### [1.4.10](https://git.odit.services/lfk/frontend/compare/1.4.9...1.4.10) | ||||
|  | ||||
| > 10 May 2023 | ||||
|  | ||||
| - chore(deps): Bumped svelte-table [`29a2854`](https://git.odit.services/lfk/frontend/commit/29a2854671b3af5b85ea96d050a9076f47b6575d) | ||||
| - 🚀RELEASE v1.4.10 [`c3e9c27`](https://git.odit.services/lfk/frontend/commit/c3e9c27cd3d4b916f1661d4958cabab038918587) | ||||
| - chore(deps): Pin and bump [`8e6786e`](https://git.odit.services/lfk/frontend/commit/8e6786e72227b3f07cc805f0957d5b7fd123ec13) | ||||
| - chore(deps): Bumped scanclientjs [`6ad4056`](https://git.odit.services/lfk/frontend/commit/6ad40564e3e342046f6ee19fab9e455ec3bbff9b) | ||||
|  | ||||
| #### [1.4.9](https://git.odit.services/lfk/frontend/compare/1.4.8...1.4.9) | ||||
|  | ||||
| > 9 May 2023 | ||||
|  | ||||
| - 🚀RELEASE v1.4.9 [`776973b`](https://git.odit.services/lfk/frontend/commit/776973bfe9b34c26a1c80d5e458cc2644dd9036b) | ||||
| - Changed the in table replacement method [`d9a47f8`](https://git.odit.services/lfk/frontend/commit/d9a47f882c1c6bcf98ef85d50d70c010d54b326e) | ||||
| - Fixed empty return [`6025e43`](https://git.odit.services/lfk/frontend/commit/6025e43baa8516657a60a1de9a82c2189221c6ac) | ||||
|  | ||||
| #### [1.4.8](https://git.odit.services/lfk/frontend/compare/1.4.7...1.4.8) | ||||
|  | ||||
| > 9 May 2023 | ||||
|  | ||||
| - Switched donor loading to non-paginated [`59fe2df`](https://git.odit.services/lfk/frontend/commit/59fe2dfabb224863876c4db31a965c34a51a9369) | ||||
| - 🚀RELEASE v1.4.8 [`4235758`](https://git.odit.services/lfk/frontend/commit/4235758a6d1499715287d6ab193cc87c68d5742e) | ||||
|  | ||||
| #### [1.4.7](https://git.odit.services/lfk/frontend/compare/1.4.6...1.4.7) | ||||
|  | ||||
| > 4 May 2023 | ||||
|  | ||||
| - Paginated modal data loading [`a8a7711`](https://git.odit.services/lfk/frontend/commit/a8a771114df6eb57d5b1d5497a5be49e619d4102) | ||||
| - Moved loading to onmount [`4e0a2c8`](https://git.odit.services/lfk/frontend/commit/4e0a2c83015bde5e360c5fb2c0babbeaa03dc2b5) | ||||
| - 🚀RELEASE v1.4.7 [`6364536`](https://git.odit.services/lfk/frontend/commit/6364536dcd840c71f7cb6afb31bbc4f160ac4f73) | ||||
|  | ||||
| #### [1.4.6](https://git.odit.services/lfk/frontend/compare/1.4.5...1.4.6) | ||||
|  | ||||
| > 4 May 2023 | ||||
|  | ||||
| - 🚀RELEASE v1.4.6 [`b6fed92`](https://git.odit.services/lfk/frontend/commit/b6fed92a176af1c975484d9146ee5634e0031401) | ||||
| - fix(donor/details): don't load donations [`a2ff5b8`](https://git.odit.services/lfk/frontend/commit/a2ff5b8a142ce4e6b8876f64935f9787ec44a51e) | ||||
| - fix(donor/detail): Set email to null to avoid vaidation errors [`97b57ae`](https://git.odit.services/lfk/frontend/commit/97b57aeb0cc9058542a36dea9c8b2852169c250f) | ||||
| - fix(donor/detail): Set phone to null to avoid vaidation errors [`e25ed1f`](https://git.odit.services/lfk/frontend/commit/e25ed1fff9b200605d5d2b78238b774ec7289aaa) | ||||
|  | ||||
| #### [1.4.5](https://git.odit.services/lfk/frontend/compare/1.4.4...1.4.5) | ||||
|  | ||||
| > 4 May 2023 | ||||
|  | ||||
| - Revert "revert: buggy pagination" [`dacb2f8`](https://git.odit.services/lfk/frontend/commit/dacb2f8ace373f6594fc64af133971af053f00c0) | ||||
| - fix: Removed dynamic pagesize adjustments [`803d64c`](https://git.odit.services/lfk/frontend/commit/803d64c78caa570d31d6055e70e2d2af6834f04b) | ||||
| - 🚀RELEASE v1.4.5 [`0284f18`](https://git.odit.services/lfk/frontend/commit/0284f18beb8b24d4d4d071eca13bc5868666232c) | ||||
|  | ||||
| #### [1.4.4](https://git.odit.services/lfk/frontend/compare/1.4.3...1.4.4) | ||||
|  | ||||
| > 4 May 2023 | ||||
|  | ||||
| - 🚀RELEASE v1.4.4 [`b7a5396`](https://git.odit.services/lfk/frontend/commit/b7a53960e5f37ae089d77bc11668d917145e2abb) | ||||
| - fix(AddDonationModal): missing toast dismiss on success distance donation [`66f1e6b`](https://git.odit.services/lfk/frontend/commit/66f1e6b4fe1350ee79673a0aff97e36f44179c92) | ||||
|  | ||||
| #### [1.4.3](https://git.odit.services/lfk/frontend/compare/1.4.2...1.4.3) | ||||
|  | ||||
| > 4 May 2023 | ||||
|  | ||||
| - revert: buggy pagination [`b264864`](https://git.odit.services/lfk/frontend/commit/b2648645e8fc05f8742ecfc592557f954261671b) | ||||
| - 🚀RELEASE v1.4.3 [`33166bf`](https://git.odit.services/lfk/frontend/commit/33166bfafcffb9d86dfc7dfcd2cb8ba5c85da7e7) | ||||
|  | ||||
| #### [1.4.2](https://git.odit.services/lfk/frontend/compare/1.4.1...1.4.2) | ||||
|  | ||||
| > 4 May 2023 | ||||
|  | ||||
| - 🚀RELEASE v1.4.2 [`53e3ddb`](https://git.odit.services/lfk/frontend/commit/53e3ddb751c1150a4640ae6302e4df5b88cedc51) | ||||
| - fix(GenerateRunnerCertificates): missing toast import [`d49f545`](https://git.odit.services/lfk/frontend/commit/d49f545d94acabc0c96860f212466b7a4cbe7dab) | ||||
| - fix(DonorDetail): missing toast import [`edc2dca`](https://git.odit.services/lfk/frontend/commit/edc2dcab92c3cace05335a283a849c3c978ec8ec) | ||||
|  | ||||
| #### [1.4.1](https://git.odit.services/lfk/frontend/compare/1.4.0...1.4.1) | ||||
|  | ||||
| > 1 May 2023 | ||||
|  | ||||
| - 🚀RELEASE v1.4.1 [`3b98c99`](https://git.odit.services/lfk/frontend/commit/3b98c99b72f24b8552e2b2334f13622bdf6ef90d) | ||||
| - Fixed translation [`1da775a`](https://git.odit.services/lfk/frontend/commit/1da775a09b8be90a49e06aed16df917d221ee989) | ||||
|  | ||||
| #### [1.4.0](https://git.odit.services/lfk/frontend/compare/1.3.4...1.4.0) | ||||
|   | ||||
| @@ -1,9 +1,9 @@ | ||||
| FROM registry.odit.services/hub/library/node:20.0.0-alpine3.17 as build | ||||
| FROM registry.odit.services/hub/library/node:23.2.0-alpine3.20 AS build | ||||
| ARG NPM_REGISTRY_URL=https://registry.npmjs.org | ||||
| WORKDIR /app | ||||
|  | ||||
| COPY package.json pnpm-lock.yaml vite.config.js tailwind.config.js postcss.config.cjs index.html ./ | ||||
| RUN npm config set registry $NPM_REGISTRY_URL && npm i -g pnpm@8 | ||||
| COPY package.json pnpm-lock.yaml vite.config.js tailwind.config.cjs postcss.config.cjs index.html ./ | ||||
| RUN npm config set registry $NPM_REGISTRY_URL && npm i -g pnpm@9 | ||||
| RUN mkdir /pnpm && pnpm config set store-dir /pnpm && pnpm i | ||||
|  | ||||
| COPY src ./src | ||||
| @@ -11,6 +11,6 @@ COPY public ./public | ||||
| RUN pnpm build | ||||
|  | ||||
| # final image | ||||
| FROM registry.odit.services/library/nginx-brotli:3.15 as final | ||||
| FROM registry.odit.services/library/nginx-brotli:3.15 AS final | ||||
| COPY --from=build /app/dist /usr/share/nginx/html | ||||
| COPY ./nginx.conf /etc/nginx/nginx.conf | ||||
| @@ -13,7 +13,7 @@ | ||||
|  | ||||
|   <body> | ||||
|     <span style="display: none; visibility: hidden" id="buildinfo" | ||||
|       >RELEASE_INFO-1.4.1-RELEASE_INFO</span | ||||
|       >RELEASE_INFO-1.5.3-RELEASE_INFO</span | ||||
|     > | ||||
|     <noscript>You need to enable JavaScript to run this app.</noscript> | ||||
|     <script src="/env.js"></script> | ||||
|   | ||||
							
								
								
									
										32
									
								
								package.json
									
									
									
									
									
								
							
							
						
						
									
										32
									
								
								package.json
									
									
									
									
									
								
							| @@ -1,6 +1,6 @@ | ||||
| { | ||||
|   "name": "@odit/lfk-frontend", | ||||
|   "version": "1.4.1", | ||||
|   "version": "1.6.0", | ||||
|   "type": "module", | ||||
|   "scripts": { | ||||
|     "i18n-order": "node order.js", | ||||
| @@ -12,16 +12,16 @@ | ||||
|   }, | ||||
|   "license": "CC-BY-NC-SA-4.0", | ||||
|   "devDependencies": { | ||||
|     "@odit/license-exporter": "0.0.12", | ||||
|     "@odit/license-exporter": "0.2.0", | ||||
|     "@sveltejs/vite-plugin-svelte": "2.1.1", | ||||
|     "auto-changelog": "2.4.0", | ||||
|     "autoprefixer": "10.4.14", | ||||
|     "postcss": "8.4.23", | ||||
|     "prettier": "^2.8.8", | ||||
|     "prettier-plugin-svelte": "^2.10.0", | ||||
|     "release-it": "15.10.1", | ||||
|     "auto-changelog": "2.5.0", | ||||
|     "autoprefixer": "10.4.20", | ||||
|     "postcss": "8.4.49", | ||||
|     "prettier": "3.3.3", | ||||
|     "prettier-plugin-svelte": "3.2.8", | ||||
|     "release-it": "17.10.0", | ||||
|     "svelte-select": "3.17.0", | ||||
|     "tailwindcss": "3.3.2", | ||||
|     "tailwindcss": "3.4.15", | ||||
|     "vite": "4.3.3" | ||||
|   }, | ||||
|   "release-it": { | ||||
| @@ -42,19 +42,19 @@ | ||||
|     } | ||||
|   }, | ||||
|   "dependencies": { | ||||
|     "@odit/lfk-client-js": "1.1.1", | ||||
|     "@paralleldrive/cuid2": "^2.2.0", | ||||
|     "@tanstack/svelte-table": "^8.8.6", | ||||
|     "bwip-js": "^3.4.0", | ||||
|     "check-password-strength": "2.0.7", | ||||
|     "@odit/lfk-client-js": "1.1.3", | ||||
|     "@paralleldrive/cuid2": "2.2.2", | ||||
|     "@tanstack/svelte-table": "8.9.1", | ||||
|     "bwip-js": "3.4.0", | ||||
|     "check-password-strength": "2.0.10", | ||||
|     "csvtojson": "2.0.10", | ||||
|     "localforage": "1.10.0", | ||||
|     "marked": "4.3.0", | ||||
|     "svelte": "3.58.0", | ||||
|     "svelte-french-toast": "1.0.4-beta.0", | ||||
|     "svelte-french-toast": "1.2.0", | ||||
|     "svelte-i18n": "3.6.0", | ||||
|     "tinro": "0.6.12", | ||||
|     "validator": "13.9.0", | ||||
|     "validator": "13.12.0", | ||||
|     "xlsx": "0.18.5" | ||||
|   }, | ||||
|   "volta": { | ||||
|   | ||||
							
								
								
									
										5481
									
								
								pnpm-lock.yaml
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										5481
									
								
								pnpm-lock.yaml
									
									
									
										generated
									
									
									
								
							
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							| @@ -1,5 +1,6 @@ | ||||
| const config = { | ||||
| 	baseurl: "http://localhost:4010", | ||||
| 	baseurl_selfservice: "http://localhost:5174", | ||||
| 	baseurl_documentserver: "http://localhost:4010/documents", | ||||
| 	documentserver_key: | ||||
| 		"NqZSYTy5AFQ7MppbLW5moqpTk7u7YrNUHKYhKYuThnnya2WpCOIU694hIZT1FzYe", | ||||
| @@ -8,3 +9,4 @@ const config = { | ||||
| 	default_password: "demo", | ||||
| 	prefersHashRouting: true, | ||||
| }; | ||||
| window.config = config; | ||||
|   | ||||
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							| @@ -20,7 +20,6 @@ | ||||
|         OpenAPI.TOKEN = value.access_token; | ||||
|         const jwtinfo = JSON.parse(atob(OpenAPI.TOKEN.split(".")[1])); | ||||
|         store.login(value, jwtinfo); | ||||
|         toast($_("welcome_wavinghand")); | ||||
|       } | ||||
|     } | ||||
|   }); | ||||
| @@ -50,7 +49,6 @@ | ||||
|           store.login(result.access_token, jwtinfo); | ||||
|           location.replace("/"); | ||||
|           toast.dismiss(); | ||||
|           toast($_("welcome_wavinghand")); | ||||
|         }) | ||||
|         .catch((err) => { | ||||
|           toast.dismiss(); | ||||
|   | ||||
| @@ -11,15 +11,16 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("cards")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("CARD:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("add-card")} | ||||
|     </button> | ||||
| @@ -28,12 +29,11 @@ | ||||
|         bulk_modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("create-bulk-cards")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <CardsOverview bind:current_cards bind:addCards /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -5,7 +5,7 @@ | ||||
|  | ||||
| <div class="text-center items-center justify-center"> | ||||
|   <p class="mb-16 text-lg text-gray-500"> | ||||
|     <img class="m-auto" style="height:15rem" src={cards_empty} alt="" /> | ||||
|     <img class="m-auto mt-2" style="height:15rem" src={cards_empty} alt="" /> | ||||
|     <span class="font-bold">{$_("there-are-no-cards-yet")}</span><br /> | ||||
|     <span>{$_("add-your-first-card")}</span> | ||||
|   </p> | ||||
|   | ||||
| @@ -151,9 +151,8 @@ | ||||
|   } | ||||
|  | ||||
|   onMount(async () => { | ||||
|     toast.loading($_("loading-cards")); | ||||
|     let page = 0; | ||||
|     let pagesize = 100; | ||||
|     let pagesize = 500; | ||||
|     while (page >= 0) { | ||||
|       const cards = await RunnerCardService.runnerCardControllerGetAll( | ||||
|         page, | ||||
| @@ -171,10 +170,7 @@ | ||||
|  | ||||
|       dataLoaded = true; | ||||
|       page++; | ||||
|       pagesize += 100; | ||||
|     } | ||||
|     toast.dismiss(); | ||||
|     toast.success($_("all-cards-loaded")); | ||||
|   }); | ||||
| </script> | ||||
|  | ||||
| @@ -220,7 +216,7 @@ | ||||
|       {#if selected.length > 0} | ||||
|         <button | ||||
|           type="button" | ||||
|           class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm inline-flex" | ||||
|           class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm inline-flex" | ||||
|           id="options-menu" | ||||
|           on:click={async () => { | ||||
|             const prom = []; | ||||
|   | ||||
| @@ -152,7 +152,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteContact} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-deletion")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -169,7 +169,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-contact")}</button | ||||
|             > | ||||
|           {/if} | ||||
| @@ -180,7 +180,7 @@ | ||||
|             class:opacity-50={!save_enabled} | ||||
|             type="button" | ||||
|             on:click={submit} | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
|   | ||||
| @@ -8,20 +8,20 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("contacts")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("CONTACT:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|     > | ||||
|       {$_("create-a-new-contact")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <ContactsOverview bind:current_contacts /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -32,7 +32,7 @@ | ||||
|         bind:value={searchvalue} | ||||
|         placeholder={$_("datatable.search")} | ||||
|         aria-label={$_("datatable.search")} | ||||
|         class="mb-4" | ||||
|         class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|       /> | ||||
|       <div | ||||
|         class="shadow border-b border-gray-200 sm:rounded-lg overflow-x-scroll" | ||||
|   | ||||
| @@ -24,12 +24,12 @@ | ||||
|     </a> | ||||
|     <nav class="text-sm font-medium text-gray-600" aria-label="Main Navigation"> | ||||
|       <a | ||||
|         class:bg-gray-100={$router.path === "/"} | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|         class:activenav={$router.path === "/"} | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|         href="/" | ||||
|       > | ||||
|         <svg | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|           xmlns="http://www.w3.org/2000/svg" | ||||
|           viewBox="0 0 20 20" | ||||
|           fill="currentColor" | ||||
| @@ -40,79 +40,16 @@ | ||||
|         </svg> | ||||
|         <span>{$_("dashboard-title")}</span> | ||||
|       </a> | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("ORGANIZATION:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path.includes("/orgs/")} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           href="/orgs/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 24 24" | ||||
|             width="24" | ||||
|             height="24" | ||||
|             ><path fill="none" d="M0 0h24v24H0z" /> | ||||
|             <path | ||||
|               d="M17 19h2v-8h-6v8h2v-6h2v6zM3 19V4a1 1 0 0 1 1-1h14a1 1 0 0 1 1 1v5h2v10h1v2H2v-2h1zm4-8v2h2v-2H7zm0 4v2h2v-2H7zm0-8v2h2V7H7z" | ||||
|             /></svg | ||||
|           > | ||||
|           <span>{$_("orgs")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("USER:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/users/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           href="/users/" | ||||
|         > | ||||
|           <svg | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             width="24" | ||||
|             height="24" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             viewBox="0 0 24 24" | ||||
|             ><path fill="none" d="M0 0h24v24H0z" /> | ||||
|             <path | ||||
|               d="M12 14v8H4a8 8 0 018-8zm0-1a6 6 0 110-12 6 6 0 010 12zm2.6 5.81a3.51 3.51 0 010-1.62l-1-.57 1-1.74 1 .58a3.5 3.5 0 011.4-.82V13.5h2v1.15a3.5 3.5 0 011.4.8l1-.57 1 1.74-1 .57a3.51 3.51 0 010 1.62l1 .57-1 1.74-1-.58a3.5 3.5 0 01-1.4.82v1.14h-2v-1.15a3.5 3.5 0 01-1.4-.8l-1 .57-1-1.74 1-.57zM18 17a1 1 0 100 2 1 1 0 000-2z" | ||||
|             /></svg | ||||
|           > | ||||
|           <span>{$_("users")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("USERGROUP:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/groups/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           href="/groups/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 640 512" | ||||
|             ><path | ||||
|               fill="currentColor" | ||||
|               d="M610.5 341.3c2.6-14.1 2.6-28.5 0-42.6l25.8-14.9c3-1.7 4.3-5.2 3.3-8.5-6.7-21.6-18.2-41.2-33.2-57.4-2.3-2.5-6-3.1-9-1.4l-25.8 14.9c-10.9-9.3-23.4-16.5-36.9-21.3v-29.8c0-3.4-2.4-6.4-5.7-7.1-22.3-5-45-4.8-66.2 0-3.3.7-5.7 3.7-5.7 7.1v29.8c-13.5 4.8-26 12-36.9 21.3l-25.8-14.9c-2.9-1.7-6.7-1.1-9 1.4-15 16.2-26.5 35.8-33.2 57.4-1 3.3.4 6.8 3.3 8.5l25.8 14.9c-2.6 14.1-2.6 28.5 0 42.6l-25.8 14.9c-3 1.7-4.3 5.2-3.3 8.5 6.7 21.6 18.2 41.1 33.2 57.4 2.3 2.5 6 3.1 9 1.4l25.8-14.9c10.9 9.3 23.4 16.5 36.9 21.3v29.8c0 3.4 2.4 6.4 5.7 7.1 22.3 5 45 4.8 66.2 0 3.3-.7 5.7-3.7 5.7-7.1v-29.8c13.5-4.8 26-12 36.9-21.3l25.8 14.9c2.9 1.7 6.7 1.1 9-1.4 15-16.2 26.5-35.8 33.2-57.4 1-3.3-.4-6.8-3.3-8.5l-25.8-14.9zM496 368.5c-26.8 0-48.5-21.8-48.5-48.5s21.8-48.5 48.5-48.5 48.5 21.8 48.5 48.5-21.7 48.5-48.5 48.5zM96 224c35.3 0 64-28.7 64-64s-28.7-64-64-64-64 28.7-64 64 28.7 64 64 64zm224 32c1.9 0 3.7-.5 5.6-.6 8.3-21.7 20.5-42.1 36.3-59.2 7.4-8 17.9-12.6 28.9-12.6 6.9 0 13.7 1.8 19.6 5.3l7.9 4.6c.8-.5 1.6-.9 2.4-1.4 7-14.6 11.2-30.8 11.2-48 0-61.9-50.1-112-112-112S208 82.1 208 144c0 61.9 50.1 112 112 112zm105.2 194.5c-2.3-1.2-4.6-2.6-6.8-3.9-8.2 4.8-15.3 9.8-27.5 9.8-10.9 0-21.4-4.6-28.9-12.6-18.3-19.8-32.3-43.9-40.2-69.6-10.7-34.5 24.9-49.7 25.8-50.3-.1-2.6-.1-5.2 0-7.8l-7.9-4.6c-3.8-2.2-7-5-9.8-8.1-3.3.2-6.5.6-9.8.6-24.6 0-47.6-6-68.5-16h-8.3C179.6 288 128 339.6 128 403.2V432c0 26.5 21.5 48 48 48h255.4c-3.7-6-6.2-12.8-6.2-20.3v-9.2zM173.1 274.6C161.5 263.1 145.6 256 128 256H64c-35.3 0-64 28.7-64 64v32c0 17.7 14.3 32 32 32h65.9c6.3-47.4 34.9-87.3 75.2-109.4z" | ||||
|             /></svg | ||||
|           > | ||||
|           <span>{$_("user-groups")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("RUNNER:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/runners/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/runners/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/runners/" | ||||
|         > | ||||
|           <svg | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 24 24" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
| @@ -126,12 +63,12 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("TEAM:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/teams/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/teams/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/teams/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
| @@ -145,14 +82,35 @@ | ||||
|           <span>{$_("teams")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("ORGANIZATION:GET")} | ||||
|         <a | ||||
|           class:activenav={$router.path.includes("/orgs/")} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/orgs/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 24 24" | ||||
|             width="24" | ||||
|             height="24" | ||||
|             ><path fill="none" d="M0 0h24v24H0z" /> | ||||
|             <path | ||||
|               d="M17 19h2v-8h-6v8h2v-6h2v6zM3 19V4a1 1 0 0 1 1-1h14a1 1 0 0 1 1 1v5h2v10h1v2H2v-2h1zm4-8v2h2v-2H7zm0 4v2h2v-2H7zm0-8v2h2V7H7z" | ||||
|             /></svg | ||||
|           > | ||||
|           <span>{$_("orgs")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("DONOR:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path.includes("/donors/")} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path.includes("/donors/")} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/donors/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 24 24" | ||||
| @@ -168,12 +126,12 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("DONATION:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path.includes("/donations/")} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path.includes("/donations/")} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/donations/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 24 24" | ||||
| @@ -189,12 +147,12 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("TRACK:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/tracks/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/tracks/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/tracks/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
| @@ -210,12 +168,12 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("CARD:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/cards/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/cards/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/cards/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
| @@ -233,12 +191,12 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("SCAN:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/scans/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/scans/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/scans/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
| @@ -255,13 +213,13 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("CONTACT:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/contacts/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/contacts/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/contacts/" | ||||
|         > | ||||
|           <svg | ||||
|             fill="currentColor" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 24 24" | ||||
|             width="24" | ||||
| @@ -276,12 +234,12 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("STATION:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/scanstations/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/scanstations/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/scanstations/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
| @@ -298,12 +256,12 @@ | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("STATSCLIENT:GET")} | ||||
|         <a | ||||
|           class:bg-gray-100={$router.path === "/statsclients/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/statsclients/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/statsclients/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
| @@ -318,13 +276,55 @@ | ||||
|           <span>{$_("statsclients")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("USER:GET")} | ||||
|         <a | ||||
|         class:bg-gray-100={$router.path === "/settings/"} | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|           class:activenav={$router.path === "/users/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/users/" | ||||
|         > | ||||
|           <svg | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             width="24" | ||||
|             height="24" | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             viewBox="0 0 24 24" | ||||
|             ><path fill="none" d="M0 0h24v24H0z" /> | ||||
|             <path | ||||
|               d="M12 14v8H4a8 8 0 018-8zm0-1a6 6 0 110-12 6 6 0 010 12zm2.6 5.81a3.51 3.51 0 010-1.62l-1-.57 1-1.74 1 .58a3.5 3.5 0 011.4-.82V13.5h2v1.15a3.5 3.5 0 011.4.8l1-.57 1 1.74-1 .57a3.51 3.51 0 010 1.62l1 .57-1 1.74-1-.58a3.5 3.5 0 01-1.4.82v1.14h-2v-1.15a3.5 3.5 0 01-1.4-.8l-1 .57-1-1.74 1-.57zM18 17a1 1 0 100 2 1 1 0 000-2z" | ||||
|             /></svg | ||||
|           > | ||||
|           <span>{$_("users")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       {#if store.state.jwtinfo.userdetails.permissions.includes("USERGROUP:GET")} | ||||
|         <a | ||||
|           class:activenav={$router.path === "/groups/"} | ||||
|           class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|           href="/groups/" | ||||
|         > | ||||
|           <svg | ||||
|             class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|             fill="currentColor" | ||||
|             width="24" | ||||
|             height="24" | ||||
|             xmlns="http://www.w3.org/2000/svg" | ||||
|             viewBox="0 0 640 512" | ||||
|             ><path | ||||
|               fill="currentColor" | ||||
|               d="M610.5 341.3c2.6-14.1 2.6-28.5 0-42.6l25.8-14.9c3-1.7 4.3-5.2 3.3-8.5-6.7-21.6-18.2-41.2-33.2-57.4-2.3-2.5-6-3.1-9-1.4l-25.8 14.9c-10.9-9.3-23.4-16.5-36.9-21.3v-29.8c0-3.4-2.4-6.4-5.7-7.1-22.3-5-45-4.8-66.2 0-3.3.7-5.7 3.7-5.7 7.1v29.8c-13.5 4.8-26 12-36.9 21.3l-25.8-14.9c-2.9-1.7-6.7-1.1-9 1.4-15 16.2-26.5 35.8-33.2 57.4-1 3.3.4 6.8 3.3 8.5l25.8 14.9c-2.6 14.1-2.6 28.5 0 42.6l-25.8 14.9c-3 1.7-4.3 5.2-3.3 8.5 6.7 21.6 18.2 41.1 33.2 57.4 2.3 2.5 6 3.1 9 1.4l25.8-14.9c10.9 9.3 23.4 16.5 36.9 21.3v29.8c0 3.4 2.4 6.4 5.7 7.1 22.3 5 45 4.8 66.2 0 3.3-.7 5.7-3.7 5.7-7.1v-29.8c13.5-4.8 26-12 36.9-21.3l25.8 14.9c2.9 1.7 6.7 1.1 9-1.4 15-16.2 26.5-35.8 33.2-57.4 1-3.3-.4-6.8-3.3-8.5l-25.8-14.9zM496 368.5c-26.8 0-48.5-21.8-48.5-48.5s21.8-48.5 48.5-48.5 48.5 21.8 48.5 48.5-21.7 48.5-48.5 48.5zM96 224c35.3 0 64-28.7 64-64s-28.7-64-64-64-64 28.7-64 64 28.7 64 64 64zm224 32c1.9 0 3.7-.5 5.6-.6 8.3-21.7 20.5-42.1 36.3-59.2 7.4-8 17.9-12.6 28.9-12.6 6.9 0 13.7 1.8 19.6 5.3l7.9 4.6c.8-.5 1.6-.9 2.4-1.4 7-14.6 11.2-30.8 11.2-48 0-61.9-50.1-112-112-112S208 82.1 208 144c0 61.9 50.1 112 112 112zm105.2 194.5c-2.3-1.2-4.6-2.6-6.8-3.9-8.2 4.8-15.3 9.8-27.5 9.8-10.9 0-21.4-4.6-28.9-12.6-18.3-19.8-32.3-43.9-40.2-69.6-10.7-34.5 24.9-49.7 25.8-50.3-.1-2.6-.1-5.2 0-7.8l-7.9-4.6c-3.8-2.2-7-5-9.8-8.1-3.3.2-6.5.6-9.8.6-24.6 0-47.6-6-68.5-16h-8.3C179.6 288 128 339.6 128 403.2V432c0 26.5 21.5 48 48 48h255.4c-3.7-6-6.2-12.8-6.2-20.3v-9.2zM173.1 274.6C161.5 263.1 145.6 256 128 256H64c-35.3 0-64 28.7-64 64v32c0 17.7 14.3 32 32 32h65.9c6.3-47.4 34.9-87.3 75.2-109.4z" | ||||
|             /></svg | ||||
|           > | ||||
|           <span>{$_("user-groups")}</span> | ||||
|         </a> | ||||
|       {/if} | ||||
|       <a | ||||
|         class:activenav={$router.path === "/settings/"} | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|         href="/settings/" | ||||
|       > | ||||
|         <svg | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|           xmlns="http://www.w3.org/2000/svg" | ||||
|           viewBox="0 0 20 20" | ||||
|           fill="currentColor" | ||||
| @@ -338,12 +338,12 @@ | ||||
|         <span>{$_("settings")}</span> | ||||
|       </a> | ||||
|       <a | ||||
|         class:bg-gray-100={$router.path === "/about/"} | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|         class:activenav={$router.path === "/about/"} | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|         href="/about/" | ||||
|       > | ||||
|         <svg | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|           xmlns="http://www.w3.org/2000/svg" | ||||
|           fill="none" | ||||
|           stroke="currentColor" | ||||
| @@ -358,14 +358,14 @@ | ||||
|       </a> | ||||
|       <button | ||||
|         tabindex="0" | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-100 hover:text-gray-900" | ||||
|         class="flex items-center px-4 py-3 transition cursor-pointer group hover:bg-gray-200 hover:text-gray-900" | ||||
|         on:click={() => { | ||||
|           AuthService.authControllerLogout(); | ||||
|           logout(); | ||||
|         }} | ||||
|       > | ||||
|         <svg | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 text-gray-400 transition group-hover:text-gray-600" | ||||
|           class="flex-shrink-0 w-5 h-5 mr-2 transition group-hover:text-gray-600" | ||||
|           fill="currentColor" | ||||
|           width="24" | ||||
|           height="24" | ||||
| @@ -382,7 +382,7 @@ | ||||
|   </div> | ||||
|   <div class="ml-0 transition md:ml-60"> | ||||
|     <header | ||||
|       class="flex items-center justify-between w-full px-4 bg-white border-b h-14 md:hidden" | ||||
|       class="flex items-center w-full px-4 bg-white border-b h-14 md:hidden" | ||||
|     > | ||||
|       <button | ||||
|         on:click={() => { | ||||
| @@ -390,18 +390,15 @@ | ||||
|         }} | ||||
|         class="block btn btn-light md:hidden" | ||||
|       > | ||||
|         <span class="sr-only">Menu</span><svg | ||||
|           class="w-4 h-4" | ||||
|           xmlns="http://www.w3.org/2000/svg" | ||||
|           viewBox="0 0 20 20" | ||||
|           fill="currentcolor" | ||||
|           ><path | ||||
|             fill-rule="evenodd" | ||||
|             d="M3 5a1 1 0 011-1h12a1 1 0 110 2H4A1 1 0 013 5zm0 5a1 1 0 011-1h12a1 1 0 110 2H4a1 1 0 01-1-1zm0 5a1 1 0 011-1h12a1 1 0 110 2H4a1 1 0 01-1-1z" | ||||
|             clip-rule="evenodd" | ||||
|           /></svg | ||||
|         ></button | ||||
|         <span class="sr-only">Menu</span><svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke-width="1.5" stroke="currentColor" class="size-6"> | ||||
|           <path stroke-linecap="round" stroke-linejoin="round" d="M3.75 6.75h16.5M3.75 12h16.5m-16.5 5.25h16.5" /> | ||||
|         </svg> | ||||
|         </button | ||||
|       > | ||||
|       <span class="inline-block"> | ||||
|         <img src="/lfk-logo.png" alt="Logo" class="h-8 inline-block" /> | ||||
|         <span class="text-lg font-bold">LfK!Admin</span> | ||||
|       </span> | ||||
|     </header> | ||||
|     <Toaster position="top-right" /> | ||||
|     <slot> | ||||
|   | ||||
| @@ -3,18 +3,16 @@ | ||||
|   import { StatsService } from "@odit/lfk-client-js"; | ||||
|   import store from "../../store"; | ||||
|   import StatCard from "./StatCard.svelte"; | ||||
|   let navOpen = false; | ||||
|   const stats_promise = StatsService.statsControllerGet(); | ||||
| </script> | ||||
|  | ||||
| <div class="p-2 md:p-5 overflow-x-hidden"> | ||||
|   <h1 class="text-3xl leading-tight mb-4"> | ||||
|     {$_("dashboard-greeting")}, | ||||
|     <span class="text-blue-500" | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("dashboard-greeting")} <span class="text-blue-500" | ||||
|       >{store.state.jwtinfo.userdetails.firstname} | ||||
|       {store.state.jwtinfo.userdetails.lastname}</span | ||||
|     > | ||||
|   </h1> | ||||
|   </h4> | ||||
|   {#await stats_promise} | ||||
|     <div | ||||
|       class="bg-teal-lightest border-t-4 border-teal rounded-b text-teal-darkest px-4 py-3 shadow-md my-2" | ||||
| @@ -25,7 +23,7 @@ | ||||
|     </div> | ||||
|   {:then stats} | ||||
|     <div | ||||
|       class="grid gap-2 grid-cols-2 lg:grid-cols-3 xl:grid-cols-5 2xl:grid-cols-6 sm:gap-4" | ||||
|       class="grid gap-1 grid-cols-2 lg:grid-cols-3 xl:grid-cols-5 2xl:grid-cols-6 sm:gap-4" | ||||
|     > | ||||
|       <StatCard | ||||
|         title={$_("runners")} | ||||
|   | ||||
| @@ -7,13 +7,13 @@ | ||||
| </script> | ||||
|  | ||||
| <a {href}> | ||||
|   <div class="p-4 rounded-lg bg-white border border-grey-100"> | ||||
|   <div class="p-3 py-4 sm:p-4 rounded-lg bg-white border border-grey-100"> | ||||
|     <div class="flex flex-row items-center justify-between"> | ||||
|       <div class="flex flex-col"> | ||||
|         <div class="text-xs uppercase font-normal text-grey-500"> | ||||
|         <div class="text-md sm:text-xs uppercase font-normal text-grey-500"> | ||||
|           {title} | ||||
|         </div> | ||||
|         <div class="text-xl font-bold font-mono">{value}</div> | ||||
|         <div class="text-2xl sm:text-xl font-bold font-mono">{value}</div> | ||||
|       </div> | ||||
|       <slot /> | ||||
|     </div> | ||||
|   | ||||
| @@ -8,7 +8,7 @@ | ||||
|     RunnerService, | ||||
|   } from "@odit/lfk-client-js"; | ||||
|   import Select from "svelte-select"; | ||||
|   import { createEventDispatcher } from "svelte"; | ||||
|   import { createEventDispatcher, onMount } from "svelte"; | ||||
|   import toast from "svelte-french-toast"; | ||||
|   export let modal_open; | ||||
|   const dispatch = createEventDispatcher(); | ||||
| @@ -23,16 +23,6 @@ | ||||
|   $: runners = []; | ||||
|   $: is_fixed = false; | ||||
|   $: is_paid = false; | ||||
|   DonorService.donorControllerGetAll().then((val) => { | ||||
|     donors = val.map((r) => { | ||||
|       return { label: getDonorLabel(r), value: r }; | ||||
|     }); | ||||
|   }); | ||||
|   RunnerService.runnerControllerGetAll().then((val) => { | ||||
|     runners = val.map((r) => { | ||||
|       return { label: getDonorLabel(r), value: r }; | ||||
|     }); | ||||
|   }); | ||||
|   $: amount_input = 0; | ||||
|   $: processed_last_submit = true; | ||||
|   $: is_amount_valid = amount_input > 0; | ||||
| @@ -95,6 +85,7 @@ | ||||
|             amount_input = 0; | ||||
|             modal_open = false; | ||||
|             // | ||||
|             toast.dismiss(); | ||||
|             toast.success($_("donation_added")); | ||||
|             dispatch("created", { donations: [result] }); | ||||
|           }) | ||||
| @@ -107,6 +98,19 @@ | ||||
|       } | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   onMount(async () => { | ||||
|     donors = (await DonorService.donorControllerGetAll()).map( | ||||
|       (r) => { | ||||
|         return { label: getDonorLabel(r), value: r }; | ||||
|       } | ||||
|     ); | ||||
|     runners = (await RunnerService.runnerControllerGetAll()).map( | ||||
|       (r) => { | ||||
|         return { label: getDonorLabel(r), value: r }; | ||||
|       } | ||||
|     ); | ||||
|   }); | ||||
| </script> | ||||
|  | ||||
| {#if modal_open} | ||||
|   | ||||
| @@ -33,7 +33,7 @@ | ||||
|       toast.loading($_("updating-donation")); | ||||
|       const editable = Object.assign({}, original_data); | ||||
|       editable.donor = editable.donor.id; | ||||
|       editable.paidAmount = paid_amount_input * 100; | ||||
|       editable.paidAmount = Math.round(paid_amount_input * 100); | ||||
|       if (editable.responseType == "DISTANCEDONATION" || editable.runner) { | ||||
|         editable.runner = editable.runner.id; | ||||
|         DonationService.donationControllerPutDistance( | ||||
| @@ -46,7 +46,7 @@ | ||||
|             toast.dismiss(); | ||||
|  | ||||
|             toast.success($_("donation-updated")); | ||||
|             dispatch("created", { donation: response }); | ||||
|             dispatch("created", { donation: result }); | ||||
|           }) | ||||
|           .catch((err) => { | ||||
|             // | ||||
| @@ -61,7 +61,7 @@ | ||||
|             // | ||||
|             toast.dismiss(); | ||||
|             toast.success($_("donation-updated")); | ||||
|             dispatch("created", { donation: response }); | ||||
|             dispatch("created", { donation: result }); | ||||
|           }) | ||||
|           .catch((err) => { | ||||
|             // | ||||
|   | ||||
| @@ -6,6 +6,7 @@ | ||||
|     DonorService, | ||||
|     RunnerService, | ||||
|   } from "@odit/lfk-client-js"; | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   import PromiseError from "../base/PromiseError.svelte"; | ||||
|   import Select from "svelte-select"; | ||||
|   | ||||
| @@ -9,20 +9,20 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("donations")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("DONATION:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|     > | ||||
|       {$_("add-donation")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <DonationsOverview bind:current_donations bind:addDonations /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -5,7 +5,7 @@ | ||||
|  | ||||
| <div class="text-center items-center justify-center"> | ||||
|   <p class="mb-16 text-lg text-gray-500"> | ||||
|     <img class="m-auto" style="height:15rem" src={donations_empty} alt="" /> | ||||
|     <img class="m-auto mt-2" style="height:15rem" src={donations_empty} alt="" /> | ||||
|     <span class="font-bold">{$_("there-are-no-donations-yet")}</span><br /> | ||||
|     <span>{$_("add-your-fist-donation")}</span> | ||||
|   </p> | ||||
|   | ||||
| @@ -168,7 +168,7 @@ | ||||
|  | ||||
|   onMount(async () => { | ||||
|     let page = 0; | ||||
|     let pagesize = 100; | ||||
|     let pagesize = 300; | ||||
|     while (page >= 0) { | ||||
|       const donations = await DonationService.donationControllerGetAll( | ||||
|         page, | ||||
| @@ -186,7 +186,6 @@ | ||||
|  | ||||
|       dataLoaded = true; | ||||
|       page++; | ||||
|       pagesize += 100; | ||||
|     } | ||||
|   }); | ||||
| </script> | ||||
| @@ -196,9 +195,12 @@ | ||||
|   payment_modal_open={active_edits.length > 0} | ||||
|   paid_amount_input={(active_edits[0]?.paidAmount || 0) / 100} | ||||
|   on:created={(event) => { | ||||
|     current_donations[ | ||||
|       current_donations.findIndex((d) => d.id === event.detail.donation.id) | ||||
|     ].paidAmount = event.detail.donation.paidAmount; | ||||
|     current_donations = current_donations.map((d)=>{ | ||||
|       if(d.id === event.detail.donation.id){ | ||||
|         d.paidAmount = event.detail.donation.paidAmount; | ||||
|       } | ||||
|       return d; | ||||
|     }) | ||||
|     options.update((options) => ({ | ||||
|       ...options, | ||||
|       data: current_donations, | ||||
| @@ -229,7 +231,7 @@ | ||||
|       bind:value={searchvalue} | ||||
|       placeholder={$_("datatable.search")} | ||||
|       aria-label={$_("datatable.search")} | ||||
|       class="mb-4" | ||||
|       class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|     /> | ||||
|     <div | ||||
|       class="shadow border-b border-gray-200 sm:rounded-lg overflow-x-scroll" | ||||
|   | ||||
| @@ -6,12 +6,12 @@ | ||||
|   import PromiseError from "../base/PromiseError.svelte"; | ||||
|   import isEmail from "validator/es/lib/isEmail"; | ||||
|   import ConfirmDonorDeletion from "./ConfirmDonorDeletion.svelte"; | ||||
|   import toast from "svelte-french-toast"; | ||||
|   let data_loaded = false; | ||||
|   export let params; | ||||
|   $: delete_triggered = false; | ||||
|   $: original_data = {}; | ||||
|   $: editable = {}; | ||||
|   $: current_donations = []; | ||||
|   $: changes_performed = !( | ||||
|     JSON.stringify(original_data) === JSON.stringify(editable) | ||||
|   ); | ||||
| @@ -28,11 +28,6 @@ | ||||
|     isPhoneValidOrEmpty && | ||||
|     ((isAddress1Valid && iszipcodevalid && iscityvalid) || | ||||
|       editable.address_checked === false); | ||||
|   const donation_promise = DonationService.donationControllerGetAll().then( | ||||
|     (val) => { | ||||
|       current_donations = val; | ||||
|     } | ||||
|   ); | ||||
|   const promise = DonorService.donorControllerGetOne(params.donorid).then( | ||||
|     (data) => { | ||||
|       data_loaded = true; | ||||
| @@ -68,7 +63,9 @@ | ||||
|         editable.address = null; | ||||
|       } | ||||
|       if (editable.email) editable.email = editable.email; | ||||
|       else editable.email = null; | ||||
|       if (editable.phone) editable.phone = editable.phone; | ||||
|       else editable.phone = null; | ||||
|       if (editable.middlename) editable.middlename = editable.middlename; | ||||
|       editable.receiptNeeded = editable.address_checked; | ||||
|       DonorService.donorControllerPut(original_data.id, editable) | ||||
| @@ -95,7 +92,7 @@ | ||||
| </script> | ||||
|  | ||||
| <ConfirmDonorDeletion bind:modal_open bind:delete_donor /> | ||||
| {#await promise && donation_promise} | ||||
| {#await promise} | ||||
|   {$_("loading-donor-details")} | ||||
| {:then} | ||||
|   <section class="container p-5 select-none"> | ||||
| @@ -205,8 +202,8 @@ | ||||
|       > | ||||
|       <br /> | ||||
|       <span class="font-medium text-gray-700">{$_("donations")}:</span> | ||||
|       {#if current_donations.filter((d) => d.donor.id == editable.id).length > 0} | ||||
|         {#each current_donations.filter((o) => o.donor.id == editable.id) as d} | ||||
|       {#if original_data.donations.length > 0} | ||||
|         {#each original_data.donations as d} | ||||
|           {#if d.responseType === "DISTANCEDONATION"} | ||||
|             <a | ||||
|               href="../donations/{d.id}" | ||||
|   | ||||
| @@ -9,15 +9,16 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("donors")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("DONOR:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("add-donor")} | ||||
|     </button> | ||||
| @@ -35,7 +36,7 @@ | ||||
|               d.firstname, | ||||
|               d.middlename, | ||||
|               d.lastname, | ||||
|                 d.paidDonationAmount, | ||||
|               (d.paidDonationAmount/100).toFixed(2), | ||||
|               address, | ||||
|             ]; | ||||
|           }); | ||||
| @@ -58,12 +59,11 @@ | ||||
|         hiddenElement.remove(); | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("sponsoring-quittungs-liste_herunterladen")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <DonorsOverview bind:current_donors bind:addDonors /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -147,7 +147,7 @@ | ||||
|  | ||||
|   onMount(async () => { | ||||
|     let page = 0; | ||||
|     let pagesize = 100; | ||||
|     let pagesize = 300; | ||||
|     while (page >= 0) { | ||||
|       const donors = await DonorService.donorControllerGetAll(page, pagesize); | ||||
|       if (donors.length == 0) { | ||||
| @@ -162,7 +162,6 @@ | ||||
|  | ||||
|       dataLoaded = true; | ||||
|       page++; | ||||
|       pagesize += 100; | ||||
|     } | ||||
|   }); | ||||
| </script> | ||||
| @@ -203,7 +202,7 @@ | ||||
|       bind:value={searchvalue} | ||||
|       placeholder={$_("datatable.search")} | ||||
|       aria-label={$_("datatable.search")} | ||||
|       class="mb-4" | ||||
|       class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|     /> | ||||
|     <div | ||||
|       class="shadow border-b border-gray-200 sm:rounded-lg overflow-x-scroll" | ||||
|   | ||||
| @@ -2,7 +2,7 @@ | ||||
| 	import { _ } from "svelte-i18n"; | ||||
| 	import { clickOutside } from "../base/outsideclick"; | ||||
|  | ||||
|   export let modal_open; | ||||
| 	let modal_open = false; | ||||
| 	(function () { | ||||
| 		document.onkeydown = function (e) { | ||||
| 			e = e || window.event; | ||||
| @@ -31,7 +31,7 @@ | ||||
| 		}} | ||||
| 	> | ||||
| 		<div | ||||
|       class="flex items-end justify-center min-h-screen pt-4 px-4 pb-20 text-center sm:block sm:p-0" | ||||
| 			class="flex items-end justify-center min-h-screen pt-4 px-4 pb-20 sm:block sm:p-0" | ||||
| 		> | ||||
| 			<div class="fixed inset-0 transition-opacity" aria-hidden="true"> | ||||
| 				<div | ||||
| @@ -67,7 +67,7 @@ | ||||
| 								/></svg | ||||
| 							> | ||||
| 						</div> | ||||
|             <div class="mt-3 text-center sm:mt-0 sm:ml-4 sm:text-left"> | ||||
| 						<div class="mt-3 sm:mt-0 sm:ml-4 sm:text-left"> | ||||
| 							<h3 class="text-lg leading-6 font-medium"> | ||||
| 								{$_("read-license")} | ||||
| 							</h3> | ||||
| @@ -86,7 +86,7 @@ | ||||
| 							modal_open = false; | ||||
| 						}} | ||||
| 						type="button" | ||||
|             class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
| 						class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
| 					> | ||||
| 						{$_("close")} | ||||
| 					</button> | ||||
| @@ -96,41 +96,28 @@ | ||||
| 	</div> | ||||
| {/if} | ||||
| <!-- /// --> | ||||
| <div class="pt-12 px-4 sm:px-6 lg:px-8 lg:pt-20 bg-gray-900 pb-12"> | ||||
|   <div class="text-center mb-8"> | ||||
|     <h1 | ||||
|       class="mt-9 font-display text-4xl leading-none font-semibold text-white sm:text-5xl lg:text-6xl" | ||||
|     > | ||||
| <section class="container p-5"> | ||||
| 	<h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
| 		{$_("about")} | ||||
|       🧾 | ||||
|     </h1> | ||||
|     <p | ||||
|       class="mt-2 max-w-xl mx-auto text-xl lg:max-w-3xl lg:text-2xl text-gray-300" | ||||
|     > | ||||
| 	</h4> | ||||
| 	<p class="mt-2 mb-2"> | ||||
| 		Lauf für Kaya! | ||||
|       <strong class="text-white font-medium"> | ||||
| 		<strong class="font-medium"> | ||||
| 			{$_("by")} | ||||
| 			<a href="https://odit.services" class="underline">ODIT.Services</a> | ||||
| 		</strong> | ||||
| 		<br /> | ||||
|       <span class="text-lg">{$_("lfk-is-os")}</span> | ||||
| 		<span>{$_("lfk-is-os")}</span> | ||||
| 	</p> | ||||
|   </div> | ||||
| </div> | ||||
|  | ||||
| <div class="pt-0 pb-16 overflow-hidden lg:pt-12 lg:py-24"> | ||||
|   <div class="max-w-7xl mx-auto py-6 px-4 sm:px-6 lg:px-8"> | ||||
|     <h2 class="text-4xl font-display font-semibold md:text-5xl"> | ||||
| 	<h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
| 		{$_("credits")} | ||||
|     </h2> | ||||
|     <div class="max-w-3xl mx-auto text-xl leading-8 font-medium mt-8"> | ||||
|       <p class="text-center">{$_("oss_credit_description")}</p> | ||||
|     </div> | ||||
|     <div class="w-screen leading-8 pl-5 mt-5"> | ||||
| 	</h4> | ||||
| 	<p class="text-left">{$_("oss_credit_description")}</p> | ||||
| 	<div class="mt-5 overflow-x-auto"> | ||||
| 		{#await license_promise} | ||||
|         <p class="text-center w-full">{$_("licenses-are-being-loaded")}</p> | ||||
| 			<p>{$_("licenses-are-being-loaded")}</p> | ||||
| 		{:then} | ||||
|         <table> | ||||
| 			<table class="font-mono"> | ||||
| 				<thead class="border-b border-gray-400"> | ||||
| 					<tr class="odd:bg-white even:bg-gray-100"> | ||||
| 						<th>{$_("dependency_name")}</th> | ||||
| @@ -142,17 +129,17 @@ | ||||
| 				</thead> | ||||
| 				<tbody> | ||||
| 					{#each licenses as l} | ||||
|               <tr class="odd:bg-white even:bg-gray-100"> | ||||
| 						<tr class="odd:bg-white even:bg-gray-100 *:p-2"> | ||||
| 							<td>{l.name}</td> | ||||
| 							<td> | ||||
|                   {l.license || "?"}<br /><button | ||||
| 								<button | ||||
| 									class="underline cursor-pointer" | ||||
| 									on:click={() => { | ||||
| 										modal_open = true; | ||||
| 										currentlicense = l.name + "@" + l.version; | ||||
| 										licensetext = | ||||
| 											l.licensetext || $_("no-license-text-could-be-found"); | ||||
|                     }}>{$_("read-license")}</button | ||||
| 									}}>{l.license || "?"}</button | ||||
| 								> | ||||
| 							</td> | ||||
| 							<td> | ||||
| @@ -177,9 +164,9 @@ | ||||
| 			</div> | ||||
| 		{/await} | ||||
| 	</div> | ||||
|     <div class="w-full leading-8 mt-8"> | ||||
|       <p class="text-xl font-medium">{$_("icon-image-credits")}</p> | ||||
|       <ul class="list-disc"> | ||||
| 	<div class="w-full mt-8"> | ||||
| 		<p class="font-medium">{$_("icon-image-credits")}</p> | ||||
| 		<ul class="list-disc ml-6"> | ||||
| 			<li> | ||||
| 				<a | ||||
| 					class="underline" | ||||
| @@ -206,5 +193,4 @@ | ||||
| 			</li> | ||||
| 		</ul> | ||||
| 	</div> | ||||
|   </div> | ||||
| </div> | ||||
| </section> | ||||
|   | ||||
| @@ -2,6 +2,7 @@ | ||||
|   import { _ } from "svelte-i18n"; | ||||
|   import store from "../../store"; | ||||
|   import { UserGroupService } from "@odit/lfk-client-js"; | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   import PromiseError from "../base/PromiseError.svelte"; | ||||
|   let data_loaded = false; | ||||
| @@ -131,7 +132,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteGroup} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-deletion")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -148,7 +149,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-group")}</button | ||||
|             > | ||||
|           {/if} | ||||
| @@ -159,7 +160,7 @@ | ||||
|             class:opacity-50={!save_enabled} | ||||
|             type="button" | ||||
|             on:click={submit} | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
|   | ||||
| @@ -5,6 +5,7 @@ | ||||
|     CreatePermission, | ||||
|     UserGroupService, | ||||
|   } from "@odit/lfk-client-js"; | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   import PromiseError from "../base/PromiseError.svelte"; | ||||
|   export let params; | ||||
| @@ -142,13 +143,13 @@ | ||||
|             class:opacity-50={save_enabled} | ||||
|             type="button" | ||||
|             on:click={submit} | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {:else} | ||||
|           <button | ||||
|             type="button" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-yellow-600 text-base font-medium text-white hover:bg-yellow-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-yellow-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-yellow-600 text-base font-medium text-white hover:bg-yellow-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-yellow-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("applying-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
| @@ -192,7 +193,7 @@ | ||||
|                       } | ||||
|                     }} | ||||
|                     type="button" | ||||
|                     class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-green-200 text-base font-medium text-black hover:bg-green-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-green-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|                     class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-green-200 text-base font-medium text-black hover:bg-green-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-green-500 sm:w-auto sm:text-sm" | ||||
|                     >+</button | ||||
|                   > | ||||
|                 </p> | ||||
| @@ -232,7 +233,7 @@ | ||||
|                     } | ||||
|                   }} | ||||
|                   type="button" | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-300 text-base font-medium text-black hover:bg-red-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-300 text-base font-medium text-black hover:bg-red-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500 sm:w-auto sm:text-sm" | ||||
|                   >-</button | ||||
|                 > | ||||
|               </p> | ||||
|   | ||||
| @@ -8,20 +8,20 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("user-groups")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("USERGROUP:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|     > | ||||
|       {$_("add-user-group")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <UserGroupsOverview bind:current_groups /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -31,7 +31,7 @@ | ||||
|         bind:value={searchvalue} | ||||
|         placeholder={$_("datatable.search")} | ||||
|         aria-label={$_("datatable.search")} | ||||
|         class="mb-4" | ||||
|         class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|       /> | ||||
|       <div | ||||
|         class="shadow border-b border-gray-200 sm:rounded-lg overflow-x-scroll" | ||||
|   | ||||
| @@ -4,6 +4,7 @@ | ||||
|     RunnerOrganizationService, | ||||
|   } from "@odit/lfk-client-js"; | ||||
|   import { getLocaleFromNavigator, _ } from "svelte-i18n"; | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   import store from "../../store"; | ||||
|   import ConfirmOrgDeletion from "./ConfirmOrgDeletion.svelte"; | ||||
| @@ -37,7 +38,7 @@ | ||||
|   $: cards_show = true; | ||||
|   $: certificates_show = true; | ||||
|   $: generate_orgs = [original_object]; | ||||
|   $: registrationLink = `${config.baseurl}/selfservice/register/${editable.registrationKey}`; | ||||
|   $: registrationLink = `${config.baseurl_selfservice}/register/${editable.registrationKey}`; | ||||
|   const getContactLabel = (option) => | ||||
|     option.firstname + " " + (option.middlename || "") + " " + option.lastname; | ||||
|   const promise = RunnerOrganizationService.runnerOrganizationControllerGetOne( | ||||
| @@ -162,7 +163,7 @@ | ||||
|               import_modal_open = true; | ||||
|             }} | ||||
|             type="button" | ||||
|             class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|           > | ||||
|             {$_("import-runners")} | ||||
|           </button> | ||||
| @@ -171,7 +172,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteOrganization} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-delete")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -188,7 +189,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-organization")}</button | ||||
|             > | ||||
|           {/if} | ||||
| @@ -199,7 +200,7 @@ | ||||
|             disabled={!save_enabled} | ||||
|             class:opacity-50={!save_enabled} | ||||
|             type="button" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
| @@ -470,6 +471,11 @@ | ||||
|             {/if} | ||||
|           </div> | ||||
|         {/if} | ||||
|         <div class="text-sm w-full"> | ||||
|           <span class="font-medium text-gray-700">{$_("distance")}</span> | ||||
|           <br /> | ||||
|           <span class="text-gray-700">{(original_object.total_distance / 1000).toFixed(2)} km</span> | ||||
|         </div> | ||||
|       </div> | ||||
|     </div> | ||||
|   </section> | ||||
|   | ||||
| @@ -58,7 +58,7 @@ | ||||
|         bind:value={searchvalue} | ||||
|         placeholder={$_("datatable.search")} | ||||
|         aria-label={$_("datatable.search")} | ||||
|         class="mb-4" | ||||
|         class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|       /> | ||||
|       <div class="h-12"> | ||||
|         <GenerateSponsoringContracts | ||||
|   | ||||
| @@ -10,15 +10,16 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("organizations")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("ORGANIZATION:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("create-organization")} | ||||
|     </button> | ||||
| @@ -29,12 +30,11 @@ | ||||
|         import_modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("import-runners")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <OrgOverview bind:current_organizations /> | ||||
| </section> | ||||
|  | ||||
| @@ -48,7 +48,6 @@ | ||||
|     passed_org={{}} | ||||
|     passed_orgs={current_organizations} | ||||
|     opened_from="OrgOverview" | ||||
|     current_runners={[]} | ||||
|     bind:import_modal_open | ||||
|   /> | ||||
| {/if} | ||||
|   | ||||
| @@ -5,6 +5,7 @@ | ||||
|     RunnerOrganizationService, | ||||
|     RunnerTeamService, | ||||
|   } from "@odit/lfk-client-js"; | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   import { init } from "@paralleldrive/cuid2"; | ||||
|   const createId = init({ length: 10, fingerprint: "lfk-frontend" }); | ||||
|   | ||||
| @@ -5,8 +5,8 @@ | ||||
|     RunnerTeamService, | ||||
|     RunnerOrganizationService, | ||||
|   } from "@odit/lfk-client-js"; | ||||
|  | ||||
|   import { init } from "@paralleldrive/cuid2"; | ||||
|   import toast from "svelte-french-toast"; | ||||
|   const createId = init({ length: 10, fingerprint: "lfk-frontend" }); | ||||
|  | ||||
|   export let certificates_show = false; | ||||
|   | ||||
| @@ -12,6 +12,7 @@ | ||||
|   import Select from "svelte-select"; | ||||
|   import { createEventDispatcher } from "svelte"; | ||||
|   const dispatch = createEventDispatcher(); | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   export let modal_open; | ||||
|   $: selected_team = undefined; | ||||
|   | ||||
| @@ -149,7 +149,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteRunner} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-deletion")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -175,7 +175,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-runner")}</button | ||||
|             > | ||||
|           {/if} | ||||
| @@ -186,7 +186,7 @@ | ||||
|             class:opacity-50={!save_enabled} | ||||
|             type="button" | ||||
|             on:click={submit} | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
|   | ||||
| @@ -11,15 +11,16 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("runners")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("RUNNER:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("laeufer-hinzufuegen")} | ||||
|     </button> | ||||
| @@ -28,12 +29,11 @@ | ||||
|         import_modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm mt-1 sm:mt-0" | ||||
|     > | ||||
|       {$_("import-runners")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <RunnersOverview bind:current_runners bind:addRunners /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -9,20 +9,20 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("scans")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("SCAN:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|     > | ||||
|       {$_("add-scan")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <ScansOverview bind:current_scans bind:addScans /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -5,7 +5,7 @@ | ||||
|  | ||||
| <div class="text-center items-center justify-center"> | ||||
|   <p class="mb-16 text-lg text-gray-500"> | ||||
|     <img class="m-auto" style="height:15rem" src={scans_empty} alt="" /> | ||||
|     <img class="m-auto mt-2" style="height:15rem" src={scans_empty} alt="" /> | ||||
|     <span class="font-bold">{$_("there-are-no-scans-yet")}</span><br /> | ||||
|     <span>{$_("add-your-fist-scan")}</span> | ||||
|   </p> | ||||
|   | ||||
| @@ -179,7 +179,7 @@ | ||||
|  | ||||
|   onMount(async () => { | ||||
|     let page = 0; | ||||
|     let pagesize = 100; | ||||
|     let pagesize = 500; | ||||
|     while (page >= 0) { | ||||
|       const scans = await ScanService.scanControllerGetAll(page, pagesize); | ||||
|       if (scans.length == 0) { | ||||
| @@ -194,9 +194,6 @@ | ||||
|  | ||||
|       dataLoaded = true; | ||||
|       page++; | ||||
|       if (pagesize < 1000) { | ||||
|         pagesize += 100; | ||||
|       } | ||||
|     } | ||||
|   }); | ||||
| </script> | ||||
| @@ -223,7 +220,7 @@ | ||||
|     {#if selected.length > 0} | ||||
|       <button | ||||
|         type="button" | ||||
|         class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm inline-flex" | ||||
|         class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm inline-flex" | ||||
|         id="options-menu" | ||||
|         on:click={async () => { | ||||
|           const prom = []; | ||||
|   | ||||
| @@ -1,12 +1,11 @@ | ||||
| <script> | ||||
| 	import { _ } from "svelte-i18n"; | ||||
|  | ||||
|   import { tick, createEventDispatcher } from "svelte"; | ||||
| 	import { tick } from "svelte"; | ||||
| 	import bwipjs from "bwip-js"; | ||||
| 	import toast from "svelte-french-toast"; | ||||
|  | ||||
| 	export let copy_modal_open; | ||||
| 	export let new_station; | ||||
|   const dispatch = createEventDispatcher(); | ||||
| 	let valueCopy = null; | ||||
| 	let areaDom; | ||||
| 	let copied = false; | ||||
|   | ||||
| @@ -111,7 +111,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteStation} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-deletion")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -128,7 +128,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-station")}</button | ||||
|             > | ||||
|           {/if} | ||||
| @@ -139,7 +139,7 @@ | ||||
|             class:opacity-50={!save_enabled} | ||||
|             type="button" | ||||
|             on:click={submit} | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
|   | ||||
| @@ -1,36 +1,221 @@ | ||||
| <script> | ||||
| 	import { _ } from "svelte-i18n"; | ||||
| 	import store from "../../store"; | ||||
| 	import { ScanStationService } from "@odit/lfk-client-js"; | ||||
| 	import AddScanStationModal from "./AddScanStationModal.svelte"; | ||||
| 	import CopyScanStationTokenModal from "./CopyScanStationTokenModal.svelte"; | ||||
|   import ScanStationsOverview from "./ScanStationsOverview.svelte"; | ||||
| 	import ScanStationsEmptyState from "./ScanStationsEmptyState.svelte"; | ||||
| 	import ConfirmScanStationDeletion from "./ConfirmScanStationDeletion.svelte"; | ||||
| 	import toast from "svelte-french-toast"; | ||||
| 	// | ||||
| 	export let modal_open = false; | ||||
| 	export let copy_modal_open = false; | ||||
| 	export let new_station = {}; | ||||
| 	// | ||||
| 	const promise = ScanStationService.scanStationControllerGetAll().then( | ||||
| 		(result) => { | ||||
| 			current_stations = result; | ||||
| 		} | ||||
| 	); | ||||
| 	$: searchvalue = ""; | ||||
| 	$: active_deletes = []; | ||||
| 	let delete_station = {}; | ||||
| 	let current_stations = []; | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
| 	<h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
| 		{$_("scanstations")} | ||||
| 	</h4> | ||||
| 	{#if store.state.jwtinfo.userdetails.permissions.includes("STATION:CREATE")} | ||||
| 		<button | ||||
| 			on:click={() => { | ||||
| 				modal_open = true; | ||||
| 			}} | ||||
| 			type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
| 			class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
| 		> | ||||
| 			{$_("create-a-new-scanstation")} | ||||
| 		</button> | ||||
| 	{/if} | ||||
|   </span> | ||||
|   <ScanStationsOverview | ||||
|     bind:current_stations | ||||
| 	<ConfirmScanStationDeletion | ||||
| 		on:cancelDelete={(event) => { | ||||
| 			modal_open = false; | ||||
| 			active_deletes[event.detail.id] = false; | ||||
| 		}} | ||||
| 		bind:modal_open | ||||
|     bind:new_station | ||||
|     bind:copy_modal_open | ||||
| 		bind:delete_station | ||||
| 	/> | ||||
| 	{#if store.state.jwtinfo.userdetails.permissions.includes("STATION:GET")} | ||||
| 		{#await promise} | ||||
| 			<div | ||||
| 				class="bg-teal-lightest border-t-4 border-teal rounded-b text-teal-darkest px-4 py-3 shadow-md my-2" | ||||
| 				role="alert" | ||||
| 			> | ||||
| 				<p class="font-bold">{$_("scanstations-are-being-loaded")}</p> | ||||
| 				<p class="text-sm">{$_("this-might-take-a-moment")}</p> | ||||
| 			</div> | ||||
| 		{:then} | ||||
| 			{#if current_stations.length === 0} | ||||
| 				<ScanStationsEmptyState /> | ||||
| 			{:else} | ||||
| 				<input | ||||
| 					type="search" | ||||
| 					bind:value={searchvalue} | ||||
| 					placeholder={$_("datatable.search")} | ||||
| 					aria-label={$_("datatable.search")} | ||||
| 					class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
| 				/> | ||||
| 				<div | ||||
| 					class="shadow border-b border-gray-200 sm:rounded-lg overflow-x-scroll" | ||||
| 				> | ||||
| 					<table class="divide-y divide-gray-200 w-full"> | ||||
| 						<thead class="bg-gray-50"> | ||||
| 							<tr class="odd:bg-white even:bg-gray-100"> | ||||
| 								<th | ||||
| 									scope="col" | ||||
| 									class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider" | ||||
| 								> | ||||
| 									{$_("track")} | ||||
| 								</th> | ||||
| 								<th | ||||
| 									scope="col" | ||||
| 									class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider" | ||||
| 								> | ||||
| 									{$_("description")} | ||||
| 								</th> | ||||
| 								<th | ||||
| 									scope="col" | ||||
| 									class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider" | ||||
| 								> | ||||
| 									{$_("status")} | ||||
| 								</th> | ||||
| 								<th scope="col" class="relative px-6 py-3"> | ||||
| 									<span class="sr-only">{$_("action")}</span> | ||||
| 								</th> | ||||
| 							</tr> | ||||
| 						</thead> | ||||
| 						<tbody class="divide-y divide-gray-200"> | ||||
| 							{#each current_stations as s} | ||||
| 								{#if Object.values(s) | ||||
| 									.toString() | ||||
| 									.toLowerCase() | ||||
| 									.includes(searchvalue)} | ||||
| 									<tr | ||||
| 										class="odd:bg-white even:bg-gray-100" | ||||
| 										data-rowid="station_{s.id}" | ||||
| 									> | ||||
| 										<td class="px-6 py-4 whitespace-nowrap"> | ||||
| 											<div class="flex items-center"> | ||||
| 												<div class="ml-4"> | ||||
| 													<div class="text-sm font-medium text-gray-900"> | ||||
| 														<a | ||||
| 															href="../tracks" | ||||
| 															class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-gray-100 text-gray-800" | ||||
| 														> | ||||
| 															{s.track.name || s.track.distance + "m"}</a | ||||
| 														> | ||||
| 													</div> | ||||
| 												</div> | ||||
| 											</div> | ||||
| 										</td> | ||||
| 										<td class="px-6 py-4 whitespace-nowrap"> | ||||
| 											<div class="flex items-center"> | ||||
| 												<div class="ml-4"> | ||||
| 													<div class="text-sm font-medium text-gray-900"> | ||||
| 														{s.description} | ||||
| 													</div> | ||||
| 												</div> | ||||
| 											</div> | ||||
| 										</td> | ||||
| 										<td class="px-6 py-4 whitespace-nowrap"> | ||||
| 											<div class="flex items-center"> | ||||
| 												{#if s.enabled} | ||||
| 													<span | ||||
| 														class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-green-100 text-green-800" | ||||
| 														>{$_("active")}</span | ||||
| 													> | ||||
| 												{:else} | ||||
| 													<span | ||||
| 														class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-red-100 text-red-800" | ||||
| 														>{$_("inactive")}</span | ||||
| 													> | ||||
| 												{/if} | ||||
| 											</div> | ||||
| 										</td> | ||||
| 										{#if active_deletes[s.id] === true} | ||||
| 											<td | ||||
| 												class="px-6 py-4 whitespace-nowrap text-right text-sm font-medium" | ||||
| 											> | ||||
| 												<button | ||||
| 													on:click={() => { | ||||
| 														active_deletes[s.id] = false; | ||||
| 													}} | ||||
| 													tabindex="0" | ||||
| 													class="ml-4 text-indigo-600 hover:text-indigo-900 cursor-pointer" | ||||
| 													>{$_("cancel-delete")}</button | ||||
| 												> | ||||
| 												<button | ||||
| 													on:click={() => { | ||||
| 														ScanStationService.scanStationControllerRemove( | ||||
| 															s.id, | ||||
| 															false | ||||
| 														) | ||||
| 															.then((resp) => { | ||||
| 																current_stations = current_stations.filter( | ||||
| 																	(obj) => obj.id !== s.id | ||||
| 																); | ||||
| 																toast($_("station-deleted")); | ||||
| 															}) | ||||
| 															.catch((err) => { | ||||
| 																modal_open = true; | ||||
| 																delete_station = s; | ||||
| 															}); | ||||
| 													}} | ||||
| 													tabindex="0" | ||||
| 													class="ml-4 text-red-600 hover:text-red-900 cursor-pointer" | ||||
| 													>{$_("confirm-delete")}</button | ||||
| 												> | ||||
| 											</td> | ||||
| 										{:else} | ||||
| 											<td | ||||
| 												class="px-6 py-4 whitespace-nowrap text-right text-sm font-medium" | ||||
| 											> | ||||
| 												<a | ||||
| 													href="/scanstations/{s.id}" | ||||
| 													class="text-indigo-600 hover:text-indigo-900" | ||||
| 													>{$_("details")}</a | ||||
| 												> | ||||
| 												{#if store.state.jwtinfo.userdetails.permissions.includes("STATION:DELETE")} | ||||
| 													<button | ||||
| 														on:click={() => { | ||||
| 															active_deletes[s.id] = true; | ||||
| 														}} | ||||
| 														tabindex="0" | ||||
| 														class="ml-4 text-red-600 hover:text-red-900 cursor-pointer" | ||||
| 														>{$_("delete")}</button | ||||
| 													> | ||||
| 												{/if} | ||||
| 											</td> | ||||
| 										{/if} | ||||
| 									</tr> | ||||
| 								{/if} | ||||
| 							{/each} | ||||
| 						</tbody> | ||||
| 					</table> | ||||
| 				</div> | ||||
| 			{/if} | ||||
| 		{:catch error} | ||||
| 			<div | ||||
| 				class="text-white px-6 py-4 border-0 rounded relative mb-4 bg-red-500" | ||||
| 			> | ||||
| 				<span class="inline-block align-middle mr-8"> | ||||
| 					<b class="capitalize">{$_("general_promise_error")}</b> | ||||
| 					{error} | ||||
| 				</span> | ||||
| 			</div> | ||||
| 		{/await} | ||||
| 	{/if} | ||||
| </section> | ||||
|  | ||||
| {#if store.state.jwtinfo.userdetails.permissions.includes("STATION:CREATE")} | ||||
|   | ||||
| @@ -1,195 +0,0 @@ | ||||
| <script> | ||||
|   import { _ } from "svelte-i18n"; | ||||
|   import { ScanStationService } from "@odit/lfk-client-js"; | ||||
|   const promise = ScanStationService.scanStationControllerGetAll().then( | ||||
|     (result) => { | ||||
|       current_stations = result; | ||||
|     } | ||||
|   ); | ||||
|   import store from "../../store"; | ||||
|   import ScanStationsEmptyState from "./ScanStationsEmptyState.svelte"; | ||||
|   import ConfirmScanStationDeletion from "./ConfirmScanStationDeletion.svelte"; | ||||
|   import toast from "svelte-french-toast"; | ||||
|   $: searchvalue = ""; | ||||
|   $: active_deletes = []; | ||||
|   let delete_station = {}; | ||||
|   let modal_open = false; | ||||
|   export let current_stations = []; | ||||
| </script> | ||||
|  | ||||
| <ConfirmScanStationDeletion | ||||
|   on:cancelDelete={(event) => { | ||||
|     modal_open = false; | ||||
|     active_deletes[event.detail.id] = false; | ||||
|   }} | ||||
|   bind:modal_open | ||||
|   bind:delete_station | ||||
| /> | ||||
| {#if store.state.jwtinfo.userdetails.permissions.includes("STATION:GET")} | ||||
|   {#await promise} | ||||
|     <div | ||||
|       class="bg-teal-lightest border-t-4 border-teal rounded-b text-teal-darkest px-4 py-3 shadow-md my-2" | ||||
|       role="alert" | ||||
|     > | ||||
|       <p class="font-bold">{$_("scanstations-are-being-loaded")}</p> | ||||
|       <p class="text-sm">{$_("this-might-take-a-moment")}</p> | ||||
|     </div> | ||||
|   {:then} | ||||
|     {#if current_stations.length === 0} | ||||
|       <ScanStationsEmptyState /> | ||||
|     {:else} | ||||
|       <input | ||||
|         type="search" | ||||
|         bind:value={searchvalue} | ||||
|         placeholder={$_("datatable.search")} | ||||
|         aria-label={$_("datatable.search")} | ||||
|         class="mb-4" | ||||
|       /> | ||||
|       <div | ||||
|         class="shadow border-b border-gray-200 sm:rounded-lg overflow-x-scroll" | ||||
|       > | ||||
|         <table class="divide-y divide-gray-200 w-full"> | ||||
|           <thead class="bg-gray-50"> | ||||
|             <tr class="odd:bg-white even:bg-gray-100"> | ||||
|               <th | ||||
|                 scope="col" | ||||
|                 class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider" | ||||
|               > | ||||
|                 {$_("track")} | ||||
|               </th> | ||||
|               <th | ||||
|                 scope="col" | ||||
|                 class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider" | ||||
|               > | ||||
|                 {$_("description")} | ||||
|               </th> | ||||
|               <th | ||||
|                 scope="col" | ||||
|                 class="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider" | ||||
|               > | ||||
|                 {$_("status")} | ||||
|               </th> | ||||
|               <th scope="col" class="relative px-6 py-3"> | ||||
|                 <span class="sr-only">{$_("action")}</span> | ||||
|               </th> | ||||
|             </tr> | ||||
|           </thead> | ||||
|           <tbody class="divide-y divide-gray-200"> | ||||
|             {#each current_stations as s} | ||||
|               {#if Object.values(s) | ||||
|                 .toString() | ||||
|                 .toLowerCase() | ||||
|                 .includes(searchvalue)} | ||||
|                 <tr | ||||
|                   class="odd:bg-white even:bg-gray-100" | ||||
|                   data-rowid="station_{s.id}" | ||||
|                 > | ||||
|                   <td class="px-6 py-4 whitespace-nowrap"> | ||||
|                     <div class="flex items-center"> | ||||
|                       <div class="ml-4"> | ||||
|                         <div class="text-sm font-medium text-gray-900"> | ||||
|                           <a | ||||
|                             href="../tracks" | ||||
|                             class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-gray-100 text-gray-800" | ||||
|                           > | ||||
|                             {s.track.name || s.track.distance + "m"}</a | ||||
|                           > | ||||
|                         </div> | ||||
|                       </div> | ||||
|                     </div> | ||||
|                   </td> | ||||
|                   <td class="px-6 py-4 whitespace-nowrap"> | ||||
|                     <div class="flex items-center"> | ||||
|                       <div class="ml-4"> | ||||
|                         <div class="text-sm font-medium text-gray-900"> | ||||
|                           {s.description} | ||||
|                         </div> | ||||
|                       </div> | ||||
|                     </div> | ||||
|                   </td> | ||||
|                   <td class="px-6 py-4 whitespace-nowrap"> | ||||
|                     <div class="flex items-center"> | ||||
|                       {#if s.enabled} | ||||
|                         <span | ||||
|                           class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-green-100 text-green-800" | ||||
|                           >{$_("active")}</span | ||||
|                         > | ||||
|                       {:else} | ||||
|                         <span | ||||
|                           class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-red-100 text-red-800" | ||||
|                           >{$_("inactive")}</span | ||||
|                         > | ||||
|                       {/if} | ||||
|                     </div> | ||||
|                   </td> | ||||
|                   {#if active_deletes[s.id] === true} | ||||
|                     <td | ||||
|                       class="px-6 py-4 whitespace-nowrap text-right text-sm font-medium" | ||||
|                     > | ||||
|                       <button | ||||
|                         on:click={() => { | ||||
|                           active_deletes[s.id] = false; | ||||
|                         }} | ||||
|                         tabindex="0" | ||||
|                         class="ml-4 text-indigo-600 hover:text-indigo-900 cursor-pointer" | ||||
|                         >{$_("cancel-delete")}</button | ||||
|                       > | ||||
|                       <button | ||||
|                         on:click={() => { | ||||
|                           ScanStationService.scanStationControllerRemove( | ||||
|                             s.id, | ||||
|                             false | ||||
|                           ) | ||||
|                             .then((resp) => { | ||||
|                               current_stations = current_stations.filter( | ||||
|                                 (obj) => obj.id !== s.id | ||||
|                               ); | ||||
|                               toast($_("station-deleted")); | ||||
|                             }) | ||||
|                             .catch((err) => { | ||||
|                               modal_open = true; | ||||
|                               delete_station = s; | ||||
|                             }); | ||||
|                         }} | ||||
|                         tabindex="0" | ||||
|                         class="ml-4 text-red-600 hover:text-red-900 cursor-pointer" | ||||
|                         >{$_("confirm-delete")}</button | ||||
|                       > | ||||
|                     </td> | ||||
|                   {:else} | ||||
|                     <td | ||||
|                       class="px-6 py-4 whitespace-nowrap text-right text-sm font-medium" | ||||
|                     > | ||||
|                       <a | ||||
|                         href="/scanstations/{s.id}" | ||||
|                         class="text-indigo-600 hover:text-indigo-900" | ||||
|                         >{$_("details")}</a | ||||
|                       > | ||||
|                       {#if store.state.jwtinfo.userdetails.permissions.includes("STATION:DELETE")} | ||||
|                         <button | ||||
|                           on:click={() => { | ||||
|                             active_deletes[s.id] = true; | ||||
|                           }} | ||||
|                           tabindex="0" | ||||
|                           class="ml-4 text-red-600 hover:text-red-900 cursor-pointer" | ||||
|                           >{$_("delete")}</button | ||||
|                         > | ||||
|                       {/if} | ||||
|                     </td> | ||||
|                   {/if} | ||||
|                 </tr> | ||||
|               {/if} | ||||
|             {/each} | ||||
|           </tbody> | ||||
|         </table> | ||||
|       </div> | ||||
|     {/if} | ||||
|   {:catch error} | ||||
|     <div class="text-white px-6 py-4 border-0 rounded relative mb-4 bg-red-500"> | ||||
|       <span class="inline-block align-middle mr-8"> | ||||
|         <b class="capitalize">{$_("general_promise_error")}</b> | ||||
|         {error} | ||||
|       </span> | ||||
|     </div> | ||||
|   {/await} | ||||
| {/if} | ||||
| @@ -2,6 +2,7 @@ | ||||
|   import { _ } from "svelte-i18n"; | ||||
|   import isEmail from "validator/es/lib/isEmail"; | ||||
|   import { MeService } from "@odit/lfk-client-js"; | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   import ConfirmProfileDeletion from "./ConfirmProfileDeletion.svelte"; | ||||
|   import PasswordStrength, { | ||||
| @@ -168,7 +169,7 @@ | ||||
|                   disabled={!save_enabled} | ||||
|                   class:opacity-50={!save_enabled} | ||||
|                   on:click={submit} | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|                 > | ||||
|                   {$_("save-changes")} | ||||
|                 </button> | ||||
| @@ -232,7 +233,7 @@ | ||||
|                   disabled={!update_password_enabled} | ||||
|                   class:opacity-50={!update_password_enabled} | ||||
|                   on:click={changePassword} | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|                 > | ||||
|                   {$_("update-password")} | ||||
|                 </button> | ||||
|   | ||||
| @@ -1,8 +1,8 @@ | ||||
| <script> | ||||
| 	import { _ } from "svelte-i18n"; | ||||
|  | ||||
|   export let detailsLink; | ||||
|   export let detailsAction; | ||||
| 	export let detailsLink = null; | ||||
| 	export let detailsAction = null; | ||||
| 	export let deleteEnabled; | ||||
| 	export let deleteAction; | ||||
| </script> | ||||
|   | ||||
| @@ -5,14 +5,14 @@ | ||||
|   import { createEventDispatcher } from "svelte"; | ||||
|   import toast from "svelte-french-toast"; | ||||
|   export let modal_open; | ||||
|   export let delete_station; | ||||
|   export let delete_client; | ||||
|   const dispatch = createEventDispatcher(); | ||||
|   function cancelDelete() { | ||||
|     modal_open = false; | ||||
|     dispatch("cancelDelete", { id: delete_station.id }); | ||||
|     dispatch("cancelDelete", { id: delete_client.id }); | ||||
|   } | ||||
|   function deleteClient() { | ||||
|     StatsClientService.statsClientControllerRemove(delete_station.id, true) | ||||
|     StatsClientService.statsClientControllerRemove(delete_client.id, true) | ||||
|       .then((resp) => { | ||||
|         toast($_("statsclient-deleted")); | ||||
|         location.replace("./"); | ||||
|   | ||||
| @@ -4,6 +4,7 @@ | ||||
|   import { tick, createEventDispatcher } from "svelte"; | ||||
|   export let copy_modal_open; | ||||
|   export let new_client; | ||||
|   import toast from 'svelte-french-toast' | ||||
|   const dispatch = createEventDispatcher(); | ||||
|   let valueCopy = null; | ||||
|   let areaDom; | ||||
|   | ||||
| @@ -82,7 +82,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteClient} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-deletion")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -99,7 +99,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-statsclient")}</button | ||||
|             > | ||||
|           {/if} | ||||
|   | ||||
| @@ -11,26 +11,21 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
| 	<h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
| 		{$_("statsclients")} | ||||
| 	</h4> | ||||
| 	{#if store.state.jwtinfo.userdetails.permissions.includes("STATSCLIENT:CREATE")} | ||||
| 		<button | ||||
| 			on:click={() => { | ||||
| 				modal_open = true; | ||||
| 			}} | ||||
| 			type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
| 			class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
| 		> | ||||
| 			{$_("create-a-new-statsclient")} | ||||
| 		</button> | ||||
| 	{/if} | ||||
|   </span> | ||||
|   <StatsClientsOverview | ||||
|     bind:current_clients | ||||
|     bind:modal_open | ||||
|     bind:new_client | ||||
|     bind:copy_modal_open | ||||
|   /> | ||||
| 	<StatsClientsOverview bind:current_clients /> | ||||
| </section> | ||||
|  | ||||
| {#if store.state.jwtinfo.userdetails.permissions.includes("STATSCLIENT:CREATE")} | ||||
|   | ||||
| @@ -43,7 +43,7 @@ | ||||
|         bind:value={searchvalue} | ||||
|         placeholder={$_("datatable.search")} | ||||
|         aria-label={$_("datatable.search")} | ||||
|         class="mb-4" | ||||
|         class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|       /> | ||||
|       <div | ||||
|         class="shadow border-b border-gray-200 sm:rounded-lg overflow-x-scroll" | ||||
|   | ||||
| @@ -5,6 +5,7 @@ | ||||
|     RunnerTeamService, | ||||
|   } from "@odit/lfk-client-js"; | ||||
|   import { getLocaleFromNavigator, _ } from "svelte-i18n"; | ||||
|   import toast from 'svelte-french-toast' | ||||
|  | ||||
|   import store from "../../store"; | ||||
|   import Select from "svelte-select"; | ||||
| @@ -125,7 +126,7 @@ | ||||
|               import_modal_open = true; | ||||
|             }} | ||||
|             type="button" | ||||
|             class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|           > | ||||
|             {$_("import-runners")} | ||||
|           </button> | ||||
| @@ -134,7 +135,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteTeam} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-delete")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -151,7 +152,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-team")}</button | ||||
|             > | ||||
|           {/if} | ||||
| @@ -162,7 +163,7 @@ | ||||
|             disabled={!save_enabled} | ||||
|             class:opacity-50={!save_enabled} | ||||
|             type="button" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
| @@ -290,6 +291,13 @@ | ||||
|         on:clear={() => (teamdata.parentGroup = null)} | ||||
|       /> | ||||
|     </div> | ||||
|     <div class="text-sm w-full"> | ||||
|       <span class="font-medium text-gray-700">{$_("distance")}</span> | ||||
|       <br /> | ||||
|       <span class="text-gray-700" | ||||
|         >{(original.total_distance / 1000).toFixed(2)} km</span | ||||
|       > | ||||
|     </div> | ||||
|   </section> | ||||
| {:else} | ||||
|   {#await promise} | ||||
|   | ||||
| @@ -8,20 +8,20 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("teams")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("TEAM:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|     > | ||||
|       {$_("create-team")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <TeamsOverview bind:current_teams /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -54,7 +54,7 @@ | ||||
|         bind:value={searchvalue} | ||||
|         placeholder={$_("datatable.search")} | ||||
|         aria-label={$_("datatable.search")} | ||||
|         class="mb-4" | ||||
|         class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|       /> | ||||
|       <div class="h-12"> | ||||
|         <GenerateSponsoringContracts | ||||
|   | ||||
| @@ -223,7 +223,7 @@ | ||||
|             type="button" | ||||
|             class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|           > | ||||
|             Create | ||||
|             {$_("create")} | ||||
|           </button> | ||||
|           <button | ||||
|             on:click={() => { | ||||
|   | ||||
| @@ -19,18 +19,18 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|     Tracks | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("tracks")} | ||||
|   </h4> | ||||
|   <button | ||||
|     on:click={() => { | ||||
|       modal_open = true; | ||||
|     }} | ||||
|     type="button" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|     class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|   > | ||||
|     {$_("create-track")} | ||||
|   </button> | ||||
|   </span> | ||||
|   {#await tracks_promise} | ||||
|     <div | ||||
|       class="bg-teal-lightest border-t-4 border-teal rounded-b text-teal-darkest px-4 py-3 shadow-md my-2" | ||||
|   | ||||
| @@ -162,7 +162,7 @@ | ||||
|           {#if delete_triggered} | ||||
|             <button | ||||
|               on:click={deleteUser} | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("confirm-delete")}</button | ||||
|             > | ||||
|             <button | ||||
| @@ -179,7 +179,7 @@ | ||||
|                 delete_triggered = true; | ||||
|               }} | ||||
|               type="button" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|               class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-600 text-base font-medium text-white hover:bg-red-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-red-500 sm:w-auto sm:text-sm" | ||||
|               >{$_("delete-user")}</button | ||||
|             > | ||||
|           {/if} | ||||
| @@ -190,7 +190,7 @@ | ||||
|             class:opacity-50={!save_enabled} | ||||
|             type="button" | ||||
|             on:click={submit} | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
|   | ||||
| @@ -150,13 +150,13 @@ | ||||
|             class:opacity-50={save_enabled} | ||||
|             type="button" | ||||
|             on:click={submit} | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("save-changes")}</button | ||||
|           > | ||||
|         {:else} | ||||
|           <button | ||||
|             type="button" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-yellow-600 text-base font-medium text-white hover:bg-yellow-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-yellow-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|             class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-yellow-600 text-base font-medium text-white hover:bg-yellow-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-yellow-500 sm:w-auto sm:text-sm" | ||||
|             >{$_("applying-changes")}</button | ||||
|           > | ||||
|         {/if} | ||||
| @@ -203,7 +203,7 @@ | ||||
|                       } | ||||
|                     }} | ||||
|                     type="button" | ||||
|                     class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-green-200 text-base font-medium text-black hover:bg-green-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-green-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|                     class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-green-200 text-base font-medium text-black hover:bg-green-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-green-500 sm:w-auto sm:text-sm" | ||||
|                     >+</button | ||||
|                   > | ||||
|                 </p> | ||||
| @@ -243,7 +243,7 @@ | ||||
|                     } | ||||
|                   }} | ||||
|                   type="button" | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-300 text-base font-medium text-black hover:bg-red-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|                   class="w-full justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-red-300 text-base font-medium text-black hover:bg-red-700 hover:text-white focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500 sm:w-auto sm:text-sm" | ||||
|                   >-</button | ||||
|                 > | ||||
|               </p> | ||||
|   | ||||
| @@ -8,20 +8,20 @@ | ||||
| </script> | ||||
|  | ||||
| <section class="container p-5"> | ||||
|   <span class="mb-1 text-3xl font-extrabold leading-tight"> | ||||
|   <h4 class="mb-1 text-3xl font-extrabold leading-tight font-mono"> | ||||
|     {$_("users")} | ||||
|   </h4> | ||||
|   {#if store.state.jwtinfo.userdetails.permissions.includes("USER:CREATE")} | ||||
|     <button | ||||
|       on:click={() => { | ||||
|         modal_open = true; | ||||
|       }} | ||||
|       type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:ml-3 sm:w-auto sm:text-sm" | ||||
|       class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-blue-600 text-base font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-blue-500 sm:w-auto sm:text-sm" | ||||
|     > | ||||
|       {$_("create-user")} | ||||
|     </button> | ||||
|   {/if} | ||||
|   </span> | ||||
|   <UsersOverview bind:current_users /> | ||||
| </section> | ||||
|  | ||||
|   | ||||
| @@ -37,7 +37,7 @@ | ||||
|         bind:value={searchvalue} | ||||
|         placeholder={$_("datatable.search")} | ||||
|         aria-label={$_("datatable.search")} | ||||
|         class="mb-4" | ||||
|         class="mb-2 w-full sm:w-auto mt-1 sm:mt-0 p-2 rounded-md border" | ||||
|       /> | ||||
|       <!-- {/if} --> | ||||
|       <!-- <button | ||||
| @@ -45,7 +45,7 @@ | ||||
|           advanced_search = !advanced_search; | ||||
|         }} | ||||
|         type="button" | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-gray-600 text-base font-medium text-white hover:bg-gray-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500 sm:ml-3 sm:w-auto sm:text-sm"> | ||||
|         class="w-full inline-flex justify-center rounded-md border border-transparent shadow-sm px-4 py-2 bg-gray-600 text-base font-medium text-white hover:bg-gray-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-gray-500 sm:w-auto sm:text-sm"> | ||||
|         {#if advanced_search} | ||||
|           toggle simple search | ||||
|         {:else}toggle advanced search{/if} | ||||
| @@ -105,12 +105,12 @@ | ||||
|                   <td class="px-6 py-4 whitespace-nowrap"> | ||||
|                     {#if u.enabled} | ||||
|                       <span | ||||
|                         class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-green-100 text-green-800" | ||||
|                         class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full border bg-green-100 text-green-800" | ||||
|                         >{$_("active")}</span | ||||
|                       > | ||||
|                     {:else} | ||||
|                       <span | ||||
|                         class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-red-100 text-red-800" | ||||
|                         class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full border bg-red-100 text-red-800" | ||||
|                         >{$_("inactive")}</span | ||||
|                       > | ||||
|                     {/if} | ||||
| @@ -119,7 +119,7 @@ | ||||
|                     {#each u.groups as g} | ||||
|                       <a | ||||
|                         href="../groups/{g.id}" | ||||
|                         class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full bg-gray-100 text-gray-800" | ||||
|                         class="px-2 inline-flex text-xs leading-5 font-semibold rounded-full border bg-gray-100 text-gray-800" | ||||
|                         >{g.name}</a | ||||
|                       > | ||||
|                     {/each} | ||||
|   | ||||
| @@ -37,6 +37,7 @@ | ||||
|     "all-associated-scans-will-get-deleted-as-well": "Alle Scans dieser Station werden ebenfalls gelöscht", | ||||
|     "all-associated-teams-and-runners-will-be-deleted-too": "Alle assoziierten Teams und Läufer werden auch gelöscht!", | ||||
|     "all-cards-loaded": "Alle Karten geladen", | ||||
|     "all-donors-loaded": "Alle Sponsoren geladen", | ||||
|     "already-paid": "Bereits bezahlt", | ||||
|     "amount": "Anzahl", | ||||
|     "amount-per-kilometer": "Betrag pro Kilometer", | ||||
| @@ -111,7 +112,7 @@ | ||||
|     "create-a-new-scanstation": "Neue Station erstellen", | ||||
|     "create-a-new-statsclient": "Neuen Statsclient erstellen", | ||||
|     "create-a-new-team": "Erstelle ein neues Team", | ||||
|     "create-a-new-track": "Neuen Track erstellen", | ||||
|     "create-a-new-track": "Neue Laufstrecke erstellen", | ||||
|     "create-a-new-user": "Neuen Benutzer anlegen", | ||||
|     "create-a-new-user-group": "Erstelle eine neue Gruppe", | ||||
|     "create-and-generate-pdf": "Erstellen und PDF herunterladen", | ||||
| @@ -119,7 +120,7 @@ | ||||
|     "create-bulk-cards": "Blankokarten erstellen", | ||||
|     "create-organization": "Organisation erstellen", | ||||
|     "create-team": "Team erstellen", | ||||
|     "create-track": "Track erstellen", | ||||
|     "create-track": "Laufstrecke erstellen", | ||||
|     "create-user": "Benutzer anlegen", | ||||
|     "create-without-pdf": "Ohne PDF erstellen", | ||||
|     "created-blanco-cards": "Blankokarten wurden erstellt", | ||||
| @@ -270,6 +271,7 @@ | ||||
|     "loading-contact-details": "Kontaktdaten werden geladen ...", | ||||
|     "loading-donation-details": "Lade Sponsoringdetails", | ||||
|     "loading-donor-details": "Lade Details", | ||||
|     "loading-donors": "Sponsoren werden geladen", | ||||
|     "loading-group-detail": "Lade Gruppendetails...", | ||||
|     "loading-profile-data": "Lade Profildaten", | ||||
|     "loading-runners": "Läufer werden geladen...", | ||||
| @@ -452,20 +454,20 @@ | ||||
|     "total-paid-amount": "Gezahlt", | ||||
|     "total-scans": "Scans", | ||||
|     "total_donation_amount_in_eur": "Gesamtbetrag in €", | ||||
|     "track": "Track", | ||||
|     "track-added": "Track hinzugefügt", | ||||
|     "track-data-is-being-loaded": "Trackdaten werden geladen", | ||||
|     "track-deleted": "Track gelöscht", | ||||
|     "track-is-being-added": "Track wird hinzugefügt...", | ||||
|     "track-is-being-deleted": "Track wird gelöscht", | ||||
|     "track-is-being-updated": "Track wird aktualisiert...", | ||||
|     "track-length-in-m": "Tracklänge (in Metern)", | ||||
|     "track": "Laufstrecke", | ||||
|     "track-added": "Laufstrecke hinzugefügt", | ||||
|     "track-data-is-being-loaded": "Laufstrecke wird geladen", | ||||
|     "track-deleted": "Laufstrecke gelöscht", | ||||
|     "track-is-being-added": "Laufstrecke wird hinzugefügt...", | ||||
|     "track-is-being-deleted": "Laufstrecke wird gelöscht", | ||||
|     "track-is-being-updated": "Laufstrecke wird aktualisiert...", | ||||
|     "track-length-in-m": "Laufstrecke in Metern", | ||||
|     "track-length-must-be-greater-than-0": "Die Länge muss größer als 0 (Meter) sein", | ||||
|     "track-name": "Trackname", | ||||
|     "track-name": "Name der Laufstrecke", | ||||
|     "track-name-must-not-be-empty": "Der Name muss angegeben werden", | ||||
|     "track-updated": "Track aktualisiert", | ||||
|     "track-was-updated": "Track wurde aktualisiert", | ||||
|     "tracks": "Tracks", | ||||
|     "track-updated": "Laufstrecke aktualisiert", | ||||
|     "track-was-updated": "Laufstrecke wurde aktualisiert", | ||||
|     "tracks": "Laufstrecken", | ||||
|     "unpaid": "Offen", | ||||
|     "update-card": "Karte aktualisieren", | ||||
|     "update-password": "Passwort ändern", | ||||
|   | ||||
| @@ -37,6 +37,7 @@ | ||||
|     "all-associated-scans-will-get-deleted-as-well": "All associated scans will get deleted as well", | ||||
|     "all-associated-teams-and-runners-will-be-deleted-too": "All associated teams and runners will be deleted too!", | ||||
|     "all-cards-loaded": "All cards loaded", | ||||
|     "all-donors-loaded": "All donors loaded", | ||||
|     "already-paid": "Already paid", | ||||
|     "amount": "Amount", | ||||
|     "amount-per-kilometer": "Amount per kilometer", | ||||
| @@ -270,6 +271,7 @@ | ||||
|     "loading-contact-details": "Loading contact details...", | ||||
|     "loading-donation-details": "Loading donation details", | ||||
|     "loading-donor-details": "Loading donor details", | ||||
|     "loading-donors": "Loading donors", | ||||
|     "loading-group-detail": "Loading group detail...", | ||||
|     "loading-profile-data": "Loading profile data", | ||||
|     "loading-runners": "loading runners...", | ||||
|   | ||||
| @@ -1,3 +1,7 @@ | ||||
| @tailwind base; | ||||
| @tailwind components; | ||||
| .activenav { | ||||
|     @apply bg-gray-300; | ||||
|     @apply text-black; | ||||
| } | ||||
| @tailwind utilities; | ||||
|   | ||||
		Reference in New Issue
	
	Block a user