@glissandoo/lib 1.116.0 → 1.117.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/functions/event.d.ts +22 -0
- package/functions/eventPlayer.d.ts +2 -0
- package/functions/eventoPayout.d.ts +70 -0
- package/functions/eventoPayout.js +2 -0
- package/functions/groupModule.d.ts +13 -0
- package/functions/groupModule.js +2 -0
- package/functions/groupPayment.d.ts +62 -0
- package/functions/groupPayment.js +2 -0
- package/functions/groupPayoutRule.d.ts +18 -0
- package/functions/groupPayoutRule.js +2 -0
- package/functions/index.d.ts +12 -0
- package/functions/index.js +12 -0
- package/functions/regions.js +12 -0
- package/helpers/appScenes.d.ts +2 -0
- package/helpers/appScenes.js +2 -0
- package/helpers/currency.d.ts +4 -0
- package/helpers/currency.js +277 -0
- package/helpers/errors.d.ts +7 -1
- package/helpers/errors.js +6 -0
- package/helpers/paymentForecast.d.ts +37 -0
- package/helpers/paymentForecast.js +58 -0
- package/helpers/payoutRules.d.ts +45 -0
- package/helpers/payoutRules.js +166 -0
- package/lang/ca.json +6 -0
- package/lang/de.json +6 -0
- package/lang/en.json +6 -0
- package/lang/es.json +6 -0
- package/lang/eu.json +6 -0
- package/lang/fr.json +6 -0
- package/lang/gl.json +6 -0
- package/lang/it.json +6 -0
- package/lang/nl.json +6 -0
- package/lang/pt.json +6 -0
- package/models/Evento/Player/index.d.ts +1 -0
- package/models/Evento/Player/index.js +3 -0
- package/models/Evento/Player/types.d.ts +1 -0
- package/models/Evento/index.d.ts +2 -0
- package/models/Evento/index.js +6 -0
- package/models/Evento/types.d.ts +13 -1
- package/models/Evento/types.js +3 -0
- package/models/Group/Payment/index.d.ts +45 -0
- package/models/Group/Payment/index.js +110 -0
- package/models/Group/Payment/supabase.d.ts +16 -0
- package/models/Group/Payment/supabase.js +46 -0
- package/models/Group/Payment/types.d.ts +96 -0
- package/models/Group/Payment/types.js +26 -0
- package/models/Group/index.d.ts +8 -1
- package/models/Group/index.js +19 -0
- package/models/Group/types.d.ts +30 -0
- package/models/Group/types.js +14 -1
- package/models/Notification/types.d.ts +4 -1
- package/models/Notification/types.js +3 -0
- package/package.json +1 -1
- package/types/payoutRule.d.ts +126 -0
- package/types/payoutRule.js +34 -0
- package/types/payoutRule.ts +132 -0
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const types_1 = require("./types");
|
|
4
|
+
/**
|
|
5
|
+
* Plain-object model for a `group_payment` row. Mirrors the previous
|
|
6
|
+
* Firestore-backed model API so dashboard components keep working with
|
|
7
|
+
* `payment.foo` getters. Build with `new GroupPayment(rowData)` where
|
|
8
|
+
* `rowData` is the deserialized DB record (or a snapshot built from a
|
|
9
|
+
* realtime callback).
|
|
10
|
+
*
|
|
11
|
+
* Timestamp getters return native `Date` objects so consumers can call
|
|
12
|
+
* `.getTime()` / format them with `date-fns`/`dayjs` directly.
|
|
13
|
+
*/
|
|
14
|
+
class GroupPayment {
|
|
15
|
+
constructor(data) {
|
|
16
|
+
this.id = data.id;
|
|
17
|
+
this._data = data;
|
|
18
|
+
this.exists = true;
|
|
19
|
+
}
|
|
20
|
+
get data() {
|
|
21
|
+
return this._data;
|
|
22
|
+
}
|
|
23
|
+
get groupId() {
|
|
24
|
+
return this._data.groupId;
|
|
25
|
+
}
|
|
26
|
+
get type() {
|
|
27
|
+
return this._data.type;
|
|
28
|
+
}
|
|
29
|
+
get isIncome() {
|
|
30
|
+
return this.type === types_1.GroupPaymentType.Income;
|
|
31
|
+
}
|
|
32
|
+
get isExpense() {
|
|
33
|
+
return this.type === types_1.GroupPaymentType.Expense;
|
|
34
|
+
}
|
|
35
|
+
get eventId() {
|
|
36
|
+
return this._data.eventId || null;
|
|
37
|
+
}
|
|
38
|
+
get playerId() {
|
|
39
|
+
return this._data.playerId || null;
|
|
40
|
+
}
|
|
41
|
+
get concept() {
|
|
42
|
+
return this._data.concept || '';
|
|
43
|
+
}
|
|
44
|
+
get assignedTo() {
|
|
45
|
+
return this._data.assignedTo || '';
|
|
46
|
+
}
|
|
47
|
+
get totalAmount() {
|
|
48
|
+
return this._data.totalAmount;
|
|
49
|
+
}
|
|
50
|
+
get baseAmount() {
|
|
51
|
+
return this._data.baseAmount ?? this._data.totalAmount;
|
|
52
|
+
}
|
|
53
|
+
get appliedRules() {
|
|
54
|
+
return this._data.appliedRules || [];
|
|
55
|
+
}
|
|
56
|
+
get currency() {
|
|
57
|
+
return this._data.currency || 'EUR';
|
|
58
|
+
}
|
|
59
|
+
get displayTotal() {
|
|
60
|
+
if (this.totalAmount === null)
|
|
61
|
+
return '— €';
|
|
62
|
+
const sign = this.isExpense ? '-' : '';
|
|
63
|
+
return `${sign}${this.totalAmount} €`;
|
|
64
|
+
}
|
|
65
|
+
get status() {
|
|
66
|
+
return this._data.status;
|
|
67
|
+
}
|
|
68
|
+
get isPending() {
|
|
69
|
+
return this.status === types_1.GroupPaymentStatus.Pending;
|
|
70
|
+
}
|
|
71
|
+
get isPaid() {
|
|
72
|
+
return this.status === types_1.GroupPaymentStatus.Paid;
|
|
73
|
+
}
|
|
74
|
+
get isCancelled() {
|
|
75
|
+
return this.status === types_1.GroupPaymentStatus.Cancelled;
|
|
76
|
+
}
|
|
77
|
+
get paymentMethod() {
|
|
78
|
+
return this._data.paymentMethod || null;
|
|
79
|
+
}
|
|
80
|
+
get history() {
|
|
81
|
+
return this._data.history || [];
|
|
82
|
+
}
|
|
83
|
+
get historyOrdered() {
|
|
84
|
+
return this.history
|
|
85
|
+
.slice()
|
|
86
|
+
.sort((a, b) => new Date(a.changedAt).getTime() < new Date(b.changedAt).getTime() ? 1 : -1);
|
|
87
|
+
}
|
|
88
|
+
get paidAt() {
|
|
89
|
+
return this._data.paidAt ? new Date(this._data.paidAt) : null;
|
|
90
|
+
}
|
|
91
|
+
get paidBy() {
|
|
92
|
+
return this._data.paidBy || null;
|
|
93
|
+
}
|
|
94
|
+
get note() {
|
|
95
|
+
return this._data.note || null;
|
|
96
|
+
}
|
|
97
|
+
get createdAt() {
|
|
98
|
+
return new Date(this._data.createdAt);
|
|
99
|
+
}
|
|
100
|
+
get createdBy() {
|
|
101
|
+
return this._data.createdBy;
|
|
102
|
+
}
|
|
103
|
+
get editedAt() {
|
|
104
|
+
return this._data.editedAt ? new Date(this._data.editedAt) : null;
|
|
105
|
+
}
|
|
106
|
+
get editedBy() {
|
|
107
|
+
return this._data.editedBy || null;
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
exports.default = GroupPayment;
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { Database } from '../../../types/supabase';
|
|
2
|
+
import { GroupPaymentData, GroupPaymentHistoryItem } from './types';
|
|
3
|
+
export type GroupPaymentRow = Database['public']['Tables']['group_payment']['Row'];
|
|
4
|
+
export type GroupPaymentInsert = Database['public']['Tables']['group_payment']['Insert'];
|
|
5
|
+
export type GroupPaymentUpdate = Database['public']['Tables']['group_payment']['Update'];
|
|
6
|
+
export type GroupPaymentHistoryRow = Database['public']['Tables']['group_payment_history']['Row'];
|
|
7
|
+
export type GroupPaymentHistoryInsert = Database['public']['Tables']['group_payment_history']['Insert'];
|
|
8
|
+
export declare const GROUP_PAYMENT_TABLE: "group_payment";
|
|
9
|
+
export declare const GROUP_PAYMENT_HISTORY_TABLE: "group_payment_history";
|
|
10
|
+
/**
|
|
11
|
+
* Convert a raw `group_payment` DB row into the canonical `GroupPaymentData`
|
|
12
|
+
* shape consumed by the `GroupPayment` model. `history` defaults to an empty
|
|
13
|
+
* array; hydrate it from the history table when needed.
|
|
14
|
+
*/
|
|
15
|
+
export declare function rowToGroupPaymentData(row: GroupPaymentRow, history?: GroupPaymentHistoryItem[]): GroupPaymentData;
|
|
16
|
+
export declare function historyRowToItem(row: GroupPaymentHistoryRow): GroupPaymentHistoryItem;
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.historyRowToItem = exports.rowToGroupPaymentData = exports.GROUP_PAYMENT_HISTORY_TABLE = exports.GROUP_PAYMENT_TABLE = void 0;
|
|
4
|
+
exports.GROUP_PAYMENT_TABLE = 'group_payment';
|
|
5
|
+
exports.GROUP_PAYMENT_HISTORY_TABLE = 'group_payment_history';
|
|
6
|
+
/**
|
|
7
|
+
* Convert a raw `group_payment` DB row into the canonical `GroupPaymentData`
|
|
8
|
+
* shape consumed by the `GroupPayment` model. `history` defaults to an empty
|
|
9
|
+
* array; hydrate it from the history table when needed.
|
|
10
|
+
*/
|
|
11
|
+
function rowToGroupPaymentData(row, history = []) {
|
|
12
|
+
return {
|
|
13
|
+
id: row.id,
|
|
14
|
+
groupId: row.groupId,
|
|
15
|
+
type: row.type,
|
|
16
|
+
eventId: row.eventId,
|
|
17
|
+
playerId: row.playerId,
|
|
18
|
+
concept: row.concept,
|
|
19
|
+
assignedTo: row.assignedTo,
|
|
20
|
+
totalAmount: row.totalAmount === null ? null : Number(row.totalAmount),
|
|
21
|
+
baseAmount: row.baseAmount === null ? null : Number(row.baseAmount),
|
|
22
|
+
appliedRules: row.appliedRules ?? [],
|
|
23
|
+
currency: row.currency,
|
|
24
|
+
status: row.status,
|
|
25
|
+
history,
|
|
26
|
+
paymentMethod: row.paymentMethod ?? null,
|
|
27
|
+
paidAt: row.paidAt,
|
|
28
|
+
paidBy: row.paidBy,
|
|
29
|
+
note: row.note,
|
|
30
|
+
createdAt: row.createdAt,
|
|
31
|
+
createdBy: row.createdBy,
|
|
32
|
+
editedAt: row.updatedAt,
|
|
33
|
+
editedBy: row.editedBy,
|
|
34
|
+
};
|
|
35
|
+
}
|
|
36
|
+
exports.rowToGroupPaymentData = rowToGroupPaymentData;
|
|
37
|
+
function historyRowToItem(row) {
|
|
38
|
+
return {
|
|
39
|
+
action: row.action,
|
|
40
|
+
oldValue: row.old_value,
|
|
41
|
+
newValue: row.new_value,
|
|
42
|
+
changedAt: row.changed_at,
|
|
43
|
+
changedBy: row.changed_by,
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
exports.historyRowToItem = historyRowToItem;
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import { AppliedRuleEntry } from '../../../helpers/payoutRules';
|
|
2
|
+
export declare enum GroupPaymentType {
|
|
3
|
+
Income = "income",
|
|
4
|
+
Expense = "expense"
|
|
5
|
+
}
|
|
6
|
+
export declare enum GroupPaymentStatus {
|
|
7
|
+
Pending = "pending",
|
|
8
|
+
Paid = "paid",
|
|
9
|
+
Cancelled = "cancelled"
|
|
10
|
+
}
|
|
11
|
+
export declare enum GroupPaymentMethod {
|
|
12
|
+
Cash = "cash",
|
|
13
|
+
Transfer = "transfer"
|
|
14
|
+
}
|
|
15
|
+
export declare enum GroupPaymentHistoryAction {
|
|
16
|
+
Status = "status",
|
|
17
|
+
Amount = "amount",
|
|
18
|
+
Concept = "concept",
|
|
19
|
+
Method = "method"
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Unified audit entry for a payment. Each entry records one change to a
|
|
23
|
+
* single field (status, amount, concept or method) with the previous and
|
|
24
|
+
* new values, who performed it and when.
|
|
25
|
+
*
|
|
26
|
+
* For the very first entry (creation), `oldValue` is `null` and `newValue`
|
|
27
|
+
* holds the initial status.
|
|
28
|
+
*
|
|
29
|
+
* Timestamps are ISO 8601 strings (Postgres `timestamptz` representation).
|
|
30
|
+
*/
|
|
31
|
+
export interface GroupPaymentHistoryItem {
|
|
32
|
+
action: GroupPaymentHistoryAction;
|
|
33
|
+
oldValue: string | number | null;
|
|
34
|
+
newValue: string | number | null;
|
|
35
|
+
changedAt: string;
|
|
36
|
+
changedBy: string;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Flat payment record at the group level — represents both incomes
|
|
40
|
+
* (e.g. event payout owed to a musician) and expenses (e.g. fuel reimbursement,
|
|
41
|
+
* supplier invoice). Persisted in Postgres (`public.group_payment`).
|
|
42
|
+
*
|
|
43
|
+
* `totalAmount` is always positive; the sign is encoded by `type`.
|
|
44
|
+
*
|
|
45
|
+
* `assignedTo` is a free-form string: it may be a userId (a player), a groupId
|
|
46
|
+
* (the band itself), or any free string (external supplier name).
|
|
47
|
+
*
|
|
48
|
+
* `playerId` is only set when the payment originates from rollcall — it links
|
|
49
|
+
* the payment back to the attendee via `eventPlayer.paymentId`.
|
|
50
|
+
*
|
|
51
|
+
* Timestamps are ISO 8601 strings.
|
|
52
|
+
*/
|
|
53
|
+
export interface GroupPaymentData {
|
|
54
|
+
id: string;
|
|
55
|
+
groupId: string;
|
|
56
|
+
type: GroupPaymentType;
|
|
57
|
+
eventId: string | null;
|
|
58
|
+
playerId: string | null;
|
|
59
|
+
concept: string;
|
|
60
|
+
assignedTo: string;
|
|
61
|
+
/**
|
|
62
|
+
* Positive amount. `null` only while the payment is Pending (e.g. payouts
|
|
63
|
+
* waiting for the admin to fix a per-member share). Transitioning to Paid
|
|
64
|
+
* requires a concrete number.
|
|
65
|
+
*/
|
|
66
|
+
totalAmount: number | null;
|
|
67
|
+
/**
|
|
68
|
+
* `importByMember` at the moment the payment was created/recomputed.
|
|
69
|
+
* Equals `totalAmount` when no rules apply. `null` mirrors `totalAmount`
|
|
70
|
+
* when the per-member share is "to be determined".
|
|
71
|
+
*/
|
|
72
|
+
baseAmount: number | null;
|
|
73
|
+
/**
|
|
74
|
+
* Snapshot of the event payout rules that affected this player, ordered
|
|
75
|
+
* by `order`. Empty array when no rules matched. Used for traceability
|
|
76
|
+
* and to drive the breakdown tooltip in the UI.
|
|
77
|
+
*/
|
|
78
|
+
appliedRules: AppliedRuleEntry[];
|
|
79
|
+
currency: string;
|
|
80
|
+
status: GroupPaymentStatus;
|
|
81
|
+
/**
|
|
82
|
+
* In-memory audit trail loaded from `group_payment_history`. Empty `[]`
|
|
83
|
+
* when not hydrated. Use the model's `historyOrdered` getter for a desc
|
|
84
|
+
* view.
|
|
85
|
+
*/
|
|
86
|
+
history: GroupPaymentHistoryItem[];
|
|
87
|
+
paymentMethod: GroupPaymentMethod | null;
|
|
88
|
+
paidAt: string | null;
|
|
89
|
+
paidBy: string | null;
|
|
90
|
+
note: string | null;
|
|
91
|
+
createdAt: string;
|
|
92
|
+
createdBy: string;
|
|
93
|
+
editedAt: string | null;
|
|
94
|
+
editedBy: string | null;
|
|
95
|
+
}
|
|
96
|
+
export type AGroupPaymentData = GroupPaymentData;
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.GroupPaymentHistoryAction = exports.GroupPaymentMethod = exports.GroupPaymentStatus = exports.GroupPaymentType = void 0;
|
|
4
|
+
var GroupPaymentType;
|
|
5
|
+
(function (GroupPaymentType) {
|
|
6
|
+
GroupPaymentType["Income"] = "income";
|
|
7
|
+
GroupPaymentType["Expense"] = "expense";
|
|
8
|
+
})(GroupPaymentType = exports.GroupPaymentType || (exports.GroupPaymentType = {}));
|
|
9
|
+
var GroupPaymentStatus;
|
|
10
|
+
(function (GroupPaymentStatus) {
|
|
11
|
+
GroupPaymentStatus["Pending"] = "pending";
|
|
12
|
+
GroupPaymentStatus["Paid"] = "paid";
|
|
13
|
+
GroupPaymentStatus["Cancelled"] = "cancelled";
|
|
14
|
+
})(GroupPaymentStatus = exports.GroupPaymentStatus || (exports.GroupPaymentStatus = {}));
|
|
15
|
+
var GroupPaymentMethod;
|
|
16
|
+
(function (GroupPaymentMethod) {
|
|
17
|
+
GroupPaymentMethod["Cash"] = "cash";
|
|
18
|
+
GroupPaymentMethod["Transfer"] = "transfer";
|
|
19
|
+
})(GroupPaymentMethod = exports.GroupPaymentMethod || (exports.GroupPaymentMethod = {}));
|
|
20
|
+
var GroupPaymentHistoryAction;
|
|
21
|
+
(function (GroupPaymentHistoryAction) {
|
|
22
|
+
GroupPaymentHistoryAction["Status"] = "status";
|
|
23
|
+
GroupPaymentHistoryAction["Amount"] = "amount";
|
|
24
|
+
GroupPaymentHistoryAction["Concept"] = "concept";
|
|
25
|
+
GroupPaymentHistoryAction["Method"] = "method";
|
|
26
|
+
})(GroupPaymentHistoryAction = exports.GroupPaymentHistoryAction || (exports.GroupPaymentHistoryAction = {}));
|
package/models/Group/index.d.ts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
import { DocumentReference } from '@google-cloud/firestore';
|
|
2
2
|
import { PlansGroup } from '../../helpers/plans';
|
|
3
3
|
import { LanguagesTypes } from '../../lang';
|
|
4
|
+
import { GroupPayoutRuleEntry } from '../../types/payoutRule';
|
|
4
5
|
import { EventPlayerStatus } from '../Evento/Player/types';
|
|
5
6
|
import { DocumentModel } from '../Model';
|
|
6
7
|
import GroupBasic from './basic';
|
|
7
|
-
import { AGroupCustomField, AGroupInstrument, AdminPermissions, CustomGroupInstrument, GroupConfigShowAttendanceToMembers, GroupData, GroupStatus, SocialNetwork } from './types';
|
|
8
|
+
import { AGroupCustomField, AGroupInstrument, AdminPermissions, CustomGroupInstrument, GroupConfigShowAttendanceToMembers, GroupData, GroupModuleData, GroupModuleId, GroupModules, GroupStatus, SocialNetwork } from './types';
|
|
8
9
|
export default class Group extends GroupBasic<GroupData> {
|
|
9
10
|
constructor(doc: DocumentModel, lang?: LanguagesTypes);
|
|
10
11
|
get owner(): DocumentReference;
|
|
@@ -32,6 +33,8 @@ export default class Group extends GroupBasic<GroupData> {
|
|
|
32
33
|
get eventTotalCount(): number;
|
|
33
34
|
get communicationCount(): number;
|
|
34
35
|
get country(): string;
|
|
36
|
+
get currency(): string;
|
|
37
|
+
get currencySymbol(): string;
|
|
35
38
|
get activePlayers(): string[];
|
|
36
39
|
get playersList(): {
|
|
37
40
|
id: string;
|
|
@@ -130,4 +133,8 @@ export default class Group extends GroupBasic<GroupData> {
|
|
|
130
133
|
get customFieldsList(): AGroupCustomField[];
|
|
131
134
|
get inventoryId(): string;
|
|
132
135
|
get coverURL(): string | null;
|
|
136
|
+
get modules(): GroupModules;
|
|
137
|
+
getModule(id: GroupModuleId): GroupModuleData | null;
|
|
138
|
+
isModuleEnabled(id: GroupModuleId): boolean;
|
|
139
|
+
get payoutRules(): GroupPayoutRuleEntry[];
|
|
133
140
|
}
|
package/models/Group/index.js
CHANGED
|
@@ -6,6 +6,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
6
6
|
const date_fns_1 = require("date-fns");
|
|
7
7
|
const lodash_1 = require("lodash");
|
|
8
8
|
const collections_1 = require("../../helpers/collections");
|
|
9
|
+
const currency_1 = require("../../helpers/currency");
|
|
9
10
|
const glissandooAdmin_1 = require("../../helpers/glissandooAdmin");
|
|
10
11
|
const orders_1 = require("../../helpers/instruments/orders");
|
|
11
12
|
const objects_1 = require("../../helpers/objects");
|
|
@@ -108,6 +109,12 @@ class Group extends basic_1.default {
|
|
|
108
109
|
get country() {
|
|
109
110
|
return this.data.country || 'ES';
|
|
110
111
|
}
|
|
112
|
+
get currency() {
|
|
113
|
+
return this.data.currency || currency_1.DEFAULT_CURRENCY;
|
|
114
|
+
}
|
|
115
|
+
get currencySymbol() {
|
|
116
|
+
return (0, currency_1.getCurrencySymbol)(this.currency, this.lang);
|
|
117
|
+
}
|
|
111
118
|
get activePlayers() {
|
|
112
119
|
return Object.keys(this.players);
|
|
113
120
|
}
|
|
@@ -301,5 +308,17 @@ class Group extends basic_1.default {
|
|
|
301
308
|
get coverURL() {
|
|
302
309
|
return this.data.coverURL || null;
|
|
303
310
|
}
|
|
311
|
+
get modules() {
|
|
312
|
+
return this.data.modules || {};
|
|
313
|
+
}
|
|
314
|
+
getModule(id) {
|
|
315
|
+
return this.modules[id] || null;
|
|
316
|
+
}
|
|
317
|
+
isModuleEnabled(id) {
|
|
318
|
+
return !!this.getModule(id)?.enabled;
|
|
319
|
+
}
|
|
320
|
+
get payoutRules() {
|
|
321
|
+
return this.data.payoutRules || [];
|
|
322
|
+
}
|
|
304
323
|
}
|
|
305
324
|
exports.default = Group;
|
package/models/Group/types.d.ts
CHANGED
|
@@ -3,6 +3,7 @@ import { CustomInstrumentId, DefaultInstrumentId } from '../../helpers/instrumen
|
|
|
3
3
|
import { MusicStyleType } from '../../helpers/musicStyles';
|
|
4
4
|
import { PlansGroup } from '../../helpers/plans';
|
|
5
5
|
import { CreatedOn } from '../../helpers/types';
|
|
6
|
+
import { GroupPayoutRuleEntry } from '../../types/payoutRule';
|
|
6
7
|
import { EventPlayerStatus } from '../Evento/Player/types';
|
|
7
8
|
import { EventType } from '../Evento/types';
|
|
8
9
|
import { PlayerBasicData } from '../Player/types';
|
|
@@ -97,6 +98,32 @@ export declare enum GroupStatus {
|
|
|
97
98
|
Inactive = "inactive",
|
|
98
99
|
Deleted = "deleted"
|
|
99
100
|
}
|
|
101
|
+
export declare enum GroupModuleId {
|
|
102
|
+
Payout = "payout",
|
|
103
|
+
Inventory = "inventory",
|
|
104
|
+
Vacancies = "vacancies",
|
|
105
|
+
Partnership = "partnership",
|
|
106
|
+
MusicSchool = "musicSchool"
|
|
107
|
+
}
|
|
108
|
+
export declare enum GroupModulePlan {
|
|
109
|
+
Free = "free",
|
|
110
|
+
Paid = "paid"
|
|
111
|
+
}
|
|
112
|
+
export interface GroupModuleData {
|
|
113
|
+
enabled: boolean;
|
|
114
|
+
activatedAt: Timestamp | null;
|
|
115
|
+
activatedBy: string | null;
|
|
116
|
+
disabledAt: Timestamp | null;
|
|
117
|
+
disabledBy: string | null;
|
|
118
|
+
plan: GroupModulePlan;
|
|
119
|
+
/**
|
|
120
|
+
* Reserved for future Stripe integration. Not used yet.
|
|
121
|
+
*/
|
|
122
|
+
subscriptionId: string | null;
|
|
123
|
+
stripeCustomerId: string | null;
|
|
124
|
+
stripeSubscriptionId: string | null;
|
|
125
|
+
}
|
|
126
|
+
export type GroupModules = Partial<Record<GroupModuleId, GroupModuleData>>;
|
|
100
127
|
export declare enum SocialNetwork {
|
|
101
128
|
Facebook = "facebook",
|
|
102
129
|
Twitter = "twitter",
|
|
@@ -242,6 +269,7 @@ export interface GroupData extends GroupBasicData {
|
|
|
242
269
|
eventCount: Record<EventType, number>;
|
|
243
270
|
communicationCount: number;
|
|
244
271
|
country: string;
|
|
272
|
+
currency: string;
|
|
245
273
|
instruments: GroupInstruments;
|
|
246
274
|
metadata: Record<string, string>;
|
|
247
275
|
firstAnswerAt: Timestamp | null;
|
|
@@ -254,6 +282,8 @@ export interface GroupData extends GroupBasicData {
|
|
|
254
282
|
customFields: Record<string, GroupCustomField>;
|
|
255
283
|
inventoryId: string;
|
|
256
284
|
coverURL: string | null;
|
|
285
|
+
modules: GroupModules;
|
|
286
|
+
payoutRules: GroupPayoutRuleEntry[];
|
|
257
287
|
readonly createdOn: CreatedOn;
|
|
258
288
|
readonly owner: DocumentReference;
|
|
259
289
|
readonly createdAt: Timestamp;
|
package/models/Group/types.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.GroupRepertoireTagDefault = exports.GroupRepertoireTagReserved = exports.SocialNetwork = exports.GroupStatus = exports.GroupConfigShowAttendanceToMembers = exports.GroupConfigSitesKey = exports.GroupConfigKey = exports.AdminPermissions = exports.GroupCustomFieldType = exports.GroupHistoryAction = void 0;
|
|
3
|
+
exports.GroupRepertoireTagDefault = exports.GroupRepertoireTagReserved = exports.SocialNetwork = exports.GroupModulePlan = exports.GroupModuleId = exports.GroupStatus = exports.GroupConfigShowAttendanceToMembers = exports.GroupConfigSitesKey = exports.GroupConfigKey = exports.AdminPermissions = exports.GroupCustomFieldType = exports.GroupHistoryAction = void 0;
|
|
4
4
|
var GroupHistoryAction;
|
|
5
5
|
(function (GroupHistoryAction) {
|
|
6
6
|
GroupHistoryAction["Created"] = "created";
|
|
@@ -74,6 +74,19 @@ var GroupStatus;
|
|
|
74
74
|
GroupStatus["Inactive"] = "inactive";
|
|
75
75
|
GroupStatus["Deleted"] = "deleted";
|
|
76
76
|
})(GroupStatus = exports.GroupStatus || (exports.GroupStatus = {}));
|
|
77
|
+
var GroupModuleId;
|
|
78
|
+
(function (GroupModuleId) {
|
|
79
|
+
GroupModuleId["Payout"] = "payout";
|
|
80
|
+
GroupModuleId["Inventory"] = "inventory";
|
|
81
|
+
GroupModuleId["Vacancies"] = "vacancies";
|
|
82
|
+
GroupModuleId["Partnership"] = "partnership";
|
|
83
|
+
GroupModuleId["MusicSchool"] = "musicSchool";
|
|
84
|
+
})(GroupModuleId = exports.GroupModuleId || (exports.GroupModuleId = {}));
|
|
85
|
+
var GroupModulePlan;
|
|
86
|
+
(function (GroupModulePlan) {
|
|
87
|
+
GroupModulePlan["Free"] = "free";
|
|
88
|
+
GroupModulePlan["Paid"] = "paid";
|
|
89
|
+
})(GroupModulePlan = exports.GroupModulePlan || (exports.GroupModulePlan = {}));
|
|
77
90
|
var SocialNetwork;
|
|
78
91
|
(function (SocialNetwork) {
|
|
79
92
|
SocialNetwork["Facebook"] = "facebook";
|
|
@@ -148,7 +148,10 @@ export declare enum NotificationActions {
|
|
|
148
148
|
GroupOnboardingEvent = "group.onboarding.event",
|
|
149
149
|
OfferApplicantAdd = "offer.applicant.add",
|
|
150
150
|
OfferSelectApplicant = "offer.select.applicant",
|
|
151
|
-
OfferAlarm = "offer.alarm"
|
|
151
|
+
OfferAlarm = "offer.alarm",
|
|
152
|
+
GroupPaymentPaid = "groupPayment.paid",
|
|
153
|
+
GroupPaymentCancelled = "groupPayment.cancelled",
|
|
154
|
+
GroupPaymentAmountChanged = "groupPayment.amountChanged"
|
|
152
155
|
}
|
|
153
156
|
export declare enum NotificationActionsFilter {
|
|
154
157
|
EventCreated = "eventCreated",
|
|
@@ -146,6 +146,9 @@ var NotificationActions;
|
|
|
146
146
|
NotificationActions["OfferApplicantAdd"] = "offer.applicant.add";
|
|
147
147
|
NotificationActions["OfferSelectApplicant"] = "offer.select.applicant";
|
|
148
148
|
NotificationActions["OfferAlarm"] = "offer.alarm";
|
|
149
|
+
NotificationActions["GroupPaymentPaid"] = "groupPayment.paid";
|
|
150
|
+
NotificationActions["GroupPaymentCancelled"] = "groupPayment.cancelled";
|
|
151
|
+
NotificationActions["GroupPaymentAmountChanged"] = "groupPayment.amountChanged";
|
|
149
152
|
})(NotificationActions = exports.NotificationActions || (exports.NotificationActions = {}));
|
|
150
153
|
var NotificationActionsFilter;
|
|
151
154
|
(function (NotificationActionsFilter) {
|
package/package.json
CHANGED
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
import { Timestamp } from '@google-cloud/firestore';
|
|
2
|
+
/**
|
|
3
|
+
* Shared types for the payout rules engine.
|
|
4
|
+
* Rules live at two levels:
|
|
5
|
+
* - Group level (templates, can be `pinned` to auto-apply to new events)
|
|
6
|
+
* - Event level (snapshot copied from the group when payout is initialized)
|
|
7
|
+
*/
|
|
8
|
+
export declare enum PayoutRuleType {
|
|
9
|
+
EntityShare = "entityShare",
|
|
10
|
+
DefaultExpense = "defaultExpense",
|
|
11
|
+
PlayerMultiplier = "playerMultiplier",
|
|
12
|
+
PlayerBonus = "playerBonus",
|
|
13
|
+
PlayerFixed = "playerFixed",
|
|
14
|
+
PlayerExclude = "playerExclude"
|
|
15
|
+
}
|
|
16
|
+
export declare enum PayoutRuleConditionOperator {
|
|
17
|
+
Eq = "eq",
|
|
18
|
+
Neq = "neq",
|
|
19
|
+
Gt = "gt",
|
|
20
|
+
Gte = "gte",
|
|
21
|
+
Lt = "lt",
|
|
22
|
+
Lte = "lte",
|
|
23
|
+
In = "in",
|
|
24
|
+
Nin = "nin"
|
|
25
|
+
}
|
|
26
|
+
export type PayoutRuleConditionFieldKind = 'mainInstrument' | 'isGuest' | `custom.${string}`;
|
|
27
|
+
export type PayoutRuleConditionValue = string | number | boolean | string[] | number[] | null;
|
|
28
|
+
export interface PayoutRuleCondition {
|
|
29
|
+
field: PayoutRuleConditionFieldKind;
|
|
30
|
+
operator: PayoutRuleConditionOperator;
|
|
31
|
+
value: PayoutRuleConditionValue;
|
|
32
|
+
}
|
|
33
|
+
export declare enum PayoutRuleEntityShareMode {
|
|
34
|
+
Fixed = "fixed",
|
|
35
|
+
Percentage = "percentage"
|
|
36
|
+
}
|
|
37
|
+
export interface PayoutRuleEntityShareEffect {
|
|
38
|
+
mode: PayoutRuleEntityShareMode;
|
|
39
|
+
value: number;
|
|
40
|
+
}
|
|
41
|
+
export interface PayoutRuleDefaultExpenseEffect {
|
|
42
|
+
concept: string;
|
|
43
|
+
amount: number;
|
|
44
|
+
/**
|
|
45
|
+
* `null` = expense remains general (reduces the shared pot).
|
|
46
|
+
* Future: could materialize per-attendee expenses.
|
|
47
|
+
*/
|
|
48
|
+
assignTo: null;
|
|
49
|
+
}
|
|
50
|
+
export interface PayoutRulePlayerMultiplierEffect {
|
|
51
|
+
multiplier: number;
|
|
52
|
+
}
|
|
53
|
+
export interface PayoutRulePlayerBonusEffect {
|
|
54
|
+
amount: number;
|
|
55
|
+
}
|
|
56
|
+
export interface PayoutRulePlayerFixedEffect {
|
|
57
|
+
amount: number;
|
|
58
|
+
}
|
|
59
|
+
export type PayoutRulePlayerExcludeEffect = Record<string, never>;
|
|
60
|
+
export type PayoutRuleEffect = {
|
|
61
|
+
type: PayoutRuleType.EntityShare;
|
|
62
|
+
data: PayoutRuleEntityShareEffect;
|
|
63
|
+
} | {
|
|
64
|
+
type: PayoutRuleType.DefaultExpense;
|
|
65
|
+
data: PayoutRuleDefaultExpenseEffect;
|
|
66
|
+
} | {
|
|
67
|
+
type: PayoutRuleType.PlayerMultiplier;
|
|
68
|
+
data: PayoutRulePlayerMultiplierEffect;
|
|
69
|
+
} | {
|
|
70
|
+
type: PayoutRuleType.PlayerBonus;
|
|
71
|
+
data: PayoutRulePlayerBonusEffect;
|
|
72
|
+
} | {
|
|
73
|
+
type: PayoutRuleType.PlayerFixed;
|
|
74
|
+
data: PayoutRulePlayerFixedEffect;
|
|
75
|
+
} | {
|
|
76
|
+
type: PayoutRuleType.PlayerExclude;
|
|
77
|
+
data: PayoutRulePlayerExcludeEffect;
|
|
78
|
+
};
|
|
79
|
+
/**
|
|
80
|
+
* Common shape stored in both group templates and event snapshots.
|
|
81
|
+
*/
|
|
82
|
+
export interface PayoutRuleBaseData {
|
|
83
|
+
name: string;
|
|
84
|
+
description: string | null;
|
|
85
|
+
order: number;
|
|
86
|
+
conditions: PayoutRuleCondition[];
|
|
87
|
+
effect: PayoutRuleEffect;
|
|
88
|
+
createdAt: Timestamp;
|
|
89
|
+
createdBy: string;
|
|
90
|
+
editedAt: Timestamp | null;
|
|
91
|
+
editedBy: string | null;
|
|
92
|
+
}
|
|
93
|
+
/**
|
|
94
|
+
* Helper used by the pure rules engine. Holds the minimal data
|
|
95
|
+
* required to evaluate conditions against a player.
|
|
96
|
+
*/
|
|
97
|
+
export interface PayoutRulePlayerInput {
|
|
98
|
+
id: string;
|
|
99
|
+
mainInstrument: string;
|
|
100
|
+
isGuest: boolean;
|
|
101
|
+
customFields: Record<string, string | number | boolean | null>;
|
|
102
|
+
}
|
|
103
|
+
export interface GroupPayoutRuleEntry {
|
|
104
|
+
id: string;
|
|
105
|
+
name: string;
|
|
106
|
+
order: number;
|
|
107
|
+
pinned: boolean;
|
|
108
|
+
conditions: PayoutRuleCondition[];
|
|
109
|
+
effect: PayoutRuleEffect;
|
|
110
|
+
createdAt: Timestamp;
|
|
111
|
+
createdBy: string;
|
|
112
|
+
editedAt: Timestamp | null;
|
|
113
|
+
editedBy: string | null;
|
|
114
|
+
}
|
|
115
|
+
export interface EventoPayoutRuleEntry {
|
|
116
|
+
id: string;
|
|
117
|
+
name: string;
|
|
118
|
+
order: number;
|
|
119
|
+
sourceGroupRuleId: string | null;
|
|
120
|
+
conditions: PayoutRuleCondition[];
|
|
121
|
+
effect: PayoutRuleEffect;
|
|
122
|
+
createdAt: Timestamp;
|
|
123
|
+
createdBy: string;
|
|
124
|
+
editedAt: Timestamp | null;
|
|
125
|
+
editedBy: string | null;
|
|
126
|
+
}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.PayoutRuleEntityShareMode = exports.PayoutRuleConditionOperator = exports.PayoutRuleType = void 0;
|
|
4
|
+
/**
|
|
5
|
+
* Shared types for the payout rules engine.
|
|
6
|
+
* Rules live at two levels:
|
|
7
|
+
* - Group level (templates, can be `pinned` to auto-apply to new events)
|
|
8
|
+
* - Event level (snapshot copied from the group when payout is initialized)
|
|
9
|
+
*/
|
|
10
|
+
var PayoutRuleType;
|
|
11
|
+
(function (PayoutRuleType) {
|
|
12
|
+
PayoutRuleType["EntityShare"] = "entityShare";
|
|
13
|
+
PayoutRuleType["DefaultExpense"] = "defaultExpense";
|
|
14
|
+
PayoutRuleType["PlayerMultiplier"] = "playerMultiplier";
|
|
15
|
+
PayoutRuleType["PlayerBonus"] = "playerBonus";
|
|
16
|
+
PayoutRuleType["PlayerFixed"] = "playerFixed";
|
|
17
|
+
PayoutRuleType["PlayerExclude"] = "playerExclude";
|
|
18
|
+
})(PayoutRuleType = exports.PayoutRuleType || (exports.PayoutRuleType = {}));
|
|
19
|
+
var PayoutRuleConditionOperator;
|
|
20
|
+
(function (PayoutRuleConditionOperator) {
|
|
21
|
+
PayoutRuleConditionOperator["Eq"] = "eq";
|
|
22
|
+
PayoutRuleConditionOperator["Neq"] = "neq";
|
|
23
|
+
PayoutRuleConditionOperator["Gt"] = "gt";
|
|
24
|
+
PayoutRuleConditionOperator["Gte"] = "gte";
|
|
25
|
+
PayoutRuleConditionOperator["Lt"] = "lt";
|
|
26
|
+
PayoutRuleConditionOperator["Lte"] = "lte";
|
|
27
|
+
PayoutRuleConditionOperator["In"] = "in";
|
|
28
|
+
PayoutRuleConditionOperator["Nin"] = "nin";
|
|
29
|
+
})(PayoutRuleConditionOperator = exports.PayoutRuleConditionOperator || (exports.PayoutRuleConditionOperator = {}));
|
|
30
|
+
var PayoutRuleEntityShareMode;
|
|
31
|
+
(function (PayoutRuleEntityShareMode) {
|
|
32
|
+
PayoutRuleEntityShareMode["Fixed"] = "fixed";
|
|
33
|
+
PayoutRuleEntityShareMode["Percentage"] = "percentage";
|
|
34
|
+
})(PayoutRuleEntityShareMode = exports.PayoutRuleEntityShareMode || (exports.PayoutRuleEntityShareMode = {}));
|