From 53cfa3ea5ed0b98cf2430d3611ac4db9e5fe1888 Mon Sep 17 00:00:00 2001 From: Marc Velmer Date: Thu, 24 Oct 2024 16:05:50 +0200 Subject: [PATCH 1/3] Added new meta fields for questions and choices --- src/services/election.ts | 2 ++ src/types/election/election.ts | 8 ++++---- src/types/election/unpublished.ts | 8 +++++--- src/types/metadata/election.ts | 3 +++ test/integration/election.test.ts | 7 +++++++ 5 files changed, 21 insertions(+), 7 deletions(-) diff --git a/src/services/election.ts b/src/services/election.ts index a41755ed..d9e82bd2 100644 --- a/src/services/election.ts +++ b/src/services/election.ts @@ -233,7 +233,9 @@ export class ElectionService extends Service implements ElectionServicePropertie title: choice.title, value: choice.value, results: this.calculateChoiceResults(electionInfo.metadata.type.name, electionInfo.result, qIndex, cIndex), + ...(choice.meta && { meta: choice.meta }), })), + ...(question.meta && { meta: question.meta }), })), resultsType: electionInfo.metadata?.type, raw: electionInfo, diff --git a/src/types/election/election.ts b/src/types/election/election.ts index 8d3a46cf..d0423b48 100644 --- a/src/types/election/election.ts +++ b/src/types/election/election.ts @@ -107,7 +107,7 @@ interface JsonMap { } interface JsonArray extends Array {} -export type ElectionMeta = AnyJson | JsonArray | JsonMap; +export type CustomMeta = AnyJson | JsonArray | JsonMap; /** * Define election parameters. @@ -132,7 +132,7 @@ export interface IElectionParameters { /** * Metadata (anything added by the election creator) */ - meta?: ElectionMeta; + meta?: CustomMeta; startDate?: string | number | Date; endDate: string | number | Date; census: Census; @@ -172,7 +172,7 @@ export abstract class Election { protected _description: MultiLanguage; protected _header: string; protected _streamUri: string; - protected _meta: ElectionMeta; + protected _meta: CustomMeta; protected _startDate: Date; protected _endDate: Date; protected _electionType: IElectionType; @@ -232,7 +232,7 @@ export abstract class Election { return this._streamUri; } - get meta(): ElectionMeta { + get meta(): CustomMeta { return this._meta; } diff --git a/src/types/election/unpublished.ts b/src/types/election/unpublished.ts index fd0025f4..af09a971 100644 --- a/src/types/election/unpublished.ts +++ b/src/types/election/unpublished.ts @@ -8,7 +8,7 @@ import { } from '../metadata'; import invariant from 'tiny-invariant'; import { Census } from '../census'; -import { Election, ElectionMeta, IElectionParameters, IElectionType, IVoteType } from './election'; +import { Election, CustomMeta, IElectionParameters, IElectionType, IVoteType } from './election'; import { SDK_VERSION } from '../../version'; import { Asymmetric } from '../../util/encryption'; @@ -110,10 +110,12 @@ export class UnpublishedElection extends Election { return { title: question.title, description: question.description, + meta: question.meta, choices: question.choices.map((choice) => { return { title: choice.title, value: choice.value, + meta: choice.meta, }; }), }; @@ -204,11 +206,11 @@ export class UnpublishedElection extends Election { this._streamUri = value; } - get meta(): ElectionMeta { + get meta(): CustomMeta { return super.meta; } - set meta(value: ElectionMeta) { + set meta(value: CustomMeta) { invariant(!value || value['sdk'] === undefined, 'Field `sdk` is restricted in metadata'); this._meta = value; } diff --git a/src/types/metadata/election.ts b/src/types/metadata/election.ts index d93a6ffc..c86658ef 100644 --- a/src/types/metadata/election.ts +++ b/src/types/metadata/election.ts @@ -1,5 +1,6 @@ import { object, array, string, number } from 'yup'; import { MultiLanguage, multiLanguageStringKeys } from '../../util/lang'; +import { CustomMeta } from '../election'; /** * Asserts that the given metadata is valid. @@ -23,6 +24,7 @@ export function checkValidElectionMetadata(electionMetadata: ElectionMetadata): export interface IChoice { title: MultiLanguage; value: number; + meta?: CustomMeta; results?: string; answer?: number; } @@ -31,6 +33,7 @@ export interface IQuestion { title: MultiLanguage; description?: MultiLanguage; numAbstains?: string; + meta?: CustomMeta; choices: Array; } diff --git a/test/integration/election.test.ts b/test/integration/election.test.ts index 1c2a39af..d10f30e6 100644 --- a/test/integration/election.test.ts +++ b/test/integration/election.test.ts @@ -77,6 +77,10 @@ describe('Election integration tests', () => { }, }; + election.questions[0].meta = { image: 'https://img.io/test1.png' }; + election.questions[0].choices[0].meta = { image: 'https://img.io/test2.png' }; + election.questions[0].choices[1].meta = { image: 'https://img.io/test3.png' }; + await client.createAccount(); await client @@ -104,6 +108,9 @@ describe('Election integration tests', () => { version: SDK_VERSION, }, }); + expect(publishedElection.questions[0].meta).toStrictEqual({ image: 'https://img.io/test1.png' }); + expect(publishedElection.questions[0].choices[0].meta).toStrictEqual({ image: 'https://img.io/test2.png' }); + expect(publishedElection.questions[0].choices[1].meta).toStrictEqual({ image: 'https://img.io/test3.png' }); expect(publishedElection.get('census.type')).toEqual('spreadsheet'); expect(publishedElection.electionType).toStrictEqual({ interruptible: true, From da6fd4bc83361570d4f7a9dcb3f2f9fa7ae578a2 Mon Sep 17 00:00:00 2001 From: Marc Velmer Date: Fri, 25 Oct 2024 10:41:48 +0200 Subject: [PATCH 2/3] Fixed lint --- src/types/election/unpublished.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/types/election/unpublished.ts b/src/types/election/unpublished.ts index af09a971..88a932c1 100644 --- a/src/types/election/unpublished.ts +++ b/src/types/election/unpublished.ts @@ -115,7 +115,7 @@ export class UnpublishedElection extends Election { return { title: choice.title, value: choice.value, - meta: choice.meta, + meta: choice.meta, }; }), }; From 6fbd8ff8f6eec177cdc89b9ca4bdded176f5b74f Mon Sep 17 00:00:00 2001 From: Marc Velmer Date: Fri, 25 Oct 2024 11:29:36 +0200 Subject: [PATCH 3/3] Fixed `addQuestion` in `UnpublishedElection` for accepting metadata for questions and choices --- src/types/election/unpublished.ts | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/types/election/unpublished.ts b/src/types/election/unpublished.ts index 88a932c1..fb87beee 100644 --- a/src/types/election/unpublished.ts +++ b/src/types/election/unpublished.ts @@ -42,7 +42,11 @@ export class UnpublishedElection extends Election { public addQuestion( title: string | MultiLanguage, description: string | MultiLanguage, - choices: Array<{ title: string; value: number } | { title: MultiLanguage; value: number }> + choices: Array< + | { title: string; value: number; meta?: CustomMeta } + | { title: MultiLanguage; value: number; meta?: CustomMeta } + >, + meta?: CustomMeta ): UnpublishedElection { this._questions.push({ title: typeof title === 'string' ? { default: title } : title, @@ -51,8 +55,10 @@ export class UnpublishedElection extends Election { return { title: typeof choice.title === 'string' ? { default: choice.title } : choice.title, value: choice.value, + ...(choice.meta && { meta: choice.meta }), } as IChoice; }), + ...(meta && { meta: meta }), }); return this;