├── .stylelintignore ├── .wp-env.json ├── LICENSE ├── README.md ├── archived-changelog.txt ├── compat ├── component-aliases.php ├── register-hooks.php ├── src-deprecated │ ├── Abstracts │ │ └── Adapter.php │ ├── Adapter │ │ ├── JSON.php │ │ └── WordPress.php │ ├── Database │ │ └── Queries │ │ │ └── NotificationQueries.php │ ├── Defaults │ │ ├── Carrier │ │ │ ├── Webhook.php │ │ │ └── WebhookJson.php │ │ └── Recipient │ │ │ └── Webhook.php │ ├── Interfaces │ │ └── Adaptable.php │ ├── Traits │ │ └── Webhook.php │ ├── Utils │ │ ├── Cache │ │ │ ├── Cache.php │ │ │ ├── ObjectCache.php │ │ │ └── Transient.php │ │ ├── Interfaces │ │ │ └── Cacheable.php │ │ └── Settings │ │ │ └── CoreFields │ │ │ └── HTML.php │ ├── functions.php │ ├── helpers.php │ └── namespaces.php └── stub-finder.php ├── composer.json ├── dependencies └── .gitkeep ├── extensions └── .gitignore ├── load.php ├── notification.php ├── package.json ├── phpstan.neon ├── readme.txt ├── resources ├── css │ └── src │ │ ├── _variables.scss │ │ ├── fields │ │ ├── _code-editor.scss │ │ ├── _image.scss │ │ └── _repeater.scss │ │ ├── partials │ │ ├── _admin-carriers.scss │ │ ├── _admin-trigger.scss │ │ ├── _admin-wizard.scss │ │ ├── _carriers-widget.scss │ │ ├── _extensions.scss │ │ ├── _global.scss │ │ ├── _help.scss │ │ ├── _import-export.scss │ │ ├── _logs.scss │ │ ├── _messages.scss │ │ ├── _metabox.scss │ │ ├── _notifications-table.scss │ │ ├── _pretty-select.scss │ │ ├── _settings.scss │ │ └── _upsell.scss │ │ └── style.scss ├── images │ ├── menu-icon.svg │ └── notification-pro.svg ├── js │ └── src │ │ ├── component │ │ ├── carriers-widget.js │ │ ├── import-export.js │ │ ├── logs.js │ │ ├── mergetag.js │ │ ├── pretty-select.js │ │ ├── remove-confirmation.js │ │ ├── settings.js │ │ ├── switch.js │ │ ├── sync.js │ │ ├── trigger.js │ │ └── wizard.js │ │ ├── fields │ │ ├── code-editor.js │ │ ├── color-picker.js │ │ ├── image.js │ │ ├── repeater │ │ │ ├── components │ │ │ │ ├── inputs │ │ │ │ │ └── select.js │ │ │ │ └── repeater │ │ │ │ │ ├── nestedSubField.js │ │ │ │ │ ├── recipientRow.js │ │ │ │ │ ├── repeaterRow.js │ │ │ │ │ └── repeaterSubRow.js │ │ │ ├── mixins │ │ │ │ ├── fieldHandler.js │ │ │ │ ├── init.js │ │ │ │ ├── inputsHandler.js │ │ │ │ ├── repeaterHandler.js │ │ │ │ └── sortableHandle.js │ │ │ └── nestedRepeater.js │ │ └── section-repeater │ │ │ ├── components │ │ │ ├── checkbox.js │ │ │ ├── input.js │ │ │ ├── select.js │ │ │ └── textarea.js │ │ │ ├── mixins │ │ │ ├── init.js │ │ │ ├── inputNameHandler.js │ │ │ ├── sectionsHandler.js │ │ │ └── sectionsModal.js │ │ │ ├── sectionRepeater.js │ │ │ └── sections │ │ │ ├── nestedSubSection.js │ │ │ ├── sectionSubRow.js │ │ │ └── sectionsRow.js │ │ ├── scripts.js │ │ └── vendor │ │ └── event-manager.js ├── templates │ ├── box.php │ ├── carriers │ │ └── widget-add.php │ ├── debug │ │ ├── error-log.php │ │ ├── notification-log.php │ │ └── pagination.php │ ├── export │ │ └── notifications.php │ ├── extension │ │ ├── activation-error.php │ │ ├── activation-success.php │ │ ├── extension-box-premium.php │ │ ├── extension-box.php │ │ ├── inactive-license.php │ │ ├── page.php │ │ └── promo-box.php │ ├── form │ │ ├── empty-form.php │ │ ├── field-hidden.php │ │ ├── field.php │ │ └── table.php │ ├── help │ │ ├── global-merge-tags.php │ │ └── sidebar.php │ ├── import │ │ └── notifications.php │ ├── mergetag │ │ ├── metabox-accordion.php │ │ ├── metabox-list.php │ │ ├── metabox-nomergetags.php │ │ ├── metabox-notrigger.php │ │ ├── searchbox.php │ │ └── tag.php │ ├── notice │ │ └── webhook-deprecated.php │ ├── save-metabox.php │ ├── settings │ │ └── page.php │ ├── sync │ │ ├── actions.php │ │ ├── disabled.php │ │ ├── notifications-empty.php │ │ └── notifications.php │ ├── trigger │ │ ├── metabox.php │ │ └── select.php │ ├── upsell │ │ ├── carriers-list.php │ │ ├── carriers-upsell.php │ │ ├── conditionals-metabox.php │ │ ├── custom-development.php │ │ ├── custom-fields-mergetag-group.php │ │ ├── review-queue-switch.php │ │ ├── scheduled-triggers-setting.php │ │ └── triggers-upsell.php │ └── wizard.php └── wizard-data │ ├── comment_added.json │ ├── comment_moderation.json │ ├── comment_published.json │ ├── comment_reply.json │ ├── new_user.json │ ├── password_forgotten.json │ ├── password_reset.json │ ├── post_published_admin.json │ ├── post_published_subscribers.json │ ├── post_review.json │ ├── post_updated.json │ ├── welcome_email.json │ └── your_account.json ├── src ├── Admin │ ├── Debugging.php │ ├── Extensions.php │ ├── ImportExport.php │ ├── NotificationDuplicator.php │ ├── PostTable.php │ ├── PostType.php │ ├── Screen.php │ ├── Scripts.php │ ├── Settings.php │ ├── Sync.php │ ├── Upsell.php │ └── Wizard.php ├── Api │ ├── Api.php │ └── Controller │ │ ├── CheckRestApiController.php │ │ ├── RepeaterController.php │ │ ├── SectionRepeaterController.php │ │ └── SelectInputController.php ├── Cli │ └── DumpHooks.php ├── Compat │ ├── RestApiCompat.php │ └── WebhookCompat.php ├── Core │ ├── Binder.php │ ├── Cron.php │ ├── Debugging.php │ ├── License.php │ ├── Notification.php │ ├── Processor.php │ ├── Queue.php │ ├── Resolver.php │ ├── Runner.php │ ├── Settings.php │ ├── Sync.php │ ├── Templates.php │ ├── Upgrade.php │ └── Whitelabel.php ├── Database │ ├── DatabaseService.php │ ├── NotificationDatabaseService.php │ └── Queries │ │ └── UserQueries.php ├── ErrorHandler.php ├── Integration │ ├── TwoFactor.php │ ├── WordPressEmails.php │ └── WordPressIntegration.php ├── Interfaces │ ├── Convertable.php │ ├── Fillable.php │ ├── Nameable.php │ ├── Receivable.php │ ├── Resolvable.php │ ├── Sendable.php │ ├── Storable.php │ ├── Taggable.php │ └── Triggerable.php ├── Register.php ├── Repository │ ├── Carrier │ │ ├── BaseCarrier.php │ │ └── Email.php │ ├── CarrierRepository.php │ ├── Converter │ │ ├── ArrayConverter.php │ │ └── JsonConverter.php │ ├── Field │ │ ├── BaseField.php │ │ ├── CheckboxField.php │ │ ├── CodeEditorField.php │ │ ├── ColorPickerField.php │ │ ├── EditorField.php │ │ ├── ImageField.php │ │ ├── InputField.php │ │ ├── MessageField.php │ │ ├── NonceField.php │ │ ├── RecipientsField.php │ │ ├── RepeaterField.php │ │ ├── SectionRepeater.php │ │ ├── SectionsField.php │ │ ├── SelectField.php │ │ └── TextareaField.php │ ├── GlobalMergeTagRepository.php │ ├── MergeTag │ │ ├── BaseMergeTag.php │ │ ├── BooleanTag.php │ │ ├── Comment │ │ │ ├── CommentActionApprove.php │ │ │ ├── CommentActionDelete.php │ │ │ ├── CommentActionSpam.php │ │ │ ├── CommentActionTrash.php │ │ │ ├── CommentAuthorIP.php │ │ │ ├── CommentAuthorUrl.php │ │ │ ├── CommentAuthorUserAgent.php │ │ │ ├── CommentContent.php │ │ │ ├── CommentContentHtml.php │ │ │ ├── CommentID.php │ │ │ ├── CommentIsReply.php │ │ │ ├── CommentStatus.php │ │ │ └── CommentType.php │ │ ├── DateTime │ │ │ ├── Date.php │ │ │ ├── DateTime.php │ │ │ └── Time.php │ │ ├── EmailTag.php │ │ ├── FloatTag.php │ │ ├── HtmlTag.php │ │ ├── IPTag.php │ │ ├── IntegerTag.php │ │ ├── Media │ │ │ ├── AttachmentDirectUrl.php │ │ │ ├── AttachmentID.php │ │ │ ├── AttachmentMimeType.php │ │ │ ├── AttachmentPage.php │ │ │ └── AttachmentTitle.php │ │ ├── Post │ │ │ ├── FeaturedImageId.php │ │ │ ├── FeaturedImageUrl.php │ │ │ ├── PostContent.php │ │ │ ├── PostContentHtml.php │ │ │ ├── PostExcerpt.php │ │ │ ├── PostID.php │ │ │ ├── PostPermalink.php │ │ │ ├── PostSlug.php │ │ │ ├── PostStatus.php │ │ │ ├── PostTerms.php │ │ │ ├── PostTitle.php │ │ │ ├── PostType.php │ │ │ ├── RevisionLink.php │ │ │ └── ThumbnailUrl.php │ │ ├── StringTag.php │ │ ├── Taxonomy │ │ │ ├── TaxonomyName.php │ │ │ ├── TaxonomySlug.php │ │ │ ├── TermDescription.php │ │ │ ├── TermID.php │ │ │ ├── TermName.php │ │ │ ├── TermPermalink.php │ │ │ └── TermSlug.php │ │ ├── UrlTag.php │ │ └── User │ │ │ ├── Avatar.php │ │ │ ├── AvatarUrl.php │ │ │ ├── UserBio.php │ │ │ ├── UserDisplayName.php │ │ │ ├── UserEmail.php │ │ │ ├── UserFirstName.php │ │ │ ├── UserID.php │ │ │ ├── UserLastName.php │ │ │ ├── UserLogin.php │ │ │ ├── UserNicename.php │ │ │ ├── UserNickname.php │ │ │ ├── UserPasswordResetLink.php │ │ │ └── UserRole.php │ ├── Recipient │ │ ├── Administrator.php │ │ ├── BaseRecipient.php │ │ ├── Email.php │ │ ├── Role.php │ │ ├── User.php │ │ └── UserID.php │ ├── RecipientRepository.php │ ├── Resolver │ │ ├── BaseResolver.php │ │ └── Basic.php │ ├── ResolverRepository.php │ ├── Trigger │ │ ├── BaseTrigger.php │ │ ├── Comment │ │ │ ├── CommentAdded.php │ │ │ ├── CommentApproved.php │ │ │ ├── CommentPublished.php │ │ │ ├── CommentReplied.php │ │ │ ├── CommentSpammed.php │ │ │ ├── CommentTrashed.php │ │ │ ├── CommentTrigger.php │ │ │ └── CommentUnapproved.php │ │ ├── Media │ │ │ ├── MediaAdded.php │ │ │ ├── MediaTrashed.php │ │ │ ├── MediaTrigger.php │ │ │ └── MediaUpdated.php │ │ ├── Plugin │ │ │ ├── Activated.php │ │ │ ├── Deactivated.php │ │ │ ├── Installed.php │ │ │ ├── PluginTrigger.php │ │ │ ├── Removed.php │ │ │ └── Updated.php │ │ ├── Post │ │ │ ├── PostAdded.php │ │ │ ├── PostApproved.php │ │ │ ├── PostDrafted.php │ │ │ ├── PostPending.php │ │ │ ├── PostPublished.php │ │ │ ├── PostPublishedPrivately.php │ │ │ ├── PostScheduled.php │ │ │ ├── PostTrashed.php │ │ │ ├── PostTrigger.php │ │ │ └── PostUpdated.php │ │ ├── Privacy │ │ │ ├── DataEraseRequest.php │ │ │ ├── DataErased.php │ │ │ ├── DataExportRequest.php │ │ │ ├── DataExported.php │ │ │ └── PrivacyTrigger.php │ │ ├── Taxonomy │ │ │ ├── TermAdded.php │ │ │ ├── TermDeleted.php │ │ │ ├── TermTrigger.php │ │ │ └── TermUpdated.php │ │ ├── Theme │ │ │ ├── Installed.php │ │ │ ├── Switched.php │ │ │ ├── ThemeTrigger.php │ │ │ └── Updated.php │ │ ├── User │ │ │ ├── UserDeleted.php │ │ │ ├── UserEmailChangeRequest.php │ │ │ ├── UserEmailChanged.php │ │ │ ├── UserLogin.php │ │ │ ├── UserLoginFailed.php │ │ │ ├── UserLogout.php │ │ │ ├── UserPasswordChanged.php │ │ │ ├── UserPasswordResetRequest.php │ │ │ ├── UserProfileUpdated.php │ │ │ ├── UserRegistered.php │ │ │ ├── UserRoleChanged.php │ │ │ └── UserTrigger.php │ │ └── WordPress │ │ │ ├── EmailChangeRequest.php │ │ │ ├── EmailChanged.php │ │ │ ├── Updated.php │ │ │ └── UpdatesAvailable.php │ └── TriggerRepository.php ├── Runtime.php ├── Store │ ├── Carrier.php │ ├── GlobalMergeTag.php │ ├── Notification.php │ ├── Recipient.php │ ├── Resolver.php │ └── Trigger.php ├── Traits │ ├── ClassUtils.php │ ├── HasDescription.php │ ├── HasGroup.php │ ├── HasName.php │ ├── HasReturnField.php │ ├── HasSlug.php │ └── Storage.php └── Utils │ ├── EDDUpdater.php │ ├── Settings.php │ ├── Settings │ ├── CoreFields │ │ ├── Button.php │ │ ├── Checkbox.php │ │ ├── Editor.php │ │ ├── Image.php │ │ ├── Message.php │ │ ├── Number.php │ │ ├── Range.php │ │ ├── Select.php │ │ ├── Text.php │ │ └── Url.php │ ├── Field.php │ ├── Fields │ │ ├── ErrorLog.php │ │ ├── Export.php │ │ ├── Import.php │ │ ├── NotificationLog.php │ │ └── SyncTable.php │ ├── Group.php │ └── Section.php │ └── WpObjectHelper.php └── uninstall.php /.stylelintignore: -------------------------------------------------------------------------------- 1 | dependencies/**/* 2 | node_modules/**/* 3 | vendor/**/* 4 | resources/css/dist/**/* 5 | -------------------------------------------------------------------------------- /.wp-env.json: -------------------------------------------------------------------------------- 1 | { 2 | "phpVersion": "7.4", 3 | "mappings": { 4 | "wp-content/plugins/notification": "." 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /compat/component-aliases.php: -------------------------------------------------------------------------------- 1 | Core\Cron::class, 16 | 'core_whitelabel' => Core\Whitelabel::class, 17 | 'core_debugging' => Core\Debugging::class, 18 | 'core_settings' => Core\Settings::class, 19 | 'core_upgrade' => Core\Upgrade::class, 20 | 'core_sync' => Core\Sync::class, 21 | 'core_binder' => Core\Binder::class, 22 | 'core_processor' => Core\Processor::class, 23 | 'test_rest_api' => Compat\RestApiCompat::class, 24 | 'admin_impexp' => Admin\ImportExport::class, 25 | 'admin_settings' => Admin\Settings::class, 26 | 'admin_duplicator' => Admin\NotificationDuplicator::class, 27 | 'admin_post_type' => Admin\PostType::class, 28 | 'admin_post_table' => Admin\PostTable::class, 29 | 'admin_extensions' => Admin\Extensions::class, 30 | 'admin_scripts' => Admin\Scripts::class, 31 | 'admin_screen' => Admin\Screen::class, 32 | 'admin_wizard' => Admin\Wizard::class, 33 | 'admin_sync' => Admin\Sync::class, 34 | 'admin_debugging' => Admin\Debugging::class, 35 | 'admin_upsell' => Admin\Upsell::class, 36 | 'integration_wp' => Integration\WordPressIntegration::class, 37 | 'integration_wp_emails' => Integration\WordPressEmails::class, 38 | 'integration_2fa' => Integration\TwoFactor::class, 39 | 'api' => Api\Api::class, 40 | ]; 41 | -------------------------------------------------------------------------------- /compat/src-deprecated/Adapter/JSON.php: -------------------------------------------------------------------------------- 1 | setupNotification(notification_convert_data((array)$data)); 38 | $this->setSource('JSON'); 39 | 40 | return $this; 41 | } 42 | 43 | /** 44 | * {@inheritdoc} 45 | * 46 | * @param int|null $jsonOptions JSON options, pass null to use default as well. 47 | * @param bool $onlyEnabledCarriers If only enabled Carriers should be saved. 48 | * @return mixed 49 | */ 50 | public function save($jsonOptions = JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE, $onlyEnabledCarriers = false) 51 | { 52 | if ($jsonOptions === null) { 53 | $jsonOptions = JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE; 54 | } 55 | 56 | $data = $this->getNotification()->toArray($onlyEnabledCarriers); 57 | return wp_json_encode($data, $jsonOptions); 58 | } 59 | } 60 | -------------------------------------------------------------------------------- /compat/src-deprecated/Interfaces/Adaptable.php: -------------------------------------------------------------------------------- 1 | key = $key; 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /compat/src-deprecated/Utils/Interfaces/Cacheable.php: -------------------------------------------------------------------------------- 1 | addon( 'field' ); 32 | 33 | // The HTML must be escaped externally. 34 | // phpcs:ignore WordPress.Security.EscapeOutput.OutputNotEscaped 35 | echo is_callable( $field ) ? $field() : $field; 36 | } 37 | 38 | /** 39 | * Sanitize input value 40 | * 41 | * @param string $value Saved value. 42 | * @return string Sanitized text 43 | */ 44 | public function sanitize( $value ) { 45 | return $value; 46 | } 47 | 48 | } 49 | -------------------------------------------------------------------------------- /compat/src-deprecated/helpers.php: -------------------------------------------------------------------------------- 1 | deprecated since version %2$s! Use %3$s instead.'), $class, $version, $replacement), E_USER_DEPRECATED); 27 | } else { 28 | /* translators: 1: Class name, 2: version number */ 29 | trigger_error(sprintf(__('Class %1$s is deprecated since version %2$s with no alternative available.'), $class, $version), E_USER_DEPRECATED); 30 | } 31 | } else { 32 | if (! is_null($replacement)) { 33 | trigger_error(sprintf('Class %1$s is deprecated since version %2$s! Use %3$s instead.', $class, $version, $replacement), E_USER_DEPRECATED); 34 | } else { 35 | trigger_error(sprintf('Class %1$s is deprecated since version %2$s with no alternative available.', $class, $version), E_USER_DEPRECATED); 36 | } 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /compat/stub-finder.php: -------------------------------------------------------------------------------- 1 | in( realpath( __DIR__ . '/..' ) ) 16 | ->notPath( 'dependencies/' ) 17 | ->notPath( 'resources/' ) 18 | ->notPath( 'node_modules/' ) 19 | ->notPath( 'vendor/' ) 20 | ->notPath( 'tests/' ) 21 | ->sortByName(); 22 | -------------------------------------------------------------------------------- /dependencies/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/BracketSpace/Notification/a3bb0d7a5aa63f3f08e70eaa74e5a0e757e13158/dependencies/.gitkeep -------------------------------------------------------------------------------- /extensions/.gitignore: -------------------------------------------------------------------------------- 1 | * 2 | !.gitignore 3 | -------------------------------------------------------------------------------- /load.php: -------------------------------------------------------------------------------- 1 | init(); 23 | }, 24 | 4 25 | ); 26 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "notification", 3 | "version": "7.0.0", 4 | "description": "Notification plugin", 5 | "scripts": { 6 | "build": "mp-scripts build --mode=development", 7 | "build:production": "mp-scripts build --mode=production", 8 | "start": "mp-scripts start", 9 | "lint:css": "mp-scripts lint-style", 10 | "lint:js": "mp-scripts lint-js", 11 | "fix:css": "mp-scripts lint-style --fix", 12 | "fix:js": "mp-scripts lint-js --fix", 13 | "lint": "run-p \"lint:*\"", 14 | "fix": "run-p \"fix:*\"", 15 | "test-php": "wp-env run tests-wordpress --env-cwd=wp-content/plugins/notification ./vendor/bin/pest -- --configuration phpunit.xml" 16 | }, 17 | "author": "BracketSpace", 18 | "license": "GPL-3.0-or-later", 19 | "devDependencies": { 20 | "@micropackage/scripts": "^1.2.5", 21 | "@wordpress/env": "^9.7.0", 22 | "npm-run-all": "^4.1.5" 23 | }, 24 | "dependencies": { 25 | "clipboard": "^2.0.4", 26 | "jquery-collapse": "^1.1.2", 27 | "selectize": "^0.12.4", 28 | "vue": "2.6.11" 29 | }, 30 | "mpScriptsConfig": { 31 | "paths": { 32 | "src": "resources", 33 | "scripts": "js/src", 34 | "styles": "css/src", 35 | "output": "resources" 36 | } 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /phpstan.neon: -------------------------------------------------------------------------------- 1 | includes: 2 | - vendor/szepeviktor/phpstan-wordpress/extension.neon 3 | - phpstan-baseline.neon 4 | parameters: 5 | level: max 6 | inferPrivatePropertyTypeFromConstructor: true 7 | treatPhpDocTypesAsCertain: false 8 | scanFiles: 9 | - vendor/php-stubs/wp-cli-stubs/wp-cli-stubs.php 10 | paths: 11 | - notification.php 12 | - load.php 13 | - uninstall.php 14 | - src/ 15 | - compat/ 16 | typeAliases: 17 | NotificationData: ''' 18 | array{ 19 | hash?: string, 20 | title?: string, 21 | trigger?: BracketSpace\Notification\Interfaces\Triggerable, 22 | carriers?: array, 23 | enabled?: bool, 24 | extras?: array|bool|float|int|string>, 25 | version?: int, 26 | } 27 | ''' 28 | NotificationAsArray: ''' 29 | array{ 30 | hash: string, 31 | title: string, 32 | trigger: string, 33 | carriers: array>, 34 | enabled: bool, 35 | extras: array|bool|float|int|string>, 36 | version: int, 37 | } 38 | ''' 39 | NotificationUnconvertedData: ''' 40 | array{ 41 | hash?: string, 42 | title?: string, 43 | trigger?: BracketSpace\Notification\Interfaces\Triggerable|string, 44 | carriers?: array>, 45 | enabled?: bool, 46 | extras?: array|bool|float|int|string>, 47 | version?: int, 48 | } 49 | ''' 50 | excludePaths: 51 | - compat/src-deprecated/helpers.php 52 | - compat/stubs.php 53 | - dependencies/ 54 | - src/Utils/EDDUpdater.php 55 | -------------------------------------------------------------------------------- /resources/css/src/_variables.scss: -------------------------------------------------------------------------------- 1 | $mobile-width: 782px; 2 | 3 | @mixin mobile { 4 | 5 | @media (max-width: #{$mobile-width}) { 6 | @content; 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /resources/css/src/fields/_code-editor.scss: -------------------------------------------------------------------------------- 1 | .notification-code-editor-field { 2 | 3 | /* stylelint-disable */ 4 | + .CodeMirror { 5 | /* stylelint-enable */ 6 | border: 1px solid #e5e5e5; 7 | } 8 | 9 | } 10 | -------------------------------------------------------------------------------- /resources/css/src/fields/_image.scss: -------------------------------------------------------------------------------- 1 | .notification-image-field { 2 | 3 | .image-input { 4 | display: none; 5 | } 6 | 7 | .image { 8 | display: none; 9 | position: relative; 10 | 11 | .clear { 12 | background: #fff; 13 | border: 1px solid #fff; 14 | border-radius: 50%; 15 | cursor: pointer; 16 | font-size: 26px; 17 | height: 26px; 18 | position: absolute; 19 | right: -9px; 20 | top: -9px; 21 | width: 28px; 22 | } 23 | 24 | .preview { 25 | border: 1px solid #e5e5e5; 26 | border-radius: 5px; 27 | cursor: pointer; 28 | height: auto; 29 | max-width: 200px; 30 | } 31 | 32 | } 33 | 34 | &.selected { 35 | 36 | .image { 37 | display: inline-block; 38 | } 39 | 40 | .select-image { 41 | display: none; 42 | } 43 | 44 | } 45 | 46 | } 47 | -------------------------------------------------------------------------------- /resources/css/src/partials/_admin-trigger.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Notifications styles 3 | */ 4 | 5 | body.post-type-notification { 6 | 7 | .selectize-control .selectize-dropdown .caption { 8 | color: #a0a0a0; 9 | display: block; 10 | font-size: 12px; 11 | } 12 | 13 | .selectize-control .selectize-dropdown div[data-selectable] { 14 | padding: 6px 8px; 15 | } 16 | 17 | .selectize-control .selectize-dropdown-content { 18 | max-height: 550px; 19 | } 20 | 21 | } 22 | -------------------------------------------------------------------------------- /resources/css/src/partials/_extensions.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Extensions styles 3 | */ 4 | 5 | .notification-extensions { 6 | 7 | h1 { 8 | margin-bottom: 16px; 9 | } 10 | 11 | .plugin-card { 12 | 13 | .action-links { 14 | 15 | .official { 16 | background: #0073aa; 17 | border-radius: 4px; 18 | box-sizing: border-box; 19 | color: #fff; 20 | display: inline-block; 21 | margin-top: 3px; 22 | padding: 3px 10px; 23 | text-align: center; 24 | text-transform: uppercase; 25 | width: 100%; 26 | } 27 | 28 | .discount { 29 | background: #00aa4c; 30 | border-radius: 4px; 31 | box-sizing: border-box; 32 | color: #fff; 33 | display: inline-block; 34 | margin-top: 3px; 35 | padding: 3px 10px; 36 | text-align: center; 37 | text-transform: uppercase; 38 | width: 100%; 39 | } 40 | 41 | } 42 | 43 | &-premium { 44 | 45 | .desc { 46 | margin-right: 0; 47 | } 48 | 49 | .plugin-card-bottom { 50 | 51 | .column-license { 52 | clear: left; 53 | float: left; 54 | width: 65%; 55 | width: calc(100% - 180px); 56 | } 57 | 58 | .column-submit { 59 | clear: right; 60 | float: right; 61 | max-width: 180px; 62 | } 63 | 64 | } 65 | 66 | } 67 | 68 | &.promo { 69 | 70 | .desc, 71 | .name, 72 | .action-links { 73 | margin-left: 0; 74 | } 75 | 76 | } 77 | 78 | } 79 | 80 | } 81 | -------------------------------------------------------------------------------- /resources/css/src/partials/_help.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Screen help styles 3 | */ 4 | 5 | #contextual-help-wrap { 6 | 7 | #tab-panel-notification_global_merge_tags { /* stylelint-disable-line */ 8 | 9 | table { 10 | 11 | td { 12 | padding: 5px 10px; 13 | 14 | label { 15 | cursor: text; 16 | } 17 | 18 | code { 19 | cursor: pointer; 20 | } 21 | 22 | } 23 | 24 | } 25 | 26 | } 27 | 28 | } 29 | -------------------------------------------------------------------------------- /resources/css/src/partials/_import-export.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Import/Export styles 3 | */ 4 | 5 | .notification-settings .section-import_export { /* stylelint-disable-line */ 6 | 7 | p.submit { 8 | display: none; 9 | } 10 | 11 | .message { 12 | 13 | &.error { 14 | color: #f00; 15 | } 16 | 17 | &.success { 18 | color: #00ad00; 19 | } 20 | 21 | } 22 | 23 | } 24 | -------------------------------------------------------------------------------- /resources/css/src/partials/_messages.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Message styles for notifications 3 | */ 4 | 5 | .notification-notice { 6 | 7 | .dismiss-beg-message { 8 | float: right; 9 | } 10 | 11 | } 12 | -------------------------------------------------------------------------------- /resources/css/src/partials/_notifications-table.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Notifications table 3 | */ 4 | 5 | .post-type-notification .wp-list-table { 6 | 7 | .column-switch { 8 | width: 70px; 9 | } 10 | 11 | @media ( max-width: 782px ) { 12 | 13 | .column-switch { 14 | display: none !important; 15 | padding-left: 35%; 16 | } 17 | 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /resources/css/src/partials/_pretty-select.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Selectize styles to not wrap the text 3 | */ 4 | 5 | .selectize-input { 6 | 7 | > * { 8 | vertical-align: middle; 9 | } 10 | 11 | .item { 12 | max-width: 80%; 13 | overflow: hidden; 14 | text-overflow: ellipsis; 15 | white-space: nowrap; 16 | } 17 | 18 | } 19 | -------------------------------------------------------------------------------- /resources/css/src/partials/_upsell.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Upsell styles 3 | */ 4 | 5 | /* stylelint-disable */ 6 | #notification_conditionals.postbox .inside { 7 | /* stylelint-enable */ 8 | margin-top: 12px; 9 | 10 | .notification-pretty-select { 11 | margin-bottom: 12px; 12 | } 13 | } 14 | 15 | .notification-upsell-banner { 16 | background: #d8eede; 17 | border-radius: 10px; 18 | padding: 10px; 19 | } 20 | -------------------------------------------------------------------------------- /resources/css/src/style.scss: -------------------------------------------------------------------------------- 1 | /** 2 | * Variables 3 | */ 4 | @import "variables"; 5 | 6 | /** 7 | * Vendors 8 | */ 9 | @import "../../../node_modules/selectize/dist/css/selectize"; 10 | @import "../../../node_modules/selectize/dist/css/selectize.default"; 11 | 12 | /** 13 | * Partials 14 | */ 15 | @import "partials/global"; 16 | @import "partials/metabox"; 17 | @import "partials/messages"; 18 | @import "partials/extensions"; 19 | @import "partials/admin-carriers"; 20 | @import "partials/admin-trigger"; 21 | @import "partials/admin-wizard"; 22 | @import "partials/pretty-select"; 23 | @import "partials/settings"; 24 | @import "partials/notifications-table"; 25 | @import "partials/help"; 26 | @import "partials/import-export"; 27 | @import "partials/logs"; 28 | @import "partials/carriers-widget"; 29 | @import "partials/upsell"; 30 | 31 | /** 32 | * Fields 33 | */ 34 | @import "fields/repeater"; 35 | @import "fields/image"; 36 | @import "fields/code-editor"; 37 | -------------------------------------------------------------------------------- /resources/images/menu-icon.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /resources/js/src/component/logs.js: -------------------------------------------------------------------------------- 1 | /* global jQuery */ 2 | (function ($) { 3 | $(document).ready(function () { 4 | $('.log-container .log-item .log-handle').on('click', function (event) { 5 | event.preventDefault(); 6 | $(this).parent().toggleClass('expanded'); 7 | $(this) 8 | .find('.indicator') 9 | .toggleClass('dashicons-arrow-down dashicons-arrow-up'); 10 | }); 11 | }); 12 | })(jQuery); 13 | 14 | (function ($) { 15 | $(document).ready(function () { 16 | function toggleSuppressingSetting() { 17 | const $log = $( 18 | '#notification-setting-debugging-settings-debug_log' 19 | ); 20 | const $suppressing = $( 21 | '.notification-settings .field-debug_suppressing' 22 | ); 23 | 24 | if ($log.is(':checked')) { 25 | $suppressing.show(); 26 | } else { 27 | $suppressing.hide(); 28 | } 29 | } 30 | 31 | toggleSuppressingSetting(); 32 | 33 | $('#notification-setting-debugging-settings-debug_log').change( 34 | toggleSuppressingSetting 35 | ); 36 | }); 37 | })(jQuery); 38 | -------------------------------------------------------------------------------- /resources/js/src/component/pretty-select.js: -------------------------------------------------------------------------------- 1 | /* global jQuery */ 2 | 3 | import 'selectize'; 4 | 5 | (function ($) { 6 | $(document).ready(function () { 7 | $( 8 | '.notification-pretty-select:visible:not( repeater-select )' 9 | ).selectize(); 10 | }); 11 | })(jQuery); 12 | -------------------------------------------------------------------------------- /resources/js/src/component/remove-confirmation.js: -------------------------------------------------------------------------------- 1 | /* eslint no-alert: 0 */ 2 | /* global jQuery, confirm */ 3 | (function ($) { 4 | const __ = wp.i18n.__; 5 | 6 | $(document).ready(function () { 7 | $('.notification-delete-post').click(function (e) { 8 | if ( 9 | !confirm( 10 | __( 11 | 'Are you sure you want to permanently delete this notification?', 12 | 'notification' 13 | ) 14 | ) 15 | ) { 16 | e.preventDefault(); 17 | } 18 | }); 19 | }); 20 | })(jQuery); 21 | -------------------------------------------------------------------------------- /resources/js/src/component/settings.js: -------------------------------------------------------------------------------- 1 | /* global jQuery, jQueryCollapse */ 2 | 3 | import 'selectize'; 4 | import 'jquery-collapse/src/jquery.collapse.js'; 5 | 6 | (function ($) { 7 | $(document).ready(function () { 8 | $('.underdev-settings .pretty-select').selectize(); 9 | new jQueryCollapse($('.underdev-settings .setting-group'), { 10 | open() { 11 | this.slideDown(100); 12 | }, 13 | close() { 14 | this.slideUp(100); 15 | }, 16 | }); 17 | $('.setting-group-header').click(function () { 18 | const wrapper = $(this) 19 | .parents('.setting-group') 20 | .find('.form-table'); 21 | wrapper.trigger('toggle'); 22 | }); 23 | }); 24 | })(jQuery); 25 | -------------------------------------------------------------------------------- /resources/js/src/component/switch.js: -------------------------------------------------------------------------------- 1 | /* eslint no-alert: 0 */ 2 | /* global notification, jQuery, alert */ 3 | (function ($) { 4 | $(document).ready(function () { 5 | $('.column-switch .onoffswitch').on('click', function (event) { 6 | const $switch = $(this), 7 | postId = $switch.data('postid'); 8 | 9 | event.preventDefault(); 10 | 11 | notification.hooks.doAction( 12 | 'notification.status.changed', 13 | $switch, 14 | postId 15 | ); 16 | }); 17 | 18 | notification.hooks.addAction( 19 | 'notification.status.changed', 20 | function ($switch, postId) { 21 | const status = !$switch.find('input').attr('checked'); 22 | 23 | $switch.addClass('loading'); 24 | 25 | const data = { 26 | action: 'change_notification_status', 27 | _ajax_nonce: notification.csrfToken, 28 | post_id: postId, 29 | status, 30 | nonce: $switch.data('nonce'), 31 | }; 32 | 33 | $.post(notification.ajaxurl, data, function (response) { 34 | if (response.success === true) { 35 | $switch.removeClass('loading'); 36 | $switch.find('input').attr('checked', status); 37 | } else { 38 | alert(response.data); 39 | } 40 | }); 41 | } 42 | ); 43 | }); 44 | })(jQuery); 45 | -------------------------------------------------------------------------------- /resources/js/src/component/trigger.js: -------------------------------------------------------------------------------- 1 | /* global notification, jQuery */ 2 | 3 | import 'selectize'; 4 | 5 | (function ($) { 6 | $(document).ready(function () { 7 | $('#notification_trigger_select').selectize({ 8 | render: { 9 | item(item) { 10 | return ( 11 | '
' + 12 | item.text.replace(/\[\[(.*)\]\]/g, '') + 13 | '
' 14 | ); 15 | }, 16 | option(item) { 17 | return ( 18 | '
' + 19 | item.text.replace( 20 | /(.*)\[\[(.*)\]\]/g, 21 | '$1$2' 22 | ) + 23 | '
' 24 | ); 25 | }, 26 | }, 27 | }); 28 | 29 | $('#notification_trigger_select') 30 | .selectize() 31 | .change(function () { 32 | notification.hooks.doAction( 33 | 'notification.trigger.changed', 34 | $(this) 35 | ); 36 | }); 37 | }); 38 | })(jQuery); 39 | -------------------------------------------------------------------------------- /resources/js/src/component/wizard.js: -------------------------------------------------------------------------------- 1 | /* global jQuery */ 2 | (function ($) { 3 | $(document).ready(function () { 4 | let count = $('#notifications-wizard').data( 5 | 'selected-notifications-count' 6 | ) 7 | ? $('#notifications-wizard').data('selected-notifications-count') 8 | : 0; 9 | 10 | $('#notifications-wizard .notifications-tile').on( 11 | 'click', 12 | function (e) { 13 | e.preventDefault(); 14 | 15 | if ($(this).hasClass('selected')) { 16 | $(this).removeClass('selected'); 17 | const checkbox = $(this)[0].querySelector('input'); 18 | checkbox.checked = false; 19 | count = count - 1; 20 | } else { 21 | $(this).addClass('selected'); 22 | const checkbox = $(this)[0].querySelector('input'); 23 | checkbox.checked = true; 24 | count = count + 1; 25 | } 26 | 27 | $('#notifications-wizard').data( 28 | 'selected-notifications-count', 29 | count 30 | ); 31 | 32 | if (count > 0) { 33 | const text = wp.i18n.sprintf( 34 | // translators: %d: number of notifications 35 | wp.i18n._n( 36 | 'Create %d notification', 37 | 'Create %d notifications', 38 | count, 39 | 'notification' 40 | ), 41 | count 42 | ); 43 | $('.create-notifications').removeClass('hidden').text(text); 44 | $('.skip-wizard') 45 | .removeClass('button') 46 | .removeClass('button-secondary') 47 | .addClass('as-link'); 48 | } else { 49 | $('.create-notifications').addClass('hidden'); 50 | $('.skip-wizard') 51 | .addClass('button') 52 | .addClass('button-secondary') 53 | .removeClass('as-link'); 54 | } 55 | } 56 | ); 57 | }); 58 | })(jQuery); 59 | -------------------------------------------------------------------------------- /resources/js/src/fields/code-editor.js: -------------------------------------------------------------------------------- 1 | /* global _, notification, jQuery */ 2 | 3 | (function ($) { 4 | function initCodeEditor($elem) { 5 | const editorSettings = wp.codeEditor.defaultSettings 6 | ? _.clone(wp.codeEditor.defaultSettings) 7 | : {}; 8 | editorSettings.codemirror = _.extend( 9 | {}, 10 | editorSettings.codemirror, 11 | $elem.data('settings') 12 | ); 13 | let editor = wp.codeEditor.initialize($elem, editorSettings); // eslint-disable-line prefer-const 14 | 15 | notification.hooks.addAction('notification.carrier.toggled', () => { 16 | editor.codemirror.refresh(); 17 | }); 18 | } 19 | 20 | $(document).ready(function () { 21 | $('.notification-code-editor-field').each(function () { 22 | initCodeEditor($(this)); 23 | }); 24 | }); 25 | })(jQuery); 26 | -------------------------------------------------------------------------------- /resources/js/src/fields/color-picker.js: -------------------------------------------------------------------------------- 1 | /* global notification, jQuery */ 2 | (function ($) { 3 | $(document).ready(function () { 4 | $('.notification-color-picker:visible').wpColorPicker(); 5 | }); 6 | 7 | notification.hooks.addAction( 8 | 'notification.carrier.repeater.row.added', 9 | function (repeater) { 10 | const colorPickers = repeater.$el.querySelectorAll( 11 | '.notification-color-picker' 12 | ); 13 | 14 | colorPickers.forEach((colorPicker) => { 15 | colorPicker.wpColorPicker(); 16 | }); 17 | } 18 | ); 19 | })(jQuery); 20 | -------------------------------------------------------------------------------- /resources/js/src/fields/repeater/components/repeater/nestedSubField.js: -------------------------------------------------------------------------------- 1 | import Vue from 'vue/dist/vue.js'; 2 | import { fieldHandler } from '../../mixins/fieldHandler'; 3 | import { repeaterHandler } from '../../mixins/repeaterHandler'; 4 | 5 | Vue.component('nested-sub-field', { 6 | template: `
7 | 8 | 19 |
20 | Add sub field 23 |
24 | `, 25 | props: [ 26 | 'model', 27 | 'nestedFields', 28 | 'nestedValues', 29 | 'subRows', 30 | 'type', 31 | 'rowIndex', 32 | 'subName', 33 | 'fieldName', 34 | ], 35 | mixins: [fieldHandler, repeaterHandler], 36 | }); 37 | -------------------------------------------------------------------------------- /resources/js/src/fields/repeater/components/repeater/recipientRow.js: -------------------------------------------------------------------------------- 1 | import Vue from 'vue/dist/vue.js'; 2 | import { fieldHandler } from '../../mixins/fieldHandler'; 3 | import { inputsHandler } from '../../mixins/inputsHandler'; 4 | 5 | Vue.component('recipient-row', { 6 | template: ` 7 | 8 | {{keyIndex + 1}} 9 | 41 | 42 | 43 | `, 44 | props: ['field', 'keyIndex', 'fields', 'type'], 45 | mixins: [fieldHandler, inputsHandler], 46 | }); 47 | -------------------------------------------------------------------------------- /resources/js/src/fields/repeater/mixins/init.js: -------------------------------------------------------------------------------- 1 | /* global notification */ 2 | 3 | import sortableHandle from './sortableHandle'; 4 | 5 | export const init = { 6 | mounted() { 7 | this.setType(); 8 | this.apiCall(); 9 | this.sortable(); 10 | }, 11 | methods: { 12 | apiCall() { 13 | this.postID = notification.postId; 14 | 15 | fetch(`${notification.repeaterRestUrl}${this.postID}`, { 16 | method: 'POST', 17 | headers: { 18 | Accept: 'application/json', 19 | 'Content-Type': 'application/json', 20 | 'X-WP-Nonce': notification.restNonce, 21 | }, 22 | body: JSON.stringify(this.type), 23 | }) 24 | .then((res) => res.json()) 25 | .then((data) => { 26 | // eslint-disable-next-line camelcase 27 | const { field, values } = data; 28 | 29 | if (field) { 30 | this.addNestedModel(field); 31 | this.addModel(field); 32 | 33 | if (values) { 34 | this.values = values; 35 | this.rowCount = this.values.length; 36 | this.addFields(this.rowCount, this.model); 37 | this.addFieldValues(); 38 | } 39 | } 40 | }) 41 | //eslint-disable-next-line no-unused-vars 42 | .catch((err) => { 43 | this.repeaterError = true; 44 | }); 45 | }, 46 | setType() { 47 | const instance = this.$el; 48 | const fieldType = instance.getAttribute('data-field-name'); 49 | const fieldCarrier = instance.getAttribute('data-carrier'); 50 | 51 | this.type = { 52 | fieldType, 53 | fieldCarrier, 54 | }; 55 | }, 56 | sortable() { 57 | sortableHandle(); 58 | }, 59 | }, 60 | }; 61 | -------------------------------------------------------------------------------- /resources/js/src/fields/repeater/mixins/repeaterHandler.js: -------------------------------------------------------------------------------- 1 | export const repeaterHandler = { 2 | data() { 3 | return { 4 | fields: [], 5 | values: this.nestedValues[this.rowIndex], 6 | subModel: [], 7 | subRowName: null, 8 | }; 9 | }, 10 | mounted() { 11 | this.$emit('add-nested-field'); 12 | this.addSubFieldRows(); 13 | this.addFieldValues(); 14 | }, 15 | methods: { 16 | addNestedSubField(e) { 17 | e.preventDefault(); 18 | this.addField(); 19 | this.$emit('add-nested-field'); 20 | }, 21 | removeSubField(index) { 22 | this.removeField(index, this.fields); 23 | }, 24 | addSubFieldRows() { 25 | if (this.values) { 26 | this.rowCount = this.values.length; 27 | this.addFields(this.rowCount, this.model); 28 | } 29 | }, 30 | }, 31 | }; 32 | -------------------------------------------------------------------------------- /resources/js/src/fields/repeater/mixins/sortableHandle.js: -------------------------------------------------------------------------------- 1 | /* global jQuery */ 2 | 3 | export default () => { 4 | jQuery('.fields-repeater-sortable > tbody').sortable({ 5 | handle: '.handle', 6 | containment: 'parent', 7 | axis: 'y', 8 | start(e, ui) { 9 | ui.placeholder.height(ui.helper[0].scrollHeight); 10 | }, 11 | }); 12 | 13 | jQuery('.fields-repeater-nested-sortable').sortable({ 14 | handle: '.sub-handle', 15 | connectWith: '.fields-repeater-nested-sortable', 16 | containment: 'parent', 17 | items: 'tr.row', 18 | placeholder: 'tr.row', 19 | axis: 'y', 20 | start(e, ui) { 21 | ui.placeholder.height(ui.helper[0].scrollHeight); 22 | }, 23 | }); 24 | }; 25 | -------------------------------------------------------------------------------- /resources/js/src/fields/repeater/nestedRepeater.js: -------------------------------------------------------------------------------- 1 | import Vue from 'vue/dist/vue.js'; 2 | import { init } from './mixins/init'; 3 | import { fieldHandler } from './mixins/fieldHandler'; 4 | import { inputsHandler } from './mixins/inputsHandler'; 5 | import { sectionsModal } from '../section-repeater/mixins/sectionsModal'; 6 | 7 | document.addEventListener('DOMContentLoaded', () => { 8 | const vueWrappers = document.querySelectorAll('.vue-repeater'); 9 | const vueInstances = {}; 10 | 11 | for (const wrapper of vueWrappers) { 12 | const wrapperId = wrapper.getAttribute('id'); 13 | 14 | vueInstances[wrapperId] = new Vue({ 15 | el: `#${wrapperId}`, 16 | mixins: [init, fieldHandler, inputsHandler, sectionsModal], 17 | data: { 18 | model: [], 19 | nestedModel: [], 20 | type: {}, 21 | fields: [], 22 | nestedFields: [], 23 | rowCount: 0, 24 | nestedRowCount: 0, 25 | values: [], 26 | nestedValues: [], 27 | postID: '', 28 | nestedRepeater: false, 29 | repeaterError: false, 30 | }, 31 | }); 32 | } 33 | }); 34 | -------------------------------------------------------------------------------- /resources/js/src/fields/section-repeater/components/checkbox.js: -------------------------------------------------------------------------------- 1 | import Vue from 'vue/dist/vue.js'; 2 | import { inputsHandler } from '../../repeater/mixins/inputsHandler'; 3 | import { fieldHandler } from '../../repeater/mixins/fieldHandler'; 4 | import { inputNameHandler } from '../mixins/inputNameHandler'; 5 | 6 | Vue.component('notification-checkbox', { 7 | template: ` 8 |
9 | 20 |
21 | `, 22 | props: [ 23 | 'subfield', 24 | 'rowIndex', 25 | 'keyIndex', 26 | 'type', 27 | 'sectionName', 28 | 'inputType', 29 | 'parentField', 30 | ], 31 | mixins: [inputsHandler, fieldHandler, inputNameHandler], 32 | computed: { 33 | inputName() { 34 | const baseFieldName = this.createFieldName( 35 | this.type, 36 | this.rowIndex, 37 | this.subfield 38 | ); 39 | const fieldName = `[${this.parentFieldName}][${this.keyIndex}]`; 40 | if ('repeater' === this.inputType) { 41 | return `${baseFieldName}${fieldName.toLowerCase()}[${this.sectionName.toLowerCase()}][${this.subfield.name.toLowerCase()}]`; 42 | } 43 | return `${baseFieldName}${fieldName.toLowerCase()}[${this.subfield.name.toLowerCase()}]`; 44 | }, 45 | }, 46 | }); 47 | -------------------------------------------------------------------------------- /resources/js/src/fields/section-repeater/components/textarea.js: -------------------------------------------------------------------------------- 1 | import Vue from 'vue/dist/vue.js'; 2 | import { inputsHandler } from '../../repeater/mixins/inputsHandler'; 3 | import { fieldHandler } from '../../repeater/mixins/fieldHandler'; 4 | import { inputNameHandler } from '../mixins/inputNameHandler'; 5 | 6 | Vue.component('notification-textarea', { 7 | template: ` 8 |
9 | 12 | 22 | 25 | {{ subfield.description }} 26 | 27 |
28 | `, 29 | props: [ 30 | 'subfield', 31 | 'rowIndex', 32 | 'keyIndex', 33 | 'type', 34 | 'sectionName', 35 | 'inputType', 36 | 'parentField', 37 | ], 38 | mixins: [inputsHandler, fieldHandler, inputNameHandler], 39 | computed: { 40 | inputName() { 41 | const baseFieldName = this.createFieldName( 42 | this.type, 43 | this.rowIndex, 44 | this.subfield 45 | ); 46 | const fieldName = `[${this.parentFieldName}][${this.keyIndex}]`; 47 | if ('repeater' === this.inputType) { 48 | return `${baseFieldName}${fieldName.toLowerCase()}[${this.sectionName.toLowerCase()}][${this.subfield.name.toLowerCase()}]`; 49 | } 50 | return `${baseFieldName}${fieldName.toLowerCase()}[${this.subfield.name.toLowerCase()}]`; 51 | }, 52 | }, 53 | }); 54 | -------------------------------------------------------------------------------- /resources/js/src/fields/section-repeater/mixins/init.js: -------------------------------------------------------------------------------- 1 | /* global notification */ 2 | 3 | export const init = { 4 | mounted() { 5 | this.setType(); 6 | this.apiCall(); 7 | }, 8 | methods: { 9 | apiCall() { 10 | this.postID = notification.postId; 11 | 12 | fetch(`${notification.sectionRepeaterRestUrl}${this.postID}`, { 13 | method: 'POST', 14 | headers: { 15 | Accept: 'application/json', 16 | 'Content-Type': 'application/json', 17 | 'X-WP-Nonce': notification.restNonce, 18 | }, 19 | body: JSON.stringify(this.type), 20 | }) 21 | .then((res) => res.json()) 22 | .then((data) => { 23 | const { sections, values } = data; 24 | 25 | if (sections) { 26 | this.sections = sections; 27 | this.extractFields(); 28 | } 29 | 30 | if (values) { 31 | this.values = values; 32 | this.addFieldSectionValues(); 33 | } 34 | }) 35 | //eslint-disable-next-line no-unused-vars 36 | .catch((err) => { 37 | this.repeaterError = true; 38 | }); 39 | }, 40 | extractFields() { 41 | const baseFields = {}; 42 | // eslint-disable-next-line no-unused-vars 43 | for (const [section, field] of Object.entries(this.sections)) { 44 | for (const [name, data] of Object.entries(field.fields)) { 45 | baseFields[name] = data; 46 | } 47 | } 48 | 49 | this.baseFields = baseFields; 50 | }, 51 | setType() { 52 | const instance = this.$el; 53 | const fieldType = instance.getAttribute('data-field-name'); 54 | const fieldCarrier = instance.getAttribute('data-carrier'); 55 | 56 | this.type = { 57 | fieldType, 58 | fieldCarrier, 59 | }; 60 | }, 61 | }, 62 | }; 63 | -------------------------------------------------------------------------------- /resources/js/src/fields/section-repeater/mixins/inputNameHandler.js: -------------------------------------------------------------------------------- 1 | export const inputNameHandler = { 2 | data() { 3 | return { 4 | parentFieldName: null, 5 | nested: false, 6 | }; 7 | }, 8 | mounted() { 9 | this.setProps(); 10 | }, 11 | methods: { 12 | setProps() { 13 | const parent = this.$parent; 14 | 15 | this.parentFieldName = Object.freeze( 16 | this.parentField.toLowerCase() 17 | ); 18 | this.nested = Object.freeze(parent.nested); 19 | }, 20 | }, 21 | }; 22 | -------------------------------------------------------------------------------- /resources/js/src/fields/section-repeater/mixins/sectionsModal.js: -------------------------------------------------------------------------------- 1 | export const sectionsModal = { 2 | data() { 3 | return { 4 | modalOpen: false, 5 | }; 6 | }, 7 | methods: { 8 | addSection(e) { 9 | if (e) { 10 | e.preventDefault(); 11 | } 12 | 13 | this.modalOpen = true; 14 | 15 | window.addEventListener('click', (event) => { 16 | if ( 17 | !event.target.classList.contains('add-new-sections-field') 18 | ) { 19 | this.modalOpen = false; 20 | } 21 | }); 22 | }, 23 | createSection(e, section) { 24 | e.preventDefault(); 25 | e.stopPropagation(); 26 | 27 | this.selectedSection = section.name; 28 | this.savedSections.push(section.name); 29 | this.addFieldSection(section.fields); 30 | this.modalOpen = false; 31 | }, 32 | createSubSection(section) { 33 | this.addSubFieldSection(section.name); 34 | this.modalOpen = false; 35 | }, 36 | }, 37 | }; 38 | -------------------------------------------------------------------------------- /resources/js/src/fields/section-repeater/sectionRepeater.js: -------------------------------------------------------------------------------- 1 | import Vue from 'vue/dist/vue.js'; 2 | import { init } from './mixins/init'; 3 | import { sectionsModal } from './mixins/sectionsModal'; 4 | import { sectionsHandler } from './mixins/sectionsHandler'; 5 | 6 | document.addEventListener('DOMContentLoaded', () => { 7 | const sectionWrappers = document.querySelectorAll('.vue-section-repeater'); 8 | const sectionRepeaters = {}; 9 | 10 | for (const wrapper of sectionWrappers) { 11 | const wrapperId = wrapper.getAttribute('id'); 12 | 13 | sectionRepeaters[wrapperId] = new Vue({ 14 | el: `#${wrapperId}`, 15 | mixins: [init, sectionsModal, sectionsHandler], 16 | data: { 17 | type: {}, 18 | sections: {}, 19 | rows: {}, 20 | rowCount: 0, 21 | selectedSection: null, 22 | savedSections: [], 23 | values: {}, 24 | subFieldValues: [], 25 | baseFields: {}, 26 | repeaterError: false, 27 | }, 28 | }); 29 | } 30 | }); 31 | -------------------------------------------------------------------------------- /resources/js/src/scripts.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Vendor 3 | */ 4 | import './vendor/event-manager.js'; 5 | 6 | /** 7 | * Components 8 | */ 9 | import './component/carriers-widget.js'; 10 | import './component/import-export.js'; 11 | import './component/logs.js'; 12 | import './component/mergetag.js'; 13 | import './component/pretty-select.js'; 14 | import './component/remove-confirmation.js'; 15 | import './component/settings.js'; 16 | import './component/switch.js'; 17 | import './component/sync.js'; 18 | import './component/trigger.js'; 19 | import './component/wizard.js'; 20 | 21 | /** 22 | * Fields 23 | */ 24 | import './fields/code-editor.js'; 25 | import './fields/color-picker.js'; 26 | import './fields/image.js'; 27 | // Repeater 28 | import './fields/repeater/components/inputs/select'; 29 | import './fields/repeater/components/repeater/repeaterRow'; 30 | import './fields/repeater/components/repeater/recipientRow'; 31 | import './fields/repeater/components/repeater/nestedSubField'; 32 | import './fields/repeater/components/repeater/repeaterSubRow'; 33 | import './fields/repeater/mixins/init'; 34 | import './fields/repeater/nestedRepeater'; 35 | // Section Repeater 36 | import './fields/section-repeater/components/select'; 37 | import './fields/section-repeater/components/input'; 38 | import './fields/section-repeater/components/checkbox'; 39 | import './fields/section-repeater/components/textarea'; 40 | import './fields/section-repeater/sections/sectionSubRow'; 41 | import './fields/section-repeater/sections/sectionsRow'; 42 | import './fields/section-repeater/sections/nestedSubSection'; 43 | import './fields/section-repeater/sectionRepeater'; 44 | -------------------------------------------------------------------------------- /resources/templates/debug/pagination.php: -------------------------------------------------------------------------------- 1 | admin_url( 19 | 'edit.php?post_type=notification&page=settings§ion=debugging&' . $get('query_arg') . '=%#%' 20 | ), 21 | 'current' => $get('current'), 22 | 'total' => $get('total'), 23 | ] 24 | ); 25 | 26 | if ($links === null) { 27 | return; 28 | } 29 | 30 | ?> 31 | 32 |
33 | 34 |
35 | -------------------------------------------------------------------------------- /resources/templates/extension/activation-error.php: -------------------------------------------------------------------------------- 1 | 17 | 18 |
19 |

20 | 21 |

22 | 32 | : 33 |

34 | 35 |
36 | -------------------------------------------------------------------------------- /resources/templates/extension/activation-success.php: -------------------------------------------------------------------------------- 1 | 19 | 20 |
21 |

22 |
23 | -------------------------------------------------------------------------------- /resources/templates/form/empty-form.php: -------------------------------------------------------------------------------- 1 | 17 | 18 |

19 | 25 |

26 | -------------------------------------------------------------------------------- /resources/templates/form/field-hidden.php: -------------------------------------------------------------------------------- 1 | field(); 19 | -------------------------------------------------------------------------------- /resources/templates/help/global-merge-tags.php: -------------------------------------------------------------------------------- 1 | 17 | 18 |

19 | 25 |

26 | 27 | 28 | 29 | 30 | 31 | 39 | 52 | 53 | 54 |
getName()); ?> 32 | 36 | {getSlug()); ?>} 37 | 38 | 40 | getDescription(); ?> 41 | 42 |

43 | isDescriptionExample()) : ?> 44 | 45 | 46 | 47 | 48 | 49 |

50 | 51 |
55 | -------------------------------------------------------------------------------- /resources/templates/help/sidebar.php: -------------------------------------------------------------------------------- 1 | 17 | 18 |

19 | 25 |

26 | 27 | 68 | -------------------------------------------------------------------------------- /resources/templates/import/notifications.php: -------------------------------------------------------------------------------- 1 | 17 | 18 |
19 | 24 | 29 | 34 | 35 |

36 |
37 | -------------------------------------------------------------------------------- /resources/templates/mergetag/metabox-list.php: -------------------------------------------------------------------------------- 1 | 28 | 29 |
    30 | 36 | 37 |
  • 38 | $tag] 42 | ); 43 | ?> 44 |
  • 45 | 46 | 52 |
53 | 54 | 58 | -------------------------------------------------------------------------------- /resources/templates/mergetag/metabox-nomergetags.php: -------------------------------------------------------------------------------- 1 | 17 | 18 |

19 | 25 |

26 | -------------------------------------------------------------------------------- /resources/templates/mergetag/metabox-notrigger.php: -------------------------------------------------------------------------------- 1 | 17 | 18 |

19 | 20 |

21 | -------------------------------------------------------------------------------- /resources/templates/mergetag/searchbox.php: -------------------------------------------------------------------------------- 1 | 17 | 18 | 25 | -------------------------------------------------------------------------------- /resources/templates/mergetag/tag.php: -------------------------------------------------------------------------------- 1 | 20 | 21 |
22 | 23 | 27 | {getSlug()); ?>} 28 | 29 |
30 | getDescription(); ?> 31 | 32 | 33 | ? 34 |
35 |
36 | isDescriptionExample()) : ?> 37 | 45 | 46 |
47 | 48 |
49 | isDescriptionExample()) : ?> 50 | (getValueType()); ?>) 51 | 52 |
53 |
54 |
55 | 56 | -------------------------------------------------------------------------------- /resources/templates/sync/actions.php: -------------------------------------------------------------------------------- 1 | 17 | 18 | 26 | -------------------------------------------------------------------------------- /resources/templates/sync/disabled.php: -------------------------------------------------------------------------------- 1 | \BracketSpace\Notification\Core\Sync::enable()' 23 | ), 24 | 'notification' 25 | ) 26 | ); 27 | -------------------------------------------------------------------------------- /resources/templates/sync/notifications-empty.php: -------------------------------------------------------------------------------- 1 | 19 | 20 |

21 | 27 |

28 | 29 | 30 |

31 | 37 |

38 | 39 | 40 | 48 | 49 | get_vars() 53 | ); 54 | ?> 55 | 56 | 64 | 65 | 66 | -------------------------------------------------------------------------------- /resources/templates/trigger/select.php: -------------------------------------------------------------------------------- 1 | 19 | 20 | 56 | -------------------------------------------------------------------------------- /resources/templates/upsell/carriers-upsell.php: -------------------------------------------------------------------------------- 1 | 12 | 13 |

14 | extensions.', 20 | 'notification' 21 | ), 22 | admin_url('edit.php?post_type=notification&page=extensions') 23 | ); 24 | // phpcs:enable 25 | ?> 26 |

27 | 28 |
29 | -------------------------------------------------------------------------------- /resources/templates/upsell/conditionals-metabox.php: -------------------------------------------------------------------------------- 1 | %s', 14 | __( 15 | 'Conditionals extension', 16 | 'notification' 17 | ) 18 | ); 19 | 20 | ?> 21 | 22 | 57 | 58 | PRO 59 | 70 | -------------------------------------------------------------------------------- /resources/templates/upsell/custom-development.php: -------------------------------------------------------------------------------- 1 | 12 | 13 |
14 |

15 | 21 |

22 |

23 | 29 |

30 | %s', 34 | esc_html__( 35 | 'Find out more', 36 | 'notification' 37 | ) 38 | ); 39 | 40 | echo wp_kses_post($description); 41 | ?> 42 |
43 | -------------------------------------------------------------------------------- /resources/templates/upsell/custom-fields-mergetag-group.php: -------------------------------------------------------------------------------- 1 | %s', 14 | __( 15 | 'Custom Fields extension', 16 | 'notification' 17 | ) 18 | ); 19 | 20 | ?> 21 | 22 |

23 | 29 |

30 |
    34 | PRO 35 | {postmeta …}, {usermeta …}, {commentmeta …}, or {acf …}' 45 | ); 46 | // phpcs:enable 47 | ?> 48 |
49 | -------------------------------------------------------------------------------- /resources/templates/upsell/review-queue-switch.php: -------------------------------------------------------------------------------- 1 | 12 | 13 | 33 |
34 | 38 | 42 |
43 |
44 | -------------------------------------------------------------------------------- /resources/templates/upsell/scheduled-triggers-setting.php: -------------------------------------------------------------------------------- 1 | %s', 14 | __( 15 | 'Scheduled Triggers extension', 16 | 'notification' 17 | ) 18 | ); 19 | 20 | ?> 21 | 22 |

23 | PRO 24 | 35 |

36 |
37 |

38 | 44 |

45 | -------------------------------------------------------------------------------- /resources/templates/upsell/triggers-upsell.php: -------------------------------------------------------------------------------- 1 | 12 | 13 |

14 | extensions.', 20 | 'notification' 21 | ), 22 | admin_url('edit.php?post_type=notification&page=extensions') 23 | ); 24 | // phpcs:enable 25 | ?> 26 |

27 | 28 |
29 | -------------------------------------------------------------------------------- /resources/wizard-data/comment_added.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3af4a63af8b", 3 | "title": "Comment added - post author", 4 | "trigger": "comment/comment/added", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - a new comment to your \"{post_title}\" post has been added", 10 | "body": "A new comment on the post \"{post_title}\" is waiting for your approval\r\n{post_permalink}\r\n\r\nAuthor: {comment_author_user_display_name} (IP address: {comment_author_IP})\r\nEmail: {comment_author_user_email}\r\nURL: {comment_author_url}\r\nComment: {comment_content}\r\n\r\nApprove it: {comment_approve_action_url}\r\nTrash it: {comment_trash_action_url}\r\nDelet it: {comment_delete_action_url}\r\nSpam it: {comment_spam_action_url}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{post_author_user_email}" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564144806 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/comment_moderation.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3adb5ed7076", 3 | "title": "Comment is awaiting moderation", 4 | "trigger": "comment/comment/added", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - Please moderate: \"{post_title}\"", 10 | "body": "A new comment on the post \"{post_title}\" is waiting for your approval\r\n{post_permalink}\r\n\r\nAuthor: {comment_author_user_display_name} (IP address: {comment_author_IP})\r\nEmail: {comment_author_user_email}\r\nURL: {comment_author_url}\r\nComment: {comment_content}\r\n\r\nApprove it: {comment_approve_action_url}\r\nTrash it: {comment_trash_action_url}\r\nDelet it: {comment_delete_action_url}\r\nSpam it: {comment_spam_action_url}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{post_author_user_email}" 15 | }, 16 | { 17 | "type": "administrator", 18 | "recipient": "" 19 | } 20 | ], 21 | "headers": null 22 | } 23 | }, 24 | "enabled": true, 25 | "extras": [], 26 | "version": 1564138334 27 | } 28 | -------------------------------------------------------------------------------- /resources/wizard-data/comment_published.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5cac7fb9e2619", 3 | "title": "Comment has been published", 4 | "trigger": "comment/comment/approved", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - Comment: \"{post_title}\"", 10 | "body": "New comment on your post \"{post_title}\"\r\n\r\nAuthor: {comment_author_user_display_name} (IP address: {comment_author_IP})\r\n\r\nEmail: {comment_author_user_email}\r\n\r\nURL: {comment_author_url}\r\n\r\nComment: {comment_content}\r\n\r\nYou can see all comments on this post here:\r\n{post_permalink}#comments\r\n\r\nPermalink: {post_permalink}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{post_author_user_email}" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564138047 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/comment_reply.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3af50b188af", 3 | "title": "Comment reply - comment author", 4 | "trigger": "comment/comment/replied", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - a new reply to your comment on \"{post_title}\"", 10 | "body": "A new reply to your comment on the post \"{post_title}\" has been just added.\r\n{post_permalink}\r\n\r\nAuthor: {comment_author_user_display_name}\r\nURL: {comment_author_url}\r\nComment: {comment_content}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{parent_comment_author_user_email}" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564144907 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/new_user.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5cac7b60d7b35", 3 | "title": "New user registration - admin", 4 | "trigger": "user/registered", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - New User Registration", 10 | "body": "New user registration on your site {site_name}:\r\n\r\nUsername: {user_login}\r\n\r\nEmail: {user_email}", 11 | "recipients": [ 12 | { 13 | "type": "administrator", 14 | "recipient": "" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1560424422 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/password_forgotten.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5cac7aa3e5b47", 3 | "title": "User requests a password reset via \\\"Lost your password?\\\"", 4 | "trigger": "user/password_reset_request", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - Password Reset", 10 | "body": "Someone has requested a password reset for the following account:\r\n\r\nSite Name: {site_title}\r\n\r\nUsername: {user_nicename}\r\n\r\nIf this was a mistake, just ignore this email and nothing will happen.\r\n\r\nTo reset your password, visit the following address:\r\n\r\n{user_password_reset_link}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{user_email}" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1560424019 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/password_reset.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5cac81ab3044e", 3 | "title": "User resets their password from the password reset link", 4 | "trigger": "user/password_changed", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - Password Reset", 10 | "body": "Password changed for user: {user_login}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{user_email}" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1560424061 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/post_published_admin.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3af2af40f08", 3 | "title": "Post published - admin", 4 | "trigger": "post/post/published", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - Post \"{post_title}\" has been published", 10 | "body": "The post \"{post_title}\" has been just published.\r\n\r\nView: {post_permalink}\r\nEdit: {home_url}/wp-admin/post.php?post={post_ID}&action=edit", 11 | "recipients": [ 12 | { 13 | "type": "administrator", 14 | "recipient": "" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564144303 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/post_published_subscribers.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3af33ca0f05", 3 | "title": "Post published - subscribers", 4 | "trigger": "post/post/published", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - New post: \"{post_title}\"", 10 | "body": "Howdy,\r\n\r\nwe just published a new post: \"{post_title}\".\r\n\r\nSee the post: {post_permalink}", 11 | "recipients": [ 12 | { 13 | "type": "role", 14 | "recipient": "subscriber" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564144458 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/post_review.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3af398e4f96", 3 | "title": "Post pending review - admin", 4 | "trigger": "post/post/pending", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - A new post \"{post_title}\" is pending review", 10 | "body": "The post \"{post_title}\" has been just sent for a review.\r\n\r\nView: {post_permalink}\r\nEdit: {home_url}/wp-admin/post.php?post={post_ID}&action=edit", 11 | "recipients": [ 12 | { 13 | "type": "administrator", 14 | "recipient": "" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564144536 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/post_updated.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3af3d844ac5", 3 | "title": "Post updated - admin", 4 | "trigger": "post/post/updated", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - The post \"{post_title}\" has been updated", 10 | "body": "The post \"{post_title}\" has been just updated.\r\n\r\nView: {post_permalink}\r\nEdit: {home_url}/wp-admin/post.php?post={post_ID}&action=edit", 11 | "recipients": [ 12 | { 13 | "type": "administrator", 14 | "recipient": "" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564144600 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/welcome_email.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5d3af43eb9397", 3 | "title": "Welcome email", 4 | "trigger": "user/registered", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "Your account at {site_title}", 10 | "body": "Howdy,\r\n\r\nthanks for registering your account on our website!\r\n\r\nYour username is: {user_login}\r\n\r\nPlease, setup your password: {user_password_setup_link}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{user_email}" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564144702 23 | } 24 | -------------------------------------------------------------------------------- /resources/wizard-data/your_account.json: -------------------------------------------------------------------------------- 1 | { 2 | "hash": "notification_5cac7c1bbfd28", 3 | "title": "New user registration - user", 4 | "trigger": "user/registered", 5 | "carriers": { 6 | "email": { 7 | "activated": true, 8 | "enabled": true, 9 | "subject": "{site_title} - Login Details", 10 | "body": "Username: %s\r\n\r\nTo set your password, visit the following address:\r\n\r\n{user_password_setup_link}", 11 | "recipients": [ 12 | { 13 | "type": "email", 14 | "recipient": "{user_email}" 15 | } 16 | ], 17 | "headers": null 18 | } 19 | }, 20 | "enabled": true, 21 | "extras": [], 22 | "version": 1564137499 23 | } 24 | -------------------------------------------------------------------------------- /src/Api/Controller/CheckRestApiController.php: -------------------------------------------------------------------------------- 1 | send('RestApi'); 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /src/Api/Controller/SelectInputController.php: -------------------------------------------------------------------------------- 1 | get_params(); 33 | $carrier = $params['carrier']; 34 | $type = $params['type']; 35 | $recipient = RecipientStore::get($carrier, $type); 36 | $response = new Response(); 37 | 38 | if ($recipient) { 39 | $input = $recipient->input(); 40 | 41 | $data['options'] = $input->options; 42 | $data['pretty'] = $input->pretty; 43 | $data['label'] = $input->label; 44 | $data['checkbox_label'] = $input->checkboxLabel; 45 | $data['name'] = $input->name; 46 | $data['description'] = $input->description; 47 | $data['section'] = $input->section; 48 | $data['disabled'] = $input->disabled; 49 | $data['css_class'] = $input->cssClass; 50 | $data['id'] = $input->id; 51 | $data['placeholder'] = $input->placeholder; 52 | $data['type'] = strtolower(str_replace('Field', '', $input->fieldTypeHtml)); 53 | $data['value'] = $input->value; 54 | 55 | $response->send($data); 56 | } else { 57 | $response->send(['message' => 'no recipient']); 58 | } 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /src/Compat/RestApiCompat.php: -------------------------------------------------------------------------------- 1 | base === 'post' && $currentScreen->post_type === 'notification'; 35 | } 36 | 37 | if (! $isEdit) { 38 | return; 39 | } 40 | 41 | $response = wp_remote_get(get_rest_url(null, \Notification::component(Api::class)->getEndpoint('check'))); 42 | 43 | $message = json_decode(wp_remote_retrieve_body($response), true); 44 | 45 | $isAvailable = false; 46 | 47 | if ( 48 | is_array($message) && 49 | array_key_exists('data', $message) && 50 | $message['data'] === 'RestApi' 51 | ) { 52 | return; 53 | } 54 | 55 | printf( 56 | '

%1$s

', 57 | esc_html__( 58 | "The Notification plugin requires enabled REST API endpoint: notification/v1/. 59 | Please ensure your WP REST API works correctly and you're not blocking this endpoint from access.", 60 | 'notification' 61 | ) 62 | ); 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /src/Compat/WebhookCompat.php: -------------------------------------------------------------------------------- 1 | get_var( 32 | DatabaseService::db()->prepare( 33 | "SELECT COUNT(*) FROM %i WHERE slug IN ('webhook', 'webhook_json')", 34 | NotificationDatabaseService::getNotificationCarriersTableName() 35 | ) 36 | ); 37 | } 38 | 39 | /** 40 | * Displays a notice message when someone is 41 | * using the deprecated webhooks. 42 | * 43 | * @action admin_notices 44 | * 45 | * @return void 46 | */ 47 | public function displayNotice() 48 | { 49 | if (! self::hasDeprecatedWebhookCarriers()) { 50 | return; 51 | } 52 | 53 | Templates::render('notice/webhook-deprecated'); 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /src/Core/Binder.php: -------------------------------------------------------------------------------- 1 | $triggers Array of Triggers or single Trigger. 24 | * @return void 25 | * @since 8.0.0 26 | */ 27 | public static function bind($triggers) 28 | { 29 | if (!is_array($triggers)) { 30 | $triggers = [$triggers]; 31 | } 32 | 33 | foreach ($triggers as $trigger) { 34 | \assert($trigger instanceof \BracketSpace\Notification\Interfaces\Triggerable); 35 | foreach ($trigger->getActions() as $action) { 36 | add_action( 37 | $action['tag'], 38 | [new Runner($trigger), 'run'], 39 | $action['priority'], 40 | $action['accepted_args'] 41 | ); 42 | } 43 | } 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /src/Database/DatabaseService.php: -------------------------------------------------------------------------------- 1 | prefix . $tableName; 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /src/ErrorHandler.php: -------------------------------------------------------------------------------- 1 | getSlug() !== 'user/login') { 30 | return; 31 | } 32 | 33 | $trigger->addAction( 34 | 'ntfn_proxy_two_factor_user_authenticated', 35 | 10, 36 | 2 37 | ); 38 | } 39 | 40 | /** 41 | * Proxies the 2FA action to change parameters 42 | * 43 | * @action two_factor_user_authenticated 44 | * 45 | * @param \WP_User $user User instance. 46 | * @return void 47 | * @since 7.0.0 48 | */ 49 | public function userLoginWith2fa($user) 50 | { 51 | // phpcs:ignore Squiz.NamingConventions.ValidVariableName.MemberNotCamelCaps 52 | do_action('ntfn_proxy_two_factor_user_authenticated', $user->user_login, $user); 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/Interfaces/Convertable.php: -------------------------------------------------------------------------------- 1 | $data The notification representation 24 | * @return Notification 25 | */ 26 | public function from($data): Notification; 27 | 28 | /** 29 | * Converts the notification to another type of representation 30 | * 31 | * @since 9.0.0 32 | * @param Notification $notification Notification instance 33 | * @param array $config The additional configuration of the converter 34 | * @return mixed 35 | */ 36 | public function to(Notification $notification, array $config = []); 37 | } 38 | -------------------------------------------------------------------------------- /src/Interfaces/Nameable.php: -------------------------------------------------------------------------------- 1 | array of resolved values 24 | */ 25 | public function parseValue($value = ''); 26 | 27 | /** 28 | * Returns input object 29 | * Must be defined in the child class 30 | * 31 | * @return object 32 | */ 33 | public function input(); 34 | 35 | /** 36 | * Gets default value 37 | * 38 | * @return string 39 | */ 40 | public function getDefaultValue(); 41 | } 42 | -------------------------------------------------------------------------------- /src/Interfaces/Resolvable.php: -------------------------------------------------------------------------------- 1 | $match Match array. 43 | * @param \BracketSpace\Notification\Interfaces\Triggerable $trigger Trigger object. 44 | * @return string Resolved value 45 | */ 46 | public function resolveMergeTag($match, Triggerable $trigger); 47 | } 48 | -------------------------------------------------------------------------------- /src/Interfaces/Storable.php: -------------------------------------------------------------------------------- 1 | 31 | */ 32 | public function getMergeTags($type = 'all', $grouped = false); 33 | 34 | /** 35 | * Clears the merge tags 36 | * 37 | * @return $this 38 | */ 39 | public function clearMergeTags(); 40 | 41 | /** 42 | * Stops the trigger. 43 | * 44 | * @return void 45 | */ 46 | public function stop(); 47 | 48 | /** 49 | * Checks if trigger has been stopped 50 | * 51 | * @return bool 52 | */ 53 | public function isStopped(): bool; 54 | 55 | /** 56 | * Gets Trigger actions 57 | * 58 | * @return array 59 | * @since 8.0.0 60 | */ 61 | public function getActions(): array; 62 | 63 | /** 64 | * Gets group 65 | * 66 | * @return string|null 67 | */ 68 | public function getGroup(); 69 | } 70 | -------------------------------------------------------------------------------- /src/Repository/CarrierRepository.php: -------------------------------------------------------------------------------- 1 | getSetting('carriers/email/enable')) { 27 | Register::carrier(\Notification::component(Carrier\Email::class)); 28 | } 29 | 30 | if ( 31 | ! \Notification::settings()->getSetting('carriers/webhook/enable') || 32 | ! apply_filters('notification/compat/webhook/register', true) 33 | ) { 34 | return; 35 | } 36 | 37 | Register::carrier(new Webhook('Webhook')); 38 | Register::carrier(new WebhookJson('Webhook JSON')); 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /src/Repository/Field/CheckboxField.php: -------------------------------------------------------------------------------- 1 | $params field configuration parameters. 30 | * @since 5.0.0 31 | */ 32 | public function __construct($params = []) 33 | { 34 | $this->checkboxLabel = $params['checkbox_label'] ?? __('Enable', 'notification'); 35 | 36 | parent::__construct($params); 37 | } 38 | 39 | /** 40 | * Returns field HTML 41 | * 42 | * @return string html 43 | */ 44 | public function field() 45 | { 46 | return sprintf( 47 | '', 48 | esc_attr($this->getName()), 49 | esc_attr($this->getId()), 50 | checked($this->getValue(), '1', false), 51 | esc_attr($this->cssClass()), 52 | $this->maybeDisable(), 53 | esc_html($this->checkboxLabel) 54 | ); 55 | } 56 | 57 | /** 58 | * Sanitizes the value sent by user 59 | * 60 | * @param mixed $value value to sanitize. 61 | * @return mixed sanitized value 62 | */ 63 | public function sanitize($value) 64 | { 65 | return $value 66 | ? 1 67 | : 0; 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /src/Repository/Field/ColorPickerField.php: -------------------------------------------------------------------------------- 1 | ', 27 | esc_attr($this->getName()), 28 | esc_attr($this->getId()), 29 | esc_attr($this->getValue()), 30 | esc_attr($this->cssClass()), 31 | $this->maybeDisable() 32 | ); 33 | } 34 | 35 | /** 36 | * Sanitizes the value sent by user 37 | * 38 | * @param mixed $value value to sanitize. 39 | * @return mixed sanitized value 40 | */ 41 | public function sanitize($value) 42 | { 43 | if (strpos($value, 'rgba') === false) { 44 | return sanitize_hex_color($value); 45 | } 46 | 47 | $color = str_replace(' ', '', $value); 48 | sscanf($color, 'rgba(%d,%d,%d,%f)', $red, $green, $blue, $alpha); 49 | return 'rgba(' . $red . ',' . $green . ',' . $blue . ',' . $alpha . ')'; 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /src/Repository/Field/ImageField.php: -------------------------------------------------------------------------------- 1 | getValue() > 0 27 | ? 'selected' 28 | : ''; 29 | 30 | return sprintf( 31 | '
32 | 33 | 34 |
35 | 36 | 37 |
38 |
', 39 | esc_attr($class), 40 | esc_attr($this->getName()), 41 | esc_attr($this->getId()), 42 | esc_attr($this->getValue()), 43 | esc_attr($this->cssClass()), 44 | $this->maybeDisable(), 45 | esc_html__('Select image', 'notification'), 46 | wp_get_attachment_thumb_url($this->getValue()) 47 | ); 48 | } 49 | 50 | /** 51 | * Sanitizes the value sent by user 52 | * 53 | * @param string $value value to sanitize. 54 | * @return mixed sanitized value 55 | */ 56 | public function sanitize($value) 57 | { 58 | return intval($value); 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /src/Repository/Field/MessageField.php: -------------------------------------------------------------------------------- 1 | $params field configuration parameters. 50 | * @since 6.3.1 Allow for whitespace characters. 51 | * @since 5.0.0 52 | */ 53 | public function __construct($params = []) 54 | { 55 | if (!isset($params['message'])) { 56 | trigger_error('MessageField requires message param', E_USER_ERROR); 57 | } 58 | 59 | $this->message = $params['message']; 60 | 61 | if (isset($params['name'])) { 62 | $this->name = $params['name']; 63 | } 64 | 65 | parent::__construct($params); 66 | } 67 | 68 | /** 69 | * Returns field HTML 70 | * 71 | * @return string html 72 | */ 73 | public function field() 74 | { 75 | return wp_kses_post(is_callable($this->message) ? $this->message() : $this->message); 76 | } 77 | 78 | /** 79 | * Sanitizes the value sent by user 80 | * 81 | * @param mixed $value value to sanitize. 82 | * @return null 83 | */ 84 | public function sanitize($value) 85 | { 86 | return null; 87 | } 88 | } 89 | -------------------------------------------------------------------------------- /src/Repository/Field/NonceField.php: -------------------------------------------------------------------------------- 1 | $params field configuration parameters. 29 | * @since 5.0.0 30 | */ 31 | public function __construct($params = []) 32 | { 33 | if (!isset($params['nonce_key'])) { 34 | trigger_error('NonceField requires nonce_key param', E_USER_ERROR); 35 | } 36 | 37 | $this->nonceKey = $params['nonce_key']; 38 | 39 | parent::__construct($params); 40 | } 41 | 42 | /** 43 | * Returns field HTML 44 | * 45 | * @return string html 46 | */ 47 | public function field() 48 | { 49 | return wp_nonce_field( 50 | $this->nonceKey, 51 | $this->getName(), 52 | true, 53 | false 54 | ); 55 | } 56 | 57 | /** 58 | * Sanitizes the value sent by user 59 | * 60 | * @param mixed $value value to sanitize. 61 | * @return mixed sanitized value 62 | */ 63 | public function sanitize($value) 64 | { 65 | return null; 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /src/Repository/Field/SectionsField.php: -------------------------------------------------------------------------------- 1 | 22 | */ 23 | protected $sections = []; 24 | 25 | /** 26 | * Field constructor 27 | * 28 | * @param array $params field configuration parameters. 29 | * @since 5.0.0 30 | */ 31 | public function __construct($params = []) 32 | { 33 | if (!isset($params['sections'])) { 34 | trigger_error('SectionsField requires sections param', E_USER_ERROR); 35 | } 36 | 37 | $this->sections = $params['sections']; 38 | 39 | parent::__construct($params); 40 | } 41 | 42 | /** 43 | * Prints repeater row 44 | * 45 | * @return string row HTML 46 | * @since 5.0.0 47 | */ 48 | public function row() 49 | { 50 | return ''; 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/BooleanTag.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 32 | * @since 5.0.0 33 | */ 34 | public function __construct($params = []) 35 | { 36 | if (isset($params['comment_type']) && !empty($params['comment_type'])) { 37 | $this->commentType = $params['comment_type']; 38 | } 39 | 40 | $this->setTriggerProp($params['property_name'] ?? $this->commentType); 41 | 42 | $commentTypeName = WpObjectHelper::getCommentTypeName($this->commentType); 43 | 44 | $args = wp_parse_args( 45 | $params, 46 | [ 47 | 'slug' => 'comment_author_IP', 48 | // Translators: Comment type name. 49 | 'name' => sprintf(__('%s author IP', 'notification'), $commentTypeName), 50 | 'description' => '127.0.0.1', 51 | 'example' => true, 52 | // Translators: comment type author. 53 | 'group' => sprintf(__('%s author', 'notification'), $commentTypeName), 54 | 'resolver' => function ($trigger) { 55 | return $trigger->{$this->getTriggerProp()}->comment_author_IP; 56 | }, 57 | ] 58 | ); 59 | 60 | parent::__construct($args); 61 | } 62 | } 63 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Comment/CommentContent.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 32 | * @since 5.0.0 33 | */ 34 | public function __construct($params = []) 35 | { 36 | if (isset($params['comment_type']) && !empty($params['comment_type'])) { 37 | $this->commentType = $params['comment_type']; 38 | } 39 | 40 | $this->setTriggerProp($params['property_name'] ?? $this->commentType); 41 | 42 | $commentTypeName = WpObjectHelper::getCommentTypeName($this->commentType); 43 | 44 | $args = wp_parse_args( 45 | $params, 46 | [ 47 | 'slug' => 'comment_content', 48 | // Translators: Comment type name. 49 | 'name' => sprintf(__('%s content', 'notification'), $commentTypeName), 50 | 'description' => __('Great post!', 'notification'), 51 | 'example' => true, 52 | 'group' => $commentTypeName, 53 | 'resolver' => function ($trigger) { 54 | return $trigger->{$this->getTriggerProp()}->comment_content; 55 | }, 56 | ] 57 | ); 58 | 59 | parent::__construct($args); 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Comment/CommentContentHtml.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 32 | * @since 5.0.0 33 | */ 34 | public function __construct($params = []) 35 | { 36 | if (isset($params['comment_type']) && !empty($params['comment_type'])) { 37 | $this->commentType = $params['comment_type']; 38 | } 39 | 40 | $this->setTriggerProp($params['property_name'] ?? $this->commentType); 41 | 42 | $commentTypeName = WpObjectHelper::getCommentTypeName($this->commentType); 43 | 44 | $args = wp_parse_args( 45 | $params, 46 | [ 47 | 'slug' => 'comment_content_html', 48 | // Translators: Comment type name. 49 | 'name' => sprintf(__('%s HTML content', 'notification'), $commentTypeName), 50 | 'description' => __('Great post!', 'notification'), 51 | 'example' => true, 52 | 'group' => $commentTypeName, 53 | 'resolver' => function ($trigger) { 54 | return $trigger->{$this->getTriggerProp()}->comment_content; 55 | }, 56 | ] 57 | ); 58 | 59 | parent::__construct($args); 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Comment/CommentID.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 32 | * @since 5.0.0 33 | */ 34 | public function __construct($params = []) 35 | { 36 | if (isset($params['comment_type']) && !empty($params['comment_type'])) { 37 | $this->commentType = $params['comment_type']; 38 | } 39 | 40 | $this->setTriggerProp($params['property_name'] ?? $this->commentType); 41 | 42 | $commentTypeName = WpObjectHelper::getCommentTypeName($this->commentType); 43 | 44 | $args = wp_parse_args( 45 | $params, 46 | [ 47 | 'slug' => 'comment_ID', 48 | // Translators: Comment type name. 49 | 'name' => sprintf(__('%s ID', 'notification'), $commentTypeName), 50 | 'description' => '35', 51 | 'example' => true, 52 | 'group' => $commentTypeName, 53 | 'resolver' => function ($trigger) { 54 | return $trigger->{$this->getTriggerProp()}->comment_ID; 55 | }, 56 | ] 57 | ); 58 | 59 | parent::__construct($args); 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Comment/CommentType.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 32 | * @since 5.0.0 33 | */ 34 | public function __construct($params = []) 35 | { 36 | if (isset($params['comment_type']) && !empty($params['comment_type'])) { 37 | $this->commentType = $params['comment_type']; 38 | } 39 | 40 | $this->setTriggerProp($params['property_name'] ?? $this->commentType); 41 | 42 | $args = wp_parse_args( 43 | $params, 44 | [ 45 | 'slug' => 'comment_type', 46 | 'name' => __('Comment type', 'notification'), 47 | 'description' => __('Comment or Pingback or Trackback or Custom', 'notification'), 48 | 'group' => WpObjectHelper::getCommentTypeName($this->commentType), 49 | 'resolver' => function ($trigger) { 50 | return get_comment_type($trigger->{$this->getTriggerProp()}); 51 | }, 52 | ] 53 | ); 54 | 55 | parent::__construct($args); 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/EmailTag.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 24 | * @since 5.0.0 25 | */ 26 | public function __construct($params = []) 27 | { 28 | $this->setTriggerProp($params['property_name'] ?? 'attachment'); 29 | 30 | $args = wp_parse_args( 31 | $params, 32 | [ 33 | 'slug' => 'attachment_direct_url', 34 | 'name' => __('Attachment direct URL', 'notification'), 35 | 'description' => __( 36 | 'http://example.com/wp-content/uploads/2018/02/forest-landscape.jpg', 37 | 'notification' 38 | ), 39 | 'example' => true, 40 | 'group' => __('Attachment', 'notification'), 41 | 'resolver' => function () { 42 | return wp_get_attachment_url($this->trigger->{$this->getTriggerProp()}->ID); 43 | }, 44 | ] 45 | ); 46 | 47 | parent::__construct($args); 48 | 49 | $this->setGroup(__('Attachment', 'notification')); 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Media/AttachmentID.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 24 | * @since 5.0.0 25 | */ 26 | public function __construct($params = []) 27 | { 28 | $this->setTriggerProp($params['property_name'] ?? 'attachment'); 29 | 30 | $args = wp_parse_args( 31 | $params, 32 | [ 33 | 'slug' => 'attachment_ID', 34 | 'name' => __('Attachment ID', 'notification'), 35 | 'description' => '35', 36 | 'example' => true, 37 | 'group' => __('Attachment', 'notification'), 38 | 'resolver' => function ($trigger) { 39 | return $trigger->{$this->getTriggerProp()}->ID; 40 | }, 41 | ] 42 | ); 43 | 44 | parent::__construct($args); 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Media/AttachmentMimeType.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 24 | * @since 5.0.0 25 | */ 26 | public function __construct($params = []) 27 | { 28 | $this->setTriggerProp($params['property_name'] ?? 'attachment'); 29 | 30 | $args = wp_parse_args( 31 | $params, 32 | [ 33 | 'slug' => 'attachment_mime_type', 34 | 'name' => __('Attachment MIME type', 'notification'), 35 | 'description' => 'image/jpeg', 36 | 'example' => true, 37 | 'resolver' => function ($trigger) { 38 | return $trigger->{$this->getTriggerProp()}->post_mime_type; 39 | }, 40 | 'group' => __('Attachment', 'notification'), 41 | ] 42 | ); 43 | 44 | parent::__construct($args); 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Media/AttachmentPage.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 24 | * @since 5.0.0 25 | */ 26 | public function __construct($params = []) 27 | { 28 | $this->setTriggerProp($params['property_name'] ?? 'attachment'); 29 | 30 | $args = wp_parse_args( 31 | $params, 32 | [ 33 | 'slug' => 'attachment_page_link', 34 | 'name' => __('Attachment page link', 'notification'), 35 | 'description' => __('http://example.com/forest-landscape/', 'notification'), 36 | 'example' => true, 37 | 'group' => __('Attachment', 'notification'), 38 | 'resolver' => function () { 39 | return get_permalink($this->{$this->getTriggerProp()}->attachment->ID); 40 | }, 41 | ] 42 | ); 43 | 44 | parent::__construct($args); 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Media/AttachmentTitle.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 24 | * @since 5.0.0 25 | */ 26 | public function __construct($params = []) 27 | { 28 | $this->setTriggerProp($params['property_name'] ?? 'attachment'); 29 | 30 | $args = wp_parse_args( 31 | $params, 32 | [ 33 | 'slug' => 'attachment_title', 34 | 'name' => __('Attachment title', 'notification'), 35 | 'description' => __('Forest landscape', 'notification'), 36 | 'example' => true, 37 | 'group' => __('Attachment', 'notification'), 38 | 'resolver' => function ($trigger) { 39 | return $trigger->{$this->getTriggerProp()}->post_title; 40 | }, 41 | ] 42 | ); 43 | 44 | parent::__construct($args); 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/FeaturedImageId.php: -------------------------------------------------------------------------------- 1 | $params Merge tag configuration params. 28 | * @since 6.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_featured_image_id', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s featured image id', 'notification'), $postTypeName), 42 | 'description' => __('123', 'notification'), 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | $postId = $trigger->{$this->getTriggerProp()}->ID; 47 | 48 | return (int)get_post_thumbnail_id($postId); 49 | }, 50 | ] 51 | ); 52 | 53 | parent::__construct($args); 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/FeaturedImageUrl.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 6.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_featured_image_url', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s featured image url', 'notification'), $postTypeName), 42 | 'description' => __('https://example.com/wp-content/2019/01/image.jpg', 'notification'), 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return wp_get_attachment_image_url( 47 | get_post_thumbnail_id($trigger->{$this->getTriggerProp()}->ID), 48 | 'full' 49 | ); 50 | }, 51 | ] 52 | ); 53 | 54 | parent::__construct($args); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostContent.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_content', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s content', 'notification'), $postTypeName), 42 | 'description' => __( 43 | 'Welcome to WordPress. This is your first post. Edit or delete it, then start writing!', 44 | 'notification' 45 | ), 46 | 'example' => true, 47 | 'group' => $postTypeName, 48 | 'resolver' => function ($trigger) { 49 | return apply_filters('the_content', $trigger->{$this->getTriggerProp()}->post_content); 50 | }, 51 | ] 52 | ); 53 | 54 | parent::__construct($args); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostContentHtml.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.2.4 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_content_html', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s content HTML', 'notification'), $postTypeName), 42 | 'description' => __( 43 | 'Welcome to WordPress. This is your first post. Edit or delete it, then start writing!', 44 | 'notification' 45 | ), 46 | 'example' => true, 47 | 'group' => $postTypeName, 48 | 'resolver' => function ($trigger) { 49 | return apply_filters('the_content', $trigger->{$this->getTriggerProp()}->post_content); 50 | }, 51 | ] 52 | ); 53 | 54 | parent::__construct($args); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostExcerpt.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_excerpt', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s excerpt', 'notification'), $postTypeName), 42 | 'description' => __('Welcome to WordPress...', 'notification'), 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return get_the_excerpt($trigger->{$this->getTriggerProp()}); 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostID.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_ID', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s ID', 'notification'), $postTypeName), 42 | 'description' => '35', 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return $trigger->{$this->getTriggerProp()}->ID; 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostPermalink.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_permalink', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s permalink', 'notification'), $postTypeName), 42 | 'description' => __('https://example.com/hello-world/', 'notification'), 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return get_permalink($trigger->{$this->getTriggerProp()}->ID); 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostSlug.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_slug', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s slug', 'notification'), $postTypeName), 42 | 'description' => __('hello-world', 'notification'), 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return $trigger->{$this->getTriggerProp()}->post_name; 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostStatus.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_status', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s status', 'notification'), $postTypeName), 42 | 'description' => 'publish', 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return get_post_status($trigger->{$this->getTriggerProp()}->ID); 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostTitle.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_title', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s title', 'notification'), $postTypeName), 42 | 'description' => __('Hello World', 'notification'), 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return html_entity_decode(get_the_title($trigger->{$this->getTriggerProp()})); 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/PostType.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'post_type', 38 | 'name' => __('Post Type', 'notification'), 39 | 'description' => 'post', 40 | 'example' => true, 41 | 'group' => WpObjectHelper::getPostTypeName($this->getTriggerProp()), 42 | 'resolver' => static function ($trigger) { 43 | return $trigger->postType; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Post/ThumbnailUrl.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 6.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'post'); 33 | 34 | $postTypeName = WpObjectHelper::getPostTypeName($params['post_type'] ?? 'post'); 35 | 36 | $args = wp_parse_args( 37 | $params, 38 | [ 39 | 'slug' => sprintf('%s_thumbnail_url', $params['post_type'] ?? 'post'), 40 | // translators: singular post name. 41 | 'name' => sprintf(__('%s thumbnail url', 'notification'), $postTypeName), 42 | 'description' => __('https://example.com/wp-content/2019/01/image.jpg', 'notification'), 43 | 'example' => true, 44 | 'group' => $postTypeName, 45 | 'resolver' => function ($trigger) { 46 | return wp_get_attachment_image_url(get_post_thumbnail_id($trigger->{$this->getTriggerProp()}->ID)); 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/StringTag.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.2.2 28 | */ 29 | public function __construct($params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'taxonomy'); 32 | 33 | $args = wp_parse_args( 34 | $params, 35 | [ 36 | 'slug' => sprintf('%s_name', $params['tag_name'] ?? 'taxonomy'), 37 | 'name' => __('Taxonomy name', 'notification'), 38 | 'description' => __('Hello World', 'notification'), 39 | 'example' => true, 40 | 'group' => __('Taxonomy', 'notification'), 41 | 'resolver' => function ($trigger) { 42 | 43 | return $trigger->{$this->getTriggerProp()}->labels->singular_name ?? ''; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Taxonomy/TaxonomySlug.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.2.2 28 | */ 29 | public function __construct($params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'taxonomy'); 32 | 33 | $args = wp_parse_args( 34 | $params, 35 | [ 36 | 'slug' => sprintf('%s_slug', $params['tag_name'] ?? 'taxonomy'), 37 | 'name' => __('Taxonomy slug', 'notification'), 38 | 'description' => __('hello-world', 'notification'), 39 | 'example' => true, 40 | 'group' => __('Taxonomy', 'notification'), 41 | 'resolver' => function ($trigger) { 42 | return $trigger->{$this->getTriggerProp()}->name ?? ''; 43 | }, 44 | ] 45 | ); 46 | 47 | parent::__construct($args); 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Taxonomy/TermDescription.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.2.2 28 | */ 29 | public function __construct($params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'term'); 32 | 33 | $args = wp_parse_args( 34 | [ 35 | 'slug' => sprintf('%s_description', $this->getTriggerProp()), 36 | 'name' => __('Term description', 'notification'), 37 | 'description' => 'Lorem ipsum sit dolor amet', 38 | 'example' => true, 39 | 'group' => __('Term', 'notification'), 40 | 'resolver' => function ($trigger) { 41 | return $trigger->{$this->getTriggerProp()}->description; 42 | }, 43 | ] 44 | ); 45 | 46 | parent::__construct($args); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Taxonomy/TermID.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.2.2 28 | */ 29 | public function __construct($params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'term'); 32 | 33 | $args = wp_parse_args( 34 | [ 35 | 'slug' => sprintf('%s_ID', $this->getTriggerProp()), 36 | 'name' => __('Term ID', 'notification'), 37 | 'description' => '35', 38 | 'example' => true, 39 | 'group' => __('Term', 'notification'), 40 | 'resolver' => function ($trigger) { 41 | return $trigger->{$this->getTriggerProp()}->term_id; 42 | }, 43 | ] 44 | ); 45 | 46 | parent::__construct($args); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Taxonomy/TermName.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.2.2 28 | */ 29 | public function __construct($params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'term'); 32 | 33 | $args = wp_parse_args( 34 | [ 35 | 'slug' => sprintf('%s_name', $this->getTriggerProp()), 36 | 'name' => __('Term name', 'notification'), 37 | 'description' => 'Nature', 38 | 'example' => true, 39 | 'group' => __('Term', 'notification'), 40 | 'resolver' => function ($trigger) { 41 | return $trigger->{$this->getTriggerProp()}->name; 42 | }, 43 | ] 44 | ); 45 | 46 | parent::__construct($args); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Taxonomy/TermPermalink.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.2.2 28 | */ 29 | public function __construct($params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'term'); 32 | 33 | $args = wp_parse_args( 34 | [ 35 | 'slug' => sprintf('%s_link', $this->getTriggerProp()), 36 | 'name' => __('Term link', 'notification'), 37 | 'description' => 'http://example.com/category/nature', 38 | 'example' => true, 39 | 'group' => __('Term', 'notification'), 40 | 'resolver' => static function ($trigger) { 41 | // phpcs:ignore Squiz.NamingConventions.ValidVariableName.MemberNotCamelCaps 42 | return $trigger->term_permalink; 43 | }, 44 | ] 45 | ); 46 | 47 | parent::__construct($args); 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/Taxonomy/TermSlug.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.2.2 28 | */ 29 | public function __construct($params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'term'); 32 | 33 | $args = wp_parse_args( 34 | [ 35 | 'slug' => sprintf('%s_slug', $this->getTriggerProp()), 36 | 'name' => __('Term slug', 'notification'), 37 | 'description' => 'nature', 38 | 'example' => true, 39 | 'group' => __('Term', 'notification'), 40 | 'resolver' => function ($trigger) { 41 | return $trigger->{$this->getTriggerProp()}->slug; 42 | }, 43 | ] 44 | ); 45 | 46 | parent::__construct($args); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/UrlTag.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 29 | * @since 6.3.0 30 | */ 31 | public function __construct($params = []) 32 | { 33 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 34 | 35 | $args = wp_parse_args( 36 | $params, 37 | [ 38 | 'slug' => 'user_avatar', 39 | 'name' => __('User avatar', 'notification'), 40 | 'description' => __('HTML img tag with avatar', 'notification'), 41 | 'example' => true, 42 | 'group' => __('User', 'notification'), 43 | 'resolver' => function ($trigger) { 44 | if (isset($trigger->{$this->getTriggerProp()}->user_email)) { 45 | return get_avatar($trigger->{$this->getTriggerProp()}->user_email); 46 | } 47 | 48 | return ''; 49 | }, 50 | ] 51 | ); 52 | 53 | parent::__construct($args); 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/AvatarUrl.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 27 | * @since 5.0.0 28 | */ 29 | public function __construct(array $params = []) 30 | { 31 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 32 | 33 | $args = wp_parse_args( 34 | $params, 35 | [ 36 | 'slug' => 'user_avatar_url', 37 | 'name' => __('User avatar url', 'notification'), 38 | 'description' => __( 39 | 'http://0.gravatar.com/avatar/320eab812ab24ef3dbaa2e6dc6e024e0?s=96&d=mm&r=g', 40 | 'notification' 41 | ), 42 | 'example' => true, 43 | 'group' => __('User', 'notification'), 44 | 'resolver' => function ($trigger) { 45 | if (isset($trigger->{$this->getTriggerProp()}->user_email)) { 46 | return get_avatar_url($trigger->{$this->getTriggerProp()}->user_email); 47 | } 48 | 49 | return ''; 50 | }, 51 | ] 52 | ); 53 | 54 | parent::__construct($args); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserBio.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_bio', 38 | 'name' => __('User bio', 'notification'), 39 | 'description' => __( 40 | 'Developer based in Ontario, Canada', 41 | 'notification' 42 | ), 43 | 'example' => true, 44 | 'group' => __('User', 'notification'), 45 | 'resolver' => function ($trigger) { 46 | return $trigger->{$this->getTriggerProp()}->description; 47 | }, 48 | ] 49 | ); 50 | 51 | parent::__construct($args); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserDisplayName.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_display_name', 38 | 'name' => __('User display name', 'notification'), 39 | 'description' => __('John - fast finegrs - Doe', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->display_name; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserEmail.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_email', 38 | 'name' => __('User email', 'notification'), 39 | 'description' => __('john.doe@example.com', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->user_email; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserFirstName.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_first_name', 38 | 'name' => __('User first name', 'notification'), 39 | 'description' => __('John', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->first_name; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserID.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_ID', 38 | 'name' => __('User ID', 'notification'), 39 | 'description' => '25', 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->ID; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserLastName.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_last_name', 38 | 'name' => __('User last name', 'notification'), 39 | 'description' => __('Doe', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->last_name; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserLogin.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_login', 38 | 'name' => __('User login', 'notification'), 39 | 'description' => __('johndoe', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->user_login; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserNicename.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_nicename', 38 | 'name' => __('User nicename', 'notification'), 39 | 'description' => __('Johhnie', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->user_nicename; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserNickname.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_nickname', 38 | 'name' => __('User nickname', 'notification'), 39 | 'description' => __('jonny69', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function ($trigger) { 43 | return $trigger->{$this->getTriggerProp()}->nickname; 44 | }, 45 | ] 46 | ); 47 | 48 | parent::__construct($args); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Repository/MergeTag/User/UserRole.php: -------------------------------------------------------------------------------- 1 | $params merge tag configuration params. 28 | * @since 5.0.0 29 | */ 30 | public function __construct($params = []) 31 | { 32 | $this->setTriggerProp($params['property_name'] ?? 'user_object'); 33 | 34 | $args = wp_parse_args( 35 | $params, 36 | [ 37 | 'slug' => 'user_role', 38 | 'name' => __('User role', 'notification'), 39 | 'description' => __('Subscriber', 'notification'), 40 | 'example' => true, 41 | 'group' => __('User', 'notification'), 42 | 'resolver' => function () { 43 | $roles = array_map( 44 | static function ($role) { 45 | $roleObject = get_role($role); 46 | return translate_user_role(ucfirst($roleObject->name)); 47 | }, 48 | $this->trigger->{$this->getTriggerProp()}->roles 49 | ); 50 | 51 | return implode(', ', $roles); 52 | }, 53 | ] 54 | ); 55 | 56 | parent::__construct($args); 57 | } 58 | } 59 | -------------------------------------------------------------------------------- /src/Repository/RecipientRepository.php: -------------------------------------------------------------------------------- 1 | 25 | */ 26 | public static $webhookRecipientTypes = [ 27 | 'post' => 'POST', 28 | 'get' => 'GET', 29 | 'put' => 'PUT', 30 | 'delete' => 'DELETE', 31 | 'patch' => 'PATCH', 32 | ]; 33 | 34 | /** 35 | * @return void 36 | */ 37 | public static function register() 38 | { 39 | Register::recipient('email', new Recipient\Email()); 40 | Register::recipient('email', new Recipient\Administrator()); 41 | Register::recipient('email', new Recipient\User()); 42 | Register::recipient('email', new Recipient\UserID()); 43 | Register::recipient('email', new Recipient\Role()); 44 | 45 | if (! apply_filters('notification/compat/webhook/register', true)) { 46 | return; 47 | } 48 | 49 | foreach (self::$webhookRecipientTypes as $type => $name) { 50 | $recipient = new Webhook($type, $name); 51 | 52 | Register::recipient('webhook', $recipient); 53 | Register::recipient('webhook_json', $recipient); 54 | } 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /src/Repository/Resolver/Basic.php: -------------------------------------------------------------------------------- 1 | $match Match array. 41 | * @param \BracketSpace\Notification\Interfaces\Triggerable $trigger Trigger object. 42 | * @return mixed Resolved value 43 | */ 44 | public function resolveMergeTag($match, Triggerable $trigger) 45 | { 46 | $mergeTags = $trigger->getMergeTags('all', true); 47 | $tagSlug = trim(str_replace(['{', '}'], '', $match[0])); 48 | 49 | if (!isset($mergeTags[$tagSlug])) { 50 | return $match[0]; 51 | } 52 | 53 | return apply_filters( 54 | 'notification/merge_tag/value/resolved', 55 | $mergeTags[$tagSlug]->resolve(), 56 | $mergeTags[$tagSlug] 57 | ); 58 | } 59 | } 60 | -------------------------------------------------------------------------------- /src/Repository/ResolverRepository.php: -------------------------------------------------------------------------------- 1 | addAction('add_attachment', 10, 1); 29 | $this->setDescription(__('Fires when new attachment is added', 'notification')); 30 | } 31 | 32 | /** 33 | * Sets trigger's context 34 | * 35 | * @param int $attachmentId Attachment Post ID. 36 | * @return void 37 | */ 38 | public function context($attachmentId) 39 | { 40 | $this->attachment = get_post($attachmentId); 41 | if (!$this->attachment instanceof \WP_Post) { 42 | return; 43 | } 44 | $this->userId = (int)$this->attachment->post_author; 45 | $user = get_userdata($this->userId); 46 | 47 | if (!$user instanceof \WP_User) { 48 | return; 49 | } 50 | $this->userObject = $user; 51 | 52 | $this->attachmentCreationDate = strtotime($this->attachment->post_date_gmt); 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/Repository/Trigger/Plugin/Activated.php: -------------------------------------------------------------------------------- 1 | addAction('activated_plugin', 1000); 35 | 36 | $this->setGroup(__('Plugin', 'notification')); 37 | 38 | $this->setDescription(__('Fires when plugin is activated', 'notification')); 39 | } 40 | 41 | /** 42 | * Trigger action 43 | * 44 | * @param string $pluginRelPath Plugin path. 45 | * @return void 46 | */ 47 | public function context($pluginRelPath) 48 | { 49 | $pluginDir = WP_PLUGIN_DIR . DIRECTORY_SEPARATOR . $pluginRelPath; 50 | $this->plugin = get_plugin_data($pluginDir, false); 51 | $this->pluginActivationDateTime = (string)time(); 52 | } 53 | 54 | /** 55 | * Registers attached merge tags 56 | * 57 | * @return void 58 | */ 59 | public function mergeTags() 60 | { 61 | parent::mergeTags(); 62 | 63 | $this->addMergeTag( 64 | new MergeTag\DateTime\DateTime( 65 | [ 66 | 'slug' => 'plugin_activation_date_time', 67 | 'name' => __('Plugin activation date and time', 'notification'), 68 | ] 69 | ) 70 | ); 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /src/Repository/Trigger/Plugin/Deactivated.php: -------------------------------------------------------------------------------- 1 | addAction('deactivated_plugin', 1000); 35 | 36 | $this->setGroup(__('Plugin', 'notification')); 37 | 38 | $this->setDescription(__('Fires when plugin is deactivated', 'notification')); 39 | } 40 | 41 | /** 42 | * Trigger action 43 | * 44 | * @param string $pluginRelPath Plugin path. 45 | * @return void 46 | */ 47 | public function context($pluginRelPath) 48 | { 49 | $pluginDir = WP_PLUGIN_DIR . DIRECTORY_SEPARATOR . $pluginRelPath; 50 | $this->plugin = get_plugin_data($pluginDir, false); 51 | $this->pluginDeactivationDateTime = (string)time(); 52 | } 53 | 54 | /** 55 | * Registers attached merge tags 56 | * 57 | * @return void 58 | */ 59 | public function mergeTags() 60 | { 61 | parent::mergeTags(); 62 | 63 | $this->addMergeTag( 64 | new MergeTag\DateTime\DateTime( 65 | [ 66 | 'slug' => 'plugin_deactivation_date_time', 67 | 'name' => __('Plugin deactivation date and time', 'notification'), 68 | ] 69 | ) 70 | ); 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /src/Repository/Trigger/Plugin/Removed.php: -------------------------------------------------------------------------------- 1 | addAction('delete_plugin', 1000); 35 | 36 | $this->setGroup(__('Plugin', 'notification')); 37 | 38 | $this->setDescription(__('Fires when plugin is deleted', 'notification')); 39 | } 40 | 41 | /** 42 | * Trigger action. 43 | * 44 | * @param string $pluginRelPath Plugin path. 45 | * @return mixed void or false if no notifications should be sent. 46 | */ 47 | public function context($pluginRelPath) 48 | { 49 | $pluginDir = WP_PLUGIN_DIR . DIRECTORY_SEPARATOR . $pluginRelPath; 50 | $this->plugin = get_plugin_data($pluginDir, false); 51 | $this->pluginDeletionDateTime = (string)time(); 52 | } 53 | 54 | /** 55 | * Registers attached merge tags. 56 | * 57 | * @return void. 58 | */ 59 | public function mergeTags() 60 | { 61 | parent::mergeTags(); 62 | 63 | $this->addMergeTag( 64 | new MergeTag\DateTime\DateTime( 65 | [ 66 | 'slug' => 'plugin_deletion_date_time', 67 | 'name' => __('Plugin deletion date and time', 'notification'), 68 | ] 69 | ) 70 | ); 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /src/Repository/Trigger/Privacy/DataEraseRequest.php: -------------------------------------------------------------------------------- 1 | addAction('user_request_action_confirmed', 10, 1); 26 | 27 | $this->setDescription(__('Fires when user requests privacy data erase', 'notification')); 28 | } 29 | 30 | /** 31 | * Sets trigger's context 32 | * 33 | * @param int $requestId Request id. 34 | */ 35 | public function context($requestId) 36 | { 37 | $this->request = wp_get_user_request($requestId); 38 | 39 | $user = get_userdata($this->request->user_id); 40 | 41 | if (!$user instanceof \WP_User) { 42 | return; 43 | } 44 | 45 | $this->userObject = $user; 46 | $this->dataOperationTime = (string)time(); 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /src/Repository/Trigger/Privacy/DataErased.php: -------------------------------------------------------------------------------- 1 | addAction('wp_privacy_personal_data_erased', 10, 1); 26 | 27 | $this->setDescription(__('Fires when user personal data is erased', 'notification')); 28 | } 29 | 30 | /** 31 | * Sets trigger's context 32 | * 33 | * @param int $requestId Request id. 34 | */ 35 | public function context($requestId) 36 | { 37 | $this->request = wp_get_user_request($requestId); 38 | $user = get_userdata($this->request->user_id); 39 | 40 | if (!$user instanceof \WP_User) { 41 | return; 42 | } 43 | 44 | $this->userObject = $user; 45 | $this->dataOperationTime = (string)time(); 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /src/Repository/Trigger/Privacy/DataExportRequest.php: -------------------------------------------------------------------------------- 1 | addAction('user_request_action_confirmed', 10, 1); 29 | 30 | $this->setDescription(__('Fires when user requests privacy data export', 'notification')); 31 | } 32 | 33 | /** 34 | * Sets trigger's context 35 | * 36 | * @param int $requestId Request id. 37 | */ 38 | public function context($requestId) 39 | { 40 | $this->request = wp_get_user_request($requestId); 41 | $user = get_userdata($this->request->user_id); 42 | 43 | if (!$user instanceof \WP_User) { 44 | return; 45 | } 46 | 47 | $this->userObject = $user; 48 | $this->dataOperationTime = (string)time(); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /src/Store/Carrier.php: -------------------------------------------------------------------------------- 1 | */ 22 | use Storage; 23 | } 24 | -------------------------------------------------------------------------------- /src/Store/GlobalMergeTag.php: -------------------------------------------------------------------------------- 1 | */ 22 | use Storage; 23 | } 24 | -------------------------------------------------------------------------------- /src/Store/Notification.php: -------------------------------------------------------------------------------- 1 | */ 26 | use Storage; 27 | 28 | /** 29 | * Gets the Notifications with specific Trigger 30 | * 31 | * @param string $triggerSlug Trigger slug. 32 | * @return array 33 | * @since 6.0.0 34 | * @since 8.0.0 Is static method 35 | */ 36 | public static function withTrigger($triggerSlug) 37 | { 38 | return array_filter( 39 | static::all(), 40 | function ($notification) use ($triggerSlug) { 41 | return !empty($notification->getTrigger()) && $notification->getTrigger()->getSlug() === $triggerSlug; 42 | } 43 | ); 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /src/Store/Resolver.php: -------------------------------------------------------------------------------- 1 | */ 22 | use Storage; 23 | 24 | /** 25 | * Gets all Resolvers sorted by priority. 26 | * 27 | * @return array 28 | * @since 8.0.0 29 | */ 30 | public static function sorted(): array 31 | { 32 | $resolvers = static::all(); 33 | 34 | usort( 35 | $resolvers, 36 | static function ($a, $b) { 37 | if ($a->getPriority() === $b->getPriority()) { 38 | return 0; 39 | } 40 | 41 | return $a->getPriority() < $b->getPriority() 42 | ? -1 43 | : 1; 44 | } 45 | ); 46 | 47 | return $resolvers; 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /src/Store/Trigger.php: -------------------------------------------------------------------------------- 1 | */ 22 | use Storage; 23 | 24 | /** 25 | * Gets all Triggers grouped. 26 | * 27 | * @return array> 28 | * @since 8.0.0 29 | */ 30 | public static function grouped(): array 31 | { 32 | $groups = []; 33 | 34 | foreach (static::all() as $trigger) { 35 | if (!isset($groups[$trigger->getGroup()])) { 36 | $groups[(string)$trigger->getGroup()] = []; 37 | } 38 | 39 | $groups[(string)$trigger->getGroup()][$trigger->getSlug()] = $trigger; 40 | } 41 | 42 | return $groups; 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /src/Traits/ClassUtils.php: -------------------------------------------------------------------------------- 1 | getShortName(); 26 | } 27 | 28 | /** 29 | * Get nice class names with title case and spaces 30 | * 31 | * @return string 32 | */ 33 | public function getNiceClassName() 34 | { 35 | return (string)preg_replace( 36 | '/(.)(?=[A-Z])/u', 37 | '$1 ', 38 | $this->getShortClassName() 39 | ); 40 | } 41 | 42 | /** 43 | * Get class slug with dash separators 44 | * 45 | * @return string 46 | */ 47 | public function getClassSlug() 48 | { 49 | return strtolower( 50 | (string)preg_replace( 51 | '/(.)(?=[A-Z])/u', 52 | '$1-', 53 | $this->getShortClassName() 54 | ) 55 | ); 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /src/Traits/HasDescription.php: -------------------------------------------------------------------------------- 1 | description; 33 | } 34 | 35 | /** 36 | * Sets description 37 | * 38 | * @param string $description Description. 39 | * @return $this 40 | */ 41 | public function setDescription(string $description) 42 | { 43 | $this->description = $description; 44 | 45 | return $this; 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /src/Traits/HasGroup.php: -------------------------------------------------------------------------------- 1 | group; 33 | } 34 | 35 | /** 36 | * Sets group 37 | * 38 | * @param string $group Group name. 39 | * @return $this 40 | */ 41 | public function setGroup(string $group) 42 | { 43 | $this->group = $group; 44 | 45 | return $this; 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /src/Traits/HasName.php: -------------------------------------------------------------------------------- 1 | name === null) { 36 | return $this->getNiceClassName(); 37 | } 38 | 39 | return $this->name; 40 | } 41 | 42 | /** 43 | * Sets name 44 | * 45 | * @param string $name Name. 46 | * @return $this 47 | */ 48 | public function setName(string $name) 49 | { 50 | $this->name = $name; 51 | 52 | return $this; 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/Traits/HasReturnField.php: -------------------------------------------------------------------------------- 1 | returnField ?? $this->getDefaultReturnField(); 45 | } 46 | 47 | /** 48 | * Sets return field name. 49 | * 50 | * @param string $returnField Return field name. 51 | * @return $this 52 | */ 53 | public function setReturnField(string $returnField) 54 | { 55 | $availableReturnFields = ['ID', 'user_email']; 56 | 57 | if (!in_array($returnField, $availableReturnFields, true)) { 58 | ErrorHandler::error(sprintf('Recipient return field "%s" is not supported.', $returnField)); 59 | 60 | $returnField = $this->getDefaultReturnField(); 61 | } 62 | 63 | $this->returnField = $returnField; 64 | 65 | return $this; 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /src/Traits/HasSlug.php: -------------------------------------------------------------------------------- 1 | slug === null) { 36 | return $this->getClassSlug(); 37 | } 38 | 39 | return $this->slug; 40 | } 41 | 42 | /** 43 | * Sets slug 44 | * 45 | * @param string $slug Slug. 46 | * @return $this 47 | */ 48 | public function setSlug(string $slug) 49 | { 50 | $this->slug = $slug; 51 | 52 | return $this; 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Button.php: -------------------------------------------------------------------------------- 1 | %s', 28 | esc_url_raw($field->addon('url')), 29 | esc_html($field->addon('label')) 30 | ); 31 | } 32 | 33 | /** 34 | * Sanitize button URL 35 | * 36 | * @param string $value URL. 37 | * @return string Sanitized URL 38 | */ 39 | public function sanitize($value) 40 | { 41 | return esc_url_raw($value); 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Checkbox.php: -------------------------------------------------------------------------------- 1 | value(), ['true', true], true); 28 | 29 | printf( 30 | '', 31 | esc_attr($field->inputId()), 32 | esc_attr($field->inputName()), 33 | checked( 34 | $checked, 35 | true, 36 | false 37 | ), 38 | wp_kses_data($field->addon('label')) 39 | ); 40 | } 41 | 42 | /** 43 | * Sanitize checkbox value 44 | * Allows only for empty string and 'true' 45 | * 46 | * @param string $value saved value. 47 | * @return string empty string or 'true' 48 | */ 49 | public function sanitize($value) 50 | { 51 | return ($value !== 'true') ? '' : $value; 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Editor.php: -------------------------------------------------------------------------------- 1 | addon('wpautop') 27 | ? $field->addon('wpautop') 28 | : true; 29 | $mediaButtons = $field->addon('media_buttons') 30 | ? $field->addon('media_buttons') 31 | : false; 32 | $textareaRows = $field->addon('textarea_rows') 33 | ? $field->addon('textarea_rows') 34 | : 10; 35 | $teeny = $field->addon('teeny') 36 | ? $field->addon('teeny') 37 | : false; 38 | 39 | $settings = [ 40 | 'textarea_name' => $field->inputName(), 41 | 'editor_css' => null, 42 | 'wpautop' => $wpautop, 43 | 'media_buttons' => $mediaButtons, 44 | 'textarea_rows' => $textareaRows, 45 | 'teeny' => $teeny, 46 | ]; 47 | 48 | wp_editor($field->value(), $field->inputId(), $settings); 49 | } 50 | 51 | /** 52 | * Sanitize input value 53 | * 54 | * @param string $value Saved value. 55 | * @return string Sanitized content 56 | */ 57 | public function sanitize($value) 58 | { 59 | return wp_kses_post($value); 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Message.php: -------------------------------------------------------------------------------- 1 | addon('code')) { 27 | echo '
';
28 | 		}
29 | 
30 | 		$message = $field->addon('message');
31 | 
32 | 		echo wp_kses_post(
33 | 			is_callable($message)
34 | 				? $message()
35 | 				: $message
36 | 		);
37 | 
38 | 		if (!$field->addon('code')) {
39 | 			return;
40 | 		}
41 | 
42 | 		echo '
'; 43 | } 44 | 45 | /** 46 | * Sanitize input value 47 | * 48 | * @param string $value Saved value. 49 | * @return string Sanitized text 50 | */ 51 | public function sanitize($value) 52 | { 53 | return $value; 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Number.php: -------------------------------------------------------------------------------- 1 | ', 30 | esc_attr($field->inputId()), 31 | esc_attr($field->inputName()), 32 | esc_attr($field->value()), 33 | esc_attr($field->addon('min')), 34 | esc_attr($field->addon('max')), 35 | esc_attr($field->addon('step')) 36 | ); 37 | } 38 | 39 | /** 40 | * Sanitize input value 41 | * 42 | * @param string $value saved value. 43 | * @return int|float sanitized number 44 | */ 45 | public function sanitize($value) 46 | { 47 | if (!is_numeric($value)) { 48 | return 0; 49 | } 50 | 51 | return floatval($value); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Range.php: -------------------------------------------------------------------------------- 1 | ', 30 | esc_attr($field->inputId()), 31 | esc_attr($field->inputName()), 32 | esc_attr($field->value()), 33 | esc_attr($field->addon('min')), 34 | esc_attr($field->addon('max')), 35 | esc_attr($field->addon('step')) 36 | ); 37 | } 38 | 39 | /** 40 | * Sanitize input value 41 | * 42 | * @param mixed $value Saved value. 43 | * @return float Sanitized number 44 | */ 45 | public function sanitize($value) 46 | { 47 | if (!is_numeric($value)) { 48 | return 0; 49 | } 50 | 51 | return floatval($value); 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Text.php: -------------------------------------------------------------------------------- 1 | ', 28 | esc_attr($field->inputId()), 29 | esc_attr($field->inputName()), 30 | esc_attr($field->value()) 31 | ); 32 | } 33 | 34 | /** 35 | * Sanitize input value 36 | * 37 | * @param string $value Saved value. 38 | * @return string Sanitized text 39 | */ 40 | public function sanitize($value) 41 | { 42 | return sanitize_text_field($value); 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /src/Utils/Settings/CoreFields/Url.php: -------------------------------------------------------------------------------- 1 | ', 28 | esc_attr($field->inputId()), 29 | esc_attr($field->inputName()), 30 | esc_attr($field->value()) 31 | ); 32 | } 33 | 34 | /** 35 | * Sanitize input value 36 | * 37 | * @param string $value saved value. 38 | * @return string sanitized url 39 | */ 40 | public function sanitize($value) 41 | { 42 | return esc_url_raw($value); 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /src/Utils/Settings/Fields/ErrorLog.php: -------------------------------------------------------------------------------- 1 | get_option('date_format') . ' ' . get_option('time_format'), 41 | 'logs' => $debug->getLogs( 42 | $page, 43 | ['error', 'warning'] 44 | ), 45 | ] 46 | ); 47 | 48 | Templates::render( 49 | 'debug/pagination', 50 | [ 51 | 'query_arg' => 'error_log_page', 52 | 'total' => $debug->getLogsCount('pages'), 53 | 'current' => $page, 54 | ] 55 | ); 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /src/Utils/Settings/Fields/Export.php: -------------------------------------------------------------------------------- 1 | NotificationDatabaseService::getAll(), 39 | 'download_link' => $downloadLink, 40 | ] 41 | ); 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /src/Utils/Settings/Fields/Import.php: -------------------------------------------------------------------------------- 1 |