Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
97.83% covered (success)
97.83%
45 / 46
90.00% covered (success)
90.00%
9 / 10
CRAP
0.00% covered (danger)
0.00%
0 / 1
Feedback_Author
97.83% covered (success)
97.83%
45 / 46
90.00% covered (success)
90.00%
9 / 10
20
0.00% covered (danger)
0.00%
0 / 1
 __construct
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
1 / 1
1
 from_submission
100.00% covered (success)
100.00%
9 / 9
100.00% covered (success)
100.00%
1 / 1
3
 get_computed_author_info
100.00% covered (success)
100.00%
11 / 11
100.00% covered (success)
100.00%
1 / 1
4
 get_display_name
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
2
 get_avatar_url
85.71% covered (warning)
85.71%
6 / 7
0.00% covered (danger)
0.00%
0 / 1
3.03
 get_name
100.00% covered (success)
100.00%
8 / 8
100.00% covered (success)
100.00%
1 / 1
3
 get_email
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_url
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_first_name
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get_last_name
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
1<?php
2/**
3 * Feedback class.
4 *
5 * @package automattic/jetpack-forms
6 */
7
8namespace Automattic\Jetpack\Forms\ContactForm;
9
10/**
11 * Class Feedback_Author
12 *
13 * Represents the author of a feedback entry, including their name, email, and URL.
14 */
15class Feedback_Author {
16
17    /**
18     * The name of the author.
19     *
20     * @var string
21     */
22    private $name;
23
24    /**
25     * The email of the author.
26     *
27     * @var string
28     */
29    private $email;
30
31    /**
32     * The url of the author.
33     *
34     * @var string
35     */
36    private $url;
37
38    /**
39     * The first name of the author.
40     *
41     * @var string
42     */
43    private $first_name = '';
44
45    /**
46     * The last name of the author.
47     *
48     * @var string
49     */
50    private $last_name = '';
51
52    /**
53     * Constructor for Feedback_Author.
54     *
55     * @param string $name  The name of the author.
56     * @param string $email The email of the author.
57     * @param string $url   The URL of the author.
58     * @param string $first_name The first name of the author.
59     * @param string $last_name  The last name of the author.
60     */
61    public function __construct( $name = '', $email = '', $url = '', $first_name = '', $last_name = '' ) {
62        $this->name       = $name;
63        $this->email      = $email;
64        $this->url        = $url;
65        $this->first_name = $first_name;
66        $this->last_name  = $last_name;
67    }
68
69    /**
70     * Create a Feedback_Author instance from the submission data.
71     *
72     * @param array        $post_data The post data from the form submission.
73     * @param Contact_Form $form      The form object.
74     * @return Feedback_Author The Feedback_Author instance.
75     */
76    public static function from_submission( $post_data, $form ) {
77        $first = isset( $post_data['first-name'] ) ? sanitize_text_field( wp_unslash( $post_data['first-name'] ) ) : '';
78        $last  = isset( $post_data['last-name'] ) ? sanitize_text_field( wp_unslash( $post_data['last-name'] ) ) : '';
79        return new self(
80            self::get_computed_author_info( $post_data, 'name', 'pre_comment_author_name', $form ),
81            self::get_computed_author_info( $post_data, 'email', 'pre_comment_author_email', $form ),
82            self::get_computed_author_info( $post_data, 'url', 'pre_comment_author_url', $form ),
83            $first,
84            $last
85        );
86    }
87
88    /**
89     * Gets the computed author.
90     *
91     * @param array        $post_data The post data from the form submission.
92     * @param string       $type The type of author information to retrieve (e.g., 'name', 'email', 'url').
93     * @param string       $filter Optional filter to apply to the value.
94     * @param Contact_Form $form The form object.
95     *
96     * @return string Filter value for the author information.
97     */
98    private static function get_computed_author_info( $post_data, $type, $filter, $form ) {
99        $field_ids = $form->get_field_ids();
100        if ( isset( $field_ids[ $type ] ) ) {
101            $key   = $field_ids[ $type ];
102            $value = isset( $post_data[ $key ] ) ? sanitize_text_field( wp_unslash( $post_data[ $key ] ) ) : '';
103            if ( is_string( $value ) ) {
104                return Contact_Form_Plugin::strip_tags(
105                    stripslashes(
106                        /**
107                         *
108                         * Listed to help search find the filters.
109                         * apply_filters( ''pre_comment_author_name', $value )
110                         * apply_filters( ''pre_comment_author_email', $value )
111                         * apply_filters( ''pre_comment_author_url', $value )
112                        */
113                        apply_filters( $filter, addslashes( $value ) )
114                    )
115                );
116
117            }
118        }
119        return '';
120    }
121
122    /**
123     * Get the display name of the author.
124     *
125     * If the name is not set, it will return the email.
126     *
127     * @return string The display name of the author.
128     */
129    public function get_display_name(): string {
130        $name = $this->get_name();
131        return empty( $name ) ? $this->email : $name;
132    }
133
134    /**
135     * Get the avatar URL of the author.
136     *
137     * Uses Gravatar's "initials" default so that users without a Gravatar
138     * get a colored circle with their initials — matching the dashboard.
139     *
140     * @see https://docs.gravatar.com/api/avatars/images/#default-image
141     *
142     * @return string The avatar URL of the author.
143     */
144    public function get_avatar_url(): string {
145        if ( empty( $this->email ) ) {
146            return '';
147        }
148
149        $hash = md5( strtolower( trim( $this->email ) ) );
150        $name = $this->get_name();
151
152        if ( empty( $name ) ) {
153            // Use the email prefix as a fallback for initials.
154            $name = strstr( $this->email, '@', true );
155        }
156
157        return "https://gravatar.com/avatar/{$hash}?d=initials&name=" . rawurlencode( $name ) . '&s=96';
158    }
159
160    /**
161     * Get the name of the author.
162     *
163     * @return string The name of the author.
164     */
165    public function get_name() {
166        if ( $this->first_name && $this->last_name ) {
167            $raw = trim( $this->first_name . ' ' . $this->last_name );
168            return Contact_Form_Plugin::strip_tags(
169                stripslashes(
170                    /** This filter is already documented in core/wp-includes/comment-functions.php */
171                    apply_filters( 'pre_comment_author_name', addslashes( $raw ) )
172                )
173            );
174        }
175        // This name value is filtered upstream when class is instantiated.
176        return $this->name;
177    }
178
179    /**
180     * Get the email of the author.
181     *
182     * @return string The email of the author.
183     */
184    public function get_email() {
185        return $this->email;
186    }
187
188    /**
189     * Get the URL of the author.
190     *
191     * @return string The URL of the author.
192     */
193    public function get_url() {
194        return $this->url;
195    }
196
197    /**
198     * Get the first name of the author (if provided separately).
199     *
200     * @return string
201     */
202    public function get_first_name() {
203        return $this->first_name;
204    }
205
206    /**
207     * Get the last name of the author (if provided separately).
208     *
209     * @return string
210     */
211    public function get_last_name() {
212        return $this->last_name;
213    }
214}