简体   繁体   中英

Typedi + Jest + sequelize + Typescript

I'm struggling to figure out how to unit test my services:

Here is what I have:

userChecklistService.ts:

@Service()
export class UserChecklistsService {
            constructor(
        private userChecklistsRepository: UserChecklistsRepository,
        private userChecklistsSolvedRepository: UserChecklistsSolvedRepository,
    ) { }

    async findAll() {
        const response = await this.userChecklistsRepository.findAll({
            attributes: { ... }

userCheckListRepository

import * as S from '@sequelize'
import { Purchase, PurchaseAssociationMethods } from './Purchase.model'
import { UserChecklistsSolved, UserChecklistsSolvedAssociationMethods } from './UserChecklistsSolved.model'
/**
 * UserChecklists table fields
 */
export interface IUserChecklists {
    id: number
    purchaseId: number
    approved: boolean
    obs: string | null
    createdAt: Date
    updatedAt: Date
}

/**
 * UserChecklists creation fields
 */
export type ICreationUserChecklists = S.Optional<IUserChecklists, 'id'|'obs'>
/**
 * Indexes
 */
const PrimaryIndex = S.BTREEIndex({ name: 'PRIMARY', unique: true })
/**
 * UserChecklists table model
 */
@S.Table({
    tableName: 'user_checklists',
    timestamps: true,
    createdAt: 'created_at',
    updatedAt: 'updated_at',
    deletedAt: false,
})
export class UserChecklists extends S.Model<IUserChecklists, ICreationUserChecklists> implements IUserChecklists {
    /**
     * Fields
     */
    @S.PrimaryKey
    @S.AutoIncrement
    @S.NotNull
    @PrimaryIndex
    @S.Column({ type: S.DataType.INTEGER, allowNull: false })
    id: number

    @S.NotNull
    @S.ForeignKey(() => Purchase)
    @S.Column({ type: S.DataType.INTEGER, allowNull: false, unique: true })
    purchase_id: number

    @S.Column(S.DataType.STRING(255))
    obs: string | null

    @S.NotNull
    @S.Column({ type: S.DataType.TINYINT, allowNull: false })
    approved: number
    /**
     * Timestamps
     */
    @S.CreatedAt
    @S.Column({ type: S.DataType.DATE, field: 'created_at' })
    createdAt: Date

    @S.UpdatedAt
    @S.Column({ type: S.DataType.DATE, field: 'updated_at' })
    updatedAt: Date
    /**
     * Associations
     */
    @S.BelongsTo(() => Purchase, 'purchase_id')
    purchase: Purchase

    @S.HasOne(() => UserChecklistsSolved, 'user_checklists_id')
    userChecklistsSolved: UserChecklistsSolved
}
/**
 * Association types
 */
export type UserChecklistsAssociationMethods = S.AssociationMethods<'UserChecklists', UserChecklists>
/**
 * UserChecklists associations
 */
type UserChecklistsAssociations =
    & PurchaseAssociationMethods['belongsTo']
    & UserChecklistsSolvedAssociationMethods['hasOne']
/**
 * UserChecklists Repository
 */
@S.Repository(() => UserChecklists) <-------------
export class UserChecklistsRepository extends S.RepositoryClass<UserChecklists, UserChecklistsAssociations> { }

My userChecklistService.test.ts

import { UserChecklistsService } from "../userChecklists.service";
import { UserChecklistsRepository, UserChecklistsSolvedRepository } from '@models';
import { mocked } from "ts-jest/utils";

jest.mock('../../models/UserChecklists.model.ts', () => {
    const repo = { findAll: jest.fn() }
    return { UserChecklistsRepository: jest.fn(() => repo) }
})

jest.mock('../../models/UserChecklistsSolved.model.ts', () => {
    const repo = { findAll: jest.fn() }
    return { UserChecklistsSolvedRepository: jest.fn(() => repo) }
})

describe('test', () => {

    let service;

    beforeAll(() => {
        const mockedUserChecklistRepo = mocked(new UserChecklistsRepository(), true)
        const mockedUserChecklistSolvedRepo = mocked(new UserChecklistsSolvedRepository())
        service = new UserChecklistsService(mockedUserChecklistRepo, mockedUserChecklistSolvedRepo)
    })

    it('test', () => {

    })
})

The problem is, I can't figure out how to mock my repos. Doing the above, gives me this error:

src/services/__tests__/userChecklist.service.test.ts:22:45 - error TS2345: Argument of type 'MockedObjectDeep<UserChecklistsRepository>' is not assignable to parameter of type 'UserChecklistsRepository'.
      Type 'MockInstance<UserChecklists & { getPurchase: BelongsToGetAssociationMixin<Purchase>; } & { setPurchase: BelongsToSetAssociationMixin<Purchase, number>; } & { ...; } & { ...; } & { ...; } & { ...; }, []> & { ...; } & { ...; }' provides no match for the signature 'new (): UserChecklists & { getPurchase: BelongsToGetAssociationMixin<Purchase>; } & { setPurchase: BelongsToSetAssociationMixin<Purchase, number>; } & { ...; } & { ...; } & { ...; } & { ...; }'.

    22         service = new UserChecklistsService(mockedUserChecklistRepo, mockedUserChecklistSolvedRepo)

here you go, i think it should be something like this: (cant be sure without tinkering with it a bit)

jest.mock('../../models/UserChecklists.model.ts', () => {
    ...jest.requireActual('../../models/UserChecklists.model.ts'),
    UserChecklistsRepository: () => ({ 
       findAll: jest.fn() 
    })
})

last time I've used it was something like this:

jest.mock('react-router-dom', () => ({
  ...jest.requireActual('react-router-dom'),
  useHistory: () => ({
    push: jest.fn()
  })

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM