Skip to content

Commit

Permalink
build: support tsx components and storybook (#1564)
Browse files Browse the repository at this point in the history
* build: support tsx components and storybook

* improvement(storybook): props and style for button test case

* improvement(storybook): improve file structure

* feat: build proper tsx button component

* rfct: use new button component

* rfct: remove compiled files

* build: don't compile stories to js

* rfct: style

* rfct: use dash-case for button props

Reagent will convert it into camelCase automatically.

* docs: add js components ADR

* rfct: remove unused files

* rfct: simplify yarn clean cmd

* rfct: rename storybook scripts for consistency

* fix: remove unused src path

* build: only watch component dir for components

* docs: update js components ADR

* rfct: remove devcards

* rfct: remove main devcards file

* build: ignore storybook build folder

* docs: add deferred work items to JS components ADR

Co-authored-by: shanberg <[email protected]>
  • Loading branch information
filipesilva and shanberg authored Sep 8, 2021
1 parent c697b7c commit 925f7a4
Show file tree
Hide file tree
Showing 70 changed files with 8,390 additions and 2,762 deletions.
4 changes: 1 addition & 3 deletions .clj-kondo/config.edn
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
{:linters {:unresolved-namespace {:exclude [clojure.string]}
:unresolved-symbol {:exclude [(devcards.core/defcard)
(devcards.core/defcard-rg)
random-uuid
:unresolved-symbol {:exclude [random-uuid
goog.DEBUG
(com.rpl.specter/recursive-path)]}
:unused-referred-var {:exclude {clojure.test [is deftest testing]}}
Expand Down
9 changes: 9 additions & 0 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,9 @@ jobs:
- name: Fetch JS deps
run: yarn

- name: Compile components
run: yarn components

# TODO: re-enable once web build is fixed
# - name: Run Karma tests
# run: script/test/karma
Expand Down Expand Up @@ -165,6 +168,9 @@ jobs:
- name: Fetch yarn
run: yarn install --frozen-lockfile

- name: Compile components
run: yarn components

- name: Compile app
run: COMMIT_URL="https://github.com/${GITHUB_REPOSITORY}/commit/${GITHUB_SHA}" lein run -m shadow.cljs.devtools.cli --npm release app --config-merge "{:closure-defines {athens.core/SENTRY_DSN \"${SENTRY_DSN}\" athens.util/COMMIT_URL \"${COMMIT_URL}\" }}"
env:
Expand Down Expand Up @@ -239,6 +245,9 @@ jobs:
mkdir -p ~/private_keys/
echo '${{ secrets.api_key }}' > ~/private_keys/AuthKey_${{ secrets.api_key_id }}.p8
- name: Compile components
run: yarn components

- name: Compile JS Assets (*nix)
if: matrix.os != 'windows-latest'
run: lein run -m shadow.cljs.devtools.cli --npm release main renderer --config-merge "{:closure-defines {athens.core/SENTRY_DSN \"${SENTRY_DSN}\" athens.main.core/AUTO_UPDATE ${AUTO_UPDATE}}}"
Expand Down
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -31,3 +31,7 @@

# electron build
dist

# design system ts output
/src/js/components/**/*.js
/storybook-static
19 changes: 19 additions & 0 deletions .storybook/main.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
module.exports = {
"stories": [
"../src/js/**/*.stories.mdx",
"../src/js/**/*.stories.tsx"
],
"addons": [
"@storybook/addon-links",
"@storybook/addon-essentials"
],
webpackFinal: async (config, { configType }) => {
// Always prefer .tsx files when resolving modules.
// We output the .js files from tsc directly on the same folder, but want
// storybook to process the original .tsx for the additional TS tooling.
config.resolve.extensions.unshift(".tsx");

// Return the altered config.
return config;
}
}
146 changes: 146 additions & 0 deletions .storybook/preview.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
import React from 'react';
import styled from 'styled-components';

export const parameters = {
actions: { argTypesRegex: "^on[A-Z].*" },
controls: {
matchers: {
color: /(background|color)$/i,
date: /Date$/,
},
},
}

const cssVars = `
:root {
--background-color---opacity-high: hsla(0, 0%, 10.196078431372548%, 0.75);
--background-color---opacity-higher: hsla(0, 0%, 10.196078431372548%, 0.85);
--background-color---opacity-low: hsla(0, 0%, 10.196078431372548%, 0.25);
--background-color---opacity-lower: hsla(0, 0%, 10.196078431372548%, 0.1);
--background-color---opacity-med: hsla(0, 0%, 10.196078431372548%, 0.5);
--background-color: #1A1A1A;
--background-minus-1---opacity-high: hsla(0, 0%, 8.235294117647058%, 0.75);
--background-minus-1---opacity-higher: hsla(0, 0%, 8.235294117647058%, 0.85);
--background-minus-1---opacity-low: hsla(0, 0%, 8.235294117647058%, 0.25);
--background-minus-1---opacity-lower: hsla(0, 0%, 8.235294117647058%, 0.1);
--background-minus-1---opacity-med: hsla(0, 0%, 8.235294117647058%, 0.5);
--background-minus-1: #151515;
--background-minus-2---opacity-high: hsla(0, 0%, 6.6667%, 0.75);
--background-minus-2---opacity-higher: hsla(0, 0%, 6.6667%, 0.85);
--background-minus-2---opacity-low: hsla(0, 0%, 6.6667%, 0.25);
--background-minus-2---opacity-lower: hsla(0, 0%, 6.6667%, 0.1);
--background-minus-2---opacity-med: hsla(0, 0%, 6.6667%, 0.5);
--background-minus-2: #111;
--background-plus-1---opacity-high: hsla(0, 0%, 13.333%, 0.75);
--background-plus-1---opacity-higher: hsla(0, 0%, 13.333%, 0.85);
--background-plus-1---opacity-low: hsla(0, 0%, 13.333%, 0.25);
--background-plus-1---opacity-lower: hsla(0, 0%, 13.333%, 0.1);
--background-plus-1---opacity-med: hsla(0, 0%, 13.333%, 0.5);
--background-plus-1: #222;
--background-plus-2---opacity-high: hsla(0, 0%, 20%, 0.75);
--background-plus-2---opacity-higher: hsla(0, 0%, 20%, 0.85);
--background-plus-2---opacity-low: hsla(0, 0%, 20%, 0.25);
--background-plus-2---opacity-lower: hsla(0, 0%, 20%, 0.1);
--background-plus-2---opacity-med: hsla(0, 0%, 20%, 0.5);
--background-plus-2: #333;
--body-text-color---opacity-high: hsla(0, 0%, 66.666%, 0.75);
--body-text-color---opacity-higher: hsla(0, 0%, 66.666%, 0.85);
--body-text-color---opacity-low: hsla(0, 0%, 66.666%, 0.25);
--body-text-color---opacity-lower: hsla(0, 0%, 66.666%, 0.1);
--body-text-color---opacity-med: hsla(0, 0%, 66.666%, 0.5);
--body-text-color: #AAA;
--border-color---opacity-high: hsla(0, 0%, 0%, 0.75);
--border-color---opacity-higher: hsla(0, 0%, 0%, 0.85);
--border-color---opacity-low: hsla(0, 0%, 0%, 0.25);
--border-color---opacity-lower: hsla(0, 0%, 0%, 0.1);
--border-color---opacity-med: hsla(0, 0%, 0%, 0.5);
--border-color: hsla(32, 81%, 90%, 0.08);
--confirmation-color---opacity-high: hsla(133.43283582089555, 73.62637362637363%, 35.68627450980392%, 0.75);
--confirmation-color---opacity-higher: hsla(133.43283582089555, 73.62637362637363%, 35.68627450980392%, 0.85);
--confirmation-color---opacity-low: hsla(133.43283582089555, 73.62637362637363%, 35.68627450980392%, 0.25);
--confirmation-color---opacity-lower: hsla(133.43283582089555, 73.62637362637363%, 35.68627450980392%, 0.1);
--confirmation-color---opacity-med: hsla(133.43283582089555, 73.62637362637363%, 35.68627450980392%, 0.5);
--confirmation-color: #189E36;
--error-color---opacity-high: hsla(4.838709677419331, 97.89473684210527%, 62.745098039215684%, 0.75);
--error-color---opacity-higher: hsla(4.838709677419331, 97.89473684210527%, 62.745098039215684%, 0.85);
--error-color---opacity-low: hsla(4.838709677419331, 97.89473684210527%, 62.745098039215684%, 0.25);
--error-color---opacity-lower: hsla(4.838709677419331, 97.89473684210527%, 62.745098039215684%, 0.1);
--error-color---opacity-med: hsla(4.838709677419331, 97.89473684210527%, 62.745098039215684%, 0.5);
--error-color: #fd5243;
--graph-control-bg---opacity-high: hsla(0, 0%, 15.294117647058824%, 0.75);
--graph-control-bg---opacity-higher: hsla(0, 0%, 15.294117647058824%, 0.85);
--graph-control-bg---opacity-low: hsla(0, 0%, 15.294117647058824%, 0.25);
--graph-control-bg---opacity-lower: hsla(0, 0%, 15.294117647058824%, 0.1);
--graph-control-bg---opacity-med: hsla(0, 0%, 15.294117647058824%, 0.5);
--graph-control-bg: #272727;
--graph-control-color---opacity-high: hsla(0, 0%, 0%, 0.75);
--graph-control-color---opacity-higher: hsla(0, 0%, 0%, 0.85);
--graph-control-color---opacity-low: hsla(0, 0%, 0%, 0.25);
--graph-control-color---opacity-lower: hsla(0, 0%, 0%, 0.1);
--graph-control-color---opacity-med: hsla(0, 0%, 0%, 0.5);
--graph-control-color: white;
--graph-link-normal---opacity-high: hsla(0, 0%, 19.607843137254903%, 0.75);
--graph-link-normal---opacity-higher: hsla(0, 0%, 19.607843137254903%, 0.85);
--graph-link-normal---opacity-low: hsla(0, 0%, 19.607843137254903%, 0.25);
--graph-link-normal---opacity-lower: hsla(0, 0%, 19.607843137254903%, 0.1);
--graph-link-normal---opacity-med: hsla(0, 0%, 19.607843137254903%, 0.5);
--graph-link-normal: #323232;
--graph-node-hlt---opacity-high: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.75);
--graph-node-hlt---opacity-higher: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.85);
--graph-node-hlt---opacity-low: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.25);
--graph-node-hlt---opacity-lower: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.1);
--graph-node-hlt---opacity-med: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.5);
--graph-node-hlt: #FBBE63;
--graph-node-normal---opacity-high: hsla(0, 0%, 56.470588235294116%, 0.75);
--graph-node-normal---opacity-higher: hsla(0, 0%, 56.470588235294116%, 0.85);
--graph-node-normal---opacity-low: hsla(0, 0%, 56.470588235294116%, 0.25);
--graph-node-normal---opacity-lower: hsla(0, 0%, 56.470588235294116%, 0.1);
--graph-node-normal---opacity-med: hsla(0, 0%, 56.470588235294116%, 0.5);
--graph-node-normal: #909090;
--header-text-color---opacity-high: hsla(0, 0%, 72.94117647058823%, 0.75);
--header-text-color---opacity-higher: hsla(0, 0%, 72.94117647058823%, 0.85);
--header-text-color---opacity-low: hsla(0, 0%, 72.94117647058823%, 0.25);
--header-text-color---opacity-lower: hsla(0, 0%, 72.94117647058823%, 0.1);
--header-text-color---opacity-med: hsla(0, 0%, 72.94117647058823%, 0.5);
--header-text-color: #BABABA;
--highlight-color---opacity-high: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.75);
--highlight-color---opacity-higher: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.85);
--highlight-color---opacity-low: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.25);
--highlight-color---opacity-lower: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.1);
--highlight-color---opacity-med: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.5);
--highlight-color: #FBBE63;
--link-color---opacity-high: hsla(203.8775510204082, 80.32786885245902%, 52.156862745098046%, 0.75);
--link-color---opacity-higher: hsla(203.8775510204082, 80.32786885245902%, 52.156862745098046%, 0.85);
--link-color---opacity-low: hsla(203.8775510204082, 80.32786885245902%, 52.156862745098046%, 0.25);
--link-color---opacity-lower: hsla(203.8775510204082, 80.32786885245902%, 52.156862745098046%, 0.1);
--link-color---opacity-med: hsla(203.8775510204082, 80.32786885245902%, 52.156862745098046%, 0.5);
--link-color: #2399E7;
--text-highlight-color---opacity-high: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.75);
--text-highlight-color---opacity-higher: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.85);
--text-highlight-color---opacity-low: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.25);
--text-highlight-color---opacity-lower: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.1);
--text-highlight-color---opacity-med: hsla(35.92105263157896, 94.99999999999999%, 68.62745098039215%, 0.5);
--text-highlight-color: #FBBE63;
--warning-color---opacity-high: hsla(8.571428571428555, 74.11764705882354%, 50%, 0.75);
--warning-color---opacity-higher: hsla(8.571428571428555, 74.11764705882354%, 50%, 0.85);
--warning-color---opacity-low: hsla(8.571428571428555, 74.11764705882354%, 50%, 0.25);
--warning-color---opacity-lower: hsla(8.571428571428555, 74.11764705882354%, 50%, 0.1);
--warning-color---opacity-med: hsla(8.571428571428555, 74.11764705882354%, 50%, 0.5);
--warning-color: #DE3C21;
}
.docs-story {
background: var(--background-color);
}`

const StoryWrapper = styled.div`
`;

export const decorators = [
(Story) => (
<StoryWrapper>
<style>{cssVars}</style>
<Story />
</StoryWrapper>
),
];
52 changes: 52 additions & 0 deletions doc/adr/0010-js-components.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
# 10. JS Components

Date: 2021-08-23

## Status

Proposed.


## Context

Inspired by [David Nolen's ClojureScript in the Age of TypeScript](https://vouch.io/developing-mobile-digital-key-applications-with-clojurescript/) talk and post, we started thinking about how viable it would be to use JS (instead of CLJS) components.

This change would provide design with a better and more familiar development environment for components and reduce their dependency on engineering to ship work.
The separation also has several second order benefits related to organization and communication.

Costs for this change are centered around the degree of separation between application and components, where cljs is the primary language on the former and js on the latter, and maintaining extra tooling.

Part of [Ongoing Hypothesis](https://docs.google.com/document/d/18ExzXHB5aezyINmIVWDBpZpXgV67kAhuAO8MvX6dbPw/edit).


## Decision

Decided to use JS components with Storybook, compiled from TSX, after seeing how much Stuart was able to get done with them.


## Consequences

Negative consequences:
* JS/CLJS context switching when working in the app and on components at the same time
* Higher surface area for JS interop problems
* More complex build step
* More tooling to maintain
* Harder for for CLJS engineers to develop and maintain components


Positive consequences:
* Better development and testing environment for components
* Clearer defined deliverable scope and context for components
* Component documentation
* Smaller and simpler application codebase
* Looser coupling between engineering and design
* Design can deliver work on separate cadence, units, and timeline, from engineering
* Easier to enforce discipline on components as pure functions
* CLJS proficiency is not necessary for design work
* Easier for contributors to contribute to components
* Reduced bus factor in design

Deferred work items:
* The [devcards style guide](https://github.com/athensresearch/athens/blob/c697b7c62d60dd9fca0b03a32b35cc4776a90c54/src/cljs/athens/devcards/style_guide.cljs) will need to be reimplemented in Storybook
* The [devcards stylify guide conventions](https://github.com/athensresearch/athens/blob/c697b7c62d60dd9fca0b03a32b35cc4776a90c54/src/cljs/athens/devcards/styling_with_stylefy.cljs) will need to be carried over to Storybook equivalents
* The [partial work on filters](https://github.com/athensresearch/athens/blob/feature/rtc-v1/src/cljs/athens/views/filters.cljs) should be used as reference for a future filters implementation
30 changes: 23 additions & 7 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,16 @@
"scripts": {
"update:dry": "standard-version --dry-run -p --releaseCommitMessageFormat v{{currentTag}}",
"update": "standard-version -p --releaseCommitMessageFormat v{{currentTag}}",
"dev": "shadow-cljs watch main renderer app",
"compile": "shadow-cljs compile main renderer app",
"prod": "shadow-cljs release main renderer app",
"clean": "rm -rf resources/public/**/*.js && rm -rf target && rm -rf .shadow-cljs",
"dist": "electron-builder -p always"
"dev": "concurrently \"yarn components:watch\" \"yarn client:watch\"",
"client:watch": "shadow-cljs watch main renderer app",
"components": "yarn tsc",
"components:watch": "yarn tsc --watch",
"compile": "yarn components && shadow-cljs compile main renderer app",
"prod": "yarn components && shadow-cljs release main renderer app",
"clean": "rm -rf resources/public/**/*.js target .shadow-cljs ./src/stories/**/*.js",
"dist": "electron-builder -p always",
"storybook:watch": "start-storybook -p 6006",
"storybook": "build-storybook"
},
"main": "resources/main.js",
"build": {
Expand Down Expand Up @@ -66,16 +71,26 @@
"electron-log": "^4.2.4",
"electron-updater": "^4.3.4",
"highlight.js": "^10.7.2",
"iconoir": "^1.0.0",
"katex": "^0.12.0",
"marked": "^1.0.0",
"nedb": "^1.8.0",
"react": "17.0.1",
"react-codemirror2": "^7.2.1",
"react-dom": "17.0.1",
"react-force-graph-2d": "^1.19.0",
"react-highlight.js": "1.0.7"
"react-highlight.js": "1.0.7",
"styled-components": "^5.3.0",
"tslib": "^2.3.1"
},
"devDependencies": {
"@babel/core": "^7.15.0",
"@storybook/addon-actions": "^6.3.7",
"@storybook/addon-essentials": "^6.3.7",
"@storybook/addon-links": "^6.3.7",
"@storybook/react": "^6.3.7",
"babel-loader": "^8.2.2",
"concurrently": "^6.2.1",
"electron": "^12.0.4",
"electron-builder": "22.10",
"electron-builder-notarize": "^1.2.0",
Expand All @@ -86,7 +101,8 @@
"karma-junit-reporter": "^2.0.1",
"shadow-cljs": "^2.15.3",
"source-map-support": "^0.5.19",
"standard-version": "^9.3.1"
"standard-version": "^9.3.1",
"typescript": "^4.3.5"
},
"standard-version": {
"types": [
Expand Down
3 changes: 0 additions & 3 deletions project.clj
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@
[metosin/reitit "0.5.13"]
[metosin/komponentit "0.3.10"]
[instaparse/instaparse "1.4.10"]
[devcards/devcards "0.2.7"]
[borkdude/sci "0.2.5"]
[garden/garden "1.3.10"]
[stylefy/stylefy "3.0.0"]
Expand Down Expand Up @@ -76,8 +75,6 @@
["run" "-m" "shadow.cljs.devtools.cli" "compile" "main" "renderer" "app"]]
"prod" ["with-profile" "prod" "do"
["run" "-m" "shadow.cljs.devtools.cli" "release" "main" "renderer" "app"]]
"devcards" ["with-profile" "dev" "do"
["run" "-m" "shadow.cljs.devtools.cli" "watch" "devcards"]]
"build-report" ["with-profile" "prod" "do"
["run" "-m" "shadow.cljs.devtools.cli" "run" "shadow.cljs.build-report" "app" "target/build-report.html"]
["shell" "open" "target/build-report.html"]]
Expand Down
17 changes: 0 additions & 17 deletions resources/public/cards.html

This file was deleted.

6 changes: 0 additions & 6 deletions shadow-cljs.edn
Original file line number Diff line number Diff line change
Expand Up @@ -38,12 +38,6 @@
:main athens.main.core/main
:compiler-options {:output-feature-set :es-next}}

:devcards {:asset-path "js/devcards"
:modules {:main {:init-fn athens.devcards/main}}
:compiler-options {:devcards true}
:output-dir "resources/public/js/devcards"
:target :browser}

:karma-test {:target :karma
:ns-regexp "-test$"
:output-to "target/karma-test.js"}}}
Loading

0 comments on commit 925f7a4

Please sign in to comment.