diff --git a/.changeset/sour-eels-develop.md b/.changeset/sour-eels-develop.md new file mode 100644 index 0000000000..f16b80316b --- /dev/null +++ b/.changeset/sour-eels-develop.md @@ -0,0 +1,5 @@ +--- +'@siemens/ix': patch +--- + +fix(core/select): rollback and fix object iteration diff --git a/.github/workflows/pr.yml b/.github/workflows/pr.yml index 71e4f81072..ee3bd91946 100644 --- a/.github/workflows/pr.yml +++ b/.github/workflows/pr.yml @@ -46,6 +46,8 @@ jobs: - packages/core/** - packages/angular/** - packages/react/** + - packages/angular-test-app/** + - packages/react-test-app/** build: needs: changes diff --git a/packages/angular-test-app/karma.conf.js b/packages/angular-test-app/karma.conf.js index d0854135d7..54a02df30a 100644 --- a/packages/angular-test-app/karma.conf.js +++ b/packages/angular-test-app/karma.conf.js @@ -46,7 +46,13 @@ module.exports = function (config) { colors: true, logLevel: config.LOG_INFO, autoWatch: true, - browsers: ['Chrome'], + browsers: ['ChromeHeadlessCI'], + customLaunchers: { + ChromeHeadlessCI: { + base: 'ChromeHeadless', + flags: ['--no-sandbox'] + } + }, singleRun: false, restartOnFileChange: true }); diff --git a/packages/angular-test-app/package.json b/packages/angular-test-app/package.json index 401c358873..6873097012 100644 --- a/packages/angular-test-app/package.json +++ b/packages/angular-test-app/package.json @@ -6,7 +6,8 @@ "ng": "ng", "start": "ng serve", "build": "ng build --preserve-symlinks -c production", - "watch": "ng build --watch --configuration development" + "watch": "ng build --watch --configuration development", + "test": "ng test --no-watch --no-progress --browsers=ChromeHeadlessCI" }, "private": true, "dependencies": { diff --git a/packages/angular-test-app/src/select/select.spec.ts b/packages/angular-test-app/src/select/select.spec.ts new file mode 100644 index 0000000000..a926dfa033 --- /dev/null +++ b/packages/angular-test-app/src/select/select.spec.ts @@ -0,0 +1,62 @@ +import { + FormControl, + FormGroup, + FormsModule, + ReactiveFormsModule, +} from '@angular/forms'; + +import { + ApplicationInitStatus, + Component, + CUSTOM_ELEMENTS_SCHEMA, +} from '@angular/core'; +import { ComponentFixture, TestBed } from '@angular/core/testing'; +import { IxModule } from '@siemens/ix-angular'; +import { By } from '@angular/platform-browser'; + +@Component({ + selector: 'ix-example-form-select', + template: `
+ + Test + + + + + + +
`, +}) +class SelectComponent { + public form = new FormGroup({ select: new FormControl('1') }); +} + +describe('SelectFormComponent', () => { + let component: SelectComponent; + let fixture: ComponentFixture; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + declarations: [SelectComponent], + schemas: [CUSTOM_ELEMENTS_SCHEMA], + imports: [FormsModule, ReactiveFormsModule, IxModule.forRoot()], + }).compileComponents(); + + fixture = TestBed.createComponent(SelectComponent); + component = fixture.componentInstance; + }); + + beforeEach(async () => { + // until https://github.com/angular/angular/issues/24218 is fixed + await TestBed.inject(ApplicationInitStatus).donePromise; + }); + + it('should change the input value', async () => { + const select = fixture.debugElement.query(By.css('ix-select')); + component.form.get('select')!.setValue('2'); + fixture.detectChanges(); + + expect(select.nativeElement.value).toBe('2'); + expect(component).toBeDefined(); + }); +}); diff --git a/packages/angular-test-app/src/test.ts b/packages/angular-test-app/src/test.ts index 2ffa612967..9202196750 100644 --- a/packages/angular-test-app/src/test.ts +++ b/packages/angular-test-app/src/test.ts @@ -8,13 +8,12 @@ */ // This file is required by karma.conf.js and loads recursively all the .spec and framework files - +import 'zone.js/testing'; import { getTestBed } from '@angular/core/testing'; import { BrowserDynamicTestingModule, platformBrowserDynamicTesting, } from '@angular/platform-browser-dynamic/testing'; -import 'zone.js/testing'; declare const require: { context( diff --git a/packages/core/src/components/select/select.tsx b/packages/core/src/components/select/select.tsx index 41ddf3ef75..504435853a 100644 --- a/packages/core/src/components/select/select.tsx +++ b/packages/core/src/components/select/select.tsx @@ -305,14 +305,13 @@ export class Select { } this.items.forEach((item) => { - item.selected = ids.some( - // Check can be removed if value is type of string in future releases - (i) => - i === - (item.value !== undefined && item.value !== null - ? item.value.toString() - : '') - ); + item.selected = ids.some((i) => { + if (typeof i !== typeof item.value) { + return i.toString() === item.value.toString(); + } else { + return i === item.value; + } + }); }); this.selectedLabels = this.selectedItems.map((item) => item.label); diff --git a/packages/core/src/components/select/test/select.ct.ts b/packages/core/src/components/select/test/select.ct.ts index c59261767a..5044d27f97 100644 --- a/packages/core/src/components/select/test/select.ct.ts +++ b/packages/core/src/components/select/test/select.ct.ts @@ -264,6 +264,45 @@ test('type in a novel item name in editable mode, click outside and reopen the s await expect(page.getByRole('button', { name: 'Item 3' })).toBeVisible(); }); +test('pass object as value and check if it is selectable', async ({ + mount, + page, +}) => { + await mount(` + + Test + Test + Test + + `); + const selectElement = page.locator('ix-select'); + await expect(selectElement).toHaveClass(/hydrated/); + + async function setSelectItemValue(index: number): Promise { + await page + .locator('ix-select-item') + .nth(index) + .evaluate((e: HTMLIxSelectItemElement, index) => { + e.value = { selectLabel: `Item ${index}`, selectValue: `${index}` }; + }); + } + + for (let index = 0; index < 3; index++) { + await setSelectItemValue(index); + } + + await page.locator('[data-select-dropdown]').click(); + await page.locator('ix-select-item').last().click(); + await page.locator('[data-select-dropdown]').click(); + + await expect(page.getByRole('button', { name: 'Item 1' })).toBeVisible(); + await expect(page.getByRole('button', { name: 'Item 2' })).toBeVisible(); + await expect(page.getByRole('button', { name: 'Item 3' })).toBeVisible(); + await expect( + page.getByRole('button', { name: 'Item 3' }).locator('ix-icon') + ).toBeVisible(); +}); + test.describe('arrow key navigation', () => { test.describe('ArrowDown', () => { test('input -> slotted item', async ({ mount, page }) => {