Skip to content
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

UI test framework #11

Open
wants to merge 11 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 13 additions & 1 deletion .github/workflows/test-coverage.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -27,10 +27,22 @@ jobs:
with:
go-version: "1.19"

- name: Unit tests
- name: Run backend unit tests
run: |
go test ./... -coverprofile coverage.out -covermode count
go tool cover -func coverage.out
- name: Set up Node.js
uses: actions/setup-node@v2
with:
node-version: 16
- name: Install frontend test dependencies
run: |
cd ui
npm ci
- name: Run UI unit tests
run: |
cd ui
npm test -- --browsers=ChromeHeadless --watch=false
- name: Upload coverage reports to Codecov
uses: codecov/codecov-action@v3
with:
Expand Down
2 changes: 2 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,9 @@ update-vendor:
# Run unit tests
test:
go test -v ./...
cd ui/ && npm test -- --browsers=ChromeHeadless --watch=false
# Run code coverage with unit tests
test-coverage:
go test ./... -coverprofile coverage.out -covermode count
go tool cover -func coverage.out
cd ui/ && npm test -- --browsers=ChromeHeadless --watch=false
6 changes: 5 additions & 1 deletion ui/angular.json
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,11 @@
"./node_modules/@angular/material/prebuilt-themes/indigo-pink.css",
"src/styles.scss"
],
"scripts": []
"scripts": [],
"codeCoverage": true,
"codeCoverageExclude": [
"**/mocks/**"
]
}
}
}
Expand Down
2 changes: 1 addition & 1 deletion ui/dist/ui/index.html

Large diffs are not rendered by default.

Large diffs are not rendered by default.

3 changes: 2 additions & 1 deletion ui/karma.conf.js
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,8 @@ module.exports = function (config) {
subdir: '.',
reporters: [
{ type: 'html' },
{ type: 'text-summary' }
{ type: 'text-summary' },
{ type: 'lcovonly' },
]
},
reporters: ['progress', 'kjhtml'],
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,14 @@
import { HttpClientModule } from '@angular/common/http';
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { ReactiveFormsModule } from '@angular/forms';
import { MatButtonModule } from '@angular/material/button';
import { MatCardModule } from '@angular/material/card';
import { MatDialogModule } from '@angular/material/dialog';
import { MatFormFieldModule } from '@angular/material/form-field';
import { MatInputModule } from '@angular/material/input';
import { MatSelectModule } from '@angular/material/select';
import { MatSnackBarModule } from '@angular/material/snack-bar';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';

import { AddIndexFormComponent } from './add-index-form.component';

Expand All @@ -8,7 +18,8 @@ describe('AddIndexFormComponent', () => {

beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [ AddIndexFormComponent ]
declarations: [ AddIndexFormComponent ],
imports: [ReactiveFormsModule, HttpClientModule, MatSnackBarModule, MatSelectModule, BrowserAnimationsModule, MatFormFieldModule, MatInputModule]
})
.compileComponents();
});
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,12 @@
import { HttpClientModule } from '@angular/common/http';
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { ReactiveFormsModule } from '@angular/forms';
import { MatDialogModule, MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';
import { MatInputModule } from '@angular/material/input';
import { MatSelectModule } from '@angular/material/select';
import { MatSnackBarModule } from '@angular/material/snack-bar';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { Dialect } from 'src/app/app.constants';

import { AddNewColumnComponent } from './add-new-column.component';

Expand All @@ -8,14 +16,29 @@ describe('AddNewColumnComponent', () => {

beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [ AddNewColumnComponent ]
declarations: [AddNewColumnComponent],
imports: [ReactiveFormsModule, HttpClientModule, MatSnackBarModule, MatDialogModule, MatSelectModule, MatInputModule, BrowserAnimationsModule],
providers: [
{
provide: MatDialogRef,
useValue: {
close: () => { },
},
},
{
provide: MAT_DIALOG_DATA,
useValue: {}
}
],
})
.compileComponents();
.compileComponents();
});

beforeEach(() => {
fixture = TestBed.createComponent(AddNewColumnComponent);
component = fixture.componentInstance;
component.dialect = Dialect.GoogleStandardSQLDialect;
console.log(component.datatypes)
fixture.detectChanges();
});

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,9 @@ import { Component, Inject, OnInit } from '@angular/core';
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';
import { ColLength, DataTypes, Dialect } from 'src/app/app.constants';
import { IColumn, ISpannerDetails } from 'src/app/model/conv';
import { IAddColumnProps } from 'src/app/model/edit-table';
import { IAddColumn } from 'src/app/model/update-table';
import { DataService } from 'src/app/services/data/data.service';
import { TargetDetailsFormComponent } from '../target-details-form/target-details-form.component';
@Component({
selector: 'app-add-new-column',
templateUrl: './add-new-column.component.html',
Expand All @@ -24,13 +22,13 @@ export class AddNewColumnComponent implements OnInit {
constructor(
private formBuilder: FormBuilder,
private dataService: DataService,
private dialogRef: MatDialogRef<TargetDetailsFormComponent>,
private dialogRef: MatDialogRef<AddNewColumnComponent>,
@Inject(MAT_DIALOG_DATA) public data: IAddColumnProps) {
this.dialect = data.dialect
this.tableId = data.tableId
this.addNewColumnForm = this.formBuilder.group({
name: ['', [Validators.required, Validators.minLength(1), Validators.maxLength(128), Validators.pattern('^[a-zA-Z][a-zA-Z0-9_]*$')]],
datatype: [],
datatype: ['', Validators.required],
length: ['',Validators.pattern('^[0-9]+$')],
isNullable: [],
})
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,9 @@
import { HttpClientModule } from '@angular/common/http';
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { ReactiveFormsModule } from '@angular/forms';
import { MatSelectModule } from '@angular/material/select';
import { MatSnackBarModule } from '@angular/material/snack-bar';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';

import { AddShardIdPrimaryKeyComponent } from './add-shard-id-primary-key.component';

Expand All @@ -8,7 +13,8 @@ describe('AddShardIdPrimaryKeyComponent', () => {

beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [ AddShardIdPrimaryKeyComponent ]
declarations: [ AddShardIdPrimaryKeyComponent ],
imports: [ReactiveFormsModule, HttpClientModule, MatSnackBarModule, MatSelectModule, BrowserAnimationsModule]
})
.compileComponents();
});
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { FormControl, ReactiveFormsModule } from '@angular/forms';
import { MatDialogModule, MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';

import { BulkDropRestoreTableDialogComponent } from './bulk-drop-restore-table-dialog.component';

Expand All @@ -8,7 +10,26 @@ describe('BulkDropRestoreTableDialogComponent', () => {

beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [ BulkDropRestoreTableDialogComponent ]
declarations: [ BulkDropRestoreTableDialogComponent ],
imports: [MatDialogModule, ReactiveFormsModule],
providers: [
{
provide: MatDialogRef,
useValue: {
close: () => {},
},
},
{
provide: MAT_DIALOG_DATA,
useValue: {
tables: [
{ TableName: 'Table1', isDeleted: false },
{ TableName: 'Table2', isDeleted: true },
],
operation: 'SKIP'
}
}
],
})
.compileComponents();
});
Expand All @@ -22,4 +43,22 @@ describe('BulkDropRestoreTableDialogComponent', () => {
it('should create', () => {
expect(component).toBeTruthy();
});

it('should create a confirmation input control with the correct pattern', () => {
// Test the confirmationInput control creation
expect(component.confirmationInput instanceof FormControl).toBe(true);
expect(component.confirmationInput.valid).toBe(false); // Confirm it's invalid initially
expect(component.confirmationInput.hasError('required')).toBe(true); // Confirm it requires a value
// Test the pattern validation
component.confirmationInput.setValue('SKIP');
expect(component.confirmationInput.valid).toBe(true); // Confirm it's valid with 'SKIP'
component.confirmationInput.setValue('INVALID_VALUE');
expect(component.confirmationInput.valid).toBe(false); // Confirm it's invalid with an invalid value
});

it('should initialize eligible and ineligible tables based on the provided data', () => {
// Test the initialization of eligible and ineligible tables
expect(component.eligibleTables).toEqual(['Table1']);
expect(component.ineligibleTables).toEqual(['Table2']);
});
});
Original file line number Diff line number Diff line change
@@ -1,4 +1,11 @@
import { HttpClientModule } from '@angular/common/http';
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { ReactiveFormsModule } from '@angular/forms';
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';
import { MatInputModule } from '@angular/material/input';
import { MatRadioModule } from '@angular/material/radio';
import { MatSnackBarModule } from '@angular/material/snack-bar';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';

import { ConnectionProfileFormComponent } from './connection-profile-form.component';

Expand All @@ -8,14 +15,29 @@ describe('ConnectionProfileFormComponent', () => {

beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [ ConnectionProfileFormComponent ]
declarations: [ ConnectionProfileFormComponent ],
imports: [HttpClientModule, MatSnackBarModule, ReactiveFormsModule, MatRadioModule, MatInputModule, BrowserAnimationsModule],
providers: [
{
provide: MatDialogRef,
useValue: {
close: () => {},
},
},
{
provide: MAT_DIALOG_DATA,
useValue: {
}
}
],
})
.compileComponents();
});

beforeEach(() => {
fixture = TestBed.createComponent(ConnectionProfileFormComponent);
component = fixture.componentInstance;
component.isSource = true
fixture.detectChanges();
});

Expand Down
Original file line number Diff line number Diff line change
@@ -1,14 +1,17 @@
import { ComponentFixture, TestBed } from '@angular/core/testing';

import { RouterModule, Routes } from '@angular/router';
import { WorkspaceComponent } from '../workspace/workspace.component';
import { DatabaseLoaderComponent } from './database-loader.component';
const appRoutes: Routes = [{ path: 'workspace', component: WorkspaceComponent }]

describe('DatabaseLoaderComponent', () => {
let component: DatabaseLoaderComponent;
let fixture: ComponentFixture<DatabaseLoaderComponent>;

beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [ DatabaseLoaderComponent ]
declarations: [ DatabaseLoaderComponent ],
imports: [RouterModule.forRoot(appRoutes),]
})
.compileComponents();
});
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import { HttpClientModule } from '@angular/common/http';
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { MatDialogRef, MAT_DIALOG_DATA } from '@angular/material/dialog';

import { DataflowFormComponent } from './dataflow-form.component';

Expand All @@ -8,7 +10,21 @@ describe('DataflowFormComponent', () => {

beforeEach(async () => {
await TestBed.configureTestingModule({
declarations: [ DataflowFormComponent ]
declarations: [ DataflowFormComponent ],
imports: [HttpClientModule],
providers: [
{
provide: MatDialogRef,
useValue: {
close: () => {},
},
},
{
provide: MAT_DIALOG_DATA,
useValue: {
}
}
],
})
.compileComponents();
});
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
<div class="connect-load-database-container">
<div class="connect-load-database-container" id="direct-connection-component">
<div class="form-container">
<form [formGroup]="connectForm">
<h3 class="primary-header">Connect to Source Database</h3>

<mat-form-field class="full-width" appearance="outline">
<mat-label>Database Engine</mat-label>
<mat-select formControlName="dbEngine" (selectionChange)="refreshDbSpecifcConnectionOptions()">
<mat-select formControlName="dbEngine" (selectionChange)="refreshDbSpecifcConnectionOptions()" id="dbengine-input">
<mat-option *ngFor="let element of dbEngineList" [value]="element.value">
{{ element.displayName }}
</mat-option>
Expand Down Expand Up @@ -38,34 +38,34 @@ <h3 class="primary-header">Connection Detail</h3>

<mat-form-field class="full-width" appearance="outline">
<mat-label>Hostname</mat-label>
<input matInput placeholder="127.0.0.1" name="hostName" type="text" formControlName="hostName" />
<input matInput placeholder="127.0.0.1" name="hostName" type="text" formControlName="hostName" id="hostname-input" />
</mat-form-field>

<mat-form-field class="full-width" appearance="outline">
<mat-label>Port</mat-label>
<input matInput placeholder="3306" name="port" type="text" formControlName="port" />
<input matInput placeholder="3306" name="port" type="text" formControlName="port" id="port-input" />
<mat-error> Only numbers are allowed. </mat-error>
</mat-form-field>
<br />
<mat-form-field class="full-width" appearance="outline">
<mat-label>User name</mat-label>
<input matInput placeholder="root" name="userName" type="text" formControlName="userName" />
<input matInput placeholder="root" name="userName" type="text" formControlName="userName" id="username-input" />
</mat-form-field>

<mat-form-field class="full-width" appearance="outline">
<mat-label>Password</mat-label>
<input matInput name="password" type="password" formControlName="password" />
<input matInput name="password" type="password" formControlName="password" id="password-input" />
</mat-form-field>
<br />
<mat-form-field class="full-width" appearance="outline">
<mat-label>Database Name</mat-label>
<input matInput name="dbname" type="text" formControlName="dbName" />
<input matInput name="dbname" type="text" formControlName="dbName" id="dbname-input" />
</mat-form-field>
<br />
<h3 class="primary-header">Spanner Dialect</h3>
<mat-form-field class="full-width" appearance="outline">
<mat-label>Select a spanner dialect</mat-label>
<mat-select matSelect name="dialect" formControlName="dialect" appearance="outline">
<mat-select matSelect name="dialect" formControlName="dialect" appearance="outline" id="spanner-dialect-input">
<mat-option *ngFor="let element of dialect" [value]="element.value">
{{ element.displayName }}
</mat-option>
Expand All @@ -76,7 +76,7 @@ <h3 class="primary-header">Spanner Dialect</h3>
matTooltipPosition="above">
check_circle
</mat-icon>
<button mat-raised-button type="submit" color="accent" [disabled]="!connectForm.valid" (click)="testConn()">
<button mat-raised-button id="test-connect-btn" type="submit" color="accent" [disabled]="!connectForm.valid" (click)="testConn()">
Test Connection
</button>
<button mat-raised-button type="submit" color="primary" [disabled]="!connectForm.valid || !isTestConnectionSuccessful" (click)="connectToDb()">
Expand Down
Loading
Loading