Repository: eslint/eslint
File: lib/rule-tester/rule-tester.js (JavaScript)

Code before:
                                                `${suggestionPrefix} desc should be "${expectedSuggestion.desc}" but got "${actualSuggestion.desc}" instead.`
                                            );
                                        } else if (hasOwnProperty(expectedSuggestion, "messageId")) {
                                            assert.ok(
                                                ruleHasMetaMessages,
                                                `${suggestionPrefix} Test can not use 'messageId' if rule under test doesn't define 'meta.messages'.`
                                            );
                                            assert.ok(
                                                hasOwnProperty(rule.meta.messages, expectedSuggestion.messageId),
                                                `${suggestionPrefix} Test has invalid messageId '${expectedSuggestion.messageId}', the rule under test allows only one of ${friendlyIDList}.`
                                            );
                                            assert.strictEqual(
                                                actualSuggestion.messageId,
                                                expectedSuggestion.messageId,
                                                `${suggestionPrefix} messageId should be '${expectedSuggestion.messageId}' but got '${actualSuggestion.messageId}' instead.`
                                            );

                                            const missingPlaceholders = getUnsubstitutedMessagePlaceholders(
                                                actualSuggestion.desc,
                                                rule.meta.messages[expectedSuggestion.messageId],
                                                expectedSuggestion.data
                                            );

                                            assert.ok(
                                                missingPlaceholders.length === 0,
                                                `The message of the suggestion has ${missingPlaceholders.length > 1 ? `unsubstituted placeholders: ${missingPlaceholders.map(name => `'${name}'`).join(", ")}` : `an unsubstituted placeholder '${missingPlaceholders[0]}'`}. Please provide them via the 'data' property for the suggestion in the context.report() call.`
                                            );

                                            if (hasOwnProperty(expectedSuggestion, "data")) {
                                                const unformattedMetaMessage = rule.meta.messages[expectedSuggestion.messageId];
                                                const rehydratedDesc = interpolate(unformattedMetaMessage, expectedSuggestion.data);

                                                assert.strictEqual(
                                                    actualSuggestion.desc,
                                                    rehydratedDesc,
                                                    `${suggestionPrefix} Hydrated test desc "${rehydratedDesc}" does not match received desc "${actualSuggestion.desc}".`
                                                );
                                            }
                                        } else if (hasOwnProperty(expectedSuggestion, "data")) {
                                            assert.fail(
                                                `${suggestionPrefix} Test must specify 'messageId' if 'data' is used.`
                                            );
                                        } else {
                                            assert.fail(
                                                `${suggestionPrefix} Test must specify either 'messageId' or 'desc'.`
                                            );
                                        }

                                        assert.ok(hasOwnProperty(expectedSuggestion, "output"), `${suggestionPrefix} The "output" property is required.`);
                                        const codeWithAppliedSuggestion = SourceCodeFixer.applyFixes(item.code, [actualSuggestion]).output;


Review comment (suggestion):
```suggestion
                                                `The message of the suggestion has ${missingPlaceholders.length > 1 ? `unsubstituted placeholders: ${missingPlaceholders.map(name => `'${name}'`).join(", ")}` : `an unsubstituted placeholder '${missingPlaceholders[0]}'`}. Please provide the missing ${missingPlaceholders.length > 1 ? "values" : "value"} via the 'data' property for the suggestion in the context.report() call.`
```

Code after:
                                                `${suggestionPrefix} desc should be "${expectedSuggestion.desc}" but got "${actualSuggestion.desc}" instead.`
                                            );
                                        } else if (hasOwnProperty(expectedSuggestion, "messageId")) {
                                            assert.ok(
                                                ruleHasMetaMessages,
                                                `${suggestionPrefix} Test can not use 'messageId' if rule under test doesn't define 'meta.messages'.`
                                            );
                                            assert.ok(
                                                hasOwnProperty(rule.meta.messages, expectedSuggestion.messageId),
                                                `${suggestionPrefix} Test has invalid messageId '${expectedSuggestion.messageId}', the rule under test allows only one of ${friendlyIDList}.`
                                            );
                                            assert.strictEqual(
                                                actualSuggestion.messageId,
                                                expectedSuggestion.messageId,
                                                `${suggestionPrefix} messageId should be '${expectedSuggestion.messageId}' but got '${actualSuggestion.messageId}' instead.`
                                            );

                                            const unsubstitutedPlaceholders = getUnsubstitutedMessagePlaceholders(
                                                actualSuggestion.desc,
                                                rule.meta.messages[expectedSuggestion.messageId],
                                                expectedSuggestion.data
                                            );

                                            assert.ok(
                                                unsubstitutedPlaceholders.length === 0,
                                                `The message of the suggestion has ${unsubstitutedPlaceholders.length > 1 ? `unsubstituted placeholders: ${unsubstitutedPlaceholders.map(name => `'${name}'`).join(", ")}` : `an unsubstituted placeholder '${unsubstitutedPlaceholders[0]}'`}. Please provide the missing ${unsubstitutedPlaceholders.length > 1 ? "values" : "value"} via the 'data' property for the suggestion in the context.report() call.`
                                            );

                                            if (hasOwnProperty(expectedSuggestion, "data")) {
                                                const unformattedMetaMessage = rule.meta.messages[expectedSuggestion.messageId];
                                                const rehydratedDesc = interpolate(unformattedMetaMessage, expectedSuggestion.data);

                                                assert.strictEqual(
                                                    actualSuggestion.desc,
                                                    rehydratedDesc,
                                                    `${suggestionPrefix} Hydrated test desc "${rehydratedDesc}" does not match received desc "${actualSuggestion.desc}".`
                                                );
                                            }
                                        } else if (hasOwnProperty(expectedSuggestion, "data")) {
                                            assert.fail(
                                                `${suggestionPrefix} Test must specify 'messageId' if 'data' is used.`
                                            );
                                        } else {
                                            assert.fail(
                                                `${suggestionPrefix} Test must specify either 'messageId' or 'desc'.`
                                            );
                                        }

                                        assert.ok(hasOwnProperty(expectedSuggestion, "output"), `${suggestionPrefix} The "output" property is required.`);
                                        const codeWithAppliedSuggestion = SourceCodeFixer.applyFixes(item.code, [actualSuggestion]).output;