bug: mutating an immutable property calls related watcher functions w/ new value
Nobody has claimed this yet.
Assessment
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Newbie friendliness
- 45/100
- Issue type
- Bug
- Clarity
- Mostly clear
- Activity status
- Stale
- Tech stack
- typescript
- Domain
- frontend
Research direction
Start with the watcher and immutable-property behavior described in the issue, using the linked reproduction repository to reproduce the console output. Trace how @Prop() and @Watch() are processed when the property is mutated internally, then add a regression test showing that the watcher is not called for an immutable property and confirm the existing mutable-property behavior remains intact.
Written by the indexing model from the issue text.
Description
Prerequisites
- I have read the Contributing Guidelines.
- I agree to follow the Code of Conduct.
- I have searched for existing issues that already report this problem, without success.
Stencil Version
2.17.2
Current Behavior
When decorating a function with a @Watch decorator for an immutable property, and changing that property internally, the watcher function is still called despite the property being immutable.
Example
I have the following immutable (by default) property and watcher on that property:
@Prop() myVar: string = 'foo';
@Watch('myVar')
watchMyVar(newValue: string, oldValue: string): void {
console.log('---watchMyVar START---');
console.log(newValue, oldValue);
console.log('---watchMyVar END---');
}
If I have a method which mutates myVar internally, the watcher function is subsequently called.
mutateImmutableProperty(newVal: string): void {
this.myVar = newVal;
}
If I then call mutateImmutableProperty, watchMyVar is subsequently called because the value of myVar is updated:
this.mutateImmutableProperty(`${Date.now()}`);
// ---watchMyVar START---
// bar foo
// ---watchMyVar END---
However, myVar is immutable (mutable: false - by default) therefore, I would question if it's correct to call subsequent watcher functions.
Expected Behavior
For the @Watcher functions to not be called on immutable properties when they are modified internally.
Steps to Reproduce
- Create a Stencil component which has a property defined as follows:
@Prop() myVar: string = 'foo';
- Create a watcher on that property:
@Watch('myVar')
watchMyVar(newValue: string, oldValue: string): void {
console.log('---watchMyVar START---');
console.log(newValue, oldValue);
console.log('---watchMyVar END---');
}
- Create a method to mutate the object:
mutateImmutableProperty(newVal: string): void {
this.myVar = newVal;
}
- Call this method internally. I have attached this to the
onClickevent of a button:
render() {
return [<div>{this.myVar}</div>, <button onClick={() => this.mutateImmutable(`${Date.now()}`)}>Mutate</button>];
}
- Observe the console logs with the following output, illustrating the watcher function being called:
---watchMyVarHandler START---
1658921136478 1658920723269
---watchMyVarHandler END---
Code Reproduction URL
https://github.com/kelvindart/stencil-watcher-bug
Additional Information

- Dominant language
- TypeScript
- Stars
- 13.1k
- Forks
- 855
- Avg merge
- 4h 7m
- Merged PRs (30d)
- 44
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from stenciljs/core
-
Stencil v5
Difficulty 2/5 1-3 hours Newbie friendliness 68/100
-
Stencil v5
Difficulty 4/5 3-5 days Newbie friendliness 55/100
-
Bug: Validated Stencil v5
Difficulty 4/5 3-5 days Newbie friendliness 48/100
-
Feature: Want this? Upvote it!
Difficulty 5/5 Over a week Newbie friendliness 25/100
-
Feature: Want this? Upvote it!
Difficulty 4/5 3-5 days Newbie friendliness 48/100
Similar issues
-
clawsweeper:fix-shape-clear clawsweeper:queueable-fix clawsweeper:source-repro impact:ux-friction issue-rating: 🦞 diamond lobster no-stale P3
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
-
community first-timers-only good first issue hacktoberfest help wanted low hanging fruit up-for-grabs
Difficulty 1/5 Under an hour Newbie friendliness 76/100
-
code-quality refactoring
Difficulty 2/5 1-3 hours Newbie friendliness 84/100
github/gh-aw-firewall#8816 ·
-
integration:quickjs org:external priority:backlog topic:code-interpreter topic:middleware type:feature
Difficulty 2/5 1-3 hours Newbie friendliness 74/100
langchain-ai/deepagents#6450 ·
-
Difficulty 1/5 Under an hour Newbie friendliness 88/100
vercel/react-tweet#225 ·