@aerogel/core 0.0.0-next.7f6ed5a1f91688a86bf5ede2adc465e4fd6cfdea → 0.0.0-next.c8f032a868370824898e171969aec1bb6827688e
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/dist/aerogel-core.cjs.js +1 -1
- package/dist/aerogel-core.d.ts +229 -46
- package/dist/aerogel-core.esm.js +1 -1
- package/package.json +5 -8
- package/src/bootstrap/bootstrap.test.ts +0 -56
- package/src/bootstrap/index.ts +6 -25
- package/src/bootstrap/options.ts +5 -1
- package/src/components/basic/AGMarkdown.vue +20 -5
- package/src/components/forms/AGButton.vue +11 -1
- package/src/components/headless/forms/AGHeadlessInput.vue +2 -2
- package/src/components/headless/forms/AGHeadlessInputError.vue +9 -5
- package/src/components/headless/forms/AGHeadlessInputInput.vue +5 -1
- package/src/components/headless/forms/AGHeadlessInputLabel.vue +16 -0
- package/src/components/headless/forms/index.ts +6 -4
- package/src/components/headless/modals/AGHeadlessModal.vue +5 -1
- package/src/components/headless/modals/AGHeadlessModalPanel.vue +5 -1
- package/src/components/index.ts +2 -1
- package/src/components/modals/AGAlertModal.vue +13 -2
- package/src/components/modals/AGConfirmModal.vue +30 -0
- package/src/components/modals/AGModal.ts +4 -0
- package/src/components/modals/index.ts +3 -1
- package/src/directives/index.ts +5 -3
- package/src/forms/Form.ts +18 -6
- package/src/globals.ts +6 -0
- package/src/lang/Lang.ts +38 -7
- package/src/lang/index.ts +18 -75
- package/src/main.ts +3 -0
- package/src/plugins/Plugin.ts +7 -0
- package/src/plugins/index.ts +7 -0
- package/src/services/App.state.ts +10 -0
- package/src/services/App.ts +7 -0
- package/src/services/Service.ts +50 -9
- package/src/services/index.ts +13 -5
- package/src/types/vite.d.ts +0 -2
- package/src/ui/UI.state.ts +2 -6
- package/src/ui/UI.ts +20 -2
- package/src/ui/index.ts +15 -11
- package/src/utils/composition/hooks.ts +9 -0
- package/src/utils/index.ts +2 -0
- package/tsconfig.json +1 -10
- package/vite.config.ts +2 -6
- package/src/bootstrap/hooks.ts +0 -19
- package/src/lang/helpers.ts +0 -5
- package/src/models/index.ts +0 -18
- package/src/routing/index.ts +0 -33
- package/src/testing/stubs/lang/en.yaml +0 -1
- package/src/testing/stubs/models/User.ts +0 -3
package/src/lang/Lang.ts
CHANGED
|
@@ -1,19 +1,50 @@
|
|
|
1
|
-
import { useI18n } from 'vue-i18n';
|
|
2
1
|
import { facade } from '@noeldemartin/utils';
|
|
3
|
-
import type { Composer } from 'vue-i18n';
|
|
4
2
|
|
|
3
|
+
import App from '@/services/App';
|
|
5
4
|
import Service from '@/services/Service';
|
|
6
5
|
|
|
6
|
+
export interface LangProvider {
|
|
7
|
+
translate(key: string, parameters?: Record<string, unknown>): string;
|
|
8
|
+
}
|
|
9
|
+
|
|
7
10
|
export class LangService extends Service {
|
|
8
11
|
|
|
9
|
-
private
|
|
12
|
+
private provider: LangProvider;
|
|
13
|
+
|
|
14
|
+
constructor() {
|
|
15
|
+
super();
|
|
16
|
+
|
|
17
|
+
this.provider = {
|
|
18
|
+
translate: (key) => {
|
|
19
|
+
// eslint-disable-next-line no-console
|
|
20
|
+
App.isDevelopment && console.warn('Lang provider is missing');
|
|
21
|
+
|
|
22
|
+
return key;
|
|
23
|
+
},
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
public setProvider(provider: LangProvider): void {
|
|
28
|
+
this.provider = provider;
|
|
29
|
+
}
|
|
10
30
|
|
|
11
|
-
public
|
|
12
|
-
this.
|
|
31
|
+
public translate(key: string, parameters?: Record<string, unknown>): string {
|
|
32
|
+
return this.provider.translate(key, parameters) ?? key;
|
|
13
33
|
}
|
|
14
34
|
|
|
15
|
-
public
|
|
16
|
-
|
|
35
|
+
public translateWithDefault(key: string, defaultMessage: string): string;
|
|
36
|
+
public translateWithDefault(key: string, parameters: Record<string, unknown>, defaultMessage: string): string;
|
|
37
|
+
public translateWithDefault(
|
|
38
|
+
key: string,
|
|
39
|
+
defaultMessageOrParameters?: string | Record<string, unknown>,
|
|
40
|
+
defaultMessage?: string,
|
|
41
|
+
): string {
|
|
42
|
+
defaultMessage ??= defaultMessageOrParameters as string;
|
|
43
|
+
|
|
44
|
+
const parameters = typeof defaultMessageOrParameters === 'string' ? {} : defaultMessageOrParameters;
|
|
45
|
+
const message = this.provider.translate(key, parameters) ?? key;
|
|
46
|
+
|
|
47
|
+
return message === key ? defaultMessage : message;
|
|
17
48
|
}
|
|
18
49
|
|
|
19
50
|
}
|
package/src/lang/index.ts
CHANGED
|
@@ -1,89 +1,32 @@
|
|
|
1
|
-
import { createI18n } from 'vue-i18n';
|
|
2
|
-
import { fail, stringMatch } from '@noeldemartin/utils';
|
|
3
|
-
import type { I18nOptions } from 'vue-i18n';
|
|
4
|
-
import type { Plugin } from 'vue';
|
|
5
|
-
|
|
6
|
-
import { defineBootstrapHook, onAppMounted } from '@/bootstrap/hooks';
|
|
7
1
|
import { bootServices } from '@/services';
|
|
8
|
-
import
|
|
9
|
-
|
|
10
|
-
import Lang from './Lang';
|
|
11
|
-
|
|
12
|
-
const services = { $lang: Lang };
|
|
2
|
+
import { definePlugin } from '@/plugins';
|
|
13
3
|
|
|
14
|
-
|
|
15
|
-
if (options.lang) {
|
|
16
|
-
return options.lang;
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
if (options.langMessages) {
|
|
20
|
-
return { messages: options.langMessages };
|
|
21
|
-
}
|
|
4
|
+
import Lang, { LangProvider } from './Lang';
|
|
22
5
|
|
|
23
|
-
|
|
24
|
-
}
|
|
6
|
+
export { Lang, LangProvider };
|
|
25
7
|
|
|
26
|
-
|
|
27
|
-
return Object.entries(messageLoaders).reduce((loaders, [fileName, loader]) => {
|
|
28
|
-
const locale = stringMatch<2>(fileName, /.*\/lang\/(.+)\.yaml/)?.[1];
|
|
29
|
-
|
|
30
|
-
if (locale) {
|
|
31
|
-
loaders[locale] = () =>
|
|
32
|
-
(loader as () => Promise<{ default: Record<string, unknown> }>)().then(
|
|
33
|
-
({ default: messages }) => messages,
|
|
34
|
-
);
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
return loaders;
|
|
38
|
-
}, {} as Record<string, LazyMessages>);
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
async function createAppI18n(options: LangOptions): Promise<Plugin> {
|
|
42
|
-
const locale = options.defaultLocale ?? 'en';
|
|
43
|
-
const fallbackLocale = options.fallbackLocale ?? 'en';
|
|
44
|
-
const messageLoaders = getMessageLoaders(options.messages);
|
|
45
|
-
const lazyMessages = messageLoaders[locale] ?? fail<LazyMessages>(`Missing messages for '${locale}' locale`);
|
|
46
|
-
const messages = { [locale]: await lazyMessages() } as I18nOptions['messages'];
|
|
47
|
-
|
|
48
|
-
return createI18n({ locale, fallbackLocale, messages });
|
|
49
|
-
}
|
|
8
|
+
const services = { $lang: Lang };
|
|
50
9
|
|
|
51
10
|
export type LangServices = typeof services;
|
|
52
11
|
|
|
53
|
-
export
|
|
12
|
+
export const translate = Lang.translate.bind(Lang);
|
|
13
|
+
export const translateWithDefault = Lang.translateWithDefault.bind(Lang);
|
|
54
14
|
|
|
55
|
-
export
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
export * from './helpers';
|
|
62
|
-
export { Lang };
|
|
63
|
-
|
|
64
|
-
export default defineBootstrapHook(async (app, options) => {
|
|
65
|
-
const langOptions = getLangOptions(options);
|
|
66
|
-
|
|
67
|
-
if (!langOptions) {
|
|
68
|
-
return;
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
onAppMounted(() => Lang.setup());
|
|
72
|
-
|
|
73
|
-
const plugin = await createAppI18n(langOptions);
|
|
15
|
+
export default definePlugin({
|
|
16
|
+
async install(app) {
|
|
17
|
+
app.config.globalProperties.$t ??= translate;
|
|
18
|
+
app.config.globalProperties.$td = translateWithDefault;
|
|
74
19
|
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
await bootServices(app, services);
|
|
20
|
+
await bootServices(app, services);
|
|
21
|
+
},
|
|
78
22
|
});
|
|
79
23
|
|
|
80
|
-
declare module '@/bootstrap/options' {
|
|
81
|
-
interface BootstrapOptions {
|
|
82
|
-
lang?: LangOptions;
|
|
83
|
-
langMessages?: Record<string, unknown>;
|
|
84
|
-
}
|
|
85
|
-
}
|
|
86
|
-
|
|
87
24
|
declare module '@/services' {
|
|
88
25
|
interface Services extends LangServices {}
|
|
89
26
|
}
|
|
27
|
+
|
|
28
|
+
declare module '@vue/runtime-core' {
|
|
29
|
+
interface ComponentCustomProperties {
|
|
30
|
+
$td: typeof translateWithDefault;
|
|
31
|
+
}
|
|
32
|
+
}
|
package/src/main.ts
CHANGED
package/src/services/Service.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
|
+
import { computed, reactive } from 'vue';
|
|
1
2
|
import { MagicObject, PromisedValue } from '@noeldemartin/utils';
|
|
2
|
-
import {
|
|
3
|
+
import type { ComputedRef } from 'vue';
|
|
3
4
|
import type { Constructor } from '@noeldemartin/utils';
|
|
4
5
|
|
|
5
6
|
import ServiceBootError from '@/errors/ServiceBootError';
|
|
@@ -8,23 +9,39 @@ export type ServiceState = Record<string, any>; // eslint-disable-line @typescri
|
|
|
8
9
|
export type DefaultServiceState = {};
|
|
9
10
|
export type ServiceConstructor<T extends Service = Service> = Constructor<T> & typeof Service;
|
|
10
11
|
|
|
11
|
-
export
|
|
12
|
+
export type ComputedStateDefinition<TState extends ServiceState, TComputedState extends ServiceState> = {
|
|
13
|
+
[K in keyof TComputedState]: (state: TState) => TComputedState[K];
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
export function defineServiceState<
|
|
17
|
+
State extends ServiceState = ServiceState,
|
|
18
|
+
ComputedState extends ServiceState = {}
|
|
19
|
+
>(options: {
|
|
12
20
|
initialState: State;
|
|
13
|
-
|
|
14
|
-
|
|
21
|
+
computed?: ComputedStateDefinition<State, ComputedState>;
|
|
22
|
+
}): Constructor<State> & Constructor<ComputedState> & ServiceConstructor {
|
|
23
|
+
return class extends Service<State, ComputedState> {
|
|
15
24
|
|
|
16
25
|
protected getInitialState(): State {
|
|
17
26
|
return options.initialState;
|
|
18
27
|
}
|
|
28
|
+
|
|
29
|
+
protected getComputedStateDefinition(): ComputedStateDefinition<State, ComputedState> {
|
|
30
|
+
return options.computed ?? ({} as ComputedStateDefinition<State, ComputedState>);
|
|
31
|
+
}
|
|
19
32
|
|
|
20
|
-
} as unknown as Constructor<State> & ServiceConstructor;
|
|
33
|
+
} as unknown as Constructor<State> & Constructor<ComputedState> & ServiceConstructor;
|
|
21
34
|
}
|
|
22
35
|
|
|
23
|
-
export default class Service<
|
|
36
|
+
export default class Service<
|
|
37
|
+
State extends ServiceState = DefaultServiceState,
|
|
38
|
+
ComputedState extends ServiceState = {}
|
|
39
|
+
> extends MagicObject {
|
|
24
40
|
|
|
25
41
|
protected _namespace: string;
|
|
26
42
|
private _booted: PromisedValue<void>;
|
|
27
43
|
private _state: State;
|
|
44
|
+
private _computedState: Record<keyof ComputedState, ComputedRef>;
|
|
28
45
|
|
|
29
46
|
constructor() {
|
|
30
47
|
super();
|
|
@@ -32,6 +49,14 @@ export default class Service<State extends ServiceState = DefaultServiceState> e
|
|
|
32
49
|
this._namespace = new.target.name;
|
|
33
50
|
this._booted = new PromisedValue();
|
|
34
51
|
this._state = reactive(this.getInitialState());
|
|
52
|
+
this._computedState = Object.entries(this.getComputedStateDefinition()).reduce(
|
|
53
|
+
(computedState, [name, method]) => {
|
|
54
|
+
computedState[name as keyof ComputedState] = computed(() => method(this._state));
|
|
55
|
+
|
|
56
|
+
return computedState;
|
|
57
|
+
},
|
|
58
|
+
{} as Record<keyof ComputedState, ComputedRef>,
|
|
59
|
+
);
|
|
35
60
|
}
|
|
36
61
|
|
|
37
62
|
public get booted(): PromisedValue<void> {
|
|
@@ -55,11 +80,15 @@ export default class Service<State extends ServiceState = DefaultServiceState> e
|
|
|
55
80
|
}
|
|
56
81
|
|
|
57
82
|
protected __get(property: string): unknown {
|
|
58
|
-
if (
|
|
59
|
-
return
|
|
83
|
+
if (this.hasState(property)) {
|
|
84
|
+
return this.getState(property);
|
|
60
85
|
}
|
|
61
86
|
|
|
62
|
-
|
|
87
|
+
if (this.hasComputedState(property)) {
|
|
88
|
+
return this.getComputedState(property);
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
return super.__get(property);
|
|
63
92
|
}
|
|
64
93
|
|
|
65
94
|
protected __set(property: string, value: unknown): void {
|
|
@@ -70,12 +99,20 @@ export default class Service<State extends ServiceState = DefaultServiceState> e
|
|
|
70
99
|
return property in this._state;
|
|
71
100
|
}
|
|
72
101
|
|
|
102
|
+
protected hasComputedState<P extends keyof State>(property: P): boolean {
|
|
103
|
+
return property in this._computedState;
|
|
104
|
+
}
|
|
105
|
+
|
|
73
106
|
protected getState(): State;
|
|
74
107
|
protected getState<P extends keyof State>(property: P): State[P];
|
|
75
108
|
protected getState<P extends keyof State>(property?: P): State | State[P] {
|
|
76
109
|
return property ? this._state[property] : this._state;
|
|
77
110
|
}
|
|
78
111
|
|
|
112
|
+
protected getComputedState<P extends keyof ComputedState>(property: P): ComputedState[P] {
|
|
113
|
+
return this._computedState[property]?.value;
|
|
114
|
+
}
|
|
115
|
+
|
|
79
116
|
protected setState(state: Partial<State>): void {
|
|
80
117
|
Object.assign(this._state, state);
|
|
81
118
|
}
|
|
@@ -84,6 +121,10 @@ export default class Service<State extends ServiceState = DefaultServiceState> e
|
|
|
84
121
|
return {} as State;
|
|
85
122
|
}
|
|
86
123
|
|
|
124
|
+
protected getComputedStateDefinition(): ComputedStateDefinition<State, ComputedState> {
|
|
125
|
+
return {} as ComputedStateDefinition<State, ComputedState>;
|
|
126
|
+
}
|
|
127
|
+
|
|
87
128
|
protected async boot(): Promise<void> {
|
|
88
129
|
//
|
|
89
130
|
}
|
package/src/services/index.ts
CHANGED
|
@@ -1,15 +1,19 @@
|
|
|
1
|
-
import type { App } from 'vue';
|
|
1
|
+
import type { App as VueApp } from 'vue';
|
|
2
2
|
|
|
3
|
+
import { definePlugin } from '@/plugins';
|
|
4
|
+
|
|
5
|
+
import App from './App';
|
|
3
6
|
import Events from './Events';
|
|
4
7
|
import Service from './Service';
|
|
5
|
-
import { defineBootstrapHook } from '@/bootstrap/hooks';
|
|
6
8
|
|
|
9
|
+
export * from './App';
|
|
7
10
|
export * from './Events';
|
|
8
11
|
export * from './Service';
|
|
9
12
|
|
|
10
|
-
export { Events, Service };
|
|
13
|
+
export { App, Events, Service };
|
|
11
14
|
|
|
12
15
|
const defaultServices = {
|
|
16
|
+
$app: App,
|
|
13
17
|
$events: Events,
|
|
14
18
|
};
|
|
15
19
|
|
|
@@ -17,7 +21,7 @@ export type DefaultServices = typeof defaultServices;
|
|
|
17
21
|
|
|
18
22
|
export interface Services extends DefaultServices {}
|
|
19
23
|
|
|
20
|
-
export async function bootServices(app:
|
|
24
|
+
export async function bootServices(app: VueApp, services: Record<string, Service>): Promise<void> {
|
|
21
25
|
await Promise.all(
|
|
22
26
|
Object.entries(services).map(async ([name, service]) => {
|
|
23
27
|
// eslint-disable-next-line no-console
|
|
@@ -28,7 +32,11 @@ export async function bootServices(app: App, services: Record<string, Service>):
|
|
|
28
32
|
Object.assign(app.config.globalProperties, services);
|
|
29
33
|
}
|
|
30
34
|
|
|
31
|
-
export default
|
|
35
|
+
export default definePlugin({
|
|
36
|
+
async install(app) {
|
|
37
|
+
await bootServices(app, defaultServices);
|
|
38
|
+
},
|
|
39
|
+
});
|
|
32
40
|
|
|
33
41
|
declare module '@vue/runtime-core' {
|
|
34
42
|
interface ComponentCustomProperties extends Services {}
|
package/src/types/vite.d.ts
CHANGED
package/src/ui/UI.state.ts
CHANGED
|
@@ -2,10 +2,6 @@ import type { Component } from 'vue';
|
|
|
2
2
|
|
|
3
3
|
import { defineServiceState } from '@/services/Service';
|
|
4
4
|
|
|
5
|
-
export interface State {
|
|
6
|
-
modals: Modal[];
|
|
7
|
-
}
|
|
8
|
-
|
|
9
5
|
export interface Modal<T = unknown> {
|
|
10
6
|
id: string;
|
|
11
7
|
properties: Record<string, unknown>;
|
|
@@ -21,6 +17,6 @@ export interface ModalComponent<
|
|
|
21
17
|
Result = unknown
|
|
22
18
|
> {}
|
|
23
19
|
|
|
24
|
-
export default defineServiceState
|
|
25
|
-
initialState: { modals: [] },
|
|
20
|
+
export default defineServiceState({
|
|
21
|
+
initialState: { modals: [] as Modal[] },
|
|
26
22
|
});
|
package/src/ui/UI.ts
CHANGED
|
@@ -20,6 +20,7 @@ type ModalResult<TComponent> = TComponent extends ModalComponent<Record<string,
|
|
|
20
20
|
|
|
21
21
|
export const UIComponents = {
|
|
22
22
|
AlertModal: 'alert-modal',
|
|
23
|
+
ConfirmModal: 'confirm-modal',
|
|
23
24
|
} as const;
|
|
24
25
|
|
|
25
26
|
export type UIComponent = ObjectValues<typeof UIComponents>;
|
|
@@ -29,8 +30,25 @@ export class UIService extends Service {
|
|
|
29
30
|
private modalCallbacks: Record<string, Partial<ModalCallbacks>> = {};
|
|
30
31
|
private components: Partial<Record<UIComponent, Component>> = {};
|
|
31
32
|
|
|
32
|
-
public alert(message: string): void
|
|
33
|
-
|
|
33
|
+
public alert(message: string): void;
|
|
34
|
+
public alert(title: string, message: string): void;
|
|
35
|
+
public alert(messageOrTitle: string, message?: string): void {
|
|
36
|
+
const options = typeof message === 'string' ? { title: messageOrTitle, message } : { message: messageOrTitle };
|
|
37
|
+
|
|
38
|
+
this.openModal(this.requireComponent(UIComponents.AlertModal), options);
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
public async confirm(message: string): Promise<boolean>;
|
|
42
|
+
public async confirm(title: string, message: string): Promise<boolean>;
|
|
43
|
+
public async confirm(messageOrTitle: string, message?: string): Promise<boolean> {
|
|
44
|
+
const options = typeof message === 'string' ? { title: messageOrTitle, message } : { message: messageOrTitle };
|
|
45
|
+
const modal = await this.openModal<ModalComponent<{ message: string }, boolean>>(
|
|
46
|
+
this.requireComponent(UIComponents.ConfirmModal),
|
|
47
|
+
options,
|
|
48
|
+
);
|
|
49
|
+
const result = await modal.beforeClose;
|
|
50
|
+
|
|
51
|
+
return result ?? false;
|
|
34
52
|
}
|
|
35
53
|
|
|
36
54
|
public registerComponent(name: UIComponent, component: Component): void {
|
package/src/ui/index.ts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
import type { Component } from 'vue';
|
|
2
2
|
|
|
3
3
|
import { bootServices } from '@/services';
|
|
4
|
-
import {
|
|
4
|
+
import { definePlugin } from '@/plugins';
|
|
5
5
|
|
|
6
6
|
import UI, { UIComponents } from './UI';
|
|
7
7
|
import AGAlertModal from '../components/modals/AGAlertModal.vue';
|
|
8
|
+
import AGConfirmModal from '../components/modals/AGConfirmModal.vue';
|
|
8
9
|
import type { UIComponent } from './UI';
|
|
9
10
|
|
|
10
11
|
export { UI, UIComponents, UIComponent };
|
|
@@ -13,21 +14,24 @@ const services = { $ui: UI };
|
|
|
13
14
|
|
|
14
15
|
export type UIServices = typeof services;
|
|
15
16
|
|
|
16
|
-
export default
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
17
|
+
export default definePlugin({
|
|
18
|
+
async install(app, options) {
|
|
19
|
+
const defaultComponents = {
|
|
20
|
+
[UIComponents.AlertModal]: AGAlertModal,
|
|
21
|
+
[UIComponents.ConfirmModal]: AGConfirmModal,
|
|
22
|
+
};
|
|
20
23
|
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
24
|
+
Object.entries({
|
|
25
|
+
...defaultComponents,
|
|
26
|
+
...options.components,
|
|
27
|
+
}).forEach(([name, component]) => UI.registerComponent(name as UIComponent, component));
|
|
25
28
|
|
|
26
|
-
|
|
29
|
+
await bootServices(app, services);
|
|
30
|
+
},
|
|
27
31
|
});
|
|
28
32
|
|
|
29
33
|
declare module '@/bootstrap/options' {
|
|
30
|
-
interface
|
|
34
|
+
interface AerogelOptions {
|
|
31
35
|
components?: Partial<Record<UIComponent, Component>>;
|
|
32
36
|
}
|
|
33
37
|
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { noop } from '@noeldemartin/utils';
|
|
2
|
+
import { onMounted, onUnmounted } from 'vue';
|
|
3
|
+
|
|
4
|
+
export function onCleanMounted(operation: () => Function): void {
|
|
5
|
+
let cleanUp: Function = noop;
|
|
6
|
+
|
|
7
|
+
onMounted(() => (cleanUp = operation()));
|
|
8
|
+
onUnmounted(() => cleanUp());
|
|
9
|
+
}
|
package/src/utils/index.ts
CHANGED
package/tsconfig.json
CHANGED
|
@@ -1,15 +1,6 @@
|
|
|
1
1
|
{
|
|
2
|
+
"extends": "../../tsconfig.json",
|
|
2
3
|
"compilerOptions": {
|
|
3
|
-
"target": "esnext",
|
|
4
|
-
"module": "esnext",
|
|
5
|
-
"moduleResolution": "node",
|
|
6
|
-
"strict": true,
|
|
7
|
-
"types": [],
|
|
8
|
-
"jsx": "preserve",
|
|
9
|
-
"noUncheckedIndexedAccess": true,
|
|
10
|
-
"resolveJsonModule": true,
|
|
11
|
-
"esModuleInterop": true,
|
|
12
|
-
"lib": ["esnext", "dom"],
|
|
13
4
|
"baseUrl": ".",
|
|
14
5
|
"paths": {
|
|
15
6
|
"@/*": ["./src/*"]
|
package/vite.config.ts
CHANGED
|
@@ -1,17 +1,13 @@
|
|
|
1
|
-
import
|
|
2
|
-
import Vue from '@vitejs/plugin-vue';
|
|
1
|
+
import Aerogel from '@aerogel/vite';
|
|
3
2
|
import { defineConfig } from 'vitest/config';
|
|
4
3
|
import { resolve } from 'path';
|
|
5
4
|
|
|
6
|
-
const isTesting = process.env.NODE_ENV === 'test';
|
|
7
|
-
|
|
8
5
|
export default defineConfig({
|
|
9
6
|
test: { clearMocks: true },
|
|
10
|
-
plugins: [
|
|
7
|
+
plugins: [Aerogel()],
|
|
11
8
|
resolve: {
|
|
12
9
|
alias: {
|
|
13
10
|
'@': resolve(__dirname, './src'),
|
|
14
11
|
},
|
|
15
12
|
},
|
|
16
|
-
define: isTesting ? { __AG_BASE_PATH: 'undefined' } : undefined,
|
|
17
13
|
});
|
package/src/bootstrap/hooks.ts
DELETED
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
import type { App } from 'vue';
|
|
2
|
-
|
|
3
|
-
import type { BootstrapOptions } from '@/bootstrap/options';
|
|
4
|
-
|
|
5
|
-
const mountedHooks: Function[] = [];
|
|
6
|
-
|
|
7
|
-
export type BootstrapHook = (app: App, options: BootstrapOptions) => Promise<void>;
|
|
8
|
-
|
|
9
|
-
export function onAppMounted(hook: Function): void {
|
|
10
|
-
mountedHooks.push(hook);
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
export function runAppMountedHooks(): void {
|
|
14
|
-
mountedHooks.forEach((hook) => hook());
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
export function defineBootstrapHook<T extends BootstrapHook>(hook: T): T {
|
|
18
|
-
return hook;
|
|
19
|
-
}
|
package/src/lang/helpers.ts
DELETED
package/src/models/index.ts
DELETED
|
@@ -1,18 +0,0 @@
|
|
|
1
|
-
import { IndexedDBEngine, bootModelsFromViteGlob, setEngine } from 'soukai';
|
|
2
|
-
|
|
3
|
-
import { defineBootstrapHook } from '@/bootstrap/hooks';
|
|
4
|
-
|
|
5
|
-
export default defineBootstrapHook(async (_, options) => {
|
|
6
|
-
if (!options.models) {
|
|
7
|
-
return;
|
|
8
|
-
}
|
|
9
|
-
|
|
10
|
-
setEngine(new IndexedDBEngine());
|
|
11
|
-
bootModelsFromViteGlob(options.models);
|
|
12
|
-
});
|
|
13
|
-
|
|
14
|
-
declare module '@/bootstrap/options' {
|
|
15
|
-
interface BootstrapOptions {
|
|
16
|
-
models?: Record<string, Record<string, unknown>>;
|
|
17
|
-
}
|
|
18
|
-
}
|
package/src/routing/index.ts
DELETED
|
@@ -1,33 +0,0 @@
|
|
|
1
|
-
import { createRouter, createWebHistory } from 'vue-router';
|
|
2
|
-
import type { Plugin } from 'vue';
|
|
3
|
-
|
|
4
|
-
import { defineBootstrapHook } from '@/bootstrap/hooks';
|
|
5
|
-
|
|
6
|
-
function createAppRouter(options: { routes: RouteRecordRaw[]; basePath?: string }): Plugin {
|
|
7
|
-
return createRouter({
|
|
8
|
-
history: createWebHistory(options.basePath),
|
|
9
|
-
routes: options.routes,
|
|
10
|
-
});
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
export default defineBootstrapHook(async (app, options) => {
|
|
14
|
-
if (!options.routes) {
|
|
15
|
-
return;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
const plugin = createAppRouter({
|
|
19
|
-
routes: options.routes,
|
|
20
|
-
basePath: options.basePath ?? __AG_BASE_PATH,
|
|
21
|
-
});
|
|
22
|
-
|
|
23
|
-
app.use(plugin);
|
|
24
|
-
});
|
|
25
|
-
|
|
26
|
-
declare module '@/bootstrap/options' {
|
|
27
|
-
interface BootstrapOptions {
|
|
28
|
-
routes?: RouteRecordRaw[];
|
|
29
|
-
basePath?: string;
|
|
30
|
-
}
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
import type { RouteRecordRaw } from 'vue-router';
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
foo: Bar
|