ProjectStore.php 1.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. <?php
  2. namespace Lesson20;
  3. use Pimple\Psr11\Container;
  4. /**
  5. * Class ProjectStore
  6. *
  7. * Yay race conditions :-)
  8. *
  9. * @package Lesson20
  10. */
  11. class ProjectStore implements ContainerInjectionInterface {
  12. const NAME = 'project_store';
  13. const STORE = __DIR__ . '/../project.json';
  14. protected $data = [];
  15. public function __construct() {
  16. if (!file_exists(self::STORE)) {
  17. $this->save();
  18. }
  19. $this->load();
  20. }
  21. public function __destruct() {
  22. $this->save();
  23. }
  24. protected function load() {
  25. $raw = file_get_contents(self::STORE);
  26. $this->data = json_decode($raw, TRUE);
  27. }
  28. protected function save() {
  29. $raw = json_encode($this->data, JSON_PRETTY_PRINT);
  30. file_put_contents(self::STORE, $raw);
  31. $this->load();
  32. }
  33. public static function instantiate(Container $container) {
  34. return new static();
  35. }
  36. public function all() {
  37. return array_map(function ($item) {
  38. return new Project($item['name'], $item['description']);
  39. }, $this->data);
  40. }
  41. public function create(Project $project) {
  42. $name = $project->name;
  43. if (isset($this->data[$name])) {
  44. throw new \InvalidArgumentException("Project {$name} already exists.");
  45. }
  46. if (empty($project->name)) {
  47. throw new \InvalidArgumentException("Cannot create project without a name.");
  48. }
  49. $this->data[$name] = $project;
  50. $this->save();
  51. }
  52. public function retrieve(string $name): Project {
  53. if (!isset($this->data[$name])) {
  54. throw new \InvalidArgumentException("Trying to retrieve non-existent project $name");
  55. }
  56. return $this->data[$name];
  57. }
  58. public function update(string $name, Project $new) {
  59. // Will throw if project does not exist.
  60. $existing = $this->retrieve($name);
  61. $this->delete($existing);
  62. $this->create($new);
  63. $this->save();
  64. }
  65. public function delete(Project $project) {
  66. unset($this->data[$project->name]);
  67. }
  68. }