1
+ pragma solidity ^ 0.4.18 ;
2
+
3
+ import "./zeppelin/math/SafeMath.sol " ;
4
+ import "./zeppelin/lifecycle/Pausable.sol " ;
5
+ import "./zeppelin/ownership/Ownable.sol " ;
6
+ import "./interfaces/I_Bank.sol " ;
7
+ import "./token/LibreCash.sol " ;
8
+ import "./ComplexExchanger.sol " ;
9
+
10
+
11
+ contract Deposit is Ownable {
12
+ using SafeMath for uint256 ;
13
+ address public Libre;
14
+ LibreCash libre;
15
+
16
+ uint256 public needAmount = 20000 ether ;
17
+ uint256 constant REVERSE_PERCENT = 10000 ;
18
+ uint256 constant YEAR_SECONDS = 365.25 * 24 * 60 * 60 ;
19
+ uint256 public lockedTokens = 0 ;
20
+
21
+ DepositPlan[] public plans;
22
+
23
+ event NewDeposit (address beneficiar , uint256 timestamp , uint256 deadline , uint256 amount , uint256 margin );
24
+ event ClaimDeposit (address beneficiar , uint256 amount , uint256 margin );
25
+
26
+ struct OwnDeposit {
27
+ uint256 timestamp;
28
+ uint256 deadline;
29
+ uint256 amount;
30
+ uint256 margin;
31
+ string plan;
32
+ }
33
+
34
+ struct DepositPlan {
35
+ uint256 period;
36
+ uint256 percent;
37
+ uint256 minAmount;
38
+ string description;
39
+ }
40
+
41
+ mapping (address => OwnDeposit[]) public deposits;
42
+
43
+ /**
44
+ * @dev Constructor.
45
+ * @param _libre Address of LibreCash contract.
46
+ */
47
+ function Deposit (address _libre ) public {
48
+ Libre = _libre;
49
+ libre = LibreCash (Libre);
50
+ }
51
+
52
+ /**
53
+ * @dev Set amount the contract needs.
54
+ * @param _amount New amount.
55
+ */
56
+ function setAmount (uint256 _amount ) public onlyOwner {
57
+ needAmount = _amount;
58
+ }
59
+
60
+ /**
61
+ * @dev Return count deposits.
62
+ */
63
+ function myDepositCount () public view returns (uint256 ) {
64
+ return deposits[msg .sender ].length ;
65
+ }
66
+
67
+ /**
68
+ * @dev Lets user to get back his deposit with margin after deadline.
69
+ * @param _id Deposit ID.
70
+ */
71
+ function claimDeposit (uint256 _id ) public {
72
+ OwnDeposit storage dep = deposits[msg .sender ][_id];
73
+ require (dep.deadline <= now );
74
+ uint256 refundAmount = dep.amount.add (dep.margin);
75
+ lockedTokens = lockedTokens.sub (refundAmount);
76
+ needAmount = needAmount.add (dep.amount);
77
+ libre.transfer (msg .sender , refundAmount);
78
+ ClaimDeposit (msg .sender , dep.amount, dep.margin);
79
+ delete deposits[msg .sender ][_id];
80
+ }
81
+
82
+ /**
83
+ * @dev Creates deposit plan.
84
+ * @param _period Deposit period (lifetime in seconds).
85
+ * @param _percent Deposit percentage (annual).
86
+ * @param _minAmount Minimum deposit amount.
87
+ * @param _description Plan description.
88
+ */
89
+ function createPlan (uint256 _period , uint256 _percent , uint256 _minAmount , string _description ) public onlyOwner {
90
+ require (_period > 0 );
91
+ plans.push (DepositPlan (_period, _percent, _minAmount, _description));
92
+ }
93
+
94
+ /**
95
+ * @dev Delete deposit plan.
96
+ * @param _id Deposit plan ID.
97
+ */
98
+ function deletePlan (uint256 _id ) public onlyOwner {
99
+ delete plans[_id];
100
+ }
101
+
102
+ /**
103
+ * @dev Change deposit plan.
104
+ * @param _id Deposit plan ID.
105
+ * @param _period Deposit period (lifetime in seconds).
106
+ * @param _percent Deposit percentage (annual).
107
+ * @param _minAmount Minimum deposit amount.
108
+ * @param _description Plan description.
109
+ */
110
+ function changePlan (uint256 _id , uint256 _period , uint256 _percent , uint256 _minAmount , string _description ) public onlyOwner {
111
+ require (_period > 0 );
112
+ plans[_id] = DepositPlan (_period, _percent, _minAmount, _description);
113
+ }
114
+
115
+ /**
116
+ * @dev Create deposit.
117
+ * @param _amount Libre amount.
118
+ * @param _planId Deposit plan ID.
119
+ */
120
+ function createDeposit (uint256 _amount , uint256 _planId ) public {
121
+ _amount = (_amount <= needAmount) ? _amount : needAmount;
122
+ DepositPlan memory plan = plans[_planId];
123
+ uint256 margin = calcProfit (_amount, _planId);
124
+
125
+ require (_amount >= plan.minAmount && _amount.add (margin) <= availableTokens ());
126
+ lockedTokens = lockedTokens.add (margin).add (_amount);
127
+
128
+ libre.transferFrom (msg .sender , this , _amount);
129
+ deposits[msg .sender ].push (OwnDeposit (
130
+ now ,
131
+ now .add (plan.period),
132
+ _amount,
133
+ margin,
134
+ plan.description
135
+ ));
136
+
137
+ needAmount = needAmount.sub (_amount);
138
+ NewDeposit (msg .sender , now , now .add (plan.period), _amount, margin);
139
+ }
140
+
141
+ /**
142
+ * @dev Get available tokens on the deposit contract.
143
+ */
144
+ function availableTokens () public view returns (uint256 ) {
145
+ return libre.balanceOf (this ).sub (lockedTokens);
146
+ }
147
+
148
+ /**
149
+ * @dev Calculate potential profit.
150
+ * @param _amount Libre amount.
151
+ * @param _planId Deposit plan ID.
152
+ */
153
+ function calcProfit (uint256 _amount , uint256 _planId ) public view returns (uint256 ) {
154
+ DepositPlan storage plan = plans[_planId];
155
+ // yearlyProfitX100 = _amount * percent * 100
156
+ uint256 yearlyProfitX100 = _amount.mul (plan.percent);
157
+ // periodicProfit = yearlyProfitX100 * period / 365.25 days / 100
158
+ uint256 periodicProfit = yearlyProfitX100.mul (plan.period).div (YEAR_SECONDS).div (REVERSE_PERCENT);
159
+ return periodicProfit;
160
+ }
161
+
162
+ /**
163
+ * @dev Gets deposit plans count.
164
+ */
165
+ function plansCount () public view returns (uint256 ) {
166
+ return plans.length ;
167
+ }
168
+ }
0 commit comments