forked from moonshotcollective/tokenstream.party
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathStreamFactory.sol
More file actions
163 lines (141 loc) · 5.04 KB
/
StreamFactory.sol
File metadata and controls
163 lines (141 loc) · 5.04 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
//SPDX-License-Identifier: MIT
pragma solidity >=0.8.0;
import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
import "@openzeppelin/contracts/access/AccessControl.sol";
import "@openzeppelin/contracts/access/Ownable.sol";
import "./SimpleStream.sol";
/// @title Stream Factory Contract
/// @author ghostffcode
/// @notice Creates instances of SimpleStream for users
contract StreamFactory is AccessControl, Ownable {
/// @dev user address to stream address mapping
mapping(address => address) public userStreams;
/// @dev keep track if user has a stream or not
mapping(address => User) public users;
struct User {
bool hasStream;
}
struct OrgInfo {
/// @dev name of organization
string orgName;
/// @dev discription of the organization
string orgDescription;
/// @dev github URI of organization
string orgGithubURI;
/// @dev twitter URI of the organization
string orgTwitterURI;
/// @dev the website URI of organization
string orgWebURI;
/// @dev discord URI organization
string orgDiscordURI;
/// @dev URI to the logo of organization
string logoURI;
/// @dev total streams in organization
uint256 streamsCount;
/// @dev total amount paid out by organization
uint256 totalPaidOut;
}
OrgInfo public orgInfo;
/// @dev StreamAdded event to track the streams after creation
event StreamAdded(address creator, address user, address stream);
bytes32 public constant FACTORY_MANAGER = keccak256("FACTORY_MANAGER");
/// @dev modifier for the factory manager role
modifier isPermittedFactoryManager() {
require(
hasRole(FACTORY_MANAGER, msg.sender),
"Not an approved factory manager"
);
_;
}
constructor(
string memory _orgName,
string memory _logoURI,
string memory _orgDescription,
address owner,
address[] memory admins
) {
for (uint256 i = 0; i < admins.length; i++) {
_setupRole(DEFAULT_ADMIN_ROLE, admins[i]);
_setupRole(FACTORY_MANAGER, admins[i]);
}
orgInfo = OrgInfo(
_orgName,
_orgDescription,
'', // github URI
'', // twitter URI
'', // website URI
'', // discord URI
_logoURI,
0, // streams count
0 // total paid out
);
transferOwnership(owner);
}
/// @notice Creates a new stream
/// @param _toAddress the address of the payee
/// @param _cap the stream max balance for the period of time
/// @param _frequency the frequency of the stream
/// @param _startsFull does the stream start full?
/// @param _gtc the GTC token address
function createStreamFor(
address payable _toAddress,
uint256 _cap,
uint256 _frequency,
bool _startsFull,
IERC20 _gtc
) public isPermittedFactoryManager returns (address streamAddress) {
User storage user = users[_toAddress];
require(user.hasStream == false, "User already has a stream!");
user.hasStream = true;
// deploy a new stream contract
SimpleStream newStream = new SimpleStream(
_toAddress,
_cap,
_frequency,
_startsFull,
_gtc
);
streamAddress = address(newStream);
// map user to new stream
userStreams[_toAddress] = streamAddress;
orgInfo.streamsCount++;
emit StreamAdded(msg.sender, _toAddress, streamAddress);
}
/// @notice Add a existing stream to the factory
/// @param stream the stream contract address
function addStreamForUser(SimpleStream stream)
public
isPermittedFactoryManager
{
User storage user = users[stream.toAddress()];
require(user.hasStream == false, "User already has a stream!");
address payable _toAddress = stream.toAddress();
address streamAddress = address(stream);
userStreams[_toAddress] = streamAddress;
emit StreamAdded(msg.sender, _toAddress, streamAddress);
}
/// @notice returns a stream for a specified user
/// @param user the user to get a stream for
function getStreamForUser(address payable user)
public
view
returns (address streamAddress)
{
streamAddress = userStreams[user];
}
/// @notice Adds a new Factory Manager
/// @param _newFactoryManager the address of the person you are adding
function addFactoryManager(address _newFactoryManager) public onlyOwner {
grantRole(FACTORY_MANAGER, _newFactoryManager);
}
function increaseUserStreamCap(address user, uint256 increase)
public
isPermittedFactoryManager
{
SimpleStream(userStreams[user]).increaseCap(increase);
}
function releaseUserStream(address user) public isPermittedFactoryManager {
SimpleStream(userStreams[user]).transferOwnership(user);
orgInfo.streamsCount--;
}
}