Skip to content

Commit 94b44ac

Browse files
Merge remote-tracking branch 'openmage/main' into next
2 parents aaa410d + 2a2a2fb commit 94b44ac

File tree

6 files changed

+73
-38
lines changed

6 files changed

+73
-38
lines changed

app/code/core/Mage/Core/Helper/Data.php

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1008,4 +1008,39 @@ public function isFormKeyEnabled(): bool
10081008
{
10091009
return Mage::getStoreConfigFlag(Mage_Core_Controller_Front_Action::XML_CSRF_USE_FLAG_CONFIG_PATH);
10101010
}
1011+
1012+
/**
1013+
* @param bool $setErrorMessage Adds a predefined error message to the 'core/session' object
1014+
* @return bool
1015+
*/
1016+
public function isRateLimitExceeded($setErrorMessage = true, $recordRateLimitHit = true): bool
1017+
{
1018+
$active = Mage::getStoreConfigFlag('system/rate_limit/active');
1019+
if ($active && $remoteAddr = Mage::helper('core/http')->getRemoteAddr()) {
1020+
$cacheTag = 'rate_limit_' . $remoteAddr;
1021+
if (Mage::app()->testCache($cacheTag)) {
1022+
$errorMessage = "Too Soon: You are trying to perform this operation too frequently. Please wait a few seconds and try again.";
1023+
Mage::getSingleton('core/session')->addError($this->__($errorMessage));
1024+
return true;
1025+
}
1026+
1027+
if ($recordRateLimitHit) {
1028+
$this->recordRateLimitHit();
1029+
}
1030+
}
1031+
1032+
return false;
1033+
}
1034+
1035+
/**
1036+
* @return void
1037+
*/
1038+
public function recordRateLimitHit(): void
1039+
{
1040+
$active = Mage::getStoreConfigFlag('system/rate_limit/active');
1041+
if ($active && $remoteAddr = Mage::helper('core/http')->getRemoteAddr()) {
1042+
$cacheTag = 'rate_limit_' . $remoteAddr;
1043+
Mage::app()->saveCache(1, $cacheTag, ['brute_force'], Mage::getStoreConfig('system/rate_limit/timeframe'));
1044+
}
1045+
}
10111046
}

app/code/core/Mage/Core/etc/config.xml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -315,6 +315,10 @@
315315
<csrf>
316316
<use_form_key>1</use_form_key>
317317
</csrf>
318+
<rate_limit>
319+
<active>1</active>
320+
<timeframe>30</timeframe>
321+
</rate_limit>
318322
<cache>
319323
<flush_cron_expr>30 2 * * *</flush_cron_expr>
320324
</cache>

app/code/core/Mage/Core/etc/system.xml

Lines changed: 27 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,33 @@
5050
</use_form_key>
5151
</fields>
5252
</csrf>
53+
<rate_limit translate="label comment" module="core">
54+
<label>Rate limit</label>
55+
<sort_order>10</sort_order>
56+
<show_in_default>1</show_in_default>
57+
<show_in_website>1</show_in_website>
58+
<show_in_store>1</show_in_store>
59+
<comment>This functionality limits the number of requests a user (identified by IP address) can perform within a specific time frame, preventing excessive resources usage and maintaining system performance, stability and security.</comment>
60+
<fields>
61+
<active translate="label">
62+
<label>Enabled</label>
63+
<frontend_type>select</frontend_type>
64+
<source_model>adminhtml/system_config_source_yesno</source_model>
65+
<sort_order>10</sort_order>
66+
<show_in_default>1</show_in_default>
67+
<show_in_website>1</show_in_website>
68+
<show_in_store>1</show_in_store>
69+
</active>
70+
<timeframe translate="label comment">
71+
<label>Timeframe</label>
72+
<sort_order>20</sort_order>
73+
<show_in_default>1</show_in_default>
74+
<show_in_website>1</show_in_website>
75+
<show_in_store>1</show_in_store>
76+
<comment>Number of seconds between each allowed request.</comment>
77+
</timeframe>
78+
</fields>
79+
</rate_limit>
5380
<cache translate="label" module="core">
5481
<label>Advanced Cache Settings</label>
5582
<sort_order>1000</sort_order>
@@ -69,13 +96,6 @@
6996
</cache>
7097
</groups>
7198
</system>
72-
<!--<web_track translate="label" module="core">
73-
<label>Web Tracking</label>
74-
<sort_order>180</sort_order>
75-
<show_in_default>1</show_in_default>
76-
<show_in_website>1</show_in_website>
77-
<show_in_store>1</show_in_store>
78-
</web_track>-->
7999
<advanced translate="label" module="core">
80100
<label>Advanced</label>
81101
<tab>advanced</tab>
@@ -84,35 +104,6 @@
84104
<show_in_website>1</show_in_website>
85105
<show_in_store>1</show_in_store>
86106
<groups>
87-
<!--datashare translate="label">
88-
<label>Datasharing</label>
89-
<sort_order>1</sort_order>
90-
<show_in_default>1</show_in_default>
91-
<show_in_website>1</show_in_website>
92-
<show_in_store>0</show_in_store>
93-
<fields>
94-
<default translate="label">
95-
<label>Default</label>
96-
<frontend_type>multiselect</frontend_type>
97-
<backend_model>adminhtml/system_config_backend_datashare</backend_model>
98-
<source_model>adminhtml/system_config_source_store</source_model>
99-
<sort_order>1</sort_order>
100-
<show_in_default>1</show_in_default>
101-
<show_in_website>1</show_in_website>
102-
<show_in_store>1</show_in_store>
103-
</default>
104-
<default translate="label">
105-
<label>Default</label>
106-
<frontend_type>multiselect</frontend_type>
107-
<backend_model>adminhtml/system_config_backend_datashare</backend_model>
108-
<source_model>adminhtml/system_config_source_store</source_model>
109-
<sort_order>1</sort_order>
110-
<show_in_default>1</show_in_default>
111-
<show_in_website>1</show_in_website>
112-
<show_in_store>1</show_in_store>
113-
</default>
114-
</fields>
115-
</datashare-->
116107
<modules_disable_output translate="label">
117108
<label>Disable Modules Output</label>
118109
<frontend_model>adminhtml/system_config_form_fieldset_modules_disableOutput</frontend_model>

app/code/core/Mage/Sales/Helper/Guest.php

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,7 @@ public function loadValidOrder()
105105
$errors = true;
106106
}
107107
} else {
108+
Mage::helper('core')->recordRateLimitHit();
108109
$errors = true;
109110
}
110111
}
@@ -114,7 +115,10 @@ public function loadValidOrder()
114115
return true;
115116
}
116117

117-
Mage::getSingleton('core/session')->addError($this->__($errorMessage));
118+
if (!Mage::helper('core')->isRateLimitExceeded(true, false)) {
119+
Mage::getSingleton('core/session')->addError($this->__($errorMessage));
120+
}
121+
118122
Mage::app()->getResponse()->setRedirect(Mage::getUrl('sales/guest/form'));
119123
return false;
120124
}

app/code/core/Mage/Sales/Model/Order.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2372,7 +2372,7 @@ protected function _beforeSave()
23722372
}
23732373

23742374
if (!$this->getId()) {
2375-
$this->setData('protect_code', substr(md5(uniqid(mt_rand(), true) . ':' . microtime(true)), 5, 6));
2375+
$this->setData('protect_code', Mage::helper('core')->getRandomString(16));
23762376
}
23772377

23782378
if ($this->getStatus() !== $this->getOrigData('status')) {

app/locale/en_US/Mage_Core.csv

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -384,6 +384,7 @@
384384
"Timezone","Timezone"
385385
"Title Prefix","Title Prefix"
386386
"Title Suffix","Title Suffix"
387+
"Too Soon: You are trying to perform this operation too frequently. Please wait a few seconds and try again.","Too Soon: You are trying to perform this operation too frequently. Please wait a few seconds and try again."
387388
"Transactional Emails","Transactional Emails"
388389
"Translate Inline","Translate Inline"
389390
"Translate, blocks and other output caches should be disabled for both frontend and admin inline translations.","Translate, blocks and other output caches should be disabled for both frontend and admin inline translations."

0 commit comments

Comments
 (0)