mirror of
https://github.com/taobataoma/meanTorrent.git
synced 2026-02-03 21:19:18 +01:00
feat(users): calculate the user hourly scores income
This commit is contained in:
7
config/env/torrents.js
vendored
7
config/env/torrents.js
vendored
@@ -506,6 +506,7 @@ module.exports = {
|
||||
downloadValue: 0.5,
|
||||
downloadEnable: true,
|
||||
vipRatio: 1.5,
|
||||
uploaderRatio: 2,
|
||||
|
||||
enable: true
|
||||
},
|
||||
@@ -525,11 +526,11 @@ module.exports = {
|
||||
name: 'seedSeederAndLife',
|
||||
content: 'SEED_SEEDER_AND_LIFE',
|
||||
seederBasicRatio: 1,
|
||||
seederCoefficient: 0.2,
|
||||
seederCoefficient: 0.1,
|
||||
seederCount: 10,
|
||||
lifeBasicRatio: 1,
|
||||
lifeCoefficientOfDay: 0.002,
|
||||
lifeMaxRatio: 3,
|
||||
lifeCoefficientOfDay: 0.001,
|
||||
lifeMaxRatio: 2,
|
||||
|
||||
enable: true
|
||||
}
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
|
||||
#### :white_small_square: Data calculation and scores count
|
||||
|
||||
1. Seed uploaders calculate the upload volume of `* %(salesGlobalConfig.uploader.value.Ur).2f`。
|
||||
1. Seed uploaders calculate the upload volume of `* %(salesGlobalConfig.uploader.value.Ur).2f`, and calculate the upload scores of `* %(scoreConfig.action.seedUpDownload.uploaderRatio).2f`.
|
||||
1. Other users calculate the normal upload and download amount.
|
||||
1. All users of all the seed upload and download volume enjoy promotion bonus, in case of global promotion, they enjoy the overall promotion bonus.
|
||||
1. VIP users can enjoy additional bonuses for uploading and downloading as well as seeding scores. For details, please refer to [VIP Rights Rules Detail](/about/manual/vipRules)。
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
|
||||
#### :white_small_square: 流量計算與積分統計
|
||||
|
||||
1. 種子釋出者按 `%(salesGlobalConfig.uploader.value.Ur).2f` 倍的上傳量計算。
|
||||
1. 種子釋出者按 `%(salesGlobalConfig.uploader.value.Ur).2f` 倍的上傳量計算,並獲得 `%(scoreConfig.action.seedUpDownload.uploaderRatio).2f` 倍的上傳量積分。
|
||||
1. 分流者按正常上傳下載量計算。
|
||||
1. 所有用戶所有種子上傳下載量享有促銷加成,如遇全局促銷則享有全局促銷加成。
|
||||
1. VIP 用戶的上傳下載量以及做種積分享有額外的加成,詳情請參考 [VIP 用戶者權益細則](/about/manual/vipRules)。
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
|
||||
#### :white_small_square: 流量计算与积分统计
|
||||
|
||||
1. 种子发布者按 `%(salesGlobalConfig.uploader.value.Ur).2f` 倍的上传量计算。
|
||||
1. 种子发布者按 `%(salesGlobalConfig.uploader.value.Ur).2f` 倍的上传量计算,并获得 `%(scoreConfig.action.seedUpDownload.uploaderRatio).2f` 倍的上传量积分。
|
||||
1. 分流者按正常上传下载量计算。
|
||||
1. 所有用户所有种子上传下载量享有促销加成,如遇全局促销则享有全局促销加成。
|
||||
1. VIP 用户的上传下载量以及做种积分享有额外的加成,详情请参考 [VIP 用户权益细则](/about/manual/vipRules)。
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
none vip user get uploaded scores: 2 * 1 * 10 = 20, downloaded scores: 2 * 0.5 * 15 = 15.
|
||||
vip user get uploaded scores: 20 * 1.5 = 30, downloaded scores: 15 * 1.5 = 22.5.
|
||||
```
|
||||
* Seed uploaders calculate the upload scores of `* %(scoreConfig.action.seedUpDownload.uploaderRatio).2f`.
|
||||
* In the seeding state, the seeding scores will be get from the seeding time. For every seed, `%(scoreConfig.action.seedTimed.timedValue).2f` scores per `%(scoreConfig.action.seedTimed.additionTime_str)s`, vip user extra addition ratio is `%(scoreConfig.action.seedTimed.vipRatio).2f`.
|
||||
* Scores got for the above two items, will get extra addition based on the seed life and seeding users, <mark>And two kinds of addition are available at the same time</mark>.
|
||||
```javascript
|
||||
@@ -33,7 +34,7 @@
|
||||
Coefficient is: %(scoreConfig.action.seedSeederAndLife.seederCoefficient).2f
|
||||
Seecer count less than: %(scoreConfig.action.seedSeederAndLife.seederCount)d
|
||||
|
||||
For 1 seeding user, the extra addition ratio is: 3, [for 2 is 2.8], [for 3 is 2.6], [for 4 is 2.4], [for 5 is 2.2], [for 6 is 2.0], [for 7 is 1.8], [for 8 is 1.6], [for 9 is 1.4], [for 10 is 1.2], [more than 10 is 1, same as no extra addition].
|
||||
For 1 seeding user, the extra addition ratio is: 2, [for 2 is 1.9], [for 3 is 1.8], [for 4 is 1.7], [for 5 is 1.6], [for 6 is 1.5], [for 7 is 1.4], [for 8 is 1.3], [for 9 is 1.2], [for 10 is 1.1], [more than 10 is 1, same as no extra addition].
|
||||
```
|
||||
```javascript
|
||||
With seed life:
|
||||
@@ -42,7 +43,7 @@
|
||||
Max ratio is: %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f
|
||||
|
||||
The basic ratio is %(scoreConfig.action.seedSeederAndLife.lifeBasicRatio).2f, increase %(scoreConfig.action.seedSeederAndLife.lifeCoefficientOfDay).3f every day.
|
||||
For 10 days life ratio is 1.02, [100 days is 1.2], [200 days is 1.4] etc, the max ratio is %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f.
|
||||
For 10 days life ratio is 1.01, [100 days is 1.1], [200 days is 1.2] etc, the max ratio is %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f.
|
||||
```
|
||||
* At the end of each month, the system will award scores to users who have successfully sent invitations. the score number limit is the percentage `%(scoreConfig.transferToInviter.transRatio)f` of the monthly got of the invited users, the current award function enable status is:
|
||||
```javascript
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
非 Vip 使用者獲得上傳積分: 2 * 1 * 10 = 20, 下載積分: 2 * 0.5 * 15 = 15。
|
||||
Vip 使用者獲得上傳積分: 20 * 1.5 = 30, 下載積分: 15 * 1.5 = 22.5。
|
||||
```
|
||||
* 種子發布者按 `%(scoreConfig.action.seedUpDownload.uploaderRatio).2f` 倍計算上傳量積分。
|
||||
* 在做種狀態下,將會獲得由保種時間帶來的保種積分, 每個種子每 `%(scoreConfig.action.seedTimed.additionTime_str)s` 獲得 `%(scoreConfig.action.seedTimed.timedValue).2f` 積分,Vip 使用者額外加成係數為 `%(scoreConfig.action.seedTimed.vipRatio).2f`。
|
||||
* 對於上述兩項獲得的積分, 還會根據種子的生命期和保種人數獲得額外的再次加成,<mark>而且兩種加成疊加生效</mark>。
|
||||
```javascript
|
||||
@@ -33,7 +34,7 @@
|
||||
加成係數: %(scoreConfig.action.seedSeederAndLife.seederCoefficient).2f
|
||||
最多保種人數: %(scoreConfig.action.seedSeederAndLife.seederCount)d
|
||||
|
||||
如果只有 1 個保種使用者: 加成係數為 2, [2 使用者為 2.8], [3 使用者為 2.6], [4 使用者為 2.4], [5 使用者為 2.2], [6 使用者為 2.0], [7 使用者為 1.8], [8 使用者為 1.6], [9 使用者為 1.4], [10 使用者為 1.2], [超過 10 使用者為 1, 相當於沒有加成]。
|
||||
如果只有 1 個保種使用者: 加成係數為 2, [2 使用者為 1.9], [3 使用者為 1.8], [4 使用者為 1.7], [5 使用者為 1.6], [6 使用者為 1.5], [7 使用者為 1.4], [8 使用者為 1.3], [9 使用者為 1.2], [10 使用者為 1.1], [超過 10 使用者為 1, 相當於沒有加成]。
|
||||
```
|
||||
```javascript
|
||||
種子生命加成:
|
||||
@@ -42,7 +43,7 @@
|
||||
最大加成係數: %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f
|
||||
|
||||
加成基礎係數為 %(scoreConfig.action.seedSeederAndLife.lifeBasicRatio).2f, 根據種子生命每天增加 %(scoreConfig.action.seedSeederAndLife.lifeCoefficientOfDay).3f。
|
||||
如果種子生命(釋出時間)為 10 天,則加成係數為 1.02, [100 天是 1.2], [200 天是 1.4], 以此類推,最大加成係數為 %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f。
|
||||
如果種子生命(釋出時間)為 10 天,則加成係數為 1.01, [100 天是 1.1], [200 天是 1.2], 以此類推,最大加成係數為 %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f。
|
||||
```
|
||||
* 系統在每個月底會對成功發送過邀請函的用戶進行積分獎勵,獎勵額度為受邀請用戶當月的進帳積分的 `%(scoreConfig.transferToInviter.transRatio)f` 倍,目前該獎勵功能開關狀態為:
|
||||
```javascript
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
非 Vip 用户获得上传积分: 2 * 1 * 10 = 20, 下载积分: 2 * 0.5 * 15 = 15。
|
||||
Vip 用户获得上传积分: 20 * 1.5 = 30, 下载积分: 15 * 1.5 = 22.5。
|
||||
```
|
||||
* 种子发布者按 `%(scoreConfig.action.seedUpDownload.uploaderRatio).2f` 倍计算上传量积分。
|
||||
* 在做种状态下,将会获得由保种时间带来的保种积分, 每个种子每 `%(scoreConfig.action.seedTimed.additionTime_str)s` 获得 `%(scoreConfig.action.seedTimed.timedValue).2f` 积分,Vip 用户额外加成系数为 `%(scoreConfig.action.seedTimed.vipRatio).2f`。
|
||||
* 对于上述两项获得的积分, 还会根据种子的生命期和保种人数获得额外的再次加成,<mark>而且两种加成叠加生效</mark>。
|
||||
```javascript
|
||||
@@ -33,7 +34,7 @@
|
||||
加成系数: %(scoreConfig.action.seedSeederAndLife.seederCoefficient).2f
|
||||
最多保种人数: %(scoreConfig.action.seedSeederAndLife.seederCount)d
|
||||
|
||||
如果只有 1 个保种用户: 加成系数为 3, [2 用户为 2.8], [3 用户为 2.6], [4 用户为 2.4], [5 用户为 2.2], [6 用户为 2.0], [7 用户为 1.8], [8 用户为 1.6], [9 用户为 1.4], [10 用户为 1.2], [超过 10 用户为 1, 相当于没有加成]。
|
||||
如果只有 1 个保种用户: 加成系数为 3, [2 用户为 1.9], [3 用户为 1.8], [4 用户为 1.7], [5 用户为 1.6], [6 用户为 1.5], [7 用户为 1.4], [8 用户为 1.3], [9 用户为 1.2], [10 用户为 1.1], [超过 10 用户为 1, 相当于没有加成]。
|
||||
```
|
||||
```javascript
|
||||
种子生命加成:
|
||||
@@ -42,7 +43,7 @@
|
||||
最大加成系数: %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f
|
||||
|
||||
加成基础系数为 %(scoreConfig.action.seedSeederAndLife.lifeBasicRatio).2f, 根据种子生命每天增加 %(scoreConfig.action.seedSeederAndLife.lifeCoefficientOfDay).3f。
|
||||
如果种子生命(发布时间)为 10 天,则加成系数为 1.02, [100 天是 1.2], [200 天是 1.4], 以此类推,最大加成系数为 %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f。
|
||||
如果种子生命(发布时间)为 10 天,则加成系数为 1.01, [100 天是 1.1], [200 天是 1.2], 以此类推,最大加成系数为 %(scoreConfig.action.seedSeederAndLife.lifeMaxRatio).2f。
|
||||
```
|
||||
* 系统在每个月底会对成功发送过邀请函的用户进行积分奖励,奖励额度为受邀请用户当月的进帐积分的 `%(scoreConfig.transferToInviter.transRatio)f` 倍,目前该奖励功能开关状态为:
|
||||
```javascript
|
||||
|
||||
@@ -586,9 +586,15 @@ exports.announce = function (req, res) {
|
||||
var sp = {};
|
||||
if (curru > 0) {
|
||||
sp.peer_uspeed = Math.round(curru / (Date.now() - req.currentPeer.last_announce_at) * 1000);
|
||||
sp.peer_cuspeed = Math.round(curru / (Date.now() - req.currentPeer.last_announce_at) * 1000);
|
||||
} else {
|
||||
sp.peer_cuspeed = 0;
|
||||
}
|
||||
if (currd > 0) {
|
||||
sp.peer_dspeed = Math.round(currd / (Date.now() - req.currentPeer.last_announce_at) * 1000);
|
||||
sp.peer_cdspeed = Math.round(currd / (Date.now() - req.currentPeer.last_announce_at) * 1000);
|
||||
} else {
|
||||
sp.peer_cdspeed = 0;
|
||||
}
|
||||
req.currentPeer.update({
|
||||
$set: sp
|
||||
@@ -615,6 +621,10 @@ exports.announce = function (req, res) {
|
||||
}
|
||||
var upScore = curru / action.perlSize;
|
||||
uploadScore = upUnitScore * action.uploadValue * upScore;
|
||||
//uploader addition
|
||||
if (req.passkeyuser._id.equals(req.torrent.user._id)) {
|
||||
uploadScore = uploadScore * action.uploaderRatio;
|
||||
}
|
||||
}
|
||||
|
||||
if (currd > 0 && action.downloadEnable) {
|
||||
@@ -692,6 +702,13 @@ exports.announce = function (req, res) {
|
||||
}
|
||||
};
|
||||
dataLog.announceLog(req.passkeyuser, req.torrent, logData);
|
||||
} else {
|
||||
req.currentPeer.update({
|
||||
$set: {
|
||||
peer_cuspeed: 0,
|
||||
peer_cdspeed: 0
|
||||
}
|
||||
}).exec();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -24,6 +24,10 @@
|
||||
VALUE_SELECT_ALL: 'Select All',
|
||||
BTN_REMOVE: 'Remove',
|
||||
BTN_CONTINUE: 'Continue',
|
||||
VALUE_TRUE: 'true',
|
||||
VALUE_FALSE: 'false',
|
||||
VALUE_ON: 'on',
|
||||
VALUE_OFF: 'off',
|
||||
|
||||
//Support
|
||||
SUPPORT_GROUP_NAME_DESC: 'Management group',
|
||||
@@ -1072,9 +1076,16 @@
|
||||
//user score
|
||||
SCORE: {
|
||||
CURRENT_SCORE: 'Current score:',
|
||||
INCOME_ESTIMATE: 'My scores income estimate',
|
||||
HOW_TO_GET_LEVEL: 'How to count user level?',
|
||||
HOW_TO_GET_SCORE: 'How to get score number?'
|
||||
},
|
||||
CURR_LEECHING_TORRENTS: 'Current downloading torrents: `{{count_leech}}`.',
|
||||
CURR_SEEDING_TORRENTS: 'Current seeding torrents: `{{count_seed}}`.',
|
||||
CURR_VIP_STATE: 'Current VIP status: `{{vip_status | translate}}`.',
|
||||
CURR_UP_TOTAL_SPEED: 'Current total upload speed is: `{{up_speed | byteFmt: 2}}`.',
|
||||
CURR_DOWN_TOTAL_SPEED: 'Current total download speed is: `{{down_speed | byteFmt: 2}}`.',
|
||||
CURR_SCORE_INCOME_HOURS: 'Current estimated hourly earnings of `{{score_hour}}` scores, If you don’t understand how to calculate the points, please refer to [{{"ABOUT.MENU_ABOUT_MANUAL_SCORE_RULES" | translate}}](/about/manual/scoreRules).',
|
||||
EXCHANGE_INVITATION: 'Exchange an invitation ({{score}} scores)',
|
||||
EXCHANGE_INVITATION_CONFIRM_OK: 'Exchange',
|
||||
EXCHANGE_INVITATION_CONFIRM_CANCEL: 'Cancel',
|
||||
|
||||
@@ -24,6 +24,10 @@
|
||||
VALUE_SELECT_ALL: '全選',
|
||||
BTN_REMOVE: '刪除',
|
||||
BTN_CONTINUE: '繼續',
|
||||
VALUE_TRUE: '是',
|
||||
VALUE_FALSE: '否',
|
||||
VALUE_ON: '開',
|
||||
VALUE_OFF: '關',
|
||||
|
||||
//Support
|
||||
SUPPORT_GROUP_NAME_DESC: '管理組',
|
||||
@@ -1072,9 +1076,16 @@
|
||||
//user score
|
||||
SCORE: {
|
||||
CURRENT_SCORE: '當前積分:',
|
||||
INCOME_ESTIMATE: '我的積分收入預估',
|
||||
HOW_TO_GET_LEVEL: '怎麼計算用戶級別?',
|
||||
HOW_TO_GET_SCORE: '怎麼取得用戶積分?'
|
||||
},
|
||||
CURR_LEECHING_TORRENTS: '當前正在下載的種子:`{{count_leech}}`個。',
|
||||
CURR_SEEDING_TORRENTS: '當前正在做種的種子:`{{count_seed}}`個。',
|
||||
CURR_VIP_STATE: '當前 VIP 身份狀態:`{{vip_status | translate}}`。',
|
||||
CURR_UP_TOTAL_SPEED: '當前上傳總速度為:`{{up_speed | byteFmt: 2}}`。',
|
||||
CURR_DOWN_TOTAL_SPEED: '當前下載總速度為:`{{down_speed | byteFmt: 2}}`。',
|
||||
CURR_SCORE_INCOME_HOURS: '當前預計每小時獲得 `{{score_hour}}` 積分,如果你不明白積分怎麼計算,請參閱 [{{"ABOUT.MENU_ABOUT_MANUAL_SCORE_RULES" | translate}}](/about/manual/scoreRules)。',
|
||||
EXCHANGE_INVITATION: '兌換一個邀請 ({{score}} 積分)',
|
||||
EXCHANGE_INVITATION_CONFIRM_OK: '兌換',
|
||||
EXCHANGE_INVITATION_CONFIRM_CANCEL: '取消',
|
||||
|
||||
@@ -24,6 +24,10 @@
|
||||
VALUE_SELECT_ALL: '全选',
|
||||
BTN_REMOVE: '删除',
|
||||
BTN_CONTINUE: '继续',
|
||||
VALUE_TRUE: '是',
|
||||
VALUE_FALSE: '否',
|
||||
VALUE_ON: '开',
|
||||
VALUE_OFF: '关',
|
||||
|
||||
//Support
|
||||
SUPPORT_GROUP_NAME_DESC: '管理组',
|
||||
@@ -1072,9 +1076,16 @@
|
||||
//user score
|
||||
SCORE: {
|
||||
CURRENT_SCORE: '当前积分:',
|
||||
INCOME_ESTIMATE: '我的积分收入预估',
|
||||
HOW_TO_GET_LEVEL: '怎么计算用户级别?',
|
||||
HOW_TO_GET_SCORE: '怎么取得用户积分?'
|
||||
},
|
||||
CURR_LEECHING_TORRENTS: '当前正在下载的种子:`{{count_leech}}`个。',
|
||||
CURR_SEEDING_TORRENTS: '当前正在做种的种子:`{{count_seed}}`个。',
|
||||
CURR_VIP_STATE: '当前 VIP 身份状态:`{{vip_status | translate}}`。',
|
||||
CURR_UP_TOTAL_SPEED: '当前上传总速度为:`{{up_speed | byteFmt: 2}}`。',
|
||||
CURR_DOWN_TOTAL_SPEED: '当前下载总速度为:`{{down_speed | byteFmt: 2}}`。',
|
||||
CURR_SCORE_INCOME_HOURS: '当前预计每小时获得 `{{score_hour}}` 积分,如果你不明白积分怎么计算,请参阅 [{{"ABOUT.MENU_ABOUT_MANUAL_SCORE_RULES" | translate}}](/about/manual/scoreRules)。',
|
||||
EXCHANGE_INVITATION: '兑换一个邀请 ({{score}} 积分)',
|
||||
EXCHANGE_INVITATION_CONFIRM_OK: '兑换',
|
||||
EXCHANGE_INVITATION_CONFIRM_CANCEL: '取消',
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
function PeersService($resource, CacheFactory) {
|
||||
var peersCache = CacheFactory.get('peersCache') || CacheFactory.createCache('peersCache');
|
||||
|
||||
var Torrents = $resource('', {}, {
|
||||
var Peers = $resource('', {}, {
|
||||
getMySeedingList: {
|
||||
method: 'GET',
|
||||
url: '/api/my/seeding',
|
||||
@@ -30,6 +30,12 @@
|
||||
isArray: true,
|
||||
cache: peersCache
|
||||
},
|
||||
getMyPeers: {
|
||||
method: 'GET',
|
||||
url: '/api/my/peers',
|
||||
isArray: true,
|
||||
cache: peersCache
|
||||
},
|
||||
getUserSeedingList: {
|
||||
method: 'GET',
|
||||
url: '/api/users/:userId/seeding',
|
||||
@@ -59,6 +65,6 @@
|
||||
}
|
||||
});
|
||||
|
||||
return Torrents;
|
||||
return Peers;
|
||||
}
|
||||
}());
|
||||
|
||||
@@ -107,3 +107,27 @@ exports.getMyWarning = function (req, res) {
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* getMyPeers
|
||||
* @param req
|
||||
* @param res
|
||||
*/
|
||||
exports.getMyPeers = function (req, res) {
|
||||
Peer.find({
|
||||
user: req.user._id,
|
||||
last_announce_at: {$gt: Date.now() - announceConfig.announceInterval - announceConfig.announceIdleTime}
|
||||
}).populate({
|
||||
path: 'torrent',
|
||||
select: populateStrings.populate_torrent_string
|
||||
})
|
||||
.exec(function (err, peers) {
|
||||
if (err) {
|
||||
return res.status(422).send({
|
||||
message: errorHandler.getErrorMessage(err)
|
||||
});
|
||||
} else {
|
||||
res.json(peers);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
@@ -51,6 +51,14 @@ var PeerSchema = new Schema({
|
||||
type: Number,
|
||||
default: 0
|
||||
},
|
||||
peer_cuspeed: {
|
||||
type: Number,
|
||||
default: 0
|
||||
},
|
||||
peer_cdspeed: {
|
||||
type: Number,
|
||||
default: 0
|
||||
},
|
||||
peer_ratio: {
|
||||
type: Number,
|
||||
default: 0
|
||||
|
||||
@@ -53,6 +53,7 @@ exports.invokeRolesPolicies = function () {
|
||||
{resources: '/api/my/seeding', permissions: '*'},
|
||||
{resources: '/api/my/downloading', permissions: '*'},
|
||||
{resources: '/api/my/warning', permissions: '*'},
|
||||
{resources: '/api/my/peers', permissions: '*'},
|
||||
{resources: '/api/torrents/siteInfo', permissions: ['get']},
|
||||
|
||||
{resources: '/api/completes/:completeId', permissions: ['put']}
|
||||
@@ -88,6 +89,7 @@ exports.invokeRolesPolicies = function () {
|
||||
{resources: '/api/my/seeding', permissions: ['get']},
|
||||
{resources: '/api/my/downloading', permissions: ['get']},
|
||||
{resources: '/api/my/warning', permissions: ['get']},
|
||||
{resources: '/api/my/peers', permissions: ['get']},
|
||||
{resources: '/api/torrents/siteInfo', permissions: ['get']},
|
||||
|
||||
{resources: '/api/completes/:completeId', permissions: ['put']}
|
||||
|
||||
@@ -18,4 +18,7 @@ module.exports = function (app) {
|
||||
app.route('/api/my/warning').all(torrentsPolicy.isAllowed)
|
||||
.get(peers.getMyWarning);
|
||||
|
||||
app.route('/api/my/peers').all(torrentsPolicy.isAllowed)
|
||||
.get(peers.getMyPeers);
|
||||
|
||||
};
|
||||
|
||||
@@ -6,10 +6,12 @@
|
||||
.controller('ScoreController', ScoreController);
|
||||
|
||||
ScoreController.$inject = ['$rootScope', '$scope', '$state', '$translate', '$timeout', 'Authentication', '$window', 'ScoreLevelService', 'getStorageLangService',
|
||||
'MeanTorrentConfig', 'ModalConfirmService', 'NotifycationService', 'InvitationsService', '$templateRequest', 'marked', '$filter'];
|
||||
'MeanTorrentConfig', 'ModalConfirmService', 'NotifycationService', 'InvitationsService', '$templateRequest', 'marked', '$filter', 'PeersService', 'moment',
|
||||
'DebugConsoleService'];
|
||||
|
||||
function ScoreController($rootScope, $scope, $state, $translate, $timeout, Authentication, $window, ScoreLevelService, getStorageLangService, MeanTorrentConfig,
|
||||
ModalConfirmService, NotifycationService, InvitationsService, $templateRequest, marked, $filter) {
|
||||
ModalConfirmService, NotifycationService, InvitationsService, $templateRequest, marked, $filter, PeersService, moment,
|
||||
mtDebug) {
|
||||
var vm = this;
|
||||
vm.scoreConfig = MeanTorrentConfig.meanTorrentConfig.score;
|
||||
vm.inviteConfig = MeanTorrentConfig.meanTorrentConfig.invite;
|
||||
@@ -111,7 +113,10 @@
|
||||
closeButtonText: $translate.instant('EXCHANGE_INVITATION_CONFIRM_CANCEL'),
|
||||
actionButtonText: $translate.instant('EXCHANGE_INVITATION_CONFIRM_OK'),
|
||||
headerText: $translate.instant('EXCHANGE_INVITATION_CONFIRM_HEADER_TEXT'),
|
||||
bodyText: $translate.instant('EXCHANGE_INVITATION_CONFIRM_BODY_TEXT', {score: vm.inviteConfig.scoreExchange, hours: vm.inviteConfig.expires_str})
|
||||
bodyText: $translate.instant('EXCHANGE_INVITATION_CONFIRM_BODY_TEXT', {
|
||||
score: vm.inviteConfig.scoreExchange,
|
||||
hours: vm.inviteConfig.expires_str
|
||||
})
|
||||
};
|
||||
|
||||
ModalConfirmService.showModal({}, modalOptions)
|
||||
@@ -138,5 +143,212 @@
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* getMyPeers
|
||||
*/
|
||||
vm.getMyPeers = function () {
|
||||
PeersService.getMyPeers(function (items) {
|
||||
vm.myPeers = items;
|
||||
mtDebug.info(items);
|
||||
|
||||
vm.countByStatus = $filter('countBy')(vm.myPeers, 'peer_status');
|
||||
vm.groupByStatus = $filter('groupBy')(vm.myPeers, 'peer_status');
|
||||
|
||||
vm.sumCUSpeed = vm.myPeers.map(function (x) {
|
||||
return x.peer_cuspeed;
|
||||
}).reduce(function (a, b) {
|
||||
return a + b;
|
||||
});
|
||||
vm.sumCDSpeed = vm.myPeers.map(function (x) {
|
||||
return x.peer_cdspeed;
|
||||
}).reduce(function (a, b) {
|
||||
return a + b;
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* getMarkedCurrDownloadingString
|
||||
* @returns {*}
|
||||
*/
|
||||
vm.getMarkedCurrDownloadingString = function () {
|
||||
if (vm.countByStatus) {
|
||||
var tmp = $translate.instant('CURR_LEECHING_TORRENTS', {count_leech: vm.countByStatus.leecher || 0});
|
||||
return marked(tmp, {sanitize: false});
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* getMarkedCurrSeedingString
|
||||
* @returns {*}
|
||||
*/
|
||||
vm.getMarkedCurrSeedingString = function () {
|
||||
if (vm.countByStatus) {
|
||||
var tmp = $translate.instant('CURR_SEEDING_TORRENTS', {count_seed: vm.countByStatus.seeder || 0});
|
||||
return marked(tmp, {sanitize: false});
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* getMarkedVipStatusString
|
||||
* @returns {*}
|
||||
*/
|
||||
vm.getMarkedVipStatusString = function () {
|
||||
var tmp = $translate.instant('CURR_VIP_STATE', {vip_status: vm.user.isVip ? 'VALUE_TRUE' : 'VALUE_FALSE'});
|
||||
return marked(tmp, {sanitize: false});
|
||||
};
|
||||
|
||||
/**
|
||||
* getMarkedCurrUpSpeedString
|
||||
* @returns {*}
|
||||
*/
|
||||
vm.getMarkedCurrUpSpeedString = function () {
|
||||
var tmp = $translate.instant('CURR_UP_TOTAL_SPEED', {up_speed: vm.sumCUSpeed});
|
||||
return marked(tmp, {sanitize: false});
|
||||
};
|
||||
|
||||
/**
|
||||
* getMarkedCurrDownSpeedString
|
||||
* @returns {*}
|
||||
*/
|
||||
vm.getMarkedCurrDownSpeedString = function () {
|
||||
var tmp = $translate.instant('CURR_DOWN_TOTAL_SPEED', {down_speed: vm.sumCDSpeed});
|
||||
return marked(tmp, {sanitize: false});
|
||||
};
|
||||
|
||||
/**
|
||||
* getMarkedCurrScoreString
|
||||
* @returns {*}
|
||||
*/
|
||||
vm.getMarkedCurrScoreString = function () {
|
||||
var timedScore = getTimedScore();
|
||||
var speedScore = getSpeedScore();
|
||||
var seedScoreTotal = timedScore + speedScore;
|
||||
|
||||
seedScoreTotal = Math.round(seedScoreTotal * 100) / 100;
|
||||
|
||||
var tmp = $translate.instant('CURR_SCORE_INCOME_HOURS', {score_hour: seedScoreTotal});
|
||||
return marked(tmp, {sanitize: false});
|
||||
};
|
||||
|
||||
/**
|
||||
* getTimedScore
|
||||
* @returns {number}
|
||||
*/
|
||||
function getTimedScore() {
|
||||
var timedScore = 0;
|
||||
var action = vm.scoreConfig.action.seedTimed;
|
||||
var slAction = vm.scoreConfig.action.seedSeederAndLife;
|
||||
|
||||
if (action.enable && vm.groupByStatus) {
|
||||
angular.forEach(vm.groupByStatus.seeder, function (seed) {
|
||||
if (seed.torrent.torrent_status === 'reviewed') {
|
||||
var seedUnit = (60 * 60 * 1000) / action.additionTime;
|
||||
var seedScore = seedUnit * action.timedValue;
|
||||
|
||||
if (seedScore > 0) {
|
||||
//vip addition
|
||||
if (action.vipRatio && vm.user.isVip) {
|
||||
seedScore = seedScore * action.vipRatio;
|
||||
}
|
||||
|
||||
if (slAction.enable) {
|
||||
//torrent seeders count addition
|
||||
if (seed.torrent.torrent_seeds <= slAction.seederCount) {
|
||||
var seederUnit = slAction.seederBasicRatio + slAction.seederCoefficient * (slAction.seederCount - seed.torrent.torrent_seeds + 1);
|
||||
seedScore = seedScore * seederUnit;
|
||||
}
|
||||
|
||||
//torrent life addition
|
||||
var life = moment(Date.now()) - moment(seed.torrent.createdat);
|
||||
var days = life / (60 * 60 * 1000 * 24);
|
||||
var lifeUnit = slAction.lifeBasicRatio + slAction.lifeCoefficientOfDay * days;
|
||||
|
||||
lifeUnit = lifeUnit > slAction.lifeMaxRatio ? slAction.lifeMaxRatio : lifeUnit;
|
||||
seedScore = seedScore * lifeUnit;
|
||||
}
|
||||
}
|
||||
timedScore = timedScore + seedScore;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return timedScore;
|
||||
}
|
||||
|
||||
/**
|
||||
* getSpeedScore
|
||||
* @returns {number}
|
||||
*/
|
||||
function getSpeedScore() {
|
||||
var totalScore = 0;
|
||||
|
||||
var action = vm.scoreConfig.action.seedUpDownload;
|
||||
var slAction = vm.scoreConfig.action.seedSeederAndLife;
|
||||
|
||||
if (action.enable && vm.myPeers) {
|
||||
angular.forEach(vm.myPeers, function (peer) {
|
||||
var udScore = 0;
|
||||
var upUnitScore = 1;
|
||||
var downUnitScore = 1;
|
||||
var seederUnit = 1;
|
||||
var lifeUnit = 1;
|
||||
|
||||
var usize = peer.peer_cuspeed * 60 * 60;
|
||||
var dsize = peer.peer_cdspeed * 60 * 60;
|
||||
var uploadScore = 0;
|
||||
var downloadScore = 0;
|
||||
|
||||
if (usize > 0 && action.uploadEnable) {
|
||||
if (peer.torrent.torrent_size > action.additionSize) {
|
||||
upUnitScore = Math.sqrt(peer.torrent.torrent_size / action.additionSize);
|
||||
}
|
||||
var upScore = usize / action.perlSize;
|
||||
uploadScore = upUnitScore * action.uploadValue * upScore;
|
||||
//uploader addition
|
||||
if (vm.user._id == peer.torrent.user) {
|
||||
uploadScore = uploadScore * action.uploaderRatio;
|
||||
}
|
||||
}
|
||||
|
||||
if (dsize > 0 && action.downloadEnable) {
|
||||
if (peer.torrent.torrent_size > action.additionSize) {
|
||||
downUnitScore = Math.sqrt(peer.torrent.torrent_size / action.additionSize);
|
||||
}
|
||||
var downScore = dsize / action.perlSize;
|
||||
downloadScore = downUnitScore * action.downloadValue * downScore;
|
||||
}
|
||||
|
||||
udScore = uploadScore + downloadScore;
|
||||
|
||||
if (udScore > 0) {
|
||||
//vip addition
|
||||
if (action.vipRatio && vm.user.isVip) {
|
||||
udScore = udScore * action.vipRatio;
|
||||
}
|
||||
|
||||
if (slAction.enable) {
|
||||
//torrent seeders count addition
|
||||
if (peer.torrent.torrent_seeds <= slAction.seederCount) {
|
||||
seederUnit = slAction.seederBasicRatio + slAction.seederCoefficient * (slAction.seederCount - peer.torrent.torrent_seeds + 1);
|
||||
udScore = udScore * seederUnit;
|
||||
}
|
||||
|
||||
//torrent life addition
|
||||
var life = moment(Date.now()) - moment(peer.torrent.createdat);
|
||||
var days = life / (60 * 60 * 1000 * 24);
|
||||
lifeUnit = slAction.lifeBasicRatio + slAction.lifeCoefficientOfDay * days;
|
||||
|
||||
lifeUnit = lifeUnit > slAction.lifeMaxRatio ? slAction.lifeMaxRatio : lifeUnit;
|
||||
udScore = udScore * lifeUnit;
|
||||
}
|
||||
|
||||
}
|
||||
totalScore = totalScore + udScore;
|
||||
});
|
||||
}
|
||||
return totalScore;
|
||||
}
|
||||
}
|
||||
}());
|
||||
|
||||
@@ -44,4 +44,17 @@
|
||||
height: 150px;
|
||||
line-height: 0.8;
|
||||
overflow-y: scroll;
|
||||
}
|
||||
}
|
||||
|
||||
.curr-score-info {
|
||||
p {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
h5 {
|
||||
line-height: 1.5;
|
||||
margin: 0;
|
||||
}
|
||||
li {
|
||||
line-height: 1.8;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
1. 用戶積分級別數學計算公式為: `sqrt(score number / %(scoreConfig.levelStep)s)`.
|
||||
1. 級別`1` 需要積分累計: `1 * 1 * %(scoreConfig.levelStep)s`.
|
||||
1. 級別`2` 需要積分累計: `2 * 2 * %(scoreConfig.levelStep)s`.
|
||||
1. 級別`3` 需要積分累計: `3 * 3 * %(scoreConfig.levelStep)s`.
|
||||
1. 級別`4` 需要積分累計: `4 * 4 * %(scoreConfig.levelStep)s`.
|
||||
1. 級別`x` 需要積分累計: `x * x * %(scoreConfig.levelStep)s`.
|
||||
1. 用戶積分級別數學計算公式為: `sqrt(score number / %(scoreConfig.levelStep)s)`。
|
||||
1. 級別`1` 需要積分累計: `1 * 1 * %(scoreConfig.levelStep)s`。
|
||||
1. 級別`2` 需要積分累計: `2 * 2 * %(scoreConfig.levelStep)s`。
|
||||
1. 級別`3` 需要積分累計: `3 * 3 * %(scoreConfig.levelStep)s`。
|
||||
1. 級別`4` 需要積分累計: `4 * 4 * %(scoreConfig.levelStep)s`。
|
||||
1. 級別`x` 需要積分累計: `x * x * %(scoreConfig.levelStep)s`。
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
1. 用户积分级别数学计算公式为: `sqrt(score number / %(scoreConfig.levelStep)s)`.
|
||||
1. 级别`1` 需要积分累计: `1 * 1 * %(scoreConfig.levelStep)s`.
|
||||
1. 级别`2` 需要积分累计: `2 * 2 * %(scoreConfig.levelStep)s`.
|
||||
1. 级别`3` 需要积分累计: `3 * 3 * %(scoreConfig.levelStep)s`.
|
||||
1. 级别`4` 需要积分累计: `4 * 4 * %(scoreConfig.levelStep)s`.
|
||||
1. 级别`x` 需要积分累计: `x * x * %(scoreConfig.levelStep)s`.
|
||||
1. 用户积分级别数学计算公式为: `sqrt(score number / %(scoreConfig.levelStep)s)`。
|
||||
1. 级别`1` 需要积分累计: `1 * 1 * %(scoreConfig.levelStep)s`。
|
||||
1. 级别`2` 需要积分累计: `2 * 2 * %(scoreConfig.levelStep)s`。
|
||||
1. 级别`3` 需要积分累计: `3 * 3 * %(scoreConfig.levelStep)s`。
|
||||
1. 级别`4` 需要积分累计: `4 * 4 * %(scoreConfig.levelStep)s`。
|
||||
1. 级别`x` 需要积分累计: `x * x * %(scoreConfig.levelStep)s`。
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
1. 系統提供多種獲取積分的方式, 像每日簽到, 社群活動, 系統任務等.
|
||||
1. 儘可能多的下載和上傳量.
|
||||
1. 上傳種子檔案並長時間的為其它用戶做種.
|
||||
1. 在論壇積極回答用戶的問題.
|
||||
1. 系統提供多種獲取積分的方式, 像每日簽到, 社群活動, 系統任務等。
|
||||
1. 儘可能多的下載和上傳量。
|
||||
1. 上傳種子檔案並長時間的為其它用戶做種。
|
||||
1. 在論壇積極回答用戶的問題。
|
||||
1. 其它更多...
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
1. 系统提供多种获取积分的方式, 像每日签到, 社区活动, 系统任务等.
|
||||
1. 尽可能多的下载和上传量.
|
||||
1. 上传种子文件并长时间的为其它用户做种.
|
||||
1. 在论坛积极回答用户的问题.
|
||||
1. 系统提供多种获取积分的方式, 像每日签到, 社区活动, 系统任务等。
|
||||
1. 尽可能多的下载和上传量。
|
||||
1. 上传种子文件并长时间的其它用户做种。
|
||||
1. 在论坛积极回答用户的问题。
|
||||
1. 其它更多...
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
</div>
|
||||
|
||||
<div class="row margin-top-30">
|
||||
<div class="col-sm-8 col-sm-offset-2">
|
||||
<div class="col-md-8 col-md-offset-2">
|
||||
<div>
|
||||
<span>{{ vm.scoreLevelData.currLevelValue | number: 2 }}</span>
|
||||
<span class="pull-right">{{ vm.scoreLevelData.nextLevelValue | number: 2 }}</span>
|
||||
@@ -24,8 +24,8 @@
|
||||
</div>
|
||||
|
||||
<div class="row margin-top-30" ng-show="vm.inviteConfig.openInvite">
|
||||
<div class="col-sm-8 col-sm-offset-2 text-center">
|
||||
<button class="btn btn-default" ng-disabled="vm.user.score < vm.inviteConfig.scoreExchange"
|
||||
<div class="col-md-8 col-md-offset-2 text-center">
|
||||
<button class="btn btn-success" ng-disabled="vm.user.score < vm.inviteConfig.scoreExchange"
|
||||
translate="EXCHANGE_INVITATION" translate-values='{ score: vm.inviteConfig.scoreExchange}'
|
||||
ng-click="vm.exchangeInvitation();">
|
||||
</button>
|
||||
@@ -33,25 +33,41 @@
|
||||
</div>
|
||||
|
||||
<div class="row margin-top-30" ng-hide="vm.inviteConfig.openInvite">
|
||||
<div class="col-sm-8 col-sm-offset-2 text-center">
|
||||
<div class="col-md-8 col-md-offset-2 text-center">
|
||||
<div class="alert alert-warning" role="alert">
|
||||
<strong>{{ 'NOTE_CAPTION' | translate }}</strong> {{ 'INVITE_CLOSED' | translate }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row margin-top-30 padding-top-30"
|
||||
<div class="row margin-top-30" ng-init="vm.getMyPeers()">
|
||||
<div class="col-md-8 col-md-offset-2 curr-score-info">
|
||||
<legend class="small-legend"><i class="fa fa-caret-right"></i> {{'SCORE.INCOME_ESTIMATE' | translate}}</legend>
|
||||
<ul>
|
||||
<li ng-bind-html="vm.getMarkedCurrDownloadingString()"></li>
|
||||
<li ng-bind-html="vm.getMarkedCurrSeedingString()"></li>
|
||||
<li ng-bind-html="vm.getMarkedVipStatusString()"></li>
|
||||
<li ng-bind-html="vm.getMarkedCurrUpSpeedString()"></li>
|
||||
<li ng-bind-html="vm.getMarkedCurrDownSpeedString()"></li>
|
||||
</ul>
|
||||
<div class="alert alert-warning">
|
||||
<h5 ng-bind-html="vm.getMarkedCurrScoreString()"></h5>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row margin-top-30"
|
||||
ng-init="vm.getTemplateScoreFileContent('/modules/users/client/templates/how-level-'+vm.lang+'.md')">
|
||||
<div class="col-sm-8 col-sm-offset-2">
|
||||
<legend class="small-legend" translate="SCORE.HOW_TO_GET_LEVEL"></legend>
|
||||
<div class="col-md-8 col-md-offset-2 curr-score-info">
|
||||
<legend class="small-legend"><i class="fa fa-caret-right"></i> {{'SCORE.HOW_TO_GET_LEVEL' | translate}}</legend>
|
||||
<span ng-bind-html="vm.getTemplateMarkedContent(vm.templateScoreFileContent)"></span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row margin-top-30 margin-bottom-30"
|
||||
ng-init="vm.getTemplateLevelFileContent('/modules/users/client/templates/how-score-'+vm.lang+'.md')">
|
||||
<div class="col-sm-8 col-sm-offset-2">
|
||||
<legend class="small-legend" translate="SCORE.HOW_TO_GET_SCORE"></legend>
|
||||
<div class="col-md-8 col-md-offset-2 curr-score-info">
|
||||
<legend class="small-legend"><i class="fa fa-caret-right"></i> {{'SCORE.HOW_TO_GET_SCORE' | translate}}</legend>
|
||||
<span ng-bind-html="vm.getTemplateMarkedContent(vm.templateLevelFileContent)"></span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user