@things-factory/auth-ui 7.0.0-alpha.9 → 7.0.0

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.
Files changed (202) hide show
  1. package/client/auth-style-sign.ts +45 -33
  2. package/client/bootstrap.ts +6 -10
  3. package/client/components/abstract-auth-page.ts +48 -24
  4. package/client/components/abstract-password-reset.ts +13 -9
  5. package/client/components/abstract-sign.ts +105 -0
  6. package/client/components/change-password.ts +4 -4
  7. package/client/components/contact-us.ts +20 -26
  8. package/client/components/create-domain-popup.ts +16 -12
  9. package/client/components/create-role.ts +14 -16
  10. package/client/components/create-user.ts +15 -14
  11. package/client/components/credential-manager.ts +64 -0
  12. package/client/components/delete-user-popup.ts +4 -3
  13. package/client/components/domain-switch.ts +18 -15
  14. package/client/components/invite-customer.ts +6 -10
  15. package/client/components/invite-user.ts +5 -8
  16. package/client/components/my-login-history.ts +2 -2
  17. package/client/components/ownership-transfer-popup.ts +7 -7
  18. package/client/components/partner-info-card.ts +6 -6
  19. package/client/components/partner-role-editor.ts +15 -23
  20. package/client/components/profile-component.ts +71 -15
  21. package/client/components/role-edit-form.ts +3 -3
  22. package/client/components/role-privilege-editor.ts +19 -29
  23. package/client/components/role-selector.ts +7 -7
  24. package/client/components/user-role-editor.ts +43 -50
  25. package/client/entries/auth/activate.ts +20 -21
  26. package/client/entries/auth/checkin.ts +29 -31
  27. package/client/entries/auth/forgot-password.ts +15 -9
  28. package/client/entries/auth/result.ts +21 -18
  29. package/client/entries/auth/signin.ts +4 -0
  30. package/client/entries/auth/signup.ts +31 -14
  31. package/client/entries/oauth2/oauth2-decision-error-page.ts +2 -2
  32. package/client/entries/oauth2/oauth2-decision-page.ts +56 -55
  33. package/client/entries/public/home.ts +52 -28
  34. package/client/index.ts +93 -66
  35. package/client/pages/app-binding/app-binding.ts +48 -30
  36. package/client/pages/app-binding/app-bindings.ts +26 -7
  37. package/client/pages/appliance/appliance.ts +85 -26
  38. package/client/pages/appliance/home.ts +28 -6
  39. package/client/pages/appliance/register.ts +7 -7
  40. package/client/pages/application/application.ts +108 -76
  41. package/client/pages/application/applications.ts +29 -15
  42. package/client/pages/application/register.ts +8 -8
  43. package/client/pages/attribute/attribute-set-item-list.ts +13 -19
  44. package/client/pages/attribute/attribute-set-management.ts +14 -20
  45. package/client/pages/auth-provider/auth-provider-management.ts +10 -16
  46. package/client/pages/domain/domain-management.ts +4 -9
  47. package/client/pages/partner/partner-management.ts +2 -2
  48. package/client/pages/profile.ts +1 -1
  49. package/client/pages/role/role-management.ts +14 -12
  50. package/client/pages/user/user-management.ts +7 -5
  51. package/client/themes/auth-theme.css +7 -10
  52. package/dist-client/auth-style-sign.js +45 -33
  53. package/dist-client/auth-style-sign.js.map +1 -1
  54. package/dist-client/bootstrap.d.ts +1 -1
  55. package/dist-client/bootstrap.js +5 -5
  56. package/dist-client/bootstrap.js.map +1 -1
  57. package/dist-client/components/abstract-auth-page.d.ts +5 -4
  58. package/dist-client/components/abstract-auth-page.js +46 -24
  59. package/dist-client/components/abstract-auth-page.js.map +1 -1
  60. package/dist-client/components/abstract-password-reset.d.ts +3 -2
  61. package/dist-client/components/abstract-password-reset.js +12 -9
  62. package/dist-client/components/abstract-password-reset.js.map +1 -1
  63. package/dist-client/components/abstract-sign.d.ts +3 -0
  64. package/dist-client/components/abstract-sign.js +86 -0
  65. package/dist-client/components/abstract-sign.js.map +1 -1
  66. package/dist-client/components/change-password.js +4 -4
  67. package/dist-client/components/change-password.js.map +1 -1
  68. package/dist-client/components/contact-us.d.ts +4 -4
  69. package/dist-client/components/contact-us.js +19 -26
  70. package/dist-client/components/contact-us.js.map +1 -1
  71. package/dist-client/components/create-domain-popup.d.ts +1 -1
  72. package/dist-client/components/create-domain-popup.js +16 -12
  73. package/dist-client/components/create-domain-popup.js.map +1 -1
  74. package/dist-client/components/create-role.d.ts +1 -1
  75. package/dist-client/components/create-role.js +14 -16
  76. package/dist-client/components/create-role.js.map +1 -1
  77. package/dist-client/components/create-user.d.ts +2 -1
  78. package/dist-client/components/create-user.js +14 -14
  79. package/dist-client/components/create-user.js.map +1 -1
  80. package/dist-client/components/credential-manager.d.ts +11 -0
  81. package/dist-client/components/credential-manager.js +64 -0
  82. package/dist-client/components/credential-manager.js.map +1 -0
  83. package/dist-client/components/delete-user-popup.js +4 -3
  84. package/dist-client/components/delete-user-popup.js.map +1 -1
  85. package/dist-client/components/domain-switch.d.ts +2 -0
  86. package/dist-client/components/domain-switch.js +20 -15
  87. package/dist-client/components/domain-switch.js.map +1 -1
  88. package/dist-client/components/invite-customer.d.ts +1 -1
  89. package/dist-client/components/invite-customer.js +6 -9
  90. package/dist-client/components/invite-customer.js.map +1 -1
  91. package/dist-client/components/invite-user.js +5 -8
  92. package/dist-client/components/invite-user.js.map +1 -1
  93. package/dist-client/components/my-login-history.js +2 -2
  94. package/dist-client/components/my-login-history.js.map +1 -1
  95. package/dist-client/components/ownership-transfer-popup.d.ts +1 -1
  96. package/dist-client/components/ownership-transfer-popup.js +7 -7
  97. package/dist-client/components/ownership-transfer-popup.js.map +1 -1
  98. package/dist-client/components/partner-info-card.js +6 -6
  99. package/dist-client/components/partner-info-card.js.map +1 -1
  100. package/dist-client/components/partner-role-editor.d.ts +2 -2
  101. package/dist-client/components/partner-role-editor.js +15 -23
  102. package/dist-client/components/partner-role-editor.js.map +1 -1
  103. package/dist-client/components/profile-component.d.ts +7 -0
  104. package/dist-client/components/profile-component.js +70 -15
  105. package/dist-client/components/profile-component.js.map +1 -1
  106. package/dist-client/components/role-edit-form.js +3 -3
  107. package/dist-client/components/role-edit-form.js.map +1 -1
  108. package/dist-client/components/role-privilege-editor.js +19 -29
  109. package/dist-client/components/role-privilege-editor.js.map +1 -1
  110. package/dist-client/components/role-selector.js +7 -7
  111. package/dist-client/components/role-selector.js.map +1 -1
  112. package/dist-client/components/user-role-editor.d.ts +2 -0
  113. package/dist-client/components/user-role-editor.js +42 -49
  114. package/dist-client/components/user-role-editor.js.map +1 -1
  115. package/dist-client/entries/auth/activate.d.ts +5 -4
  116. package/dist-client/entries/auth/activate.js +19 -21
  117. package/dist-client/entries/auth/activate.js.map +1 -1
  118. package/dist-client/entries/auth/checkin.d.ts +5 -5
  119. package/dist-client/entries/auth/checkin.js +27 -28
  120. package/dist-client/entries/auth/checkin.js.map +1 -1
  121. package/dist-client/entries/auth/forgot-password.d.ts +2 -1
  122. package/dist-client/entries/auth/forgot-password.js +15 -9
  123. package/dist-client/entries/auth/forgot-password.js.map +1 -1
  124. package/dist-client/entries/auth/reset-password.js.map +1 -1
  125. package/dist-client/entries/auth/result.d.ts +5 -5
  126. package/dist-client/entries/auth/result.js +20 -18
  127. package/dist-client/entries/auth/result.js.map +1 -1
  128. package/dist-client/entries/auth/signin.d.ts +1 -0
  129. package/dist-client/entries/auth/signin.js +3 -0
  130. package/dist-client/entries/auth/signin.js.map +1 -1
  131. package/dist-client/entries/auth/signup.js +31 -14
  132. package/dist-client/entries/auth/signup.js.map +1 -1
  133. package/dist-client/entries/auth/unlock-user.js.map +1 -1
  134. package/dist-client/entries/oauth2/oauth2-decision-error-page.d.ts +1 -1
  135. package/dist-client/entries/oauth2/oauth2-decision-error-page.js +2 -2
  136. package/dist-client/entries/oauth2/oauth2-decision-error-page.js.map +1 -1
  137. package/dist-client/entries/oauth2/oauth2-decision-page.d.ts +1 -1
  138. package/dist-client/entries/oauth2/oauth2-decision-page.js +55 -54
  139. package/dist-client/entries/oauth2/oauth2-decision-page.js.map +1 -1
  140. package/dist-client/entries/public/home.d.ts +6 -5
  141. package/dist-client/entries/public/home.js +52 -28
  142. package/dist-client/entries/public/home.js.map +1 -1
  143. package/dist-client/index.d.ts +11 -2
  144. package/dist-client/index.js +74 -66
  145. package/dist-client/index.js.map +1 -1
  146. package/dist-client/pages/app-binding/app-binding.d.ts +1 -1
  147. package/dist-client/pages/app-binding/app-binding.js +47 -30
  148. package/dist-client/pages/app-binding/app-binding.js.map +1 -1
  149. package/dist-client/pages/app-binding/app-bindings.d.ts +2 -1
  150. package/dist-client/pages/app-binding/app-bindings.js +25 -7
  151. package/dist-client/pages/app-binding/app-bindings.js.map +1 -1
  152. package/dist-client/pages/appliance/appliance.d.ts +1 -1
  153. package/dist-client/pages/appliance/appliance.js +84 -26
  154. package/dist-client/pages/appliance/appliance.js.map +1 -1
  155. package/dist-client/pages/appliance/home.d.ts +2 -1
  156. package/dist-client/pages/appliance/home.js +27 -6
  157. package/dist-client/pages/appliance/home.js.map +1 -1
  158. package/dist-client/pages/appliance/register.js +7 -7
  159. package/dist-client/pages/appliance/register.js.map +1 -1
  160. package/dist-client/pages/application/application.d.ts +1 -1
  161. package/dist-client/pages/application/application.js +107 -76
  162. package/dist-client/pages/application/application.js.map +1 -1
  163. package/dist-client/pages/application/applications.d.ts +2 -1
  164. package/dist-client/pages/application/applications.js +28 -15
  165. package/dist-client/pages/application/applications.js.map +1 -1
  166. package/dist-client/pages/application/register.js +8 -8
  167. package/dist-client/pages/application/register.js.map +1 -1
  168. package/dist-client/pages/attribute/attribute-set-item-list.d.ts +1 -1
  169. package/dist-client/pages/attribute/attribute-set-item-list.js +11 -18
  170. package/dist-client/pages/attribute/attribute-set-item-list.js.map +1 -1
  171. package/dist-client/pages/attribute/attribute-set-management.d.ts +11 -2
  172. package/dist-client/pages/attribute/attribute-set-management.js +7 -11
  173. package/dist-client/pages/attribute/attribute-set-management.js.map +1 -1
  174. package/dist-client/pages/auth-provider/auth-provider-management.d.ts +11 -2
  175. package/dist-client/pages/auth-provider/auth-provider-management.js +8 -11
  176. package/dist-client/pages/auth-provider/auth-provider-management.js.map +1 -1
  177. package/dist-client/pages/domain/domain-management.d.ts +1 -0
  178. package/dist-client/pages/domain/domain-management.js +3 -7
  179. package/dist-client/pages/domain/domain-management.js.map +1 -1
  180. package/dist-client/pages/partner/partner-management.js +2 -2
  181. package/dist-client/pages/partner/partner-management.js.map +1 -1
  182. package/dist-client/pages/profile.js +1 -1
  183. package/dist-client/pages/profile.js.map +1 -1
  184. package/dist-client/pages/role/role-management.js +13 -10
  185. package/dist-client/pages/role/role-management.js.map +1 -1
  186. package/dist-client/pages/user/user-management.d.ts +1 -0
  187. package/dist-client/pages/user/user-management.js +6 -5
  188. package/dist-client/pages/user/user-management.js.map +1 -1
  189. package/dist-client/route.js.map +1 -1
  190. package/dist-client/themes/auth-theme.css +7 -10
  191. package/dist-client/tsconfig.tsbuildinfo +1 -1
  192. package/dist-client/utils/password-rule.js.map +1 -1
  193. package/dist-server/index.d.ts +0 -0
  194. package/dist-server/tsconfig.tsbuildinfo +1 -1
  195. package/package.json +14 -18
  196. package/translations/en.json +2 -0
  197. package/translations/ja.json +2 -0
  198. package/translations/ko.json +2 -1
  199. package/translations/ms.json +2 -0
  200. package/translations/zh.json +2 -0
  201. package/views/auth-page.html +5 -3
  202. package/views/oauth2-page.html +3 -2
@@ -3,7 +3,8 @@ import { css } from 'lit'
3
3
  export const AUTH_STYLE_SIGN = css`
4
4
  :host {
5
5
  display: flex;
6
- background-color: var(--auth-background);
6
+ background-color: var(--md-sys-color-primary);
7
+ color: var(--md-sys-color-on-primary);
7
8
  }
8
9
 
9
10
  :host *:focus {
@@ -14,10 +15,6 @@ export const AUTH_STYLE_SIGN = css`
14
15
  box-sizing: border-box;
15
16
  }
16
17
 
17
- ::placeholder {
18
- color: var(--opacity-light-color);
19
- font: var(--auth-input-font);
20
- }
21
18
  .wrap {
22
19
  display: block;
23
20
  width: 450px;
@@ -26,13 +23,15 @@ export const AUTH_STYLE_SIGN = css`
26
23
  padding-bottom: 100px;
27
24
  text-align: center;
28
25
  }
26
+
29
27
  .auth-brand {
30
- color: #fff;
28
+ color: var(--md-sys-color-on-primary);
31
29
  }
30
+
32
31
  .auth-brand img {
33
32
  margin: 15% auto 5px auto;
34
33
  width: 100px;
35
- border: 3px solid var(--theme-white-color);
34
+ border: 3px solid var(--md-sys-color-on-primary);
36
35
  border-radius: 25px;
37
36
  box-shadow: var(--box-shadow);
38
37
  }
@@ -46,7 +45,7 @@ export const AUTH_STYLE_SIGN = css`
46
45
  }
47
46
  .auth-form {
48
47
  display: grid;
49
- grid-gap: var(--margin-default);
48
+ grid-gap: var(--spacing-medium);
50
49
  grid-template-columns: 1fr 1fr;
51
50
  }
52
51
 
@@ -54,7 +53,7 @@ export const AUTH_STYLE_SIGN = css`
54
53
  grid-column: 1 / -1;
55
54
  display: grid;
56
55
  grid-template-columns: 1fr 1fr;
57
- grid-gap: var(--margin-default);
56
+ grid-gap: var(--spacing-medium);
58
57
  align-items: center;
59
58
  }
60
59
 
@@ -62,7 +61,7 @@ export const AUTH_STYLE_SIGN = css`
62
61
  grid-column: 1 / -1;
63
62
  margin: 50px 0 0 0;
64
63
  font: var(--auth-title-font);
65
- color: var(--auth-title-color);
64
+ color: var(--auth-title-color, var(--md-sys-color-on-primary));
66
65
  text-transform: uppercase;
67
66
  }
68
67
 
@@ -71,47 +70,60 @@ export const AUTH_STYLE_SIGN = css`
71
70
  text-align: left;
72
71
  }
73
72
 
74
- .field mwc-textfield {
73
+ .submit-buttons-container {
74
+ grid-column: 1 / -1;
75
+ text-align: center;
76
+
77
+ display: flex;
78
+ align-items: center;
79
+ gap: 10px;
80
+ }
81
+
82
+ .fingerprint {
83
+ color: var(--md-sys-color-on-primary);
84
+ border: 1.5px solid var(--md-sys-color-on-primary);
85
+ border-radius: 20%;
86
+ width: 36px;
87
+ height: 36px;
88
+ }
89
+
90
+ .field md-filled-text-field {
91
+ grid-column: 1 / -1;
75
92
  width: 100%;
76
- --mdc-theme-primary: var(--auth-input-color);
77
- --mdc-theme-error: #fdd55f;
78
- --mdc-text-field-fill-color: transparent;
79
- --mdc-text-field-ink-color: var(--auth-input-color);
80
- --mdc-text-field-label-ink-color: var(--auth-input-color);
81
- --mdc-text-field-idle-line-color: var(--auth-input-color);
82
- --mdc-text-field-hover-line-color: var(--auth-input-color);
83
- font: var(--auth-input-font);
84
- }
85
-
86
- mwc-button {
87
- --mdc-theme-primary: var(--auth-button-background-color);
88
- --mdc-theme-on-primary: var(--primary-color);
89
- --mdc-button-horizontal-padding: var(--padding-default);
90
- --mdc-button-ink-color: var(--primary-color);
93
+ }
94
+
95
+ md-text-button,
96
+ md-elevated-button {
91
97
  grid-column: 1 / -1;
98
+ flex: 1;
92
99
  }
93
100
 
94
101
  .wrap .link {
95
102
  text-decoration: none;
96
103
  justify-self: flex-start;
97
- color: var(--auth-title-color);
98
104
  }
99
105
 
100
- .wrap .link > mwc-button {
101
- --mdc-theme-primary: var(--auth-title-color);
106
+ .wrap .link md-text-button {
107
+ --md-text-button-label-text-color: var(--md-sys-color-on-primary);
108
+ --md-text-button-focus-label-text-color: var(--md-sys-color-on-primary);
109
+ --md-text-button-hover-label-text-color: var(--md-sys-color-on-primary);
110
+ }
111
+
112
+ .wrap .link md-icon {
113
+ color: var(--md-sys-color-on-primary);
102
114
  }
103
115
 
104
116
  #locale-area {
105
117
  display: flex;
106
118
  grid-column: 1 / -1;
107
- padding: 0 var(--padding-default);
119
+ padding: 0 var(--spacing-medium);
108
120
  }
109
121
 
110
122
  #locale-area > label {
111
123
  display: flex;
112
124
  align-items: center;
113
- color: var(--theme-white-color);
114
- --mdc-icon-size: 16px;
125
+ color: var(--md-sys-color-on-primary);
126
+ --md-icon-size: 16px;
115
127
  }
116
128
 
117
129
  #locale-selector {
@@ -123,7 +135,7 @@ export const AUTH_STYLE_SIGN = css`
123
135
  --i18n-selector-field-border: none;
124
136
  --i18n-selector-field-background-color: none;
125
137
  --i18n-selector-field-font-size: 14px;
126
- --i18n-selector-field-color: var(--theme-white-color);
138
+ --i18n-selector-field-color: var(--md-sys-color-on-primary);
127
139
  }
128
140
 
129
141
  .lottie-container {
@@ -1,4 +1,4 @@
1
- import '@material/mwc-icon'
1
+ import '@material/web/icon/icon.js'
2
2
  import '@operato/i18n/ox-i18n.js'
3
3
  import '@operato/attribute/grist-editor' /* for register data-grist editor type 'attributes' */
4
4
 
@@ -7,14 +7,10 @@ import { html } from 'lit-html'
7
7
  import { navigate, store } from '@operato/shell'
8
8
  import { TOOL_POSITION } from '@operato/layout'
9
9
  import { OxGristEditorPrivilege } from '@operato/app/grist-editor/ox-grist-editor-privilege.js'
10
+ import { registerEditor as registerGristEditor, registerRenderer as registerGristRenderer, OxGristRendererJson5 } from '@operato/data-grist'
10
11
 
11
- import {
12
- registerEditor as registerGristEditor,
13
- registerRenderer as registerGristRenderer,
14
- OxGristRendererJson5
15
- } from '@operato/data-grist'
16
- import { auth } from '@things-factory/auth-base/dist-client'
17
- import { ADD_MORENDA } from '@things-factory/more-base'
12
+ import { auth } from '@things-factory/auth-base/dist-client/auth.js'
13
+ import { ADD_MORENDA } from '@things-factory/more-base/client'
18
14
 
19
15
  export default function bootstrap() {
20
16
  registerGristEditor('privilege', OxGristEditorPrivilege)
@@ -24,7 +20,7 @@ export default function bootstrap() {
24
20
  store.dispatch({
25
21
  type: ADD_MORENDA,
26
22
  morenda: {
27
- icon: html` <mwc-icon>account_circle</mwc-icon> `,
23
+ icon: html` <md-icon>account_circle</md-icon> `,
28
24
  name: html` <ox-i18n msgid="text.auth profile"></ox-i18n> `,
29
25
  position: TOOL_POSITION.FRONT_END,
30
26
  action: () => {
@@ -37,7 +33,7 @@ export default function bootstrap() {
37
33
  store.dispatch({
38
34
  type: ADD_MORENDA,
39
35
  morenda: {
40
- icon: html` <mwc-icon>exit_to_app</mwc-icon> `,
36
+ icon: html` <md-icon>exit_to_app</md-icon> `,
41
37
  name: html` <ox-i18n msgid="field.sign out"></ox-i18n> `,
42
38
  position: TOOL_POSITION.FRONT_END,
43
39
  action: () => {
@@ -1,7 +1,8 @@
1
- import '@material/mwc-button'
2
- import '@material/mwc-icon'
3
- import '@material/mwc-icon-button'
4
- import '@material/mwc-textfield'
1
+ import '@material/web/icon/icon.js'
2
+ import '@material/web/button/elevated-button.js'
3
+ import '@material/web/button/text-button.js'
4
+ import '@material/web/textfield/filled-text-field.js'
5
+
5
6
  import '@operato/lottie-player'
6
7
  import '@operato/i18n/ox-i18n.js'
7
8
  import '@operato/i18n/ox-i18n-selector.js'
@@ -31,17 +32,22 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
31
32
  height: 100vh;
32
33
  height: 100dvh;
33
34
  }
35
+
34
36
  .content {
35
37
  flex: 1;
36
38
  overflow: auto;
37
39
  }
38
40
 
39
- [home] {
41
+ .home {
40
42
  position: absolute;
43
+ padding: var(--padding-dufault, 9px);
44
+ left: 20px;
41
45
  top: 10px;
42
- left: 10px;
43
- font-size: 2em;
44
- color: white;
46
+ color: var(--md-sys-color-on-primary);
47
+ }
48
+
49
+ div.field {
50
+ margin-bottom: var(--spacing-medium);
45
51
  }
46
52
 
47
53
  [hidden] {
@@ -78,12 +84,16 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
78
84
  description: string
79
85
  }
80
86
 
87
+ get autocompletable() {
88
+ return false
89
+ }
90
+
81
91
  render() {
82
92
  const { disableUserFavoredLanguage, languages } = this.data || {}
83
93
  var { icon, title, description } = this.applicationMeta
84
94
 
85
95
  return html`
86
- <div class="content">
96
+ <div class="content md-typescale-display-medium">
87
97
  <div class="wrap">
88
98
  <div class="auth-brand">
89
99
  <img src=${icon} />
@@ -98,6 +108,7 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
98
108
  id="form"
99
109
  action="${this.actionUrl}"
100
110
  method="post"
111
+ autocomplete=${this.autocompletable ? "on": "off"}
101
112
  @keypress=${e => {
102
113
  if (e.key == 'Enter') this._onSubmit(e)
103
114
  }}
@@ -107,7 +118,7 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
107
118
  ${this.links}
108
119
  ${!disableUserFavoredLanguage
109
120
  ? html` <div id="locale-area">
110
- <label for="locale-selector"><mwc-icon>language</mwc-icon></label>
121
+ <label for="locale-selector"><md-icon>language</md-icon></label>
111
122
  <ox-i18n-selector
112
123
  id="locale-selector"
113
124
  value=${i18next.language || 'en-US'}
@@ -124,7 +135,9 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
124
135
  </div>
125
136
  </div>
126
137
 
127
- <mwc-icon-button home icon="home" @click=${e => (window.location.href = '/')}></mwc-icon-button>
138
+ <md-icon-button class="home" @click=${e => (window.location.href = '/')}
139
+ ><md-icon>home</md-icon></md-icon-button
140
+ >
128
141
  <ox-snack-bar id="snackbar" level="error" .message=${this.message}></ox-snack-bar>
129
142
 
130
143
  ${isSafari()
@@ -140,7 +153,7 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
140
153
 
141
154
  firstUpdated() {
142
155
  setTimeout(() => {
143
- ;(this.renderRoot.querySelector('mwc-textfield') as any).focus()
156
+ ;(this.renderRoot.querySelector('md-filled-text-field') as any).focus()
144
157
  }, 100)
145
158
 
146
159
  this.formEl.reset = () => {
@@ -164,35 +177,37 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
164
177
 
165
178
  get formfields() {
166
179
  const email = this.data?.email || ''
180
+ // .validationMessage=${String(i18next.t('text.invalid-email'))}
167
181
 
168
182
  return html`
169
183
  <input id="redirectTo" type="hidden" name="redirectTo" .value=${this.redirectTo || '/'} />
170
184
 
171
185
  <div class="field">
172
- <mwc-textfield
186
+ <md-filled-text-field
173
187
  name="email"
174
188
  type="email"
175
189
  label=${String(i18next.t('field.email'))}
176
190
  required
177
191
  .value=${email}
178
- .validationMessage=${String(i18next.t('text.invalid-email'))}
179
- autocomplete="username"
192
+ autocomplete="off"
180
193
  autocapitalize="off"
181
- ></mwc-textfield>
194
+ ><md-icon slot="leading-icon">mail</md-icon></md-filled-text-field
195
+ >
182
196
  </div>
183
197
  <div class="field">
184
- <mwc-textfield
198
+ <md-filled-text-field
185
199
  name="password"
186
200
  type="password"
187
201
  label=${String(i18next.t('field.password'))}
188
- autocomplete="current-password"
202
+ autocomplete="off"
189
203
  required
190
- ></mwc-textfield>
204
+ ><md-icon slot="leading-icon">vpn_key</md-icon></md-filled-text-field
205
+ >
191
206
  </div>
192
207
 
193
- <mwc-button class="ui" type="submit" raised @click=${e => this._onSubmit(e)}>
208
+ <md-elevated-button class="ui" type="submit" raised @click=${e => this._onSubmit(e)}>
194
209
  <ox-i18n msgid="field.${this.pageName}"> </ox-i18n>
195
- </mwc-button>
210
+ </md-elevated-button>
196
211
  `
197
212
  }
198
213
 
@@ -203,17 +218,26 @@ export abstract class AbstractAuthPage extends localize(i18next)(LitElement) {
203
218
  ${!disableUserSignupProcess
204
219
  ? html`
205
220
  <a class="link" href="/auth/signup">
206
- <mwc-button icon="add_task"><ox-i18n msgid="field.sign up"></ox-i18n></mwc-button>
221
+ <md-text-button>
222
+ <md-icon slot="icon">add_task</md-icon>
223
+ <ox-i18n msgid="field.sign up"></ox-i18n>
224
+ </md-text-button>
207
225
  </a>
208
226
  <a class="link" href="/auth/forgot-password">
209
- <mwc-button icon="lock_open"><ox-i18n msgid="field.forgot-password"></ox-i18n></mwc-button>
227
+ <md-text-button>
228
+ <md-icon slot="icon">lock_open</md-icon>
229
+ <ox-i18n msgid="field.forgot-password"></ox-i18n>
230
+ </md-text-button>
210
231
  </a>
211
232
  `
212
233
  : nothing}
213
234
  ${ssoLinks.map(
214
235
  sso => html`
215
236
  <a class="link" href=${sso.link}>
216
- <mwc-button icon="badge">${i18next.t('label.signin with', { title: sso.title })}</mwc-button>
237
+ <md-text-button>
238
+ <md-icon slot="icon">badge</md-icon>
239
+ ${i18next.t('label.signin with', { title: sso.title })}
240
+ </md-text-button>
217
241
  </a>
218
242
  `
219
243
  )}
@@ -1,5 +1,7 @@
1
- import '@material/mwc-button'
2
- import '@material/mwc-textfield'
1
+ import '@material/web/icon/icon.js'
2
+ import '@material/web/button/elevated-button.js'
3
+ import '@material/web/textfield/filled-text-field.js'
4
+
3
5
  import '@operato/lottie-player'
4
6
  import '../components/profile-component'
5
7
  import '@operato/i18n/ox-i18n.js'
@@ -77,38 +79,40 @@ export abstract class AbstractPasswordReset extends AbstractAuthPage {
77
79
  >
78
80
  <input name="token" type="hidden" .value=${this.token || ''} required />
79
81
  <div class="field">
80
- <mwc-textfield
82
+ <md-filled-text-field
81
83
  name="password"
82
84
  type="password"
83
85
  label=${String(i18next.t('label.password'))}
84
86
  .pattern=${this.passwordPattern}
85
87
  helper=${this.passwordHelp}
86
88
  helperPersistent
89
+ autocomplete="off"
87
90
  @input=${e => {
88
91
  var val = e.target.value
89
92
  this.confirmPass.setAttribute('pattern', val.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, '[$&]'))
90
93
  }}
91
94
  required
92
- ></mwc-textfield>
95
+ ></md-filled-text-field>
93
96
  </div>
94
97
 
95
98
  <div class="field">
96
- <mwc-textfield
99
+ <md-filled-text-field
97
100
  id="confirm-password"
98
101
  name="confirm-password"
99
102
  type="password"
100
103
  label=${String(i18next.t('field.confirm password'))}
104
+ autocomplete="off"
101
105
  required
102
- ></mwc-textfield>
106
+ ></md-filled-text-field>
103
107
  </div>
104
108
 
105
- <mwc-button id="submit-button" type="submit" raised @click=${e => this._onSubmit(e)}>
109
+ <md-elevated-button id="submit-button" type="submit" @click=${e => this._onSubmit(e)}>
106
110
  <ox-i18n msgid="${this.submitButtonLabel}"></ox-i18n>
107
- </mwc-button>
111
+ </md-elevated-button>
108
112
 
109
113
  ${!disableUserFavoredLanguage
110
114
  ? html` <div id="locale-area">
111
- <label for="locale-selector"><mwc-icon>language</mwc-icon></label>
115
+ <label for="locale-selector"><md-icon>language</md-icon></label>
112
116
  <ox-i18n-selector
113
117
  id="locale-selector"
114
118
  value=${i18next.language || 'en-US'}
@@ -1,5 +1,28 @@
1
+ import '@operato/i18n/ox-i18n.js'
2
+
3
+ import { html, nothing } from 'lit'
4
+ import { startAuthentication } from '@simplewebauthn/browser'
5
+
6
+ import { i18next } from '@operato/i18n'
7
+ import { notify } from '@operato/layout'
8
+
1
9
  import { AbstractAuthPage } from './abstract-auth-page.js'
2
10
 
11
+ const isAvailableWebauthn = 'PublicKeyCredential' in window
12
+
13
+ interface AssertionResponse {
14
+ id: string
15
+ rawId?: number[]
16
+ response: {
17
+ authenticatorData: string
18
+ clientDataJSON: string
19
+ signature: string
20
+ userHandle: string | null
21
+ }
22
+ type: PublicKeyCredentialType
23
+ authenticatorAttachment?: AuthenticatorAttachment
24
+ }
25
+
3
26
  export abstract class AbstractSign extends AbstractAuthPage {
4
27
  async submit() {
5
28
  this.formEl.submit()
@@ -19,4 +42,86 @@ export abstract class AbstractSign extends AbstractAuthPage {
19
42
  }
20
43
  }
21
44
  }
45
+
46
+ get formfields() {
47
+ const email = this.data?.email || ''
48
+ const autocompletable = this.autocompletable
49
+
50
+ return html`
51
+ <input id="redirectTo" type="hidden" name="redirectTo" .value=${this.redirectTo || '/'} />
52
+
53
+ <div class="field">
54
+ <md-filled-text-field
55
+ name="email"
56
+ type="email"
57
+ label=${String(i18next.t('field.email'))}
58
+ required
59
+ .value=${email}
60
+ autocomplete=${autocompletable ? "username" : "off"}
61
+ autocapitalize="off"
62
+ @input=${(e: Event) => {
63
+ const target = e.target as HTMLInputElement
64
+ if (target.validity.typeMismatch) {
65
+ target.setCustomValidity(i18next.t('text.invalid-email'))
66
+ } else {
67
+ target.setCustomValidity('')
68
+ }
69
+ }}
70
+ ><md-icon slot="leading-icon">mail</md-icon></md-filled-text-field
71
+ >
72
+ </div>
73
+ <div class="field">
74
+ <md-filled-text-field
75
+ name="password"
76
+ type="password"
77
+ label=${String(i18next.t('field.password'))}
78
+ autocomplete=${autocompletable ? "current-password" : "off"}
79
+ required
80
+ ><md-icon slot="leading-icon">vpn_key</md-icon></md-filled-text-field
81
+ >
82
+ </div>
83
+
84
+ <div class="submit-buttons-container">
85
+ <md-elevated-button class="submit-button" type="submit" raised @click=${e => this._onSubmit(e)}>
86
+ <ox-i18n msgid="field.${this.pageName}"> </ox-i18n>
87
+ </md-elevated-button>
88
+ ${isAvailableWebauthn
89
+ ? html` <md-icon class="fingerprint" raised @click=${e => this.authenticateUser()}> fingerprint </md-icon>`
90
+ : nothing}
91
+ </div>
92
+ `
93
+ }
94
+
95
+ async authenticateUser() {
96
+ try {
97
+ const options = await fetch('/auth/signin-webauthn/challenge').then(res => res.json())
98
+ const assertionResp = await startAuthentication(options)
99
+ const verification = await fetch('/auth/signin-webauthn', {
100
+ method: 'POST',
101
+ headers: {
102
+ 'Content-Type': 'application/json'
103
+ },
104
+ body: JSON.stringify(assertionResp)
105
+ }).then(res => res.json())
106
+
107
+ if (verification.verified) {
108
+ const { redirectURL } = verification
109
+
110
+ if (redirectURL) {
111
+ window.location.href = redirectURL
112
+ }
113
+ } else {
114
+ notify({
115
+ level: 'error',
116
+ message: verification.message
117
+ })
118
+ }
119
+
120
+ } catch (error) {
121
+ notify({
122
+ level: 'error',
123
+ message: i18next.t('error.authn verification failed')
124
+ })
125
+ }
126
+ }
22
127
  }
@@ -2,7 +2,7 @@ import { css, html, LitElement } from 'lit'
2
2
  import { customElement, query } from 'lit/decorators.js'
3
3
 
4
4
  import { i18next, localize } from '@operato/i18n'
5
- import { auth } from '@things-factory/auth-base/dist-client'
5
+ import { auth } from '@things-factory/auth-base/dist-client/auth.js'
6
6
 
7
7
  @customElement('change-password')
8
8
  export class ChangePassword extends localize(i18next)(LitElement) {
@@ -40,8 +40,8 @@ export class ChangePassword extends localize(i18next)(LitElement) {
40
40
  text-transform: capitalize;
41
41
  }
42
42
 
43
- mwc-button {
44
- margin: var(--margin-narrow) auto var(--margin-default) auto;
43
+ md-elevated-button {
44
+ margin: var(--spacing-small) auto var(--spacing-medium) auto;
45
45
  }
46
46
 
47
47
  button {
@@ -78,7 +78,7 @@ export class ChangePassword extends localize(i18next)(LitElement) {
78
78
  <input type="password" name="confirm_pass" placeholder=${i18next.t('text.confirm password')} required />
79
79
  </div>
80
80
 
81
- <mwc-button raised label="${i18next.t('text.change password')}" @click=${this.submit.bind(this)}></mwc-button>
81
+ <md-elevated-button @click=${this.submit.bind(this)}>${i18next.t('text.change password')}</md-elevated-button>
82
82
  </form>
83
83
  `
84
84
  }
@@ -1,24 +1,21 @@
1
- import '@material/mwc-textarea'
2
- import '@material/mwc-textfield'
3
- import '@material/mwc-button'
4
- import '@material/mwc-dialog'
1
+ import '@material/web/button/text-button.js'
2
+ import '@material/web/button/elevated-button.js'
3
+ import '@material/web/textfield/filled-text-field.js'
4
+ import '@material/web/dialog/dialog.js'
5
+
5
6
  import '@operato/i18n'
6
7
 
7
8
  import { css, html, LitElement } from 'lit'
8
9
  import { customElement, query } from 'lit/decorators.js'
9
10
 
10
11
  import { i18next, localize } from '@operato/i18n'
11
- import { auth } from '@things-factory/auth-base/dist-client'
12
+ import { auth } from '@things-factory/auth-base/dist-client/auth.js'
12
13
 
13
14
  @customElement('contact-us')
14
15
  export class ContactUs extends localize(i18next)(LitElement) {
15
16
  static get styles() {
16
17
  return [
17
18
  css`
18
- :host {
19
- --mdc-theme-primary: var(--primary-color);
20
- }
21
-
22
19
  * {
23
20
  box-sizing: border-box;
24
21
  }
@@ -43,16 +40,16 @@ export class ContactUs extends localize(i18next)(LitElement) {
43
40
 
44
41
  render() {
45
42
  return html`
46
- <mwc-button raised label=${i18next.t('button.need help')} @click=${e => (this.dialog.open = true)}></mwc-button>
43
+ <md-elevated-button @click=${e => (this.dialog.open = true)}>${i18next.t('button.need help')}</md-elevated-button>
47
44
 
48
- <mwc-dialog id="dialog" heading=${i18next.t('title.need help')}>
45
+ <md-dialog id="dialog" heading=${i18next.t('title.need help')}>
49
46
  <form action="" method="POST">
50
47
  <input id="subject-input" name="subject" type="hidden" />
51
48
  <input id="sender-input" name="sender" type="hidden" />
52
49
  <input id="content-input" name="content" type="hidden" />
53
50
  </form>
54
51
  <div id="input-form">
55
- <mwc-textfield
52
+ <md-filled-text-field
56
53
  type="text"
57
54
  label=${i18next.t('label.subject')}
58
55
  dialogInitialFocus
@@ -61,8 +58,8 @@ export class ContactUs extends localize(i18next)(LitElement) {
61
58
  const val = e.target.value
62
59
  this.subjectInput.value = val
63
60
  }}
64
- ></mwc-textfield>
65
- <mwc-textfield
61
+ ></md-filled-text-field>
62
+ <md-filled-text-field
66
63
  type="text"
67
64
  name="sender"
68
65
  label=${i18next.t('label.email')}
@@ -71,9 +68,10 @@ export class ContactUs extends localize(i18next)(LitElement) {
71
68
  const val = e.target.value
72
69
  this.senderInput.value = val
73
70
  }}
74
- ></mwc-textfield>
75
- <mwc-textarea
71
+ ></md-filled-text-field>
72
+ <md-filled-text-field
76
73
  name="content"
74
+ type="textarea"
77
75
  label=${i18next.t('label.content')}
78
76
  required
79
77
  @keydown=${e => e.stopPropagation()}
@@ -81,17 +79,13 @@ export class ContactUs extends localize(i18next)(LitElement) {
81
79
  const val = e.target.value
82
80
  this.contentInput.value = val
83
81
  }}
84
- ></mwc-textarea>
82
+ ></md-filled-text-field>
85
83
  </div>
86
- <mwc-button
87
- slot="primaryAction"
88
- type="submit"
89
- label=${i18next.t('button.submit')}
90
- raised
91
- @click=${e => this._submit(e)}
92
- ></mwc-button>
93
- <mwc-button slot="secondaryAction" dialogAction="cancel" label=${i18next.t('button.cancel')}></mwc-button>
94
- </mwc-dialog>
84
+ <md-elevated-button slot="primaryAction" type="submit" @click=${e => this._submit(e)}
85
+ >${i18next.t('button.submit')}</md-elevated-button
86
+ >
87
+ <md-text-button slot="secondaryAction" dialogAction="cancel">${i18next.t('button.cancel')}</md-text-button>
88
+ </md-dialog>
95
89
  `
96
90
  }
97
91