vue-command
vue-command copied to clipboard
Bug: Wrong prompt display when updated during command execution
Hi,
Thank you for the hard work on this library! I can't manage to update the prompt property from a custom command component. Maybe it's a misuse on my side.
For example, I've created a cd
command bound to a ChangeDirectoryCommand
component.
<vue-command
:commands="commands"
:executed="new Set()"
show-intro
show-help
:title="prompt"
:prompt="prompt"
/>
// ...
computed: {
commands() {
return {
cd: () => ChangeDirectoryCommand,
help: () =>
createStdout(`
cd: Change directory<br />
help: Display help text<br />`),
};
},
prompt() {
// Prompt is retrieved from a global store.
return this.$root.$data.prompt;
},
},
};
The ChangeDirectoryCommand
is in charge of the display and business logic (retrieve command parameters and updating props accordingly)
<script>
export default {
name: "ChangeDirectoryCommand",
inject: ["terminate"],
computed: {
targetDirectory: function () {
return this.context.parsed._[1];
},
},
mounted() {
this.$root.$data.prompt = this.$root.$data.prompt + "/" + this.targetDirectory;
this.terminate();
},
};
</script>
You can find the complete example here: https://codesandbox.io/s/vue-command-cd-o58s2?file=/src/App.vue
When I run this sample code and execute cd home
the next prompt displayed after command execution is outdated.
user@system:# cd home
Moving to home
user@system:#
But if I hit enter (or run a new command) the current prompt will be updated with the correct value.
user@system:# cd home
Moving to home
user@system:#/home
user@system:#/home
After some checks, I think I've found why it's happening. When my stdout component is pushed to the history, the next stdin is rendered with it's local.prompt
property. At this time, my command has not been executed so the prompt in the global state is still user@system:#
. When my command terminates the global state has been updated to user@system:#/home
but not the stdin local state. Then, when we run a new command the current stdin prompt is persisted with the root component prompt property which is bound to the global state (user@system:#/home
).
How to ensure that the next prompt is up to date?
Thank you,
@DropSnorz I found a workaround to this issue, you can access the last stdin component reference and call setPrompt()
manully to set the next prompt. Code may be like this:
const stdins = this.$refs.vueCommand.$refs.stdin;
const lastStdin = stdins[stdins.length - 1];
lastStdin.setPrompt(<next prompt>);
@MudOnTire Thank you for sharing this workaround. It works well! 😉
Please test it with the newest version.