PluginProbe
The Innovative Form Builder – IvyForms / 1.4.1
The Innovative Form Builder – IvyForms v1.4.1
1.5.1 1.5 1.4.1 1.4 trunk 0.1.2 0.2 0.2.1 0.3 0.3.1 0.4 0.5 0.6 0.6.1 0.6.1-backup 0.6.1.1 0.7 0.8 0.8.1 0.8.2 0.9 0.9.1 1.0 1.1 1.1.1 All 27 releases
ivyforms / backend / src / Services / Menu / MenuMapper.php

MenuMapper.php in The Innovative Form Builder – IvyForms 1.4.1, at backend/src/Services/Menu/MenuMapper.php

154 lines 6.4 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace IvyForms\Services\Menu;
4
5 use IvyForms\Services\API\IvyFormsAPI;
6 use IvyForms\Services\Permissions\IvyFormsAccess;
7 use IvyForms\Services\Permissions\PermissionResolver;
8 use IvyForms\Services\Translations\BackendStrings;
9
10 /**
11 * Class Menu
12 */
13 class MenuMapper
14 {
15 private ?PermissionResolver $permissionResolver;
16
17 public function __construct(
18 ?PermissionResolver $permissionResolver = null
19 ) {
20 $this->permissionResolver = $permissionResolver;
21 }
22
23 /**
24 * @return mixed[]
25 */
26 public function __invoke(): array
27 {
28 $menus =
29 [
30 // [
31 // 'parentSlug' => 'ivyforms',
32 // 'pageTitle' => 'Dashboard',
33 // 'menuTitle' => BackendStrings::getDashboardStrings()['dashboard'],
34 // 'capability' => 'manage_options',
35 // 'menuSlug' => 'ivyforms-dashboard',
36 // ],
37 [
38 'parentSlug' => 'ivyforms',
39 'pageTitle' => 'All Forms',
40 'menuTitle' => BackendStrings::getCommonStrings()['all_forms'],
41 // WP checks this cap on the admin menu row; fine-grained access uses PermissionResolver below.
42 'capability' => IvyFormsAccess::CAP_ACCESS_PLUGIN,
43 'menuSlug' => 'ivyforms-forms',
44 ],
45 [
46 'parentSlug' => 'ivyforms',
47 'pageTitle' => 'New form',
48 'menuTitle' => BackendStrings::getCommonStrings()['new_form'],
49 'capability' => IvyFormsAccess::CAP_ACCESS_PLUGIN,
50 'menuSlug' => 'ivyforms-builder',
51 ],
52 [
53 'parentSlug' => 'ivyforms',
54 'pageTitle' => 'Entries',
55 'menuTitle' => BackendStrings::getEntriesStrings()['entries'],
56 'capability' => IvyFormsAccess::CAP_ACCESS_PLUGIN,
57 'menuSlug' => 'ivyforms-entries',
58 ],
59 // // TODO Add Settings page
60 [
61 'parentSlug' => 'ivyforms',
62 'pageTitle' => 'Settings',
63 'menuTitle' => BackendStrings::getCommonStrings()['settings'],
64 'capability' => IvyFormsAccess::CAP_ACCESS_PLUGIN,
65 'menuSlug' => 'ivyforms-settings',
66 ],
67 [
68 'parentSlug' => 'ivyforms',
69 'pageTitle' => 'Integrations',
70 'menuTitle' => BackendStrings::getIntegrationsStrings()['integrations'],
71 'capability' => IvyFormsAccess::CAP_ACCESS_PLUGIN,
72 'menuSlug' => 'ivyforms-integrations',
73 ],
74 ];
75
76 // Add "Upgrade to PRO" menu only if Pro plugin is not installed/activated
77 if (!IvyFormsAPI::isProPluginActive()) {
78 $menus[] = [
79 'parentSlug' => 'ivyforms',
80 'pageTitle' => 'Upgrade to PRO',
81 // phpcs:ignore Generic.Files.LineLength.TooLong
82 'menuTitle' => '<span class="ivyforms-upgrade-to-pro">' . __('Upgrade to PRO', 'ivyforms') . '<svg xmlns="http://www.w3.org/2000/svg" width="14" height="14" viewBox="0 0 14 14" fill="none"><path d="M3.30739 5.78346L5.09363 3.36669C6.24826 1.80449 6.82558 1.02339 7.3642 1.18846C7.90283 1.35352 7.90283 2.31153 7.90283 4.22757V4.40823C7.90283 5.0993 7.90283 5.44483 8.12364 5.66157L8.13533 5.6728C8.36091 5.88496 8.72054 5.88496 9.4398 5.88496C10.7341 5.88496 11.3813 5.88496 11.6 6.27751C11.6037 6.28401 11.6072 6.29056 11.6106 6.29716C11.8171 6.69579 11.4424 7.20277 10.6929 8.21673L8.90667 10.6335C7.75202 12.1957 7.1747 12.9768 6.63607 12.8117C6.09744 12.6466 6.09746 11.6886 6.09748 9.77256L6.09749 9.59198C6.0975 8.9009 6.0975 8.55536 5.87669 8.33861L5.865 8.32739C5.63942 8.11522 5.27979 8.11522 4.56052 8.11522C3.26618 8.11522 2.61901 8.11522 2.40029 7.72267C2.39666 7.71617 2.39314 7.70962 2.38973 7.70302C2.18325 7.3044 2.55796 6.79742 3.30739 5.78346Z" fill="white"/></svg></span>',
83 'capability' => IvyFormsAccess::CAP_ACCESS_PLUGIN,
84 // phpcs:ignore Generic.Files.LineLength.TooLong
85 'menuSlug' => 'https://ivyforms.com/pricing?utm_source=ivy-lite&utm_medium=lite-upgrade&utm_content=ivy&utm_campaign=ivy',
86 'isExternal' => true,
87 ];
88 }
89
90 $visibleMenus = [];
91 foreach ($menus as $menu) {
92 if (!$this->canAccessMenu($menu)) {
93 continue;
94 }
95 $visibleMenus[] = $menu;
96 }
97
98 return $visibleMenus;
99 }
100
101 /**
102 * @param mixed[] $menu
103 */
104 private function canAccessMenu(array $menu): bool
105 {
106 if (IvyFormsAccess::hasImplicitElevatedAccess()) {
107 return true;
108 }
109
110 $resolver = $this->permissionResolver;
111 $user = wp_get_current_user();
112 if (!$resolver || !$user instanceof \WP_User || (int) $user->ID <= 0) {
113 return false;
114 }
115
116 $slug = (string) ($menu['menuSlug'] ?? '');
117 if ($slug === '' || strpos($slug, 'http') === 0) {
118 return true;
119 }
120
121 return $this->canAccessBySlug($slug, $resolver, $user);
122 }
123
124 /**
125 * @param list<string> $permissionKeys
126 */
127 private function userCanAnyOf(PermissionResolver $resolver, \WP_User $user, array $permissionKeys): bool
128 {
129 return $resolver->userCanAnyOf($user, $permissionKeys);
130 }
131
132 private function canAccessBySlug(string $slug, PermissionResolver $resolver, \WP_User $user): bool
133 {
134 if ($slug === 'ivyforms-forms') {
135 return $this->userCanAnyOf($resolver, $user, [
136 'view_forms_list',
137 'add_edit_forms',
138 'delete_forms',
139 ]);
140 }
141 if ($slug === 'ivyforms-builder') {
142 return $resolver->userCanIncludingFormScoped('add_edit_forms', $user, null);
143 }
144 if ($slug === 'ivyforms-entries') {
145 return $this->userCanAnyOf($resolver, $user, ['view_entries_admin', 'delete_entries_admin']);
146 }
147 if (in_array($slug, ['ivyforms-settings', 'ivyforms-integrations'], true)) {
148 return $resolver->userCanIncludingFormScoped('access_settings_page', $user, null);
149 }
150
151 return true;
152 }
153 }
154