diff options
author | ArthurHoaro <arthur@hoa.ro> | 2017-05-07 17:40:17 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2017-05-07 17:40:17 +0200 |
commit | b4189928f84758e1589715dfe04e2d966a4f3b88 (patch) | |
tree | f17b8fa91fe8244fed7a913d64ce3220551916ff | |
parent | a4af59f47103a3f9c903eeddb1e30ab9cb7344f0 (diff) | |
parent | b86aeccf6a99a9617c66cded7252a33b1df560cd (diff) | |
download | Shaarli-b4189928f84758e1589715dfe04e2d966a4f3b88.tar.gz Shaarli-b4189928f84758e1589715dfe04e2d966a4f3b88.tar.zst Shaarli-b4189928f84758e1589715dfe04e2d966a4f3b88.zip |
Merge pull request #858 from ArthurHoaro/api/history-entries
Add history entries for API endpoint
-rw-r--r-- | application/FileUtils.php | 2 | ||||
-rw-r--r-- | application/History.php | 4 | ||||
-rw-r--r-- | application/Updater.php | 11 | ||||
-rw-r--r-- | application/api/ApiMiddleware.php | 5 | ||||
-rw-r--r-- | application/api/controllers/ApiController.php | 9 | ||||
-rw-r--r-- | application/api/controllers/History.php | 3 | ||||
-rw-r--r-- | application/api/controllers/Links.php | 5 | ||||
-rw-r--r-- | index.php | 20 | ||||
-rw-r--r-- | tests/HistoryTest.php | 24 | ||||
-rw-r--r-- | tests/NetscapeBookmarkUtils/BookmarkImportTest.php | 4 | ||||
-rw-r--r-- | tests/api/controllers/DeleteLinkTest.php | 22 | ||||
-rw-r--r-- | tests/api/controllers/GetLinkIdTest.php | 1 | ||||
-rw-r--r-- | tests/api/controllers/GetLinksTest.php | 1 | ||||
-rw-r--r-- | tests/api/controllers/HistoryTest.php | 7 | ||||
-rw-r--r-- | tests/api/controllers/InfoTest.php | 1 | ||||
-rw-r--r-- | tests/api/controllers/PostLinkTest.php | 23 | ||||
-rw-r--r-- | tests/api/controllers/PutLinkTest.php | 23 | ||||
-rw-r--r-- | tests/utils/ReferenceHistory.php | 22 |
18 files changed, 137 insertions, 50 deletions
diff --git a/application/FileUtils.php b/application/FileUtils.php index b8ad8970..a167f642 100644 --- a/application/FileUtils.php +++ b/application/FileUtils.php | |||
@@ -26,7 +26,7 @@ class FileUtils | |||
26 | * The file will be created if it doesn't exist. | 26 | * The file will be created if it doesn't exist. |
27 | * | 27 | * |
28 | * @param string $file File path. | 28 | * @param string $file File path. |
29 | * @param string $content Content to write. | 29 | * @param mixed $content Content to write. |
30 | * | 30 | * |
31 | * @return int|bool Number of bytes written or false if it fails. | 31 | * @return int|bool Number of bytes written or false if it fails. |
32 | * | 32 | * |
diff --git a/application/History.php b/application/History.php index f93b0356..116b9264 100644 --- a/application/History.php +++ b/application/History.php | |||
@@ -135,7 +135,7 @@ class History | |||
135 | 135 | ||
136 | $item = [ | 136 | $item = [ |
137 | 'event' => $status, | 137 | 'event' => $status, |
138 | 'datetime' => (new DateTime())->format(DateTime::ATOM), | 138 | 'datetime' => new DateTime(), |
139 | 'id' => $id !== null ? $id : '', | 139 | 'id' => $id !== null ? $id : '', |
140 | ]; | 140 | ]; |
141 | $this->history = array_merge([$item], $this->history); | 141 | $this->history = array_merge([$item], $this->history); |
@@ -177,7 +177,7 @@ class History | |||
177 | { | 177 | { |
178 | $comparaison = new DateTime('-'. $this->retentionTime . ' seconds'); | 178 | $comparaison = new DateTime('-'. $this->retentionTime . ' seconds'); |
179 | foreach ($this->history as $key => $value) { | 179 | foreach ($this->history as $key => $value) { |
180 | if (DateTime::createFromFormat(DateTime::ATOM, $value['datetime']) < $comparaison) { | 180 | if ($value['datetime'] < $comparaison) { |
181 | unset($this->history[$key]); | 181 | unset($this->history[$key]); |
182 | } | 182 | } |
183 | } | 183 | } |
diff --git a/application/Updater.php b/application/Updater.php index 0fb68c5a..03d93a6f 100644 --- a/application/Updater.php +++ b/application/Updater.php | |||
@@ -440,6 +440,17 @@ class Updater | |||
440 | $this->conf->write($this->isLoggedIn); | 440 | $this->conf->write($this->isLoggedIn); |
441 | return true; | 441 | return true; |
442 | } | 442 | } |
443 | |||
444 | /** | ||
445 | * Reset history store file due to date format change. | ||
446 | */ | ||
447 | public function updateMethodResetHistoryFile() | ||
448 | { | ||
449 | if (is_file($this->conf->get('resource.history'))) { | ||
450 | unlink($this->conf->get('resource.history')); | ||
451 | } | ||
452 | return true; | ||
453 | } | ||
443 | } | 454 | } |
444 | 455 | ||
445 | /** | 456 | /** |
diff --git a/application/api/ApiMiddleware.php b/application/api/ApiMiddleware.php index 4120f7a9..ff209393 100644 --- a/application/api/ApiMiddleware.php +++ b/application/api/ApiMiddleware.php | |||
@@ -4,6 +4,7 @@ namespace Shaarli\Api; | |||
4 | use Shaarli\Api\Exceptions\ApiException; | 4 | use Shaarli\Api\Exceptions\ApiException; |
5 | use Shaarli\Api\Exceptions\ApiAuthorizationException; | 5 | use Shaarli\Api\Exceptions\ApiAuthorizationException; |
6 | 6 | ||
7 | use Shaarli\Config\ConfigManager; | ||
7 | use Slim\Container; | 8 | use Slim\Container; |
8 | use Slim\Http\Request; | 9 | use Slim\Http\Request; |
9 | use Slim\Http\Response; | 10 | use Slim\Http\Response; |
@@ -31,7 +32,7 @@ class ApiMiddleware | |||
31 | protected $container; | 32 | protected $container; |
32 | 33 | ||
33 | /** | 34 | /** |
34 | * @var \ConfigManager instance. | 35 | * @var ConfigManager instance. |
35 | */ | 36 | */ |
36 | protected $conf; | 37 | protected $conf; |
37 | 38 | ||
@@ -121,7 +122,7 @@ class ApiMiddleware | |||
121 | * | 122 | * |
122 | * FIXME! LinkDB could use a refactoring to avoid this trick. | 123 | * FIXME! LinkDB could use a refactoring to avoid this trick. |
123 | * | 124 | * |
124 | * @param \ConfigManager $conf instance. | 125 | * @param ConfigManager $conf instance. |
125 | */ | 126 | */ |
126 | protected function setLinkDb($conf) | 127 | protected function setLinkDb($conf) |
127 | { | 128 | { |
diff --git a/application/api/controllers/ApiController.php b/application/api/controllers/ApiController.php index f35b923a..3be85b98 100644 --- a/application/api/controllers/ApiController.php +++ b/application/api/controllers/ApiController.php | |||
@@ -2,6 +2,7 @@ | |||
2 | 2 | ||
3 | namespace Shaarli\Api\Controllers; | 3 | namespace Shaarli\Api\Controllers; |
4 | 4 | ||
5 | use Shaarli\Config\ConfigManager; | ||
5 | use \Slim\Container; | 6 | use \Slim\Container; |
6 | 7 | ||
7 | /** | 8 | /** |
@@ -19,7 +20,7 @@ abstract class ApiController | |||
19 | protected $ci; | 20 | protected $ci; |
20 | 21 | ||
21 | /** | 22 | /** |
22 | * @var \ConfigManager | 23 | * @var ConfigManager |
23 | */ | 24 | */ |
24 | protected $conf; | 25 | protected $conf; |
25 | 26 | ||
@@ -29,6 +30,11 @@ abstract class ApiController | |||
29 | protected $linkDb; | 30 | protected $linkDb; |
30 | 31 | ||
31 | /** | 32 | /** |
33 | * @var \History | ||
34 | */ | ||
35 | protected $history; | ||
36 | |||
37 | /** | ||
32 | * @var int|null JSON style option. | 38 | * @var int|null JSON style option. |
33 | */ | 39 | */ |
34 | protected $jsonStyle; | 40 | protected $jsonStyle; |
@@ -45,6 +51,7 @@ abstract class ApiController | |||
45 | $this->ci = $ci; | 51 | $this->ci = $ci; |
46 | $this->conf = $ci->get('conf'); | 52 | $this->conf = $ci->get('conf'); |
47 | $this->linkDb = $ci->get('db'); | 53 | $this->linkDb = $ci->get('db'); |
54 | $this->history = $ci->get('history'); | ||
48 | if ($this->conf->get('dev.debug', false)) { | 55 | if ($this->conf->get('dev.debug', false)) { |
49 | $this->jsonStyle = JSON_PRETTY_PRINT; | 56 | $this->jsonStyle = JSON_PRETTY_PRINT; |
50 | } else { | 57 | } else { |
diff --git a/application/api/controllers/History.php b/application/api/controllers/History.php index c4ff3e5d..2ff9deaf 100644 --- a/application/api/controllers/History.php +++ b/application/api/controllers/History.php | |||
@@ -28,8 +28,7 @@ class History extends ApiController | |||
28 | */ | 28 | */ |
29 | public function getHistory($request, $response) | 29 | public function getHistory($request, $response) |
30 | { | 30 | { |
31 | $history = (new \History($this->conf->get('resource.history')))->getHistory(); | 31 | $history = $this->history->getHistory(); |
32 | $history = array_reverse($history); | ||
33 | 32 | ||
34 | // Return history operations from the {offset}th, starting from {since}. | 33 | // Return history operations from the {offset}th, starting from {since}. |
35 | $since = \DateTime::createFromFormat(\DateTime::ATOM, $request->getParam('since')); | 34 | $since = \DateTime::createFromFormat(\DateTime::ATOM, $request->getParam('since')); |
diff --git a/application/api/controllers/Links.php b/application/api/controllers/Links.php index a40e974d..eb78dd26 100644 --- a/application/api/controllers/Links.php +++ b/application/api/controllers/Links.php | |||
@@ -141,6 +141,7 @@ class Links extends ApiController | |||
141 | 141 | ||
142 | $this->linkDb[$link['id']] = $link; | 142 | $this->linkDb[$link['id']] = $link; |
143 | $this->linkDb->save($this->conf->get('resource.page_cache')); | 143 | $this->linkDb->save($this->conf->get('resource.page_cache')); |
144 | $this->history->addLink($link); | ||
144 | $out = ApiUtils::formatLink($link, index_url($this->ci['environment'])); | 145 | $out = ApiUtils::formatLink($link, index_url($this->ci['environment'])); |
145 | $redirect = $this->ci->router->relativePathFor('getLink', ['id' => $link['id']]); | 146 | $redirect = $this->ci->router->relativePathFor('getLink', ['id' => $link['id']]); |
146 | return $response->withAddedHeader('Location', $redirect) | 147 | return $response->withAddedHeader('Location', $redirect) |
@@ -184,6 +185,7 @@ class Links extends ApiController | |||
184 | $responseLink = ApiUtils::updateLink($responseLink, $requestLink); | 185 | $responseLink = ApiUtils::updateLink($responseLink, $requestLink); |
185 | $this->linkDb[$responseLink['id']] = $responseLink; | 186 | $this->linkDb[$responseLink['id']] = $responseLink; |
186 | $this->linkDb->save($this->conf->get('resource.page_cache')); | 187 | $this->linkDb->save($this->conf->get('resource.page_cache')); |
188 | $this->history->updateLink($responseLink); | ||
187 | 189 | ||
188 | $out = ApiUtils::formatLink($responseLink, $index); | 190 | $out = ApiUtils::formatLink($responseLink, $index); |
189 | return $response->withJson($out, 200, $this->jsonStyle); | 191 | return $response->withJson($out, 200, $this->jsonStyle); |
@@ -205,9 +207,10 @@ class Links extends ApiController | |||
205 | if (! isset($this->linkDb[$args['id']])) { | 207 | if (! isset($this->linkDb[$args['id']])) { |
206 | throw new ApiLinkNotFoundException(); | 208 | throw new ApiLinkNotFoundException(); |
207 | } | 209 | } |
208 | 210 | $link = $this->linkDb[$args['id']]; | |
209 | unset($this->linkDb[(int) $args['id']]); | 211 | unset($this->linkDb[(int) $args['id']]); |
210 | $this->linkDb->save($this->conf->get('resource.page_cache')); | 212 | $this->linkDb->save($this->conf->get('resource.page_cache')); |
213 | $this->history->deleteLink($link); | ||
211 | 214 | ||
212 | return $response->withStatus(204); | 215 | return $response->withStatus(204); |
213 | } | 216 | } |
@@ -707,7 +707,7 @@ function showLinkList($PAGE, $LINKSDB, $conf, $pluginManager) { | |||
707 | * @param PluginManager $pluginManager Plugin Manager instance, | 707 | * @param PluginManager $pluginManager Plugin Manager instance, |
708 | * @param LinkDB $LINKSDB | 708 | * @param LinkDB $LINKSDB |
709 | */ | 709 | */ |
710 | function renderPage($conf, $pluginManager, $LINKSDB) | 710 | function renderPage($conf, $pluginManager, $LINKSDB, $history) |
711 | { | 711 | { |
712 | $updater = new Updater( | 712 | $updater = new Updater( |
713 | read_updates_file($conf->get('resource.updates')), | 713 | read_updates_file($conf->get('resource.updates')), |
@@ -728,12 +728,6 @@ function renderPage($conf, $pluginManager, $LINKSDB) | |||
728 | die($e->getMessage()); | 728 | die($e->getMessage()); |
729 | } | 729 | } |
730 | 730 | ||
731 | try { | ||
732 | $history = new History($conf->get('resource.history')); | ||
733 | } catch(Exception $e) { | ||
734 | die($e->getMessage()); | ||
735 | } | ||
736 | |||
737 | $PAGE = new PageBuilder($conf); | 731 | $PAGE = new PageBuilder($conf); |
738 | $PAGE->assign('linkcount', count($LINKSDB)); | 732 | $PAGE->assign('linkcount', count($LINKSDB)); |
739 | $PAGE->assign('privateLinkcount', count_private($LINKSDB)); | 733 | $PAGE->assign('privateLinkcount', count_private($LINKSDB)); |
@@ -1167,7 +1161,6 @@ function renderPage($conf, $pluginManager, $LINKSDB) | |||
1167 | $PAGE->assign('hide_public_links', $conf->get('privacy.hide_public_links', false)); | 1161 | $PAGE->assign('hide_public_links', $conf->get('privacy.hide_public_links', false)); |
1168 | $PAGE->assign('api_enabled', $conf->get('api.enabled', true)); | 1162 | $PAGE->assign('api_enabled', $conf->get('api.enabled', true)); |
1169 | $PAGE->assign('api_secret', $conf->get('api.secret')); | 1163 | $PAGE->assign('api_secret', $conf->get('api.secret')); |
1170 | $history->updateSettings(); | ||
1171 | $PAGE->renderPage('configure'); | 1164 | $PAGE->renderPage('configure'); |
1172 | exit; | 1165 | exit; |
1173 | } | 1166 | } |
@@ -1578,7 +1571,6 @@ function renderPage($conf, $pluginManager, $LINKSDB) | |||
1578 | 1571 | ||
1579 | // Plugin administration form action | 1572 | // Plugin administration form action |
1580 | if ($targetPage == Router::$PAGE_SAVE_PLUGINSADMIN) { | 1573 | if ($targetPage == Router::$PAGE_SAVE_PLUGINSADMIN) { |
1581 | $history->updateSettings(); | ||
1582 | try { | 1574 | try { |
1583 | if (isset($_POST['parameters_form'])) { | 1575 | if (isset($_POST['parameters_form'])) { |
1584 | unset($_POST['parameters_form']); | 1576 | unset($_POST['parameters_form']); |
@@ -1590,6 +1582,7 @@ function renderPage($conf, $pluginManager, $LINKSDB) | |||
1590 | $conf->set('general.enabled_plugins', save_plugin_config($_POST)); | 1582 | $conf->set('general.enabled_plugins', save_plugin_config($_POST)); |
1591 | } | 1583 | } |
1592 | $conf->write(isLoggedIn()); | 1584 | $conf->write(isLoggedIn()); |
1585 | $history->updateSettings(); | ||
1593 | } | 1586 | } |
1594 | catch (Exception $e) { | 1587 | catch (Exception $e) { |
1595 | error_log( | 1588 | error_log( |
@@ -2240,9 +2233,16 @@ $linkDb = new LinkDB( | |||
2240 | $conf->get('redirector.encode_url') | 2233 | $conf->get('redirector.encode_url') |
2241 | ); | 2234 | ); |
2242 | 2235 | ||
2236 | try { | ||
2237 | $history = new History($conf->get('resource.history')); | ||
2238 | } catch(Exception $e) { | ||
2239 | die($e->getMessage()); | ||
2240 | } | ||
2241 | |||
2243 | $container = new \Slim\Container(); | 2242 | $container = new \Slim\Container(); |
2244 | $container['conf'] = $conf; | 2243 | $container['conf'] = $conf; |
2245 | $container['plugins'] = $pluginManager; | 2244 | $container['plugins'] = $pluginManager; |
2245 | $container['history'] = $history; | ||
2246 | $app = new \Slim\App($container); | 2246 | $app = new \Slim\App($container); |
2247 | 2247 | ||
2248 | // REST API routes | 2248 | // REST API routes |
@@ -2262,7 +2262,7 @@ $response = $app->run(true); | |||
2262 | if ($response->getStatusCode() == 404 && strpos($_SERVER['REQUEST_URI'], '/api/v1') === false) { | 2262 | if ($response->getStatusCode() == 404 && strpos($_SERVER['REQUEST_URI'], '/api/v1') === false) { |
2263 | // We use UTF-8 for proper international characters handling. | 2263 | // We use UTF-8 for proper international characters handling. |
2264 | header('Content-Type: text/html; charset=utf-8'); | 2264 | header('Content-Type: text/html; charset=utf-8'); |
2265 | renderPage($conf, $pluginManager, $linkDb); | 2265 | renderPage($conf, $pluginManager, $linkDb, $history); |
2266 | } else { | 2266 | } else { |
2267 | $app->respond($response); | 2267 | $app->respond($response); |
2268 | } | 2268 | } |
diff --git a/tests/HistoryTest.php b/tests/HistoryTest.php index 91525845..d3bef5a3 100644 --- a/tests/HistoryTest.php +++ b/tests/HistoryTest.php | |||
@@ -74,21 +74,21 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
74 | $history->addLink(['id' => 0]); | 74 | $history->addLink(['id' => 0]); |
75 | $actual = $history->getHistory()[0]; | 75 | $actual = $history->getHistory()[0]; |
76 | $this->assertEquals(History::CREATED, $actual['event']); | 76 | $this->assertEquals(History::CREATED, $actual['event']); |
77 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 77 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
78 | $this->assertEquals(0, $actual['id']); | 78 | $this->assertEquals(0, $actual['id']); |
79 | 79 | ||
80 | $history = new History(self::$historyFilePath); | 80 | $history = new History(self::$historyFilePath); |
81 | $history->addLink(['id' => 1]); | 81 | $history->addLink(['id' => 1]); |
82 | $actual = $history->getHistory()[0]; | 82 | $actual = $history->getHistory()[0]; |
83 | $this->assertEquals(History::CREATED, $actual['event']); | 83 | $this->assertEquals(History::CREATED, $actual['event']); |
84 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 84 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
85 | $this->assertEquals(1, $actual['id']); | 85 | $this->assertEquals(1, $actual['id']); |
86 | 86 | ||
87 | $history = new History(self::$historyFilePath); | 87 | $history = new History(self::$historyFilePath); |
88 | $history->addLink(['id' => 'str']); | 88 | $history->addLink(['id' => 'str']); |
89 | $actual = $history->getHistory()[0]; | 89 | $actual = $history->getHistory()[0]; |
90 | $this->assertEquals(History::CREATED, $actual['event']); | 90 | $this->assertEquals(History::CREATED, $actual['event']); |
91 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 91 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
92 | $this->assertEquals('str', $actual['id']); | 92 | $this->assertEquals('str', $actual['id']); |
93 | } | 93 | } |
94 | 94 | ||
@@ -101,7 +101,7 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
101 | $history->updateLink(['id' => 1]); | 101 | $history->updateLink(['id' => 1]); |
102 | $actual = $history->getHistory()[0]; | 102 | $actual = $history->getHistory()[0]; |
103 | $this->assertEquals(History::UPDATED, $actual['event']); | 103 | $this->assertEquals(History::UPDATED, $actual['event']); |
104 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 104 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
105 | $this->assertEquals(1, $actual['id']); | 105 | $this->assertEquals(1, $actual['id']); |
106 | } | 106 | } |
107 | 107 | ||
@@ -114,7 +114,7 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
114 | $history->deleteLink(['id' => 1]); | 114 | $history->deleteLink(['id' => 1]); |
115 | $actual = $history->getHistory()[0]; | 115 | $actual = $history->getHistory()[0]; |
116 | $this->assertEquals(History::DELETED, $actual['event']); | 116 | $this->assertEquals(History::DELETED, $actual['event']); |
117 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 117 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
118 | $this->assertEquals(1, $actual['id']); | 118 | $this->assertEquals(1, $actual['id']); |
119 | } | 119 | } |
120 | 120 | ||
@@ -127,7 +127,7 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
127 | $history->updateSettings(); | 127 | $history->updateSettings(); |
128 | $actual = $history->getHistory()[0]; | 128 | $actual = $history->getHistory()[0]; |
129 | $this->assertEquals(History::SETTINGS, $actual['event']); | 129 | $this->assertEquals(History::SETTINGS, $actual['event']); |
130 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 130 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
131 | $this->assertEmpty($actual['id']); | 131 | $this->assertEmpty($actual['id']); |
132 | } | 132 | } |
133 | 133 | ||
@@ -140,13 +140,13 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
140 | $history->updateLink(['id' => 1]); | 140 | $history->updateLink(['id' => 1]); |
141 | $actual = $history->getHistory()[0]; | 141 | $actual = $history->getHistory()[0]; |
142 | $this->assertEquals(History::UPDATED, $actual['event']); | 142 | $this->assertEquals(History::UPDATED, $actual['event']); |
143 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 143 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
144 | $this->assertEquals(1, $actual['id']); | 144 | $this->assertEquals(1, $actual['id']); |
145 | 145 | ||
146 | $history->addLink(['id' => 1]); | 146 | $history->addLink(['id' => 1]); |
147 | $actual = $history->getHistory()[0]; | 147 | $actual = $history->getHistory()[0]; |
148 | $this->assertEquals(History::CREATED, $actual['event']); | 148 | $this->assertEquals(History::CREATED, $actual['event']); |
149 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 149 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
150 | $this->assertEquals(1, $actual['id']); | 150 | $this->assertEquals(1, $actual['id']); |
151 | } | 151 | } |
152 | 152 | ||
@@ -160,7 +160,7 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
160 | $history = new History(self::$historyFilePath); | 160 | $history = new History(self::$historyFilePath); |
161 | $actual = $history->getHistory()[0]; | 161 | $actual = $history->getHistory()[0]; |
162 | $this->assertEquals(History::UPDATED, $actual['event']); | 162 | $this->assertEquals(History::UPDATED, $actual['event']); |
163 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 163 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
164 | $this->assertEquals(1, $actual['id']); | 164 | $this->assertEquals(1, $actual['id']); |
165 | } | 165 | } |
166 | 166 | ||
@@ -176,12 +176,12 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
176 | $history = new History(self::$historyFilePath); | 176 | $history = new History(self::$historyFilePath); |
177 | $actual = $history->getHistory()[0]; | 177 | $actual = $history->getHistory()[0]; |
178 | $this->assertEquals(History::CREATED, $actual['event']); | 178 | $this->assertEquals(History::CREATED, $actual['event']); |
179 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 179 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
180 | $this->assertEquals(1, $actual['id']); | 180 | $this->assertEquals(1, $actual['id']); |
181 | 181 | ||
182 | $actual = $history->getHistory()[1]; | 182 | $actual = $history->getHistory()[1]; |
183 | $this->assertEquals(History::UPDATED, $actual['event']); | 183 | $this->assertEquals(History::UPDATED, $actual['event']); |
184 | $this->assertTrue(new DateTime('-2 seconds') < DateTime::createFromFormat(DateTime::ATOM, $actual['datetime'])); | 184 | $this->assertTrue(new DateTime('-2 seconds') < $actual['datetime']); |
185 | $this->assertEquals(1, $actual['id']); | 185 | $this->assertEquals(1, $actual['id']); |
186 | } | 186 | } |
187 | 187 | ||
@@ -194,7 +194,7 @@ class HistoryTest extends PHPUnit_Framework_TestCase | |||
194 | $history->updateLink(['id' => 1]); | 194 | $history->updateLink(['id' => 1]); |
195 | $this->assertEquals(1, count($history->getHistory())); | 195 | $this->assertEquals(1, count($history->getHistory())); |
196 | $arr = $history->getHistory(); | 196 | $arr = $history->getHistory(); |
197 | $arr[0]['datetime'] = (new DateTime('-1 hour'))->format(DateTime::ATOM); | 197 | $arr[0]['datetime'] = new DateTime('-1 hour'); |
198 | FileUtils::writeFlatDB(self::$historyFilePath, $arr); | 198 | FileUtils::writeFlatDB(self::$historyFilePath, $arr); |
199 | 199 | ||
200 | $history = new History(self::$historyFilePath, 60); | 200 | $history = new History(self::$historyFilePath, 60); |
diff --git a/tests/NetscapeBookmarkUtils/BookmarkImportTest.php b/tests/NetscapeBookmarkUtils/BookmarkImportTest.php index f838f259..5fc1d1e8 100644 --- a/tests/NetscapeBookmarkUtils/BookmarkImportTest.php +++ b/tests/NetscapeBookmarkUtils/BookmarkImportTest.php | |||
@@ -628,7 +628,7 @@ class BookmarkImportTest extends PHPUnit_Framework_TestCase | |||
628 | $this->assertEquals($nbLinks, count($history)); | 628 | $this->assertEquals($nbLinks, count($history)); |
629 | foreach ($history as $value) { | 629 | foreach ($history as $value) { |
630 | $this->assertEquals(History::CREATED, $value['event']); | 630 | $this->assertEquals(History::CREATED, $value['event']); |
631 | $this->assertTrue(new DateTime('-5 seconds') < DateTime::createFromFormat(DateTime::ATOM, $value['datetime'])); | 631 | $this->assertTrue(new DateTime('-5 seconds') < $value['datetime']); |
632 | $this->assertTrue(is_int($value['id'])); | 632 | $this->assertTrue(is_int($value['id'])); |
633 | } | 633 | } |
634 | 634 | ||
@@ -638,7 +638,7 @@ class BookmarkImportTest extends PHPUnit_Framework_TestCase | |||
638 | $this->assertEquals($nbLinks * 2, count($history)); | 638 | $this->assertEquals($nbLinks * 2, count($history)); |
639 | for ($i = 0 ; $i < $nbLinks ; $i++) { | 639 | for ($i = 0 ; $i < $nbLinks ; $i++) { |
640 | $this->assertEquals(History::UPDATED, $history[$i]['event']); | 640 | $this->assertEquals(History::UPDATED, $history[$i]['event']); |
641 | $this->assertTrue(new DateTime('-5 seconds') < DateTime::createFromFormat(DateTime::ATOM, $history[$i]['datetime'])); | 641 | $this->assertTrue(new DateTime('-5 seconds') < $history[$i]['datetime']); |
642 | $this->assertTrue(is_int($history[$i]['id'])); | 642 | $this->assertTrue(is_int($history[$i]['id'])); |
643 | } | 643 | } |
644 | } | 644 | } |
diff --git a/tests/api/controllers/DeleteLinkTest.php b/tests/api/controllers/DeleteLinkTest.php index 6894e8a2..7d797137 100644 --- a/tests/api/controllers/DeleteLinkTest.php +++ b/tests/api/controllers/DeleteLinkTest.php | |||
@@ -17,6 +17,11 @@ class DeleteLinkTest extends \PHPUnit_Framework_TestCase | |||
17 | protected static $testDatastore = 'sandbox/datastore.php'; | 17 | protected static $testDatastore = 'sandbox/datastore.php'; |
18 | 18 | ||
19 | /** | 19 | /** |
20 | * @var string datastore to test write operations | ||
21 | */ | ||
22 | protected static $testHistory = 'sandbox/history.php'; | ||
23 | |||
24 | /** | ||
20 | * @var ConfigManager instance | 25 | * @var ConfigManager instance |
21 | */ | 26 | */ |
22 | protected $conf; | 27 | protected $conf; |
@@ -32,6 +37,11 @@ class DeleteLinkTest extends \PHPUnit_Framework_TestCase | |||
32 | protected $linkDB; | 37 | protected $linkDB; |
33 | 38 | ||
34 | /** | 39 | /** |
40 | * @var \History instance. | ||
41 | */ | ||
42 | protected $history; | ||
43 | |||
44 | /** | ||
35 | * @var Container instance. | 45 | * @var Container instance. |
36 | */ | 46 | */ |
37 | protected $container; | 47 | protected $container; |
@@ -50,9 +60,13 @@ class DeleteLinkTest extends \PHPUnit_Framework_TestCase | |||
50 | $this->refDB = new \ReferenceLinkDB(); | 60 | $this->refDB = new \ReferenceLinkDB(); |
51 | $this->refDB->write(self::$testDatastore); | 61 | $this->refDB->write(self::$testDatastore); |
52 | $this->linkDB = new \LinkDB(self::$testDatastore, true, false); | 62 | $this->linkDB = new \LinkDB(self::$testDatastore, true, false); |
63 | $refHistory = new \ReferenceHistory(); | ||
64 | $refHistory->write(self::$testHistory); | ||
65 | $this->history = new \History(self::$testHistory); | ||
53 | $this->container = new Container(); | 66 | $this->container = new Container(); |
54 | $this->container['conf'] = $this->conf; | 67 | $this->container['conf'] = $this->conf; |
55 | $this->container['db'] = $this->linkDB; | 68 | $this->container['db'] = $this->linkDB; |
69 | $this->container['history'] = $this->history; | ||
56 | 70 | ||
57 | $this->controller = new Links($this->container); | 71 | $this->controller = new Links($this->container); |
58 | } | 72 | } |
@@ -63,6 +77,7 @@ class DeleteLinkTest extends \PHPUnit_Framework_TestCase | |||
63 | public function tearDown() | 77 | public function tearDown() |
64 | { | 78 | { |
65 | @unlink(self::$testDatastore); | 79 | @unlink(self::$testDatastore); |
80 | @unlink(self::$testHistory); | ||
66 | } | 81 | } |
67 | 82 | ||
68 | /** | 83 | /** |
@@ -83,6 +98,13 @@ class DeleteLinkTest extends \PHPUnit_Framework_TestCase | |||
83 | 98 | ||
84 | $this->linkDB = new \LinkDB(self::$testDatastore, true, false); | 99 | $this->linkDB = new \LinkDB(self::$testDatastore, true, false); |
85 | $this->assertFalse(isset($this->linkDB[$id])); | 100 | $this->assertFalse(isset($this->linkDB[$id])); |
101 | |||
102 | $historyEntry = $this->history->getHistory()[0]; | ||
103 | $this->assertEquals(\History::DELETED, $historyEntry['event']); | ||
104 | $this->assertTrue( | ||
105 | (new \DateTime())->add(\DateInterval::createFromDateString('-5 seconds')) < $historyEntry['datetime'] | ||
106 | ); | ||
107 | $this->assertEquals($id, $historyEntry['id']); | ||
86 | } | 108 | } |
87 | 109 | ||
88 | /** | 110 | /** |
diff --git a/tests/api/controllers/GetLinkIdTest.php b/tests/api/controllers/GetLinkIdTest.php index 45b18e6a..57528d5a 100644 --- a/tests/api/controllers/GetLinkIdTest.php +++ b/tests/api/controllers/GetLinkIdTest.php | |||
@@ -62,6 +62,7 @@ class GetLinkIdTest extends \PHPUnit_Framework_TestCase | |||
62 | $this->container = new Container(); | 62 | $this->container = new Container(); |
63 | $this->container['conf'] = $this->conf; | 63 | $this->container['conf'] = $this->conf; |
64 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); | 64 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); |
65 | $this->container['history'] = null; | ||
65 | 66 | ||
66 | $this->controller = new Links($this->container); | 67 | $this->controller = new Links($this->container); |
67 | } | 68 | } |
diff --git a/tests/api/controllers/GetLinksTest.php b/tests/api/controllers/GetLinksTest.php index 10330cd9..84ae7f7a 100644 --- a/tests/api/controllers/GetLinksTest.php +++ b/tests/api/controllers/GetLinksTest.php | |||
@@ -61,6 +61,7 @@ class GetLinksTest extends \PHPUnit_Framework_TestCase | |||
61 | $this->container = new Container(); | 61 | $this->container = new Container(); |
62 | $this->container['conf'] = $this->conf; | 62 | $this->container['conf'] = $this->conf; |
63 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); | 63 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); |
64 | $this->container['history'] = null; | ||
64 | 65 | ||
65 | $this->controller = new Links($this->container); | 66 | $this->controller = new Links($this->container); |
66 | } | 67 | } |
diff --git a/tests/api/controllers/HistoryTest.php b/tests/api/controllers/HistoryTest.php index 21e9c0ba..61046d97 100644 --- a/tests/api/controllers/HistoryTest.php +++ b/tests/api/controllers/HistoryTest.php | |||
@@ -30,11 +30,6 @@ class HistoryTest extends \PHPUnit_Framework_TestCase | |||
30 | protected $refHistory = null; | 30 | protected $refHistory = null; |
31 | 31 | ||
32 | /** | 32 | /** |
33 | * @var \History instance. | ||
34 | */ | ||
35 | protected $history; | ||
36 | |||
37 | /** | ||
38 | * @var Container instance. | 33 | * @var Container instance. |
39 | */ | 34 | */ |
40 | protected $container; | 35 | protected $container; |
@@ -52,10 +47,10 @@ class HistoryTest extends \PHPUnit_Framework_TestCase | |||
52 | $this->conf = new ConfigManager('tests/utils/config/configJson.json.php'); | 47 | $this->conf = new ConfigManager('tests/utils/config/configJson.json.php'); |
53 | $this->refHistory = new \ReferenceHistory(); | 48 | $this->refHistory = new \ReferenceHistory(); |
54 | $this->refHistory->write(self::$testHistory); | 49 | $this->refHistory->write(self::$testHistory); |
55 | $this->conf->set('resource.history', self::$testHistory); | ||
56 | $this->container = new Container(); | 50 | $this->container = new Container(); |
57 | $this->container['conf'] = $this->conf; | 51 | $this->container['conf'] = $this->conf; |
58 | $this->container['db'] = true; | 52 | $this->container['db'] = true; |
53 | $this->container['history'] = new \History(self::$testHistory); | ||
59 | 54 | ||
60 | $this->controller = new History($this->container); | 55 | $this->controller = new History($this->container); |
61 | } | 56 | } |
diff --git a/tests/api/controllers/InfoTest.php b/tests/api/controllers/InfoTest.php index 4beef3f7..e85eb281 100644 --- a/tests/api/controllers/InfoTest.php +++ b/tests/api/controllers/InfoTest.php | |||
@@ -54,6 +54,7 @@ class InfoTest extends \PHPUnit_Framework_TestCase | |||
54 | $this->container = new Container(); | 54 | $this->container = new Container(); |
55 | $this->container['conf'] = $this->conf; | 55 | $this->container['conf'] = $this->conf; |
56 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); | 56 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); |
57 | $this->container['history'] = null; | ||
57 | 58 | ||
58 | $this->controller = new Info($this->container); | 59 | $this->controller = new Info($this->container); |
59 | } | 60 | } |
diff --git a/tests/api/controllers/PostLinkTest.php b/tests/api/controllers/PostLinkTest.php index 3ed7bcb0..31954e39 100644 --- a/tests/api/controllers/PostLinkTest.php +++ b/tests/api/controllers/PostLinkTest.php | |||
@@ -24,6 +24,11 @@ class PostLinkTest extends \PHPUnit_Framework_TestCase | |||
24 | protected static $testDatastore = 'sandbox/datastore.php'; | 24 | protected static $testDatastore = 'sandbox/datastore.php'; |
25 | 25 | ||
26 | /** | 26 | /** |
27 | * @var string datastore to test write operations | ||
28 | */ | ||
29 | protected static $testHistory = 'sandbox/history.php'; | ||
30 | |||
31 | /** | ||
27 | * @var ConfigManager instance | 32 | * @var ConfigManager instance |
28 | */ | 33 | */ |
29 | protected $conf; | 34 | protected $conf; |
@@ -34,6 +39,11 @@ class PostLinkTest extends \PHPUnit_Framework_TestCase | |||
34 | protected $refDB = null; | 39 | protected $refDB = null; |
35 | 40 | ||
36 | /** | 41 | /** |
42 | * @var \History instance. | ||
43 | */ | ||
44 | protected $history; | ||
45 | |||
46 | /** | ||
37 | * @var Container instance. | 47 | * @var Container instance. |
38 | */ | 48 | */ |
39 | protected $container; | 49 | protected $container; |
@@ -57,9 +67,14 @@ class PostLinkTest extends \PHPUnit_Framework_TestCase | |||
57 | $this->refDB = new \ReferenceLinkDB(); | 67 | $this->refDB = new \ReferenceLinkDB(); |
58 | $this->refDB->write(self::$testDatastore); | 68 | $this->refDB->write(self::$testDatastore); |
59 | 69 | ||
70 | $refHistory = new \ReferenceHistory(); | ||
71 | $refHistory->write(self::$testHistory); | ||
72 | $this->history = new \History(self::$testHistory); | ||
73 | |||
60 | $this->container = new Container(); | 74 | $this->container = new Container(); |
61 | $this->container['conf'] = $this->conf; | 75 | $this->container['conf'] = $this->conf; |
62 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); | 76 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); |
77 | $this->container['history'] = new \History(self::$testHistory); | ||
63 | 78 | ||
64 | $this->controller = new Links($this->container); | 79 | $this->controller = new Links($this->container); |
65 | 80 | ||
@@ -85,6 +100,7 @@ class PostLinkTest extends \PHPUnit_Framework_TestCase | |||
85 | public function tearDown() | 100 | public function tearDown() |
86 | { | 101 | { |
87 | @unlink(self::$testDatastore); | 102 | @unlink(self::$testDatastore); |
103 | @unlink(self::$testHistory); | ||
88 | } | 104 | } |
89 | 105 | ||
90 | /** | 106 | /** |
@@ -112,6 +128,13 @@ class PostLinkTest extends \PHPUnit_Framework_TestCase | |||
112 | $this->assertEquals(false, $data['private']); | 128 | $this->assertEquals(false, $data['private']); |
113 | $this->assertTrue(new \DateTime('5 seconds ago') < \DateTime::createFromFormat(\DateTime::ATOM, $data['created'])); | 129 | $this->assertTrue(new \DateTime('5 seconds ago') < \DateTime::createFromFormat(\DateTime::ATOM, $data['created'])); |
114 | $this->assertEquals('', $data['updated']); | 130 | $this->assertEquals('', $data['updated']); |
131 | |||
132 | $historyEntry = $this->history->getHistory()[0]; | ||
133 | $this->assertEquals(\History::CREATED, $historyEntry['event']); | ||
134 | $this->assertTrue( | ||
135 | (new \DateTime())->add(\DateInterval::createFromDateString('-5 seconds')) < $historyEntry['datetime'] | ||
136 | ); | ||
137 | $this->assertEquals(43, $historyEntry['id']); | ||
115 | } | 138 | } |
116 | 139 | ||
117 | /** | 140 | /** |
diff --git a/tests/api/controllers/PutLinkTest.php b/tests/api/controllers/PutLinkTest.php index 4096c1a7..8a562571 100644 --- a/tests/api/controllers/PutLinkTest.php +++ b/tests/api/controllers/PutLinkTest.php | |||
@@ -18,6 +18,11 @@ class PutLinkTest extends \PHPUnit_Framework_TestCase | |||
18 | protected static $testDatastore = 'sandbox/datastore.php'; | 18 | protected static $testDatastore = 'sandbox/datastore.php'; |
19 | 19 | ||
20 | /** | 20 | /** |
21 | * @var string datastore to test write operations | ||
22 | */ | ||
23 | protected static $testHistory = 'sandbox/history.php'; | ||
24 | |||
25 | /** | ||
21 | * @var ConfigManager instance | 26 | * @var ConfigManager instance |
22 | */ | 27 | */ |
23 | protected $conf; | 28 | protected $conf; |
@@ -28,6 +33,11 @@ class PutLinkTest extends \PHPUnit_Framework_TestCase | |||
28 | protected $refDB = null; | 33 | protected $refDB = null; |
29 | 34 | ||
30 | /** | 35 | /** |
36 | * @var \History instance. | ||
37 | */ | ||
38 | protected $history; | ||
39 | |||
40 | /** | ||
31 | * @var Container instance. | 41 | * @var Container instance. |
32 | */ | 42 | */ |
33 | protected $container; | 43 | protected $container; |
@@ -51,9 +61,14 @@ class PutLinkTest extends \PHPUnit_Framework_TestCase | |||
51 | $this->refDB = new \ReferenceLinkDB(); | 61 | $this->refDB = new \ReferenceLinkDB(); |
52 | $this->refDB->write(self::$testDatastore); | 62 | $this->refDB->write(self::$testDatastore); |
53 | 63 | ||
64 | $refHistory = new \ReferenceHistory(); | ||
65 | $refHistory->write(self::$testHistory); | ||
66 | $this->history = new \History(self::$testHistory); | ||
67 | |||
54 | $this->container = new Container(); | 68 | $this->container = new Container(); |
55 | $this->container['conf'] = $this->conf; | 69 | $this->container['conf'] = $this->conf; |
56 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); | 70 | $this->container['db'] = new \LinkDB(self::$testDatastore, true, false); |
71 | $this->container['history'] = new \History(self::$testHistory); | ||
57 | 72 | ||
58 | $this->controller = new Links($this->container); | 73 | $this->controller = new Links($this->container); |
59 | 74 | ||
@@ -71,6 +86,7 @@ class PutLinkTest extends \PHPUnit_Framework_TestCase | |||
71 | public function tearDown() | 86 | public function tearDown() |
72 | { | 87 | { |
73 | @unlink(self::$testDatastore); | 88 | @unlink(self::$testDatastore); |
89 | @unlink(self::$testHistory); | ||
74 | } | 90 | } |
75 | 91 | ||
76 | /** | 92 | /** |
@@ -100,6 +116,13 @@ class PutLinkTest extends \PHPUnit_Framework_TestCase | |||
100 | \DateTime::createFromFormat(\DateTime::ATOM, $data['created']) | 116 | \DateTime::createFromFormat(\DateTime::ATOM, $data['created']) |
101 | ); | 117 | ); |
102 | $this->assertTrue(new \DateTime('5 seconds ago') < \DateTime::createFromFormat(\DateTime::ATOM, $data['updated'])); | 118 | $this->assertTrue(new \DateTime('5 seconds ago') < \DateTime::createFromFormat(\DateTime::ATOM, $data['updated'])); |
119 | |||
120 | $historyEntry = $this->history->getHistory()[0]; | ||
121 | $this->assertEquals(\History::UPDATED, $historyEntry['event']); | ||
122 | $this->assertTrue( | ||
123 | (new \DateTime())->add(\DateInterval::createFromDateString('-5 seconds')) < $historyEntry['datetime'] | ||
124 | ); | ||
125 | $this->assertEquals($id, $historyEntry['id']); | ||
103 | } | 126 | } |
104 | 127 | ||
105 | /** | 128 | /** |
diff --git a/tests/utils/ReferenceHistory.php b/tests/utils/ReferenceHistory.php index 20284770..75cbb326 100644 --- a/tests/utils/ReferenceHistory.php +++ b/tests/utils/ReferenceHistory.php | |||
@@ -15,15 +15,14 @@ class ReferenceHistory | |||
15 | public function __construct() | 15 | public function __construct() |
16 | { | 16 | { |
17 | $this->addEntry( | 17 | $this->addEntry( |
18 | History::CREATED, | 18 | History::DELETED, |
19 | DateTime::createFromFormat('Ymd_His', '20170101_121212'), | 19 | DateTime::createFromFormat('Ymd_His', '20170303_121216'), |
20 | 123 | 20 | 124 |
21 | ); | 21 | ); |
22 | 22 | ||
23 | $this->addEntry( | 23 | $this->addEntry( |
24 | History::CREATED, | 24 | History::SETTINGS, |
25 | DateTime::createFromFormat('Ymd_His', '20170201_121214'), | 25 | DateTime::createFromFormat('Ymd_His', '20170302_121215') |
26 | 124 | ||
27 | ); | 26 | ); |
28 | 27 | ||
29 | $this->addEntry( | 28 | $this->addEntry( |
@@ -33,14 +32,15 @@ class ReferenceHistory | |||
33 | ); | 32 | ); |
34 | 33 | ||
35 | $this->addEntry( | 34 | $this->addEntry( |
36 | History::SETTINGS, | 35 | History::CREATED, |
37 | DateTime::createFromFormat('Ymd_His', '20170302_121215') | 36 | DateTime::createFromFormat('Ymd_His', '20170201_121214'), |
37 | 124 | ||
38 | ); | 38 | ); |
39 | 39 | ||
40 | $this->addEntry( | 40 | $this->addEntry( |
41 | History::DELETED, | 41 | History::CREATED, |
42 | DateTime::createFromFormat('Ymd_His', '20170303_121216'), | 42 | DateTime::createFromFormat('Ymd_His', '20170101_121212'), |
43 | 124 | 43 | 123 |
44 | ); | 44 | ); |
45 | } | 45 | } |
46 | 46 | ||