nitro-web 0.0.1 → 0.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintrc.json +2 -5
- package/_example/{.env-example → .env} +3 -3
- package/_example/client/config.ts +1 -5
- package/_example/client/index.ts +1 -18
- package/_example/components/auth.api.js +1 -1
- package/_example/components/index.tsx +11 -3
- package/_example/components/settings.api.js +1 -1
- package/_example/package.json +109 -0
- package/_example/server/config.js +3 -16
- package/_example/server/index.js +4 -3
- package/_example/tailwind.config.js +12 -21
- package/_example/tsconfig.json +2 -2
- package/_example/types/index.d.ts +13 -0
- package/_example/types/twin.d.ts +19 -0
- package/_example/webpack.config.js +2 -3
- package/client/index.js +42 -0
- package/components/auth/signin.jsx +9 -1
- package/components/partials/element/modal.jsx +1 -1
- package/components/partials/form/drop-handler.jsx +1 -1
- package/components/partials/form/input-currency.jsx +5 -2
- package/components/partials/form/input-date.jsx +6 -6
- package/components/partials/form/input.jsx +9 -9
- package/components/partials/layout/layout2.jsx +1 -1
- package/components/partials/styleguide.jsx +6 -7
- package/components/settings/settings-account.jsx +1 -1
- package/components/settings/settings-business.jsx +1 -4
- package/components/settings/settings-team--member.jsx +1 -1
- package/package.json +28 -97
- package/readme.md +39 -9
- package/server/email/index.js +12 -10
- package/server/index.js +23 -0
- package/server/router.js +4 -8
- package/util.js +13 -0
- package/webpack.config.js +43 -42
- package/_example/types.d.ts +0 -7
- package/client.js +0 -42
- package/server.js +0 -20
|
@@ -17,7 +17,7 @@ export function Layout2({ Logo }) {
|
|
|
17
17
|
<Outlet />
|
|
18
18
|
</div>
|
|
19
19
|
|
|
20
|
-
<div class="wrapper-2 w-full px-5 pb-4 flex items-center
|
|
20
|
+
<div class="wrapper-2 w-full px-5 pb-4 flex items-center text-sm text-[#1F1F1F]">
|
|
21
21
|
<ul class="flex-1 flex gap-4 list-style-none">
|
|
22
22
|
<li><Link class="underline1" to="/">Home</Link></li>
|
|
23
23
|
<li><Link class="underline1" to="/signin">About</Link></li>
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
/*eslint-disable*/
|
|
2
1
|
import { getCountryOptions, getCurrencyOptions, ucFirst } from '../../util.js'
|
|
3
2
|
import { CheckIcon } from '@heroicons/react/20/solid'
|
|
4
3
|
import { Input } from './form/input.jsx'
|
|
@@ -14,14 +13,13 @@ export function Styleguide({ config }) {
|
|
|
14
13
|
address: '',
|
|
15
14
|
country: 'us',
|
|
16
15
|
currency: 'nzd', // can be commented too
|
|
17
|
-
|
|
18
|
-
|
|
16
|
+
amount: 100,
|
|
17
|
+
brandColor: '#F3CA5F',
|
|
19
18
|
firstName: 'Tony',
|
|
20
19
|
date: Date.now(),
|
|
21
20
|
errors: [
|
|
22
21
|
{ title: 'address', detail: 'Address is required' },
|
|
23
22
|
{ title: 'currency', detail: 'Currency is required' },
|
|
24
|
-
// { title: 'brandColor', detail: 'Color is required' },
|
|
25
23
|
],
|
|
26
24
|
})
|
|
27
25
|
|
|
@@ -75,7 +73,8 @@ export function Styleguide({ config }) {
|
|
|
75
73
|
</div>
|
|
76
74
|
<div>
|
|
77
75
|
<label for="input1">Label</label>
|
|
78
|
-
<Checkbox name="input1" type="radio" text="Radio 1" subtext="some additional text here 1." id="input1-1" class="!mb-0"
|
|
76
|
+
<Checkbox name="input1" type="radio" text="Radio 1" subtext="some additional text here 1." id="input1-1" class="!mb-0"
|
|
77
|
+
defaultChecked />
|
|
79
78
|
<Checkbox name="input1" type="radio" text="Radio 2" subtext="some additional text here 2." id="input1-2" class="!mt-0" />
|
|
80
79
|
</div>
|
|
81
80
|
<div>
|
|
@@ -118,8 +117,8 @@ export function Styleguide({ config }) {
|
|
|
118
117
|
<div><Button color="primary-md">*-md (default)</Button></div>
|
|
119
118
|
<div><Button color="primary-lg">*-lg button</Button></div>
|
|
120
119
|
<div><Button IconLeft={<CheckIcon class="size-5 -my-5 -mx-0.5" />}>IconLeft=Element</Button></div>
|
|
121
|
-
<div><Button IconRight="v">IconRight
|
|
122
|
-
<div><Button IconRight2="v" className="w-[200px]">IconRight2
|
|
120
|
+
<div><Button IconRight="v">IconRight="v"</Button></div>
|
|
121
|
+
<div><Button IconRight2="v" className="w-[200px]">IconRight2="v"</Button></div>
|
|
123
122
|
<div><Button color="primary" isLoading>primary isLoading</Button></div>
|
|
124
123
|
</div>
|
|
125
124
|
|
|
@@ -36,7 +36,7 @@ export function SettingsBusiness({ config }) {
|
|
|
36
36
|
}
|
|
37
37
|
|
|
38
38
|
return (
|
|
39
|
-
<div
|
|
39
|
+
<div>
|
|
40
40
|
<Topbar
|
|
41
41
|
title={<>Settings</>}
|
|
42
42
|
submenu={
|
|
@@ -116,6 +116,3 @@ export function SettingsBusiness({ config }) {
|
|
|
116
116
|
)
|
|
117
117
|
}
|
|
118
118
|
|
|
119
|
-
import { css } from '@emotion/react'
|
|
120
|
-
const style = (_theme) => css`
|
|
121
|
-
`
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// todo: finish tailwind conversion
|
|
2
|
-
import { css } from '
|
|
2
|
+
import { css } from 'twin.macro'
|
|
3
3
|
import { Button } from '../partials/element/button.jsx'
|
|
4
4
|
import { Modal } from '../partials/element/modal.jsx'
|
|
5
5
|
import { FormError } from '../partials/form/form-error.jsx'
|
package/package.json
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"name": "nitro-web",
|
|
3
3
|
"description": "Nitro is a battle-tested, modular base project to turbocharge your projects, styled using Tailwind 🚀",
|
|
4
4
|
"repository": "github:boycce/nitro-web",
|
|
5
|
-
"version": "0.0.
|
|
5
|
+
"version": "0.0.3",
|
|
6
6
|
"main": "client.js",
|
|
7
7
|
"type": "module",
|
|
8
8
|
"keywords": [
|
|
@@ -14,41 +14,28 @@
|
|
|
14
14
|
"tailwind",
|
|
15
15
|
"webpack"
|
|
16
16
|
],
|
|
17
|
-
"
|
|
18
|
-
"
|
|
19
|
-
|
|
20
|
-
"
|
|
21
|
-
"
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
17
|
+
"workspaces": [
|
|
18
|
+
"_example"
|
|
19
|
+
],
|
|
20
|
+
"exports": {
|
|
21
|
+
".": "./client/index.js",
|
|
22
|
+
"./server": "./server/index.js",
|
|
23
|
+
"./util": "./util.js",
|
|
24
|
+
"./.eslintrc.json": "./.eslintrc.json",
|
|
25
|
+
"./webpack.config.js": "./webpack.config.js"
|
|
25
26
|
},
|
|
26
27
|
"scripts": {
|
|
27
|
-
"
|
|
28
|
-
"dev": "clear && npm run dev:server:lint --silent & npm run dev:server --silent & npm run dev:client --silent",
|
|
29
|
-
"dev:client": "NITRO=true webpack serve --progress --config ./_example/webpack.config.js",
|
|
30
|
-
"dev:server": "NITRO=true nodemon ./_example/server -q -w ./_example/server/ -w ./_example/components/ -w ./server/ -w ./components/ -e js",
|
|
31
|
-
"dev:server:lint": "eslint ./_example/components ./_example/server ./components/ ./server/",
|
|
28
|
+
"dev": "npm run dev -w example",
|
|
32
29
|
"major": "standard-version --release-as major && npm publish",
|
|
33
30
|
"minor": "standard-version --release-as minor && npm publish",
|
|
34
|
-
"patch": "standard-version --release-as patch && npm publish"
|
|
35
|
-
"start": "node ./_example/server",
|
|
36
|
-
"stripe": "stripe listen --forward-to localhost:3001/api/stripe/webhook"
|
|
31
|
+
"patch": "standard-version --release-as patch && npm publish"
|
|
37
32
|
},
|
|
38
33
|
"dependencies": {
|
|
39
|
-
"@emotion/react": "^11.11.4",
|
|
40
|
-
"@headlessui/react": "^2.2.0",
|
|
41
|
-
"@heroicons/react": "^2.2.0",
|
|
42
|
-
"@hokify/axios": "^0.19.1",
|
|
43
|
-
"@stripe/react-stripe-js": "^1.9.0",
|
|
44
|
-
"@stripe/stripe-js": "^1.34.0",
|
|
45
34
|
"@uiw/color-convert": "^2.3.0",
|
|
46
35
|
"@uiw/react-color-hue": "^2.3.0",
|
|
47
36
|
"@uiw/react-color-saturation": "^2.3.0",
|
|
48
|
-
"axios-retry": "^3.3.1",
|
|
49
37
|
"bcrypt": "^5.0.0",
|
|
50
38
|
"body-parser": "^1.19.0",
|
|
51
|
-
"chart.js": "^4.4.3",
|
|
52
39
|
"compression": "^1.7.4",
|
|
53
40
|
"connect-mongo": "^5.1.0",
|
|
54
41
|
"date-fns": "^3.6.0",
|
|
@@ -58,98 +45,51 @@
|
|
|
58
45
|
"express-fileupload": "^1.1.6",
|
|
59
46
|
"express-session": "^1.17.0",
|
|
60
47
|
"inline-css": "^4.0.2",
|
|
61
|
-
"monastery": "~3.5.1",
|
|
62
48
|
"nanoid": "^4.0.0",
|
|
63
49
|
"nodemailer": "^6.5.0",
|
|
64
50
|
"nodemailer-mailgun-transport": "^2.0.2",
|
|
65
51
|
"nunjucks": "^3.2.2",
|
|
66
52
|
"passport": "^0.4.1",
|
|
67
|
-
"passport-jwt": "^4.0.0",
|
|
68
53
|
"passport-local": "^1.0.0",
|
|
69
|
-
"pdf-to-img": "^4.1.0",
|
|
70
|
-
"pdfmake": "0.2.7",
|
|
71
|
-
"react": "^18.3.1",
|
|
72
|
-
"react-chartjs-2": "^5.2.0",
|
|
73
54
|
"react-currency-input-field": "^3.8.0",
|
|
74
55
|
"react-day-picker": "^8.10.1",
|
|
75
|
-
"react-dom": "^18.3.1",
|
|
76
56
|
"react-number-format": "^5.4.0",
|
|
77
57
|
"react-router-dom": "6.24.1",
|
|
78
58
|
"react-select": "^5.9.0",
|
|
79
59
|
"react-tracked": "^1.3.0",
|
|
80
|
-
"sort-route-addresses-nodeps": "0.0.4"
|
|
81
|
-
|
|
60
|
+
"sort-route-addresses-nodeps": "0.0.4"
|
|
61
|
+
},
|
|
62
|
+
"peerDependencies": {
|
|
63
|
+
"@headlessui/react": "^2.2.0",
|
|
64
|
+
"@heroicons/react": "^2.2.0",
|
|
65
|
+
"@hokify/axios": "^0.19.1",
|
|
66
|
+
"@stripe/stripe-js": "^1.34.0",
|
|
67
|
+
"axios-retry": "^3.3.1",
|
|
68
|
+
"monastery": "^3.5.2",
|
|
69
|
+
"react": "^18.3.1",
|
|
70
|
+
"react-dom": "^18.3.1",
|
|
71
|
+
"stripe": "^9.16.0",
|
|
72
|
+
"twin.macro": "^3.4.1"
|
|
82
73
|
},
|
|
83
74
|
"devDependencies": {
|
|
84
|
-
"@babel/core": "^7.8.0",
|
|
85
|
-
"@babel/plugin-syntax-dynamic-import": "^7.8.3",
|
|
86
|
-
"@babel/plugin-transform-runtime": "^7.17.0",
|
|
87
|
-
"@babel/preset-env": "^7.8.0",
|
|
88
|
-
"@babel/preset-react": "^7.9.4",
|
|
89
|
-
"@babel/preset-typescript": "^7.24.7",
|
|
90
|
-
"@emotion/babel-plugin": "^11.11.0",
|
|
91
75
|
"@emotion/eslint-plugin": "^11.11.0",
|
|
92
|
-
"@
|
|
93
|
-
"@
|
|
76
|
+
"@emotion/react": "^11.11.4",
|
|
77
|
+
"@emotion/styled": "^11.11.4",
|
|
94
78
|
"@types/react": "^19.0.2",
|
|
95
79
|
"@types/react-dom": "^19.0.2",
|
|
96
80
|
"@typescript-eslint/eslint-plugin": "^8.18.1",
|
|
97
81
|
"@typescript-eslint/parser": "^8.18.1",
|
|
98
|
-
"autoprefixer": "^9.8.8",
|
|
99
82
|
"babel-eslint": "^10.0.3",
|
|
100
|
-
"babel-loader": "^8.0.6",
|
|
101
|
-
"babel-plugin-macros": "^3.1.0",
|
|
102
|
-
"babel-plugin-react-html-attrs": "^2.1.0",
|
|
103
|
-
"clean-terminal-webpack-plugin": "https://github.com/boycce/clean-terminal-webpack-plugin.git",
|
|
104
|
-
"color": "^4.2.3",
|
|
105
|
-
"copy-webpack-plugin": "^12.0.2",
|
|
106
|
-
"core-js": "^3.12.1",
|
|
107
|
-
"css-loader": "^3.6.0",
|
|
108
|
-
"csv-loader": "^3.0.5",
|
|
109
83
|
"eslint": "^8.57.1",
|
|
110
84
|
"eslint-plugin-import": "^2.26.0",
|
|
111
|
-
"eslint-plugin-jest": "^28.9.0",
|
|
112
85
|
"eslint-plugin-react": "^7.19.0",
|
|
113
86
|
"eslint-plugin-react-hooks": "^4.0.0",
|
|
114
87
|
"eslint-webpack-plugin": "^2.7.0",
|
|
115
|
-
"
|
|
116
|
-
"html-webpack-plugin": "^5.6.0",
|
|
117
|
-
"jest": "^29.7.0",
|
|
118
|
-
"migrate-mongo": "^10.0.0",
|
|
119
|
-
"mini-css-extract-plugin": "^2.9.0",
|
|
120
|
-
"nodemon": "^2.0.1",
|
|
121
|
-
"postcss": "^8.4.49",
|
|
122
|
-
"postcss-for": "^2.1.1",
|
|
123
|
-
"postcss-import": "^16.1.0",
|
|
124
|
-
"postcss-import-resolver": "^2.0.0",
|
|
125
|
-
"postcss-loader": "^8.1.1",
|
|
126
|
-
"postcss-nested": "^7.0.2",
|
|
127
|
-
"react-refresh": "^0.14.2",
|
|
128
|
-
"standard-version": "^9.3.2",
|
|
129
|
-
"string-replace-loader": "^3.1.0",
|
|
130
|
-
"super-nunjucks-loader": "^2.0.0",
|
|
131
|
-
"tailwind-merge": "^2.6.0",
|
|
132
|
-
"tailwindcss": "^3.4.17",
|
|
133
|
-
"twin.macro": "^3.4.1",
|
|
134
|
-
"typescript": "^5.5.2",
|
|
135
|
-
"webpack": "^5.92.1",
|
|
136
|
-
"webpack-cli": "^5.1.4",
|
|
137
|
-
"webpack-dev-server": "^4.6.0",
|
|
138
|
-
"webpack-node-externals": "^1.7.2"
|
|
88
|
+
"standard-version": "^9.3.2"
|
|
139
89
|
},
|
|
140
90
|
"engines": {
|
|
141
91
|
"node": "^18"
|
|
142
92
|
},
|
|
143
|
-
"browserslist": [
|
|
144
|
-
"> 1%",
|
|
145
|
-
"last 2 versions",
|
|
146
|
-
"not ie <= 10"
|
|
147
|
-
],
|
|
148
|
-
"nodemonConfig": {
|
|
149
|
-
"events": {
|
|
150
|
-
"restart": "echo \"\\033[0;35mExpress restarting..\\033[0m\""
|
|
151
|
-
}
|
|
152
|
-
},
|
|
153
93
|
"standard-version": {
|
|
154
94
|
"releaseCommitMessageFormat": "{{currentTag}}",
|
|
155
95
|
"sign": true,
|
|
@@ -158,15 +98,6 @@
|
|
|
158
98
|
"tag": true
|
|
159
99
|
}
|
|
160
100
|
},
|
|
161
|
-
"prettier": {
|
|
162
|
-
"printWidth": 140,
|
|
163
|
-
"quoteProps": "consistent",
|
|
164
|
-
"semi": false,
|
|
165
|
-
"singleQuote": true,
|
|
166
|
-
"tabWidth": 2,
|
|
167
|
-
"trailingComma": "es5",
|
|
168
|
-
"useTabs": false
|
|
169
|
-
},
|
|
170
101
|
"jest": {
|
|
171
102
|
"transform": {}
|
|
172
103
|
},
|
package/readme.md
CHANGED
|
@@ -1,22 +1,43 @@
|
|
|
1
1
|
# Nitro
|
|
2
2
|
|
|
3
|
-
[](https://www.npmjs.com/package/nitro-web)
|
|
3
|
+
[](https://www.npmjs.com/package/nitro-web)
|
|
4
4
|
|
|
5
5
|
Nitro is a battle-tested, modular base project to turbocharge your projects, styled using Tailwind 🚀
|
|
6
6
|
|
|
7
|
-
### Install
|
|
8
|
-
|
|
9
7
|
```bash
|
|
10
8
|
npm i nitro-web
|
|
11
9
|
```
|
|
12
10
|
|
|
13
|
-
###
|
|
11
|
+
### Install
|
|
14
12
|
|
|
15
|
-
1. Copy
|
|
16
|
-
2.
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
13
|
+
1. Copy ./_example into your project
|
|
14
|
+
2. In package.json, replace `"nitro-web": "file:.."` with `"nitro-web": "^0.0.1"`
|
|
15
|
+
3. In package.json, replace `"../.eslintrc.json"` with `"./node_modules/nitro-web/.eslintrc.json"`
|
|
16
|
+
4. In tsconfig.json, remove
|
|
17
|
+
```json
|
|
18
|
+
"paths": {
|
|
19
|
+
"nitro-web": [
|
|
20
|
+
"../client/index.js",
|
|
21
|
+
],
|
|
22
|
+
},
|
|
23
|
+
```
|
|
24
|
+
5. Run `npm i`
|
|
25
|
+
|
|
26
|
+
### Usage
|
|
27
|
+
|
|
28
|
+
On the client, you can import components and page-components as you would normally. See ./example for further info.
|
|
29
|
+
|
|
30
|
+
```javascript
|
|
31
|
+
import { SigninPage, Toggle, util } from 'nitro-web'
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
On the server, you can import the express router, default models, and controllers. See ./example for further info.
|
|
35
|
+
|
|
36
|
+
```javascript
|
|
37
|
+
import { setupRouter, util } from 'nitro-web/server'
|
|
38
|
+
const server = await setupRouter(config)
|
|
39
|
+
server.listen(3001, '0.0.0.0')
|
|
40
|
+
```
|
|
20
41
|
|
|
21
42
|
### Running in development
|
|
22
43
|
|
|
@@ -41,3 +62,12 @@ npm run start
|
|
|
41
62
|
- React `^18.3`
|
|
42
63
|
- Tailwind `^3.4`
|
|
43
64
|
- Webpack `^5.92`
|
|
65
|
+
|
|
66
|
+
### Common packages
|
|
67
|
+
|
|
68
|
+
- `pdf-to-img`
|
|
69
|
+
- `pdfmake`
|
|
70
|
+
- `react-chartjs-2`
|
|
71
|
+
- `jest: ^29.7.0`
|
|
72
|
+
- `migrate-mongo: ^10.0.0`
|
|
73
|
+
- `eslint-plugin-jest: ^28.9.0`
|
package/server/email/index.js
CHANGED
|
@@ -5,12 +5,13 @@ import nunjucks from 'nunjucks'
|
|
|
5
5
|
import inlineCss from 'inline-css'
|
|
6
6
|
import { dirname, join } from 'path'
|
|
7
7
|
import { fileURLToPath } from 'url'
|
|
8
|
+
import path from 'path'
|
|
9
|
+
import { getDirectories } from '../../util.js'
|
|
8
10
|
|
|
9
11
|
let templates = {}
|
|
10
12
|
let nodemailerMailgun = undefined
|
|
11
13
|
const _dirname = dirname(fileURLToPath(import.meta.url)) + '/'
|
|
12
14
|
|
|
13
|
-
|
|
14
15
|
export async function sendEmail({ template, to, bcc, data={}, from, replyTo, recipientVariables, subject, test, skipCssInline, config }) {
|
|
15
16
|
/**
|
|
16
17
|
* Email recipient a predefined template with data and/or recipientVariables
|
|
@@ -72,7 +73,7 @@ export async function sendEmail({ template, to, bcc, data={}, from, replyTo, rec
|
|
|
72
73
|
let settings = {
|
|
73
74
|
bcc: bcc,
|
|
74
75
|
from: from,
|
|
75
|
-
isDev: config.clientUrl.match(/:/),
|
|
76
|
+
isDev: config.clientUrl.match(/:/), // possibly use config.env here
|
|
76
77
|
recipientVariables: recipientVariables,
|
|
77
78
|
replyTo: replyTo,
|
|
78
79
|
skipCssInline: skipCssInline,
|
|
@@ -81,34 +82,35 @@ export async function sendEmail({ template, to, bcc, data={}, from, replyTo, rec
|
|
|
81
82
|
test: config.emailTestMode || test,
|
|
82
83
|
to: to,
|
|
83
84
|
url: config.clientUrl,
|
|
85
|
+
emailTemplateDir: getDirectories(path, config.pwd).emailTemplateDir,
|
|
84
86
|
}
|
|
85
87
|
|
|
86
88
|
// Grab html and send
|
|
87
|
-
let html = template.match('<') ? template : await getTemplate(settings
|
|
89
|
+
let html = template.match('<') ? template : await getTemplate(settings)
|
|
88
90
|
if (!html) throw new Error('Sendmail: No template returned from getTemplate(..)')
|
|
89
91
|
return await sendWithMailgun(settings, html) // note, mailgun errors are resolved
|
|
90
92
|
}
|
|
91
93
|
|
|
92
|
-
async function getTemplate(settings
|
|
94
|
+
async function getTemplate(settings) {
|
|
93
95
|
try {
|
|
94
96
|
var templateName = settings.template
|
|
95
97
|
if (!templates[templateName] || settings.isDev) {
|
|
96
|
-
nunjucks.configure({ noCache:
|
|
98
|
+
nunjucks.configure({ noCache: settings.isDev })
|
|
97
99
|
// Setup the nunjucks environment
|
|
98
|
-
let
|
|
99
|
-
new nunjucks.FileSystemLoader(`${
|
|
100
|
+
let nunjucksEnv = new nunjucks.Environment([
|
|
101
|
+
new nunjucks.FileSystemLoader(`${settings.emailTemplateDir}`), // user templates take precedence
|
|
100
102
|
new nunjucks.FileSystemLoader(`${_dirname}`), // then fallback to nitro default templates
|
|
101
103
|
])
|
|
102
104
|
// Get the template
|
|
103
|
-
let template =
|
|
105
|
+
let template = nunjucksEnv.getTemplate(templateName + '.html', true)
|
|
104
106
|
// Render the template
|
|
105
107
|
let html = template.render({})
|
|
106
108
|
if (settings.skipCssInline && settings.test) {
|
|
107
109
|
templates[templateName] = html
|
|
108
110
|
} else {
|
|
109
111
|
try {
|
|
110
|
-
// First try to inline the CSS from the user templates directory
|
|
111
|
-
templates[templateName] = await inlineCssForPath(html,
|
|
112
|
+
// First try to inline the CSS from the user templates directory
|
|
113
|
+
templates[templateName] = await inlineCssForPath(html, settings.emailTemplateDir)
|
|
112
114
|
} catch (e) {
|
|
113
115
|
// If the CSS is not found, use default nitro CSS file
|
|
114
116
|
if (templateName == 'reset-password' || templateName == 'welcome') {
|
package/server/index.js
ADDED
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
export * from '../util.js'
|
|
2
|
+
export * as util from '../util.js'
|
|
3
|
+
|
|
4
|
+
// Export models
|
|
5
|
+
import userModel from './models/user.js'
|
|
6
|
+
import companyModel from './models/company.js'
|
|
7
|
+
async function setupDefaultModels(db) {
|
|
8
|
+
// Load default nitro models, if they don't exist already
|
|
9
|
+
if (!db.models.user) await db.model('user', userModel)
|
|
10
|
+
if (!db.models.company) await db.model('company', companyModel)
|
|
11
|
+
}
|
|
12
|
+
export { userModel, companyModel, setupDefaultModels }
|
|
13
|
+
|
|
14
|
+
// Export router
|
|
15
|
+
export { setupRouter } from './router.js'
|
|
16
|
+
|
|
17
|
+
// Export email utility
|
|
18
|
+
export { sendEmail } from './email/index.js'
|
|
19
|
+
|
|
20
|
+
// Export api default controllers
|
|
21
|
+
export { default as auth } from '../components/auth/auth.api.js'
|
|
22
|
+
export { default as settings } from '../components/settings/settings.api.js'
|
|
23
|
+
export { default as stripe } from '../components/billing/stripe.api.js'
|
package/server/router.js
CHANGED
|
@@ -14,19 +14,16 @@ import * as util from '../util.js'
|
|
|
14
14
|
const _dirname = dirname(fileURLToPath(import.meta.url)) + '/'
|
|
15
15
|
|
|
16
16
|
export async function setupRouter (config) {
|
|
17
|
-
const {
|
|
17
|
+
const { env, middleware, version } = config
|
|
18
|
+
const { componentsDir, distDir, emailTemplateDir } = util.getDirectories(path, config.pwd)
|
|
18
19
|
const expressApp = express()
|
|
19
20
|
const server = http.createServer(expressApp)
|
|
20
21
|
const apiRoutes = {}
|
|
21
22
|
const controllers = {}
|
|
22
23
|
const allMiddleware = { ...defaultMiddleware, ...(middleware || {}) }
|
|
23
24
|
|
|
24
|
-
if (!
|
|
25
|
-
throw new Error('setupRouter: `config.componentsDir` missing')
|
|
26
|
-
} else if (!env) {
|
|
25
|
+
if (!env) {
|
|
27
26
|
throw new Error('setupRouter: `config.env` missing')
|
|
28
|
-
} else if (!emailTemplateDir) {
|
|
29
|
-
throw new Error('setupRouter: `config.emailTemplateDir` missing')
|
|
30
27
|
}
|
|
31
28
|
|
|
32
29
|
// Extend request/response with our custom error responses
|
|
@@ -95,8 +92,7 @@ export async function setupRouter (config) {
|
|
|
95
92
|
expressApp.get('/email/partials/email.css', (req, res) => {
|
|
96
93
|
// first check if there is a custom email.css in the emailTemplateDir
|
|
97
94
|
// if not, return the default nitro email.css
|
|
98
|
-
|
|
99
|
-
if (fs.existsSync(emailTemplateDir + '/partials/email.css')) res.sendFile(emailTemplateDir + '/partials/email.css')
|
|
95
|
+
if (fs.existsSync(emailTemplateDir + 'partials/email.css')) res.sendFile(emailTemplateDir + 'partials/email.css')
|
|
100
96
|
else res.sendFile(_dirname + 'email/partials/email.css')
|
|
101
97
|
})
|
|
102
98
|
expressApp.get('/email/:name', async (req, res) => {
|
package/util.js
CHANGED
|
@@ -490,6 +490,19 @@ export function getCurrencyPrefixWidth (prefix, paddingRight=0) {
|
|
|
490
490
|
return width
|
|
491
491
|
}
|
|
492
492
|
|
|
493
|
+
export function getDirectories (path, pwd) {
|
|
494
|
+
const _pwd = pwd || process.env.PWD
|
|
495
|
+
return {
|
|
496
|
+
clientDir: path.join(_pwd, process.env.clientDir || 'client', '/'),
|
|
497
|
+
componentsDir: path.join(_pwd, process.env.componentsDir || 'components', '/'),
|
|
498
|
+
distDir: path.join(_pwd, process.env.distDir || ((process.env.clientDir || 'client') + '/dist'), '/'),
|
|
499
|
+
emailTemplateDir: path.join(_pwd, process.env.emailTemplateDir || 'server/email', '/'),
|
|
500
|
+
fontsDir: path.join(_pwd, (process.env.clientDir || 'client'), 'fonts', '/'),
|
|
501
|
+
imgsDir: path.join(_pwd, (process.env.clientDir || 'client'), 'imgs', '/'),
|
|
502
|
+
tmpDir: path.join(_pwd, process.env.tmpDir || 'tmp', '/'),
|
|
503
|
+
}
|
|
504
|
+
}
|
|
505
|
+
|
|
493
506
|
export function getLink (obj, query) {
|
|
494
507
|
/**
|
|
495
508
|
* @param {object} obj - new query object
|