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

Add TaskProvider implementation for dynamic task generation #787

Open
daviwil opened this issue May 26, 2017 · 12 comments
Open

Add TaskProvider implementation for dynamic task generation #787

daviwil opened this issue May 26, 2017 · 12 comments
Labels
Area-Tasks Issue-Enhancement A feature request (enhancement).

Comments

@daviwil
Copy link
Contributor

daviwil commented May 26, 2017

In the upcoming 1.13.0 release, VS Code will be getting a new "task provider" API which will allow us to automatically populate the "Task: Run Task" menu with a task list that we generate from code. This would be really useful for scooping the task names out of a psake or Invoke-Build script so that the user can run them easily.

There isn't any documentation yet but the API shape is here:

https://github.com/Microsoft/vscode/blob/447622435ae4745a0a4b9b7033e178d399c82b88/src/vs/vscode.d.ts#L3804

@daviwil daviwil added the Issue-Enhancement A feature request (enhancement). label May 26, 2017
@daviwil daviwil added this to the 1.3.0 milestone May 26, 2017
@nightroman
Copy link

nightroman commented May 27, 2017

@daviwil
This is going to be really useful.

I have a question related to Invoke-Build. There is a tool New-VSCodeTask.ps1
which generates VSCode tasks bound to Invoke-Build tasks. You are probably
aware of it. But I noticed you do not use it and make tasks.json manually.
You may have your reasons but I see some shortcomings of the tool, too.
I was just about to improve it for generating tasks.json almost like yours.

This is doable and not that difficult. But I wonder if such a tool is needed at
all with the new task provider coming. What do you think?

NB

@daviwil
Copy link
Contributor Author

daviwil commented May 27, 2017

Hey Roman! Yep, I definitely know about it. I haven't used it because I'm pretty comfortable editing the tasks.json file. I'll give it a try though! You may not need to maintain that script much longer if the PowerShell extension will be able to get the list of tasks on its own.

Does the output encoding issue still exist with the new 2.0.0 version of the task runner that uses the Integrated Terminal? In theory it will use powershell.exe's default encoding, so whatever works there should work fine in the new task runner's output.

Quick thought on how I'll make this feature work: I'm thinking that at first I'll look for build scripts in the typical default file names for psake and Invoke-Build: FolderName.build.ps1, build.ps1, .build.ps1, psake.ps1, etc in the root workspace folder. I'll also provide a workspace-level setting where you can configure the path to the build script to override that behavior. Once I have the build script path, I'll parse the file and look for top-level function invocations that call Task and then read their first parameter to get the task name. That should be enough to cover 90% of cases, don't you think?

I'm also thinking about providing a $psEditor API so that module authors can arbitrarily add tasks, but that will come a little later :)

@rkeithhill
Copy link
Contributor

@nightroman In addition to the encoding issue see microsoft/vscode#15179 (comment). Adding tasks to an existing tasks.json is a pain. And you do need to be able to add to existing tasks.json files. I frequently have my own custom tasks defined so modifications need to be additive.

Frankly I was hoping they would go with a file-based approach e.g.: psmodule-tasks.json, gulp-tasks.json, etc. With the API approach, I'm not sure yet how this helps Plaster when run outside the context of VSCode. Even in the context of VSCode we'll need to wire up Plaster with this API somehow. Maybe we pass $psEditor into Plaster?

@daviwil
Copy link
Contributor Author

daviwil commented May 27, 2017

I think the new API allows you to do exactly what you would hope for: making your own file-based approach. An extension could add a task provider that can pull tasks from any file type containing tasks (MSBuild, PowerShell build scripts, Gulp, etc). I believe this should work in addition to the existing tasks.json file.

As far as Plaster plugging into this is concerned, when Plaster starts to provide the "project model" for module projects, it will hook into PSES to provide a list of tasks that can be run in VS Code. Either Plaster can be the place where the task-sourcing behavior comes from or it could override a simple built-in implementation that works even when Plaster isn't present.

@nightroman
Copy link

@daviwil

Does the output encoding issue still exist with the new 2.0.0 version of the task runner that uses the Integrated Terminal?

I think so. Unless I am using a different version or do something not quite right. How can I check?

That should be enough to cover 90% of cases, don't you think?

Perhaps much more that 90%. Yet I have some doubts on guessing about the default
script and getting tasks by parsing. There may be unknown "rules". Some tasks
may be imported, task names may be dynamic (not literal strings), or script
location/name may be not standard for the given workspace directory, for
example Invoke-Build also searches in parent directories and supports
user hooks for custom script resolution, see help.

For Invoke-Build the proper way would be

    ### How to get task names

    # change to the workspace root
    Set-Location -LiteralPath $env:VSCODE_CWD
    # get tasks as IB sees them
    $tasks = Invoke-Build ??
    # task names
    $tasks.Keys

    ### How to invoke
    # change to the workspace root
    Set-Location -LiteralPath $env:VSCODE_CWD
    # invoke
    Invoke-Build $taskName

Note that IB finds the default build script in both cases.

@nightroman
Copy link

@rkeithhill

Adding tasks to an existing tasks.json is a pain. And you do need to be able
to add to existing tasks.json files. I frequently have my own custom tasks
defined so modifications need to be additive.

I agree with every sentence. I was planning to support this in New-VSCodeTask.ps1,
to some extent. But now I am not sure because the PowerShell integrated console
came to VSCode and now task providers are coming, too.

Frankly, the integrated console alone made New-VSCodeTask.ps1 somewhat obsolete.
Running build tasks there is easy, flexible (combination of tasks, parameters),
and handy for troubleshooting (debugging, post-mortem error analysis, etc.)

@daviwil
Copy link
Contributor Author

daviwil commented May 28, 2017

@nightroman In a tasks.json file, set the version field to "2.0.0", restart VS Code, then run a task which prints output that typically doesn't work in task output. The task will be run inside of an integrated terminal window so it should print everything out acceptably.

Thanks for the example on getting Invoke-Build tasks! You're right, just parsing the build script won't be good enough. I'm trying to avoid the need for module-specific task gathering code but I think there just might not be a way around it.

@nightroman
Copy link

@daviwil I tried "version": "0.2.0" (you probably mean this, not 2.0.0), the problem is still there.
The PS integrated console does not have this problem.

@daviwil
Copy link
Contributor Author

daviwil commented May 28, 2017

I definitely meant "2.0.0", I don't know why they jumped from "0.1.0" to "2.0.0" though :)

@nightroman
Copy link

Ah, at first I tried 2.0.0, it failed to start, so I thought it was a typo.

I tried again, this time I also changed the format of tasks.json (to be like
yours). It works now and the problem seems to be fixed, non-ASCII is shown fine.

There is one difference though, not sure if it is important or not.
The task I use for testing the output:

    task test {
        [Console]::OutputEncoding.CodePage
        "йцукен"
    }

When I run it as VSCode task:

    866
    йцукен

When I run it in the integrated console:

    65001
    йцукен

So "йцукен" is printed fine in cases (this is good). But the console
OutputEncoding is different. Maybe it is nothing to worry about...

@nightroman
Copy link

@daviwil

FWIW, I have updated New-VSCodeTask.

It uses the terminal 2.0.0, it does not need the work around output encoding,
and it is cross-platform (in theory, cannot test). The generated JSON file is
almost like your manually created tasks.json.

@daviwil
Copy link
Contributor Author

daviwil commented May 29, 2017

Looks like the default codepage in PowerShell is set to the one that's used by default on your system. For the Integrated Console I'm setting it to UTF-8 on purpose to avoid some issues that users have seen with characters in their language. I don't think there's anything to worry about there.

Thanks for updating your script, i'll have to give it a try!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Area-Tasks Issue-Enhancement A feature request (enhancement).
Projects
None yet
Development

No branches or pull requests

5 participants