angular - 如何使用 Jasmine 在 Angular 单元测试中模拟 window.screen.width

标签 angular unit-testing jasmine karma-jasmine chromium

我有一个 BreakpointService,它告诉我 - 根据屏幕宽度 - 我应该在哪种 SidebarMode(关闭 - 缩小 - 打开)中显示我的侧边栏。

这是服务的主要部分:

constructor(private breakpointObserver: BreakpointObserver) {
    this.closed$ = this.breakpointObserver.observe(['(min-width: 1024px)']).pipe(
      filter((state: BreakpointState) => !state.matches),
      mapTo(SidebarMode.Closed)
    );

    this.opened$ = this.breakpointObserver.observe(['(min-width: 1366px)']).pipe(
      filter((state: BreakpointState) => state.matches),
      mapTo(SidebarMode.Open)
    );

    const minifiedStart$: Observable<boolean> = this.breakpointObserver.observe(['(min-width: 1024px)']).pipe(map(state => state.matches));

    const minifiedEnd$: Observable<boolean> = this.breakpointObserver.observe(['(max-width: 1366px)']).pipe(map(state => state.matches));

    this.minified$ = minifiedStart$.pipe(
      flatMap(start => minifiedEnd$.pipe(map(end => start && end))),
      distinctUntilChanged(),
      filter(val => val === true),
      mapTo(SidebarMode.Minified)
    );

    this.observer$ = merge(this.closed$, this.minified$, this.opened$);
  }

通过这一行我可以订阅事件:

this.breakpointService.observe().subscribe();

现在,我想在单元测试中测试不同的模式,但我不知道

如何在测试中模拟 window.screen.width 属性

我尝试了很多方法,但没有任何效果。

这是我到目前为止的测试设置:

describe('observe()', () => {
    function resize(width: number): void {
      // did not work
      // window.resizeTo(width, window.innerHeight);
      // (<any>window).screen = { width: 700 };
      // spyOn(window, 'screen').and.returnValue(...)
    }

    let currentMode;
    beforeAll(() => {
      service.observe().subscribe(mode => (currentMode = mode));
    });

    it('should return Observable<SidebarMode>', async () => {
      resize(1000);

      expect(Object.values(SidebarMode).includes(SidebarMode[currentMode])).toBeTruthy();
    });

    xit('should return SidebarMode.Closed', async () => {
      resize(600);

      expect(currentMode).toBe(SidebarMode.Closed);
    });

    xit('should return SidebarMode.Minified', async () => {
      resize(1200);

      expect(currentMode).toBe(SidebarMode.Minified);
    });

    xit('should return SidebarMode.Open', async () => {
      resize(2000);

      expect(currentMode).toBe(SidebarMode.Open);
    });
  });

最佳答案

我猜测 BreakPointObserver 会监听调整大小事件,所以也许您可以尝试使用 jasmine 模拟 window.innerWidth/window.outerWidth 之类的操作?

spyOnProperty(window, 'innerWidth').and.returnValue(760);

然后您手动触发调整大小事件:

window.dispatchEvent(new Event('resize'));

它看起来像这样:

    it('should mock window inner width', () => {
        spyOnProperty(window, 'innerWidth').and.returnValue(760);
        window.dispatchEvent(new Event('resize'));
    });

关于angular - 如何使用 Jasmine 在 Angular 单元测试中模拟 window.screen.width,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53204907/

相关文章:

c++ - 如何在用Boost MSM编写的状态机中直接达到任何状态

unit-testing - AssertJ:记录所有通过(和失败)的断言

javascript - spyOn:期待一个 spy ,但得到了功能

typescript - 在/node_modules/angular2/src/testing/matchers.d.ts 中找不到命名空间 Jasmine

Angular 地理定位

angular - 如何派发空 Action ?

unit-testing - 使用 jasmine 进行 Angular2 异步单元测试

angular - 多指令选择器 - 查找模板中使用了哪个选择器

java - 模拟或构建 Jersey InboundJaxrsResponse

javascript - 'inject' Angular 和 Jasmine 错误