Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions etc/brick-types.api.md
Original file line number Diff line number Diff line change
Expand Up @@ -1160,12 +1160,12 @@ export interface ExtendedHistory {
// @internal (undocumented)
getBlockMessage: () => string;
// Warning: (ae-incompatible-release-tags) The symbol "push" is marked as @public, but its signature references "PluginHistoryState" which is marked as @internal
push?: History_2<PluginHistoryState>["push"];
push?: (location: LocationDescriptor<PluginHistoryState>, state?: PluginHistoryState, callback?: (blocked: boolean) => void) => void;
pushAnchor: UpdateAnchorFunction;
pushQuery: UpdateQueryFunction;
reload: () => void;
reload: (callback?: (blocked: boolean) => void) => void;
// Warning: (ae-incompatible-release-tags) The symbol "replace" is marked as @public, but its signature references "PluginHistoryState" which is marked as @internal
replace?: History_2<PluginHistoryState>["replace"];
replace?: (location: LocationDescriptor<PluginHistoryState>, state?: PluginHistoryState, callback?: (blocked: boolean) => void) => void;
replaceQuery: UpdateQueryFunction;
// @internal (undocumented)
setBlockMessage: (message: string) => void;
Expand Down Expand Up @@ -2436,10 +2436,10 @@ export interface TransformMap {
// Warning: (ae-incompatible-release-tags) The symbol "UpdateAnchorFunction" is marked as @public, but its signature references "PluginHistoryState" which is marked as @internal
//
// @public
export type UpdateAnchorFunction = (hash: string, state?: PluginHistoryState) => void;
export type UpdateAnchorFunction = (hash: string, state?: PluginHistoryState, callback?: (blocked: boolean) => void) => void;

// @public
export type UpdateQueryFunction = (query: Record<string, unknown>, options?: UpdateQueryOptions) => void;
export type UpdateQueryFunction = (query: Record<string, unknown>, options?: UpdateQueryOptions, callback?: (blocked: boolean) => void) => void;

// Warning: (ae-incompatible-release-tags) The symbol "UpdateQueryOptions" is marked as @public, but its signature references "PluginHistoryState" which is marked as @internal
//
Expand Down
1 change: 0 additions & 1 deletion packages/brick-kit/src/core/LocationContext.ts
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,6 @@ import { preConstructMenus } from "../internal/menu";
import { Media } from "../internal/mediaQuery";
import { getReadOnlyProxy } from "../internal/proxyFactories";
import { customTemplateRegistry } from "./CustomTemplates/constants";
import { CustomTemplate } from "../../../brick-types/dist/types/manifest";
import {
ExpandCustomForm,
formDataProperties,
Expand Down
6 changes: 5 additions & 1 deletion packages/brick-kit/src/history.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
import { createBrowserHistory } from "history";
import { PluginHistory } from "@next-core/brick-types";
import { historyExtended } from "./internal/historyExtended";
import {
getUserConfirmation,
historyExtended,
} from "./internal/historyExtended";
import { getBasePath } from "./internal/getBasePath";

let history: PluginHistory;
Expand All @@ -9,6 +12,7 @@ let history: PluginHistory;
export function createHistory(): PluginHistory {
const browserHistory = createBrowserHistory({
basename: getBasePath().replace(/\/$/, ""),
getUserConfirmation,
});
Object.assign(browserHistory, historyExtended(browserHistory));
history = browserHistory as PluginHistory;
Expand Down
115 changes: 99 additions & 16 deletions packages/brick-kit/src/internal/bindListeners.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -50,8 +50,12 @@ customElements.define(
);

const mockHistory = {
push: jest.fn(),
replace: jest.fn(),
push: jest.fn((loc, state, callback) => {
callback?.(true);
}),
replace: jest.fn((loc, state, callback) => {
callback?.(false);
}),
pushQuery: jest.fn(),
replaceQuery: jest.fn(),
pushAnchor: jest.fn(),
Expand Down Expand Up @@ -312,10 +316,40 @@ describe("bindListeners", () => {
window.parent.postMessage = jest.fn();
const eventsMap: BrickEventsMap = {
key1: [
{ action: "history.push" },
{
action: "history.push",
callback: {
success: {
action: "console.info",
args: ["<% `history.push:success:${EVENT.detail.blocked}` %>"],
},
error: {
action: "console.info",
args: ["<% `history.push:error:${EVENT.detail.blocked}` %>"],
},
finally: {
action: "console.info",
args: ["<% `history.push:finally:${EVENT.detail.blocked}` %>"],
},
},
},
{
action: "history.replace",
args: ["specified args for history.replace"],
callback: {
success: {
action: "console.info",
args: ["<% `history.replace:success:${EVENT.detail.blocked}` %>"],
},
error: {
action: "console.info",
args: ["<% `history.replace:error:${EVENT.detail.blocked}` %>"],
},
finally: {
action: "console.info",
args: ["<% `history.replace:finally:${EVENT.detail.blocked}` %>"],
},
},
},
{
action: "history.pushQuery",
Expand Down Expand Up @@ -366,7 +400,24 @@ describe("bindListeners", () => {
args: [true],
},
{ action: "location.assign", args: ["www.baidu.com"] },
{ action: "segue.push", args: ["testSegueIdA"] },
{
action: "segue.push",
args: ["testSegueIdA"],
callback: {
success: {
action: "console.info",
args: ["<% `segue.push:success:${EVENT.detail.blocked}` %>"],
},
error: {
action: "console.info",
args: ["<% `segue.push:error:${EVENT.detail.blocked}` %>"],
},
finally: {
action: "console.info",
args: ["<% `segue.push:finally:${EVENT.detail.blocked}` %>"],
},
},
},
{
action: "segue.replace",
args: ["testSegueIdB", { id: "${EVENT.detail}" }],
Expand Down Expand Up @@ -685,8 +736,18 @@ describe("bindListeners", () => {
expect(sessionStorage.removeItem).toBeCalledWith("foo");

const history = mockHistory;
expect(history.push).toHaveBeenNthCalledWith(1, "for-good");
expect(history.push).toHaveBeenNthCalledWith(2, "/segue-target-a");
expect(history.push).toHaveBeenNthCalledWith(
1,
"for-good",
undefined,
expect.any(Function)
);
expect(history.push).toHaveBeenNthCalledWith(
2,
"/segue-target-a",
undefined,
expect.any(Function)
);
expect(history.push).toHaveBeenNthCalledWith(3, "/mock/alias/a");
expect(history.pushQuery).toBeCalledWith(
{
Expand All @@ -702,20 +763,27 @@ describe("bindListeners", () => {
);
expect(history.replace).toHaveBeenNthCalledWith(
1,
"specified args for history.replace"
"specified args for history.replace",
undefined,
expect.any(Function)
);
expect(history.replace).toHaveBeenNthCalledWith(
2,
"/segue-target-b/for-good"
"/segue-target-b/for-good",
undefined,
undefined
);
expect(history.replace).toHaveBeenNthCalledWith(
3,
"/mock/alias/b/for-good"
);
expect(history.replaceQuery).toBeCalledWith({
page: 1,
});
expect(history.pushAnchor).toBeCalledWith("yes");
expect(history.replaceQuery).toBeCalledWith(
{
page: 1,
},
undefined
);
expect(history.pushAnchor).toBeCalledWith("yes", undefined);
expect(history.goBack).toBeCalledWith();
expect(history.goForward).toBeCalledWith();
expect(history.reload).toBeCalled();
Expand Down Expand Up @@ -758,26 +826,41 @@ describe("bindListeners", () => {
);
expect((console.log as jest.Mock).mock.calls[3][0].detail).toBe("resolved");

expect(console.info).toBeCalledTimes(4);
expect(console.info).toHaveBeenNthCalledWith(1, expectEvent(event1));
expect(console.info).toBeCalledTimes(10);
expect(console.info).toHaveBeenNthCalledWith(1, "history.push:error:true");
expect(console.info).toHaveBeenNthCalledWith(
2,
"history.push:finally:true"
);
expect(console.info).toHaveBeenNthCalledWith(
3,
"history.replace:success:false"
);
expect(console.info).toHaveBeenNthCalledWith(
4,
"history.replace:finally:false"
);
expect(console.info).toHaveBeenNthCalledWith(5, "segue.push:error:true");
expect(console.info).toHaveBeenNthCalledWith(6, "segue.push:finally:true");
expect(console.info).toHaveBeenNthCalledWith(7, expectEvent(event1));
expect(console.info).toHaveBeenNthCalledWith(
8,
expectEvent(
new CustomEvent("callback.finally", {
detail: undefined,
})
)
);
expect(console.info).toHaveBeenNthCalledWith(
3,
9,
expectEvent(
new CustomEvent("callback.progress", {
detail: "progressing",
})
)
);
expect(console.info).toHaveBeenNthCalledWith(
4,
10,
expectEvent(
new CustomEvent("callback.progress", {
detail: "resolved",
Expand Down
94 changes: 64 additions & 30 deletions packages/brick-kit/src/internal/bindListeners.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ import { getMessageDispatcher } from "../core/MessageDispatcher";
import { PluginWebSocketMessageTopic } from "../websocket/interfaces";
import { applyTheme, applyMode } from "../themeAndMode";
import { clearMenuTitleCache, clearMenuCache } from "./menu";
import { PollableCallback, PollableCallbackFunction, startPoll } from "./poll";
import { PollableCallback, startPoll } from "./poll";
import { getArgsOfCustomApi } from "../core/FlowApi";
import { getRuntime } from "../runtime";
import {
Expand Down Expand Up @@ -125,19 +125,15 @@ export function listenerFactory(
case "history.replaceQuery":
case "history.pushAnchor":
case "history.block":
return builtinHistoryListenerFactory(
method,
handler.args,
handler,
context
);
case "history.goBack":
case "history.goForward":
case "history.reload":
case "history.unblock":
return builtinHistoryWithoutArgsListenerFactory(
return builtinHistoryListenerFactory(
method,
handler.args,
handler,
handler.callback,
context
);
case "segue.push":
Expand All @@ -146,6 +142,7 @@ export function listenerFactory(
method,
handler.args,
handler,
handler.callback,
context
);
case "alias.push":
Expand Down Expand Up @@ -428,6 +425,7 @@ function builtinSegueListenerFactory(
method: "push" | "replace",
args: unknown[],
ifContainer: IfContainer,
callback: BrickEventHandlerCallback,
context: PluginRuntimeContext
): EventListener {
return function (event: CustomEvent): void {
Expand All @@ -443,7 +441,19 @@ function builtinSegueListenerFactory(
...(argsFactory(args, context, event) as Parameters<
ReturnType<typeof getUrlBySegueFactory>
>)
)
),
undefined,
callback
? (blocked) => {
const callbackFactory = eventCallbackFactory(
callback,
() => context,
null
);
callbackFactory(blocked ? "error" : "success")({ blocked });
callbackFactory("finally")({ blocked });
}
: undefined
);
} as EventListener;
}
Expand Down Expand Up @@ -759,37 +769,61 @@ function builtinHistoryListenerFactory(
| "pushQuery"
| "replaceQuery"
| "pushAnchor"
| "block",
| "block"
| "goBack"
| "goForward"
| "reload"
| "unblock",
args: unknown[],
ifContainer: IfContainer,
callback: BrickEventHandlerCallback,
context: PluginRuntimeContext
): EventListener {
return function (event: CustomEvent): void {
if (!looseCheckIf(ifContainer, { ...context, event })) {
return;
}
(
getHistory()[method === "block" ? "setBlockMessage" : method] as (
...args: unknown[]
) => unknown
)(
...argsFactory(args, context, event, {
let baseArgsLength = 0;
let hasCallback = false;
let overrideMethod = method as "setBlockMessage";
switch (method) {
case "push":
case "replace":
case "pushQuery":
case "replaceQuery":
case "pushAnchor":
baseArgsLength = 2;
hasCallback = true;
break;
case "reload":
hasCallback = true;
break;
case "block":
baseArgsLength = 1;
overrideMethod = "setBlockMessage";
break;
}
let computedArgs: unknown[] = [];
if (baseArgsLength > 0) {
computedArgs = argsFactory(args, context, event, {
useEventDetailAsDefault: true,
})
);
} as EventListener;
}

function builtinHistoryWithoutArgsListenerFactory(
method: "goBack" | "goForward" | "reload" | "unblock",
ifContainer: IfContainer,
context: PluginRuntimeContext
): EventListener {
return function (event: CustomEvent): void {
if (!looseCheckIf(ifContainer, { ...context, event })) {
return;
});
computedArgs.length = baseArgsLength;
}
getHistory()[method]();
if (hasCallback && callback) {
const callbackFactory = eventCallbackFactory(
callback,
() => context,
null
);
computedArgs.push((blocked: boolean) => {
callbackFactory(blocked ? "error" : "success")({ blocked });
callbackFactory("finally")({ blocked });
});
}
(getHistory()[overrideMethod] as (...args: unknown[]) => unknown)(
...computedArgs
);
} as EventListener;
}

Expand Down
Loading