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

Refactor in-context state to feature file #251

Merged
merged 1 commit into from
Feb 13, 2023
Merged

Conversation

shakyShane
Copy link
Collaborator

@shakyShane shakyShane commented Feb 10, 2023

Reviewer:
Asana:

Description

@alistairjcbrown This is my 100% my issue for not seeing this earlier, but I was debugging some things recently I noticed that the purpose of Settings has not been communicated correctly in the past, something I will address.

For now, the short version is this: can we just create a feature-file for this work instead, which will allow you to hold your own internal state and not need to interact with settings as much (only for the true purpose, which was feature flags etc)

Please read through the comments and let me know if anything isn't clear, but the short version is this:

  • Settings was designed as a cross-platform way to retrieve global settings/feature toggles etc, we shouldn't expand it's use to feature-related state
  • When we do add new features, we can use the composition + dependency injection techniques instead, it's the exact same code if you look, but now the feature is self contained. It also then gives you a little container (the class) in which you can have your own internal state without this feature touching too many parts of the codebase.
  • If you look at what I've removed from Settings and extension.transport.js I'm sure you'll be happy 😎
export class InContextSignup {
    // your own internal state, instead of expanding the scope of `Settings`
    permanentlyDismissed = false
    initiallyDismissed = false

    /**
     * Pass the device as a constructor param, and then do everything as before
     * @param {import("./DeviceInterface/InterfacePrototype").default} device
     */
    constructor(device) {
        this.device = device
    }

    async init() { 
       // etc 
    } 
}

// then, you can do the composition + dependency injection like this:
class ExtensionInterface extends InterfacePrototype {
    inContextSignup = new InContextSignup(this)
}

Steps to test

Can you run this locally and see if it works? I just put it together as a POC (I've not changed any functionality of course) but it would be good to get this resolved before your feature is rolled out :)

@github-actions
Copy link

Note: Password rules outdated

inntopia.travel not present in current
	rules: minlength: 7; maxlength: 19; required: digit; allowed: upper,lower,[-];

You can update the rules with the following command

cd packages/password && npm run rules:update

Once you've updated the rules, re-run the build from the root with npm run build and then commit all changes.

/**
* Adding this here since only the extension currently supports this
*/
inContextSignup = new InContextSignup(this)
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

we can prevent the base InterfacePrototype from growing in size for every feature we add by using composition like this and dependency injection so that the feature can call back to the device.

return TOOLTIP_TYPES.EmailSignup
}

return null
}

onIncontextSignup () {
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

both of these methods are only relevant to this feature, so move these into it

async resetAutofillUI (callback) {
this.removeAutofillUIFromPage()

// Start the setup process again
await this.refreshSettings()
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

no need to refresh global settings - anything this 'feature' needs can be done in 'setupAutofill'

@@ -86,11 +65,6 @@
await this.postInit()
}

removeAutofillUIFromPage () {
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

moved to the base, since it's truly generic/reusable

/**
* In the extension, we must resolve `inContextSignup` data as past of setup
*/
await this.inContextSignup.init()
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

if any features need 'startup' data, fetch it here inside 'setupAutofill'

@@ -47,6 +47,9 @@ class InterfacePrototype {
/** @type {PasswordGenerator} */
passwordGenerator = new PasswordGenerator();

/** @type {import("../InContextSignup.js").InContextSignup | null} */
inContextSignup = null
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

null because not all devices support this yet, and TS helps by forcing us to check for null

Comment on lines +8 to +9
permanentlyDismissed = false
initiallyDismissed = false
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

instead of adding to Settings, why not just add some specific data here?

Comment on lines +19 to +21
const incontextSignupDismissedAt = await this.device.deviceApi.request(new GetIncontextSignupDismissedAtCall(null))
this.permanentlyDismissed = Boolean(incontextSignupDismissedAt.permanentlyDismissedAt)
this.initiallyDismissed = Boolean(incontextSignupDismissedAt.initiallyDismissedAt)
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

this is the logic that was mixed between the extension transport and the Settings, we can just make the call directly here and store the data ourselves without it expanding the scope of the Device or Settings

/**
* @returns {Promise<boolean|null>}
*/
async getIncontextSignupInitiallyDismissed () {
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

This verbose pattern of fetching and verifying the data was for the global configuration, feature toggles and available input types since they affect ALL features one way or another.

I can see why you added these here, and we probably need to update the docs/guides to be clearer, but we shouldn't be expanding Settings to include any new state from individual features. :)

@@ -55,7 +55,6 @@ async function extensionSpecificRuntimeConfiguration (deviceApi) {
const contentScope = await getContentScopeConfig()
const emailProtectionEnabled = isAutofillEnabledFromProcessedConfig(contentScope)
const incontextSignupEnabled = isIncontextSignupEnabledFromProcessedConfig(contentScope)
const incontextSignupDismissedAt = await deviceApi.send(new GetIncontextSignupDismissedAtCall(null))
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

As mentioned above, this appears to be user-state related and not actually relevant to 'global' settings, so it's moved into the feature file

@alistairjcbrown
Copy link
Member

I added a branch with integration tests, and this branch passed 🎉 (with the typo fix applied) -- #254

@shakyShane
Copy link
Collaborator Author

@alistairjcbrown feel free to just take over this PR/branch and rebase against the integration tests etc.

Basically I'll leave you to apply both this + integration tests, just ping when ready and I can approve stuff :)

@alistairjcbrown alistairjcbrown changed the base branch from main to abrown/incontext-integration-tests February 13, 2023 11:39
Base automatically changed from abrown/incontext-integration-tests to main February 13, 2023 12:03
Create a feature file for in-context state to be
managed in, instead of using the settings setup
which is intended for more global state.
@alistairjcbrown alistairjcbrown changed the title shane/in-context Refactor in-context state to feature file Feb 13, 2023
Copy link
Member

@alistairjcbrown alistairjcbrown left a comment

Choose a reason for hiding this comment

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

LGTM :shipit:

CDRussell pushed a commit to duckduckgo/Android that referenced this pull request Mar 23, 2023
Task/Issue URL:
https://app.asana.com/0/1204250253793536/1204250253793536
Autofill Release:
https://github.com/duckduckgo/duckduckgo-autofill/releases/tag/6.4.1


## Description
Updates Autofill to version
[6.4.1](https://github.com/duckduckgo/duckduckgo-autofill/releases/tag/6.4.1).

### Autofill 6.4.0 and 6.4.1 release notes
## What's Changed

### Tooling and Tests
* Update integration tests for in-context signup by @alistairjcbrown in
duckduckgo/duckduckgo-autofill#254 and
duckduckgo/duckduckgo-autofill#255
* Update macOS browser repository ID in `asana-release.yml` by @ayoy in
duckduckgo/duckduckgo-autofill#259
* Use node v18 and update actions to read `.nvmrc` file by
@alistairjcbrown in
duckduckgo/duckduckgo-autofill#269
* Bugfix: Update release script to add checkout path to node version
file path by @alistairjcbrown in
duckduckgo/duckduckgo-autofill#286

### Source Code Updates
* Refactor in-context state to feature file by @shakyShane in
duckduckgo/duckduckgo-autofill#251
* Prevent duplicated schema types by using JSON schema throughout by
@shakyShane in
duckduckgo/duckduckgo-autofill#253
* Stop scanning pages with a large number of inputs by @alistairjcbrown
in duckduckgo/duckduckgo-autofill#257 and
duckduckgo/duckduckgo-autofill#262
* Ignore small email inputs by @alistairjcbrown in
duckduckgo/duckduckgo-autofill#261
* Fix username not saved by @GioSensation in
duckduckgo/duckduckgo-autofill#275
* Updates to in-context signup treatment by @alistairjcbrown and
@GioSensation in
duckduckgo/duckduckgo-autofill#284


**Full Changelog**:
duckduckgo/duckduckgo-autofill@6.3.0...6.4.1

## Steps to test
This release has been tested during autofill development. For smoke test
steps see [this
task](https://app.asana.com/0/1198964220583541/1200583647142330/f).

Co-authored-by: alistairjcbrown <alistairjcbrown@users.noreply.github.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants