Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/phabricator
Path: blob/master/src/applications/config/check/PhabricatorStorageSetupCheck.php
12256 views
1
<?php
2
3
final class PhabricatorStorageSetupCheck extends PhabricatorSetupCheck {
4
5
public function getDefaultGroup() {
6
return self::GROUP_OTHER;
7
}
8
9
/**
10
* @phutil-external-symbol class PhabricatorStartup
11
*/
12
protected function executeChecks() {
13
$engines = PhabricatorFileStorageEngine::loadWritableChunkEngines();
14
$chunk_engine_active = (bool)$engines;
15
16
$this->checkS3();
17
18
if (!$chunk_engine_active) {
19
$doc_href = PhabricatorEnv::getDoclink('Configuring File Storage');
20
21
$message = pht(
22
'Large file storage has not been configured, which will limit '.
23
'the maximum size of file uploads. See %s for '.
24
'instructions on configuring uploads and storage.',
25
phutil_tag(
26
'a',
27
array(
28
'href' => $doc_href,
29
'target' => '_blank',
30
),
31
pht('Configuring File Storage')));
32
33
$this
34
->newIssue('large-files')
35
->setShortName(pht('Large Files'))
36
->setName(pht('Large File Storage Not Configured'))
37
->setMessage($message);
38
}
39
40
$post_max_size = ini_get('post_max_size');
41
if ($post_max_size && ((int)$post_max_size > 0)) {
42
$post_max_bytes = phutil_parse_bytes($post_max_size);
43
$post_max_need = (32 * 1024 * 1024);
44
if ($post_max_need > $post_max_bytes) {
45
$summary = pht(
46
'Set %s in your PHP configuration to at least 32MB '.
47
'to support large file uploads.',
48
phutil_tag('tt', array(), 'post_max_size'));
49
50
$message = pht(
51
'Adjust %s in your PHP configuration to at least 32MB. When '.
52
'set to smaller value, large file uploads may not work properly.',
53
phutil_tag('tt', array(), 'post_max_size'));
54
55
$this
56
->newIssue('php.post_max_size')
57
->setName(pht('PHP post_max_size Not Configured'))
58
->setSummary($summary)
59
->setMessage($message)
60
->setGroup(self::GROUP_PHP)
61
->addPHPConfig('post_max_size');
62
}
63
}
64
65
// This is somewhat arbitrary, but make sure we have enough headroom to
66
// upload a default file at the chunk threshold (8MB), which may be
67
// base64 encoded, then JSON encoded in the request, and may need to be
68
// held in memory in the raw and as a query string.
69
$need_bytes = (64 * 1024 * 1024);
70
71
$memory_limit = PhabricatorStartup::getOldMemoryLimit();
72
if ($memory_limit && ((int)$memory_limit > 0)) {
73
$memory_limit_bytes = phutil_parse_bytes($memory_limit);
74
$memory_usage_bytes = memory_get_usage();
75
76
$available_bytes = ($memory_limit_bytes - $memory_usage_bytes);
77
78
if ($need_bytes > $available_bytes) {
79
$summary = pht(
80
'Your PHP memory limit is configured in a way that may prevent '.
81
'you from uploading large files or handling large requests.');
82
83
$message = pht(
84
'When you upload a file via drag-and-drop or the API, chunks must '.
85
'be buffered into memory before being written to permanent '.
86
'storage. This server needs memory available to store these '.
87
'chunks while they are uploaded, but PHP is currently configured '.
88
'to severely limit the available memory.'.
89
"\n\n".
90
'PHP processes currently have very little free memory available '.
91
'(%s). To work well, processes should have at least %s.'.
92
"\n\n".
93
'(Note that the application itself must also fit in available '.
94
'memory, so not all of the memory under the memory limit is '.
95
'available for running workloads.)'.
96
"\n\n".
97
"The easiest way to resolve this issue is to set %s to %s in your ".
98
"PHP configuration, to disable the memory limit. There is ".
99
"usually little or no value to using this option to limit ".
100
"process memory.".
101
"\n\n".
102
"You can also increase the limit or ignore this issue and accept ".
103
"that you may encounter problems uploading large files and ".
104
"processing large requests.",
105
phutil_format_bytes($available_bytes),
106
phutil_format_bytes($need_bytes),
107
phutil_tag('tt', array(), 'memory_limit'),
108
phutil_tag('tt', array(), '-1'));
109
110
$this
111
->newIssue('php.memory_limit.upload')
112
->setName(pht('Memory Limit Restricts File Uploads'))
113
->setSummary($summary)
114
->setMessage($message)
115
->setGroup(self::GROUP_PHP)
116
->addPHPConfig('memory_limit')
117
->addPHPConfigOriginalValue('memory_limit', $memory_limit);
118
}
119
}
120
121
122
$local_path = PhabricatorEnv::getEnvConfig('storage.local-disk.path');
123
if (!$local_path) {
124
return;
125
}
126
127
if (!Filesystem::pathExists($local_path) ||
128
!is_readable($local_path) ||
129
!is_writable($local_path)) {
130
131
$message = pht(
132
'Configured location for storing uploaded files on disk ("%s") does '.
133
'not exist, or is not readable or writable. Verify the directory '.
134
'exists and is readable and writable by the webserver.',
135
$local_path);
136
137
$this
138
->newIssue('config.storage.local-disk.path')
139
->setShortName(pht('Local Disk Storage'))
140
->setName(pht('Local Disk Storage Not Readable/Writable'))
141
->setMessage($message)
142
->addPhabricatorConfig('storage.local-disk.path');
143
}
144
}
145
146
private function checkS3() {
147
$access_key = PhabricatorEnv::getEnvConfig('amazon-s3.access-key');
148
$secret_key = PhabricatorEnv::getEnvConfig('amazon-s3.secret-key');
149
$region = PhabricatorEnv::getEnvConfig('amazon-s3.region');
150
$endpoint = PhabricatorEnv::getEnvConfig('amazon-s3.endpoint');
151
152
$how_many = 0;
153
154
if ($access_key !== null && strlen($access_key)) {
155
$how_many++;
156
}
157
158
if ($secret_key !== null && strlen($secret_key)) {
159
$how_many++;
160
}
161
162
if ($region !== null && strlen($region)) {
163
$how_many++;
164
}
165
166
if ($endpoint !== null && strlen($endpoint)) {
167
$how_many++;
168
}
169
170
// Nothing configured, no issues here.
171
if ($how_many === 0) {
172
return;
173
}
174
175
// Everything configured, no issues here.
176
if ($how_many === 4) {
177
return;
178
}
179
180
$message = pht(
181
'File storage in Amazon S3 has been partially configured, but you are '.
182
'missing some required settings. S3 will not be available to store '.
183
'files until you complete the configuration. Either configure S3 fully '.
184
'or remove the partial configuration.');
185
186
$this->newIssue('storage.s3.partial-config')
187
->setShortName(pht('S3 Partially Configured'))
188
->setName(pht('Amazon S3 is Only Partially Configured'))
189
->setMessage($message)
190
->addPhabricatorConfig('amazon-s3.access-key')
191
->addPhabricatorConfig('amazon-s3.secret-key')
192
->addPhabricatorConfig('amazon-s3.region')
193
->addPhabricatorConfig('amazon-s3.endpoint');
194
}
195
196
}
197
198