feat: [code-1755]: add signup integration test (#1207)

gitness-test1
Calvin Lee 2024-04-11 23:35:26 +00:00 committed by Harness
parent 622cc58b21
commit a314709402
11 changed files with 1538 additions and 1 deletions

1
.gitignore vendored
View File

@ -14,6 +14,7 @@ release
.vscode/settings.json
coverage.out
gitness.session.sql
web/cypress/node_modules
# ignore any executables we build
/gitness

View File

@ -0,0 +1,19 @@
import { defineConfig } from 'cypress'
export default defineConfig({
e2e: {
baseUrl: 'http://localhost:3020',
specPattern: 'integration/**/*.spec.{ts,tsx}',
supportFile: 'support/e2e.ts',
fixturesFolder: 'fixtures',
videoUploadOnPasses: false
},
projectId: 'mcssf4',
viewportWidth: 1500,
viewportHeight: 1000,
retries: {
runMode: 2,
openMode: 0
},
fixturesFolder: 'fixtures'
})

View File

@ -0,0 +1,5 @@
{
"name": "Using fixtures to represent data",
"email": "hello@cypress.io",
"body": "Fixtures are a great way to mock data for responses to routes"
}

View File

@ -0,0 +1,45 @@
import {
CreateUserResponse,
GetUserResponse,
membershipGetCall,
membershipQueryGetCall,
signupPostCall,
userGetCall
} from './constants'
describe('Signup', () => {
beforeEach(() => {
cy.on('uncaught:exception', () => false)
cy.intercept('POST', signupPostCall, CreateUserResponse).as('signupPostCall')
cy.intercept('GET', userGetCall, GetUserResponse).as('userGetCall')
cy.intercept('GET', membershipGetCall, []).as('membershipGetCall')
cy.intercept('GET', membershipQueryGetCall, []).as('membershipQueryGetCall')
})
it('should signup a new user', () => {
cy.visit('/register')
cy.contains('div p', 'Sign Up').should('be.visible')
cy.contains('span', 'User ID').should('be.visible')
cy.contains('span', 'Email').should('be.visible')
cy.contains('span', 'Password').should('be.visible')
cy.contains('span', 'Confirm Password').should('be.visible')
// Fill fields
cy.get('input[name="username"]').type('testuser')
cy.get('input[name="email"]').type('test@harness.io')
cy.get('input[name="password"]').type('password')
cy.get('input[name="confirmPassword"]').type('password')
//click signup
cy.contains('button span', 'Sign Up').click()
cy.wait('@signupPostCall')
cy.wait('@userGetCall')
cy.get('@signupPostCall').its('request.body').should('deep.equal', {
display_name: 'testuser',
email: 'test@harness.io',
uid: 'testuser',
password: 'password'
})
cy.wait('@membershipGetCall')
cy.wait('@membershipQueryGetCall')
})
})

View File

@ -0,0 +1,27 @@
export const CreateUserResponse = {
access_token: 'token',
token: {
principal_id: 1,
type: 'session',
identifier: 'register',
expires_at: 1715463431214,
issued_at: 1712871431214,
created_by: 15,
uid: 'register'
}
}
export const GetUserResponse = {
uid: 'testuser',
email: 'test@harness.io',
display_name: 'testuser',
admin: false,
blocked: false,
created: 1712871431212,
updated: 1712871431212
}
export const signupPostCall = `/api/v1/register?include_cookie=true`
export const userGetCall = `/api/v1/user`
export const membershipGetCall = '/api/v1/user/memberships'
export const membershipQueryGetCall = '/api/v1/user/memberships?query='

13
web/cypress/package.json Normal file
View File

@ -0,0 +1,13 @@
{
"name": "cypress-tests",
"private": "true",
"scripts": {
"cypress:open": "cypress open",
"server": "node server.js"
},
"main": "index.js",
"dependencies": {
"cypress": "10.8.0",
"wait-on": "^6.0.1"
}
}

61
web/cypress/server.js Normal file
View File

@ -0,0 +1,61 @@
/*
* Copyright 2023 Harness, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
const express = require('express')
const fs = require('fs')
const app = express()
const path = require('path')
const PORT = 8080
function checkFileExistsSync(filepath) {
let flag = true
try {
fs.accessSync(filepath, fs.constants.F_OK)
} catch (e) {
flag = false
}
return flag
}
function getFile(req) {
const url = req.url.split('?')[0].replace(/^\/gateway/, '')
return path.resolve(__dirname, `fixtures${url}${req.method === 'POST' ? '.post' : ''}.json`)
}
app.all('*', (req, res) => {
if (req.get('Content-Type') === 'text/plain') {
res.setHeader('Content-Type', 'text/plain')
} else {
res.setHeader('Content-Type', 'application/json')
}
const file = getFile(req)
if (['POST', 'GET', 'PUT'].indexOf(req.method) > -1 && checkFileExistsSync(file)) {
res.end(fs.readFileSync(file))
} else {
res.end(
JSON.stringify({
correlationId: '',
data: {},
status: 'SUCCESS'
})
)
}
})
app.listen(PORT, () => {
console.log(`⚡️[server]: Server is running at http://localhost:${PORT}`)
})

View File

@ -0,0 +1,84 @@
// @ts-check
///<reference path="../../src/global.d.ts" />
// ***********************************************
// This example commands.js shows you how to
// create various custom commands and overwrite
// existing commands.
//
// For more comprehensive examples of custom
// commands please read more here:
// https://on.cypress.io/custom-commands
// ***********************************************
//
//
// -- This is a parent command --
// Cypress.Commands.add('login', (email, password) => { ... })
//
//
// -- This is a child command --
// Cypress.Commands.add('drag', { prevSubject: 'element'}, (subject, options) => { ... })
//
//
// -- This is a dual command --
// Cypress.Commands.add('dismiss', { prevSubject: 'optional'}, (subject, options) => { ... })
//
//
// -- This will overwrite an existing command --
// Cypress.Commands.overwrite('visit', (originalFn, url, options) => { ... })
declare namespace Cypress {
interface Chainable {
clickSubmit(): void
visitPageAssertion(className?: string): void
getAccountIdentifier(): any
apiRequest(
method: string,
endpoint: string,
body?: any,
queryParams?: { [key: string]: string },
headerOptions?: HeadersInit
): void
getSecret(scope: string): any
fillName(name: string): void
fillField(fieldName: string, value: string): void
login(username?: string, password?: string): void
}
}
export const activeTabClassName = '.TabNavigation--active'
Cypress.Commands.add('visitPageAssertion', (className = activeTabClassName) => {
cy.get(className, {
timeout: 30000
}).should('be.visible')
cy.wait(1000)
})
Cypress.Commands.add('clickSubmit', () => {
cy.get('input[type="submit"]').click()
})
Cypress.Commands.add('getAccountIdentifier', () => {
cy.location('hash').then(hash => {
return cy.wrap(hash.split('/')[2])
})
})
Cypress.Commands.add(
'apiRequest',
(
method: string,
endpoint: string,
body?: unknown,
queryParams?: { [key: string]: string },
headerOptions?: HeadersInit
) => {
cy.request(generateRequestObject(method, endpoint, body, queryParams, headerOptions))
}
)
Cypress.Commands.add('fillField', (fieldName: string, value: string) => {
cy.get(`[name="${fieldName}"]`).clear().type(value)
})
Cypress.Commands.add('fillName', (value: string) => {
cy.fillField('name', value)
})

View File

@ -0,0 +1,20 @@
// ***********************************************************
// This example support/e2e.ts is processed and
// loaded automatically before your test files.
//
// This is a great place to put global configuration and
// behavior that modifies Cypress.
//
// You can change the location of this file or turn off
// automatically serving support files with the
// 'supportFile' configuration option.
//
// You can read more here:
// https://on.cypress.io/configuration
// ***********************************************************
// Import commands.js using ES2015 syntax:
import './commands'
// Alternatively you can use CommonJS syntax:
// require('./commands')

1261
web/cypress/yarn.lock Normal file

File diff suppressed because it is too large Load Diff

View File

@ -31,7 +31,8 @@
"services": "restful-react import --config restful-react.config.js",
"postservices": "prettier --write src/services/**/*.tsx",
"strings": "npm-run-all strings:*",
"strings:genTypes": "node scripts/strings/generateTypesCli.mjs"
"strings:genTypes": "node scripts/strings/generateTypesCli.mjs",
"dev:cypress": "NODE_ENV=development TARGET_LOCALHOST=false CYPRESS=true PROJECT_ID=CYPRESS_PROJECT_ID ORG_ID=CYPRESS_ORG_ID ACCOUNT_ID=CYPRESS_ACCOUNT_ID BASE_URL=http://localhost:8080 NODE_OPTIONS=\"--max-old-space-size=6144\" webpack serve --progress --config config/webpack.dev.js"
},
"dependencies": {
"@blueprintjs/core": "3.26.1",