Avoid suggesting UNIX timestamp integers for `type: integer` props
>>> [!note] Migrated issue <!-- Drupal.org comment --> <!-- Migrated from issue #3533675. --> Reported by: [wim leers](https://www.drupal.org/user/99777) Related to !428 !426 !425 >>> <h3 id="overview">Overview</h3> <p>Over a year ago, XB added <code>StringSemanticsConstraint</code>. Because URLs, titles, names of people, filenames and so on all are strings, but they're NOT all the same <em>kind</em> of string.</p> <p>This is coming up again for integers over at <a href="https://git.drupalcode.org/project/experience_builder/-/merge_requests/1138/diffs#note_545070">https://git.drupalcode.org/project/experience_builder/-/merge_requests/1138/diffs#note_545070</a>, for video width/height:</p> <blockquote><p> &#128027; This <code>width&#8605;entity&#9244;&#9244;entity:file&#9245;filesize&#9246;&#9247;value</code> is <em>nonsense</em> ("filesize" is assigned as width). Same for <code>height&#8605;entity&#9244;&#9244;entity:file&#9245;created&#9246;&#9247;value</code> ("created" UNIX timestamp is assigned as height). </p></blockquote> <p>This results in the following incoherent set of suggestions when populating a <code>type: integer</code> prop in a <code>ContentTemplate</code>:</p> <pre>"Authored by &rarr; User &rarr; Last access" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;access&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Authored by &rarr; User &rarr; Changed" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;changed&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Authored by &rarr; User &rarr; Created" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;created&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Authored by &rarr; User &rarr; Last login" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;login&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 'Authored by &rarr; User &rarr; Picture &rarr; Height' =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;user_picture&#9246;&#9247;height',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 'Authored by &rarr; User &rarr; Picture &rarr; Width' =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;user_picture&#9246;&#9247;width',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Authored on" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;created&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Changed" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;changed&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Silly image &#129313; &rarr; Changed" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;field_silly_image&#9246;&#9247;entity&#9244;&#9244;entity:file&#9245;changed&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Silly image &#129313; &rarr; Created" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;field_silly_image&#9246;&#9247;entity&#9244;&#9244;entity:file&#9245;created&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Silly image &#129313; &rarr; File size" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;field_silly_image&#9246;&#9247;entity&#9244;&#9244;entity:file&#9245;filesize&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Silly image &#129313; &rarr; Height" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;field_silly_image&#9246;&#9247;height',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Silly image &#129313; &rarr; Width" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;field_silly_image&#9246;&#9247;width',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Revision create time" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;revision_timestamp&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Revision user &rarr; User &rarr; Last access" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;revision_uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;access&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Revision user &rarr; User &rarr; Changed" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;revision_uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;changed&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Revision user &rarr; User &rarr; Created" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;revision_uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;created&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; "Revision user &rarr; User &rarr; Last login" =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;revision_uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;login&#9246;&#9247;value',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 'Revision user &rarr; User &rarr; Picture &rarr; Height' =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;revision_uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;user_picture&#9246;&#9247;height',<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 'Revision user &rarr; User &rarr; Picture &rarr; Width' =&gt; '&#8505;&#65038;&#9244;entity:node:foo&#9245;revision_uid&#9246;&#9247;entity&#9244;&#9244;entity:user&#9245;user_picture&#9246;&#9247;width',</pre><h3 id="proposed-resolution">Proposed resolution</h3> <p>See the "goal" MR: <a href="https://git.drupalcode.org/project/canvas/-/merge_requests/425/diffs —">https://git.drupalcode.org/project/canvas/-/merge_requests/425/diffs —</a> this shows ONLY what the goal is.</p> <ol> <li>Approach 1: "semantics constraint" MR: <a href="https://git.drupalcode.org/project/canvas/-/merge_requests/426">https://git.drupalcode.org/project/canvas/-/merge_requests/426</a> &mdash; based on the original issue summary and the research comments 6 through 8, concerns listed in comment 13 </li><li>Approach 2: "reuse the existing "Range" constraint on timestamp fields": <a href="https://git.drupalcode.org/project/canvas/-/merge_requests/428/diffs">https://git.drupalcode.org/project/canvas/-/merge_requests/428/diffs</a>, reuses the infra additions from approach 1, without the new constraint </li></ol> <h3 id="ui-changes">User interface changes</h3> <p>None &mdash; except that if <code>DynamicPropSource</code> suggestions are visible, they will now make a lot more sense:</p> <dl> <dt>before</dt> <dd><img src="https://www.drupal.org/files/issues/2025-12-17/before.png"> </dd><dt>after</dt> <dd><img src="https://www.drupal.org/files/issues/2025-12-17/after.png"><br> &#128070; if you drill down, you'll find these allow you to pick "image width/height", including on the user picture<br> </dd></dl> <p>(tested using the "integer" prop on the "all-props" test SDC, when editing a <code>ContentTemplate</code>)</p> > Related issue: [Issue #2226493](https://www.drupal.org/node/2226493) > Related issue: [Issue #3521088](https://www.drupal.org/node/3521088)
issue