From 27dbcbf28d95f082523cdbb3d58ebba79b36e5d2 Mon Sep 17 00:00:00 2001 From: Konstantin Schaper Date: Tue, 2 Aug 2022 08:39:37 +0200 Subject: [PATCH] Integrate tailwind css and create new button library (#2098) Introduce tailwind as new frontend styling library to replace bulma in the longer run. Also create the first new ui library `ui-buttons` which will be the new standard for buttons ins SCM-Manager. In this library we reconsidered which types of buttons should be used to create a clean and consistent ui. Co-authored-by: Eduard Heimbuch --- .gitignore | 1 + package.json | 9 +- scm-it/gradle.lockfile | 39 +- scm-plugins/scm-git-plugin/package.json | 4 +- scm-plugins/scm-hg-plugin/package.json | 4 +- scm-plugins/scm-legacy-plugin/package.json | 4 +- scm-plugins/scm-svn-plugin/package.json | 4 +- scm-ui/build.gradle | 1 + scm-ui/e2e-tests/package.json | 4 +- scm-ui/ui-api/package.json | 4 +- scm-ui/ui-api/src/plugins.ts | 5 +- scm-ui/ui-buttons/.storybook/.babelrc | 4 + .../.storybook/RemoveThemesPlugin.js | 57 + scm-ui/ui-buttons/.storybook/index.css | 27 + scm-ui/ui-buttons/.storybook/main.js | 109 + .../ui-buttons/.storybook/preview-head.html | 26 + scm-ui/ui-buttons/.storybook/preview.js | 97 + .../ui-buttons/.storybook/tailwind.config.js | 33 + .../ui-buttons/.storybook/withApiProvider.js | 45 + .../ui-buttons/docs/introduction.stories.mdx | 64 + scm-ui/ui-buttons/docs/usage.stories.mdx | 22 + scm-ui/ui-buttons/package.json | 85 + scm-ui/ui-buttons/postcss.config.js | 30 + ...age-snapshots-tests-dark-states-1-snap.png | Bin 0 -> 35883 bytes ...hots-tests-high-contrast-states-1-snap.png | Bin 0 -> 35126 bytes ...ge-snapshots-tests-light-states-1-snap.png | Bin 0 -> 34677 bytes scm-ui/ui-buttons/src/a11y.test.ts | 34 + scm-ui/ui-buttons/src/button.stories.tsx | 91 + scm-ui/ui-buttons/src/button.test.stories.mdx | 73 + scm-ui/ui-buttons/src/button.tsx | 109 + scm-ui/ui-buttons/src/image-snapshot.test.ts | 33 + scm-ui/ui-buttons/src/index.css | 26 + scm-ui/ui-buttons/src/index.ts | 27 + scm-ui/ui-buttons/tailwind.config.js | 34 + scm-ui/ui-buttons/tsconfig.json | 7 + scm-ui/ui-components/package.json | 4 +- .../ui-components/src/OverviewPageActions.tsx | 15 +- .../src/__snapshots__/storyshots.test.ts.snap | 3209 +++-- .../src/forms/InputField.stories.tsx | 5 +- .../remarkChangesetShortLinkParser.ts | 8 +- .../markdown/remarkValuelessTextAdapter.ts | 6 +- scm-ui/ui-components/src/table/Table.tsx | 16 +- scm-ui/ui-extensions/package.json | 4 +- scm-ui/ui-legacy/package.json | 4 +- scm-ui/ui-modules/package.json | 4 +- scm-ui/ui-plugins/package.json | 4 +- scm-ui/ui-scripts/package.json | 11 +- scm-ui/ui-scripts/src/tailwind.config.js | 41 + scm-ui/ui-scripts/src/tailwind.css | 27 + scm-ui/ui-scripts/src/webpack.config.js | 41 +- scm-ui/ui-styles/package.json | 4 +- scm-ui/ui-styles/src/dark.scss | 17 + scm-ui/ui-styles/src/highcontrast.scss | 17 + scm-ui/ui-styles/src/light.scss | 17 + .../ui-styles/src/tailwind.config.preset.js | 55 + scm-ui/ui-styles/src/utils/_post.scss | 16 +- scm-ui/ui-syntaxhighlighting/package.json | 4 +- .../src/worker/SyntaxHighlighter.worker.ts | 3 +- scm-ui/ui-text/package.json | 4 +- scm-ui/ui-types/package.json | 4 +- scm-ui/ui-webapp/package.json | 9 +- scm-ui/ui-webapp/public/index.mustache | 1 + scm-ui/ui-webapp/src/index.tsx | 3 + scm-webapp/gradle.lockfile | 10 +- .../scm/PushStateDispatcherProvider.java | 2 +- .../sonia/scm/web/tailwind/StylesServlet.java | 111 + yarn.lock | 11323 +++++++--------- 67 files changed, 8592 insertions(+), 7519 deletions(-) create mode 100644 scm-ui/ui-buttons/.storybook/.babelrc create mode 100644 scm-ui/ui-buttons/.storybook/RemoveThemesPlugin.js create mode 100644 scm-ui/ui-buttons/.storybook/index.css create mode 100644 scm-ui/ui-buttons/.storybook/main.js create mode 100644 scm-ui/ui-buttons/.storybook/preview-head.html create mode 100644 scm-ui/ui-buttons/.storybook/preview.js create mode 100644 scm-ui/ui-buttons/.storybook/tailwind.config.js create mode 100644 scm-ui/ui-buttons/.storybook/withApiProvider.js create mode 100644 scm-ui/ui-buttons/docs/introduction.stories.mdx create mode 100644 scm-ui/ui-buttons/docs/usage.stories.mdx create mode 100644 scm-ui/ui-buttons/package.json create mode 100644 scm-ui/ui-buttons/postcss.config.js create mode 100644 scm-ui/ui-buttons/src/__image_snapshots__/image-snapshot-test-ts-image-snapshots-tests-dark-states-1-snap.png create mode 100644 scm-ui/ui-buttons/src/__image_snapshots__/image-snapshot-test-ts-image-snapshots-tests-high-contrast-states-1-snap.png create mode 100644 scm-ui/ui-buttons/src/__image_snapshots__/image-snapshot-test-ts-image-snapshots-tests-light-states-1-snap.png create mode 100644 scm-ui/ui-buttons/src/a11y.test.ts create mode 100644 scm-ui/ui-buttons/src/button.stories.tsx create mode 100644 scm-ui/ui-buttons/src/button.test.stories.mdx create mode 100644 scm-ui/ui-buttons/src/button.tsx create mode 100644 scm-ui/ui-buttons/src/image-snapshot.test.ts create mode 100644 scm-ui/ui-buttons/src/index.css create mode 100644 scm-ui/ui-buttons/src/index.ts create mode 100644 scm-ui/ui-buttons/tailwind.config.js create mode 100644 scm-ui/ui-buttons/tsconfig.json create mode 100644 scm-ui/ui-scripts/src/tailwind.config.js create mode 100644 scm-ui/ui-scripts/src/tailwind.css create mode 100644 scm-ui/ui-styles/src/tailwind.config.preset.js create mode 100644 scm-webapp/src/main/java/sonia/scm/web/tailwind/StylesServlet.java diff --git a/.gitignore b/.gitignore index 52552352c3..ba9ee3b799 100644 --- a/.gitignore +++ b/.gitignore @@ -40,3 +40,4 @@ rebel.xml .cache .turbo +storybook-static diff --git a/package.json b/package.json index e9cdda49c1..2455b30856 100644 --- a/package.json +++ b/package.json @@ -18,20 +18,21 @@ "set-version": "ui-scripts version" }, "dependencies": { - "@scm-manager/eslint-config": "^2.15.1" + "@scm-manager/eslint-config": "2.16.0" }, "devDependencies": { "@scm-manager/remark-preset-lint": "^1.0.0", "babel-plugin-reflow": "^0.2.7", + "cross-env": "^7.0.3", "husky": "^4.2.5", "lint-staged": "^10.2.11", "remark-cli": "^9.0.0", - "turbo": "^1.2.5", - "cross-env": "^7.0.3" + "turbo": "^1.2.5" }, "resolutions": { "babel-core": "7.0.0-bridge.0", - "gitdiff-parser": "https://github.com/scm-manager/gitdiff-parser#420d6cfa17a6a8f9bf1a517a2c629dcb332dbe13" + "gitdiff-parser": "https://github.com/scm-manager/gitdiff-parser#420d6cfa17a6a8f9bf1a517a2c629dcb332dbe13", + "@types/react": "17.0.47" }, "babel": { "presets": [ diff --git a/scm-it/gradle.lockfile b/scm-it/gradle.lockfile index a1d8bb208c..603078d0b6 100644 --- a/scm-it/gradle.lockfile +++ b/scm-it/gradle.lockfile @@ -10,7 +10,7 @@ com.cloudogu.legman.support:micrometer:2.0.0=testRuntimeClasspath,testRuntimeCla com.cloudogu.legman.support:shiro:2.0.0=testRuntimeClasspath,testRuntimeClasspathCopy com.cloudogu.legman:core:2.0.0=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.cloudogu.spotter:spotter-core:4.0.0=testRuntimeClasspath,testRuntimeClasspathCopy -com.cronutils:cron-utils:9.1.6=testRuntimeClasspath,testRuntimeClasspathCopy +com.cronutils:cron-utils:9.1.8=testRuntimeClasspath,testRuntimeClasspathCopy com.damnhandy:handy-uri-templates:2.1.7=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.fasterxml.jackson.core:jackson-annotations:2.11.3=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.fasterxml.jackson.core:jackson-core:2.11.3=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy @@ -34,8 +34,7 @@ com.github.sdorra:web-resources:1.1.1=testRuntimeClasspath,testRuntimeClasspathC com.github.spullara.mustache.java:compiler:0.9.7=testRuntimeClasspath,testRuntimeClasspathCopy com.google.auto:auto-common:0.11=testRuntimeClasspath,testRuntimeClasspathCopy com.google.code.findbugs:jsr305:3.0.2=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy -com.google.code.gson:gson:2.8.6=testRuntimeClasspath -com.google.code.gson:gson:2.8.7=testRuntimeClasspathCopy +com.google.code.gson:gson:2.8.7=testRuntimeClasspath,testRuntimeClasspathCopy com.google.errorprone:error_prone_annotations:2.3.4=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.google.guava:failureaccess:1.0.1=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.google.guava:guava:30.1-jre=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy @@ -46,8 +45,7 @@ com.google.inject.extensions:guice-servlet:5.0.1=testCompileClasspath,testCompil com.google.inject.extensions:guice-throwingproviders:5.0.1=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.google.inject:guice:5.0.1=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.google.j2objc:j2objc-annotations:1.3=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy -com.googlecode.javaewah:JavaEWAH:1.1.12=testCompileClasspathCopy,testRuntimeClasspathCopy -com.googlecode.javaewah:JavaEWAH:1.1.7=testCompileClasspath,testRuntimeClasspath +com.googlecode.javaewah:JavaEWAH:1.1.12=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.ibm.async:asyncutil:0.1.0=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy com.jcraft:jsch.agentproxy.connector-factory:0.0.7=testRuntimeClasspath,testRuntimeClasspathCopy com.jcraft:jsch.agentproxy.core:0.0.7=testRuntimeClasspath,testRuntimeClasspathCopy @@ -147,13 +145,10 @@ org.apache.sling:org.apache.sling.javax.activation:0.1.0=testCompileClasspath,te org.apache.tika:tika-core:1.25=testRuntimeClasspath,testRuntimeClasspathCopy org.apiguardian:apiguardian-api:1.1.0=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.assertj:assertj-core:3.18.1=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy -org.bouncycastle:bcpg-jdk15on:1.67=testRuntimeClasspath -org.bouncycastle:bcpg-jdk15on:1.69=testRuntimeClasspathCopy -org.bouncycastle:bcpkix-jdk15on:1.67=testRuntimeClasspath -org.bouncycastle:bcpkix-jdk15on:1.69=testRuntimeClasspathCopy -org.bouncycastle:bcprov-jdk15on:1.67=testRuntimeClasspath -org.bouncycastle:bcprov-jdk15on:1.69=testRuntimeClasspathCopy -org.bouncycastle:bcutil-jdk15on:1.69=testRuntimeClasspathCopy +org.bouncycastle:bcpg-jdk15on:1.69=testRuntimeClasspath,testRuntimeClasspathCopy +org.bouncycastle:bcpkix-jdk15on:1.69=testRuntimeClasspath,testRuntimeClasspathCopy +org.bouncycastle:bcprov-jdk15on:1.69=testRuntimeClasspath,testRuntimeClasspathCopy +org.bouncycastle:bcutil-jdk15on:1.69=testRuntimeClasspath,testRuntimeClasspathCopy org.ccil.cowan.tagsoup:tagsoup:1.2.1=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.checkerframework:checker-qual:3.5.0=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.codehaus.groovy:groovy-json:3.0.2=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy @@ -162,6 +157,7 @@ org.codehaus.groovy:groovy:3.0.2=testCompileClasspath,testCompileClasspathCopy,t org.eclipse.microprofile.config:microprofile-config-api:2.0=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.glassfish.jaxb:jaxb-runtime:2.3.3=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.glassfish.jaxb:txw2:2.3.3=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy +org.glassfish:jakarta.el:3.0.4=testRuntimeClasspath,testRuntimeClasspathCopy org.glassfish:javax.el:3.0.1-b11=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.glassfish:javax.json:1.1.4=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.hamcrest:hamcrest-core:2.1=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy @@ -174,7 +170,6 @@ org.jacoco:org.jacoco.ant:0.8.7=jacocoAntCopy org.jacoco:org.jacoco.core:0.8.7=jacocoAntCopy org.jacoco:org.jacoco.report:0.8.7=jacocoAntCopy org.javahg:javahg:1.0.0=testRuntimeClasspath,testRuntimeClasspathCopy -org.javassist:javassist:3.27.0-GA=testRuntimeClasspath,testRuntimeClasspathCopy org.jboss.logging:jboss-logging:3.4.2.Final=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.jboss.resteasy:resteasy-client-api:4.7.5.Final=testRuntimeClasspath,testRuntimeClasspathCopy org.jboss.resteasy:resteasy-client:4.7.5.Final=testRuntimeClasspath,testRuntimeClasspathCopy @@ -215,18 +210,12 @@ org.reactivestreams:reactive-streams:1.0.3=testCompileClasspath,testCompileClass org.slf4j:jcl-over-slf4j:1.7.30=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.slf4j:slf4j-api:1.7.30=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy org.tmatesoft.sqljet:sqljet:1.1.14=testRuntimeClasspath,testRuntimeClasspathCopy -sonia.jgit:org.eclipse.jgit.gpg.bc:5.11.1.202105131744-r-scm2=testRuntimeClasspath -sonia.jgit:org.eclipse.jgit.gpg.bc:5.13.0.202109080827-r-scm1=testRuntimeClasspathCopy -sonia.jgit:org.eclipse.jgit.http.apache:5.11.1.202105131744-r-scm2=testRuntimeClasspath -sonia.jgit:org.eclipse.jgit.http.apache:5.13.0.202109080827-r-scm1=testRuntimeClasspathCopy -sonia.jgit:org.eclipse.jgit.http.server:5.11.1.202105131744-r-scm2=testRuntimeClasspath -sonia.jgit:org.eclipse.jgit.http.server:5.13.0.202109080827-r-scm1=testRuntimeClasspathCopy -sonia.jgit:org.eclipse.jgit.lfs.server:5.11.1.202105131744-r-scm2=testRuntimeClasspath -sonia.jgit:org.eclipse.jgit.lfs.server:5.13.0.202109080827-r-scm1=testRuntimeClasspathCopy -sonia.jgit:org.eclipse.jgit.lfs:5.11.1.202105131744-r-scm2=testRuntimeClasspath -sonia.jgit:org.eclipse.jgit.lfs:5.13.0.202109080827-r-scm1=testRuntimeClasspathCopy -sonia.jgit:org.eclipse.jgit:5.11.1.202105131744-r-scm2=testCompileClasspath,testRuntimeClasspath -sonia.jgit:org.eclipse.jgit:5.13.0.202109080827-r-scm1=testCompileClasspathCopy,testRuntimeClasspathCopy +sonia.jgit:org.eclipse.jgit.gpg.bc:5.13.0.202109080827-r-scm1=testRuntimeClasspath,testRuntimeClasspathCopy +sonia.jgit:org.eclipse.jgit.http.apache:5.13.0.202109080827-r-scm1=testRuntimeClasspath,testRuntimeClasspathCopy +sonia.jgit:org.eclipse.jgit.http.server:5.13.0.202109080827-r-scm1=testRuntimeClasspath,testRuntimeClasspathCopy +sonia.jgit:org.eclipse.jgit.lfs.server:5.13.0.202109080827-r-scm1=testRuntimeClasspath,testRuntimeClasspathCopy +sonia.jgit:org.eclipse.jgit.lfs:5.13.0.202109080827-r-scm1=testRuntimeClasspath,testRuntimeClasspathCopy +sonia.jgit:org.eclipse.jgit:5.13.0.202109080827-r-scm1=testCompileClasspath,testCompileClasspathCopy,testRuntimeClasspath,testRuntimeClasspathCopy sonia.svnkit:svnkit-dav:1.10.3-scm2=testRuntimeClasspath,testRuntimeClasspathCopy sonia.svnkit:svnkit:1.10.3-scm2=testRuntimeClasspath,testRuntimeClasspathCopy empty=annotationProcessor,annotationProcessorCopy,archives,archivesCopy,compileClasspath,compileClasspathCopy,corePlugin,corePluginCopy,default,defaultCopy,itPlugin,itPluginCopy,itWebApp,itWebAppCopy,runtimeClasspath,runtimeClasspathCopy,testAnnotationProcessor,testAnnotationProcessorCopy diff --git a/scm-plugins/scm-git-plugin/package.json b/scm-plugins/scm-git-plugin/package.json index eb22ed05f5..6d61086592 100644 --- a/scm-plugins/scm-git-plugin/package.json +++ b/scm-plugins/scm-git-plugin/package.json @@ -15,7 +15,7 @@ }, "devDependencies": { "@scm-manager/babel-preset": "^2.13.1", - "@scm-manager/eslint-config": "^2.15.1", + "@scm-manager/eslint-config": "^2.16.0", "@scm-manager/jest-preset": "^2.13.0", "@scm-manager/plugin-scripts": "^1.2.2", "@scm-manager/prettier-config": "^2.11.1", @@ -33,4 +33,4 @@ "eslintConfig": { "extends": "@scm-manager/eslint-config" } -} \ No newline at end of file +} diff --git a/scm-plugins/scm-hg-plugin/package.json b/scm-plugins/scm-hg-plugin/package.json index c0111a9226..421e31fc8f 100644 --- a/scm-plugins/scm-hg-plugin/package.json +++ b/scm-plugins/scm-hg-plugin/package.json @@ -14,7 +14,7 @@ }, "devDependencies": { "@scm-manager/babel-preset": "^2.13.1", - "@scm-manager/eslint-config": "^2.15.1", + "@scm-manager/eslint-config": "^2.16.0", "@scm-manager/jest-preset": "^2.13.0", "@scm-manager/plugin-scripts": "^1.2.2", "@scm-manager/prettier-config": "^2.11.1", @@ -32,4 +32,4 @@ "eslintConfig": { "extends": "@scm-manager/eslint-config" } -} \ No newline at end of file +} diff --git a/scm-plugins/scm-legacy-plugin/package.json b/scm-plugins/scm-legacy-plugin/package.json index fdd92b946c..cb927b4a9b 100644 --- a/scm-plugins/scm-legacy-plugin/package.json +++ b/scm-plugins/scm-legacy-plugin/package.json @@ -14,7 +14,7 @@ }, "devDependencies": { "@scm-manager/babel-preset": "^2.13.1", - "@scm-manager/eslint-config": "^2.15.1", + "@scm-manager/eslint-config": "^2.16.0", "@scm-manager/jest-preset": "^2.13.0", "@scm-manager/plugin-scripts": "^1.2.2", "@scm-manager/prettier-config": "^2.11.1", @@ -32,4 +32,4 @@ "eslintConfig": { "extends": "@scm-manager/eslint-config" } -} \ No newline at end of file +} diff --git a/scm-plugins/scm-svn-plugin/package.json b/scm-plugins/scm-svn-plugin/package.json index 5087d30d9b..a7d6251716 100644 --- a/scm-plugins/scm-svn-plugin/package.json +++ b/scm-plugins/scm-svn-plugin/package.json @@ -14,7 +14,7 @@ }, "devDependencies": { "@scm-manager/babel-preset": "^2.13.1", - "@scm-manager/eslint-config": "^2.15.1", + "@scm-manager/eslint-config": "^2.16.0", "@scm-manager/jest-preset": "^2.13.0", "@scm-manager/plugin-scripts": "^1.2.2", "@scm-manager/prettier-config": "^2.11.1", @@ -32,4 +32,4 @@ "eslintConfig": { "extends": "@scm-manager/eslint-config" } -} \ No newline at end of file +} diff --git a/scm-ui/build.gradle b/scm-ui/build.gradle index 78e6a09e57..95acc300d3 100644 --- a/scm-ui/build.gradle +++ b/scm-ui/build.gradle @@ -279,6 +279,7 @@ license { exclude '**/*.snap' exclude '**/*.iml' exclude '**/.babelrc' + exclude '**/storybook-static/**' tasks { modules { diff --git a/scm-ui/e2e-tests/package.json b/scm-ui/e2e-tests/package.json index 4315bc8404..77d00eb193 100644 --- a/scm-ui/e2e-tests/package.json +++ b/scm-ui/e2e-tests/package.json @@ -17,7 +17,7 @@ "fluent-ffmpeg": "^2.1.2" }, "devDependencies": { - "@scm-manager/eslint-config": "^2.15.1" + "@scm-manager/eslint-config": "^2.16.0" }, "prettier": "@scm-manager/prettier-config", "eslintConfig": { @@ -26,4 +26,4 @@ "publishConfig": { "access": "public" } -} \ No newline at end of file +} diff --git a/scm-ui/ui-api/package.json b/scm-ui/ui-api/package.json index 967ffef61d..4309afac0a 100644 --- a/scm-ui/ui-api/package.json +++ b/scm-ui/ui-api/package.json @@ -19,7 +19,7 @@ }, "devDependencies": { "@scm-manager/babel-preset": "^2.13.1", - "@scm-manager/eslint-config": "^2.15.1", + "@scm-manager/eslint-config": "^2.16.0", "@scm-manager/jest-preset": "^2.13.0", "@scm-manager/prettier-config": "^2.10.1", "@scm-manager/tsconfig": "^2.13.0", @@ -52,4 +52,4 @@ "publishConfig": { "access": "public" } -} \ No newline at end of file +} diff --git a/scm-ui/ui-api/src/plugins.ts b/scm-ui/ui-api/src/plugins.ts index d6e27e1ec2..44163000b5 100644 --- a/scm-ui/ui-api/src/plugins.ts +++ b/scm-ui/ui-api/src/plugins.ts @@ -23,12 +23,15 @@ */ import { ApiResult, useIndexLink, useRequiredIndexLink } from "./base"; -import { isPluginCollection, PendingPlugins, Plugin, PluginCollection } from "@scm-manager/ui-types"; +import type { PendingPlugins, Plugin, PluginCollection, HalRepresentation } from "@scm-manager/ui-types"; import { useMutation, useQuery, useQueryClient } from "react-query"; import { apiClient } from "./apiclient"; import { requiredLink } from "./links"; import { BadGatewayError } from "./errors"; +const isPluginCollection = (input: HalRepresentation): input is PluginCollection => + input._embedded ? "plugins" in input._embedded : false; + type WaitForRestartOptions = { initialDelay?: number; timeout?: number; diff --git a/scm-ui/ui-buttons/.storybook/.babelrc b/scm-ui/ui-buttons/.storybook/.babelrc new file mode 100644 index 0000000000..2fa1f1e174 --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/.babelrc @@ -0,0 +1,4 @@ +{ + "presets": ["@scm-manager/babel-preset"], + "plugins": ["@babel/plugin-syntax-dynamic-import"] +} diff --git a/scm-ui/ui-buttons/.storybook/RemoveThemesPlugin.js b/scm-ui/ui-buttons/.storybook/RemoveThemesPlugin.js new file mode 100644 index 0000000000..9976554354 --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/RemoveThemesPlugin.js @@ -0,0 +1,57 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +const HtmlWebpackPlugin = require('html-webpack-plugin'); + +class RemoveThemesPlugin { + apply (compiler) { + compiler.hooks.compilation.tap('RemoveThemesPlugin', (compilation) => { + + HtmlWebpackPlugin.getHooks(compilation).beforeAssetTagGeneration.tapAsync( + 'RemoveThemesPlugin', + (data, cb) => { + + // remove generated style-loader bundles from the page + // there should be a better way, which does not generate the bundles at all + // but for now it works + if (data.assets.js) { + data.assets.js = data.assets.js.filter(bundle => !bundle.startsWith("ui-theme-")) + .filter(bundle => !bundle.startsWith("runtime~ui-theme-")) + } + + // remove css links to avoid conflicts with the themes + // so we remove all and add our own via preview-head.html + if (data.assets.css) { + data.assets.css = data.assets.css.filter(css => !css.startsWith("ui-theme-")) + } + + // Tell webpack to move on + cb(null, data) + } + ) + }) + } +} + +module.exports = RemoveThemesPlugin diff --git a/scm-ui/ui-buttons/.storybook/index.css b/scm-ui/ui-buttons/.storybook/index.css new file mode 100644 index 0000000000..903dbfaa56 --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/index.css @@ -0,0 +1,27 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +@tailwind base; +@tailwind components; +@tailwind utilities; diff --git a/scm-ui/ui-buttons/.storybook/main.js b/scm-ui/ui-buttons/.storybook/main.js new file mode 100644 index 0000000000..dd8037ff73 --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/main.js @@ -0,0 +1,109 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +const path = require("path"); +const fs = require("fs"); +const MiniCssExtractPlugin = require("mini-css-extract-plugin"); +const RemoveThemesPlugin = require("./RemoveThemesPlugin"); +const ReactDOM = require("react-dom"); + +const root = path.resolve(".."); + +const themedir = path.join(root, "ui-styles", "src"); + +ReactDOM.createPortal = (node) => node; + +const themes = fs + .readdirSync(themedir) + .map((filename) => path.parse(filename)) + .filter((p) => p.ext === ".scss") + .reduce((entries, current) => ({ ...entries, [`ui-theme-${current.name}`]: path.join(themedir, current.base) }), {}); + +module.exports = { + typescript: { reactDocgen: false }, + core: { + builder: "webpack5", + }, + stories: ["../docs/**/*.stories.mdx", "../src/**/*.stories.mdx", "../src/**/*.stories.@(js|jsx|ts|tsx)"], + addons: [ + "storybook-addon-i18next", + "storybook-addon-themes", + "@storybook/addon-links", + "@storybook/addon-essentials", + "@storybook/addon-interactions", + "@storybook/addon-a11y", + "storybook-addon-pseudo-states" + ], + framework: "@storybook/react", + webpackFinal: async (config) => { + // add our themes to webpack entry points + config.entry = { + main: config.entry, + ...themes, + }; + + // create separate css files for our themes + config.plugins.push( + new MiniCssExtractPlugin({ + filename: "[name].css", + ignoreOrder: false, + }) + ); + + config.module.rules.push({ + test: /\.scss$/, + use: [MiniCssExtractPlugin.loader, "css-loader", "sass-loader"], + }); + + config.module.rules.push({ + test: /\.css$/, + use: [ + { + loader: "postcss-loader", + options: { + postcssOptions: { + plugins: { + tailwindcss: { config: require("./tailwind.config") }, + autoprefixer: {}, + }, + }, + }, + }, + ], + include: path.resolve(__dirname, "../"), + }); + + // the html-webpack-plugin adds the generated css and js files to the iframe, + // which overrides our manually loaded css files. + // So we use a custom plugin which uses a hook of html-webpack-plugin + // to filter our themes from the output. + config.plugins.push(new RemoveThemesPlugin()); + + // force cjs instead of esm + // https://github.com/tannerlinsley/react-query/issues/3513 + config.resolve.alias["react-query/devtools"] = require.resolve("react-query/devtools"); + + return config; + }, +}; diff --git a/scm-ui/ui-buttons/.storybook/preview-head.html b/scm-ui/ui-buttons/.storybook/preview-head.html new file mode 100644 index 0000000000..d1c34ac7ef --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/preview-head.html @@ -0,0 +1,26 @@ + + + + diff --git a/scm-ui/ui-buttons/.storybook/preview.js b/scm-ui/ui-buttons/.storybook/preview.js new file mode 100644 index 0000000000..fb70b7769b --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/preview.js @@ -0,0 +1,97 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +import "./index.css"; + +import i18next from "i18next"; +import { initReactI18next } from "react-i18next"; +import { withI18next } from "storybook-addon-i18next"; +import React, {useEffect} from "react"; +import withApiProvider from "./withApiProvider"; +import { withThemes } from 'storybook-addon-themes/react'; + +let i18n = i18next; + +// only use fetch backend for storybook +// and not for storyshots +if (!process.env.JEST_WORKER_ID) { + const Backend = require("i18next-fetch-backend"); + i18n = i18n.use(Backend.default); +} + +i18n.use(initReactI18next).init({ + whitelist: ["en", "de", "es"], + lng: "en", + fallbackLng: "en", + interpolation: { + escapeValue: false, + }, + react: { + useSuspense: false, + }, + backend: { + loadPath: "/locales/{{lng}}/{{ns}}.json", + init: { + credentials: "same-origin", + }, + }, +}); + +export const decorators = [ + withI18next({ + i18n, + languages: { + en: "English", + de: "Deutsch", + es: "Spanisch", + }, + }), + withApiProvider, + withThemes +]; + +const Decorator = ({children, themeName}) => { + useEffect(() => { + const link = document.querySelector("#ui-theme"); + if (link && link["data-theme"] !== themeName) { + link.href = `ui-theme-${themeName}.css`; + link["data-theme"] = themeName; + } + }, [themeName]); + return <>{children} +}; + +export const parameters = { + actions: { argTypesRegex: "^on[A-Z].*" }, + themes: { + Decorator, + clearable: false, + default: "light", + list: [ + { name: "light", color: "#fff" }, + { name: "highcontrast", color: "#050514" }, + { name: "dark", color: "#121212" }, + ], + } +}; diff --git a/scm-ui/ui-buttons/.storybook/tailwind.config.js b/scm-ui/ui-buttons/.storybook/tailwind.config.js new file mode 100644 index 0000000000..165f3fef58 --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/tailwind.config.js @@ -0,0 +1,33 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +const path = require("path"); + +module.exports = { + presets: [ + // eslint-disable-next-line global-require,import/no-extraneous-dependencies + require("@scm-manager/ui-scripts/src/tailwind.config"), + ], + content: [path.join(__dirname, "../{src,docs}/**/*.{tsx,mdx}")], +}; diff --git a/scm-ui/ui-buttons/.storybook/withApiProvider.js b/scm-ui/ui-buttons/.storybook/withApiProvider.js new file mode 100644 index 0000000000..8aa561d39c --- /dev/null +++ b/scm-ui/ui-buttons/.storybook/withApiProvider.js @@ -0,0 +1,45 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ +import * as React from "react"; +import { ApiProvider } from "@scm-manager/ui-api"; + +const withApiProvider = (storyFn) => { + return React.createElement(ApiProvider, { + index: { + version: "x.y.z", + _links: {} + }, + me: { + name: "trillian", + displayName: "Trillian McMillan", + mail: "trillian@hitchhiker.com", + groups: [], + _links: {} + }, + devtools: false, + children: storyFn() + }); +} + +export default withApiProvider; diff --git a/scm-ui/ui-buttons/docs/introduction.stories.mdx b/scm-ui/ui-buttons/docs/introduction.stories.mdx new file mode 100644 index 0000000000..bae9510291 --- /dev/null +++ b/scm-ui/ui-buttons/docs/introduction.stories.mdx @@ -0,0 +1,64 @@ +import { Meta } from "@storybook/addon-docs"; +import { Button } from "../src"; + + + +# Buttons + +The `@scm-manager/ui-buttons` library provides [atoms](https://atomicdesign.bradfrost.com/chapter-2/#atoms) implemented +as minimal wrappers around native html elements styled to match the general SCM-Manager aesthetic. + +## Components + +There are three actionable components available. Styling is consistent amongst them and all have the required `variant` property. + +1. [Button](?path=/story/components--button) +2. [Link Button](?path=/story/components--link-button) +3. [External Link Button](?path=/story/components--external-link-button) + +## Usage + +Actionable components serve a dedicated purpose. It is therefore important to know when and how to use them. + +### Variants + +There are four variants available to each of the three button types, varying in importance. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
EmphasisButton VariantUsage Examples
Very HighDestructive actions
HighForm submit
NormalCancel action in dialog
LowCircumstantially relevant action on page with many actionable elements
+ +## Content + +Buttons exclusively contain text and no icons. Icons tend to be ambiguous and not always applicable which leads to inconsistent +and cluttered layouts. + +Button text should be short, concise and describe the action performed. diff --git a/scm-ui/ui-buttons/docs/usage.stories.mdx b/scm-ui/ui-buttons/docs/usage.stories.mdx new file mode 100644 index 0000000000..79057e1b02 --- /dev/null +++ b/scm-ui/ui-buttons/docs/usage.stories.mdx @@ -0,0 +1,22 @@ +import { Meta, Story } from "@storybook/addon-docs"; +import { Button } from "../src"; + + + +In confirmation dialogs, there are two actions.
+One to cancel the current process and one to confirm it.
+Aborting is always the secondary action, confirmation always the primary. +Focus is always on the cancelling action. + + +
+

Delete User

+

Do you really want to delete this user ?

+
+ + +
+
+
diff --git a/scm-ui/ui-buttons/package.json b/scm-ui/ui-buttons/package.json new file mode 100644 index 0000000000..45d6f501a9 --- /dev/null +++ b/scm-ui/ui-buttons/package.json @@ -0,0 +1,85 @@ +{ + "name": "@scm-manager/ui-buttons", + "version": "2.37.3-SNAPSHOT", + "private": true, + "main": "build/index.js", + "module": "build/index.mjs", + "types": "build/index.d.ts", + "files": [ + "build" + ], + "scripts": { + "build": "tsup ./src/index.ts -d build --format esm,cjs --dts", + "dev": "tsup ./src/index.ts -d build --format esm,cjs --dts --watch", + "lint": "eslint src", + "typecheck": "tsc", + "storybook": "start-storybook -p 6006 -s ../ui-webapp/public", + "build-storybook": "build-storybook", + "image-snapshots": "jest \"image-snapshot.test.ts\"", + "a11y-check": "jest \"a11y.test.ts\"", + "depcheck": "depcheck --ignores=@scm-manager/prettier-config,@scm-manager/tsconfig,@babel/core,sass-loader,autoprefixer,babel-loader,postcss-loader,tailwindcss,storybook-addon-*,@storybook/*,webpack" + }, + "peerDependencies": { + "react": "^17.0.1", + "react-dom": "^17.0.1", + "react-router-dom": "^5.3.1", + "classnames": "^2.2.6" + }, + "devDependencies": { + "@scm-manager/ui-scripts": "2.37.3-SNAPSHOT", + "@scm-manager/ui-styles": "2.37.3-SNAPSHOT", + "@scm-manager/ui-api": "2.37.3-SNAPSHOT", + "@scm-manager/eslint-config": "^2.16.0", + "@babel/core": "^7.17.8", + "@scm-manager/tsconfig": "^2.12.0", + "@storybook/addon-essentials": "^6.4.20", + "@storybook/addon-interactions": "^6.4.20", + "@storybook/addon-a11y": "^6.4.20", + "@storybook/addon-links": "^6.4.20", + "@storybook/builder-webpack5": "^6.4.20", + "@storybook/manager-webpack5": "^6.4.20", + "@storybook/react": "^6.4.20", + "@storybook/addon-storyshots-puppeteer": "^6.4.20", + "@storybook/addon-storyshots": "^6.4.20", + "@storybook/testing-library": "^0.0.9", + "jest-transform-css": "^4.0.1", + "puppeteer": "^15.5.0", + "storybook-addon-pseudo-states": "^1.15.1", + "storybook-react-router": "^1.0.8", + "@types/storybook-react-router": "^1.0.2", + "sass-loader": "^12.3.0", + "storybook-addon-themes": "^6.1.0", + "autoprefixer": "^10.4.4", + "babel-loader": "^8.2.4", + "postcss": "^8.4.12", + "postcss-loader": "^6.2.1", + "tailwindcss": "^3.0.23", + "webpack": "5", + "tsup": "^6.1.2", + "mini-css-extract-plugin": "^1.6.2", + "html-webpack-plugin": "^5.5.0", + "react-query": "^3.25.1", + "i18next": "^19.9.2", + "react-i18next": "^10.13.2", + "i18next-fetch-backend": "^2.3.1" + }, + "babel": { + "presets": [ + "@scm-manager/babel-preset" + ] + }, + "jest": { + "transform": { + "^.+\\.[tj]sx?$": "babel-jest", + "^.+\\.(css|less|scss)$": "jest-transform-css", + "^.+\\.mdx?$": "@storybook/addon-docs/jest-transform-mdx" + } + }, + "prettier": "@scm-manager/prettier-config", + "eslintConfig": { + "extends": "@scm-manager/eslint-config" + }, + "publishConfig": { + "access": "restricted" + } +} diff --git a/scm-ui/ui-buttons/postcss.config.js b/scm-ui/ui-buttons/postcss.config.js new file mode 100644 index 0000000000..14a7a4674d --- /dev/null +++ b/scm-ui/ui-buttons/postcss.config.js @@ -0,0 +1,30 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +module.exports = { + plugins: { + tailwindcss: {}, + autoprefixer: {}, + }, +}; diff --git a/scm-ui/ui-buttons/src/__image_snapshots__/image-snapshot-test-ts-image-snapshots-tests-dark-states-1-snap.png b/scm-ui/ui-buttons/src/__image_snapshots__/image-snapshot-test-ts-image-snapshots-tests-dark-states-1-snap.png new file mode 100644 index 0000000000000000000000000000000000000000..f9ebfc3806ff715facd68fe4d62282db23304350 GIT binary patch literal 35883 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 Ax&QzG literal 0 HcmV?d00001 diff --git a/scm-ui/ui-buttons/src/a11y.test.ts b/scm-ui/ui-buttons/src/a11y.test.ts new file mode 100644 index 0000000000..99e8c009b2 --- /dev/null +++ b/scm-ui/ui-buttons/src/a11y.test.ts @@ -0,0 +1,34 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ +import initStoryshots from "@storybook/addon-storyshots"; +import { axeTest } from "@storybook/addon-storyshots-puppeteer"; +import path from "path"; + +initStoryshots({ + suite: "A11y checks", + test: axeTest({ + storybookUrl: `file://${path.resolve(__dirname, "../storybook-static")}`, + }), + storyNameRegex: /High-Contrast States/, +}); diff --git a/scm-ui/ui-buttons/src/button.stories.tsx b/scm-ui/ui-buttons/src/button.stories.tsx new file mode 100644 index 0000000000..b5cddfd31f --- /dev/null +++ b/scm-ui/ui-buttons/src/button.stories.tsx @@ -0,0 +1,91 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +import React from "react"; + +import { + Button as ButtonComponent, + ButtonVariantList, + ButtonVariants, + ExternalLinkButton as ExternalLinkButtonComponent, + LinkButton as LinkButtonComponent, +} from "./button"; +import StoryRouter from "storybook-react-router"; +import { StoryFn } from "@storybook/react"; + +type ExtractProps = T extends React.ComponentType ? U : never; + +// More on default export: https://storybook.js.org/docs/react/writing-stories/introduction#default-export +export default { + title: "Components", + component: null, + subcomponents: { + Button: ButtonComponent, + LinkButton: LinkButtonComponent, + ExternalLinkButton: ExternalLinkButtonComponent, + }, + argTypes: { + variant: { + options: ButtonVariantList, + control: { type: "select" }, + }, + }, + decorators: [StoryRouter()], + parameters: { + storyshots: { disable: true }, + }, +}; + +// More on component templates: https://storybook.js.org/docs/react/writing-stories/introduction#using-args +const ButtonTemplate: StoryFn> = (args) => ; +const LinkButtonTemplate: StoryFn> = (args) => ( + +); +const ExternalLinkButtonTemplate: StoryFn> = (args) => ( + +); + +export const Button = ButtonTemplate.bind({}); +// More on args: https://storybook.js.org/docs/react/writing-stories/args +Button.args = { + children: "Button", + variant: ButtonVariants.PRIMARY, + disabled: false, +}; + +export const LinkButton = LinkButtonTemplate.bind({}); +// More on args: https://storybook.js.org/docs/react/writing-stories/args +LinkButton.args = { + children: "Link Button", + to: "/repos", + variant: ButtonVariants.PRIMARY, +}; + +export const ExternalLinkButton = ExternalLinkButtonTemplate.bind({}); +// More on args: https://storybook.js.org/docs/react/writing-stories/args +ExternalLinkButton.args = { + children: "External Link Button", + href: "https://scm-manager.org", + variant: ButtonVariants.PRIMARY, +}; diff --git a/scm-ui/ui-buttons/src/button.test.stories.mdx b/scm-ui/ui-buttons/src/button.test.stories.mdx new file mode 100644 index 0000000000..83a22a4f4a --- /dev/null +++ b/scm-ui/ui-buttons/src/button.test.stories.mdx @@ -0,0 +1,73 @@ +import { Meta, Story } from "@storybook/addon-docs"; +import { Button, ButtonVariantList } from "./button"; + + + + `#${variant}-Hover`), + focus: ButtonVariantList.map(variant => `#${variant}-Focus`), + active: ButtonVariantList.map(variant => `#${variant}-Active`), + }, + themes: { + default: 'light', + }, +}}> + + + + {ButtonVariantList.map(variant => )} + + {["Normal", "Hover", "Active", "Focus", "Disabled"].map(state => + + {ButtonVariantList.map(variant => )} + )} +
STATE{variant.toUpperCase()}
{state}
+
+ + `#${variant}-Hover`), + focus: ButtonVariantList.map(variant => `#${variant}-Focus`), + active: ButtonVariantList.map(variant => `#${variant}-Active`), + }, + themes: { + default: 'dark', + }, +}}> + + + + {ButtonVariantList.map(variant => )} + + {["Normal", "Hover", "Active", "Focus", "Disabled"].map(state => + + {ButtonVariantList.map(variant => )} + )} +
STATE{variant.toUpperCase()}
{state}
+
+ + `#${variant}-Hover`), + focus: ButtonVariantList.map(variant => `#${variant}-Focus`), + active: ButtonVariantList.map(variant => `#${variant}-Active`), + }, + themes: { + default: 'highcontrast', + }, +}}> + + + + {ButtonVariantList.map(variant => )} + + {["Normal", "Hover", "Active", "Focus", "Disabled"].map(state => + + {ButtonVariantList.map(variant => )} + )} +
STATE{variant.toUpperCase()}
{state}
+
diff --git a/scm-ui/ui-buttons/src/button.tsx b/scm-ui/ui-buttons/src/button.tsx new file mode 100644 index 0000000000..8796a4113f --- /dev/null +++ b/scm-ui/ui-buttons/src/button.tsx @@ -0,0 +1,109 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +import React, { AnchorHTMLAttributes, ButtonHTMLAttributes } from "react"; +import { Link as ReactRouterLink, LinkProps as ReactRouterLinkProps } from "react-router-dom"; +import classNames from "classnames"; + +export const ButtonVariants = { + PRIMARY: "primary", + SECONDARY: "secondary", + TERTIARY: "tertiary", + SIGNAL: "signal", +} as const; + +export const ButtonVariantList = Object.values(ButtonVariants); + +type ButtonVariant = typeof ButtonVariants[keyof typeof ButtonVariants]; + +const BASE_BUTTON_CLASSES = classNames( + "inline-block whitespace-nowrap rounded border py-2 px-6 text-center font-semibold focus:z-10 focus:outline focus:outline-offset-2 focus:outline-purple-500 disabled:cursor-not-allowed" +); +const DEFAULT_BUTTON_CLASSES = classNames( + "border-gray-200 hover:border-gray-400 active:shadow-inner disabled:hover:border-gray-200 disabled:active:shadow-none" +); +const PRIMARY_BUTTON_CLASSES = classNames( + "border-transparent bg-primary text-primary-contrast hover:bg-primary-hover active:bg-primary-active disabled:bg-primary-disabled disabled:text-primary-disabled-contrast " +); +const SECONDARY_BUTTON_CLASSES = classNames( + "border-primary text-primary hover:border-primary-hover hover:text-primary-hover active:border-primary-active active:text-primary-active disabled:border-primary-disabled disabled:text-primary-disabled" +); +const TERTIARY_BUTTON_CLASSES = classNames( + "border-transparent text-primary hover:text-primary-hover active:text-primary-active disabled:text-primary-disabled" +); +const SIGNAL_BUTTON_CLASSES = classNames( + "border-transparent bg-signal text-signal-contrast hover:bg-signal-hover hover:text-signal-hover-contrast active:bg-signal-active active:text-signal-active-contrast disabled:bg-signal-disabled disabled:text-signal-disabled-contrast" +); + +const createButtonClasses = (variant?: ButtonVariant) => + classNames(BASE_BUTTON_CLASSES, { + [DEFAULT_BUTTON_CLASSES]: !variant, + [PRIMARY_BUTTON_CLASSES]: variant === "primary", + [SECONDARY_BUTTON_CLASSES]: variant === "secondary", + [TERTIARY_BUTTON_CLASSES]: variant === "tertiary", + [SIGNAL_BUTTON_CLASSES]: variant === "signal", + }); + +type BaseButtonProps = { + variant: ButtonVariant; +}; + +type ButtonProps = BaseButtonProps & ButtonHTMLAttributes; + +/** + * Styled html button + */ +export const Button = React.forwardRef( + ({ className, variant, children, ...props }, ref) => ( + + ) +); + +type LinkButtonProps = BaseButtonProps & ReactRouterLinkProps; + +/** + * Styled react router link + */ +export const LinkButton = React.forwardRef( + ({ className, variant, children, ...props }, ref) => ( + + {children} + + ) +); + +type ExternalLinkButtonProps = BaseButtonProps & AnchorHTMLAttributes; + +/** + * Styled html anchor + */ +export const ExternalLinkButton = React.forwardRef( + ({ className, variant, children, ...props }, ref) => ( + + {children} + + ) +); diff --git a/scm-ui/ui-buttons/src/image-snapshot.test.ts b/scm-ui/ui-buttons/src/image-snapshot.test.ts new file mode 100644 index 0000000000..d480f887d8 --- /dev/null +++ b/scm-ui/ui-buttons/src/image-snapshot.test.ts @@ -0,0 +1,33 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ +import path from "path"; +import initStoryshots from "@storybook/addon-storyshots"; +import { imageSnapshot } from "@storybook/addon-storyshots-puppeteer"; + +initStoryshots({ + suite: "Image snapshots", + test: imageSnapshot({ + storybookUrl: `file://${path.resolve(__dirname, "../storybook-static")}`, + }) +}); diff --git a/scm-ui/ui-buttons/src/index.css b/scm-ui/ui-buttons/src/index.css new file mode 100644 index 0000000000..7332595077 --- /dev/null +++ b/scm-ui/ui-buttons/src/index.css @@ -0,0 +1,26 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +@tailwind components; +@tailwind utilities; diff --git a/scm-ui/ui-buttons/src/index.ts b/scm-ui/ui-buttons/src/index.ts new file mode 100644 index 0000000000..be546f0875 --- /dev/null +++ b/scm-ui/ui-buttons/src/index.ts @@ -0,0 +1,27 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +import "./index.css"; + +export { Button, LinkButton, ExternalLinkButton, ButtonVariants } from "./button"; diff --git a/scm-ui/ui-buttons/tailwind.config.js b/scm-ui/ui-buttons/tailwind.config.js new file mode 100644 index 0000000000..5801157821 --- /dev/null +++ b/scm-ui/ui-buttons/tailwind.config.js @@ -0,0 +1,34 @@ +/* + * MIT License + * + * Copyright (c) 2020-present Cloudogu GmbH and Contributors + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +const path = require("path"); + +module.exports = { + presets: [ + // eslint-disable-next-line global-require,import/no-extraneous-dependencies + require("@scm-manager/ui-styles/src/tailwind.config.preset"), + ], + content: [path.join(__dirname, "src/**/*.tsx")], + important: true, +}; diff --git a/scm-ui/ui-buttons/tsconfig.json b/scm-ui/ui-buttons/tsconfig.json new file mode 100644 index 0000000000..cb06a28de9 --- /dev/null +++ b/scm-ui/ui-buttons/tsconfig.json @@ -0,0 +1,7 @@ +{ + "extends": "@scm-manager/tsconfig", + "include": [ + "./src", + "./docs" + ] +} diff --git a/scm-ui/ui-components/package.json b/scm-ui/ui-components/package.json index 282af272ed..6e0e959934 100644 --- a/scm-ui/ui-components/package.json +++ b/scm-ui/ui-components/package.json @@ -21,7 +21,7 @@ }, "devDependencies": { "@scm-manager/babel-preset": "^2.13.1", - "@scm-manager/eslint-config": "^2.15.1", + "@scm-manager/eslint-config": "^2.16.0", "@scm-manager/jest-preset": "^2.13.0", "@scm-manager/prettier-config": "^2.10.1", "@scm-manager/tsconfig": "^2.13.0", @@ -109,4 +109,4 @@ "publishConfig": { "access": "public" } -} \ No newline at end of file +} diff --git a/scm-ui/ui-components/src/OverviewPageActions.tsx b/scm-ui/ui-components/src/OverviewPageActions.tsx index 18c8959975..c1a3ac81db 100644 --- a/scm-ui/ui-components/src/OverviewPageActions.tsx +++ b/scm-ui/ui-components/src/OverviewPageActions.tsx @@ -23,9 +23,10 @@ */ import React, { FC, useState } from "react"; import { useHistory, useLocation } from "react-router-dom"; -import classNames from "classnames"; -import { Button, urls } from "./index"; +import { urls } from "./index"; import { FilterInput, Select } from "./forms"; +import { ButtonVariants, LinkButton } from "@scm-manager/ui-buttons"; +import classNames from "classnames"; type Props = { showCreateButton: boolean; @@ -54,7 +55,7 @@ const OverviewPageActions: FC = ({ label, testId, searchPlaceholder, - groupAriaLabelledby + groupAriaLabelledby, }) => { const history = useHistory(); const location = useLocation(); @@ -66,7 +67,7 @@ const OverviewPageActions: FC = ({ - - - One - -
- -
- - -
+
+
- - - -
- -
-

- Mind-paralyzing change needed improbability vortex machine sorts sought same theory upending job just allows +

+ +
+ + + +
+

+ Mind-paralyzing change needed improbability vortex machine sorts sought same theory upending job just allows hostess’s really oblong Infinite Improbability thing into the starship against which behavior accordance.with Kakrafoon humanoid undergarment ship powered by GPP-guided bowl of petunias nothing was frequently away incredibly ordinary mob. -

-
-
-