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

App watcher - Build extensions #4346

Open
wants to merge 21 commits into
base: main
Choose a base branch
from
Open

App watcher - Build extensions #4346

wants to merge 21 commits into from

Conversation

isaacroldan
Copy link
Contributor

@isaacroldan isaacroldan commented Aug 19, 2024

WHY are these changes introduced?

App watcher now has the responsibility of building extensions when they change.

For extensions that use ESBuild, it handles that using using contexts.

Having a unified place for watching and building extensions during dev is very convenient, as the events from here can be used by the different processes running during dev:

  • Legacy partners draft update
  • New management api updates
  • Previewable extensions using the dev console
  • ...

WHAT is this pull request doing?

  • The App Watcher will now build extensions:
    • At start, build all extensions
    • On every change, rebuild the affected extensions.
  • Remove the UpdatedSource event type for the watcher.
  • For extensions using ESBuild: use esbuild contexts to handle incremental builds (which means: faster builds)
  • All build artifacts are generated in the local .shopify directory by default.
  • Update the new dev flow to use this new feature.

How to test your changes?

Having an app with different extensions (specially ui-extensions and functions):

  • Run pnpm shopify demo watcher --path <path_to_app>
  • Open the .shopify/bundle directory, you should see all the built extensions.
  • Make a change in an extension with source code, it should update the built artifact.

Alternative: Having an org in app-management, run dev with the new API.

Post-release steps

Measuring impact

How do we know this change was effective? Please choose one:

  • n/a - this doesn't need measurement, e.g. a linting rule or a bug-fix
  • Existing analytics will cater for this addition
  • PR includes analytics changes to measure impact

Checklist

  • I've considered possible cross-platform impacts (Mac, Linux, Windows)
  • I've considered possible documentation changes

@isaacroldan isaacroldan changed the title App watcher build App watcher - Build extensions Aug 19, 2024
Copy link
Contributor

We detected some changes at either packages/*/src or packages/cli-kit/assets/cli-ruby/** and there are no updates in the .changeset.
If the changes are user-facing, run "pnpm changeset add" to track your changes and include them in the next release CHANGELOG.

Copy link
Contributor

github-actions bot commented Aug 19, 2024

Coverage report

St.
Category Percentage Covered / Total
🟡 Statements
73.18% (+0.17% 🔼)
8444/11539
🟡 Branches
69.74% (+0.17% 🔼)
4111/5895
🟡 Functions
71.89% (+0.14% 🔼)
2199/3059
🟡 Lines
73.54% (+0.19% 🔼)
7987/10861
Show new covered files 🐣
St.
File Statements Branches Functions Lines
🟢
... / app-watcher-esbuild.ts
90% 100% 84.62% 92.59%
Show files with reduced coverage 🔻
St.
File Statements Branches Functions Lines
🟢
... / app-diffing.ts
100%
85.71% (-14.29% 🔻)
100% 100%
🟢
... / app-event-watcher.ts
79.27% (-5.35% 🔻)
55% (-15% 🔻)
82.76% (-2.24% 🔻)
80% (-2.98% 🔻)
🟢
... / ConcurrentOutput.tsx
98.39% (-1.61% 🔻)
90.91% (-4.55% 🔻)
100%
98.33% (-1.67% 🔻)

Test suite run success

1892 tests passing in 859 suites.

Report generated by 🧪jest coverage report action from 196e47e

Comment on lines +249 to +259
const interval = setInterval(() => {
if (emitSpy.mock.calls.length > 0) {
clearInterval(interval)
resolve()
}
}, 100)
// Wait max 3 seconds, if not resolved, reject.
setTimeout(() => {
clearInterval(interval)
reject(new Error('Timeout waiting for emitSpy to be called'))
}, 3000)
Copy link
Contributor

Choose a reason for hiding this comment

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

I wonder if this kind of thing would be a bit easier to read:

Suggested change
const interval = setInterval(() => {
if (emitSpy.mock.calls.length > 0) {
clearInterval(interval)
resolve()
}
}, 100)
// Wait max 3 seconds, if not resolved, reject.
setTimeout(() => {
clearInterval(interval)
reject(new Error('Timeout waiting for emitSpy to be called'))
}, 3000)
const initialTime = Date.now()
while (emitSpy.mock.calls.length === 0) {
if (Date.now() - initialTime < 3000) {
await sleep(100)
} else {
reject(new Error('Timeout waiting for emitSpy to be called'))
}
}
resolve()

Note we might have something about not awaiting in loops 😢

}

async start() {
// If there is a previous build folder, delete it
if (fileExistsSync(this.buildOutputPath)) await rmdir(this.buildOutputPath, {force: true})
Copy link
Contributor

Choose a reason for hiding this comment

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

Why not:

Suggested change
if (fileExistsSync(this.buildOutputPath)) await rmdir(this.buildOutputPath, {force: true})
if (await fileExists(this.buildOutputPath)) await rmdir(this.buildOutputPath, {force: true})

It's an async function anyway, may as well use nonblocking operations.

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