@scenemesh/entity-engine
Version:
一个“元数据驱动 + 组件适配 + 动态关系 + 视图管线”式的实体引擎。以 **Model + View + FieldType + SuiteAdapter + DataSource** 为五大支点,统一 CRUD / 查询 / 引用管理 / 视图渲染 / 扩展注册,支持在运行期无侵入拼装出 **表单、网格、主从、看板、仪表盘、流程/树形视图** 等多形态界面。
510 lines (406 loc) • 19.7 kB
JavaScript
"use strict";Object.defineProperty(exports, "__esModule", {value: true}); function _interopRequireWildcard(obj) { if (obj && obj.__esModule) { return obj; } else { var newObj = {}; if (obj != null) { for (var key in obj) { if (Object.prototype.hasOwnProperty.call(obj, key)) { newObj[key] = obj[key]; } } } newObj.default = obj; return newObj; } } function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } function _nullishCoalesce(lhs, rhsFn) { if (lhs != null) { return lhs; } else { return rhsFn(); } } function _optionalChain(ops) { let lastAccessLHS = undefined; let value = ops[0]; let i = 1; while (i < ops.length) { const op = ops[i]; const fn = ops[i + 1]; i += 2; if ((op === 'optionalAccess' || op === 'optionalCall') && value == null) { return undefined; } if (op === 'access' || op === 'optionalAccess') { lastAccessLHS = value; value = fn(value); } else if (op === 'call' || op === 'optionalCall') { value = fn((...args) => value.call(lastAccessLHS, ...args)); lastAccessLHS = undefined; } } return value; }"use client";
var _chunkW3GG22TSjs = require('./chunk-W3GG22TS.js');
// src/core/types/session.types.ts
var EntitySession = class {
constructor(sessionId, userInfo, update = () => {
}) {
this.sessionId = sessionId;
this.userInfo = userInfo;
this.update = update;
}
isAuthenticated() {
return !!this.userInfo;
}
};
// src/components/renderers/view-inspector/index.tsx
var _react = require('react'); var React = _interopRequireWildcard(_react);
var _modals = require('@mantine/modals');
var _reactjsonview = require('@uiw/react-json-view'); var _reactjsonview2 = _interopRequireDefault(_reactjsonview);
var _core = require('@mantine/core');
var _lucidereact = require('lucide-react');
// src/lib/hooks/utils/use-async/use-async.ts
// src/lib/hooks/utils/use-async-effect/use-async-effect.ts
function useAsyncEffect(effect, deps) {
const abortRef = _react.useRef.call(void 0, null);
_react.useEffect.call(void 0, () => {
abortRef.current = new AbortController();
return () => {
_optionalChain([abortRef, 'access', _ => _.current, 'optionalAccess', _2 => _2.abort, 'call', _3 => _3()]);
};
}, []);
_react.useEffect.call(void 0, () => {
let canceled = false;
let result;
const load = async () => {
const signal = abortRef.current.signal;
if (canceled || signal.aborted) {
return;
}
result = await effect(signal);
};
queueMicrotask(load);
return () => {
canceled = true;
if (result) {
result();
}
};
}, deps);
}
// src/lib/hooks/utils/use-async/use-async.ts
function useAsync(func, deps) {
const [{ state, data, error }, setState] = _react.useState.call(void 0, {});
useAsyncEffect(async () => {
setState((draft) => ({ ...draft, state: "loading" }));
try {
const result = await func();
setState({ state: "hasData", data: result });
} catch (e) {
setState((draft) => ({ ...draft, state: "hasError", error: e }));
}
}, deps);
return {
state: _nullishCoalesce(state, () => ( "loading")),
data,
error
};
}
function useAsyncWithCache(func, deps) {
const [internalState, setInternalState] = _react.useState.call(void 0, { state: "loading" });
const deferredResult = _react.useDeferredValue.call(void 0, internalState);
const [loadingState, setLoadingState] = _react.useState.call(void 0, false);
useAsyncEffect(async () => {
setLoadingState(true);
try {
const result = await func();
setInternalState({ state: "hasData", data: result, error: void 0 });
} catch (e) {
setInternalState({ state: "hasError", data: void 0, error: e });
} finally {
setLoadingState(false);
}
}, deps);
return {
state: loadingState ? "loading" : _nullishCoalesce(deferredResult.state, () => ( "loading")),
data: deferredResult.data,
error: deferredResult.error
};
}
// src/services/api/trpc/react.tsx
var _superjson = require('superjson'); var _superjson2 = _interopRequireDefault(_superjson);
var _reactquery = require('@trpc/react-query');
var _client = require('@trpc/client');
var _reactquery3 = require('@tanstack/react-query');
// src/services/api/trpc/query-client.ts
var createQueryClient = () => new (0, _reactquery3.QueryClient)({
defaultOptions: {
queries: {
// With SSR, we usually want to set some default staleTime
// above 0 to avoid refetching immediately on the client
staleTime: 30 * 1e3
},
dehydrate: {
serializeData: _superjson2.default.serialize,
shouldDehydrateQuery: (query) => _reactquery3.defaultShouldDehydrateQuery.call(void 0, query) || query.state.status === "pending"
},
hydrate: {
deserializeData: _superjson2.default.deserialize
}
}
});
// src/services/api/trpc/react.tsx
var _jsxruntime = require('react/jsx-runtime');
var clientQueryClientSingleton = void 0;
var getQueryClient = () => {
if (typeof window === "undefined") {
return createQueryClient();
}
_nullishCoalesce(clientQueryClientSingleton, () => ( (clientQueryClientSingleton = createQueryClient())));
return clientQueryClientSingleton;
};
var api = _reactquery.createTRPCReact.call(void 0, );
function TRPCReactProvider(props) {
const engine = _chunkW3GG22TSjs.useEntityEngine.call(void 0, );
const queryClient = getQueryClient();
const [trpcClient] = React.useState(
() => api.createClient({
links: [
_client.loggerLink.call(void 0, {
enabled: (op) => false
// process.env.NODE_ENV === 'development' ||
// (op.direction === 'down' && op.result instanceof Error),
}),
_client.httpBatchStreamLink.call(void 0, {
transformer: _superjson2.default,
url: engine.settings.getUrl("/trpc"),
///api/ee/trpc
headers: () => {
const headers = new Headers();
headers.set("x-trpc-source", "nextjs-react");
return headers;
}
})
]
})
);
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _reactquery3.QueryClientProvider, { client: queryClient, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, api.Provider, { client: trpcClient, queryClient, children: props.children }) });
}
// src/core/engine/engine.initializer.ts
var EngineInitializer = class {
constructor(args) {
this._config = args.config;
this._suiteAdapters = args.suiteAdapters;
this._renderers = args.renderers;
this._fieldTypers = args.fieldTypers;
this._settings = args.settings;
this._modules = args.modules;
this._sessionProvider = args.sessionProvider;
}
async init(engine) {
if (this._config) {
const { models, views } = this._config;
if (models.length > 0) {
for (const model of models) {
engine.metaRegistry.registerModel(model);
}
}
if (views.length > 0) {
for (const view of views) {
engine.metaRegistry.registerView(view);
}
}
}
if (this._suiteAdapters && this._suiteAdapters.length > 0) {
for (const adapter of this._suiteAdapters) {
engine.componentRegistry.registerAdapter(adapter);
}
}
if (this._renderers && this._renderers.length > 0) {
for (const renderer of this._renderers) {
engine.componentRegistry.registerRenderer(renderer);
}
}
if (this._fieldTypers && this._fieldTypers.length > 0) {
for (const typer of this._fieldTypers) {
engine.fieldTyperRegistry.registerFieldTyper(typer);
}
}
if (this._modules && this._modules.length > 0) {
for (const mod of this._modules) {
await engine.moduleRegistry.registerModule(mod, true);
}
}
if (this._sessionProvider) {
engine.sessionManager.setProvider(this._sessionProvider);
}
if (this._settings) {
engine.settings.setBaseUrl(this._settings.baseUrl || "");
engine.settings.setEndpoint(
this._settings.endpoint || process.env.EE_SERVICE_ROOT_PATH || "/api/ee"
);
engine.settings.authenticationEnabled = this._settings.authenticationEnabled || false;
}
console.log(
`Entity Engine initialized with models(${_optionalChain([this, 'access', _4 => _4._config, 'optionalAccess', _5 => _5.models, 'access', _6 => _6.length]) || 0}) and views(${_optionalChain([this, 'access', _7 => _7._config, 'optionalAccess', _8 => _8.views, 'access', _9 => _9.length]) || 0})`
);
}
};
// src/uikit/provider/entity-engine-provider-factory.tsx
function createEntityEngineProvider(config) {
process.env.EE_SERVICE_ROOT_PATH = _optionalChain([config, 'access', _10 => _10.settings, 'optionalAccess', _11 => _11.endpoint]) || "/api/ee";
const initializer = new EngineInitializer({
config: config.config,
suiteAdapters: config.suiteAdapters,
renderers: config.renderers,
fieldTypers: config.fieldTypers,
modules: config.modules,
settings: config.settings
});
const ConfiguredProvider = ({ children }) => /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
_chunkW3GG22TSjs.EntitySuiteAdapterProvider,
{
adapter: config.suiteAdapter || { suiteName: "build-in", suiteVersion: "1.0.0" },
children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
_chunkW3GG22TSjs.EntityEngineProvider,
{
initializer,
loading: config.loading,
router: config.router,
permissionGuard: config.permissionGuard,
children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _chunkW3GG22TSjs.EntityEngineThemeProvider, { theme: config.theme, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, TRPCReactProvider, { children }) })
}
)
}
);
ConfiguredProvider.displayName = "EntityEngineProvider(Configured)";
return ConfiguredProvider;
}
// src/uikit/surface/empty-symbol-comp.tsx
function EmptySymbol() {
return null;
}
// src/uikit/consumer/entity-object-consumer.tsx
function EntityObjectsConsumer(props) {
const { modelName, query, withReference, objectsRenderer, onError, loading } = props;
const engine = _chunkW3GG22TSjs.useEntityEngine.call(void 0, );
const model = engine.metaRegistry.getModel(modelName);
if (!model) {
return null;
}
const datasource = engine.datasourceFactory.getDataSource();
const dsHook = _chunkW3GG22TSjs.toDataSourceHook.call(void 0, datasource);
const {
data,
loading: isLoading,
error
} = dsHook.useFindMany({
modelName,
query,
withAllReferences: withReference || false
});
if (isLoading || !data) {
return loading || /* @__PURE__ */ _jsxruntime.jsx.call(void 0, "div", { children: "Loading..." });
}
if (error) {
if (onError) {
return onError(error);
}
return /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, "div", { style: { color: "red" }, children: [
"Error: ",
error.message
] });
}
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _jsxruntime.Fragment, { children: objectsRenderer(data.count, data.data) });
}
function EntityObjectConsumer(props) {
const { modelName, objectId, withReference, objectRenderer, onError, loading } = props;
const engine = _chunkW3GG22TSjs.useEntityEngine.call(void 0, );
const datasource = engine.datasourceFactory.getDataSource();
const dsHook = _chunkW3GG22TSjs.toDataSourceHook.call(void 0, datasource);
const { data, error, state } = useAsync(async () => {
if (withReference) {
return await datasource.findOneWithReferences({
modelName,
id: objectId,
includeFieldNames: void 0
});
} else {
return await datasource.findOne({
modelName,
id: objectId
});
}
}, [objectId, withReference]);
if (state === "loading" || !data) {
return loading || /* @__PURE__ */ _jsxruntime.jsx.call(void 0, "div", { children: "Loading..." });
}
if (error) {
if (onError) {
return onError(error);
}
return /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, "div", { style: { color: "red" }, children: [
"Error: ",
error.message
] });
}
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _jsxruntime.Fragment, { children: objectRenderer(data) });
}
// src/components/renderers/view-inspector/index.tsx
var EntityViewInspector = {
name: "buildin-view-inspector",
slotName: "view-inspector",
disabled: false,
renderer: (props) => /* @__PURE__ */ _jsxruntime.jsx.call(void 0, EntityViewInspectorComp, { ...props })
};
function EntityViewInspectorComp(props) {
const { model, viewData } = props;
const handleAction = () => {
_modals.modals.open({
title: "\u89C6\u56FE\u914D\u7F6E\u6570\u636E",
children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, "div", { children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, InnerEntityViewInspectorComp, { ...props, model, viewData }) }),
size: "80%",
centered: true,
closeOnClickOutside: true,
closeOnEscape: true,
onClose: () => {
console.log("Settings modal closed");
}
});
};
return /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _core.ActionIcon, { variant: "subtle", "aria-label": "Settings", onClick: handleAction, children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.Settings2Icon, { size: 14, strokeWidth: 2 }) });
}
function InnerEntityViewInspectorComp(props) {
const { model, viewData, ...otherProps } = props;
const [tab, setTab] = React.default.useState("model");
const engine = _chunkW3GG22TSjs.useEntityEngine.call(void 0, );
const handleTabChange = (value) => {
setTab(value || "model");
};
return /* @__PURE__ */ _jsxruntime.jsxs.call(void 0, _core.Tabs, { value: tab, variant: "outline", color: "blue", radius: "md", onChange: handleTabChange, children: [
/* @__PURE__ */ _jsxruntime.jsxs.call(void 0, _core.Tabs.List, { children: [
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _core.Tabs.Tab, { value: "model", leftSection: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.ViewIcon, { size: 14, strokeWidth: 2 }), children: "\u6A21\u578B\u914D\u7F6E" }),
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _core.Tabs.Tab, { value: "view", leftSection: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.DatabaseIcon, { size: 14, strokeWidth: 2 }), children: "\u89C6\u56FE\u914D\u7F6E" }),
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _core.Tabs.Tab, { value: "other", leftSection: /* @__PURE__ */ _jsxruntime.jsx.call(void 0, _lucidereact.Settings2Icon, { size: 14, strokeWidth: 2 }), children: "\u5176\u4ED6\u6570\u636E" })
] }),
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _core.Tabs.Panel, { value: "model", pt: "xs", children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
_reactjsonview2.default,
{
value: JSON.parse(
JSON.stringify(model, (key, value) => {
if (typeof key === "string" && key.startsWith("_metaRegistry")) {
return void 0;
}
return value;
})
)
}
) }),
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _core.Tabs.Panel, { value: "view", pt: "xs", children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
_reactjsonview2.default,
{
value: JSON.parse(
JSON.stringify(viewData, (key, value) => {
if (typeof key === "string" && key.startsWith("_metaRegistry")) {
return void 0;
}
return value;
})
)
}
) }),
/* @__PURE__ */ _jsxruntime.jsx.call(void 0, _core.Tabs.Panel, { value: "other", pt: "xs", children: /* @__PURE__ */ _jsxruntime.jsx.call(void 0,
_reactjsonview2.default,
{
value: JSON.parse(
JSON.stringify(otherProps, (key, value) => {
if (typeof key === "string" && key.startsWith("_metaRegistry")) {
return void 0;
}
return value;
})
)
}
) })
] });
}
// src/types/data.types.ts
var QueryOperator = /* @__PURE__ */ ((QueryOperator2) => {
QueryOperator2["NONE"] = "none";
QueryOperator2["EQ"] = "eq";
QueryOperator2["NE"] = "ne";
QueryOperator2["GT"] = "gt";
QueryOperator2["GTE"] = "gte";
QueryOperator2["LT"] = "lt";
QueryOperator2["LTE"] = "lte";
QueryOperator2["CONTAINS"] = "contains";
QueryOperator2["STARTS_WITH"] = "startsWith";
QueryOperator2["ENDS_WITH"] = "endsWith";
QueryOperator2["IN"] = "in";
QueryOperator2["NOT_IN"] = "notIn";
QueryOperator2["IS_NULL"] = "isNull";
QueryOperator2["IS_NOT_NULL"] = "isNotNull";
QueryOperator2["BETWEEN"] = "between";
return QueryOperator2;
})(QueryOperator || {});
exports.BuildinModule = _chunkW3GG22TSjs.BuildinModule; exports.EmptySymbol = EmptySymbol; exports.EntityActionRegistry = _chunkW3GG22TSjs.EntityActionRegistry; exports.EntityComponentRegistry = _chunkW3GG22TSjs.EntityComponentRegistry; exports.EntityDataSourceFactory = _chunkW3GG22TSjs.EntityDataSourceFactory; exports.EntityEngine = _chunkW3GG22TSjs.EntityEngine; exports.EntityEngineProvider = _chunkW3GG22TSjs.EntityEngineProvider; exports.EntityEngineThemeProvider = _chunkW3GG22TSjs.EntityEngineThemeProvider; exports.EntityEventRegistry = _chunkW3GG22TSjs.EntityEventRegistry; exports.EntityFieldDelegate = _chunkW3GG22TSjs.EntityFieldDelegate; exports.EntityMetaRegistry = _chunkW3GG22TSjs.EntityMetaRegistry; exports.EntityModelDelegate = _chunkW3GG22TSjs.EntityModelDelegate; exports.EntityNamedRenderer = _chunkW3GG22TSjs.EntityNamedRenderer; exports.EntityObjectConsumer = EntityObjectConsumer; exports.EntityObjectsConsumer = EntityObjectsConsumer; exports.EntityPermissionGuard = _chunkW3GG22TSjs.EntityPermissionGuard; exports.EntitySession = EntitySession; exports.EntitySessionManager = _chunkW3GG22TSjs.EntitySessionManager; exports.EntitySuiteAdapterProvider = _chunkW3GG22TSjs.EntitySuiteAdapterProvider; exports.EntityView = _chunkW3GG22TSjs.EntityView; exports.EntityViewContainer = _chunkW3GG22TSjs.EntityViewContainer; exports.EntityViewDelegate = _chunkW3GG22TSjs.EntityViewDelegate; exports.EntityViewFieldDelegate = _chunkW3GG22TSjs.EntityViewFieldDelegate; exports.EntityViewInspector = EntityViewInspector; exports.EntityWidget = _chunkW3GG22TSjs.EntityWidget; exports.EntityWidgetRenderer = _chunkW3GG22TSjs.EntityWidgetRenderer; exports.ModelFieldTyperRegistry = _chunkW3GG22TSjs.ModelFieldTyperRegistry; exports.QueryOperator = QueryOperator; exports.TRPCEntityObjectDataSource = _chunkW3GG22TSjs.TRPCEntityObjectDataSource; exports.ViewContainerProvider = _chunkW3GG22TSjs.ViewContainerProvider; exports.createEntityEngineProvider = createEntityEngineProvider; exports.entityEngineDefaultTheme = _chunkW3GG22TSjs.entityEngineDefaultTheme; exports.getEntityEngine = _chunkW3GG22TSjs.getEntityEngine; exports.toDataSourceHook = _chunkW3GG22TSjs.toDataSourceHook; exports.useAsync = useAsync; exports.useAsyncEffect = useAsyncEffect; exports.useAsyncWithCache = useAsyncWithCache; exports.useContainerRouter = _chunkW3GG22TSjs.useContainerRouter; exports.useEntityEngine = _chunkW3GG22TSjs.useEntityEngine; exports.useEntityEngineRouter = _chunkW3GG22TSjs.useEntityEngineRouter; exports.useEntityEngineTheme = _chunkW3GG22TSjs.useEntityEngineTheme; exports.useEntityPermissionGuard = _chunkW3GG22TSjs.useEntityPermissionGuard; exports.useEntitySession = _chunkW3GG22TSjs.useEntitySession; exports.useEntitySuiteAdapter = _chunkW3GG22TSjs.useEntitySuiteAdapter; exports.useMasterDetailViewContainer = _chunkW3GG22TSjs.useMasterDetailViewContainer;
//# sourceMappingURL=index.js.map