From 54a3c25ebde5d1bde113adc2c595a6a88defd002 Mon Sep 17 00:00:00 2001 From: Steven Date: Sat, 30 Mar 2024 08:26:28 +0800 Subject: [PATCH] chore: update memo resource name definition --- proto/api/v2/resource_service.proto | 6 ++- proto/gen/api/v2/README.md | 4 +- proto/gen/api/v2/resource_service.pb.go | 49 +++++++++--------- server/route/api/v2/apidocs.swagger.yaml | 18 +++---- server/route/api/v2/resource_service.go | 43 ++++++++++------ web/src/components/MemoEditor/index.tsx | 6 +-- web/src/helpers/utils.ts | 63 ------------------------ web/src/pages/Resources.tsx | 14 +++--- 8 files changed, 76 insertions(+), 127 deletions(-) diff --git a/proto/api/v2/resource_service.proto b/proto/api/v2/resource_service.proto index cfac8713..4a12d8bb 100644 --- a/proto/api/v2/resource_service.proto +++ b/proto/api/v2/resource_service.proto @@ -61,7 +61,8 @@ message Resource { int64 size = 7; - optional int32 memo_id = 8; + // Format: memos/{id} + optional string memo = 8; } message CreateResourceRequest { @@ -71,7 +72,8 @@ message CreateResourceRequest { string type = 3; - optional int32 memo_id = 4; + // Format: memos/{id} + optional string memo = 4; } message CreateResourceResponse { diff --git a/proto/gen/api/v2/README.md b/proto/gen/api/v2/README.md index 0a11250b..ef705e4e 100644 --- a/proto/gen/api/v2/README.md +++ b/proto/gen/api/v2/README.md @@ -1332,7 +1332,7 @@ Used internally for obfuscating the page token. | filename | [string](#string) | | | | external_link | [string](#string) | | | | type | [string](#string) | | | -| memo_id | [int32](#int32) | optional | | +| memo | [string](#string) | optional | Format: memos/{id} | @@ -1449,7 +1449,7 @@ Used internally for obfuscating the page token. | external_link | [string](#string) | | | | type | [string](#string) | | | | size | [int64](#int64) | | | -| memo_id | [int32](#int32) | optional | | +| memo | [string](#string) | optional | Format: memos/{id} | diff --git a/proto/gen/api/v2/resource_service.pb.go b/proto/gen/api/v2/resource_service.pb.go index 211986f7..c58a03b3 100644 --- a/proto/gen/api/v2/resource_service.pb.go +++ b/proto/gen/api/v2/resource_service.pb.go @@ -39,7 +39,8 @@ type Resource struct { ExternalLink string `protobuf:"bytes,5,opt,name=external_link,json=externalLink,proto3" json:"external_link,omitempty"` Type string `protobuf:"bytes,6,opt,name=type,proto3" json:"type,omitempty"` Size int64 `protobuf:"varint,7,opt,name=size,proto3" json:"size,omitempty"` - MemoId *int32 `protobuf:"varint,8,opt,name=memo_id,json=memoId,proto3,oneof" json:"memo_id,omitempty"` + // Format: memos/{id} + Memo *string `protobuf:"bytes,8,opt,name=memo,proto3,oneof" json:"memo,omitempty"` } func (x *Resource) Reset() { @@ -123,11 +124,11 @@ func (x *Resource) GetSize() int64 { return 0 } -func (x *Resource) GetMemoId() int32 { - if x != nil && x.MemoId != nil { - return *x.MemoId +func (x *Resource) GetMemo() string { + if x != nil && x.Memo != nil { + return *x.Memo } - return 0 + return "" } type CreateResourceRequest struct { @@ -138,7 +139,8 @@ type CreateResourceRequest struct { Filename string `protobuf:"bytes,1,opt,name=filename,proto3" json:"filename,omitempty"` ExternalLink string `protobuf:"bytes,2,opt,name=external_link,json=externalLink,proto3" json:"external_link,omitempty"` Type string `protobuf:"bytes,3,opt,name=type,proto3" json:"type,omitempty"` - MemoId *int32 `protobuf:"varint,4,opt,name=memo_id,json=memoId,proto3,oneof" json:"memo_id,omitempty"` + // Format: memos/{id} + Memo *string `protobuf:"bytes,4,opt,name=memo,proto3,oneof" json:"memo,omitempty"` } func (x *CreateResourceRequest) Reset() { @@ -194,11 +196,11 @@ func (x *CreateResourceRequest) GetType() string { return "" } -func (x *CreateResourceRequest) GetMemoId() int32 { - if x != nil && x.MemoId != nil { - return *x.MemoId +func (x *CreateResourceRequest) GetMemo() string { + if x != nil && x.Memo != nil { + return *x.Memo } - return 0 + return "" } type CreateResourceResponse struct { @@ -721,7 +723,7 @@ var file_api_v2_resource_service_proto_rawDesc = []byte{ 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x5f, 0x6d, 0x61, 0x73, 0x6b, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x1a, 0x1f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x74, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, - 0x70, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0x80, 0x02, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x6f, + 0x70, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x22, 0xf8, 0x01, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x10, 0x0a, 0x03, 0x75, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, 0x69, 0x64, 0x12, 0x3b, 0x0a, 0x0b, 0x63, 0x72, @@ -735,19 +737,18 @@ var file_api_v2_resource_service_proto_rawDesc = []byte{ 0x72, 0x6e, 0x61, 0x6c, 0x4c, 0x69, 0x6e, 0x6b, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x79, 0x70, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x73, 0x69, 0x7a, 0x65, 0x18, 0x07, 0x20, 0x01, 0x28, 0x03, 0x52, 0x04, 0x73, 0x69, 0x7a, 0x65, - 0x12, 0x1c, 0x0a, 0x07, 0x6d, 0x65, 0x6d, 0x6f, 0x5f, 0x69, 0x64, 0x18, 0x08, 0x20, 0x01, 0x28, - 0x05, 0x48, 0x00, 0x52, 0x06, 0x6d, 0x65, 0x6d, 0x6f, 0x49, 0x64, 0x88, 0x01, 0x01, 0x42, 0x0a, - 0x0a, 0x08, 0x5f, 0x6d, 0x65, 0x6d, 0x6f, 0x5f, 0x69, 0x64, 0x22, 0x96, 0x01, 0x0a, 0x15, 0x43, - 0x72, 0x65, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x52, 0x65, 0x71, - 0x75, 0x65, 0x73, 0x74, 0x12, 0x1a, 0x0a, 0x08, 0x66, 0x69, 0x6c, 0x65, 0x6e, 0x61, 0x6d, 0x65, - 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x66, 0x69, 0x6c, 0x65, 0x6e, 0x61, 0x6d, 0x65, - 0x12, 0x23, 0x0a, 0x0d, 0x65, 0x78, 0x74, 0x65, 0x72, 0x6e, 0x61, 0x6c, 0x5f, 0x6c, 0x69, 0x6e, - 0x6b, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x65, 0x78, 0x74, 0x65, 0x72, 0x6e, 0x61, - 0x6c, 0x4c, 0x69, 0x6e, 0x6b, 0x12, 0x12, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x03, 0x20, - 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x79, 0x70, 0x65, 0x12, 0x1c, 0x0a, 0x07, 0x6d, 0x65, 0x6d, - 0x6f, 0x5f, 0x69, 0x64, 0x18, 0x04, 0x20, 0x01, 0x28, 0x05, 0x48, 0x00, 0x52, 0x06, 0x6d, 0x65, - 0x6d, 0x6f, 0x49, 0x64, 0x88, 0x01, 0x01, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x6d, 0x65, 0x6d, 0x6f, - 0x5f, 0x69, 0x64, 0x22, 0x4c, 0x0a, 0x16, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, + 0x12, 0x17, 0x0a, 0x04, 0x6d, 0x65, 0x6d, 0x6f, 0x18, 0x08, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, + 0x52, 0x04, 0x6d, 0x65, 0x6d, 0x6f, 0x88, 0x01, 0x01, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x6d, 0x65, + 0x6d, 0x6f, 0x22, 0x8e, 0x01, 0x0a, 0x15, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, + 0x6f, 0x75, 0x72, 0x63, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x1a, 0x0a, 0x08, + 0x66, 0x69, 0x6c, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, + 0x66, 0x69, 0x6c, 0x65, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x23, 0x0a, 0x0d, 0x65, 0x78, 0x74, 0x65, + 0x72, 0x6e, 0x61, 0x6c, 0x5f, 0x6c, 0x69, 0x6e, 0x6b, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, + 0x0c, 0x65, 0x78, 0x74, 0x65, 0x72, 0x6e, 0x61, 0x6c, 0x4c, 0x69, 0x6e, 0x6b, 0x12, 0x12, 0x0a, + 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x79, 0x70, + 0x65, 0x12, 0x17, 0x0a, 0x04, 0x6d, 0x65, 0x6d, 0x6f, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x48, + 0x00, 0x52, 0x04, 0x6d, 0x65, 0x6d, 0x6f, 0x88, 0x01, 0x01, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x6d, + 0x65, 0x6d, 0x6f, 0x22, 0x4c, 0x0a, 0x16, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x32, 0x0a, 0x08, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x16, 0x2e, 0x6d, 0x65, 0x6d, 0x6f, 0x73, 0x2e, 0x61, 0x70, 0x69, 0x2e, 0x76, 0x32, 0x2e, 0x52, diff --git a/server/route/api/v2/apidocs.swagger.yaml b/server/route/api/v2/apidocs.swagger.yaml index 5363cd00..d6652e27 100644 --- a/server/route/api/v2/apidocs.swagger.yaml +++ b/server/route/api/v2/apidocs.swagger.yaml @@ -346,11 +346,11 @@ paths: in: query required: false type: string - - name: memoId + - name: memo + description: 'Format: memos/{id}' in: query required: false - type: integer - format: int32 + type: string tags: - ResourceService /api/v2/resources:search: @@ -1476,9 +1476,9 @@ paths: size: type: string format: int64 - memoId: - type: integer - format: int32 + memo: + type: string + title: 'Format: memos/{id}' tags: - ResourceService /api/v2/{setting.name}: @@ -2183,9 +2183,9 @@ definitions: size: type: string format: int64 - memoId: - type: integer - format: int32 + memo: + type: string + title: 'Format: memos/{id}' v2SearchMemosResponse: type: object properties: diff --git a/server/route/api/v2/resource_service.go b/server/route/api/v2/resource_service.go index 1187f2f3..705f78c2 100644 --- a/server/route/api/v2/resource_service.go +++ b/server/route/api/v2/resource_service.go @@ -41,8 +41,12 @@ func (s *APIV2Service) CreateResource(ctx context.Context, request *apiv2pb.Crea ExternalLink: request.ExternalLink, Type: request.Type, } - if request.MemoId != nil { - create.MemoID = request.MemoId + if request.Memo != nil { + memoID, err := ExtractMemoIDFromName(*request.Memo) + if err != nil { + return nil, status.Errorf(codes.InvalidArgument, "invalid memo id: %v", err) + } + create.MemoID = &memoID } resource, err := s.Store.CreateResource(ctx, create) if err != nil { @@ -139,8 +143,15 @@ func (s *APIV2Service) UpdateResource(ctx context.Context, request *apiv2pb.Upda for _, field := range request.UpdateMask.Paths { if field == "filename" { update.Filename = &request.Resource.Filename - } else if field == "memo_id" { - update.MemoID = request.Resource.MemoId + } else if field == "memo" { + if request.Resource.Memo == nil { + return nil, status.Errorf(codes.InvalidArgument, "memo is required") + } + memoID, err := ExtractMemoIDFromName(*request.Resource.Memo) + if err != nil { + return nil, status.Errorf(codes.InvalidArgument, "invalid memo id: %v", err) + } + update.MemoID = &memoID } } @@ -182,17 +193,7 @@ func (s *APIV2Service) DeleteResource(ctx context.Context, request *apiv2pb.Dele } func (s *APIV2Service) convertResourceFromStore(ctx context.Context, resource *store.Resource) *apiv2pb.Resource { - var memoID *int32 - if resource.MemoID != nil { - memo, _ := s.Store.GetMemo(ctx, &store.FindMemo{ - ID: resource.MemoID, - }) - if memo != nil { - memoID = &memo.ID - } - } - - return &apiv2pb.Resource{ + resourceMessage := &apiv2pb.Resource{ Name: fmt.Sprintf("%s%d", ResourceNamePrefix, resource.ID), Uid: resource.UID, CreateTime: timestamppb.New(time.Unix(resource.CreatedTs, 0)), @@ -200,8 +201,18 @@ func (s *APIV2Service) convertResourceFromStore(ctx context.Context, resource *s ExternalLink: resource.ExternalLink, Type: resource.Type, Size: resource.Size, - MemoId: memoID, } + if resource.MemoID != nil { + memo, _ := s.Store.GetMemo(ctx, &store.FindMemo{ + ID: resource.MemoID, + }) + if memo != nil { + memoName := fmt.Sprintf("%s%d", MemoNamePrefix, memo.ID) + resourceMessage.Memo = &memoName + } + } + + return resourceMessage } // SearchResourcesFilterCELAttributes are the CEL attributes for SearchResourcesFilter. diff --git a/web/src/components/MemoEditor/index.tsx b/web/src/components/MemoEditor/index.tsx index 31fa5d37..51cc283c 100644 --- a/web/src/components/MemoEditor/index.tsx +++ b/web/src/components/MemoEditor/index.tsx @@ -8,7 +8,7 @@ import { TAB_SPACE_WIDTH } from "@/helpers/consts"; import { isValidUrl } from "@/helpers/utils"; import useCurrentUser from "@/hooks/useCurrentUser"; import { useGlobalStore, useResourceStore, useTagStore } from "@/store/module"; -import { extractMemoIdFromName, useMemoStore, useUserStore } from "@/store/v1"; +import { useMemoStore, useUserStore } from "@/store/v1"; import { MemoRelation, MemoRelation_Type } from "@/types/proto/api/v2/memo_relation_service"; import { Memo, Visibility } from "@/types/proto/api/v2/memo_service"; import { Resource } from "@/types/proto/api/v2/resource_service"; @@ -233,9 +233,9 @@ const MemoEditor = (props: Props) => { await resourceStore.updateResource({ resource: Resource.fromPartial({ name: resource.name, - memoId: extractMemoIdFromName(memoName), + memo: memoName, }), - updateMask: ["memo_id"], + updateMask: ["memo"], }); } } diff --git a/web/src/helpers/utils.ts b/web/src/helpers/utils.ts index 56795382..e6d517b4 100644 --- a/web/src/helpers/utils.ts +++ b/web/src/helpers/utils.ts @@ -1,57 +1,3 @@ -export const isNullorUndefined = (value: any) => { - return value === null || value === undefined; -}; - -export const getElementBounding = (element: HTMLElement, relativeEl?: HTMLElement) => { - const scrollTop = window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop; - const scrollLeft = window.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft; - - relativeEl = relativeEl || document.body; - - const elementRect = element.getBoundingClientRect(); - const relativeElRect = relativeEl.getBoundingClientRect(); - const relativeElPosition = window.getComputedStyle(relativeEl).getPropertyValue("position"); - - const bounding = { - width: elementRect.width, - height: elementRect.height, - }; - - if ((relativeEl.tagName !== "BODY" && relativeElPosition === "relative") || relativeElPosition === "sticky") { - return Object.assign(bounding, { - top: elementRect.top - relativeElRect.top, - left: elementRect.left - relativeElRect.left, - }); - } - - const isElementFixed = (element: HTMLElement): boolean => { - const parentNode = element.parentNode; - - if (!parentNode || parentNode.nodeName === "HTML") { - return false; - } - - const position = window.getComputedStyle(element).getPropertyValue("position"); - if (position === "fixed" || position === "static") { - return true; - } - - return isElementFixed(parentNode as HTMLElement); - }; - - if (isElementFixed(element)) { - return Object.assign(bounding, { - top: elementRect.top, - left: elementRect.left, - }); - } - - return Object.assign(bounding, { - top: elementRect.top + scrollTop, - left: elementRect.left + scrollLeft, - }); -}; - export function absolutifyLink(rel: string): string { const anchor = document.createElement("a"); anchor.setAttribute("href", rel); @@ -75,15 +21,6 @@ export function convertFileToBase64(file: File): Promise { }); } -export const formatBytes = (bytes: number) => { - if (bytes <= 0) return "0 Bytes"; - const k = 1024, - dm = 2, - sizes = ["Bytes", "KiB", "MiB", "GiB", "TiB", "PiB", "EiB", "ZiB", "YiB"], - i = Math.floor(Math.log(bytes) / Math.log(k)); - return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + " " + sizes[i]; -}; - export const isValidUrl = (url: string): boolean => { try { new URL(url); diff --git a/web/src/pages/Resources.tsx b/web/src/pages/Resources.tsx index 78b83a8e..f1bb77b9 100644 --- a/web/src/pages/Resources.tsx +++ b/web/src/pages/Resources.tsx @@ -10,7 +10,7 @@ import ResourceIcon from "@/components/ResourceIcon"; import { resourceServiceClient } from "@/grpcweb"; import useLoading from "@/hooks/useLoading"; import i18n from "@/i18n"; -import { MemoNamePrefix, extractMemoIdFromName, useMemoStore } from "@/store/v1"; +import { extractMemoIdFromName, useMemoStore } from "@/store/v1"; import { Resource } from "@/types/proto/api/v2/resource_service"; import { useTranslate } from "@/utils/i18n"; @@ -49,16 +49,14 @@ const Resources = () => { const memoStore = useMemoStore(); const [resources, setResources] = useState([]); const filteredResources = resources.filter((resource) => includes(resource.filename, state.searchQuery)); - const groupedResources = groupResourcesByDate(filteredResources.filter((resource) => resource.memoId)); - const unusedResources = filteredResources.filter((resource) => !resource.memoId); + const groupedResources = groupResourcesByDate(filteredResources.filter((resource) => resource.memo)); + const unusedResources = filteredResources.filter((resource) => !resource.memo); useEffect(() => { resourceServiceClient.listResources({}).then(({ resources }) => { setResources(resources); loadingState.setFinish(); - Promise.all( - resources.map((resource: any) => (resource.memoId ? memoStore.getOrFetchMemoByName(`${MemoNamePrefix}${resource.memoId}`) : null)), - ); + Promise.all(resources.map((resource) => (resource.memo ? memoStore.getOrFetchMemoByName(resource.memo) : null))); }); }, []); @@ -72,7 +70,7 @@ const Resources = () => { for (const resource of unusedResources) { await resourceServiceClient.deleteResource({ name: resource.name }); } - setResources(resources.filter((resource) => resource.memoId)); + setResources(resources.filter((resource) => resource.memo)); }, }); }; @@ -121,7 +119,7 @@ const Resources = () => {
{resources.map((resource) => { - const relatedMemo = resource.memoId ? memoStore.getMemoByName(`${MemoNamePrefix}${resource.memoId}`) : null; + const relatedMemo = resource.memo ? memoStore.getMemoByName(resource.memo) : null; return (