Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Custom widgets: warn user it's risky #1423

Merged

Conversation

manuhabitela
Copy link
Collaborator

@manuhabitela manuhabitela commented Feb 5, 2025

Context

Fixes #1338.

Proposed solution

I allowed myself to add a somewhat related commit for small issues I stumbled upon while working on this. So that we can't add custom url widgets without filling the url input correctly. Hope it's okay!

edit: the check preventing empty-url custom widgets has been removed. Only the check verifying valid URL string is still there

Here is a preview in video:
custom.widget.warning.mp4

edit: now the image used is specific to dark theme for better contrast

Here is what it looks like in dark mode:

image

Has this been tested?

  • 👍 yes, I added tests to the test suite
  • 💭 no, because this PR is a draft and still needs work
  • 🙅 no, because this is not relevant here
  • 🙋 no, because I need help

@manuhabitela manuhabitela self-assigned this Feb 5, 2025
@manuhabitela manuhabitela force-pushed the issue-1338-custom-widget-warning branch from 8739304 to 9758d08 Compare February 5, 2025 17:21
@manuhabitela
Copy link
Collaborator Author

I need to update the tests but the implementation is already reviewable if anyone wanna check early!

@manuhabitela
Copy link
Collaborator Author

@lusebille you'll notice a few things don't exactly match your figma design, for example the ordering of confirm / cancel buttons. I did it that way because modals in grist usually have those buttons rendered like that (I actually discovered that when seeing how modals were built in the code). Is this okay or should I do some specific design here?

@lusebille
Copy link
Collaborator

@manuhabitela ok I still think it's really more natural to have validation button on the right ( and it's much more common) but I understand we need to keep Grist homegenous ( the solution might to change it everywhere but should be another ticket anyway )

@manuhabitela manuhabitela force-pushed the issue-1338-custom-widget-warning branch 8 times, most recently from 80bf1b2 to d8b21e4 Compare February 7, 2025 10:07
@manuhabitela
Copy link
Collaborator Author

After discovering the tests suite more I ended up removing my small change of making the URL input required for custom url widgets. Looks like it's actually a feature and not a bug to allow empty strings and overall it implied a bit more change than I thought that I'm not even sure is welcomed haha.

I left the change to force entering a valid URL if you input something though.

This is good to review for me!

Appart the code review, on the design part, question remains about the placement of confirm/save button: either specifically put them on the right as per Lucie's mockup, or leave them as is (on the left) to follow usual modal buttons placement in Grist, and maybe challenge this UI choice in a global way later.

@manuhabitela manuhabitela marked this pull request as ready for review February 7, 2025 10:22
@paulfitz paulfitz added the preview Launch preview deployment of this PR label Feb 13, 2025
@paulfitz
Copy link
Member

hi @manuhabitela, thanks for this, could you resolve the conflicts that have accumulated so I can stick up a preview of this to show around?

@manuhabitela manuhabitela force-pushed the issue-1338-custom-widget-warning branch from d8b21e4 to e58c14f Compare February 19, 2025 17:19
@manuhabitela
Copy link
Collaborator Author

Oops sorry, done.

I realize with the merge conflict, that this commit seems to have introduced a somewhat similar idea I had on the markdown side. Maybe it could be reused. Seeing the code though it seems the linked commit doesn't actually returns html not wrapped in p tag but just visually removes the margins. While here the important part was removing the tag. I'll check it out further.

Copy link
Contributor

Deployed commit e58c14f36accc8943d296c43c2cdd39bcdd5de58 as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-21T17:25:01.794Z)

@paulfitz
Copy link
Member

(just adding a screenshot from the preview, for context)
Screenshot from 2025-02-20 12-21-12

@berhalak berhalak self-assigned this Feb 20, 2025
@berhalak berhalak self-requested a review February 20, 2025 17:24
? 'img/security-alert.png'
: 'img/security-alert-dark-theme.png';

return new Promise<boolean>((resolve) => {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you refactor this, and create the save modal outside of the promise? Example of such modal is in modals.ts function invokePrompt.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done! I'll let you check in case I misunderstood.

@nbush
Copy link
Contributor

nbush commented Feb 20, 2025

(just adding a screenshot from the preview, for context) Screenshot from 2025-02-20 12-21-12

Is this a universal change that is intended to be shown to all users? If so, the reference to administrator & organization will be confusing to some or inaccurate for individuals.

If this is universal, I feel like this could be greatly condensed. I also think showing the URL in question on this pane is useful.

Something like:

Adding unknown custom widget

Custom widgets have the ability to read and write your document's data, as well as send it elsewhere. Make sure that you trust the resource at this URL before you continue.

https://unknownwidget.com/widget.html

[ ] I understand this warning and accept the risks

[Confirm] [Cancel]

If there are specific requirements that necessitate elements of this dialog, that would be good to know. Apologies if I've missed something!

@manuhabitela manuhabitela force-pushed the issue-1338-custom-widget-warning branch from 7e889e4 to 7a7244f Compare February 25, 2025 10:22
Copy link
Contributor

Deployed commit 7a7244f08e3e8160181cf0a67f2c6c5f4c1b52d1 as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-27T10:28:07.568Z)

Copy link
Contributor

Deployed commit 61837a6442941b6f05cc89245b6ae2141f784190 as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-27T10:35:57.310Z)

Copy link
Collaborator

@fflorent fflorent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, thanks @manuhabitela!

Copy link
Contributor

Deployed commit a2c044278da61044638335105985f5639fab1824 as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-30T11:24:39.564Z)

@berhalak
Copy link
Contributor

berhalak commented Feb 28, 2025

Ok, code looks good, thank you for addressing my comments, but some other UX questions:

  • It is possible to add Custom URL without an URL, and it still shows the confirmation popup.
  • After adding a custom widget we allow to change the URL on the right panel: (see screenshot below):
    image
    and there is no confirmation check there.
  • We lately added sanitizeHttpUrl helper to prevent this URL from being iffy. It still works, but maybe we can improve validation on the input element to disallow even pasting it.

We can all do it in a separate PR if you want, just mentioning it, if you want to address it here.

Copy link
Contributor

@berhalak berhalak left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code looks ok, some UX questions above, but this is already a good improvement.
Thank you @manuhabitela.

Copy link
Contributor

Deployed commit 75fe467d34dab306e2fc867c26b7c3c2a2aa424e as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-30T13:32:18.013Z)

@manuhabitela
Copy link
Collaborator Author

Thanks for the thorough feedback @berhalak :)

It is possible to add Custom URL without an URL, and it still shows the confirmation popup.

Good catch, I'll fix code and change the tests for that case, you are completely right.

  • After adding a custom widget we allow to change the URL on the right panel and there is no confirmation check there.

Oh, let me try to handle this quickly. So that the confirm is triggered by the widget customdef url change and not a specific user action. if I see it's too much changes maybe yeah this can be tackled later, I feel the most important part is when first adding the widget.

  • We lately added sanitizeHttpUrl helper to prevent this URL from being iffy. It still works, but maybe we can improve validation on the input element to disallow even pasting it.

I feel it's not really necessary in my case? And rely on browser native url input check is sufficient to verify user input as this moment.

@manuhabitela manuhabitela force-pushed the issue-1338-custom-widget-warning branch from 75fe467 to f42bd9d Compare February 28, 2025 13:50
Copy link
Contributor

Deployed commit f42bd9d604d332fb3384a967d1573ba604ca8b2c as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-30T13:55:35.951Z)

Copy link
Contributor

Deployed commit ecf57b9ae0bebb47530b3de8ca709efbf01fee35 as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-30T15:02:23.882Z)

Copy link
Contributor

Deployed commit aa42ddae0278ea1845b2cabbdae3116ce9e3da18 as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-03-30T15:48:57.192Z)

@manuhabitela
Copy link
Collaborator Author

So I think this is good, besides the wording feedback from @nbush.

I added some code to handle the url change in the panel and prevent showing the warning modal with empty urls. Do you mind checking one last time @berhalak? 🙏

@@ -330,7 +330,8 @@ class CustomWidgetGallery extends Disposable {
private async _validateSelectedWidget() {
const isCustomUrlWidget = this._selectedWidgetId.get() === CUSTOM_URL_WIDGET_ID;
if (isCustomUrlWidget) {
return this._customUrlInput?.reportValidity() && await userTrustsCustomWidget();
return this._customUrlInput?.reportValidity() &&
(!this._customUrl.get().length || await userTrustsCustomWidget());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nitpicking, ignore if you like:

  • Hard to read, it would be better if this would look like the comment above
  • Comment above is outdated
    :)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Man I can't figure out what comment you talk about haha. But I updated with something more readable!

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The jsdoc for this method. Thanks for updating, it looks very nice :)

@@ -558,9 +559,14 @@ export class CustomSectionConfig extends Disposable {
return cssCustomUrlDetails(
cssTextInput(
this._url,
async value => this._url.set(value),
async (value) => {
if ((!value.length || await userTrustsCustomWidget())) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Too many ((, and shouldn't we check the validity here?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah I originally wanted to use the native reportValidity but for some reason I don't understand, it always returns true here… so the user doesn't get the native form validation with native browser message, unlike in the custom widgets gallery where it works.

So yeah I didn't use it. Sometimes those native apis are only usable if the browser detects we actually are in a user interaction, maybe something like that is the culprit. Really I'm surely missing something but I can't figure out what.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(I removed the extra parentheses, thanks)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry for that. This is caused by the rawTextInput component in editableLabel.ts. It tries to be clever and disable the input before saving, so the reportValidity doesn't work. I'll file an issue for it.

Copy link
Contributor

github-actions bot commented Mar 3, 2025

Deployed commit 7a60a4a5ce061f2cfea3f2584378dd5a821c5670 as https://grist-manuhabitela-grist-core-issue-1338-custom-widget-warning.fly.dev (until 2025-04-02T16:48:38.318Z)

@@ -558,9 +559,14 @@ export class CustomSectionConfig extends Disposable {
return cssCustomUrlDetails(
cssTextInput(
this._url,
async value => this._url.set(value),
async (value) => {
if ((!value.length || await userTrustsCustomWidget())) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry for that. This is caused by the rawTextInput component in editableLabel.ts. It tries to be clever and disable the input before saving, so the reportValidity doesn't work. I'll file an issue for it.

@berhalak berhalak merged commit 11d9dfe into gristlabs:main Mar 4, 2025
12 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
gouv.fr preview Launch preview deployment of this PR
Projects
Archived in project
Development

Successfully merging this pull request may close these issues.

Display a security disclaimer when user add a widget custom
8 participants