Pharmacy Service Review

The Pharmacy Service Review helps pharmacies understand patient experience across key touchpoints. It captures ratings on pharmacist consultation quality, staff helpfulness, wait times, prescription accuracy, and store environment. The form uses conditional logic to gather detailed feedback when issues are reported, helping pharmacy managers identify improvement opportunities and train staff effectively.

Healthcare

Try the Form

Your feedback helps us serve you better. Thank you for visiting!
Visit Details
 
 
 
Wait Time Experience
15min
15 min
060
Reasonable wait time
0/5
Staff & Service Quality
Poor Fair Good Excellent
Friendliness & courtesy*
Helpfulness & attentiveness*
Knowledge & expertise*
Clear communication
Respect for privacy
Store Environment
0/5
0/5
Overall Experience
Not at all likely
Extremely likely
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
export function pharmacyFeedbackSurvey(form: FormTs) {
// Pharmacy Service Review - Patient feedback for pharmacy visits
// Demonstrates: StarRating, Slider, MatrixQuestion, ThumbRating, EmojiRating, RadioButton, Timepicker
 
// ============================================
// HEADER
// ============================================
form.addRow(row => {
row.addTextPanel('header', {
label: 'Pharmacy Feedback',
computedValue: () => 'Your feedback helps us serve you better. Thank you for visiting!',
customStyles: {
background: 'linear-gradient(135deg, #0891b2 0%, #06b6d4 100%)',
color: 'white',
padding: '24px',
borderRadius: '12px',
textAlign: 'center'
}
});
});
 
// ============================================
// SECTION 1: Visit Details
// ============================================
const visitSection = form.addSubform('visitSection', {
title: 'Visit Details'
});
 
visitSection.addRow(row => {
row.addDatepicker('visitDate', {
label: 'Date of visit',
isRequired: true
}, '1fr');
 
row.addTimepicker('visitTime', {
label: 'Approximate time',
defaultValue: '14:00'
}, '1fr');
});
 
visitSection.addRow(row => {
row.addRadioButton('visitType', {
label: 'What was the purpose of your visit?',
options: [
{ id: 'prescription', name: 'Prescription pickup' },
{ id: 'new-rx', name: 'New prescription' },
{ id: 'consultation', name: 'Pharmacist consultation' },
{ id: 'otc', name: 'Over-the-counter purchase' },
{ id: 'vaccination', name: 'Vaccination/immunization' },
{ id: 'other', name: 'Other' }
],
orientation: 'vertical'
});
});
 
// ============================================
// SECTION 2: Wait Time Experience
// ============================================
const waitSection = form.addSubform('waitSection', {
title: 'Wait Time Experience'
});
 
waitSection.addRow(row => {
row.addSlider('waitMinutes', {
label: 'How long did you wait? (minutes)',
min: 0,
max: 60,
step: 5,
defaultValue: 15,
showValue: true,
unit: 'min'
});
});
 
waitSection.addRow(row => {
row.addTextPanel('waitContext', {
computedValue: () => {
const minutes = waitSection.slider('waitMinutes')?.value() ?? 15;
if (minutes === 0) return 'Served immediately - excellent!';
if (minutes <= 10) return 'Very quick service';
if (minutes <= 20) return 'Reasonable wait time';
if (minutes <= 30) return 'Longer than ideal';
if (minutes <= 45) return 'Extended wait';
return 'Very long wait - we apologize';
},
customStyles: () => {
const minutes = waitSection.slider('waitMinutes')?.value() ?? 15;
const baseStyle = { padding: '8px 16px', borderRadius: '6px', textAlign: 'center' };
if (minutes <= 10) return { ...baseStyle, backgroundColor: '#d1fae5', color: '#065f46' };
if (minutes <= 20) return { ...baseStyle, backgroundColor: '#e0f2fe', color: '#0369a1' };
if (minutes <= 30) return { ...baseStyle, backgroundColor: '#fef3c7', color: '#92400e' };
return { ...baseStyle, backgroundColor: '#fee2e2', color: '#991b1b' };
}
});
});
 
waitSection.addRow(row => {
row.addStarRating('waitSatisfaction', {
label: 'How satisfied were you with the wait time?',
maxStars: 5,
size: 'lg',
alignment: 'center'
});
});
 
// Long wait follow-up
waitSection.addRow(row => {
row.addTextarea('waitFeedback', {
label: 'What would have made the wait more acceptable?',
placeholder: 'e.g., better seating, status updates, text notification...',
rows: 2,
isVisible: () => {
const minutes = waitSection.slider('waitMinutes')?.value() ?? 15;
const satisfaction = waitSection.starRating('waitSatisfaction')?.value() ?? 0;
return minutes > 20 || (satisfaction > 0 && satisfaction <= 2);
}
});
});
 
// ============================================
// SECTION 3: Staff & Service Quality
// ============================================
const staffSection = form.addSubform('staffSection', {
title: 'Staff & Service Quality'
});
 
staffSection.addRow(row => {
row.addMatrixQuestion('staffRatings', {
label: 'Rate your experience with our staff:',
rows: [
{ id: 'friendly', label: 'Friendliness & courtesy', isRequired: true },
{ id: 'helpful', label: 'Helpfulness & attentiveness', isRequired: true },
{ id: 'knowledge', label: 'Knowledge & expertise', isRequired: true },
{ id: 'communication', label: 'Clear communication', isRequired: false },
{ id: 'privacy', label: 'Respect for privacy', isRequired: false }
],
columns: [
{ id: 'poor', label: 'Poor' },
{ id: 'fair', label: 'Fair' },
{ id: 'good', label: 'Good' },
{ id: 'excellent', label: 'Excellent' }
],
striped: true,
fullWidth: true
});
});
 
// ============================================
// SECTION 4: Pharmacist Consultation
// ============================================
const consultSection = form.addSubform('consultSection', {
title: 'Pharmacist Consultation',
isVisible: () => {
const visitType = visitSection.radioButton('visitType')?.value();
return visitType === 'prescription' || visitType === 'new-rx' || visitType === 'consultation';
}
});
 
consultSection.addRow(row => {
row.addThumbRating('hadConsultation', {
label: 'Did you speak with a pharmacist?',
showLabels: true,
upLabel: 'Yes',
downLabel: 'No',
size: 'lg',
alignment: 'center'
});
});
 
// Consultation details if yes
const consultDetailsSection = form.addSubform('consultDetailsSection', {
title: 'Consultation Experience',
isVisible: () => consultSection.thumbRating('hadConsultation')?.value() === 'up'
});
 
consultDetailsSection.addRow(row => {
row.addStarRating('consultQuality', {
label: 'How helpful was the pharmacist consultation?',
maxStars: 5,
size: 'lg',
alignment: 'center'
});
});
 
consultDetailsSection.addRow(row => {
row.addCheckboxList('consultTopics', {
label: 'What did you discuss?',
options: [
{ id: 'dosage', name: 'Dosage instructions' },
{ id: 'side-effects', name: 'Side effects' },
{ id: 'interactions', name: 'Drug interactions' },
{ id: 'generic', name: 'Generic alternatives' },
{ id: 'cost', name: 'Cost/insurance' },
{ id: 'otc', name: 'OTC recommendations' },
{ id: 'other', name: 'Other health questions' }
],
orientation: 'vertical'
});
});
 
consultDetailsSection.addRow(row => {
row.addThumbRating('questionsAnswered', {
label: 'Were all your questions answered?',
showLabels: true,
upLabel: 'Yes, completely',
downLabel: 'No, I still have questions',
size: 'md',
alignment: 'center'
});
});
 
consultDetailsSection.addRow(row => {
row.addTextarea('unansweredQuestions', {
label: 'What questions remain unanswered?',
placeholder: 'Please share so we can follow up...',
rows: 2,
isVisible: () => consultDetailsSection.thumbRating('questionsAnswered')?.value() === 'down'
});
});
 
// ============================================
// SECTION 5: Prescription Accuracy
// ============================================
const accuracySection = form.addSubform('accuracySection', {
title: 'Prescription Accuracy',
isVisible: () => {
const visitType = visitSection.radioButton('visitType')?.value();
return visitType === 'prescription' || visitType === 'new-rx';
}
});
 
accuracySection.addRow(row => {
row.addThumbRating('rxAccurate', {
label: 'Was your prescription filled correctly?',
showLabels: true,
upLabel: 'Yes, everything correct',
downLabel: 'No, there was an issue',
size: 'lg',
alignment: 'center'
});
});
 
// Accuracy issue follow-up
accuracySection.addRow(row => {
row.addRadioButton('accuracyIssue', {
label: 'What issue did you experience?',
options: [
{ id: 'wrong-med', name: 'Wrong medication' },
{ id: 'wrong-dose', name: 'Wrong dosage/quantity' },
{ id: 'wrong-label', name: 'Incorrect label information' },
{ id: 'missing', name: 'Medication missing from order' },
{ id: 'insurance', name: 'Insurance/billing error' },
{ id: 'other', name: 'Other issue' }
],
orientation: 'vertical',
isRequired: true,
isVisible: () => accuracySection.thumbRating('rxAccurate')?.value() === 'down'
});
});
 
accuracySection.addRow(row => {
row.addTextarea('accuracyDetails', {
label: 'Please describe the issue',
placeholder: 'Details help us prevent future errors...',
rows: 2,
isRequired: true,
isVisible: () => accuracySection.thumbRating('rxAccurate')?.value() === 'down'
});
});
 
accuracySection.addRow(row => {
row.addTextPanel('accuracyWarning', {
computedValue: () => '⚠️ We take accuracy very seriously. Our quality team will review this feedback and may contact you.',
customStyles: {
backgroundColor: '#fee2e2',
color: '#991b1b',
padding: '12px',
borderRadius: '6px',
borderLeft: '4px solid #ef4444'
},
isVisible: () => accuracySection.thumbRating('rxAccurate')?.value() === 'down'
});
});
 
// ============================================
// SECTION 6: Store Environment
// ============================================
const storeSection = form.addSubform('storeSection', {
title: 'Store Environment'
});
 
storeSection.addRow(row => {
row.addStarRating('cleanliness', {
label: 'Cleanliness',
maxStars: 5,
size: 'md',
showCounter: true
}, '1fr');
 
row.addStarRating('organization', {
label: 'Organization & ease of finding items',
maxStars: 5,
size: 'md',
showCounter: true
}, '1fr');
});
 
// ============================================
// SECTION 7: Overall Experience
// ============================================
const overallSection = form.addSubform('overallSection', {
title: 'Overall Experience',
customStyles: () => {
const mood = overallSection.emojiRating('overallMood')?.value();
if (mood === 'excellent' || mood === 'good') return { backgroundColor: '#d1fae5', padding: '16px', borderRadius: '8px' };
if (mood === 'very-bad' || mood === 'bad') return { backgroundColor: '#fee2e2', padding: '16px', borderRadius: '8px' };
return { padding: '16px', borderRadius: '8px', border: '1px solid #e2e8f0' };
}
});
 
overallSection.addRow(row => {
row.addEmojiRating('overallMood', {
label: 'How was your overall pharmacy experience?',
preset: 'satisfaction',
size: 'lg',
showLabels: true,
alignment: 'center'
});
});
 
overallSection.addRow(row => {
row.addRatingScale('recommendLikelihood', {
label: 'How likely are you to recommend our pharmacy to others?',
preset: 'nps',
showCategoryLabel: true,
showSegmentColors: true,
alignment: 'center'
});
});
 
overallSection.addSpacer();
 
overallSection.addRow(row => {
row.addTextarea('additionalComments', {
label: () => {
const mood = overallSection.emojiRating('overallMood')?.value();
if (mood === 'excellent' || mood === 'good') return 'What made your experience great?';
if (mood === 'very-bad' || mood === 'bad') return 'How can we make it right?';
return 'Any additional feedback?';
},
placeholder: 'Your feedback is valuable to us...',
rows: 3,
autoExpand: true
});
});
 
// ============================================
// SECTION 8: Summary
// ============================================
const summarySection = form.addSubform('summarySection', {
title: 'Feedback Summary',
isVisible: () => overallSection.emojiRating('overallMood')?.value() !== null
});
 
summarySection.addRow(row => {
row.addTextPanel('summary', {
computedValue: () => {
const visitType = visitSection.radioButton('visitType')?.value() || 'Visit';
const waitMinutes = waitSection.slider('waitMinutes')?.value() ?? 0;
const waitSat = waitSection.starRating('waitSatisfaction')?.value() ?? 0;
const mood = overallSection.emojiRating('overallMood')?.value();
const nps = overallSection.ratingScale('recommendLikelihood')?.value() ?? 0;
const rxAccurate = accuracySection.thumbRating('rxAccurate')?.value();
const consultQuality = consultDetailsSection.starRating('consultQuality')?.value() ?? 0;
 
const visitLabels: Record<string, string> = {
'prescription': 'Prescription Pickup', 'new-rx': 'New Prescription',
'consultation': 'Consultation', 'otc': 'OTC Purchase',
'vaccination': 'Vaccination', 'other': 'Other'
};
 
const moodLabels: Record<string, string> = {
'very-bad': 'Very Unsatisfied', 'bad': 'Unsatisfied', 'neutral': 'Neutral',
'good': 'Satisfied', 'excellent': 'Very Satisfied'
};
 
let summary = 'Pharmacy Visit Summary\n';
summary += '═'.repeat(25) + '\n\n';
summary += `Visit Type: ${visitLabels[visitType] || visitType}\n`;
summary += `Wait Time: ${waitMinutes} minutes\n`;
summary += `Wait Satisfaction: ${waitSat > 0 ? '★'.repeat(waitSat) + '☆'.repeat(5 - waitSat) : 'Not rated'}\n`;
 
if (consultQuality > 0) {
summary += `Consultation Quality: ${consultQuality}/5\n`;
}
 
if (rxAccurate) {
summary += `Prescription Accurate: ${rxAccurate === 'up' ? 'Yes' : '⚠️ ISSUE REPORTED'}\n`;
}
 
summary += `\nOverall: ${moodLabels[mood || ''] || 'Not rated'}\n`;
summary += `NPS Score: ${nps > 0 ? nps + '/10' : 'Not rated'}\n`;
 
// Alerts
if (rxAccurate === 'down') {
summary += '\n⚠️ ATTENTION: Prescription accuracy issue reported';
}
if (waitMinutes > 30) {
summary += '\n⚠️ Long wait time - review staffing levels';
}
 
return summary;
},
customStyles: () => {
const rxAccurate = accuracySection.thumbRating('rxAccurate')?.value();
const baseStyles = {
padding: '16px',
borderRadius: '8px',
whiteSpace: 'pre-wrap',
fontFamily: 'monospace',
fontSize: '13px'
};
 
if (rxAccurate === 'down') {
return { ...baseStyles, backgroundColor: '#fee2e2', borderLeft: '4px solid #ef4444' };
}
return { ...baseStyles, backgroundColor: '#ecfeff', borderLeft: '4px solid #06b6d4' };
}
});
});
 
// ============================================
// FORM CONFIGURATION
// ============================================
form.configureSubmitButton({
label: 'Submit Feedback'
});
 
form.configureCompletionScreen({
type: 'text',
title: 'Thank you for your feedback!',
message: 'Your input helps us provide better pharmacy care. If you reported any concerns, our team will review and follow up if needed. Thank you for choosing our pharmacy!'
});
}
 

Frequently Asked Questions

How do we reduce pharmacy wait time complaints?

Track wait time ratings by day and hour to identify patterns. Common solutions: better staffing during peak hours, text alerts when prescriptions are ready, drive-through options, and setting accurate expectations upfront. The biggest driver of satisfaction isn't speed - it's meeting the promised time.

How important is pharmacist consultation feedback?

Very important. Pharmacist consultations are a key differentiator and revenue driver. Track consultation quality, whether patients felt heard, and if their questions were answered. Low scores indicate training needs or staffing issues preventing adequate consultation time.

Should we ask about prescription accuracy?

Yes, but carefully. Accuracy issues are critical safety signals. Include questions about medication received matching expectations and clear labeling. Any accuracy concerns should trigger immediate follow-up through your quality assurance process.

What response rate should pharmacies target?

Target 15-25% response rate for email surveys post-pickup. In-store tablets or QR codes get 5-10% but capture immediate experience. Incentivize with loyalty points if possible. Sample regularly rather than surveying every visit.

How do we handle negative pharmacy feedback?

Respond within 24 hours to serious concerns. For wait time issues, offer solutions (order ahead, delivery). For staff complaints, investigate and coach. For accuracy concerns, treat as safety incidents. Always thank patients for feedback.