This commit is contained in:
root
2025-11-13 19:04:05 +03:00
commit 240d0aba5f
75129 changed files with 11118122 additions and 0 deletions

View File

@@ -0,0 +1,6 @@
module.exports = {
input: 'src/vote-service.js',
output: 'dist/vote-service.bundle.js',
namespace: 'BX.Vote.Service',
browserslist: true,
};

View File

@@ -0,0 +1,16 @@
<?php
if (!defined('B_PROLOG_INCLUDED') || B_PROLOG_INCLUDED !== true)
{
die();
}
return [
'js' => 'dist/vote-service.bundle.js',
'rel' => [
'main.core',
'ui.notification',
'vote.application',
],
'skip_core' => false,
];

View File

@@ -0,0 +1,202 @@
/* eslint-disable */
this.BX = this.BX || {};
this.BX.Vote = this.BX.Vote || {};
(function (exports,main_core,ui_notification,vote_application) {
'use strict';
const BackendModuleId = 'im';
const BackendEntityType = 'Bitrix\\Vote\\Attachment\\ImMessageConnector';
var _app = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("app");
var _load = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("load");
var _notifyAjaxError = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("notifyAjaxError");
var _getManyVotes = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("getManyVotes");
var _setLoading = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("setLoading");
var _sendVoteStopRequest = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("sendVoteStopRequest");
var _sendVoteRevokeRequest = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("sendVoteRevokeRequest");
var _sendBackendVote = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("sendBackendVote");
var _getEntityParams = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("getEntityParams");
var _updateStore = /*#__PURE__*/babelHelpers.classPrivateFieldLooseKey("updateStore");
class ImVoteService {
static init() {
return ImVoteService.getInstance();
}
static getInstance() {
if (!ImVoteService.instance) {
ImVoteService.instance = new ImVoteService();
}
return ImVoteService.instance;
}
constructor() {
Object.defineProperty(this, _updateStore, {
value: _updateStore2
});
Object.defineProperty(this, _getEntityParams, {
value: _getEntityParams2
});
Object.defineProperty(this, _sendBackendVote, {
value: _sendBackendVote2
});
Object.defineProperty(this, _sendVoteRevokeRequest, {
value: _sendVoteRevokeRequest2
});
Object.defineProperty(this, _sendVoteStopRequest, {
value: _sendVoteStopRequest2
});
Object.defineProperty(this, _setLoading, {
value: _setLoading2
});
Object.defineProperty(this, _getManyVotes, {
value: _getManyVotes2
});
Object.defineProperty(this, _notifyAjaxError, {
value: _notifyAjaxError2
});
Object.defineProperty(this, _load, {
value: _load2
});
Object.defineProperty(this, _app, {
writable: true,
value: null
});
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app] = vote_application.VoteApplication.init();
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app].subscribe('loadVotes', ({
data
}) => {
const {
entityIds,
voteIds
} = data;
babelHelpers.classPrivateFieldLooseBase(this, _load)[_load](entityIds, voteIds);
});
}
async sendVote(ballot, voteId, entityId) {
babelHelpers.classPrivateFieldLooseBase(this, _setLoading)[_setLoading]([voteId], true);
try {
var _response$data;
const response = await babelHelpers.classPrivateFieldLooseBase(this, _sendBackendVote)[_sendBackendVote](ballot, entityId);
if (!(response != null && (_response$data = response.data) != null && _response$data.attach)) {
babelHelpers.classPrivateFieldLooseBase(this, _setLoading)[_setLoading]([voteId], false);
return;
}
babelHelpers.classPrivateFieldLooseBase(this, _updateStore)[_updateStore](response.data.attach);
} catch (ex) {
babelHelpers.classPrivateFieldLooseBase(this, _setLoading)[_setLoading]([voteId], false);
throw ex;
}
}
async revokeVote(entityId, voteId) {
babelHelpers.classPrivateFieldLooseBase(this, _setLoading)[_setLoading]([voteId], true);
try {
var _response$data2;
const response = await babelHelpers.classPrivateFieldLooseBase(this, _sendVoteRevokeRequest)[_sendVoteRevokeRequest](entityId);
babelHelpers.classPrivateFieldLooseBase(this, _updateStore)[_updateStore](response == null ? void 0 : (_response$data2 = response.data) == null ? void 0 : _response$data2.attach);
return true;
} catch (response) {
babelHelpers.classPrivateFieldLooseBase(this, _setLoading)[_setLoading]([voteId], false);
console.error(response.errors[0].code);
throw response;
}
}
completeVote(entityId) {
return new Promise((resolve, reject) => {
babelHelpers.classPrivateFieldLooseBase(this, _sendVoteStopRequest)[_sendVoteStopRequest](entityId).then(() => {
resolve(true);
}).catch(response => {
console.error(response.errors[0].code);
reject(response);
});
});
}
}
async function _load2(entityIds, voteIds) {
try {
var _response$data3;
const response = await babelHelpers.classPrivateFieldLooseBase(this, _getManyVotes)[_getManyVotes](entityIds);
if (!(response != null && (_response$data3 = response.data) != null && _response$data3.items)) {
babelHelpers.classPrivateFieldLooseBase(this, _setLoading)[_setLoading](voteIds, false);
return;
}
response.data.items.forEach(item => {
babelHelpers.classPrivateFieldLooseBase(this, _updateStore)[_updateStore](item);
});
} catch (ex) {
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app].handleLoadError(entityIds);
babelHelpers.classPrivateFieldLooseBase(this, _notifyAjaxError)[_notifyAjaxError](ex);
babelHelpers.classPrivateFieldLooseBase(this, _setLoading)[_setLoading](voteIds, false);
}
}
function _notifyAjaxError2(ex) {
if (main_core.Type.isObject(ex) && main_core.Type.isArrayFilled(ex.errors)) {
var _ex$errors$0$message, _ex$errors$;
const content = (_ex$errors$0$message = ex == null ? void 0 : (_ex$errors$ = ex.errors[0]) == null ? void 0 : _ex$errors$.message) != null ? _ex$errors$0$message : 'Unexpected error';
ui_notification.UI.Notification.Center.notify({
content,
autoHideDelay: 4000
});
} else {
console.error(ex);
}
}
function _getManyVotes2(entityIds) {
return main_core.ajax.runAction('vote.AttachedVote.getMany', {
data: {
...babelHelpers.classPrivateFieldLooseBase(this, _getEntityParams)[_getEntityParams](),
entityIds
}
});
}
function _setLoading2(voteIds, isLoading) {
voteIds.forEach(voteId => {
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app].getStore().dispatch('vote/setLoadingStatus', {
isLoading,
voteId
});
});
}
function _sendVoteStopRequest2(entityId) {
return main_core.ajax.runAction('vote.AttachedVote.stop', {
data: {
...babelHelpers.classPrivateFieldLooseBase(this, _getEntityParams)[_getEntityParams](),
entityId
}
});
}
function _sendVoteRevokeRequest2(entityId) {
return main_core.ajax.runAction('vote.AttachedVote.recall', {
data: {
...babelHelpers.classPrivateFieldLooseBase(this, _getEntityParams)[_getEntityParams](),
entityId
}
});
}
function _sendBackendVote2(ballot, entityId) {
return main_core.ajax.runAction('vote.AttachedVote.vote', {
data: {
...babelHelpers.classPrivateFieldLooseBase(this, _getEntityParams)[_getEntityParams](),
entityId,
ballot
}
});
}
function _getEntityParams2() {
return {
moduleId: BackendModuleId,
entityType: BackendEntityType
};
}
function _updateStore2(payload) {
if (!payload) {
return;
}
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app].getStore().dispatch('vote/setCurrentUserVotes', payload.userAnswerMap);
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app].getStore().dispatch('vote/addVote', payload);
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app].getStore().dispatch('vote/addQuestion', payload.QUESTIONS);
babelHelpers.classPrivateFieldLooseBase(this, _app)[_app].getStore().dispatch('vote/addAnswer', payload.QUESTIONS);
}
exports.BackendModuleId = BackendModuleId;
exports.BackendEntityType = BackendEntityType;
exports.ImVoteService = ImVoteService;
}((this.BX.Vote.Service = this.BX.Vote.Service || {}),BX,BX,BX.Vote));
//# sourceMappingURL=vote-service.bundle.js.map

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -0,0 +1,2 @@
this.BX=this.BX||{};this.BX.Vote=this.BX.Vote||{};(function(e,s,t,a){"use strict";const r="im";const l="Bitrix\\Vote\\Attachment\\ImMessageConnector";var i=babelHelpers.classPrivateFieldLooseKey("app");var o=babelHelpers.classPrivateFieldLooseKey("load");var c=babelHelpers.classPrivateFieldLooseKey("notifyAjaxError");var n=babelHelpers.classPrivateFieldLooseKey("getManyVotes");var d=babelHelpers.classPrivateFieldLooseKey("setLoading");var b=babelHelpers.classPrivateFieldLooseKey("sendVoteStopRequest");var v=babelHelpers.classPrivateFieldLooseKey("sendVoteRevokeRequest");var h=babelHelpers.classPrivateFieldLooseKey("sendBackendVote");var p=babelHelpers.classPrivateFieldLooseKey("getEntityParams");var u=babelHelpers.classPrivateFieldLooseKey("updateStore");class P{static init(){return P.getInstance()}static getInstance(){if(!P.instance){P.instance=new P}return P.instance}constructor(){Object.defineProperty(this,u,{value:I});Object.defineProperty(this,p,{value:j});Object.defineProperty(this,h,{value:V});Object.defineProperty(this,v,{value:f});Object.defineProperty(this,b,{value:H});Object.defineProperty(this,d,{value:F});Object.defineProperty(this,n,{value:B});Object.defineProperty(this,c,{value:L});Object.defineProperty(this,o,{value:y});Object.defineProperty(this,i,{writable:true,value:null});babelHelpers.classPrivateFieldLooseBase(this,i)[i]=a.VoteApplication.init();babelHelpers.classPrivateFieldLooseBase(this,i)[i].subscribe("loadVotes",(({data:e})=>{const{entityIds:s,voteIds:t}=e;babelHelpers.classPrivateFieldLooseBase(this,o)[o](s,t)}))}async sendVote(e,s,t){babelHelpers.classPrivateFieldLooseBase(this,d)[d]([s],true);try{var a;const r=await babelHelpers.classPrivateFieldLooseBase(this,h)[h](e,t);if(!(r!=null&&(a=r.data)!=null&&a.attach)){babelHelpers.classPrivateFieldLooseBase(this,d)[d]([s],false);return}babelHelpers.classPrivateFieldLooseBase(this,u)[u](r.data.attach)}catch(e){babelHelpers.classPrivateFieldLooseBase(this,d)[d]([s],false);throw e}}async revokeVote(e,s){babelHelpers.classPrivateFieldLooseBase(this,d)[d]([s],true);try{var t;const s=await babelHelpers.classPrivateFieldLooseBase(this,v)[v](e);babelHelpers.classPrivateFieldLooseBase(this,u)[u](s==null?void 0:(t=s.data)==null?void 0:t.attach);return true}catch(e){babelHelpers.classPrivateFieldLooseBase(this,d)[d]([s],false);console.error(e.errors[0].code);throw e}}completeVote(e){return new Promise(((s,t)=>{babelHelpers.classPrivateFieldLooseBase(this,b)[b](e).then((()=>{s(true)})).catch((e=>{console.error(e.errors[0].code);t(e)}))}))}}async function y(e,s){try{var t;const a=await babelHelpers.classPrivateFieldLooseBase(this,n)[n](e);if(!(a!=null&&(t=a.data)!=null&&t.items)){babelHelpers.classPrivateFieldLooseBase(this,d)[d](s,false);return}a.data.items.forEach((e=>{babelHelpers.classPrivateFieldLooseBase(this,u)[u](e)}))}catch(t){babelHelpers.classPrivateFieldLooseBase(this,i)[i].handleLoadError(e);babelHelpers.classPrivateFieldLooseBase(this,c)[c](t);babelHelpers.classPrivateFieldLooseBase(this,d)[d](s,false)}}function L(e){if(s.Type.isObject(e)&&s.Type.isArrayFilled(e.errors)){var a,r;const s=(a=e==null?void 0:(r=e.errors[0])==null?void 0:r.message)!=null?a:"Unexpected error";t.UI.Notification.Center.notify({content:s,autoHideDelay:4e3})}else{console.error(e)}}function B(e){return s.ajax.runAction("vote.AttachedVote.getMany",{data:{...babelHelpers.classPrivateFieldLooseBase(this,p)[p](),entityIds:e}})}function F(e,s){e.forEach((e=>{babelHelpers.classPrivateFieldLooseBase(this,i)[i].getStore().dispatch("vote/setLoadingStatus",{isLoading:s,voteId:e})}))}function H(e){return s.ajax.runAction("vote.AttachedVote.stop",{data:{...babelHelpers.classPrivateFieldLooseBase(this,p)[p](),entityId:e}})}function f(e){return s.ajax.runAction("vote.AttachedVote.recall",{data:{...babelHelpers.classPrivateFieldLooseBase(this,p)[p](),entityId:e}})}function V(e,t){return s.ajax.runAction("vote.AttachedVote.vote",{data:{...babelHelpers.classPrivateFieldLooseBase(this,p)[p](),entityId:t,ballot:e}})}function j(){return{moduleId:r,entityType:l}}function I(e){if(!e){return}babelHelpers.classPrivateFieldLooseBase(this,i)[i].getStore().dispatch("vote/setCurrentUserVotes",e.userAnswerMap);babelHelpers.classPrivateFieldLooseBase(this,i)[i].getStore().dispatch("vote/addVote",e);babelHelpers.classPrivateFieldLooseBase(this,i)[i].getStore().dispatch("vote/addQuestion",e.QUESTIONS);babelHelpers.classPrivateFieldLooseBase(this,i)[i].getStore().dispatch("vote/addAnswer",e.QUESTIONS)}e.BackendModuleId=r;e.BackendEntityType=l;e.ImVoteService=P})(this.BX.Vote.Service=this.BX.Vote.Service||{},BX,BX,BX.Vote);
//# sourceMappingURL=vote-service.bundle.map.js

View File

@@ -0,0 +1,30 @@
export type BackendVote = {
ID: number;
COUNTER: number;
QUESTIONS: Record<string, BackendVoteQuestion>;
userAnswerMap: Record<QuestionId, Record<AnswerId, BackendUserAnswer>>; // userAnswerMap[questionId][answerId]
canEdit: boolean;
canVote: boolean;
canRevote: boolean;
isVoted: boolean;
};
export type BackendVoteQuestion = {
ID: number;
QUESTION: string;
COUNTER: number;
ANSWERS: Record<AnswerId, BackendVoteAnswer>;
};
export type BackendVoteAnswer = {
ID: number;
COUNTER: number;
MESSAGE: string;
PERCENT: number;
};
export type BackendUserAnswer = {
EVENT_ID: string; // but number value
EVENT_QUESTION_ID: string; // but number value
ANSWER_ID: string; // but number value
};

View File

@@ -0,0 +1,210 @@
import { Type, ajax } from 'main.core';
import { UI } from 'ui.notification';
import { type BaseEvent } from 'main.core.events';
import { VoteApplication } from 'vote.application';
import { type BackendVote } from './type';
export const BackendModuleId = 'im';
export const BackendEntityType = 'Bitrix\\Vote\\Attachment\\ImMessageConnector';
export type EntityAuthParams = {
moduleId: string,
entityType: string,
};
export class ImVoteService
{
static instance: ImVoteService;
#app: VoteApplication = null;
static init(): ImVoteService
{
return ImVoteService.getInstance();
}
static getInstance(): ImVoteService
{
if (!ImVoteService.instance)
{
ImVoteService.instance = new ImVoteService();
}
return ImVoteService.instance;
}
constructor()
{
this.#app = VoteApplication.init();
this.#app.subscribe('loadVotes', ({ data }: BaseEvent) => {
const { entityIds, voteIds } = data;
this.#load(entityIds, voteIds);
});
}
async #load(entityIds: Array<number>, voteIds: Array<string>): Promise<void>
{
try
{
const response = await this.#getManyVotes(entityIds);
if (!response?.data?.items)
{
this.#setLoading(voteIds, false);
return;
}
response.data.items.forEach((item) => {
this.#updateStore(item);
});
}
catch (ex)
{
this.#app.handleLoadError(entityIds);
this.#notifyAjaxError(ex);
this.#setLoading(voteIds, false);
}
}
#notifyAjaxError(ex): void
{
if (Type.isObject(ex) && Type.isArrayFilled(ex.errors))
{
const content = ex?.errors[0]?.message ?? 'Unexpected error';
UI.Notification.Center.notify({
content,
autoHideDelay: 4000,
});
}
else
{
console.error(ex);
}
}
#getManyVotes(entityIds: Array<number>): Promise
{
return ajax.runAction('vote.AttachedVote.getMany', {
data: {
...this.#getEntityParams(),
entityIds,
},
});
}
#setLoading(voteIds: Array<string>, isLoading: boolean): void
{
voteIds.forEach((voteId) => {
this.#app.getStore().dispatch('vote/setLoadingStatus', {
isLoading,
voteId,
});
});
}
async sendVote(ballot: Record<number, number[]>, voteId: string, entityId: number): Promise<void>
{
this.#setLoading([voteId], true);
try
{
const response = await this.#sendBackendVote(ballot, entityId);
if (!response?.data?.attach)
{
this.#setLoading([voteId], false);
return;
}
this.#updateStore(response.data.attach);
}
catch (ex)
{
this.#setLoading([voteId], false);
throw ex;
}
}
async revokeVote(entityId: number, voteId: string): Promise<boolean>
{
this.#setLoading([voteId], true);
try
{
const response = await this.#sendVoteRevokeRequest(entityId);
this.#updateStore(response?.data?.attach);
return true;
}
catch (response)
{
this.#setLoading([voteId], false);
console.error(response.errors[0].code);
throw response;
}
}
completeVote(entityId: number): Promise<boolean>
{
return new Promise((resolve, reject) => {
this.#sendVoteStopRequest(entityId)
.then(() => {
resolve(true);
})
.catch((response) => {
console.error(response.errors[0].code);
reject(response);
});
});
}
#sendVoteStopRequest(entityId: number): Promise<void>
{
return ajax.runAction('vote.AttachedVote.stop', {
data: {
...this.#getEntityParams(),
entityId,
},
});
}
#sendVoteRevokeRequest(entityId: number): Promise
{
return ajax.runAction('vote.AttachedVote.recall', {
data: {
...this.#getEntityParams(),
entityId,
},
});
}
#sendBackendVote(ballot: Record<number, number[]>, entityId: number): Promise
{
return ajax.runAction('vote.AttachedVote.vote', {
data: {
...this.#getEntityParams(),
entityId,
ballot,
},
});
}
#getEntityParams(): EntityAuthParams
{
return {
moduleId: BackendModuleId,
entityType: BackendEntityType,
};
}
#updateStore(payload: ?BackendVote): void
{
if (!payload)
{
return;
}
this.#app.getStore().dispatch('vote/setCurrentUserVotes', payload.userAnswerMap);
this.#app.getStore().dispatch('vote/addVote', payload);
this.#app.getStore().dispatch('vote/addQuestion', payload.QUESTIONS);
this.#app.getStore().dispatch('vote/addAnswer', payload.QUESTIONS);
}
}