VYPR
Moderate severityNVD Advisory· Published Sep 20, 2022· Updated May 29, 2025

Cross-site Scripting (XSS) - Stored in yetiforcecompany/yetiforcecrm

CVE-2022-2924

Description

Cross-site Scripting (XSS) - Stored in GitHub repository yetiforcecompany/yetiforcecrm prior to 6.3.

Affected packages

Versions sourced from the GitHub Security Advisory.

PackageAffected versionsPatched versions
yetiforce/yetiforce-crmPackagist
<= 6.4.0

Affected products

1

Patches

1
b716ecea3407

Improved data display on some widgets

https://github.com/yetiforcecompany/yetiforcecrmRadosław SkrzypczakAug 22, 2022via ghsa
16 files changed · +30 30
  • config/version.php+2 2 modified
    @@ -1,7 +1,7 @@
     <?php
     
     return [
    -	'appVersion' => '6.4.0',
    -	'patchVersion' => '2022.08.19',
    +	'appVersion' => '6.4.1',
    +	'patchVersion' => '2022.08.22',
     	'lib_roundcube' => '0.3.0',
     ];
    
  • layouts/basic/modules/Vtiger/dashboards/CalendarActivitiesContents.tpl+3 3 modified
    @@ -17,7 +17,7 @@
     	</style>
     	<div>
     		{foreach from=$ACTIVITIES key=INDEX item=ACTIVITY}
    -			<div class="changeActivity u-cursor-pointer" data-url="{$ACTIVITY->getActivityStateModalUrl()}" accesskey="">
    +			<div class="changeActivity u-cursor-pointer" data-url="{$ACTIVITY->getActivityStateModalUrl()|escape}" accesskey="">
     				<div class="rowActivities">
     					<div class="d-flex mb-1">
     						<div class="">
    @@ -47,7 +47,7 @@
     						<div class="w-100 mx-1">
     							{\App\TextUtils::textTruncate($ACTIVITY->getDisplayName(), $NAMELENGTH)}
     							{if $CONTRACTOR}
    -								<br /><small class="small-a">{\App\Language::translate('LBL_FOR')}&nbsp;<strong>{$ACTIVITY->getDisplayValue('contractor')}</strong></small>, <strong><small class='small-a'><a href="{$CONTRACTOR->getDetailViewUrl()}">{\App\TextUtils::textTruncate($CONTRACTOR->getDisplayName(), $HREFNAMELENGTH)}</a></small></strong>
    +								<br /><small class="small-a">{\App\Language::translate('LBL_FOR')}&nbsp;<strong>{$ACTIVITY->getDisplayValue('contractor')}</strong></small>, <strong><small class='small-a'><a href="{$CONTRACTOR->getDetailViewUrl()|escape}">{\App\TextUtils::textTruncate($CONTRACTOR->getDisplayName(), $HREFNAMELENGTH)}</a></small></strong>
     							{/if}
     							{if $LINK}
     								<br /><small class="small-a">{\App\Language::translate('LBL_FOR')}&nbsp;<strong>{$ACTIVITY->getDisplayValue('link')}</strong></small>
    @@ -84,7 +84,7 @@
     		{/foreach}
     		{if $PAGING_MODEL->get('nextPageExists') eq 'true'}
     			<div class="float-right padding5">
    -				<button type="button" class="btn btn-sm btn-primary showMoreHistory" data-url="{$WIDGET->getUrl()}&page={$PAGING_MODEL->getNextPage()}">
    +				<button type="button" class="btn btn-sm btn-primary showMoreHistory" data-url="{$WIDGET->getUrl()|escape}&page={$PAGING_MODEL->getNextPage()}">
     					{\App\Language::translate('LBL_MORE')}
     				</button>
     			</div>
    
  • layouts/basic/modules/Vtiger/dashboards/CalendarContents.tpl+2 2 modified
    @@ -1,8 +1,8 @@
     {*<!-- {[The file is published on the basis of YetiForce Public License 5.0 that can be found in the following directory: licenses/LicenseEN.txt or yetiforce.com]} -->*}
     {strip}
     	<input type="hidden" id="currentView" value="{$VIEW}" />
    -	<input type="hidden" id="activity_view" value="{$CURRENT_USER->getDetail('activity_view')}" />
    -	<input type="hidden" id="date_format" value="{$CURRENT_USER->getDetail('date_format')}" />
    +	<input type="hidden" id="activity_view" value="{$CURRENT_USER->getDetail('activity_view')|escape}" />
    +	<input type="hidden" id="date_format" value="{$CURRENT_USER->getDetail('date_format')|escape}" />
     	<input type="hidden" id="defaultDate" value="{$DEFAULTDATE}" />
     	<div class="js-calendar__container" data-js="fullcalendar"></div>
     {/strip}
    
  • layouts/basic/modules/Vtiger/dashboards/Calendar.tpl+1 1 modified
    @@ -60,7 +60,7 @@
     							</label>
     						</div>
     						<input type="hidden" value="current" data-current="{implode('##',$CURRENT_STATUS)}"
    -							data-history="{implode(',',$HISTORY_STATUS)}" class="widgetFilterSwitch" {if !empty($WIDGET_DATA['defaultFilter'])} data-default-filter="{$WIDGET_DATA['defaultFilter']}" {/if}>
    +							data-history="{implode(',',$HISTORY_STATUS)|escape}" class="widgetFilterSwitch" {if !empty($WIDGET_DATA['defaultFilter'])} data-default-filter="{$WIDGET_DATA['defaultFilter']|escape}" {/if}>
     					{/if}
     				</div>
     				<div class="col-ceq-xsm-6">
    
  • layouts/basic/modules/Vtiger/dashboards/ChartFilterContents.tpl+1 1 modified
    @@ -42,7 +42,7 @@
     										{if $IS_SUMMARY} {$SUMMARY[$HEADER][] = $CHART_DATA.$HEADER.$GROUP_HEADER.$VALUE_TYPE} {/if}
     										{assign var=VALUE value=$CHART_MODEL->convertToUserFormat($CHART_DATA.$HEADER.$GROUP_HEADER.$VALUE_TYPE)}
     										{if !empty($CHART_DATA.$HEADER.$GROUP_HEADER.link)}
    -											<a href="{$CHART_DATA.$HEADER.$GROUP_HEADER.link}">{$VALUE}</a>
    +											<a href="{$CHART_DATA.$HEADER.$GROUP_HEADER.link|escape}">{$VALUE}</a>
     										{else}
     											{$VALUE}
     										{/if}
    
  • layouts/basic/modules/Vtiger/dashboards/ChartFilter.tpl+2 2 modified
    @@ -15,7 +15,7 @@
     					<div>
     						<div class="form-group row mb-2">
     							<label class="{$COL_LBL}">{\App\Language::translate('LBL_WIDGET_NAME','Home')}</label>
    -							<div class="{$COL_CTRL}"><input type="text" class="form-control" name="title" value="{$WIDGET_MODEL->getValueForEditView('title')}"></div>
    +							<div class="{$COL_CTRL}"><input type="text" class="form-control" name="title" value="{\App\Purifier::encodeHtml($WIDGET_MODEL->getValueForEditView('title'))}"></div>
     						</div>
     						<div class="form-group row mb-2">
     							<label class="{$COL_LBL}"><span class="redColor">*</span>{\App\Language::translate('LBL_SELECT_CHART','Home')}</label>
    @@ -59,7 +59,7 @@
     			<div class="{$COL_CTRL}">
     				{assign "VALUE_FILTER" $WIDGET_MODEL->getValueForEditView('filterid')}
     				<select class="form-control filtersId" {if $CHART_TYPE!=='Funnel' && $CHART_TYPE!=='Table' }name="filtersId"
    -					multiple="multiple" {else}name="filtersId[]" 
    +					multiple="multiple" {else}name="filtersId[]"
     					{/if}
     					data-validation-engine="validate[required]" data-maximum-selection-length="{\App\Config::performance('CHART_MULTI_FILTER_LIMIT')}">
     					<option></option>
    
  • layouts/basic/modules/Vtiger/dashboards/DashBoardContents.tpl+2 2 modified
    @@ -44,8 +44,8 @@
     					data-js="css-element-queries">
     					<div id="{$WIDGETDOMID}" {if $smarty.foreach.count.index % $COLUMNS == 0 and $smarty.foreach.count.index != 0} {/if}
     						class="grid-stack-item-content dashboardWidget dashboardWidget_{$smarty.foreach.count.index}"
    -						data-url="{$WIDGET->getUrl()}"
    -						data-mode="open" data-name="{$WIDGET->getName()}" data-cache="{$WIDGET->get('cache')}"
    +						data-url="{$WIDGET->getUrl()|escape}"
    +						data-mode="open" data-name="{\App\Purifier::encodeHtml($WIDGET->getName())}" data-cache="{$WIDGET->get('cache')|escape}"
     						data-loader="widgetLoader">
     					</div>
     				</div>
    
  • layouts/basic/modules/Vtiger/dashboards/DashboardHeaderIcons.tpl+2 2 modified
    @@ -16,11 +16,11 @@
     		</a>
     		&nbsp;
     	{/if}
    -	<button class="btn btn-sm btn-light js-widget-refresh" title="{\App\Language::translate('LBL_REFRESH')}" data-url="{$WIDGET->getUrl()}&content=data" data-js="click">
    +	<button class="btn btn-sm btn-light js-widget-refresh" title="{\App\Language::translate('LBL_REFRESH')}" data-url="{$WIDGET->getUrl()|escape}&content=data" data-js="click">
     		<span class="fas fa-sync-alt"></span>
     	</button>
     	{if !$WIDGET->isDefault()}
    -		<button class="btn btn-sm btn-light js-widget-remove" title="{\App\Language::translate('LBL_CLOSE')}" data-url="{$WIDGET->getDeleteUrl()}" data-js="click">
    +		<button class="btn btn-sm btn-light js-widget-remove" title="{\App\Language::translate('LBL_CLOSE')}" data-url="{$WIDGET->getDeleteUrl()|escape}" data-js="click">
     			<span class="fas fa-times"></span>
     		</button>
     	{/if}
    
  • layouts/basic/modules/Vtiger/dashboards/DashBoardPreProcessAjax.tpl+2 2 modified
    @@ -16,11 +16,11 @@
     			{assign var=COUNT value=count($MODULES_WITH_WIDGET)}
     			<ul class="nav nav-inverted-tabs massEditTabs selectDashboradView ml-sm-2">
     				{foreach from=$MODULES_WITH_WIDGET item=MODULE_WIDGET}
    -					<li class="nav-item" data-module="{$MODULE_WIDGET}">
    +					<li class="nav-item" data-module="{$MODULE_WIDGET|escape}">
     						<a class="nav-link pt-1 pb-1 {if $MODULE_NAME eq $MODULE_WIDGET} active {/if}{if $COUNT === 1} d-none{/if}"
     							href="#"
     							data-toggle="tab">
    -							<span class="yfm-{$MODULE_WIDGET} mx-1"></span>
    +							<span class="yfm-{$MODULE_WIDGET|escape} mx-1"></span>
     							{\App\Language::translate($MODULE_WIDGET, $MODULE_WIDGET)}
     						</a>
     					</li>
    
  • layouts/basic/modules/Vtiger/dashboards/DashBoardWidgetsList.tpl+2 2 modified
    @@ -12,8 +12,8 @@
     	<div class="js-widget-list dropdown-menu widgetsList addWidgetDropDown" data-js="container">
     		{assign var="WIDGET" value=""}
     		{foreach from=$WIDGETS item=WIDGET}
    -			<a class="js-widget-list__item dropdown-item d-flex" href="#" data-name="{$WIDGET->getName()}" data-id="{$WIDGET->get('widgetid')}"
    -				data-widget-url="{$WIDGET->getUrl()}" data-linkid="{$WIDGET->get('linkid')}"
    +			<a class="js-widget-list__item dropdown-item d-flex" href="#" data-name="{\App\Purifier::encodeHtml($WIDGET->getName())}" data-id="{$WIDGET->get('widgetid')}"
    +				data-widget-url="{$WIDGET->getUrl()|escape}" data-linkid="{$WIDGET->get('linkid')}"
     				data-width="{$WIDGET->getWidth()}" data-height="{$WIDGET->getHeight()}" data-js="remove | click">
     				{\App\Language::translate($WIDGET->getTitle(), $MODULE_NAME, null, true, 'Dashboard')}
     				{if $WIDGET->isDeletable()}
    
  • layouts/basic/modules/Vtiger/dashboards/ListUpdatedRecordContents.tpl+1 1 modified
    @@ -22,7 +22,7 @@
     			{foreach key=$index item=record from=$LIST}
     				<tr>
     					{foreach from=$record item=item key=key}
    -						<td>{$item}</td>
    +						<td>{\App\Purifier::encodeHtml($item)}</td>
     					{/foreach}
     				</tr>
     			{/foreach}
    
  • layouts/basic/modules/Vtiger/dashboards/MailsList.tpl+3 3 modified
    @@ -10,11 +10,11 @@
     		<div class="d-flex flex-row flex-nowrap no-gutters justify-content-between">
     			{include file=\App\Layout::getTemplatePath('dashboards/WidgetHeaderTitle.tpl', $MODULE_NAME)}
     			<div class="d-inline-flex">
    -				<button class="btn btn-sm btn-light js-widget-refresh" title="{\App\Language::translate('LBL_REFRESH')}" data-url="{$WIDGET->getUrl()}&content=data" data-js="click">
    +				<button class="btn btn-sm btn-light js-widget-refresh" title="{\App\Language::translate('LBL_REFRESH')}" data-url="{$WIDGET->getUrl()|escape}&content=data" data-js="click">
     					<span class="fas fa-sync-alt"></span>
     				</button>
     				{if !$WIDGET->isDefault()}
    -					<button class="btn btn-sm btn-light js-widget-remove" title="{\App\Language::translate('LBL_CLOSE')}" data-url="{$WIDGET->getDeleteUrl()}" data-js="click">
    +					<button class="btn btn-sm btn-light js-widget-remove" title="{\App\Language::translate('LBL_CLOSE')}" data-url="{$WIDGET->getDeleteUrl()|escape}" data-js="click">
     						<span class="fas fa-times"></span>
     					</button>
     				{/if}
    @@ -34,7 +34,7 @@
     							<option value="-">{\App\Language::translate('--None--', $MODULE_NAME)}</option>
     						{else}
     							{foreach from=$ACCOUNTSLIST item=item key=key}
    -								<option title="{$item['username']}" value="{$item['user_id']}" {if $USER == $item['user_id']}selected{/if}>{$item['username']}</option>
    +								<option title="{\App\Purifier::encodeHtml($item['username'])}" value="{$item['user_id']}" {if $USER == $item['user_id']}selected{/if}>{\App\Purifier::encodeHtml($item['username'])}</option>
     							{/foreach}
     						{/if}
     					</select>
    
  • layouts/basic/modules/Vtiger/dashboards/MiniListWizard.tpl+3 3 modified
    @@ -34,7 +34,7 @@
     										<td class="fieldLabel alignMiddle textAlignCenter"
     											nowrap>{App\Language::translate('LBL_WIDGET_NAME','Home')}</td>
     										<td class="fieldValue position-relative">
    -											<input type="text" class="form-control" name="widgetTitle" value="{$WIDGET_MODEL->getValueForEditView('title')}"
    +											<input type="text" class="form-control" name="widgetTitle" value="{\App\Purifier::encodeHtml($WIDGET_MODEL->getValueForEditView('title'))}"
     												data-validation-engine="validate[required]" {if $WIDGET_ID} disabled{/if}>
     										</td>
     									</tr>
    @@ -46,7 +46,7 @@
     											<select class="form-control select2" name="module" {if $WIDGET_ID} disabled{/if}>
     												<option></option>
     												{foreach from=$MODULES item=MODULE_MODEL key=MODULE_THIS_NAME}
    -													<option value="{$MODULE_MODEL['name']}" {if $MODULE_MODEL['name'] === $VALUE_FIELD} selected{/if}>{App\Language::translate($MODULE_MODEL['name'], $MODULE_MODEL['name'])}</option>
    +													<option value="{$MODULE_MODEL['name']|escape}" {if $MODULE_MODEL['name'] === $VALUE_FIELD} selected{/if}>{App\Language::translate($MODULE_MODEL['name'], $MODULE_MODEL['name'])}</option>
     												{/foreach}
     											</select>
     										</td>
    @@ -152,7 +152,7 @@
     			<select class="form-control" name="fields" size="2" multiple="true">
     				<option></option>
     				{foreach from=$LIST_VIEW_FIELDS item=FIELD key=FIELD_NAME}
    -					<option value="{$FIELD_NAME}">{\App\Language::translate($FIELD->getFieldLabel(),$SELECTED_MODULE)}</option>
    +					<option value="{$FIELD_NAME|escape}">{\App\Language::translate($FIELD->getFieldLabel(),$SELECTED_MODULE)}</option>
     				{/foreach}
     			</select>
     			<select class="form-control" name="filter_fields">
    
  • layouts/basic/modules/Vtiger/dashboards/ProductsSoldToRenewContents.tpl+1 1 modified
    @@ -28,7 +28,7 @@
     	{/foreach}
     	{if count($WIDGET_RECORDS) >= $WIDGET_MODEL->getRecordLimit()}
     		<button class="btn btn-light float-right btn-sm goToListView"
    -			data-url="{$WIDGET_MODEL->getUrl()}"
    +			data-url="{$WIDGET_MODEL->getUrl()|escape}"
     			title="{\App\Language::translate('LBL_MORE', $MODULE_NAME)}">
     			<span>{\App\Language::translate('LBL_MORE', $MODULE_NAME)}</span>
     		</button>
    
  • layouts/basic/modules/Vtiger/dashboards/ProductsSoldToRenew.tpl+1 1 modified
    @@ -33,7 +33,7 @@
     			<div class="col-ceq-xsm-6">
     				<div class="float-right">
     					<button class="btn btn-light btn-sm ml-1 goToListView"
    -						data-url="{$WIDGET_MODEL->getUrl()}"
    +						data-url="{$WIDGET_MODEL->getUrl()|escape}"
     						title="{\App\Language::translate('LBL_GO_TO_RECORDS_LIST', $MODULE_NAME)}">
     						<span class="fas fa-th-list"></span>
     					</button>
    
  • layouts/basic/modules/Vtiger/dashboards/SelectAccessibleTemplate.tpl+2 2 modified
    @@ -38,11 +38,11 @@
     				{if in_array('users', $ACCESS_OPTIONS['available'])}
     					{assign var=AJAX_URL value=$AJAX_URL|cat:"&result[]=users"}
     				{/if}
    -				data-ajax-search="1" data-ajax-url="{$AJAX_URL}" data-minimum-input="{App\Config::performance('OWNER_MINIMUM_INPUT_LENGTH')}"
    +				data-ajax-search="1" data-ajax-url="{$AJAX_URL|escape}" data-minimum-input="{App\Config::performance('OWNER_MINIMUM_INPUT_LENGTH')}"
     			{/if}>
     
     			{if in_array('mine', $ACCESS_OPTIONS.available)}
    -				<option value="{$USER_MODEL->getId()}" data-name="{$USER_MODEL->getName()}"
    +				<option value="{$USER_MODEL->getId()}" data-name="{$USER_MODEL->getName()|escape}"
     					title="{\App\Language::translate('LBL_MINE')}" {if $OWNER eq $USER_MODEL->getId()} selected {/if}>{\App\Language::translate('LBL_MINE')}</option>
     			{/if}
     			{if in_array('all', $ACCESS_OPTIONS.available)}
    

Vulnerability mechanics

Generated by null/stub on May 9, 2026. Inputs: CWE entries + fix-commit diffs from this CVE's patches. Citations validated against bundle.

References

4

News mentions

0

No linked articles in our index yet.