Skip to content

Flawed getUniqAttr Parsing May Corrupt HTML Output #202

Open
@mmichaelis

Description

@mmichaelis

/**
* Gets value from
* @example
* getUniqAttr({ 'foo': true, 'bar': bar' }) => 'bar'
* @param attrs
* @returns {string}
*/
const getUniqAttr = (attrs) => keysReduce(
attrs,
(res, key) => (attrs[key] === key ? attrs[key] : null),
null,
);

Without understanding the details, the description may benefit from some enhanced description (see below). Given my assumptions and tests are correct, I will refer to a possibly even dangerous flaw in getUniqAttr handling, which can be summarized as: You can fake unique attributes within BBCode.

Suggestion for Description Enhancement

/**
 * Given a record of string to some value, this method will
 * retrieve the last entry in the record and return its key
 * when it is equal to its value.
 *
 * Such entries typically represent so-called _unique attributes_
 * after parsing, so that `[url=someUrl]` gets parsed to an
 * attributes object like: `{ someUrl: "someUrl" }`.
 *
 * @example
 * getUniqAttr({ 'foo': true, 'bar': bar' }) => 'bar'
 * @example
 * getUniqAttr({ 'bar': bar', 'foo': true }) => null
 * @param attrs - record of strings to attribute values
 * @returns {string|null} `null`, if no unique attribute could be determined
 */

The Flaw

BBCode Actual HTML Expected HTML (Suggestion)
[url fakeUnique=fakeUnique]T[/url] <a href="fakeUnique">T</a> <a href="T" fakeUnique="fakeUnique">T</a>
[url=https://example.org/ fakeUnique=fakeUnique]T[/url] <a href="fakeUnique">T</a> <a href="https://example.org/" fakeUnique="fakeUnique">T</a>
[url=https://example.org/ hidden]T[/url] <a href="hidden">T</a> <a href="T" hidden="hidden">T</a>
[url=https://example.org/ hidden]T[/url] <a href="hidden">T</a> <a href="T" hidden="hidden">T</a>
[table=onclick][tr][td]T[/td][/tr][/table] <table onclick="onclick"><tr><td>T</td></tr></table> undecided
[table onclick=onclick][tr][td]T[/td][/tr][/table] <table onclick="onclick"><tr><td>T</td></tr></table> undecided

Stumbled across this while trying to add a sanitizer that forbids on* attributes to be created during processing.

Thus, the attribute found as being "unique" may not always have been "unique" within the original BBCode.

Perhaps one possible option would be using a Symbol() as key for the unique attribute. But I did not dive into parsing, if this is even feasible.

Metadata

Metadata

Assignees

Labels

P1Moderate IssuebugSomething isn't working

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions