diff --git a/ui/src/domain/workflowRun.ts b/ui/src/domain/workflowRun.ts
index 36920de2..95b44546 100644
--- a/ui/src/domain/workflowRun.ts
+++ b/ui/src/domain/workflowRun.ts
@@ -1,3 +1,5 @@
+import type { WorkflowModel } from "./workflow";
+
 export interface WorkflowRunModel extends BaseModel {
   workflowId: string;
   status: string;
@@ -6,6 +8,9 @@ export interface WorkflowRunModel extends BaseModel {
   endedAt: ISO8601String;
   logs: WorkflowRunLog[];
   error: string;
+  expand?: {
+    workflowId?: WorkflowModel;
+  };
 }
 
 export type WorkflowRunLog = {
diff --git a/ui/src/i18n/locales/en/nls.dashboard.json b/ui/src/i18n/locales/en/nls.dashboard.json
index 865e11ec..e179f20f 100644
--- a/ui/src/i18n/locales/en/nls.dashboard.json
+++ b/ui/src/i18n/locales/en/nls.dashboard.json
@@ -8,5 +8,11 @@
   "dashboard.statistics.enabled_workflows": "Enabled workflows",
   "dashboard.statistics.unit": "",
 
-  "dashboard.latest_workflow_run": "Latest workflow run"
+  "dashboard.latest_workflow_run": "Latest workflow run",
+
+  "dashboard.quick_actions": "Quick actions",
+  "dashboard.quick_actions.create_workflow": "Create workflow",
+  "dashboard.quick_actions.change_login_password": "Change login password",
+  "dashboard.quick_actions.notification_settings": "Notification settings",
+  "dashboard.quick_actions.certificate_authority_configuration": "Certificate authority configuration"
 }
diff --git a/ui/src/i18n/locales/zh/nls.dashboard.json b/ui/src/i18n/locales/zh/nls.dashboard.json
index 72086011..471ebfce 100644
--- a/ui/src/i18n/locales/zh/nls.dashboard.json
+++ b/ui/src/i18n/locales/zh/nls.dashboard.json
@@ -8,5 +8,12 @@
   "dashboard.statistics.enabled_workflows": "已启用工作流",
   "dashboard.statistics.unit": "个",
 
-  "dashboard.latest_workflow_run": "最近执行的工作流"
+  "dashboard.latest_workflow_run": "最近执行的工作流",
+
+  "dashboard.quick_actions": "快捷操作",
+  "dashboard.quick_actions.create_workflow": "新建工作流",
+  "dashboard.quick_actions.change_login_password": "修改登录密码",
+  "dashboard.quick_actions.notification_settings": "消息推送设置",
+  "dashboard.quick_actions.certificate_authority_configuration": "证书颁发机构配置"
 }
+
diff --git a/ui/src/pages/dashboard/Dashboard.tsx b/ui/src/pages/dashboard/Dashboard.tsx
index d5a12e19..82e0acea 100644
--- a/ui/src/pages/dashboard/Dashboard.tsx
+++ b/ui/src/pages/dashboard/Dashboard.tsx
@@ -1,9 +1,22 @@
 import { useState } from "react";
 import { useTranslation } from "react-i18next";
 import { useNavigate } from "react-router-dom";
+import {
+  ApiOutlined,
+  CheckCircleOutlined,
+  ClockCircleOutlined,
+  CloseCircleOutlined,
+  LockOutlined,
+  PlusOutlined,
+  SelectOutlined,
+  SendOutlined,
+  SyncOutlined,
+} from "@ant-design/icons";
 import { PageHeader } from "@ant-design/pro-components";
 import { useRequest } from "ahooks";
-import { Card, Col, Divider, Row, Space, Statistic, Typography, notification, theme } from "antd";
+import type { TableProps } from "antd";
+import { Button, Card, Col, Divider, Empty, Flex, Grid, Row, Space, Statistic, Table, Tag, Typography, notification, theme } from "antd";
+import dayjs from "dayjs";
 import {
   CalendarClock as CalendarClockIcon,
   CalendarX2 as CalendarX2Icon,
@@ -14,18 +27,158 @@ import {
 import { ClientResponseError } from "pocketbase";
 
 import { get as getStatistics } from "@/api/statistics";
+import WorkflowRunDetailDrawer from "@/components/workflow/WorkflowRunDetailDrawer";
 import { type Statistics } from "@/domain/statistics";
+import { WORKFLOW_TRIGGERS } from "@/domain/workflow";
+import { WORKFLOW_RUN_STATUSES, type WorkflowRunModel } from "@/domain/workflowRun";
+import { list as listWorkflowRuns } from "@/repository/workflowRun";
 import { getErrMsg } from "@/utils/error";
 
+const { useBreakpoint } = Grid;
+
 const Dashboard = () => {
   const navigate = useNavigate();
 
+  const screens = useBreakpoint();
+
   const { t } = useTranslation();
 
   const { token: themeToken } = theme.useToken();
 
   const [notificationApi, NotificationContextHolder] = notification.useNotification();
 
+  const tableColumns: TableProps<WorkflowRunModel>["columns"] = [
+    {
+      key: "$index",
+      align: "center",
+      fixed: "left",
+      width: 50,
+      render: (_, __, index) => (page - 1) * pageSize + index + 1,
+    },
+    {
+      key: "name",
+      title: t("workflow.props.name"),
+      ellipsis: true,
+      render: (_, record) => (
+        <Space className="max-w-full" direction="vertical" size={4}>
+          <Typography.Text ellipsis>{record.expand?.workflowId?.name}</Typography.Text>
+          <Typography.Text type="secondary" ellipsis>
+            {record.expand?.workflowId?.description}
+          </Typography.Text>
+        </Space>
+      ),
+    },
+    {
+      key: "status",
+      title: t("workflow_run.props.status"),
+      ellipsis: true,
+      render: (_, record) => {
+        if (record.status === WORKFLOW_RUN_STATUSES.PENDING) {
+          return <Tag icon={<ClockCircleOutlined />}>{t("workflow_run.props.status.pending")}</Tag>;
+        } else if (record.status === WORKFLOW_RUN_STATUSES.RUNNING) {
+          return (
+            <Tag icon={<SyncOutlined spin />} color="processing">
+              {t("workflow_run.props.status.running")}
+            </Tag>
+          );
+        } else if (record.status === WORKFLOW_RUN_STATUSES.SUCCEEDED) {
+          return (
+            <Tag icon={<CheckCircleOutlined />} color="success">
+              {t("workflow_run.props.status.succeeded")}
+            </Tag>
+          );
+        } else if (record.status === WORKFLOW_RUN_STATUSES.FAILED) {
+          return (
+            <Tag icon={<CloseCircleOutlined />} color="error">
+              {t("workflow_run.props.status.failed")}
+            </Tag>
+          );
+        }
+
+        return <></>;
+      },
+    },
+    {
+      key: "trigger",
+      title: t("workflow_run.props.trigger"),
+      ellipsis: true,
+      render: (_, record) => {
+        if (record.trigger === WORKFLOW_TRIGGERS.AUTO) {
+          return t("workflow_run.props.trigger.auto");
+        } else if (record.trigger === WORKFLOW_TRIGGERS.MANUAL) {
+          return t("workflow_run.props.trigger.manual");
+        }
+
+        return <></>;
+      },
+    },
+    {
+      key: "startedAt",
+      title: t("workflow_run.props.started_at"),
+      ellipsis: true,
+      render: (_, record) => {
+        if (record.startedAt) {
+          return dayjs(record.startedAt).format("YYYY-MM-DD HH:mm:ss");
+        }
+
+        return <></>;
+      },
+    },
+    {
+      key: "endedAt",
+      title: t("workflow_run.props.ended_at"),
+      ellipsis: true,
+      render: (_, record) => {
+        if (record.endedAt) {
+          return dayjs(record.endedAt).format("YYYY-MM-DD HH:mm:ss");
+        }
+
+        return <></>;
+      },
+    },
+    {
+      key: "$action",
+      align: "end",
+      fixed: "right",
+      width: 120,
+      render: (_, record) => (
+        <Button.Group>
+          <WorkflowRunDetailDrawer data={record} trigger={<Button color="primary" icon={<SelectOutlined />} variant="text" />} />
+        </Button.Group>
+      ),
+    },
+  ];
+  const [tableData, setTableData] = useState<WorkflowRunModel[]>([]);
+  const [_tableTotal, setTableTotal] = useState<number>(0);
+
+  const [page, _setPage] = useState<number>(1);
+  const [pageSize, _setPageSize] = useState<number>(3);
+
+  const { loading: loadingWorkflowRun } = useRequest(
+    () => {
+      return listWorkflowRuns({
+        page: page,
+        perPage: pageSize,
+        expand: true,
+      });
+    },
+    {
+      refreshDeps: [page, pageSize],
+      onSuccess: (data) => {
+        setTableData(data.items);
+        setTableTotal(data.totalItems > 3 ? 3 : data.totalItems);
+      },
+      onError: (err) => {
+        if (err instanceof ClientResponseError && err.isAbort) {
+          return;
+        }
+
+        console.error(err);
+        notificationApi.error({ message: t("common.text.request_error"), description: getErrMsg(err) });
+      },
+    }
+  );
+
   const statisticsGridSpans = {
     xs: { flex: "50%" },
     md: { flex: "50%" },
@@ -115,7 +268,39 @@ const Dashboard = () => {
 
       <Divider />
 
-      <div>TODO: {t("dashboard.latest_workflow_run")}</div>
+      <Flex vertical={!screens.md} gap={16}>
+        <Card className="sm:h-full sm:w-[500px] sm:pb-32">
+          <div className="text-lg font-semibold">{t("dashboard.quick_actions")}</div>
+          <div className="mt-9">
+            <Button className="w-full" type="primary" size="large" icon={<PlusOutlined />} onClick={() => navigate("/workflows/new")}>
+              {t("dashboard.quick_actions.create_workflow")}
+            </Button>
+            <Button className="mt-5 w-full" size="large" icon={<LockOutlined />} onClick={() => navigate("/settings/password")}>
+              {t("dashboard.quick_actions.change_login_password")}
+            </Button>
+            <Button className="mt-5 w-full" size="large" icon={<SendOutlined />} onClick={() => navigate("/settings/notification")}>
+              {t("dashboard.quick_actions.notification_settings")}
+            </Button>
+            <Button className="mt-5 w-full" size="large" icon={<ApiOutlined />} onClick={() => navigate("/settings/ssl-provider")}>
+              {t("dashboard.quick_actions.certificate_authority_configuration")}
+            </Button>
+          </div>
+        </Card>
+        <Card className="size-full">
+          <div className="text-lg font-semibold">{t("dashboard.latest_workflow_run")} </div>
+          <Table<WorkflowRunModel>
+            className="mt-5"
+            columns={tableColumns}
+            dataSource={tableData}
+            loading={loadingWorkflowRun}
+            locale={{
+              emptyText: <Empty image={Empty.PRESENTED_IMAGE_SIMPLE} />,
+            }}
+            rowKey={(record: WorkflowRunModel) => record.id}
+            scroll={{ x: "max(100%, 960px)" }}
+          />
+        </Card>
+      </Flex>
     </div>
   );
 };
diff --git a/ui/src/repository/workflowRun.ts b/ui/src/repository/workflowRun.ts
index 7dac78a6..fd99de98 100644
--- a/ui/src/repository/workflowRun.ts
+++ b/ui/src/repository/workflowRun.ts
@@ -5,20 +5,29 @@ import { getPocketBase } from "./pocketbase";
 const COLLECTION_NAME = "workflow_run";
 
 export type ListWorkflowRunsRequest = {
-  workflowId: string;
+  workflowId?: string;
   page?: number;
   perPage?: number;
+  expand?: boolean;
 };
 
 export const list = async (request: ListWorkflowRunsRequest) => {
   const page = request.page || 1;
   const perPage = request.perPage || 10;
+  console.log("request.workflowId", request.workflowId);
+  let filter = "";
+  const params: Record<string, string> = {};
+  if (request.workflowId) {
+    filter = `workflowId={:workflowId}`;
+    params.workflowId = request.workflowId;
+  }
 
   return await getPocketBase()
     .collection(COLLECTION_NAME)
     .getList<WorkflowRunModel>(page, perPage, {
-      filter: getPocketBase().filter("workflowId={:workflowId}", { workflowId: request.workflowId }),
+      filter: getPocketBase().filter(filter, params),
       sort: "-created",
       requestKey: null,
+      expand: request.expand ? "workflowId" : undefined,
     });
 };