From 7f182a5927ffd5cab3ebfbb4af39ac2d4f1e1e21 Mon Sep 17 00:00:00 2001 From: ogerly Date: Thu, 16 Feb 2023 15:21:55 +0100 Subject: [PATCH 01/17] change fetchPolicy, add scripts.update --- frontend/src/pages/Community.vue | 2 +- package.json | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/frontend/src/pages/Community.vue b/frontend/src/pages/Community.vue index 113bcd4e4..7427aa2fa 100644 --- a/frontend/src/pages/Community.vue +++ b/frontend/src/pages/Community.vue @@ -122,13 +122,13 @@ export default { query() { return listAllContributions }, - fetchPolicy: 'network-only', variables() { return { currentPage: this.currentPageAll, pageSize: this.pageSizeAll, } }, + fetchPolicy: 'no-cache', update({ listAllContributions }) { this.contributionCountAll = listAllContributions.contributionCount this.itemsAll = listAllContributions.contributionList diff --git a/package.json b/package.json index 2220c1a85..85b8dfe53 100644 --- a/package.json +++ b/package.json @@ -7,7 +7,8 @@ "author": "Ulf Gebhardt ", "license": "Apache-2.0", "scripts": { - "release": "scripts/release.sh" + "release": "scripts/release.sh", + "update": "cd admin && yarn && cd ../backend && yarn && cd ../database && yarn && cd ../dht-node && yarn && cd ../e2e-tests && yarn && cd ../federation && yarn && cd ../frontend && yarn" }, "dependencies": { "auto-changelog": "^2.4.0", From 6567babd3b516b459e9a5bbf4a522120de37f807 Mon Sep 17 00:00:00 2001 From: ogerly Date: Thu, 16 Feb 2023 15:28:40 +0100 Subject: [PATCH 02/17] remove package json script update --- package.json | 1 - 1 file changed, 1 deletion(-) diff --git a/package.json b/package.json index 85b8dfe53..959e4d6d5 100644 --- a/package.json +++ b/package.json @@ -8,7 +8,6 @@ "license": "Apache-2.0", "scripts": { "release": "scripts/release.sh", - "update": "cd admin && yarn && cd ../backend && yarn && cd ../database && yarn && cd ../dht-node && yarn && cd ../e2e-tests && yarn && cd ../federation && yarn && cd ../frontend && yarn" }, "dependencies": { "auto-changelog": "^2.4.0", From 10327e9fd507342b240b4c91e5d0f00201d0342c Mon Sep 17 00:00:00 2001 From: ogerly Date: Thu, 16 Feb 2023 15:39:33 +0100 Subject: [PATCH 03/17] remove comma --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 959e4d6d5..2220c1a85 100644 --- a/package.json +++ b/package.json @@ -7,7 +7,7 @@ "author": "Ulf Gebhardt ", "license": "Apache-2.0", "scripts": { - "release": "scripts/release.sh", + "release": "scripts/release.sh" }, "dependencies": { "auto-changelog": "^2.4.0", From 3cc549473653142db43f529c9c92cfbd7f559f03 Mon Sep 17 00:00:00 2001 From: Moriz Wahl Date: Mon, 20 Feb 2023 14:24:42 +0100 Subject: [PATCH 04/17] refactor(backend): remove admin create contributions --- backend/src/auth/RIGHTS.ts | 1 - .../graphql/model/AdminCreateContributions.ts | 19 ------------- .../graphql/resolver/ContributionResolver.ts | 28 ------------------- 3 files changed, 48 deletions(-) delete mode 100644 backend/src/graphql/model/AdminCreateContributions.ts diff --git a/backend/src/auth/RIGHTS.ts b/backend/src/auth/RIGHTS.ts index 98f6cf118..8b0e82c86 100644 --- a/backend/src/auth/RIGHTS.ts +++ b/backend/src/auth/RIGHTS.ts @@ -42,7 +42,6 @@ export enum RIGHTS { DELETE_USER = 'DELETE_USER', UNDELETE_USER = 'UNDELETE_USER', ADMIN_CREATE_CONTRIBUTION = 'ADMIN_CREATE_CONTRIBUTION', - ADMIN_CREATE_CONTRIBUTIONS = 'ADMIN_CREATE_CONTRIBUTIONS', ADMIN_UPDATE_CONTRIBUTION = 'ADMIN_UPDATE_CONTRIBUTION', ADMIN_DELETE_CONTRIBUTION = 'ADMIN_DELETE_CONTRIBUTION', LIST_UNCONFIRMED_CONTRIBUTIONS = 'LIST_UNCONFIRMED_CONTRIBUTIONS', diff --git a/backend/src/graphql/model/AdminCreateContributions.ts b/backend/src/graphql/model/AdminCreateContributions.ts deleted file mode 100644 index aa402733a..000000000 --- a/backend/src/graphql/model/AdminCreateContributions.ts +++ /dev/null @@ -1,19 +0,0 @@ -import { ObjectType, Field } from 'type-graphql' - -@ObjectType() -export class AdminCreateContributions { - constructor() { - this.success = false - this.successfulContribution = [] - this.failedContribution = [] - } - - @Field(() => Boolean) - success: boolean - - @Field(() => [String]) - successfulContribution: string[] - - @Field(() => [String]) - failedContribution: string[] -} diff --git a/backend/src/graphql/resolver/ContributionResolver.ts b/backend/src/graphql/resolver/ContributionResolver.ts index c2f0d7d23..2e3367e1f 100644 --- a/backend/src/graphql/resolver/ContributionResolver.ts +++ b/backend/src/graphql/resolver/ContributionResolver.ts @@ -8,7 +8,6 @@ import { UserContact } from '@entity/UserContact' import { User as DbUser } from '@entity/User' import { Transaction as DbTransaction } from '@entity/Transaction' -import { AdminCreateContributions } from '@model/AdminCreateContributions' import { AdminUpdateContribution } from '@model/AdminUpdateContribution' import { Contribution, ContributionListResult } from '@model/Contribution' import { Decay } from '@model/Decay' @@ -329,33 +328,6 @@ export class ContributionResolver { return getUserCreation(emailContact.userId, clientTimezoneOffset) } - @Authorized([RIGHTS.ADMIN_CREATE_CONTRIBUTIONS]) - @Mutation(() => AdminCreateContributions) - async adminCreateContributions( - @Arg('pendingCreations', () => [AdminCreateContributionArgs]) - contributions: AdminCreateContributionArgs[], - @Ctx() context: Context, - ): Promise { - let success = false - const successfulContribution: string[] = [] - const failedContribution: string[] = [] - for (const contribution of contributions) { - await this.adminCreateContribution(contribution, context) - .then(() => { - successfulContribution.push(contribution.email) - success = true - }) - .catch(() => { - failedContribution.push(contribution.email) - }) - } - return { - success, - successfulContribution, - failedContribution, - } - } - @Authorized([RIGHTS.ADMIN_UPDATE_CONTRIBUTION]) @Mutation(() => AdminUpdateContribution) async adminUpdateContribution( From 72165ac99d5418c075c0126534fd3281515c6b69 Mon Sep 17 00:00:00 2001 From: Moriz Wahl Date: Mon, 20 Feb 2023 14:39:05 +0100 Subject: [PATCH 05/17] fix test --- .../resolver/ContributionResolver.test.ts | 117 +----------------- 1 file changed, 6 insertions(+), 111 deletions(-) diff --git a/backend/src/graphql/resolver/ContributionResolver.test.ts b/backend/src/graphql/resolver/ContributionResolver.test.ts index b56180c45..de049129a 100644 --- a/backend/src/graphql/resolver/ContributionResolver.test.ts +++ b/backend/src/graphql/resolver/ContributionResolver.test.ts @@ -13,7 +13,6 @@ import { denyContribution, confirmContribution, adminCreateContribution, - adminCreateContributions, adminUpdateContribution, adminDeleteContribution, login, @@ -1653,21 +1652,6 @@ describe('ContributionResolver', () => { }) }) - describe('adminCreateContributions', () => { - it('returns an error', async () => { - await expect( - mutate({ - mutation: adminCreateContributions, - variables: { pendingCreations: [variables] }, - }), - ).resolves.toEqual( - expect.objectContaining({ - errors: [new GraphQLError('401 Unauthorized')], - }), - ) - }) - }) - describe('adminUpdateContribution', () => { it('returns an error', async () => { await expect( @@ -1761,21 +1745,6 @@ describe('ContributionResolver', () => { }) }) - describe('adminCreateContributions', () => { - it('returns an error', async () => { - await expect( - mutate({ - mutation: adminCreateContributions, - variables: { pendingCreations: [variables] }, - }), - ).resolves.toEqual( - expect.objectContaining({ - errors: [new GraphQLError('401 Unauthorized')], - }), - ) - }) - }) - describe('adminUpdateContribution', () => { it('returns an error', async () => { await expect( @@ -2120,59 +2089,13 @@ describe('ContributionResolver', () => { }) }) - describe('adminCreateContributions', () => { + describe('adminUpdateContribution', () => { // at this point we have this data in DB: // bibi@bloxberg.de: [1000, 1000, 800] // peter@lustig.de: [1000, 600, 1000] // stephen@hawking.uk: [1000, 1000, 1000] - deleted // garrick@ollivander.com: [1000, 1000, 1000] - not activated - const massCreationVariables = [ - 'bibi@bloxberg.de', - 'peter@lustig.de', - 'stephen@hawking.uk', - 'garrick@ollivander.com', - 'bob@baumeister.de', - ].map((email) => { - return { - email, - amount: new Decimal(500), - memo: 'Grundeinkommen', - creationDate: contributionDateFormatter(new Date()), - } - }) - - it('returns success, two successful creation and three failed creations', async () => { - await expect( - mutate({ - mutation: adminCreateContributions, - variables: { pendingCreations: massCreationVariables }, - }), - ).resolves.toEqual( - expect.objectContaining({ - data: { - adminCreateContributions: { - success: true, - successfulContribution: ['bibi@bloxberg.de', 'peter@lustig.de'], - failedContribution: [ - 'stephen@hawking.uk', - 'garrick@ollivander.com', - 'bob@baumeister.de', - ], - }, - }, - }), - ) - }) - }) - - describe('adminUpdateContribution', () => { - // at this I expect to have this data in DB: - // bibi@bloxberg.de: [1000, 1000, 300] - // peter@lustig.de: [1000, 600, 500] - // stephen@hawking.uk: [1000, 1000, 1000] - deleted - // garrick@ollivander.com: [1000, 1000, 1000] - not activated - describe('user for creation to update does not exist', () => { it('throws an error', async () => { jest.clearAllMocks() @@ -2386,7 +2309,7 @@ describe('ContributionResolver', () => { date: expect.any(String), memo: 'Das war leider zu Viel!', amount: '200', - creation: ['1000', '800', '500'], + creation: ['1000', '800', '1000'], }, }, }), @@ -2424,29 +2347,12 @@ describe('ContributionResolver', () => { memo: 'Das war leider zu Viel!', amount: '200', moderator: admin.id, - creation: ['1000', '800', '500'], - }), - expect.objectContaining({ - id: expect.any(Number), - firstName: 'Peter', - lastName: 'Lustig', - email: 'peter@lustig.de', - date: expect.any(String), - memo: 'Grundeinkommen', - amount: '500', - moderator: admin.id, - creation: ['1000', '800', '500'], + creation: ['1000', '800', '1000'], }), expect.not.objectContaining({ - id: expect.any(Number), - firstName: 'Bibi', - lastName: 'Bloxberg', email: 'bibi@bloxberg.de', - date: expect.any(String), memo: 'Test contribution to delete', amount: '100', - moderator: null, - creation: ['1000', '1000', '90'], }), expect.objectContaining({ id: expect.any(Number), @@ -2457,7 +2363,7 @@ describe('ContributionResolver', () => { memo: 'Test PENDING contribution update', amount: '10', moderator: null, - creation: ['1000', '1000', '90'], + creation: ['1000', '1000', '590'], }), expect.objectContaining({ id: expect.any(Number), @@ -2468,18 +2374,7 @@ describe('ContributionResolver', () => { memo: 'Test IN_PROGRESS contribution', amount: '100', moderator: null, - creation: ['1000', '1000', '90'], - }), - expect.objectContaining({ - id: expect.any(Number), - firstName: 'Bibi', - lastName: 'Bloxberg', - email: 'bibi@bloxberg.de', - date: expect.any(String), - memo: 'Grundeinkommen', - amount: '500', - moderator: admin.id, - creation: ['1000', '1000', '90'], + creation: ['1000', '1000', '590'], }), expect.objectContaining({ id: expect.any(Number), @@ -2490,7 +2385,7 @@ describe('ContributionResolver', () => { memo: 'Aktives Grundeinkommen', amount: '200', moderator: admin.id, - creation: ['1000', '1000', '90'], + creation: ['1000', '1000', '590'], }), ]), }, From 9d60e414adfc4712991d0a004f2061401e4dbfd6 Mon Sep 17 00:00:00 2001 From: Moriz Wahl Date: Mon, 20 Feb 2023 14:53:58 +0100 Subject: [PATCH 06/17] remove admin create contributions from admin interface --- admin/src/components/CreationFormular.spec.js | 117 ------------------ admin/src/components/CreationFormular.vue | 97 ++++----------- .../src/components/Tables/SearchUserTable.vue | 1 - admin/src/graphql/adminCreateContributions.js | 11 -- 4 files changed, 26 insertions(+), 200 deletions(-) delete mode 100644 admin/src/graphql/adminCreateContributions.js diff --git a/admin/src/components/CreationFormular.spec.js b/admin/src/components/CreationFormular.spec.js index 6e4c1dc6e..36bfd33f8 100644 --- a/admin/src/components/CreationFormular.spec.js +++ b/admin/src/components/CreationFormular.spec.js @@ -1,7 +1,6 @@ import { mount } from '@vue/test-utils' import CreationFormular from './CreationFormular.vue' import { adminCreateContribution } from '../graphql/adminCreateContribution' -import { adminCreateContributions } from '../graphql/adminCreateContributions' import { toastErrorSpy, toastSuccessSpy } from '../../test/testSetup' const localVue = global.localVue @@ -328,122 +327,6 @@ describe('CreationFormular', () => { }) }) }) - - describe('mass creation with success', () => { - beforeEach(async () => { - jest.clearAllMocks() - apolloMutateMock.mockResolvedValue({ - data: { - adminCreateContributions: { - success: true, - successfulContribution: ['bob@baumeister.de', 'bibi@bloxberg.de'], - failedContribution: [], - }, - }, - }) - await wrapper.setProps({ - type: 'massCreation', - creation: [200, 400, 600], - items: [{ email: 'bob@baumeister.de' }, { email: 'bibi@bloxberg.de' }], - }) - await wrapper.findAll('input[type="radio"]').at(1).setChecked() - await wrapper.find('textarea').setValue('Test mass create coins') - await wrapper.find('input[type="number"]').setValue(200) - await wrapper.find('.test-submit').trigger('click') - }) - - it('calls the API', () => { - expect(apolloMutateMock).toBeCalledWith( - expect.objectContaining({ - mutation: adminCreateContributions, - variables: { - pendingCreations: [ - { - email: 'bob@baumeister.de', - creationDate: getCreationDate(1), - amount: 200, - memo: 'Test mass create coins', - }, - { - email: 'bibi@bloxberg.de', - creationDate: getCreationDate(1), - amount: 200, - memo: 'Test mass create coins', - }, - ], - }, - }), - ) - }) - - it('updates open creations in store', () => { - expect(stateCommitMock).toBeCalledWith('openCreationsPlus', 2) - }) - - it('emits remove-all-bookmark', () => { - expect(wrapper.emitted('remove-all-bookmark')).toBeTruthy() - }) - }) - - describe('mass creation with success but all failed', () => { - beforeEach(async () => { - jest.clearAllMocks() - apolloMutateMock.mockResolvedValue({ - data: { - adminCreateContributions: { - success: true, - successfulContribution: [], - failedContribution: ['bob@baumeister.de', 'bibi@bloxberg.de'], - }, - }, - }) - await wrapper.setProps({ - type: 'massCreation', - creation: [200, 400, 600], - items: [{ email: 'bob@baumeister.de' }, { email: 'bibi@bloxberg.de' }], - }) - await wrapper.findAll('input[type="radio"]').at(1).setChecked() - await wrapper.find('textarea').setValue('Test mass create coins') - await wrapper.find('input[type="number"]').setValue(200) - await wrapper.find('.test-submit').trigger('click') - }) - - it('updates open creations in store', () => { - expect(stateCommitMock).toBeCalledWith('openCreationsPlus', 0) - }) - - it('emits remove all bookmarks', () => { - expect(wrapper.emitted('remove-all-bookmark')).toBeTruthy() - }) - - it('emits toast failed creations with two emails', () => { - expect(wrapper.emitted('toast-failed-creations')).toEqual([ - [['bob@baumeister.de', 'bibi@bloxberg.de']], - ]) - }) - }) - - describe('mass creation with error', () => { - beforeEach(async () => { - jest.clearAllMocks() - apolloMutateMock.mockRejectedValue({ - message: 'Oh no!', - }) - await wrapper.setProps({ - type: 'massCreation', - creation: [200, 400, 600], - items: [{ email: 'bob@baumeister.de' }, { email: 'bibi@bloxberg.de' }], - }) - await wrapper.findAll('input[type="radio"]').at(1).setChecked() - await wrapper.find('textarea').setValue('Test mass create coins') - await wrapper.find('input[type="number"]').setValue(200) - await wrapper.find('.test-submit').trigger('click') - }) - - it('toasts an error message', () => { - expect(toastErrorSpy).toBeCalledWith('Oh no!') - }) - }) }) }) }) diff --git a/admin/src/components/CreationFormular.vue b/admin/src/components/CreationFormular.vue index 2201838de..137b46400 100644 --- a/admin/src/components/CreationFormular.vue +++ b/admin/src/components/CreationFormular.vue @@ -86,16 +86,11 @@