From 97f900287fef4e6f614883da97418c6522081635 Mon Sep 17 00:00:00 2001 From: Alexandre Magno Date: Mon, 2 Dec 2024 16:16:11 +0100 Subject: [PATCH] fix: fixing issue reference requirements on pull request when theres multiple issue references@ --- modules/tasks/taskSolutionFetchData.js | 11 +- test/taskSolution.test.js | 511 ++++++++++++++----------- 2 files changed, 304 insertions(+), 218 deletions(-) diff --git a/modules/tasks/taskSolutionFetchData.js b/modules/tasks/taskSolutionFetchData.js index 6df890c7..c7d5afe8 100644 --- a/modules/tasks/taskSolutionFetchData.js +++ b/modules/tasks/taskSolutionFetchData.js @@ -9,6 +9,12 @@ function extractIssueReferences(text) { return matches ? matches.map(match => match.slice(1)) : []; // Remove the '#' prefix } +function extractIssueNumberFromURL(url) { + const match = url.match(/\/issues\/(\d+)(\/)?$/); + return match ? match[1] : null; +} + + module.exports = Promise.method(async function fetchTaskSolutionData (solutionParams) { return requestPromise({ uri: `https://api.github.com/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`, @@ -59,7 +65,10 @@ module.exports = Promise.method(async function fetchTaskSolutionData (solutionPa } } const issueReferences = extractIssueReferences(pullRequestData.body) - if(issueReferences.length && task.dataValues.url.includes(issueReferences)) { + const issueNumber = extractIssueNumberFromURL(task.dataValues.url) + const issueReferencesMatch = issueReferences.some(issueReference => issueNumber === issueReference) + + if(issueReferences.length && issueReferencesMatch) { hasIssueReference = true } diff --git a/test/taskSolution.test.js b/test/taskSolution.test.js index 9c1e4934..a6c012eb 100644 --- a/test/taskSolution.test.js +++ b/test/taskSolution.test.js @@ -20,227 +20,214 @@ describe("Task Solution", () => { await truncateModels(models.Order); await truncateModels(models.Transfer); }) - it('should create a task solution', async () => { - try { - const solutionParams = { - pullRequestId: '2', - userId: 1, - repositoryName: 'test-repository', - owner: 'alexanmtz', - taskId: 1 - } - - nock('https://api.github.com') - .persist() - .get(`/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`) + + afterEach(async () => { + nock.cleanAll() + }) + describe("Create task Solution", () => { + it('should create a task solution', async () => { + try { + const solutionParams = { + pullRequestId: '2', + userId: 1, + repositoryName: 'test-repository', + owner: 'alexanmtz', + taskId: 1 + } - .reply(200, { - user: { - login: 'alexanmtz' - }, - state: 'closed', - merged: true, - title: 'test PR #1', - body: 'closes #1' - }) - // Await the login process - const loginResponse = await registerAndLogin(agent, { - email: 'tasksolutiontest@test.com', - provider: 'github', - provider_username: 'alexanmtz', - }); - const { body: user, headers } = loginResponse; - - // Create the task - const task = await createTask(agent, { - url: 'https://github.com/alexanmtz/test-repository/issues/1', - userId: user.id, - status: 'closed' - }); + nock('https://api.github.com') + .persist() + .get(`/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`) + + .reply(200, { + user: { + login: 'alexanmtz' + }, + state: 'closed', + merged: true, + title: 'test PR #1', + body: 'closes #1' + }) + // Await the login process + const loginResponse = await registerAndLogin(agent, { + email: 'tasksolutiontest@test.com', + provider: 'github', + provider_username: 'alexanmtz', + }); + const { body: user, headers } = loginResponse; + + // Create the task + const task = await createTask(agent, { + url: 'https://github.com/alexanmtz/test-repository/issues/1', + userId: user.id, + status: 'closed' + }); - // Create order - const order = await models.Order.create({ - provider: 'stripe', - amount: 100, - userId: user.id, - TaskId: task.id, - source_id: '1234', - status: 'succeeded', - paid: true - }); - - // Send a POST request to create a task solution - const taskSolutionCreateRes = await agent - .post('/tasksolutions/create') - .set('Authorization', headers.authorization) - .expect('Content-Type', /json/) - .expect(200) - .send({ - isConnectedToGitHub: true, - isAuthorOfPR: true, - isPRMerged: true, - isIssueClosed: true, - hasIssueReference: true, - pullRequestURL: "https://github.com/alexanmtz/test-repository/pull/2", + // Create order + const order = await models.Order.create({ + provider: 'stripe', + amount: 100, userId: user.id, - taskId: task.id + TaskId: task.id, + source_id: '1234', + status: 'succeeded', + paid: true }); - expect(taskSolutionCreateRes.body).to.have.property('id'); - } catch (err) { - // Fail the test if any error occurs - throw err; - } - }); - it('should create a task solution with stripe response with insuficient capatibilities', async () => { - try { - const solutionParams = { - pullRequestId: '2', - userId: 1, - repositoryName: 'test-repository', - owner: 'alexanmtz', - taskId: 1 + + // Send a POST request to create a task solution + const taskSolutionCreateRes = await agent + .post('/tasksolutions/create') + .set('Authorization', headers.authorization) + .expect('Content-Type', /json/) + .expect(200) + .send({ + isConnectedToGitHub: true, + isAuthorOfPR: true, + isPRMerged: true, + isIssueClosed: true, + hasIssueReference: true, + pullRequestURL: "https://github.com/alexanmtz/test-repository/pull/2", + userId: user.id, + taskId: task.id + }); + expect(taskSolutionCreateRes.body).to.have.property('id'); + } catch (err) { + // Fail the test if any error occurs + throw err; } + }); + it('should create a task solution with stripe response with insuficient capatibilities', async () => { + try { + const solutionParams = { + pullRequestId: '2', + userId: 1, + repositoryName: 'test-repository', + owner: 'alexanmtz', + taskId: 1 + } - nock('https://api.stripe.com') - .post('/v1/transfers') - .reply(400, { - "error": { - "code": "insufficient_capabilities_for_transfer", - "message": "Your destination account needs to have at least one of the following capabilities enabled: transfers, crypto_transfers, legacy_payments", - "request_log_url": "https://dashboard.stripe.com/logs/req_agK5H7d0oxGetF?t=1730319991", - "type": "invalid_request_error" - } - }) - - nock('https://api.github.com') - .persist() - .get(`/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`) + nock('https://api.stripe.com') + .post('/v1/transfers') + .reply(400, { + "error": { + "code": "insufficient_capabilities_for_transfer", + "message": "Your destination account needs to have at least one of the following capabilities enabled: transfers, crypto_transfers, legacy_payments", + "request_log_url": "https://dashboard.stripe.com/logs/req_agK5H7d0oxGetF?t=1730319991", + "type": "invalid_request_error" + } + }) - .reply(200, { - user: { - login: 'alexanmtz' - }, - state: 'closed', - merged: true, - title: 'test PR #1', - body: 'closes #1' - }) - // Await the login process - const loginResponse = await registerAndLogin(agent, { - email: 'tasksolutiontest@test.com', - provider: 'github', - provider_username: 'alexanmtz', - account_id: 'acc_test' - }); - const { body: user, headers } = loginResponse; - - // Create the task - const task = await createTask(agent, { - url: 'https://github.com/alexanmtz/test-repository/issues/1', - userId: user.id, - status: 'closed' - }); + nock('https://api.github.com') + .persist() + .get(`/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`) + + .reply(200, { + user: { + login: 'alexanmtz' + }, + state: 'closed', + merged: true, + title: 'test PR #1', + body: 'closes #1' + }) + // Await the login process + const loginResponse = await registerAndLogin(agent, { + email: 'tasksolutiontest@test.com', + provider: 'github', + provider_username: 'alexanmtz', + account_id: 'acc_test' + }); + const { body: user, headers } = loginResponse; + + // Create the task + const task = await createTask(agent, { + url: 'https://github.com/alexanmtz/test-repository/issues/1', + userId: user.id, + status: 'closed' + }); - // Create order - const order = await models.Order.create({ - provider: 'stripe', - amount: 100, - userId: user.id, - TaskId: task.id, - source_id: '1234', - status: 'succeeded', - paid: true - }); - - // Send a POST request to create a task solution - const taskSolutionCreateRes = await agent - .post('/tasksolutions/create') - .set('Authorization', headers.authorization) - .expect('Content-Type', /json/) - .expect(400) - .send({ - isConnectedToGitHub: true, - isAuthorOfPR: true, - isPRMerged: true, - isIssueClosed: true, - hasIssueReference: true, - pullRequestURL: "https://github.com/alexanmtz/test-repository/pull/2", + // Create order + const order = await models.Order.create({ + provider: 'stripe', + amount: 100, userId: user.id, - taskId: task.id + TaskId: task.id, + source_id: '1234', + status: 'succeeded', + paid: true }); - expect(taskSolutionCreateRes.statusCode).to.equal(400); - expect(taskSolutionCreateRes.body.error).to.equal('issue.solution.error.insufficient_capabilities_for_transfer'); - } catch (err) { - // Fail the test if any error occurs - throw err; - } - }); - it('should update a task solution', async () => { - try { - const solutionParams = { - pullRequestId: '2', - userId: 1, - repositoryName: 'test-repository', - owner: 'alexanmtz', - taskId: 1 + + // Send a POST request to create a task solution + const taskSolutionCreateRes = await agent + .post('/tasksolutions/create') + .set('Authorization', headers.authorization) + .expect('Content-Type', /json/) + .expect(400) + .send({ + isConnectedToGitHub: true, + isAuthorOfPR: true, + isPRMerged: true, + isIssueClosed: true, + hasIssueReference: true, + pullRequestURL: "https://github.com/alexanmtz/test-repository/pull/2", + userId: user.id, + taskId: task.id + }); + expect(taskSolutionCreateRes.statusCode).to.equal(400); + expect(taskSolutionCreateRes.body.error).to.equal('issue.solution.error.insufficient_capabilities_for_transfer'); + } catch (err) { + // Fail the test if any error occurs + throw err; } - - nock('https://api.github.com') - .persist() - .get(`/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`) + }); + it('should update a task solution', async () => { + try { + const solutionParams = { + pullRequestId: '2', + userId: 1, + repositoryName: 'test-repository', + owner: 'alexanmtz', + taskId: 1 + } - .reply(200, { - user: { - login: 'alexanmtz' - }, - state: 'closed', - merged: true, - title: 'test PR #1', - body: 'closes #1' - }) - // Await the login process - const loginResponse = await registerAndLogin(agent, { - email: 'tasksolutiontest2@test.com', - provider: 'github', - provider_username: 'alexanmtz', - }); - const { body: user, headers } = loginResponse; - - // Create the task - const task = await createTask(agent, { - url: 'https://github.com/alexanmtz/test-repository/issues/1', - userId: user.id, - status: 'closed' - }); + nock('https://api.github.com') + .get(`/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`) + + .reply(200, { + user: { + login: 'alexanmtz' + }, + state: 'closed', + merged: true, + title: 'test PR #1', + body: 'closes #1' + }) + // Await the login process + const loginResponse = await registerAndLogin(agent, { + email: 'tasksolutiontest2@test.com', + provider: 'github', + provider_username: 'alexanmtz', + }); + const { body: user, headers } = loginResponse; + + // Create the task + const task = await createTask(agent, { + url: 'https://github.com/alexanmtz/test-repository/issues/1', + userId: user.id, + status: 'closed' + }); - // Create order - const order = await models.Order.create({ - amount: 100, - userId: user.id, - TaskId: task.id, - source_id: '1234', - status: 'succeeded', - paid: true - }); + // Create order + const order = await models.Order.create({ + amount: 100, + userId: user.id, + TaskId: task.id, + source_id: '1234', + status: 'succeeded', + paid: true + }); - const taskSolutionCreateRes = await models.TaskSolution.create({ - isConnectedToGitHub: true, - isAuthorOfPR: true, - isPRMerged: true, - isIssueClosed: true, - hasIssueReference: true, - pullRequestURL: "https://github.com/alexanmtz/test-repository/pull/2", - userId: user.id, - taskId: task.id - }) - - // Send a PUT request to update a task solution - const taskSolutionUpdateRes = await agent - .patch('/tasksolutions/' + taskSolutionCreateRes.dataValues.id) - .set('Authorization', headers.authorization) - .expect('Content-Type', /json/) - .expect(200) - .send({ + const taskSolutionCreateRes = await models.TaskSolution.create({ isConnectedToGitHub: true, isAuthorOfPR: true, isPRMerged: true, @@ -249,15 +236,105 @@ describe("Task Solution", () => { pullRequestURL: "https://github.com/alexanmtz/test-repository/pull/2", userId: user.id, taskId: task.id + }) + + // Send a PUT request to update a task solution + const taskSolutionUpdateRes = await agent + .patch('/tasksolutions/' + taskSolutionCreateRes.dataValues.id) + .set('Authorization', headers.authorization) + .expect('Content-Type', /json/) + .expect(200) + .send({ + isConnectedToGitHub: true, + isAuthorOfPR: true, + isPRMerged: true, + isIssueClosed: true, + hasIssueReference: true, + pullRequestURL: "https://github.com/alexanmtz/test-repository/pull/2", + userId: user.id, + taskId: task.id + }); + expect(taskSolutionUpdateRes.body).to.have.property('isConnectedToGitHub'); + expect(taskSolutionUpdateRes.body).to.have.property('isAuthorOfPR'); + expect(taskSolutionUpdateRes.body).to.have.property('isPRMerged'); + expect(taskSolutionUpdateRes.body).to.have.property('isIssueClosed'); + expect(taskSolutionUpdateRes.body).to.have.property('hasIssueReference'); + } catch (err) { + // Fail the test if any error occurs + throw err; + } + }); + }) + describe("Fetch task solution data", () => { + it('should fetch task solution data', async () => { + try { + const solutionParams = { + pullRequestId: '2', + userId: 1, + repositoryName: 'test-repository', + owner: 'alexanmtz', + taskId: 1 + } + + nock('https://api.github.com') + .persist() + .get(`/repos/${solutionParams.owner}/${solutionParams.repositoryName}/pulls/${solutionParams.pullRequestId}`) + + .reply(200, { + user: { + login: 'alexanmtz' + }, + state: 'closed', + merged: true, + title: 'test PR', + body: 'closes #5 and #1 and #11111 and #1234' + }) + // Await the login process + const loginResponse = await registerAndLogin(agent, { + email: 'tasksolutiontest2@test.com', + provider: 'github', + provider_username: 'alexanmtz', + }); + const { body: user, headers } = loginResponse; + const task = await models.Task.create({ + url: 'https://github.com/alexanmtz/test-repository/issues/1', + userId: user.id, + status: 'closed' }); - expect(taskSolutionUpdateRes.body).to.have.property('isConnectedToGitHub'); - expect(taskSolutionUpdateRes.body).to.have.property('isAuthorOfPR'); - expect(taskSolutionUpdateRes.body).to.have.property('isPRMerged'); - expect(taskSolutionUpdateRes.body).to.have.property('isIssueClosed'); - expect(taskSolutionUpdateRes.body).to.have.property('hasIssueReference'); - } catch (err) { - // Fail the test if any error occurs - throw err; - } - }); + const taskAssignment = await models.Assign.create({ + userId: user.id, + TaskId: task.id + }); + + const params = { + pullRequestId: solutionParams.pullRequestId, + userId: solutionParams.userId, + repositoryName: solutionParams.repositoryName, + owner: solutionParams.owner, + taskId: solutionParams.taskId + } + // Send a GET request to fetch task solution data + const taskSolutionFetchDataRes = await agent + .get(`/tasksolutions/fetch/?owner=${params.owner}&repositoryName=${params.repositoryName}&pullRequestId=${params.pullRequestId}&userId=${params.userId}&taskId=${params.taskId}`) + .set('Authorization', headers.authorization) + .expect('Content-Type', /json/) + .expect(200) + //.send(params) + expect(taskSolutionFetchDataRes.body).to.have.property('isConnectedToGitHub'); + expect(taskSolutionFetchDataRes.body).to.have.property('isAuthorOfPR'); + expect(taskSolutionFetchDataRes.body).to.have.property('isPRMerged'); + expect(taskSolutionFetchDataRes.body).to.have.property('isIssueClosed'); + expect(taskSolutionFetchDataRes.body).to.have.property('hasIssueReference'); + + expect(taskSolutionFetchDataRes.body.isConnectedToGitHub).to.equal(true); + expect(taskSolutionFetchDataRes.body.isAuthorOfPR).to.equal(true); + expect(taskSolutionFetchDataRes.body.isPRMerged).to.equal(true); + expect(taskSolutionFetchDataRes.body.isIssueClosed).to.equal(true); + expect(taskSolutionFetchDataRes.body.hasIssueReference).to.equal(true); + } catch (err) { + // Fail the test if any error occurs + throw err; + } + }) + }) }) \ No newline at end of file