feat: add entity param for list item operation extension point (#4515)

#### What type of PR is this?

/area console
/kind feature
/milestone 2.9.x

#### What this PR does / why we need it:

Halo 在 https://github.com/halo-dev/halo/pull/4452 中为数据列表的操作选项添加了拓展点,用于通过插件扩展操作选项。但忽略了操作选项的组件需要自定义并且自行处理点击事件,这个时候组件应该比较难拿到数据列表项的数据。

此 PR 对此进行优化,在扩展点方法传入了需要的数据。

#### Does this PR introduce a user-facing change?

```release-note
None
```
pull/4523/head
Ryan Wang 2023-08-30 22:36:13 -05:00 committed by GitHub
parent 9c875e1731
commit 329b389d60
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 38 additions and 24 deletions

View File

@ -8,9 +8,9 @@
目前支持扩展的数据列表:
- 文章:`"post:list-item:operation:create"?: () => | EntityDropdownItem<ListedPost>[] | Promise<EntityDropdownItem<ListedPost>[]>`
- 插件:`"plugin:list-item:operation:create"?: () => | EntityDropdownItem<Plugin>[] | Promise<EntityDropdownItem<Plugin>[]>`
- 备份:`"backup:list-item:operation:create"?: () => | EntityDropdownItem<Backup>[] | Promise<EntityDropdownItem<Backup>[]>`
- 文章:`"post:list-item:operation:create"?: (post: Ref<ListedPost>) => | EntityDropdownItem<ListedPost>[] | Promise<EntityDropdownItem<ListedPost>[]>`
- 插件:`"plugin:list-item:operation:create"?: (plugin: Ref<Plugin>) => | EntityDropdownItem<Plugin>[] | Promise<EntityDropdownItem<Plugin>[]>`
- 备份:`"backup:list-item:operation:create"?: (backup: Ref<Backup>) => | EntityDropdownItem<Backup>[] | Promise<EntityDropdownItem<Backup>[]>`
示例:

View File

@ -40,17 +40,19 @@ export interface ExtensionPoint {
| PluginInstallationTab[]
| Promise<PluginInstallationTab[]>;
"post:list-item:operation:create"?: () =>
"post:list-item:operation:create"?: (
post: Ref<ListedPost>
) =>
| EntityDropdownItem<ListedPost>[]
| Promise<EntityDropdownItem<ListedPost>[]>;
"plugin:list-item:operation:create"?: () =>
| EntityDropdownItem<Plugin>[]
| Promise<EntityDropdownItem<Plugin>[]>;
"plugin:list-item:operation:create"?: (
plugin: Ref<Plugin>
) => EntityDropdownItem<Plugin>[] | Promise<EntityDropdownItem<Plugin>[]>;
"backup:list-item:operation:create"?: () =>
| EntityDropdownItem<Backup>[]
| Promise<EntityDropdownItem<Backup>[]>;
"backup:list-item:operation:create"?: (
backup: Ref<Backup>
) => EntityDropdownItem<Backup>[] | Promise<EntityDropdownItem<Backup>[]>;
"plugin:list-item:field:create"?: (
plugin: Ref<Plugin>

View File

@ -5,15 +5,16 @@ import type {
EntityFieldItem,
PluginModule,
} from "@halo-dev/console-shared";
import { onMounted, ref, type Ref, computed, type ComputedRef } from "vue";
import { onMounted, ref, type ComputedRef, type Ref, computed } from "vue";
export function useEntityDropdownItemExtensionPoint<T>(
extensionPointName: string,
presets: EntityDropdownItem<T>[]
entity: Ref<T>,
presets: ComputedRef<EntityDropdownItem<T>[]>
) {
const { pluginModules } = usePluginModuleStore();
const dropdownItems = ref<EntityDropdownItem<T>[]>(presets);
const itemsFromPlugins = ref<EntityDropdownItem<T>[]>([]);
onMounted(() => {
pluginModules.forEach((pluginModule: PluginModule) => {
@ -22,14 +23,16 @@ export function useEntityDropdownItemExtensionPoint<T>(
return;
}
const items = extensionPoints[
extensionPointName
]() as EntityDropdownItem<T>[];
const items = extensionPoints[extensionPointName](
entity
) as EntityDropdownItem<T>[];
dropdownItems.value.push(...items);
itemsFromPlugins.value.push(...items);
});
});
dropdownItems.value.sort((a, b) => {
const dropdownItems = computed(() => {
return [...presets.value, ...itemsFromPlugins.value].sort((a, b) => {
return a.priority - b.priority;
});
});

View File

@ -29,6 +29,7 @@ import { markRaw } from "vue";
import { useRouter } from "vue-router";
import { useEntityDropdownItemExtensionPoint } from "@/composables/use-entity-extension-points";
import EntityDropdownItems from "@/components/entity/EntityDropdownItems.vue";
import { toRefs } from "vue";
const { currentUserHasPermission } = usePermission();
const { t } = useI18n();
@ -45,6 +46,8 @@ const props = withDefaults(
}
);
const { post } = toRefs(props);
const emit = defineEmits<{
(event: "open-setting-modal", post: Post): void;
}>();
@ -121,7 +124,8 @@ const handleDelete = async () => {
const { dropdownItems } = useEntityDropdownItemExtensionPoint<ListedPost>(
"post:list-item:operation:create",
[
post,
computed(() => [
{
priority: 10,
component: markRaw(VDropdownItem),
@ -161,7 +165,7 @@ const { dropdownItems } = useEntityDropdownItemExtensionPoint<ListedPost>(
permissions: [],
action: handleDelete,
},
]
])
);
</script>

View File

@ -17,6 +17,7 @@ import prettyBytes from "pretty-bytes";
import { useI18n } from "vue-i18n";
import { useEntityDropdownItemExtensionPoint } from "@/composables/use-entity-extension-points";
import EntityDropdownItems from "@/components/entity/EntityDropdownItems.vue";
import { toRefs } from "vue";
const queryClient = useQueryClient();
const { t } = useI18n();
@ -25,6 +26,8 @@ const props = defineProps<{
backup: Backup;
}>();
const { backup } = toRefs(props);
type Phase = {
text: string;
state: "default" | "warning" | "success" | "error";
@ -99,7 +102,8 @@ function handleDelete() {
const { dropdownItems } = useEntityDropdownItemExtensionPoint<Backup>(
"backup:list-item:operation:create",
[
backup,
computed(() => [
{
priority: 10,
component: markRaw(VDropdownItem),
@ -118,7 +122,7 @@ const { dropdownItems } = useEntityDropdownItemExtensionPoint<Backup>(
visible: true,
action: () => handleDelete(),
},
]
])
);
</script>

View File

@ -78,7 +78,8 @@ const handleResetSettingConfig = async () => {
const { dropdownItems } = useEntityDropdownItemExtensionPoint<Plugin>(
"plugin:list-item:operation:create",
[
plugin,
computed(() => [
{
priority: 10,
component: markRaw(VDropdownItem),
@ -150,7 +151,7 @@ const { dropdownItems } = useEntityDropdownItemExtensionPoint<Plugin>(
handleResetSettingConfig();
},
},
]
])
);
const { startFields, endFields } = useEntityFieldItemExtensionPoint<Plugin>(