Просмотр исходного кода

support ObjectId in isPopulated and getIdForRef

Yuki Takei 1 год назад
Родитель
Сommit
b7aef01f65
2 измененных файлов с 119 добавлено и 7 удалено
  1. 110 0
      packages/core/src/interfaces/common.spec.ts
  2. 9 7
      packages/core/src/interfaces/common.ts

+ 110 - 0
packages/core/src/interfaces/common.spec.ts

@@ -0,0 +1,110 @@
+import type { HydratedDocument } from 'mongoose';
+import { Types } from 'mongoose';
+import { mock } from 'vitest-mock-extended';
+
+import { getIdForRef, isPopulated } from './common';
+import type { IPageHasId } from './page';
+import { type IPage } from './page';
+
+describe('isPopulated', () => {
+
+  it('should return true when the argument implements HasObjectId', () => {
+    // Arrange
+    const ref = mock<IPageHasId>();
+
+    // Act
+    const result = isPopulated(ref);
+
+    // Assert
+    expect(result).toBe(true);
+  });
+
+  it('should return true when the argument is a mongoose Document', () => {
+    // Arrange
+    const ref = mock<HydratedDocument<IPage>>();
+
+    // Act
+    const result = isPopulated(ref);
+
+    // Assert
+    expect(result).toBe(true);
+  });
+
+  it('should return false when the argument is string', () => {
+    // Arrange
+    const ref = new Types.ObjectId().toString();
+
+    // Act
+    const result = isPopulated(ref);
+
+    // Assert
+    expect(result).toBe(false);
+  });
+
+  it('should return false when the argument is ObjectId', () => {
+    // Arrange
+    const ref = new Types.ObjectId();
+
+    // Act
+    const result = isPopulated(ref);
+
+    // Assert
+    expect(result).toBe(false);
+  });
+
+});
+
+
+describe('getIdForRef', () => {
+
+  it('should return the id string when the argument is populated', () => {
+    // Arrange
+    const id = new Types.ObjectId();
+    const ref = mock<IPageHasId>({
+      _id: id.toString(),
+    });
+
+    // Act
+    const result = getIdForRef(ref);
+
+    // Assert
+    expect(result).toStrictEqual(id.toString());
+  });
+
+  it('should return the ObjectId when the argument is a mongoose Document', () => {
+    // Arrange
+    const id = new Types.ObjectId();
+    const ref = mock<HydratedDocument<IPage>>({
+      _id: id,
+    });
+
+    // Act
+    const result = getIdForRef(ref);
+
+    // Assert
+    expect(result).toStrictEqual(id);
+  });
+
+  it('should return the id string as is when the argument is ObjectId', () => {
+    // Arrange
+    const ref = new Types.ObjectId();
+
+    // Act
+    const result = getIdForRef(ref);
+
+    // Assert
+    expect(result).toStrictEqual(ref);
+  });
+
+  it('should return the ObjectId as is when the argument is string', () => {
+    // Arrange
+    const ref = new Types.ObjectId().toString();
+
+    // Act
+    const result = getIdForRef(ref);
+
+    // Assert
+    expect(result).toStrictEqual(ref);
+  });
+
+});

+ 9 - 7
packages/core/src/interfaces/common.ts

@@ -3,23 +3,25 @@
  */
  */
 
 
 
 
-import type { Types } from 'mongoose';
-
-import type { HasObjectId } from './has-object-id';
+import { Types } from 'mongoose';
 
 
 type ObjectId = Types.ObjectId;
 type ObjectId = Types.ObjectId;
 
 
 // Foreign key field
 // Foreign key field
-export type Ref<T> = string | ObjectId | T & HasObjectId;
+export type Ref<T> = string | ObjectId | T & { _id: string | ObjectId };
 
 
 export type Nullable<T> = T | null | undefined;
 export type Nullable<T> = T | null | undefined;
 
 
-export const isPopulated = <T>(ref?: T & HasObjectId | Ref<T>): ref is T & HasObjectId => {
-  return ref != null && typeof ref === 'object' && '_id' in ref;
+export const isPopulated = <T>(ref: Ref<T>): ref is T & { _id: string | ObjectId } => {
+  return ref != null && typeof ref !== 'string' && !(ref instanceof Types.ObjectId);
 };
 };
 
 
-export const getIdForRef = <T>(ref: T & HasObjectId | Ref<T>): string | ObjectId => {
+export const getIdForRef = <T>(ref: Ref<T>): string | ObjectId => {
   return isPopulated(ref)
   return isPopulated(ref)
     ? ref._id
     ? ref._id
     : ref;
     : ref;
 };
 };
+
+export const getIdStringForRef = <T>(ref: Ref<T>): string => {
+  return getIdForRef(ref).toString();
+};