New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to scaffold a component in the test iframe? #1

Open
bahmutov opened this Issue May 24, 2018 · 14 comments

Comments

Projects
None yet
6 participants
@bahmutov
Copy link
Owner

bahmutov commented May 24, 2018

The mount function exposed by this package should mount the given component under test in the iframe's window. For example, here is the same code from https://github.com/bahmutov/cypress-angularjs-unit-test

export const mount = function (template, modules = []) {
  if (arguments.length === 1) {
    // test did not pass a template, just list of modules
    modules = template
    template = ''
  }

  // must inject into a "div" and not into "document" directly,
  // Angular.js goes up to "html" parent element
  // and stores its state there, affecting every test afterwards
  const html = `
    <head>
      <meta charset="UTF-8">
    </head>
    <body>
      <div id="app">
        ${template}
      </div>
    </body>
  `

  const document = cy.state('document')
  document.write(html)
  document.close()

  cy.window().then(w => {
    w.angular = angular
    cy.log('Angular.js', w.angular.version.full)
    const el = document.getElementById('app')
    w.angular.bootstrap(el, modules)
  })
}

In this repo, I could not find how to scaffold Angular component on demand. See cypress/integration/spec.ts currently. I am trying to put the component into the test iframe and start the app

  beforeEach(() => {
    const html = `
      <head>
        <meta charset="UTF-8">
      </head>
      <body>
        <app-root></app-root>
      </body>
    `
    const document = (cy as any).state('document')
    document.write(html)
    document.close()

    cy.get('app-root').then(el$ => {
      platformBrowserDynamic()
        .bootstrapModule(AppModule)
        .then(function (moduleRef) {
          moduleRef.instance.app.bootstrap(AppComponent, el$.get(0))
        })
    })
  })

  it('works', () => {})

But so far - no luck.

steps to reproduce

  • Clone this repo
  • npm install
  • npx cypress open starts Cypress GUI
  • click on spec.ts file and it will run the test

Attention @IgorMinar

@meDavid

This comment has been minimized.

Copy link

meDavid commented Jul 12, 2018

I would try using the TestBed to create the components, but even then it doesn't work. There are still a lot of services like the DefaultDomRenderer2 that use the global document object instead of the one available using the DOCUMENT token with the dependency injector.

@bahmutov

This comment has been minimized.

Copy link
Owner Author

bahmutov commented Jul 12, 2018

Yeah, I am even thinking we need something like this https://glebbahmutov.com/blog/rolling-for-test/ to bundle component over and over and bootstrap it in the test iframe :(

@meDavid

This comment has been minimized.

Copy link

meDavid commented Jul 12, 2018

angular/angular#20229 might be related

@meDavid

This comment has been minimized.

Copy link

meDavid commented Jul 20, 2018

@bahmutov I have the rendering working for elements that use inline templates and styles.

When using templateUrl and styleUrls instead of template and styles in the @component decorator there specified urls (for app.component.html and app.component.css) need te be available on the server. Now the request url http://localhost:61601/__cypress/iframes/integration/app.component.html doesn't correctly resolve to /src/app/app.component.html. Another solution is to inline the template and style resources using ngc.

@geocine

This comment has been minimized.

Copy link
Contributor

geocine commented Jul 21, 2018

@meDavid thanks for pointing that out, I did not notice. The PR #2 should be able to solve this issue

@meDavid

This comment has been minimized.

Copy link

meDavid commented Jul 23, 2018

@bahmutov Is there a way to make cypress look for the .spec.ts files in the /src/* directories instead of the cypress/integration directory?

@kayvanbree

This comment has been minimized.

Copy link

kayvanbree commented Nov 6, 2018

Is there any chance they will work on angular/angular#20229, is there another way or should I just use Cypress for e2e for now and try to live with a sometimes-working Karma?

@pvdyck

This comment has been minimized.

Copy link

pvdyck commented Nov 6, 2018

I am searching for a way to get code coverage of my cypress tests for an angular7 project and this solution should be working, I mean when it will be working.

Using the angular CLI, if I can mount the application within karma and launch my cypress tests in a spec.ts file, I should get a code coverage report of my e2e tests.

Anyone tried this approach ?

Thanks a lot

@tobiaseisenschenk

This comment has been minimized.

Copy link

tobiaseisenschenk commented Nov 19, 2018

Since you get the app to start, the problem is to add the respective component dynamically? I assume the dom stays empty because angular does not load the component. We should be able to use the Dynamic Component Loader to achieve that.

@kayvanbree

This comment has been minimized.

Copy link

kayvanbree commented Dec 6, 2018

@tobiaseisenschenk shouldn't you already have bootstrapped Angular before you can use that? (I hope not, Karma is bugging me again)

@kayvanbree

This comment has been minimized.

Copy link

kayvanbree commented Dec 9, 2018

I'm getting a lot of error messages like these:

E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts
�[tsl] ���ERROR���� in ����E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts(138,47)��
��      TS1005: ';' expected.��

E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts
�[tsl] ���ERROR���� in ����E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts(138,90)��
��      TS1005: '(' expected.��

E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts
�[tsl] ���ERROR���� in ����E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts(138,104)��
��      TS1005: ']' expected.��

E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts
�[tsl] ���ERROR���� in ����E:\Projects\libraries\cypress-angular-unit-test\node_modules\@types\jasmine\index.d.ts(138,112)��
��      TS1005: ',' expected.��

Anybody know what I'm doing wrong?

@geocine

This comment has been minimized.

Copy link
Contributor

geocine commented Dec 9, 2018

Fyi guys , this issue was solved by pr #2

@kayvanbree

This comment has been minimized.

Copy link

kayvanbree commented Dec 12, 2018

@geocine so it should work? If so, the readme should be updated.

Also, the other Cypress unit test repositories have published npm modules to help you set up your tests. It should be made for Angular too.

@geocine

This comment has been minimized.

Copy link
Contributor

geocine commented Dec 15, 2018

@kayvanbree yes it should, right haven't had the chance to do pull request for the readme.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment