mirror of
https://github.com/ckaczor/azuredatastudio.git
synced 2026-02-17 11:01:37 -05:00
Compare commits
306 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
216b6eecc0 | ||
|
|
c0917e9276 | ||
|
|
0bbcbf0d2d | ||
|
|
9b998e3fca | ||
|
|
d7d65cdf21 | ||
|
|
27925289d4 | ||
|
|
03ea265bab | ||
|
|
917f9eead3 | ||
|
|
08f2e72af8 | ||
|
|
a2fb0ec029 | ||
|
|
084042ad13 | ||
|
|
8da3defe24 | ||
|
|
58f9cd32a5 | ||
|
|
f7abf5a2d5 | ||
|
|
c8c6d072f6 | ||
|
|
4d9cc604b9 | ||
|
|
1dc76fa171 | ||
|
|
1d37b9ae9c | ||
|
|
26828602a8 | ||
|
|
e253f3ac89 | ||
|
|
4d59fdea1b | ||
|
|
98a313eb5b | ||
|
|
77e1cd8b32 | ||
|
|
dede5c5ef5 | ||
|
|
d156c0be3d | ||
|
|
dc0bc6e606 | ||
|
|
05040425df | ||
|
|
36f7c283b8 | ||
|
|
9fe4237033 | ||
|
|
b03c0a3e2d | ||
|
|
87946996ed | ||
|
|
cc55023440 | ||
|
|
1f19dfc50d | ||
|
|
950a440350 | ||
|
|
c92b88bfaf | ||
|
|
10875f26dc | ||
|
|
d62e809c18 | ||
|
|
d85bf4f6dd | ||
|
|
801e201cc3 | ||
|
|
e18e0da0c1 | ||
|
|
d046b0a412 | ||
|
|
72084b8fc1 | ||
|
|
2639b2bd2c | ||
|
|
82aa493dfd | ||
|
|
6c3c7c40b5 | ||
|
|
5616751c04 | ||
|
|
7d898ca34d | ||
|
|
e26556b21a | ||
|
|
89e6d363e2 | ||
|
|
c559ac7be9 | ||
|
|
b3fbe47f0a | ||
|
|
c73af4c480 | ||
|
|
8887fe1eac | ||
|
|
ed861a6c96 | ||
|
|
e63bb6a8ec | ||
|
|
8ec09d25ce | ||
|
|
a9a01ae479 | ||
|
|
31a3864789 | ||
|
|
a5c537197c | ||
|
|
4ea13bdbc0 | ||
|
|
b06ddf2dc7 | ||
|
|
2c45ac9df3 | ||
|
|
7735f68502 | ||
|
|
ffb0f5a1c7 | ||
|
|
80c7f9e855 | ||
|
|
709ef4e39f | ||
|
|
4ceb869420 | ||
|
|
432a209184 | ||
|
|
8444271c58 | ||
|
|
2bc97c23d4 | ||
|
|
9ea02bf125 | ||
|
|
2b4de52af4 | ||
|
|
d3492ebf2f | ||
|
|
ff8698f619 | ||
|
|
16bc218ea7 | ||
|
|
72d2920dc3 | ||
|
|
fb8de0d753 | ||
|
|
352afc9827 | ||
|
|
ce699a1c84 | ||
|
|
cde20d338e | ||
|
|
8ab22e9cc8 | ||
|
|
0f2442a7a5 | ||
|
|
ba91140ea5 | ||
|
|
10f05e75ce | ||
|
|
287811f4ab | ||
|
|
a68462c7cb | ||
|
|
005c28dd3a | ||
|
|
197e1c651f | ||
|
|
c01da0f263 | ||
|
|
81ff542d0b | ||
|
|
efee27559b | ||
|
|
dc5408f874 | ||
|
|
7cf9217158 | ||
|
|
401fc8161a | ||
|
|
be2f9a6099 | ||
|
|
21989aa88e | ||
|
|
461d041a50 | ||
|
|
de8662c52f | ||
|
|
0dbbbad370 | ||
|
|
2e05c0a7d9 | ||
|
|
f12f1cb392 | ||
|
|
b6891850a7 | ||
|
|
f147d799e0 | ||
|
|
534bbe9b9a | ||
|
|
b7f4f6af3a | ||
|
|
ac96919caf | ||
|
|
05cf06656d | ||
|
|
1356f0bcf6 | ||
|
|
ce0c955c29 | ||
|
|
0e7f89169e | ||
|
|
81329fa7fa | ||
|
|
3763278366 | ||
|
|
8600dbb04e | ||
|
|
b27f69aace | ||
|
|
8e0c19fc8d | ||
|
|
54ee1c23f0 | ||
|
|
39b33160c2 | ||
|
|
d94f86b44a | ||
|
|
4ae0daa17f | ||
|
|
8d548413bd | ||
|
|
f2e7a99b1e | ||
|
|
a8c31f68b3 | ||
|
|
db49b42e4a | ||
|
|
e77c2fc9bb | ||
|
|
5197ef591a | ||
|
|
898f8ec006 | ||
|
|
37ff96ba95 | ||
|
|
fa961832f3 | ||
|
|
b66ac2781c | ||
|
|
86a0f2d4a7 | ||
|
|
f5e2a67924 | ||
|
|
45cf626230 | ||
|
|
9717b7516d | ||
|
|
b92c23df2b | ||
|
|
df617f19e0 | ||
|
|
fb565c2548 | ||
|
|
2bfc3a6c85 | ||
|
|
4ab5d84b94 | ||
|
|
154213b705 | ||
|
|
4cce29ea9d | ||
|
|
9d5d00aa8f | ||
|
|
70d47c1757 | ||
|
|
befa34790f | ||
|
|
84da9d289b | ||
|
|
7a30d535e8 | ||
|
|
199701d26b | ||
|
|
3ac2cfa528 | ||
|
|
78d68aa1b9 | ||
|
|
8042b78f1e | ||
|
|
000d064276 | ||
|
|
600a78f35f | ||
|
|
6f5e4c30dc | ||
|
|
8e7457911e | ||
|
|
43b3207937 | ||
|
|
22f2151c21 | ||
|
|
7c744f2307 | ||
|
|
08d57fed86 | ||
|
|
6e8a0fe0ef | ||
|
|
6668ec4b5d | ||
|
|
08a8288293 | ||
|
|
3001640eec | ||
|
|
efa3658ced | ||
|
|
92bc253cf7 | ||
|
|
a190190843 | ||
|
|
9c40bd1a23 | ||
|
|
dc2193138d | ||
|
|
033c8cb8b1 | ||
|
|
21c4429c6e | ||
|
|
348a96b033 | ||
|
|
0c930d7c0f | ||
|
|
98aca2b988 | ||
|
|
8d7f497e0c | ||
|
|
1b6328b451 | ||
|
|
d10e08e63e | ||
|
|
a8f21b56f0 | ||
|
|
173842510c | ||
|
|
19c08fe0eb | ||
|
|
db817a7192 | ||
|
|
2c8e93cc96 | ||
|
|
44e9a97f09 | ||
|
|
298ddc4195 | ||
|
|
d9134d6085 | ||
|
|
b17b4ce880 | ||
|
|
2304c32453 | ||
|
|
2b68e4a7df | ||
|
|
8f06e72318 | ||
|
|
5fa740ead4 | ||
|
|
e5096e61e5 | ||
|
|
2a3195636e | ||
|
|
5fb9b8ccd3 | ||
|
|
7089e2299a | ||
|
|
b553cbb68c | ||
|
|
c712411e77 | ||
|
|
48d5cc554c | ||
|
|
39bfd69dc9 | ||
|
|
d690b80493 | ||
|
|
eb48a9f993 | ||
|
|
5a54abaf44 | ||
|
|
47c161f9f1 | ||
|
|
807f8e68f3 | ||
|
|
fba8536c33 | ||
|
|
36fc1bb71a | ||
|
|
ccaa96c81e | ||
|
|
ac2f279c88 | ||
|
|
91cb99b8c8 | ||
|
|
02b1a525e3 | ||
|
|
9bf4a4b18c | ||
|
|
8a01553c49 | ||
|
|
21b913845f | ||
|
|
220e4feb1d | ||
|
|
13884c0457 | ||
|
|
b3bb6ebc6e | ||
|
|
424eb90dd8 | ||
|
|
df804d0729 | ||
|
|
79269cdfd5 | ||
|
|
2a650d4d74 | ||
|
|
017b4ecdb3 | ||
|
|
9c84bf3fd5 | ||
|
|
397b54a8c3 | ||
|
|
cb3604c0a1 | ||
|
|
1a7f0673ea | ||
|
|
0d043207b9 | ||
|
|
f995dea971 | ||
|
|
49e20488bc | ||
|
|
3e47b27192 | ||
|
|
f4fa18ec05 | ||
|
|
c6d1fa2b7d | ||
|
|
c4df7667ff | ||
|
|
6a303cfa25 | ||
|
|
4ffa5cc1da | ||
|
|
172e1cf3bf | ||
|
|
e6a32e52f5 | ||
|
|
d2b6f6844d | ||
|
|
e9ef95ef1f | ||
|
|
10eeb5374f | ||
|
|
332951bc8e | ||
|
|
4daf3280ff | ||
|
|
87bb2c74d9 | ||
|
|
ba011853a0 | ||
|
|
461a158ac3 | ||
|
|
85f59f1103 | ||
|
|
335b9f445f | ||
|
|
7cda45c904 | ||
|
|
4159fdc1a3 | ||
|
|
190da30979 | ||
|
|
ed9c74b900 | ||
|
|
6783766c33 | ||
|
|
b27018b379 | ||
|
|
021d07e04a | ||
|
|
bf0baec392 | ||
|
|
923cbac400 | ||
|
|
ab938f2536 | ||
|
|
a55b1804e9 | ||
|
|
4bfa6b3a5d | ||
|
|
d20f24be18 | ||
|
|
8a17bae7a6 | ||
|
|
d14c73fad5 | ||
|
|
ce878e1def | ||
|
|
a64a0d1db6 | ||
|
|
feab43f16d | ||
|
|
0d60fe775f | ||
|
|
6680be6a73 | ||
|
|
e026ab85a7 | ||
|
|
e53c903205 | ||
|
|
03dbe8565f | ||
|
|
708793cb23 | ||
|
|
43ae4fb0aa | ||
|
|
6b1d552277 | ||
|
|
f24f576b72 | ||
|
|
c23328564f | ||
|
|
cd6dd3dafa | ||
|
|
4081e15bef | ||
|
|
b05e3813d1 | ||
|
|
3048311f40 | ||
|
|
1045392d91 | ||
|
|
7b23ca8ee7 | ||
|
|
4d67eca8bb | ||
|
|
74c4b7311e | ||
|
|
713c74adfd | ||
|
|
408a8a6f19 | ||
|
|
e1485e49d3 | ||
|
|
30b66934cd | ||
|
|
fd49c081c2 | ||
|
|
1327120024 | ||
|
|
d2b5043972 | ||
|
|
a0e55ea3fd | ||
|
|
1f32de29c1 | ||
|
|
12be06d682 | ||
|
|
27ca9b13f8 | ||
|
|
be45905830 | ||
|
|
05d0a89655 | ||
|
|
3ba575dcd0 | ||
|
|
3e200b7f0f | ||
|
|
cbce1f7008 | ||
|
|
e99101447e | ||
|
|
0ddb326e44 | ||
|
|
460446a15c | ||
|
|
4eea24997f | ||
|
|
0b1e9c7c66 | ||
|
|
d51a7a9eb7 | ||
|
|
0f0b959e14 | ||
|
|
b2ceb09e4d | ||
|
|
53953f5cda | ||
|
|
fbd5e819a2 | ||
|
|
bdc391d376 | ||
|
|
6b618fb121 |
14
.github/ISSUE_TEMPLATE/bug_report.md
vendored
Normal file
14
.github/ISSUE_TEMPLATE/bug_report.md
vendored
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
---
|
||||||
|
name: Bug report
|
||||||
|
about: Create a report to help us improve
|
||||||
|
---
|
||||||
|
|
||||||
|
<!-- Please search existing issues to avoid creating duplicates. -->
|
||||||
|
<!-- Also please test using the latest insiders build to make sure your issue has not already been fixed. -->
|
||||||
|
|
||||||
|
<!-- Use Help > Report Issue to prefill these. -->
|
||||||
|
- SQL Operations Studio Version:
|
||||||
|
|
||||||
|
Steps to Reproduce:
|
||||||
|
|
||||||
|
1.
|
||||||
3
.gitignore
vendored
3
.gitignore
vendored
@@ -6,6 +6,8 @@ node_modules/
|
|||||||
out/
|
out/
|
||||||
out-build/
|
out-build/
|
||||||
out-editor/
|
out-editor/
|
||||||
|
out-editor-src/
|
||||||
|
out-editor-build/
|
||||||
out-editor-esm/
|
out-editor-esm/
|
||||||
out-editor-min/
|
out-editor-min/
|
||||||
out-monaco-editor-core/
|
out-monaco-editor-core/
|
||||||
@@ -14,4 +16,5 @@ out-vscode-min/
|
|||||||
build/node_modules
|
build/node_modules
|
||||||
coverage/
|
coverage/
|
||||||
test_data/
|
test_data/
|
||||||
|
test-results/
|
||||||
yarn-error.log
|
yarn-error.log
|
||||||
17
.vscode/launch.json
vendored
17
.vscode/launch.json
vendored
@@ -106,6 +106,7 @@
|
|||||||
"runtimeExecutable": "${workspaceFolder}/.build/electron/sqlops"
|
"runtimeExecutable": "${workspaceFolder}/.build/electron/sqlops"
|
||||||
},
|
},
|
||||||
"stopOnEntry": false,
|
"stopOnEntry": false,
|
||||||
|
"outputCapture": "std",
|
||||||
"args": [
|
"args": [
|
||||||
"--delay",
|
"--delay",
|
||||||
"--timeout",
|
"--timeout",
|
||||||
@@ -118,6 +119,15 @@
|
|||||||
"outFiles": [
|
"outFiles": [
|
||||||
"${workspaceFolder}/out/**/*.js"
|
"${workspaceFolder}/out/**/*.js"
|
||||||
]
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Launch Built-in Extension",
|
||||||
|
"type": "extensionHost",
|
||||||
|
"request": "launch",
|
||||||
|
"runtimeExecutable": "${execPath}",
|
||||||
|
"args": [
|
||||||
|
"--extensionDevelopmentPath=${workspaceRoot}/extensions/debug-auto-launch"
|
||||||
|
]
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"compounds": [
|
"compounds": [
|
||||||
@@ -134,6 +144,13 @@
|
|||||||
"Launch sqlops",
|
"Launch sqlops",
|
||||||
"Attach to Search Process"
|
"Attach to Search Process"
|
||||||
]
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Renderer and Extension Host processes",
|
||||||
|
"configurations": [
|
||||||
|
"Launch SQL Ops",
|
||||||
|
"Attach to Extension Host"
|
||||||
|
]
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
7
.vscode/settings.json
vendored
7
.vscode/settings.json
vendored
@@ -39,5 +39,10 @@
|
|||||||
}
|
}
|
||||||
],
|
],
|
||||||
"typescript.tsdk": "node_modules/typescript/lib",
|
"typescript.tsdk": "node_modules/typescript/lib",
|
||||||
"git.ignoreLimitWarning": true
|
"npm.exclude": "**/extensions/**",
|
||||||
|
"git.ignoreLimitWarning": true,
|
||||||
|
"emmet.excludeLanguages": [],
|
||||||
|
"typescript.preferences.importModuleSpecifier": "non-relative",
|
||||||
|
"typescript.preferences.quoteStyle": "single"
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
2
.yarnrc
2
.yarnrc
@@ -1,3 +1,3 @@
|
|||||||
disturl "https://atom.io/download/electron"
|
disturl "https://atom.io/download/electron"
|
||||||
target "1.7.12"
|
target "2.0.9"
|
||||||
runtime "electron"
|
runtime "electron"
|
||||||
|
|||||||
47
CHANGELOG.md
47
CHANGELOG.md
@@ -1,5 +1,52 @@
|
|||||||
# Change Log
|
# Change Log
|
||||||
|
|
||||||
|
## Version 0.33.7
|
||||||
|
* Release date: August 30, 2018
|
||||||
|
* Release status: Public Preview
|
||||||
|
|
||||||
|
## What's new in this version
|
||||||
|
* Announcing the SQL Server Import Extension
|
||||||
|
* SQL Server Profiler Session management
|
||||||
|
* SQL Server Agent improvements
|
||||||
|
* New community extension: First Responder Kit
|
||||||
|
* Quality of Life improvements: Connection strings
|
||||||
|
* Fix many customer reported GitHub issues
|
||||||
|
|
||||||
|
## Contributions and "thank you"
|
||||||
|
We would like to thank all our users who raised issues, and in particular the following users who helped contribute fixes:
|
||||||
|
|
||||||
|
* SebastianPfliegel `Added more saveAsCsv options #2099`
|
||||||
|
* ianychoi `Fixes a typo: Mimunum -> Minimum #1994`
|
||||||
|
* AlexFsmn `Fixed bug where proper file extension wasn't appended to filename. #2151`
|
||||||
|
* AlexFsmn `Added functionality for adding any file to import wizard #2329`
|
||||||
|
* AlexFsmn `Fixed background issue when copying a chart to clipboard #2215`
|
||||||
|
* AlexFsmn `Fixed problem where vertical charts didn't display labels correctly. #2263`
|
||||||
|
* AlexFsmn `Fixed Initial values for charts to match visuals #2266`
|
||||||
|
* AlexFsmn `Renamed chart option labels #2264`
|
||||||
|
* AlexFsmn `Added feature for opening file after exporting to CSV/XLS/JSON & query files #2216`
|
||||||
|
* AlexFsmm `Get Connection String should copy to clipboard #2175`
|
||||||
|
|
||||||
|
## Version 0.31.4
|
||||||
|
* Release date: July 19, 2018
|
||||||
|
* Release status: Public Preview
|
||||||
|
|
||||||
|
## What's new in this version
|
||||||
|
* SQL Server Agent for SQL Operations Studio extension improvements
|
||||||
|
* Added view of Alerts, Operators, and Proxies and icons on left pane
|
||||||
|
* Added dialogs for New Job, New Job Step, New Alert, and New Operator
|
||||||
|
* Added Delete Job, Delete Alert, and Delete Operator (right-click)
|
||||||
|
* Added Previous Runs visualization
|
||||||
|
* Added Filters for each column name
|
||||||
|
* SQL Server Profiler for SQL Operations Studio extension improvements
|
||||||
|
* Added Hotkeys to quickly launch and start/stop Profiler
|
||||||
|
* Added 5 Default Templates to view Extended Events
|
||||||
|
* Added Server/Database connection name
|
||||||
|
* Added support for Azure SQL Database instances
|
||||||
|
* Added suggestion to exit Profiler when tab is closed when Profiler is still running
|
||||||
|
* Release of Combine Scripts Extension
|
||||||
|
* Wizard and Dialog Extensibility
|
||||||
|
* Fix GitHub Issues
|
||||||
|
|
||||||
## Version 0.30.6
|
## Version 0.30.6
|
||||||
* Release date: June 20, 2018
|
* Release date: June 20, 2018
|
||||||
* Release status: Public Preview
|
* Release status: Public Preview
|
||||||
|
|||||||
@@ -5,9 +5,9 @@ First, please do a search in [open issues](https://github.com/Microsoft/sqlopsst
|
|||||||
|
|
||||||
If you find your issue already exists, make relevant comments and add your [reaction](https://github.com/blog/2119-add-reactions-to-pull-requests-issues-and-comments). Use a reaction in place of a "+1" comment.
|
If you find your issue already exists, make relevant comments and add your [reaction](https://github.com/blog/2119-add-reactions-to-pull-requests-issues-and-comments). Use a reaction in place of a "+1" comment.
|
||||||
|
|
||||||
👍 - upvote
|
<EFBFBD> - upvote
|
||||||
|
|
||||||
👎 - downvote
|
<EFBFBD> - downvote
|
||||||
|
|
||||||
If you cannot find an existing issue that describes your bug or feature, submit an issue using the guidelines below.
|
If you cannot find an existing issue that describes your bug or feature, submit an issue using the guidelines below.
|
||||||
|
|
||||||
|
|||||||
563
OSSREADME.json
563
OSSREADME.json
@@ -62,7 +62,7 @@
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "chromium",
|
"name": "chromium",
|
||||||
"version": "58.0.3029.110",
|
"version": "61.0.3163.100",
|
||||||
"repositoryURL": "http://www.chromium.org/Home",
|
"repositoryURL": "http://www.chromium.org/Home",
|
||||||
"licenseDetail": [
|
"licenseDetail": [
|
||||||
"BSD License",
|
"BSD License",
|
||||||
@@ -98,20 +98,20 @@
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "libchromiumcontent",
|
"name": "libchromiumcontent",
|
||||||
"version": "58.0.3029.110",
|
"version": "61.0.3163.100",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"repositoryURL": "https://github.com/electron/libchromiumcontent",
|
"repositoryURL": "https://github.com/electron/libchromiumcontent",
|
||||||
"isProd": true
|
"isProd": true
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "nodejs",
|
"name": "nodejs",
|
||||||
"version": "7.9.0",
|
"version": "8.9.3",
|
||||||
"repositoryURL": "https://github.com/nodejs/node",
|
"repositoryURL": "https://github.com/nodejs/node",
|
||||||
"isProd": true
|
"isProd": true
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "electron",
|
"name": "electron",
|
||||||
"version": "1.7.3",
|
"version": "2.0.5",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"repositoryURL": "https://github.com/electron/electron",
|
"repositoryURL": "https://github.com/electron/electron",
|
||||||
"isProd": true
|
"isProd": true
|
||||||
@@ -1192,5 +1192,560 @@
|
|||||||
" This Source Code Form is \"Incompatible With Secondary Licenses\", as",
|
" This Source Code Form is \"Incompatible With Secondary Licenses\", as",
|
||||||
" defined by the Mozilla Public License, v. 2.0."
|
" defined by the Mozilla Public License, v. 2.0."
|
||||||
]
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "mdn-data",
|
||||||
|
"version": "1.1.12",
|
||||||
|
"repositoryURL": "https://github.com/mdn/data",
|
||||||
|
"license": "MPL",
|
||||||
|
"licenseDetail": [
|
||||||
|
"Mozilla Public License Version 2.0",
|
||||||
|
"",
|
||||||
|
"Copyright (c) 2018 Mozilla Corporation",
|
||||||
|
"",
|
||||||
|
"==================================",
|
||||||
|
"",
|
||||||
|
"1. Definitions",
|
||||||
|
"--------------",
|
||||||
|
"",
|
||||||
|
"1.1. \"Contributor\"",
|
||||||
|
" means each individual or legal entity that creates, contributes to",
|
||||||
|
" the creation of, or owns Covered Software.",
|
||||||
|
"",
|
||||||
|
"1.2. \"Contributor Version\"",
|
||||||
|
" means the combination of the Contributions of others (if any) used",
|
||||||
|
" by a Contributor and that particular Contributor's Contribution.",
|
||||||
|
"",
|
||||||
|
"1.3. \"Contribution\"",
|
||||||
|
" means Covered Software of a particular Contributor.",
|
||||||
|
"",
|
||||||
|
"1.4. \"Covered Software\"",
|
||||||
|
" means Source Code Form to which the initial Contributor has attached",
|
||||||
|
" the notice in Exhibit A, the Executable Form of such Source Code",
|
||||||
|
" Form, and Modifications of such Source Code Form, in each case",
|
||||||
|
" including portions thereof.",
|
||||||
|
"",
|
||||||
|
"1.5. \"Incompatible With Secondary Licenses\"",
|
||||||
|
" means",
|
||||||
|
"",
|
||||||
|
" (a) that the initial Contributor has attached the notice described",
|
||||||
|
" in Exhibit B to the Covered Software; or",
|
||||||
|
"",
|
||||||
|
" (b) that the Covered Software was made available under the terms of",
|
||||||
|
" version 1.1 or earlier of the License, but not also under the",
|
||||||
|
" terms of a Secondary License.",
|
||||||
|
"",
|
||||||
|
"1.6. \"Executable Form\"",
|
||||||
|
" means any form of the work other than Source Code Form.",
|
||||||
|
"",
|
||||||
|
"1.7. \"Larger Work\"",
|
||||||
|
" means a work that combines Covered Software with other material, in",
|
||||||
|
" a separate file or files, that is not Covered Software.",
|
||||||
|
"",
|
||||||
|
"1.8. \"License\"",
|
||||||
|
" means this document.",
|
||||||
|
"",
|
||||||
|
"1.9. \"Licensable\"",
|
||||||
|
" means having the right to grant, to the maximum extent possible,",
|
||||||
|
" whether at the time of the initial grant or subsequently, any and",
|
||||||
|
" all of the rights conveyed by this License.",
|
||||||
|
"",
|
||||||
|
"1.10. \"Modifications\"",
|
||||||
|
" means any of the following:",
|
||||||
|
"",
|
||||||
|
" (a) any file in Source Code Form that results from an addition to,",
|
||||||
|
" deletion from, or modification of the contents of Covered",
|
||||||
|
" Software; or",
|
||||||
|
"",
|
||||||
|
" (b) any new file in Source Code Form that contains any Covered",
|
||||||
|
" Software.",
|
||||||
|
"",
|
||||||
|
"1.11. \"Patent Claims\" of a Contributor",
|
||||||
|
" means any patent claim(s), including without limitation, method,",
|
||||||
|
" process, and apparatus claims, in any patent Licensable by such",
|
||||||
|
" Contributor that would be infringed, but for the grant of the",
|
||||||
|
" License, by the making, using, selling, offering for sale, having",
|
||||||
|
" made, import, or transfer of either its Contributions or its",
|
||||||
|
" Contributor Version.",
|
||||||
|
"",
|
||||||
|
"1.12. \"Secondary License\"",
|
||||||
|
" means either the GNU General Public License, Version 2.0, the GNU",
|
||||||
|
" Lesser General Public License, Version 2.1, the GNU Affero General",
|
||||||
|
" Public License, Version 3.0, or any later versions of those",
|
||||||
|
" licenses.",
|
||||||
|
"",
|
||||||
|
"1.13. \"Source Code Form\"",
|
||||||
|
" means the form of the work preferred for making modifications.",
|
||||||
|
"",
|
||||||
|
"1.14. \"You\" (or \"Your\")",
|
||||||
|
" means an individual or a legal entity exercising rights under this",
|
||||||
|
" License. For legal entities, \"You\" includes any entity that",
|
||||||
|
" controls, is controlled by, or is under common control with You. For",
|
||||||
|
" purposes of this definition, \"control\" means (a) the power, direct",
|
||||||
|
" or indirect, to cause the direction or management of such entity,",
|
||||||
|
" whether by contract or otherwise, or (b) ownership of more than",
|
||||||
|
" fifty percent (50%) of the outstanding shares or beneficial",
|
||||||
|
" ownership of such entity.",
|
||||||
|
"",
|
||||||
|
"2. License Grants and Conditions",
|
||||||
|
"--------------------------------",
|
||||||
|
"",
|
||||||
|
"2.1. Grants",
|
||||||
|
"",
|
||||||
|
"Each Contributor hereby grants You a world-wide, royalty-free,",
|
||||||
|
"non-exclusive license:",
|
||||||
|
"",
|
||||||
|
"(a) under intellectual property rights (other than patent or trademark)",
|
||||||
|
" Licensable by such Contributor to use, reproduce, make available,",
|
||||||
|
" modify, display, perform, distribute, and otherwise exploit its",
|
||||||
|
" Contributions, either on an unmodified basis, with Modifications, or",
|
||||||
|
" as part of a Larger Work; and",
|
||||||
|
"",
|
||||||
|
"(b) under Patent Claims of such Contributor to make, use, sell, offer",
|
||||||
|
" for sale, have made, import, and otherwise transfer either its",
|
||||||
|
" Contributions or its Contributor Version.",
|
||||||
|
"",
|
||||||
|
"2.2. Effective Date",
|
||||||
|
"",
|
||||||
|
"The licenses granted in Section 2.1 with respect to any Contribution",
|
||||||
|
"become effective for each Contribution on the date the Contributor first",
|
||||||
|
"distributes such Contribution.",
|
||||||
|
"",
|
||||||
|
"2.3. Limitations on Grant Scope",
|
||||||
|
"",
|
||||||
|
"The licenses granted in this Section 2 are the only rights granted under",
|
||||||
|
"this License. No additional rights or licenses will be implied from the",
|
||||||
|
"distribution or licensing of Covered Software under this License.",
|
||||||
|
"Notwithstanding Section 2.1(b) above, no patent license is granted by a",
|
||||||
|
"Contributor:",
|
||||||
|
"",
|
||||||
|
"(a) for any code that a Contributor has removed from Covered Software;",
|
||||||
|
" or",
|
||||||
|
"",
|
||||||
|
"(b) for infringements caused by: (i) Your and any other third party's",
|
||||||
|
" modifications of Covered Software, or (ii) the combination of its",
|
||||||
|
" Contributions with other software (except as part of its Contributor",
|
||||||
|
" Version); or",
|
||||||
|
"",
|
||||||
|
"(c) under Patent Claims infringed by Covered Software in the absence of",
|
||||||
|
" its Contributions.",
|
||||||
|
"",
|
||||||
|
"This License does not grant any rights in the trademarks, service marks,",
|
||||||
|
"or logos of any Contributor (except as may be necessary to comply with",
|
||||||
|
"the notice requirements in Section 3.4).",
|
||||||
|
"",
|
||||||
|
"2.4. Subsequent Licenses",
|
||||||
|
"",
|
||||||
|
"No Contributor makes additional grants as a result of Your choice to",
|
||||||
|
"distribute the Covered Software under a subsequent version of this",
|
||||||
|
"License (see Section 10.2) or under the terms of a Secondary License (if",
|
||||||
|
"permitted under the terms of Section 3.3).",
|
||||||
|
"",
|
||||||
|
"2.5. Representation",
|
||||||
|
"",
|
||||||
|
"Each Contributor represents that the Contributor believes its",
|
||||||
|
"Contributions are its original creation(s) or it has sufficient rights",
|
||||||
|
"to grant the rights to its Contributions conveyed by this License.",
|
||||||
|
"",
|
||||||
|
"2.6. Fair Use",
|
||||||
|
"",
|
||||||
|
"This License is not intended to limit any rights You have under",
|
||||||
|
"applicable copyright doctrines of fair use, fair dealing, or other",
|
||||||
|
"equivalents.",
|
||||||
|
"",
|
||||||
|
"2.7. Conditions",
|
||||||
|
"",
|
||||||
|
"Sections 3.1, 3.2, 3.3, and 3.4 are conditions of the licenses granted",
|
||||||
|
"in Section 2.1.",
|
||||||
|
"",
|
||||||
|
"3. Responsibilities",
|
||||||
|
"-------------------",
|
||||||
|
"",
|
||||||
|
"3.1. Distribution of Source Form",
|
||||||
|
"",
|
||||||
|
"All distribution of Covered Software in Source Code Form, including any",
|
||||||
|
"Modifications that You create or to which You contribute, must be under",
|
||||||
|
"the terms of this License. You must inform recipients that the Source",
|
||||||
|
"Code Form of the Covered Software is governed by the terms of this",
|
||||||
|
"License, and how they can obtain a copy of this License. You may not",
|
||||||
|
"attempt to alter or restrict the recipients' rights in the Source Code",
|
||||||
|
"Form.",
|
||||||
|
"",
|
||||||
|
"3.2. Distribution of Executable Form",
|
||||||
|
"",
|
||||||
|
"If You distribute Covered Software in Executable Form then:",
|
||||||
|
"",
|
||||||
|
"(a) such Covered Software must also be made available in Source Code",
|
||||||
|
" Form, as described in Section 3.1, and You must inform recipients of",
|
||||||
|
" the Executable Form how they can obtain a copy of such Source Code",
|
||||||
|
" Form by reasonable means in a timely manner, at a charge no more",
|
||||||
|
" than the cost of distribution to the recipient; and",
|
||||||
|
"",
|
||||||
|
"(b) You may distribute such Executable Form under the terms of this",
|
||||||
|
" License, or sublicense it under different terms, provided that the",
|
||||||
|
" license for the Executable Form does not attempt to limit or alter",
|
||||||
|
" the recipients' rights in the Source Code Form under this License.",
|
||||||
|
"",
|
||||||
|
"3.3. Distribution of a Larger Work",
|
||||||
|
"",
|
||||||
|
"You may create and distribute a Larger Work under terms of Your choice,",
|
||||||
|
"provided that You also comply with the requirements of this License for",
|
||||||
|
"the Covered Software. If the Larger Work is a combination of Covered",
|
||||||
|
"Software with a work governed by one or more Secondary Licenses, and the",
|
||||||
|
"Covered Software is not Incompatible With Secondary Licenses, this",
|
||||||
|
"License permits You to additionally distribute such Covered Software",
|
||||||
|
"under the terms of such Secondary License(s), so that the recipient of",
|
||||||
|
"the Larger Work may, at their option, further distribute the Covered",
|
||||||
|
"Software under the terms of either this License or such Secondary",
|
||||||
|
"License(s).",
|
||||||
|
"",
|
||||||
|
"3.4. Notices",
|
||||||
|
"",
|
||||||
|
"You may not remove or alter the substance of any license notices",
|
||||||
|
"(including copyright notices, patent notices, disclaimers of warranty,",
|
||||||
|
"or limitations of liability) contained within the Source Code Form of",
|
||||||
|
"the Covered Software, except that You may alter any license notices to",
|
||||||
|
"the extent required to remedy known factual inaccuracies.",
|
||||||
|
"",
|
||||||
|
"3.5. Application of Additional Terms",
|
||||||
|
"",
|
||||||
|
"You may choose to offer, and to charge a fee for, warranty, support,",
|
||||||
|
"indemnity or liability obligations to one or more recipients of Covered",
|
||||||
|
"Software. However, You may do so only on Your own behalf, and not on",
|
||||||
|
"behalf of any Contributor. You must make it absolutely clear that any",
|
||||||
|
"such warranty, support, indemnity, or liability obligation is offered by",
|
||||||
|
"You alone, and You hereby agree to indemnify every Contributor for any",
|
||||||
|
"liability incurred by such Contributor as a result of warranty, support,",
|
||||||
|
"indemnity or liability terms You offer. You may include additional",
|
||||||
|
"disclaimers of warranty and limitations of liability specific to any",
|
||||||
|
"jurisdiction.",
|
||||||
|
"",
|
||||||
|
"4. Inability to Comply Due to Statute or Regulation",
|
||||||
|
"---------------------------------------------------",
|
||||||
|
"",
|
||||||
|
"If it is impossible for You to comply with any of the terms of this",
|
||||||
|
"License with respect to some or all of the Covered Software due to",
|
||||||
|
"statute, judicial order, or regulation then You must: (a) comply with",
|
||||||
|
"the terms of this License to the maximum extent possible; and (b)",
|
||||||
|
"describe the limitations and the code they affect. Such description must",
|
||||||
|
"be placed in a text file included with all distributions of the Covered",
|
||||||
|
"Software under this License. Except to the extent prohibited by statute",
|
||||||
|
"or regulation, such description must be sufficiently detailed for a",
|
||||||
|
"recipient of ordinary skill to be able to understand it.",
|
||||||
|
"",
|
||||||
|
"5. Termination",
|
||||||
|
"--------------",
|
||||||
|
"",
|
||||||
|
"5.1. The rights granted under this License will terminate automatically",
|
||||||
|
"if You fail to comply with any of its terms. However, if You become",
|
||||||
|
"compliant, then the rights granted under this License from a particular",
|
||||||
|
"Contributor are reinstated (a) provisionally, unless and until such",
|
||||||
|
"Contributor explicitly and finally terminates Your grants, and (b) on an",
|
||||||
|
"ongoing basis, if such Contributor fails to notify You of the",
|
||||||
|
"non-compliance by some reasonable means prior to 60 days after You have",
|
||||||
|
"come back into compliance. Moreover, Your grants from a particular",
|
||||||
|
"Contributor are reinstated on an ongoing basis if such Contributor",
|
||||||
|
"notifies You of the non-compliance by some reasonable means, this is the",
|
||||||
|
"first time You have received notice of non-compliance with this License",
|
||||||
|
"from such Contributor, and You become compliant prior to 30 days after",
|
||||||
|
"Your receipt of the notice.",
|
||||||
|
"",
|
||||||
|
"5.2. If You initiate litigation against any entity by asserting a patent",
|
||||||
|
"infringement claim (excluding declaratory judgment actions,",
|
||||||
|
"counter-claims, and cross-claims) alleging that a Contributor Version",
|
||||||
|
"directly or indirectly infringes any patent, then the rights granted to",
|
||||||
|
"You by any and all Contributors for the Covered Software under Section",
|
||||||
|
"2.1 of this License shall terminate.",
|
||||||
|
"",
|
||||||
|
"5.3. In the event of termination under Sections 5.1 or 5.2 above, all",
|
||||||
|
"end user license agreements (excluding distributors and resellers) which",
|
||||||
|
"have been validly granted by You or Your distributors under this License",
|
||||||
|
"prior to termination shall survive termination.",
|
||||||
|
"",
|
||||||
|
"************************************************************************",
|
||||||
|
"* *",
|
||||||
|
"* 6. Disclaimer of Warranty *",
|
||||||
|
"* ------------------------- *",
|
||||||
|
"* *",
|
||||||
|
"* Covered Software is provided under this License on an \"as is\" *",
|
||||||
|
"* basis, without warranty of any kind, either expressed, implied, or *",
|
||||||
|
"* statutory, including, without limitation, warranties that the *",
|
||||||
|
"* Covered Software is free of defects, merchantable, fit for a *",
|
||||||
|
"* particular purpose or non-infringing. The entire risk as to the *",
|
||||||
|
"* quality and performance of the Covered Software is with You. *",
|
||||||
|
"* Should any Covered Software prove defective in any respect, You *",
|
||||||
|
"* (not any Contributor) assume the cost of any necessary servicing, *",
|
||||||
|
"* repair, or correction. This disclaimer of warranty constitutes an *",
|
||||||
|
"* essential part of this License. No use of any Covered Software is *",
|
||||||
|
"* authorized under this License except under this disclaimer. *",
|
||||||
|
"* *",
|
||||||
|
"************************************************************************",
|
||||||
|
"",
|
||||||
|
"************************************************************************",
|
||||||
|
"* *",
|
||||||
|
"* 7. Limitation of Liability *",
|
||||||
|
"* -------------------------- *",
|
||||||
|
"* *",
|
||||||
|
"* Under no circumstances and under no legal theory, whether tort *",
|
||||||
|
"* (including negligence), contract, or otherwise, shall any *",
|
||||||
|
"* Contributor, or anyone who distributes Covered Software as *",
|
||||||
|
"* permitted above, be liable to You for any direct, indirect, *",
|
||||||
|
"* special, incidental, or consequential damages of any character *",
|
||||||
|
"* including, without limitation, damages for lost profits, loss of *",
|
||||||
|
"* goodwill, work stoppage, computer failure or malfunction, or any *",
|
||||||
|
"* and all other commercial damages or losses, even if such party *",
|
||||||
|
"* shall have been informed of the possibility of such damages. This *",
|
||||||
|
"* limitation of liability shall not apply to liability for death or *",
|
||||||
|
"* personal injury resulting from such party's negligence to the *",
|
||||||
|
"* extent applicable law prohibits such limitation. Some *",
|
||||||
|
"* jurisdictions do not allow the exclusion or limitation of *",
|
||||||
|
"* incidental or consequential damages, so this exclusion and *",
|
||||||
|
"* limitation may not apply to You. *",
|
||||||
|
"* *",
|
||||||
|
"************************************************************************",
|
||||||
|
"",
|
||||||
|
"8. Litigation",
|
||||||
|
"-------------",
|
||||||
|
"",
|
||||||
|
"Any litigation relating to this License may be brought only in the",
|
||||||
|
"courts of a jurisdiction where the defendant maintains its principal",
|
||||||
|
"place of business and such litigation shall be governed by laws of that",
|
||||||
|
"jurisdiction, without reference to its conflict-of-law provisions.",
|
||||||
|
"Nothing in this Section shall prevent a party's ability to bring",
|
||||||
|
"cross-claims or counter-claims.",
|
||||||
|
"",
|
||||||
|
"9. Miscellaneous",
|
||||||
|
"----------------",
|
||||||
|
"",
|
||||||
|
"This License represents the complete agreement concerning the subject",
|
||||||
|
"matter hereof. If any provision of this License is held to be",
|
||||||
|
"unenforceable, such provision shall be reformed only to the extent",
|
||||||
|
"necessary to make it enforceable. Any law or regulation which provides",
|
||||||
|
"that the language of a contract shall be construed against the drafter",
|
||||||
|
"shall not be used to construe this License against a Contributor.",
|
||||||
|
"",
|
||||||
|
"10. Versions of the License",
|
||||||
|
"---------------------------",
|
||||||
|
"",
|
||||||
|
"10.1. New Versions",
|
||||||
|
"",
|
||||||
|
"Mozilla Foundation is the license steward. Except as provided in Section",
|
||||||
|
"10.3, no one other than the license steward has the right to modify or",
|
||||||
|
"publish new versions of this License. Each version will be given a",
|
||||||
|
"distinguishing version number.",
|
||||||
|
"",
|
||||||
|
"10.2. Effect of New Versions",
|
||||||
|
"",
|
||||||
|
"You may distribute the Covered Software under the terms of the version",
|
||||||
|
"of the License under which You originally received the Covered Software,",
|
||||||
|
"or under the terms of any subsequent version published by the license",
|
||||||
|
"steward.",
|
||||||
|
"",
|
||||||
|
"10.3. Modified Versions",
|
||||||
|
"",
|
||||||
|
"If you create software not governed by this License, and you want to",
|
||||||
|
"create a new license for such software, you may create and use a",
|
||||||
|
"modified version of this License if you rename the license and remove",
|
||||||
|
"any references to the name of the license steward (except to note that",
|
||||||
|
"such modified license differs from this License).",
|
||||||
|
"",
|
||||||
|
"10.4. Distributing Source Code Form that is Incompatible With Secondary",
|
||||||
|
"Licenses",
|
||||||
|
"",
|
||||||
|
"If You choose to distribute Source Code Form that is Incompatible With",
|
||||||
|
"Secondary Licenses under the terms of this version of the License, the",
|
||||||
|
"notice described in Exhibit B of this License must be attached.",
|
||||||
|
"",
|
||||||
|
"Exhibit A - Source Code Form License Notice",
|
||||||
|
"-------------------------------------------",
|
||||||
|
"",
|
||||||
|
" This Source Code Form is subject to the terms of the Mozilla Public",
|
||||||
|
" License, v. 2.0. If a copy of the MPL was not distributed with this",
|
||||||
|
" file, You can obtain one at http://mozilla.org/MPL/2.0/.",
|
||||||
|
"",
|
||||||
|
"If it is not possible or desirable to put the notice in a particular",
|
||||||
|
"file, then You may include the notice in a location (such as a LICENSE",
|
||||||
|
"file in a relevant directory) where a recipient would be likely to look",
|
||||||
|
"for such a notice.",
|
||||||
|
"",
|
||||||
|
"You may add additional accurate notices of copyright ownership.",
|
||||||
|
"",
|
||||||
|
"Exhibit B - \"Incompatible With Secondary Licenses\" Notice",
|
||||||
|
"---------------------------------------------------------",
|
||||||
|
"",
|
||||||
|
" This Source Code Form is \"Incompatible With Secondary Licenses\", as",
|
||||||
|
" defined by the Mozilla Public License, v. 2.0."
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"isLicense": true,
|
||||||
|
"name": "devtools-protocol",
|
||||||
|
"licenseDetail": [
|
||||||
|
" Copyright 2015 The Chromium Authors. All rights reserved.",
|
||||||
|
"",
|
||||||
|
" Redistribution and use in source and binary forms, with or without",
|
||||||
|
" modification, are permitted provided that the following conditions are",
|
||||||
|
" met:",
|
||||||
|
"",
|
||||||
|
" * Redistributions of source code must retain the above copyright",
|
||||||
|
" notice, this list of conditions and the following disclaimer.",
|
||||||
|
" * Redistributions in binary form must reproduce the above",
|
||||||
|
" copyright notice, this list of conditions and the following disclaimer",
|
||||||
|
" in the documentation and/or other materials provided with the",
|
||||||
|
" distribution.",
|
||||||
|
" * Neither the name of Google Inc. nor the names of its",
|
||||||
|
" contributors may be used to endorse or promote products derived from",
|
||||||
|
" this software without specific prior written permission.",
|
||||||
|
"",
|
||||||
|
" THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS",
|
||||||
|
" \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT",
|
||||||
|
" LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR",
|
||||||
|
" A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT",
|
||||||
|
" OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,",
|
||||||
|
" SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT",
|
||||||
|
" LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,",
|
||||||
|
" DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY",
|
||||||
|
" THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT",
|
||||||
|
" (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE",
|
||||||
|
" OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"isLicense": true,
|
||||||
|
"name": "buffer-alloc",
|
||||||
|
"licenseDetail": [
|
||||||
|
"This project is licensed under the MIT license.",
|
||||||
|
"Copyrights are respective of each contributor listed at the beginning of each definition file.",
|
||||||
|
"",
|
||||||
|
"Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the \"Software\"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:",
|
||||||
|
"",
|
||||||
|
"The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.",
|
||||||
|
"",
|
||||||
|
"THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE."
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"isLicense": true,
|
||||||
|
"name": "expand-template",
|
||||||
|
"licenseDetail": [
|
||||||
|
" DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE",
|
||||||
|
" Version 2, December 2004",
|
||||||
|
"",
|
||||||
|
" Copyright (C) 2004 Sam Hocevar <sam@hocevar.net>",
|
||||||
|
"",
|
||||||
|
" Everyone is permitted to copy and distribute verbatim or modified",
|
||||||
|
" copies of this license document, and changing it is allowed as long",
|
||||||
|
" as the name is changed.",
|
||||||
|
"",
|
||||||
|
" DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE",
|
||||||
|
" TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION",
|
||||||
|
"",
|
||||||
|
" 0. You just DO WHAT THE FUCK YOU WANT TO."
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"isLicense": true,
|
||||||
|
"name": "tunnel-agent",
|
||||||
|
"licenseDetail": [
|
||||||
|
"Copyright (c) tunnel-agent authors",
|
||||||
|
"",
|
||||||
|
"Apache License",
|
||||||
|
"",
|
||||||
|
"Version 2.0, January 2004",
|
||||||
|
"",
|
||||||
|
"http://www.apache.org/licenses/",
|
||||||
|
"",
|
||||||
|
"TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION",
|
||||||
|
"",
|
||||||
|
"1. Definitions.",
|
||||||
|
"",
|
||||||
|
"\"License\" shall mean the terms and conditions for use, reproduction, and distribution as defined by Sections 1 through 9 of this document.",
|
||||||
|
"",
|
||||||
|
"\"Licensor\" shall mean the copyright owner or entity authorized by the copyright owner that is granting the License.",
|
||||||
|
"",
|
||||||
|
"\"Legal Entity\" shall mean the union of the acting entity and all other entities that control, are controlled by, or are under common control with that entity. For the purposes of this definition, \"control\" means (i) the power, direct or indirect, to cause the direction or management of such entity, whether by contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the outstanding shares, or (iii) beneficial ownership of such entity.",
|
||||||
|
"",
|
||||||
|
"\"You\" (or \"Your\") shall mean an individual or Legal Entity exercising permissions granted by this License.",
|
||||||
|
"",
|
||||||
|
"\"Source\" form shall mean the preferred form for making modifications, including but not limited to software source code, documentation source, and configuration files.",
|
||||||
|
"",
|
||||||
|
"\"Object\" form shall mean any form resulting from mechanical transformation or translation of a Source form, including but not limited to compiled object code, generated documentation, and conversions to other media types.",
|
||||||
|
"",
|
||||||
|
"\"Work\" shall mean the work of authorship, whether in Source or Object form, made available under the License, as indicated by a copyright notice that is included in or attached to the work (an example is provided in the Appendix below).",
|
||||||
|
"",
|
||||||
|
"\"Derivative Works\" shall mean any work, whether in Source or Object form, that is based on (or derived from) the Work and for which the editorial revisions, annotations, elaborations, or other modifications represent, as a whole, an original work of authorship. For the purposes of this License, Derivative Works shall not include works that remain separable from, or merely link (or bind by name) to the interfaces of, the Work and Derivative Works thereof.",
|
||||||
|
"",
|
||||||
|
"\"Contribution\" shall mean any work of authorship, including the original version of the Work and any modifications or additions to that Work or Derivative Works thereof, that is intentionally submitted to Licensor for inclusion in the Work by the copyright owner or by an individual or Legal Entity authorized to submit on behalf of the copyright owner. For the purposes of this definition, \"submitted\" means any form of electronic, verbal, or written communication sent to the Licensor or its representatives, including but not limited to communication on electronic mailing lists, source code control systems, and issue tracking systems that are managed by, or on behalf of, the Licensor for the purpose of discussing and improving the Work, but excluding communication that is conspicuously marked or otherwise designated in writing by the copyright owner as \"Not a Contribution.\"",
|
||||||
|
"",
|
||||||
|
"\"Contributor\" shall mean Licensor and any individual or Legal Entity on behalf of whom a Contribution has been received by Licensor and subsequently incorporated within the Work.",
|
||||||
|
"",
|
||||||
|
"2. Grant of Copyright License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable copyright license to reproduce, prepare Derivative Works of, publicly display, publicly perform, sublicense, and distribute the Work and such Derivative Works in Source or Object form.",
|
||||||
|
"",
|
||||||
|
"3. Grant of Patent License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable (except as stated in this section) patent license to make, have made, use, offer to sell, sell, import, and otherwise transfer the Work, where such license applies only to those patent claims licensable by such Contributor that are necessarily infringed by their Contribution(s) alone or by combination of their Contribution(s) with the Work to which such Contribution(s) was submitted. If You institute patent litigation against any entity (including a cross-claim or counterclaim in a lawsuit) alleging that the Work or a Contribution incorporated within the Work constitutes direct or contributory patent infringement, then any patent licenses granted to You under this License for that Work shall terminate as of the date such litigation is filed.",
|
||||||
|
"",
|
||||||
|
"4. Redistribution. You may reproduce and distribute copies of the Work or Derivative Works thereof in any medium, with or without modifications, and in Source or Object form, provided that You meet the following conditions:",
|
||||||
|
"",
|
||||||
|
"You must give any other recipients of the Work or Derivative Works a copy of this License; and",
|
||||||
|
"",
|
||||||
|
"You must cause any modified files to carry prominent notices stating that You changed the files; and",
|
||||||
|
"",
|
||||||
|
"You must retain, in the Source form of any Derivative Works that You distribute, all copyright, patent, trademark, and attribution notices from the Source form of the Work, excluding those notices that do not pertain to any part of the Derivative Works; and",
|
||||||
|
"",
|
||||||
|
"If the Work includes a \"NOTICE\" text file as part of its distribution, then any Derivative Works that You distribute must include a readable copy of the attribution notices contained within such NOTICE file, excluding those notices that do not pertain to any part of the Derivative Works, in at least one of the following places: within a NOTICE text file distributed as part of the Derivative Works; within the Source form or documentation, if provided along with the Derivative Works; or, within a display generated by the Derivative Works, if and wherever such third-party notices normally appear. The contents of the NOTICE file are for informational purposes only and do not modify the License. You may add Your own attribution notices within Derivative Works that You distribute, alongside or as an addendum to the NOTICE text from the Work, provided that such additional attribution notices cannot be construed as modifying the License. You may add Your own copyright statement to Your modifications and may provide additional or different license terms and conditions for use, reproduction, or distribution of Your modifications, or for any such Derivative Works as a whole, provided Your use, reproduction, and distribution of the Work otherwise complies with the conditions stated in this License.",
|
||||||
|
"",
|
||||||
|
"5. Submission of Contributions. Unless You explicitly state otherwise, any Contribution intentionally submitted for inclusion in the Work by You to the Licensor shall be under the terms and conditions of this License, without any additional terms or conditions. Notwithstanding the above, nothing herein shall supersede or modify the terms of any separate license agreement you may have executed with Licensor regarding such Contributions.",
|
||||||
|
"",
|
||||||
|
"6. Trademarks. This License does not grant permission to use the trade names, trademarks, service marks, or product names of the Licensor, except as required for reasonable and customary use in describing the origin of the Work and reproducing the content of the NOTICE file.",
|
||||||
|
"",
|
||||||
|
"7. Disclaimer of Warranty. Unless required by applicable law or agreed to in writing, Licensor provides the Work (and each Contributor provides its Contributions) on an \"AS IS\" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied, including, without limitation, any warranties or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are solely responsible for determining the appropriateness of using or redistributing the Work and assume any risks associated with Your exercise of permissions under this License.",
|
||||||
|
"",
|
||||||
|
"8. Limitation of Liability. In no event and under no legal theory, whether in tort (including negligence), contract, or otherwise, unless required by applicable law (such as deliberate and grossly negligent acts) or agreed to in writing, shall any Contributor be liable to You for damages, including any direct, indirect, special, incidental, or consequential damages of any character arising as a result of this License or out of the use or inability to use the Work (including but not limited to damages for loss of goodwill, work stoppage, computer failure or malfunction, or any and all other commercial damages or losses), even if such Contributor has been advised of the possibility of such damages.",
|
||||||
|
"",
|
||||||
|
"9. Accepting Warranty or Additional Liability. While redistributing the Work or Derivative Works thereof, You may choose to offer, and charge a fee for, acceptance of support, warranty, indemnity, or other liability obligations and/or rights consistent with this License. However, in accepting such obligations, You may act only on Your own behalf and on Your sole responsibility, not on behalf of any other Contributor, and only if You agree to indemnify, defend, and hold each Contributor harmless for any liability incurred by, or claims asserted against, such Contributor by reason of your accepting any such warranty or additional liability.",
|
||||||
|
"",
|
||||||
|
"END OF TERMS AND CONDITIONS"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"isLicense": true,
|
||||||
|
"name": "noop-logger",
|
||||||
|
"licenseDetail": [
|
||||||
|
"This project is licensed under the MIT license.",
|
||||||
|
"Copyrights are respective of each contributor listed at the beginning of each definition file.",
|
||||||
|
"",
|
||||||
|
"Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the \"Software\"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:",
|
||||||
|
"",
|
||||||
|
"The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.",
|
||||||
|
"",
|
||||||
|
"THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE."
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"isLicense": true,
|
||||||
|
"name": "buffer-alloc-unsafe",
|
||||||
|
"licenseDetail": [
|
||||||
|
"This project is licensed under the MIT license.",
|
||||||
|
"Copyrights are respective of each contributor listed at the beginning of each definition file.",
|
||||||
|
"",
|
||||||
|
"Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the \"Software\"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:",
|
||||||
|
"",
|
||||||
|
"The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.",
|
||||||
|
"",
|
||||||
|
"THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE."
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"isLicense": true,
|
||||||
|
"name": "buffer-fill",
|
||||||
|
"licenseDetail": [
|
||||||
|
"This project is licensed under the MIT license.",
|
||||||
|
"Copyrights are respective of each contributor listed at the beginning of each definition file.",
|
||||||
|
"",
|
||||||
|
"Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the \"Software\"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:",
|
||||||
|
"",
|
||||||
|
"The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.",
|
||||||
|
"",
|
||||||
|
"THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE."
|
||||||
|
]
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|||||||
24
README.md
24
README.md
@@ -4,16 +4,16 @@
|
|||||||
|
|
||||||
SQL Operations Studio is a data management tool that enables you to work with SQL Server, Azure SQL DB and SQL DW from Windows, macOS and Linux.
|
SQL Operations Studio is a data management tool that enables you to work with SQL Server, Azure SQL DB and SQL DW from Windows, macOS and Linux.
|
||||||
|
|
||||||
**Download SQL Operations Studio June Public Preview**
|
**Download SQL Operations Studio August Public Preview**
|
||||||
|
|
||||||
Platform | Link
|
Platform | Link
|
||||||
-- | --
|
-- | --
|
||||||
Windows Setup Installer | https://go.microsoft.com/fwlink/?linkid=875602
|
Windows Setup Installer | https://go.microsoft.com/fwlink/?linkid=2013365
|
||||||
Windows ZIP | https://go.microsoft.com/fwlink/?linkid=875603
|
Windows ZIP | https://go.microsoft.com/fwlink/?linkid=2013712
|
||||||
macOS ZIP | https://go.microsoft.com/fwlink/?linkid=875604
|
macOS ZIP | https://go.microsoft.com/fwlink/?linkid=2013715
|
||||||
Linux TAR.GZ | https://go.microsoft.com/fwlink/?linkid=875605
|
Linux TAR.GZ | https://go.microsoft.com/fwlink/?linkid=2013718
|
||||||
Linux RPM | https://go.microsoft.com/fwlink/?linkid=875606
|
Linux RPM | https://go.microsoft.com/fwlink/?linkid=2013830
|
||||||
Linux DEB | https://go.microsoft.com/fwlink/?linkid=875607
|
Linux DEB | https://go.microsoft.com/fwlink/?linkid=2013833
|
||||||
|
|
||||||
Go to our [download page](https://aka.ms/sqlopsstudio) for more specific instructions.
|
Go to our [download page](https://aka.ms/sqlopsstudio) for more specific instructions.
|
||||||
|
|
||||||
@@ -61,6 +61,16 @@ The [Microsoft Enterprise and Developer Privacy Statement](https://privacy.micro
|
|||||||
## Contributions and "thank you"
|
## Contributions and "thank you"
|
||||||
We would like to thank all our users who raised issues, and in particular the following users who helped contribute fixes:
|
We would like to thank all our users who raised issues, and in particular the following users who helped contribute fixes:
|
||||||
|
|
||||||
|
* SebastianPfliegel `Added more saveAsCsv options #2099`
|
||||||
|
* ianychoi `Fixes a typo: Mimunum -> Minimum #1994`
|
||||||
|
* AlexFsmn `Fixed bug where proper file extension wasn't appended to filename. #2151`
|
||||||
|
* AlexFsmn `Added functionality for adding any file to import wizard #2329`
|
||||||
|
* AlexFsmn `Fixed background issue when copying a chart to clipboard #2215`
|
||||||
|
* AlexFsmn `Fixed problem where vertical charts didn't display labels correctly. #2263`
|
||||||
|
* AlexFsmn `Fixed Initial values for charts to match visuals #2266`
|
||||||
|
* AlexFsmn `Renamed chart option labels #2264`
|
||||||
|
* AlexFsmn `Added feature for opening file after exporting to CSV/XLS/JSON & query files #2216`
|
||||||
|
* AlexFsmm `Get Connection String should copy to clipboard #2175`
|
||||||
* lanceklinger `Fix for double clicking column handle in results table #1504`
|
* lanceklinger `Fix for double clicking column handle in results table #1504`
|
||||||
* westerncj for `Removed duplicate contribution from README.md (#753)`
|
* westerncj for `Removed duplicate contribution from README.md (#753)`
|
||||||
* ntovas for `Fix for duplicate extensions shown in "Save File" dialog. (#779)`
|
* ntovas for `Fix for duplicate extensions shown in "Save File" dialog. (#779)`
|
||||||
|
|||||||
@@ -1,12 +1,12 @@
|
|||||||
[
|
[
|
||||||
{
|
{
|
||||||
"name": "ms-vscode.node-debug",
|
"name": "ms-vscode.node-debug",
|
||||||
"version": "1.23.3",
|
"version": "1.26.7",
|
||||||
"repo": "https://github.com/Microsoft/vscode-node-debug"
|
"repo": "https://github.com/Microsoft/vscode-node-debug"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "ms-vscode.node-debug2",
|
"name": "ms-vscode.node-debug2",
|
||||||
"version": "1.23.5",
|
"version": "1.26.8",
|
||||||
"repo": "https://github.com/Microsoft/vscode-node-debug2"
|
"repo": "https://github.com/Microsoft/vscode-node-debug2"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|||||||
@@ -12,10 +12,12 @@ const File = require('vinyl');
|
|||||||
const i18n = require('./lib/i18n');
|
const i18n = require('./lib/i18n');
|
||||||
const standalone = require('./lib/standalone');
|
const standalone = require('./lib/standalone');
|
||||||
const cp = require('child_process');
|
const cp = require('child_process');
|
||||||
|
const compilation = require('./lib/compilation');
|
||||||
|
const monacoapi = require('./monaco/api');
|
||||||
|
const fs = require('fs');
|
||||||
|
|
||||||
var root = path.dirname(__dirname);
|
var root = path.dirname(__dirname);
|
||||||
var sha1 = util.getVersion(root);
|
var sha1 = util.getVersion(root);
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
var semver = require('./monaco/package.json').version;
|
var semver = require('./monaco/package.json').version;
|
||||||
var headerVersion = semver + '(' + sha1 + ')';
|
var headerVersion = semver + '(' + sha1 + ')';
|
||||||
|
|
||||||
@@ -59,29 +61,56 @@ var BUNDLED_FILE_HEADER = [
|
|||||||
''
|
''
|
||||||
].join('\n');
|
].join('\n');
|
||||||
|
|
||||||
function editorLoaderConfig() {
|
|
||||||
var result = common.loaderConfig();
|
|
||||||
|
|
||||||
// never ship octicons in editor
|
|
||||||
result.paths['vs/base/browser/ui/octiconLabel/octiconLabel'] = 'out-build/vs/base/browser/ui/octiconLabel/octiconLabel.mock';
|
|
||||||
|
|
||||||
// force css inlining to use base64 -- see https://github.com/Microsoft/monaco-editor/issues/148
|
|
||||||
result['vs/css'] = {
|
|
||||||
inlineResources: 'base64',
|
|
||||||
inlineResourcesLimit: 3000 // see https://github.com/Microsoft/monaco-editor/issues/336
|
|
||||||
};
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
const languages = i18n.defaultLanguages.concat([]); // i18n.defaultLanguages.concat(process.env.VSCODE_QUALITY !== 'stable' ? i18n.extraLanguages : []);
|
const languages = i18n.defaultLanguages.concat([]); // i18n.defaultLanguages.concat(process.env.VSCODE_QUALITY !== 'stable' ? i18n.extraLanguages : []);
|
||||||
|
|
||||||
|
gulp.task('clean-editor-src', util.rimraf('out-editor-src'));
|
||||||
|
gulp.task('extract-editor-src', ['clean-editor-src'], function () {
|
||||||
|
console.log(`If the build fails, consider tweaking shakeLevel below to a lower value.`);
|
||||||
|
const apiusages = monacoapi.execute().usageContent;
|
||||||
|
const extrausages = fs.readFileSync(path.join(root, 'build', 'monaco', 'monaco.usage.recipe')).toString();
|
||||||
|
standalone.extractEditor({
|
||||||
|
sourcesRoot: path.join(root, 'src'),
|
||||||
|
entryPoints: [
|
||||||
|
'vs/editor/editor.main',
|
||||||
|
'vs/editor/editor.worker',
|
||||||
|
'vs/base/worker/workerMain',
|
||||||
|
],
|
||||||
|
inlineEntryPoints: [
|
||||||
|
apiusages,
|
||||||
|
extrausages
|
||||||
|
],
|
||||||
|
libs: [
|
||||||
|
`lib.d.ts`,
|
||||||
|
`lib.es2015.collection.d.ts`
|
||||||
|
],
|
||||||
|
redirects: {
|
||||||
|
'vs/base/browser/ui/octiconLabel/octiconLabel': 'vs/base/browser/ui/octiconLabel/octiconLabel.mock',
|
||||||
|
},
|
||||||
|
compilerOptions: {
|
||||||
|
module: 2, // ModuleKind.AMD
|
||||||
|
},
|
||||||
|
shakeLevel: 2, // 0-Files, 1-InnerFile, 2-ClassMembers
|
||||||
|
importIgnorePattern: /^vs\/css!/,
|
||||||
|
destRoot: path.join(root, 'out-editor-src')
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
// Full compile, including nls and inline sources in sourcemaps, for build
|
||||||
|
gulp.task('clean-editor-build', util.rimraf('out-editor-build'));
|
||||||
|
gulp.task('compile-editor-build', ['clean-editor-build', 'extract-editor-src'], compilation.compileTask('out-editor-src', 'out-editor-build', true));
|
||||||
|
|
||||||
gulp.task('clean-optimized-editor', util.rimraf('out-editor'));
|
gulp.task('clean-optimized-editor', util.rimraf('out-editor'));
|
||||||
gulp.task('optimize-editor', ['clean-optimized-editor', 'compile-client-build'], common.optimizeTask({
|
gulp.task('optimize-editor', ['clean-optimized-editor', 'compile-editor-build'], common.optimizeTask({
|
||||||
|
src: 'out-editor-build',
|
||||||
entryPoints: editorEntryPoints,
|
entryPoints: editorEntryPoints,
|
||||||
otherSources: editorOtherSources,
|
otherSources: editorOtherSources,
|
||||||
resources: editorResources,
|
resources: editorResources,
|
||||||
loaderConfig: editorLoaderConfig(),
|
loaderConfig: {
|
||||||
|
paths: {
|
||||||
|
'vs': 'out-editor-build/vs',
|
||||||
|
'vscode': 'empty:'
|
||||||
|
}
|
||||||
|
},
|
||||||
bundleLoader: false,
|
bundleLoader: false,
|
||||||
header: BUNDLED_FILE_HEADER,
|
header: BUNDLED_FILE_HEADER,
|
||||||
bundleInfo: true,
|
bundleInfo: true,
|
||||||
@@ -114,6 +143,41 @@ gulp.task('compile-editor-esm', ['extract-editor-esm', 'clean-editor-distro'], f
|
|||||||
console.log(result.stdout.toString());
|
console.log(result.stdout.toString());
|
||||||
});
|
});
|
||||||
|
|
||||||
|
function toExternalDTS(contents) {
|
||||||
|
let lines = contents.split('\n');
|
||||||
|
let killNextCloseCurlyBrace = false;
|
||||||
|
for (let i = 0; i < lines.length; i++) {
|
||||||
|
let line = lines[i];
|
||||||
|
|
||||||
|
if (killNextCloseCurlyBrace) {
|
||||||
|
if ('}' === line) {
|
||||||
|
lines[i] = '';
|
||||||
|
killNextCloseCurlyBrace = false;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (line.indexOf(' ') === 0) {
|
||||||
|
lines[i] = line.substr(4);
|
||||||
|
} else if (line.charAt(0) === '\t') {
|
||||||
|
lines[i] = line.substr(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ('declare namespace monaco {' === line) {
|
||||||
|
lines[i] = '';
|
||||||
|
killNextCloseCurlyBrace = true;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (line.indexOf('declare namespace monaco.') === 0) {
|
||||||
|
lines[i] = line.replace('declare namespace monaco.', 'export namespace ');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return lines.join('\n');
|
||||||
|
}
|
||||||
|
|
||||||
gulp.task('clean-editor-distro', util.rimraf('out-monaco-editor-core'));
|
gulp.task('clean-editor-distro', util.rimraf('out-monaco-editor-core'));
|
||||||
gulp.task('editor-distro', ['clean-editor-distro', 'compile-editor-esm', 'minify-editor', 'optimize-editor'], function () {
|
gulp.task('editor-distro', ['clean-editor-distro', 'compile-editor-esm', 'minify-editor', 'optimize-editor'], function () {
|
||||||
return es.merge(
|
return es.merge(
|
||||||
@@ -130,7 +194,7 @@ gulp.task('editor-distro', ['clean-editor-distro', 'compile-editor-esm', 'minify
|
|||||||
this.emit('data', new File({
|
this.emit('data', new File({
|
||||||
path: data.path.replace(/monaco\.d\.ts/, 'editor.api.d.ts'),
|
path: data.path.replace(/monaco\.d\.ts/, 'editor.api.d.ts'),
|
||||||
base: data.base,
|
base: data.base,
|
||||||
contents: data.contents
|
contents: new Buffer(toExternalDTS(data.contents.toString()))
|
||||||
}));
|
}));
|
||||||
}))
|
}))
|
||||||
.pipe(gulp.dest('out-monaco-editor-core/esm/vs/editor')),
|
.pipe(gulp.dest('out-monaco-editor-core/esm/vs/editor')),
|
||||||
@@ -195,7 +259,7 @@ gulp.task('editor-distro', ['clean-editor-distro', 'compile-editor-esm', 'minify
|
|||||||
});
|
});
|
||||||
|
|
||||||
gulp.task('analyze-editor-distro', function () {
|
gulp.task('analyze-editor-distro', function () {
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
// @ts-ignore
|
||||||
var bundleInfo = require('../out-editor/bundleInfo.json');
|
var bundleInfo = require('../out-editor/bundleInfo.json');
|
||||||
var graph = bundleInfo.graph;
|
var graph = bundleInfo.graph;
|
||||||
var bundles = bundleInfo.bundles;
|
var bundles = bundleInfo.bundles;
|
||||||
|
|||||||
@@ -20,7 +20,6 @@ const sourcemaps = require('gulp-sourcemaps');
|
|||||||
const nlsDev = require('vscode-nls-dev');
|
const nlsDev = require('vscode-nls-dev');
|
||||||
const root = path.dirname(__dirname);
|
const root = path.dirname(__dirname);
|
||||||
const commit = util.getVersion(root);
|
const commit = util.getVersion(root);
|
||||||
const i18n = require('./lib/i18n');
|
|
||||||
const plumber = require('gulp-plumber');
|
const plumber = require('gulp-plumber');
|
||||||
|
|
||||||
const extensionsPath = path.join(path.dirname(__dirname), 'extensions');
|
const extensionsPath = path.join(path.dirname(__dirname), 'extensions');
|
||||||
@@ -32,8 +31,6 @@ const compilations = glob.sync('**/tsconfig.json', {
|
|||||||
|
|
||||||
const getBaseUrl = out => `https://ticino.blob.core.windows.net/sourcemaps/${commit}/${out}`;
|
const getBaseUrl = out => `https://ticino.blob.core.windows.net/sourcemaps/${commit}/${out}`;
|
||||||
|
|
||||||
const languages = i18n.defaultLanguages.concat(process.env.VSCODE_QUALITY !== 'stable' ? i18n.extraLanguages : []);
|
|
||||||
|
|
||||||
const tasks = compilations.map(function (tsconfigFile) {
|
const tasks = compilations.map(function (tsconfigFile) {
|
||||||
const absolutePath = path.join(extensionsPath, tsconfigFile);
|
const absolutePath = path.join(extensionsPath, tsconfigFile);
|
||||||
const relativeDirname = path.dirname(tsconfigFile);
|
const relativeDirname = path.dirname(tsconfigFile);
|
||||||
@@ -58,7 +55,6 @@ const tasks = compilations.map(function (tsconfigFile) {
|
|||||||
const srcBase = path.join(root, 'src');
|
const srcBase = path.join(root, 'src');
|
||||||
const src = path.join(srcBase, '**');
|
const src = path.join(srcBase, '**');
|
||||||
const out = path.join(root, 'out');
|
const out = path.join(root, 'out');
|
||||||
const i18nPath = path.join(__dirname, '..', 'i18n');
|
|
||||||
const baseUrl = getBaseUrl(out);
|
const baseUrl = getBaseUrl(out);
|
||||||
|
|
||||||
let headerId, headerOut;
|
let headerId, headerOut;
|
||||||
@@ -102,9 +98,9 @@ const tasks = compilations.map(function (tsconfigFile) {
|
|||||||
sourceRoot: '../src'
|
sourceRoot: '../src'
|
||||||
}))
|
}))
|
||||||
.pipe(tsFilter.restore)
|
.pipe(tsFilter.restore)
|
||||||
.pipe(build ? nlsDev.createAdditionalLanguageFiles(languages, i18nPath, out) : es.through())
|
|
||||||
.pipe(build ? nlsDev.bundleMetaDataFiles(headerId, headerOut) : es.through())
|
.pipe(build ? nlsDev.bundleMetaDataFiles(headerId, headerOut) : es.through())
|
||||||
.pipe(build ? nlsDev.bundleLanguageFiles() : es.through())
|
// Filter out *.nls.json file. We needed them only to bundle meta data file.
|
||||||
|
.pipe(filter(['**', '!**/*.nls.json']))
|
||||||
.pipe(reporter.end(emitError));
|
.pipe(reporter.end(emitError));
|
||||||
|
|
||||||
return es.duplex(input, output);
|
return es.duplex(input, output);
|
||||||
|
|||||||
@@ -49,6 +49,7 @@ const indentationFilter = [
|
|||||||
'!src/vs/base/common/marked/marked.js',
|
'!src/vs/base/common/marked/marked.js',
|
||||||
'!src/vs/base/common/winjs.base.js',
|
'!src/vs/base/common/winjs.base.js',
|
||||||
'!src/vs/base/node/terminateProcess.sh',
|
'!src/vs/base/node/terminateProcess.sh',
|
||||||
|
'!src/vs/base/node/cpuUsage.sh',
|
||||||
'!test/assert.js',
|
'!test/assert.js',
|
||||||
|
|
||||||
// except specific folders
|
// except specific folders
|
||||||
@@ -81,8 +82,9 @@ const indentationFilter = [
|
|||||||
'!build/{lib,tslintRules}/**/*.js',
|
'!build/{lib,tslintRules}/**/*.js',
|
||||||
'!build/**/*.sh',
|
'!build/**/*.sh',
|
||||||
'!build/tfs/**/*.js',
|
'!build/tfs/**/*.js',
|
||||||
|
'!build/tfs/**/*.config',
|
||||||
'!**/Dockerfile',
|
'!**/Dockerfile',
|
||||||
'!extensions/markdown/media/*.js'
|
'!extensions/markdown-language-features/media/*.js'
|
||||||
];
|
];
|
||||||
|
|
||||||
const copyrightFilter = [
|
const copyrightFilter = [
|
||||||
@@ -103,8 +105,9 @@ const copyrightFilter = [
|
|||||||
'!**/*.code-workspace',
|
'!**/*.code-workspace',
|
||||||
'!build/**/*.init',
|
'!build/**/*.init',
|
||||||
'!resources/linux/snap/snapcraft.yaml',
|
'!resources/linux/snap/snapcraft.yaml',
|
||||||
|
'!resources/linux/snap/electron-launch',
|
||||||
'!resources/win32/bin/code.js',
|
'!resources/win32/bin/code.js',
|
||||||
'!extensions/markdown-language-features/media/tomorrow.css',
|
'!extensions/markdown-language-features/media/highlight.css',
|
||||||
'!extensions/html-language-features/server/src/modes/typescript/*',
|
'!extensions/html-language-features/server/src/modes/typescript/*',
|
||||||
'!extensions/*/server/bin/*'
|
'!extensions/*/server/bin/*'
|
||||||
];
|
];
|
||||||
@@ -136,6 +139,7 @@ const tslintFilter = [
|
|||||||
'!extensions/html-language-features/server/lib/jquery.d.ts'
|
'!extensions/html-language-features/server/lib/jquery.d.ts'
|
||||||
];
|
];
|
||||||
|
|
||||||
|
// {{SQL CARBON EDIT}}
|
||||||
const copyrightHeaderLines = [
|
const copyrightHeaderLines = [
|
||||||
'/*---------------------------------------------------------------------------------------------',
|
'/*---------------------------------------------------------------------------------------------',
|
||||||
' * Copyright (c) Microsoft Corporation. All rights reserved.',
|
' * Copyright (c) Microsoft Corporation. All rights reserved.',
|
||||||
|
|||||||
@@ -18,7 +18,6 @@ const assign = require('object-assign');
|
|||||||
// {{SQL CARBON EDIT}}
|
// {{SQL CARBON EDIT}}
|
||||||
const jeditor = require('gulp-json-editor');
|
const jeditor = require('gulp-json-editor');
|
||||||
|
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const pkg = require('../package.json');
|
const pkg = require('../package.json');
|
||||||
|
|
||||||
gulp.task('mixin', function () {
|
gulp.task('mixin', function () {
|
||||||
|
|||||||
@@ -17,19 +17,15 @@ const vfs = require('vinyl-fs');
|
|||||||
const rename = require('gulp-rename');
|
const rename = require('gulp-rename');
|
||||||
const replace = require('gulp-replace');
|
const replace = require('gulp-replace');
|
||||||
const filter = require('gulp-filter');
|
const filter = require('gulp-filter');
|
||||||
const buffer = require('gulp-buffer');
|
|
||||||
const json = require('gulp-json-editor');
|
const json = require('gulp-json-editor');
|
||||||
const _ = require('underscore');
|
const _ = require('underscore');
|
||||||
const util = require('./lib/util');
|
const util = require('./lib/util');
|
||||||
const ext = require('./lib/extensions');
|
const ext = require('./lib/extensions');
|
||||||
const buildfile = require('../src/buildfile');
|
const buildfile = require('../src/buildfile');
|
||||||
const common = require('./lib/optimize');
|
const common = require('./lib/optimize');
|
||||||
const nlsDev = require('vscode-nls-dev');
|
|
||||||
const root = path.dirname(__dirname);
|
const root = path.dirname(__dirname);
|
||||||
const commit = util.getVersion(root);
|
const commit = util.getVersion(root);
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const packageJson = require('../package.json');
|
const packageJson = require('../package.json');
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const product = require('../product.json');
|
const product = require('../product.json');
|
||||||
const crypto = require('crypto');
|
const crypto = require('crypto');
|
||||||
const i18n = require('./lib/i18n');
|
const i18n = require('./lib/i18n');
|
||||||
@@ -62,7 +58,6 @@ const nodeModules = [
|
|||||||
|
|
||||||
|
|
||||||
// Build
|
// Build
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const builtInExtensions = require('./builtInExtensions.json');
|
const builtInExtensions = require('./builtInExtensions.json');
|
||||||
|
|
||||||
const excludedExtensions = [
|
const excludedExtensions = [
|
||||||
@@ -78,6 +73,7 @@ const sqlBuiltInExtensions = [
|
|||||||
// Add SQL built-in extensions here.
|
// Add SQL built-in extensions here.
|
||||||
// the extension will be excluded from SQLOps package and will have separate vsix packages
|
// the extension will be excluded from SQLOps package and will have separate vsix packages
|
||||||
'agent',
|
'agent',
|
||||||
|
'import',
|
||||||
'profiler'
|
'profiler'
|
||||||
];
|
];
|
||||||
|
|
||||||
@@ -97,7 +93,7 @@ const vscodeResources = [
|
|||||||
'out-build/paths.js',
|
'out-build/paths.js',
|
||||||
'out-build/vs/**/*.{svg,png,cur,html}',
|
'out-build/vs/**/*.{svg,png,cur,html}',
|
||||||
'out-build/vs/base/common/performance.js',
|
'out-build/vs/base/common/performance.js',
|
||||||
'out-build/vs/base/node/{stdForkStart.js,terminateProcess.sh}',
|
'out-build/vs/base/node/{stdForkStart.js,terminateProcess.sh,cpuUsage.sh}',
|
||||||
'out-build/vs/base/browser/ui/octiconLabel/octicons/**',
|
'out-build/vs/base/browser/ui/octiconLabel/octicons/**',
|
||||||
'out-build/vs/workbench/browser/media/*-theme.css',
|
'out-build/vs/workbench/browser/media/*-theme.css',
|
||||||
'out-build/vs/workbench/electron-browser/bootstrap/**',
|
'out-build/vs/workbench/electron-browser/bootstrap/**',
|
||||||
@@ -106,7 +102,6 @@ const vscodeResources = [
|
|||||||
'out-build/vs/workbench/parts/webview/electron-browser/webview-pre.js',
|
'out-build/vs/workbench/parts/webview/electron-browser/webview-pre.js',
|
||||||
'out-build/vs/**/markdown.css',
|
'out-build/vs/**/markdown.css',
|
||||||
'out-build/vs/workbench/parts/tasks/**/*.json',
|
'out-build/vs/workbench/parts/tasks/**/*.json',
|
||||||
'out-build/vs/workbench/parts/terminal/electron-browser/terminalProcess.js',
|
|
||||||
'out-build/vs/workbench/parts/welcome/walkThrough/**/*.md',
|
'out-build/vs/workbench/parts/welcome/walkThrough/**/*.md',
|
||||||
'out-build/vs/workbench/services/files/**/*.exe',
|
'out-build/vs/workbench/services/files/**/*.exe',
|
||||||
'out-build/vs/workbench/services/files/**/*.md',
|
'out-build/vs/workbench/services/files/**/*.md',
|
||||||
@@ -142,17 +137,15 @@ const BUNDLED_FILE_HEADER = [
|
|||||||
' *--------------------------------------------------------*/'
|
' *--------------------------------------------------------*/'
|
||||||
].join('\n');
|
].join('\n');
|
||||||
|
|
||||||
const languages = i18n.defaultLanguages.concat([]); // i18n.defaultLanguages.concat(process.env.VSCODE_QUALITY !== 'stable' ? i18n.extraLanguages : []);
|
|
||||||
|
|
||||||
gulp.task('clean-optimized-vscode', util.rimraf('out-vscode'));
|
gulp.task('clean-optimized-vscode', util.rimraf('out-vscode'));
|
||||||
gulp.task('optimize-vscode', ['clean-optimized-vscode', 'compile-build', 'compile-extensions-build'], common.optimizeTask({
|
gulp.task('optimize-vscode', ['clean-optimized-vscode', 'compile-build', 'compile-extensions-build'], common.optimizeTask({
|
||||||
|
src: 'out-build',
|
||||||
entryPoints: vscodeEntryPoints,
|
entryPoints: vscodeEntryPoints,
|
||||||
otherSources: [],
|
otherSources: [],
|
||||||
resources: vscodeResources,
|
resources: vscodeResources,
|
||||||
loaderConfig: common.loaderConfig(nodeModules),
|
loaderConfig: common.loaderConfig(nodeModules),
|
||||||
header: BUNDLED_FILE_HEADER,
|
header: BUNDLED_FILE_HEADER,
|
||||||
out: 'out-vscode',
|
out: 'out-vscode',
|
||||||
languages: languages,
|
|
||||||
bundleInfo: undefined
|
bundleInfo: undefined
|
||||||
}));
|
}));
|
||||||
|
|
||||||
@@ -169,6 +162,8 @@ gulp.task('clean-minified-vscode', util.rimraf('out-vscode-min'));
|
|||||||
gulp.task('minify-vscode', ['clean-minified-vscode', 'optimize-index-js'], common.minifyTask('out-vscode', baseUrl));
|
gulp.task('minify-vscode', ['clean-minified-vscode', 'optimize-index-js'], common.minifyTask('out-vscode', baseUrl));
|
||||||
|
|
||||||
// Package
|
// Package
|
||||||
|
|
||||||
|
// @ts-ignore JSON checking: darwinCredits is optional
|
||||||
const darwinCreditsTemplate = product.darwinCredits && _.template(fs.readFileSync(path.join(root, product.darwinCredits), 'utf8'));
|
const darwinCreditsTemplate = product.darwinCredits && _.template(fs.readFileSync(path.join(root, product.darwinCredits), 'utf8'));
|
||||||
|
|
||||||
const config = {
|
const config = {
|
||||||
@@ -198,6 +193,8 @@ const config = {
|
|||||||
linuxExecutableName: product.applicationName,
|
linuxExecutableName: product.applicationName,
|
||||||
winIcon: 'resources/win32/code.ico',
|
winIcon: 'resources/win32/code.ico',
|
||||||
token: process.env['VSCODE_MIXIN_PASSWORD'] || process.env['GITHUB_TOKEN'] || void 0,
|
token: process.env['VSCODE_MIXIN_PASSWORD'] || process.env['GITHUB_TOKEN'] || void 0,
|
||||||
|
|
||||||
|
// @ts-ignore JSON checking: electronRepository is optional
|
||||||
repo: product.electronRepository || void 0
|
repo: product.electronRepository || void 0
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -273,7 +270,8 @@ function packageBuiltInExtensions() {
|
|||||||
console.info('Creating vsix for ' + element.path + ' result:' + packagePath);
|
console.info('Creating vsix for ' + element.path + ' result:' + packagePath);
|
||||||
vsce.createVSIX({
|
vsce.createVSIX({
|
||||||
cwd: element.path,
|
cwd: element.path,
|
||||||
packagePath: packagePath
|
packagePath: packagePath,
|
||||||
|
useYarn: true
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -313,15 +311,8 @@ function packageTask(platform, arch, opts) {
|
|||||||
packageBuiltInExtensions();
|
packageBuiltInExtensions();
|
||||||
|
|
||||||
const localExtensions = es.merge(...localExtensionDescriptions.map(extension => {
|
const localExtensions = es.merge(...localExtensionDescriptions.map(extension => {
|
||||||
const nlsFilter = filter('**/*.nls.json', { restore: true });
|
|
||||||
|
|
||||||
return ext.fromLocal(extension.path)
|
return ext.fromLocal(extension.path)
|
||||||
.pipe(rename(p => p.dirname = `extensions/${extension.name}/${p.dirname}`))
|
.pipe(rename(p => p.dirname = `extensions/${extension.name}/${p.dirname}`));
|
||||||
// // TODO@Dirk: this filter / buffer is here to make sure the nls.json files are buffered
|
|
||||||
.pipe(nlsFilter)
|
|
||||||
.pipe(buffer())
|
|
||||||
.pipe(nlsDev.createAdditionalLanguageFiles(languages, path.join(__dirname, '..', 'i18n')))
|
|
||||||
.pipe(nlsFilter.restore);
|
|
||||||
}));
|
}));
|
||||||
|
|
||||||
// {{SQL CARBON EDIT}}
|
// {{SQL CARBON EDIT}}
|
||||||
@@ -340,6 +331,7 @@ function packageTask(platform, arch, opts) {
|
|||||||
.pipe(filter(['**', '!**/*.js.map']));
|
.pipe(filter(['**', '!**/*.js.map']));
|
||||||
|
|
||||||
let version = packageJson.version;
|
let version = packageJson.version;
|
||||||
|
// @ts-ignore JSON checking: quality is optional
|
||||||
const quality = product.quality;
|
const quality = product.quality;
|
||||||
|
|
||||||
if (quality && quality !== 'stable') {
|
if (quality && quality !== 'stable') {
|
||||||
@@ -350,10 +342,15 @@ function packageTask(platform, arch, opts) {
|
|||||||
const packageJsonStream = gulp.src(['package.json'], { base: '.' })
|
const packageJsonStream = gulp.src(['package.json'], { base: '.' })
|
||||||
.pipe(json({ name, version }));
|
.pipe(json({ name, version }));
|
||||||
|
|
||||||
const settingsSearchBuildId = getSettingsSearchBuildId(packageJson);
|
|
||||||
const date = new Date().toISOString();
|
const date = new Date().toISOString();
|
||||||
|
const productJsonUpdate = { commit, date, checksums };
|
||||||
|
|
||||||
|
if (shouldSetupSettingsSearch()) {
|
||||||
|
productJsonUpdate.settingsSearchBuildId = getSettingsSearchBuildId(packageJson);
|
||||||
|
}
|
||||||
|
|
||||||
const productJsonStream = gulp.src(['product.json'], { base: '.' })
|
const productJsonStream = gulp.src(['product.json'], { base: '.' })
|
||||||
.pipe(json({ commit, date, checksums, settingsSearchBuildId }));
|
.pipe(json(productJsonUpdate));
|
||||||
|
|
||||||
const license = gulp.src(['LICENSES.chromium.html', 'LICENSE.txt', 'ThirdPartyNotices.txt', 'licenses/**'], { base: '.' });
|
const license = gulp.src(['LICENSES.chromium.html', 'LICENSE.txt', 'ThirdPartyNotices.txt', 'licenses/**'], { base: '.' });
|
||||||
|
|
||||||
@@ -366,6 +363,7 @@ function packageTask(platform, arch, opts) {
|
|||||||
|
|
||||||
const depsSrc = [
|
const depsSrc = [
|
||||||
..._.flatten(productionDependencies.map(d => path.relative(root, d.path)).map(d => [`${d}/**`, `!${d}/**/{test,tests}/**`])),
|
..._.flatten(productionDependencies.map(d => path.relative(root, d.path)).map(d => [`${d}/**`, `!${d}/**/{test,tests}/**`])),
|
||||||
|
// @ts-ignore JSON checking: dependencies is optional
|
||||||
..._.flatten(Object.keys(product.dependencies || {}).map(d => [`node_modules/${d}/**`, `!node_modules/${d}/**/{test,tests}/**`]))
|
..._.flatten(Object.keys(product.dependencies || {}).map(d => [`node_modules/${d}/**`, `!node_modules/${d}/**/{test,tests}/**`]))
|
||||||
];
|
];
|
||||||
|
|
||||||
@@ -526,7 +524,9 @@ gulp.task('vscode-translations-push-test', ['optimize-vscode'], function () {
|
|||||||
gulp.src(pathToMetadata).pipe(i18n.createXlfFilesForCoreBundle()),
|
gulp.src(pathToMetadata).pipe(i18n.createXlfFilesForCoreBundle()),
|
||||||
gulp.src(pathToSetup).pipe(i18n.createXlfFilesForIsl()),
|
gulp.src(pathToSetup).pipe(i18n.createXlfFilesForIsl()),
|
||||||
gulp.src(pathToExtensions).pipe(i18n.createXlfFilesForExtensions())
|
gulp.src(pathToExtensions).pipe(i18n.createXlfFilesForExtensions())
|
||||||
).pipe(i18n.findObsoleteResources(apiHostname, apiName, apiToken)
|
// {{SQL CARBON EDIT}}
|
||||||
|
// disable since function makes calls to VS Code Transifex API
|
||||||
|
// ).pipe(i18n.findObsoleteResources(apiHostname, apiName, apiToken)
|
||||||
).pipe(vfs.dest('../vscode-transifex-input'));
|
).pipe(vfs.dest('../vscode-transifex-input'));
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -574,9 +574,8 @@ gulp.task('upload-vscode-sourcemaps', ['minify-vscode'], () => {
|
|||||||
|
|
||||||
const allConfigDetailsPath = path.join(os.tmpdir(), 'configuration.json');
|
const allConfigDetailsPath = path.join(os.tmpdir(), 'configuration.json');
|
||||||
gulp.task('upload-vscode-configuration', ['generate-vscode-configuration'], () => {
|
gulp.task('upload-vscode-configuration', ['generate-vscode-configuration'], () => {
|
||||||
|
if (!shouldSetupSettingsSearch()) {
|
||||||
const branch = process.env.BUILD_SOURCEBRANCH;
|
const branch = process.env.BUILD_SOURCEBRANCH;
|
||||||
|
|
||||||
if (!/\/master$/.test(branch) && branch.indexOf('/release/') < 0) {
|
|
||||||
console.log(`Only runs on master and release branches, not ${branch}`);
|
console.log(`Only runs on master and release branches, not ${branch}`);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -599,13 +598,24 @@ gulp.task('upload-vscode-configuration', ['generate-vscode-configuration'], () =
|
|||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
|
|
||||||
function getSettingsSearchBuildId(packageJson) {
|
function shouldSetupSettingsSearch() {
|
||||||
const previous = util.getPreviousVersion(packageJson.version);
|
const branch = process.env.BUILD_SOURCEBRANCH;
|
||||||
|
return branch && (/\/master$/.test(branch) || branch.indexOf('/release/') >= 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getSettingsSearchBuildId(packageJson) {
|
||||||
try {
|
try {
|
||||||
const out = cp.execSync(`git rev-list ${previous}..HEAD --count`);
|
const branch = process.env.BUILD_SOURCEBRANCH;
|
||||||
|
const branchId = branch.indexOf('/release/') >= 0 ? 0 :
|
||||||
|
/\/master$/.test(branch) ? 1 :
|
||||||
|
2; // Some unexpected branch
|
||||||
|
|
||||||
|
const out = cp.execSync(`git rev-list HEAD --count`);
|
||||||
const count = parseInt(out.toString());
|
const count = parseInt(out.toString());
|
||||||
return util.versionStringToNumber(packageJson.version) * 1e4 + count;
|
|
||||||
|
// <version number><commit count><branchId (avoid unlikely conflicts)>
|
||||||
|
// 1.25.1, 1,234,567 commits, master = 1250112345671
|
||||||
|
return util.versionStringToNumber(packageJson.version) * 1e8 + count * 10 + branchId;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
throw new Error('Could not determine build number: ' + e.toString());
|
throw new Error('Could not determine build number: ' + e.toString());
|
||||||
}
|
}
|
||||||
@@ -619,6 +629,10 @@ gulp.task('generate-vscode-configuration', () => {
|
|||||||
return reject(new Error('$AGENT_BUILDDIRECTORY not set'));
|
return reject(new Error('$AGENT_BUILDDIRECTORY not set'));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (process.env.VSCODE_QUALITY !== 'insider' && process.env.VSCODE_QUALITY !== 'stable') {
|
||||||
|
return resolve();
|
||||||
|
}
|
||||||
|
|
||||||
const userDataDir = path.join(os.tmpdir(), 'tmpuserdata');
|
const userDataDir = path.join(os.tmpdir(), 'tmpuserdata');
|
||||||
const extensionsDir = path.join(os.tmpdir(), 'tmpextdir');
|
const extensionsDir = path.join(os.tmpdir(), 'tmpextdir');
|
||||||
const appName = process.env.VSCODE_QUALITY === 'insider' ? 'Visual\\ Studio\\ Code\\ -\\ Insiders.app' : 'Visual\\ Studio\\ Code.app';
|
const appName = process.env.VSCODE_QUALITY === 'insider' ? 'Visual\\ Studio\\ Code\\ -\\ Insiders.app' : 'Visual\\ Studio\\ Code.app';
|
||||||
|
|||||||
@@ -12,11 +12,8 @@ const shell = require('gulp-shell');
|
|||||||
const es = require('event-stream');
|
const es = require('event-stream');
|
||||||
const vfs = require('vinyl-fs');
|
const vfs = require('vinyl-fs');
|
||||||
const util = require('./lib/util');
|
const util = require('./lib/util');
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const packageJson = require('../package.json');
|
const packageJson = require('../package.json');
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const product = require('../product.json');
|
const product = require('../product.json');
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const rpmDependencies = require('../resources/linux/rpm/dependencies.json');
|
const rpmDependencies = require('../resources/linux/rpm/dependencies.json');
|
||||||
|
|
||||||
const linuxPackageRevision = Math.floor(new Date().getTime() / 1000);
|
const linuxPackageRevision = Math.floor(new Date().getTime() / 1000);
|
||||||
@@ -76,7 +73,9 @@ function prepareDebPackage(arch) {
|
|||||||
const postinst = gulp.src('resources/linux/debian/postinst.template', { base: '.' })
|
const postinst = gulp.src('resources/linux/debian/postinst.template', { base: '.' })
|
||||||
.pipe(replace('@@NAME@@', product.applicationName))
|
.pipe(replace('@@NAME@@', product.applicationName))
|
||||||
.pipe(replace('@@ARCHITECTURE@@', debArch))
|
.pipe(replace('@@ARCHITECTURE@@', debArch))
|
||||||
|
// @ts-ignore JSON checking: quality is optional
|
||||||
.pipe(replace('@@QUALITY@@', product.quality || '@@QUALITY@@'))
|
.pipe(replace('@@QUALITY@@', product.quality || '@@QUALITY@@'))
|
||||||
|
// @ts-ignore JSON checking: updateUrl is optional
|
||||||
.pipe(replace('@@UPDATEURL@@', product.updateUrl || '@@UPDATEURL@@'))
|
.pipe(replace('@@UPDATEURL@@', product.updateUrl || '@@UPDATEURL@@'))
|
||||||
.pipe(rename('DEBIAN/postinst'));
|
.pipe(rename('DEBIAN/postinst'));
|
||||||
|
|
||||||
@@ -135,7 +134,9 @@ function prepareRpmPackage(arch) {
|
|||||||
.pipe(replace('@@RELEASE@@', linuxPackageRevision))
|
.pipe(replace('@@RELEASE@@', linuxPackageRevision))
|
||||||
.pipe(replace('@@ARCHITECTURE@@', rpmArch))
|
.pipe(replace('@@ARCHITECTURE@@', rpmArch))
|
||||||
.pipe(replace('@@LICENSE@@', product.licenseName))
|
.pipe(replace('@@LICENSE@@', product.licenseName))
|
||||||
|
// @ts-ignore JSON checking: quality is optional
|
||||||
.pipe(replace('@@QUALITY@@', product.quality || '@@QUALITY@@'))
|
.pipe(replace('@@QUALITY@@', product.quality || '@@QUALITY@@'))
|
||||||
|
// @ts-ignore JSON checking: updateUrl is optional
|
||||||
.pipe(replace('@@UPDATEURL@@', product.updateUrl || '@@UPDATEURL@@'))
|
.pipe(replace('@@UPDATEURL@@', product.updateUrl || '@@UPDATEURL@@'))
|
||||||
.pipe(replace('@@DEPENDENCIES@@', rpmDependencies[rpmArch].join(', ')))
|
.pipe(replace('@@DEPENDENCIES@@', rpmDependencies[rpmArch].join(', ')))
|
||||||
.pipe(rename('SPECS/' + product.applicationName + '.spec'));
|
.pipe(rename('SPECS/' + product.applicationName + '.spec'));
|
||||||
|
|||||||
@@ -7,45 +7,71 @@
|
|||||||
|
|
||||||
const gulp = require('gulp');
|
const gulp = require('gulp');
|
||||||
const path = require('path');
|
const path = require('path');
|
||||||
|
const fs = require('fs');
|
||||||
const assert = require('assert');
|
const assert = require('assert');
|
||||||
const cp = require('child_process');
|
const cp = require('child_process');
|
||||||
const _7z = require('7zip')['7z'];
|
const _7z = require('7zip')['7z'];
|
||||||
const util = require('./lib/util');
|
const util = require('./lib/util');
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const pkg = require('../package.json');
|
const pkg = require('../package.json');
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const product = require('../product.json');
|
const product = require('../product.json');
|
||||||
const vfs = require('vinyl-fs');
|
const vfs = require('vinyl-fs');
|
||||||
|
const mkdirp = require('mkdirp');
|
||||||
|
|
||||||
const repoPath = path.dirname(__dirname);
|
const repoPath = path.dirname(__dirname);
|
||||||
// {{SQL CARBON EDIT}}
|
// {{SQL CARBON EDIT}}
|
||||||
const buildPath = arch => path.join(path.dirname(repoPath), `sqlops-win32-${arch}`);
|
const buildPath = arch => path.join(path.dirname(repoPath), `sqlops-win32-${arch}`);
|
||||||
const zipDir = arch => path.join(repoPath, '.build', `win32-${arch}`, 'archive');
|
const zipDir = arch => path.join(repoPath, '.build', `win32-${arch}`, 'archive');
|
||||||
const zipPath = arch => path.join(zipDir(arch), `VSCode-win32-${arch}.zip`);
|
const zipPath = arch => path.join(zipDir(arch), `VSCode-win32-${arch}.zip`);
|
||||||
const setupDir = arch => path.join(repoPath, '.build', `win32-${arch}`, 'setup');
|
const setupDir = (arch, target) => path.join(repoPath, '.build', `win32-${arch}`, `${target}-setup`);
|
||||||
const issPath = path.join(__dirname, 'win32', 'code.iss');
|
const issPath = path.join(__dirname, 'win32', 'code.iss');
|
||||||
const innoSetupPath = path.join(path.dirname(path.dirname(require.resolve('innosetup-compiler'))), 'bin', 'ISCC.exe');
|
const innoSetupPath = path.join(path.dirname(path.dirname(require.resolve('innosetup-compiler'))), 'bin', 'ISCC.exe');
|
||||||
|
const signPS1 = path.join(repoPath, 'build', 'tfs', 'win32', 'sign.ps1');
|
||||||
|
|
||||||
function packageInnoSetup(iss, options, cb) {
|
function packageInnoSetup(iss, options, cb) {
|
||||||
options = options || {};
|
options = options || {};
|
||||||
|
|
||||||
const definitions = options.definitions || {};
|
const definitions = options.definitions || {};
|
||||||
|
const debug = process.argv.some(arg => arg === '--debug-inno');
|
||||||
|
|
||||||
|
if (debug) {
|
||||||
|
definitions['Debug'] = 'true';
|
||||||
|
}
|
||||||
|
|
||||||
const keys = Object.keys(definitions);
|
const keys = Object.keys(definitions);
|
||||||
|
|
||||||
keys.forEach(key => assert(typeof definitions[key] === 'string', `Missing value for '${key}' in Inno Setup package step`));
|
keys.forEach(key => assert(typeof definitions[key] === 'string', `Missing value for '${key}' in Inno Setup package step`));
|
||||||
|
|
||||||
const defs = keys.map(key => `/d${key}=${definitions[key]}`);
|
const defs = keys.map(key => `/d${key}=${definitions[key]}`);
|
||||||
const args = [iss].concat(defs);
|
const args = [
|
||||||
|
iss,
|
||||||
|
...defs
|
||||||
|
//,
|
||||||
|
//`/sesrp=powershell.exe -ExecutionPolicy bypass ${signPS1} $f`
|
||||||
|
];
|
||||||
|
|
||||||
cp.spawn(innoSetupPath, args, { stdio: 'inherit' })
|
cp.spawn(innoSetupPath, args, { stdio: ['ignore', 'inherit', 'inherit'] })
|
||||||
.on('error', cb)
|
.on('error', cb)
|
||||||
.on('exit', () => cb(null));
|
.on('exit', () => cb(null));
|
||||||
}
|
}
|
||||||
|
|
||||||
function buildWin32Setup(arch) {
|
function buildWin32Setup(arch, target) {
|
||||||
|
if (target !== 'system' && target !== 'user') {
|
||||||
|
throw new Error('Invalid setup target');
|
||||||
|
}
|
||||||
|
|
||||||
return cb => {
|
return cb => {
|
||||||
const ia32AppId = product.win32AppId;
|
const ia32AppId = target === 'system' ? product.win32AppId : product.win32UserAppId;
|
||||||
const x64AppId = product.win32x64AppId;
|
const x64AppId = target === 'system' ? product.win32x64AppId : product.win32x64UserAppId;
|
||||||
|
|
||||||
|
const sourcePath = buildPath(arch);
|
||||||
|
const outputPath = setupDir(arch, target);
|
||||||
|
mkdirp.sync(outputPath);
|
||||||
|
|
||||||
|
const originalProductJsonPath = path.join(sourcePath, 'resources/app/product.json');
|
||||||
|
const productJsonPath = path.join(outputPath, 'product.json');
|
||||||
|
const productJson = JSON.parse(fs.readFileSync(originalProductJsonPath, 'utf8'));
|
||||||
|
productJson['target'] = target;
|
||||||
|
fs.writeFileSync(productJsonPath, JSON.stringify(productJson, undefined, '\t'));
|
||||||
|
|
||||||
const definitions = {
|
const definitions = {
|
||||||
NameLong: product.nameLong,
|
NameLong: product.nameLong,
|
||||||
@@ -53,35 +79,42 @@ function buildWin32Setup(arch) {
|
|||||||
DirName: product.win32DirName,
|
DirName: product.win32DirName,
|
||||||
Version: pkg.version,
|
Version: pkg.version,
|
||||||
RawVersion: pkg.version.replace(/-\w+$/, ''),
|
RawVersion: pkg.version.replace(/-\w+$/, ''),
|
||||||
NameVersion: product.win32NameVersion,
|
NameVersion: product.win32NameVersion + (target === 'user' ? ' (User)' : ''),
|
||||||
ExeBasename: product.nameShort,
|
ExeBasename: product.nameShort,
|
||||||
RegValueName: product.win32RegValueName,
|
RegValueName: product.win32RegValueName,
|
||||||
ShellNameShort: product.win32ShellNameShort,
|
ShellNameShort: product.win32ShellNameShort,
|
||||||
AppMutex: product.win32MutexName,
|
AppMutex: product.win32MutexName,
|
||||||
Arch: arch,
|
Arch: arch,
|
||||||
AppId: arch === 'ia32' ? ia32AppId : x64AppId,
|
AppId: arch === 'ia32' ? ia32AppId : x64AppId,
|
||||||
IncompatibleAppId: arch === 'ia32' ? x64AppId : ia32AppId,
|
IncompatibleTargetAppId: arch === 'ia32' ? product.win32AppId : product.win32x64AppId,
|
||||||
|
IncompatibleArchAppId: arch === 'ia32' ? x64AppId : ia32AppId,
|
||||||
AppUserId: product.win32AppUserModelId,
|
AppUserId: product.win32AppUserModelId,
|
||||||
ArchitecturesAllowed: arch === 'ia32' ? '' : 'x64',
|
ArchitecturesAllowed: arch === 'ia32' ? '' : 'x64',
|
||||||
ArchitecturesInstallIn64BitMode: arch === 'ia32' ? '' : 'x64',
|
ArchitecturesInstallIn64BitMode: arch === 'ia32' ? '' : 'x64',
|
||||||
SourceDir: buildPath(arch),
|
SourceDir: sourcePath,
|
||||||
RepoDir: repoPath,
|
RepoDir: repoPath,
|
||||||
OutputDir: setupDir(arch)
|
OutputDir: outputPath,
|
||||||
|
InstallTarget: target,
|
||||||
|
ProductJsonPath: productJsonPath
|
||||||
};
|
};
|
||||||
|
|
||||||
packageInnoSetup(issPath, { definitions }, cb);
|
packageInnoSetup(issPath, { definitions }, cb);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
gulp.task('clean-vscode-win32-ia32-setup', util.rimraf(setupDir('ia32')));
|
function defineWin32SetupTasks(arch, target) {
|
||||||
gulp.task('vscode-win32-ia32-setup', ['clean-vscode-win32-ia32-setup'], buildWin32Setup('ia32'));
|
gulp.task(`clean-vscode-win32-${arch}-${target}-setup`, util.rimraf(setupDir(arch, target)));
|
||||||
|
gulp.task(`vscode-win32-${arch}-${target}-setup`, [`clean-vscode-win32-${arch}-${target}-setup`], buildWin32Setup(arch, target));
|
||||||
|
}
|
||||||
|
|
||||||
gulp.task('clean-vscode-win32-x64-setup', util.rimraf(setupDir('x64')));
|
defineWin32SetupTasks('ia32', 'system');
|
||||||
gulp.task('vscode-win32-x64-setup', ['clean-vscode-win32-x64-setup'], buildWin32Setup('x64'));
|
defineWin32SetupTasks('x64', 'system');
|
||||||
|
defineWin32SetupTasks('ia32', 'user');
|
||||||
|
defineWin32SetupTasks('x64', 'user');
|
||||||
|
|
||||||
function archiveWin32Setup(arch) {
|
function archiveWin32Setup(arch) {
|
||||||
return cb => {
|
return cb => {
|
||||||
const args = ['a', '-tzip', zipPath(arch), '.', '-r'];
|
const args = ['a', '-tzip', zipPath(arch), '-x!CodeSignSummary*.md', '.', '-r'];
|
||||||
|
|
||||||
cp.spawn(_7z, args, { stdio: 'inherit', cwd: buildPath(arch) })
|
cp.spawn(_7z, args, { stdio: 'inherit', cwd: buildPath(arch) })
|
||||||
.on('error', cb)
|
.on('error', cb)
|
||||||
|
|||||||
@@ -17,7 +17,6 @@ const ext = require('./extensions');
|
|||||||
const util = require('gulp-util');
|
const util = require('gulp-util');
|
||||||
|
|
||||||
const root = path.dirname(path.dirname(__dirname));
|
const root = path.dirname(path.dirname(__dirname));
|
||||||
// @ts-ignore Microsoft/TypeScript#21262 complains about a require of a JSON file
|
|
||||||
const builtInExtensions = require('../builtInExtensions.json');
|
const builtInExtensions = require('../builtInExtensions.json');
|
||||||
const controlFilePath = path.join(os.homedir(), '.vscode-oss-dev', 'extensions', 'control.json');
|
const controlFilePath = path.join(os.homedir(), '.vscode-oss-dev', 'extensions', 'control.json');
|
||||||
|
|
||||||
|
|||||||
@@ -18,8 +18,9 @@ var _ = require("underscore");
|
|||||||
var monacodts = require("../monaco/api");
|
var monacodts = require("../monaco/api");
|
||||||
var fs = require("fs");
|
var fs = require("fs");
|
||||||
var reporter = reporter_1.createReporter();
|
var reporter = reporter_1.createReporter();
|
||||||
var rootDir = path.join(__dirname, '../../src');
|
function getTypeScriptCompilerOptions(src) {
|
||||||
var options = require('../../src/tsconfig.json').compilerOptions;
|
var rootDir = path.join(__dirname, "../../" + src);
|
||||||
|
var options = require("../../" + src + "/tsconfig.json").compilerOptions;
|
||||||
options.verbose = false;
|
options.verbose = false;
|
||||||
options.sourceMap = true;
|
options.sourceMap = true;
|
||||||
if (process.env['VSCODE_NO_SOURCEMAP']) { // To be used by developers in a hurry
|
if (process.env['VSCODE_NO_SOURCEMAP']) { // To be used by developers in a hurry
|
||||||
@@ -28,8 +29,10 @@ if (process.env['VSCODE_NO_SOURCEMAP']) { // To be used by developers in a hurry
|
|||||||
options.rootDir = rootDir;
|
options.rootDir = rootDir;
|
||||||
options.sourceRoot = util.toFileUri(rootDir);
|
options.sourceRoot = util.toFileUri(rootDir);
|
||||||
options.newLine = /\r\n/.test(fs.readFileSync(__filename, 'utf8')) ? 'CRLF' : 'LF';
|
options.newLine = /\r\n/.test(fs.readFileSync(__filename, 'utf8')) ? 'CRLF' : 'LF';
|
||||||
function createCompile(build, emitError) {
|
return options;
|
||||||
var opts = _.clone(options);
|
}
|
||||||
|
function createCompile(src, build, emitError) {
|
||||||
|
var opts = _.clone(getTypeScriptCompilerOptions(src));
|
||||||
opts.inlineSources = !!build;
|
opts.inlineSources = !!build;
|
||||||
opts.noFilesystemLookup = true;
|
opts.noFilesystemLookup = true;
|
||||||
var ts = tsb.create(opts, null, null, function (err) { return reporter(err.toString()); });
|
var ts = tsb.create(opts, null, null, function (err) { return reporter(err.toString()); });
|
||||||
@@ -51,31 +54,31 @@ function createCompile(build, emitError) {
|
|||||||
.pipe(sourcemaps.write('.', {
|
.pipe(sourcemaps.write('.', {
|
||||||
addComment: false,
|
addComment: false,
|
||||||
includeContent: !!build,
|
includeContent: !!build,
|
||||||
sourceRoot: options.sourceRoot
|
sourceRoot: opts.sourceRoot
|
||||||
}))
|
}))
|
||||||
.pipe(tsFilter.restore)
|
.pipe(tsFilter.restore)
|
||||||
.pipe(reporter.end(emitError));
|
.pipe(reporter.end(emitError));
|
||||||
return es.duplex(input, output);
|
return es.duplex(input, output);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
function compileTask(out, build) {
|
function compileTask(src, out, build) {
|
||||||
return function () {
|
return function () {
|
||||||
var compile = createCompile(build, true);
|
var compile = createCompile(src, build, true);
|
||||||
var src = es.merge(gulp.src('src/**', { base: 'src' }), gulp.src('node_modules/typescript/lib/lib.d.ts'));
|
var srcPipe = es.merge(gulp.src(src + "/**", { base: "" + src }), gulp.src('node_modules/typescript/lib/lib.d.ts'));
|
||||||
// Do not write .d.ts files to disk, as they are not needed there.
|
// Do not write .d.ts files to disk, as they are not needed there.
|
||||||
var dtsFilter = util.filter(function (data) { return !/\.d\.ts$/.test(data.path); });
|
var dtsFilter = util.filter(function (data) { return !/\.d\.ts$/.test(data.path); });
|
||||||
return src
|
return srcPipe
|
||||||
.pipe(compile())
|
.pipe(compile())
|
||||||
.pipe(dtsFilter)
|
.pipe(dtsFilter)
|
||||||
.pipe(gulp.dest(out))
|
.pipe(gulp.dest(out))
|
||||||
.pipe(dtsFilter.restore)
|
.pipe(dtsFilter.restore)
|
||||||
.pipe(monacodtsTask(out, false));
|
.pipe(src !== 'src' ? es.through() : monacodtsTask(out, false));
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
exports.compileTask = compileTask;
|
exports.compileTask = compileTask;
|
||||||
function watchTask(out, build) {
|
function watchTask(out, build) {
|
||||||
return function () {
|
return function () {
|
||||||
var compile = createCompile(build);
|
var compile = createCompile('src', build);
|
||||||
var src = es.merge(gulp.src('src/**', { base: 'src' }), gulp.src('node_modules/typescript/lib/lib.d.ts'));
|
var src = es.merge(gulp.src('src/**', { base: 'src' }), gulp.src('node_modules/typescript/lib/lib.d.ts'));
|
||||||
var watchSrc = watch('src/**', { base: 'src' });
|
var watchSrc = watch('src/**', { base: 'src' });
|
||||||
// Do not write .d.ts files to disk, as they are not needed there.
|
// Do not write .d.ts files to disk, as they are not needed there.
|
||||||
@@ -122,6 +125,7 @@ function monacodtsTask(out, isWatch) {
|
|||||||
fs.writeFileSync(result.filePath, result.content);
|
fs.writeFileSync(result.filePath, result.content);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
fs.writeFileSync(result.filePath, result.content);
|
||||||
resultStream.emit('error', 'monaco.d.ts is no longer up to date. Please run gulp watch and commit the new file.');
|
resultStream.emit('error', 'monaco.d.ts is no longer up to date. Please run gulp watch and commit the new file.');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -21,8 +21,9 @@ import * as fs from 'fs';
|
|||||||
|
|
||||||
const reporter = createReporter();
|
const reporter = createReporter();
|
||||||
|
|
||||||
const rootDir = path.join(__dirname, '../../src');
|
function getTypeScriptCompilerOptions(src: string) {
|
||||||
const options = require('../../src/tsconfig.json').compilerOptions;
|
const rootDir = path.join(__dirname, `../../${src}`);
|
||||||
|
const options = require(`../../${src}/tsconfig.json`).compilerOptions;
|
||||||
options.verbose = false;
|
options.verbose = false;
|
||||||
options.sourceMap = true;
|
options.sourceMap = true;
|
||||||
if (process.env['VSCODE_NO_SOURCEMAP']) { // To be used by developers in a hurry
|
if (process.env['VSCODE_NO_SOURCEMAP']) { // To be used by developers in a hurry
|
||||||
@@ -31,9 +32,11 @@ if (process.env['VSCODE_NO_SOURCEMAP']) { // To be used by developers in a hurry
|
|||||||
options.rootDir = rootDir;
|
options.rootDir = rootDir;
|
||||||
options.sourceRoot = util.toFileUri(rootDir);
|
options.sourceRoot = util.toFileUri(rootDir);
|
||||||
options.newLine = /\r\n/.test(fs.readFileSync(__filename, 'utf8')) ? 'CRLF' : 'LF';
|
options.newLine = /\r\n/.test(fs.readFileSync(__filename, 'utf8')) ? 'CRLF' : 'LF';
|
||||||
|
return options;
|
||||||
|
}
|
||||||
|
|
||||||
function createCompile(build: boolean, emitError?: boolean): (token?: util.ICancellationToken) => NodeJS.ReadWriteStream {
|
function createCompile(src: string, build: boolean, emitError?: boolean): (token?: util.ICancellationToken) => NodeJS.ReadWriteStream {
|
||||||
const opts = _.clone(options);
|
const opts = _.clone(getTypeScriptCompilerOptions(src));
|
||||||
opts.inlineSources = !!build;
|
opts.inlineSources = !!build;
|
||||||
opts.noFilesystemLookup = true;
|
opts.noFilesystemLookup = true;
|
||||||
|
|
||||||
@@ -59,7 +62,7 @@ function createCompile(build: boolean, emitError?: boolean): (token?: util.ICanc
|
|||||||
.pipe(sourcemaps.write('.', {
|
.pipe(sourcemaps.write('.', {
|
||||||
addComment: false,
|
addComment: false,
|
||||||
includeContent: !!build,
|
includeContent: !!build,
|
||||||
sourceRoot: options.sourceRoot
|
sourceRoot: opts.sourceRoot
|
||||||
}))
|
}))
|
||||||
.pipe(tsFilter.restore)
|
.pipe(tsFilter.restore)
|
||||||
.pipe(reporter.end(emitError));
|
.pipe(reporter.end(emitError));
|
||||||
@@ -68,32 +71,32 @@ function createCompile(build: boolean, emitError?: boolean): (token?: util.ICanc
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function compileTask(out: string, build: boolean): () => NodeJS.ReadWriteStream {
|
export function compileTask(src: string, out: string, build: boolean): () => NodeJS.ReadWriteStream {
|
||||||
|
|
||||||
return function () {
|
return function () {
|
||||||
const compile = createCompile(build, true);
|
const compile = createCompile(src, build, true);
|
||||||
|
|
||||||
const src = es.merge(
|
const srcPipe = es.merge(
|
||||||
gulp.src('src/**', { base: 'src' }),
|
gulp.src(`${src}/**`, { base: `${src}` }),
|
||||||
gulp.src('node_modules/typescript/lib/lib.d.ts'),
|
gulp.src('node_modules/typescript/lib/lib.d.ts'),
|
||||||
);
|
);
|
||||||
|
|
||||||
// Do not write .d.ts files to disk, as they are not needed there.
|
// Do not write .d.ts files to disk, as they are not needed there.
|
||||||
const dtsFilter = util.filter(data => !/\.d\.ts$/.test(data.path));
|
const dtsFilter = util.filter(data => !/\.d\.ts$/.test(data.path));
|
||||||
|
|
||||||
return src
|
return srcPipe
|
||||||
.pipe(compile())
|
.pipe(compile())
|
||||||
.pipe(dtsFilter)
|
.pipe(dtsFilter)
|
||||||
.pipe(gulp.dest(out))
|
.pipe(gulp.dest(out))
|
||||||
.pipe(dtsFilter.restore)
|
.pipe(dtsFilter.restore)
|
||||||
.pipe(monacodtsTask(out, false));
|
.pipe(src !== 'src' ? es.through() : monacodtsTask(out, false));
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function watchTask(out: string, build: boolean): () => NodeJS.ReadWriteStream {
|
export function watchTask(out: string, build: boolean): () => NodeJS.ReadWriteStream {
|
||||||
|
|
||||||
return function () {
|
return function () {
|
||||||
const compile = createCompile(build);
|
const compile = createCompile('src', build);
|
||||||
|
|
||||||
const src = es.merge(
|
const src = es.merge(
|
||||||
gulp.src('src/**', { base: 'src' }),
|
gulp.src('src/**', { base: 'src' }),
|
||||||
@@ -150,6 +153,7 @@ function monacodtsTask(out: string, isWatch: boolean): NodeJS.ReadWriteStream {
|
|||||||
if (isWatch) {
|
if (isWatch) {
|
||||||
fs.writeFileSync(result.filePath, result.content);
|
fs.writeFileSync(result.filePath, result.content);
|
||||||
} else {
|
} else {
|
||||||
|
fs.writeFileSync(result.filePath, result.content);
|
||||||
resultStream.emit('error', 'monaco.d.ts is no longer up to date. Please run gulp watch and commit the new file.');
|
resultStream.emit('error', 'monaco.d.ts is no longer up to date. Please run gulp watch and commit the new file.');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -44,6 +44,7 @@ function error(err) {
|
|||||||
var baseHeaders = {
|
var baseHeaders = {
|
||||||
'X-Market-Client-Id': 'VSCode Build',
|
'X-Market-Client-Id': 'VSCode Build',
|
||||||
'User-Agent': 'VSCode Build',
|
'User-Agent': 'VSCode Build',
|
||||||
|
'X-Market-User-Id': '291C1CD0-051A-4123-9B4B-30D60EF52EE2',
|
||||||
};
|
};
|
||||||
function fromMarketplace(extensionName, version) {
|
function fromMarketplace(extensionName, version) {
|
||||||
var filterType = 7;
|
var filterType = 7;
|
||||||
|
|||||||
@@ -49,6 +49,7 @@ function error(err: any): Stream {
|
|||||||
const baseHeaders = {
|
const baseHeaders = {
|
||||||
'X-Market-Client-Id': 'VSCode Build',
|
'X-Market-Client-Id': 'VSCode Build',
|
||||||
'User-Agent': 'VSCode Build',
|
'User-Agent': 'VSCode Build',
|
||||||
|
'X-Market-User-Id': '291C1CD0-051A-4123-9B4B-30D60EF52EE2',
|
||||||
};
|
};
|
||||||
|
|
||||||
export function fromMarketplace(extensionName: string, version: string): Stream {
|
export function fromMarketplace(extensionName: string, version: string): Stream {
|
||||||
|
|||||||
@@ -34,6 +34,10 @@
|
|||||||
"name": "vs/workbench/parts/codeEditor",
|
"name": "vs/workbench/parts/codeEditor",
|
||||||
"project": "vscode-workbench"
|
"project": "vscode-workbench"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "vs/workbench/parts/comments",
|
||||||
|
"project": "vscode-workbench"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "vs/workbench/parts/debug",
|
"name": "vs/workbench/parts/debug",
|
||||||
"project": "vscode-workbench"
|
"project": "vscode-workbench"
|
||||||
@@ -74,6 +78,10 @@
|
|||||||
"name": "vs/workbench/parts/logs",
|
"name": "vs/workbench/parts/logs",
|
||||||
"project": "vscode-workbench"
|
"project": "vscode-workbench"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "vs/workbench/parts/navigation",
|
||||||
|
"project": "vscode-workbench"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "vs/workbench/parts/output",
|
"name": "vs/workbench/parts/output",
|
||||||
"project": "vscode-workbench"
|
"project": "vscode-workbench"
|
||||||
@@ -146,10 +154,18 @@
|
|||||||
"name": "vs/workbench/parts/welcome",
|
"name": "vs/workbench/parts/welcome",
|
||||||
"project": "vscode-workbench"
|
"project": "vscode-workbench"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "vs/workbench/parts/outline",
|
||||||
|
"project": "vscode-workbench"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "vs/workbench/services/actions",
|
"name": "vs/workbench/services/actions",
|
||||||
"project": "vscode-workbench"
|
"project": "vscode-workbench"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "vs/workbench/services/bulkEdit",
|
||||||
|
"project": "vscode-workbench"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "vs/workbench/services/configuration",
|
"name": "vs/workbench/services/configuration",
|
||||||
"project": "vscode-workbench"
|
"project": "vscode-workbench"
|
||||||
|
|||||||
@@ -17,7 +17,6 @@ var concat = require("gulp-concat");
|
|||||||
var VinylFile = require("vinyl");
|
var VinylFile = require("vinyl");
|
||||||
var bundle = require("./bundle");
|
var bundle = require("./bundle");
|
||||||
var util = require("./util");
|
var util = require("./util");
|
||||||
var i18n = require("./i18n");
|
|
||||||
var gulpUtil = require("gulp-util");
|
var gulpUtil = require("gulp-util");
|
||||||
var flatmap = require("gulp-flatmap");
|
var flatmap = require("gulp-flatmap");
|
||||||
var pump = require("pump");
|
var pump = require("pump");
|
||||||
@@ -40,19 +39,19 @@ function loaderConfig(emptyPaths) {
|
|||||||
}
|
}
|
||||||
exports.loaderConfig = loaderConfig;
|
exports.loaderConfig = loaderConfig;
|
||||||
var IS_OUR_COPYRIGHT_REGEXP = /Copyright \(C\) Microsoft Corporation/i;
|
var IS_OUR_COPYRIGHT_REGEXP = /Copyright \(C\) Microsoft Corporation/i;
|
||||||
function loader(bundledFileHeader, bundleLoader) {
|
function loader(src, bundledFileHeader, bundleLoader) {
|
||||||
var sources = [
|
var sources = [
|
||||||
'out-build/vs/loader.js'
|
src + "/vs/loader.js"
|
||||||
];
|
];
|
||||||
if (bundleLoader) {
|
if (bundleLoader) {
|
||||||
sources = sources.concat([
|
sources = sources.concat([
|
||||||
'out-build/vs/css.js',
|
src + "/vs/css.js",
|
||||||
'out-build/vs/nls.js'
|
src + "/vs/nls.js"
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
var isFirst = true;
|
var isFirst = true;
|
||||||
return (gulp
|
return (gulp
|
||||||
.src(sources, { base: 'out-build' })
|
.src(sources, { base: "" + src })
|
||||||
.pipe(es.through(function (data) {
|
.pipe(es.through(function (data) {
|
||||||
if (isFirst) {
|
if (isFirst) {
|
||||||
isFirst = false;
|
isFirst = false;
|
||||||
@@ -74,7 +73,7 @@ function loader(bundledFileHeader, bundleLoader) {
|
|||||||
return f;
|
return f;
|
||||||
})));
|
})));
|
||||||
}
|
}
|
||||||
function toConcatStream(bundledFileHeader, sources, dest) {
|
function toConcatStream(src, bundledFileHeader, sources, dest) {
|
||||||
var useSourcemaps = /\.js$/.test(dest) && !/\.nls\.js$/.test(dest);
|
var useSourcemaps = /\.js$/.test(dest) && !/\.nls\.js$/.test(dest);
|
||||||
// If a bundle ends up including in any of the sources our copyright, then
|
// If a bundle ends up including in any of the sources our copyright, then
|
||||||
// insert a fake source at the beginning of each bundle with our copyright
|
// insert a fake source at the beginning of each bundle with our copyright
|
||||||
@@ -94,7 +93,7 @@ function toConcatStream(bundledFileHeader, sources, dest) {
|
|||||||
}
|
}
|
||||||
var treatedSources = sources.map(function (source) {
|
var treatedSources = sources.map(function (source) {
|
||||||
var root = source.path ? REPO_ROOT_PATH.replace(/\\/g, '/') : '';
|
var root = source.path ? REPO_ROOT_PATH.replace(/\\/g, '/') : '';
|
||||||
var base = source.path ? root + '/out-build' : '';
|
var base = source.path ? root + ("/" + src) : '';
|
||||||
return new VinylFile({
|
return new VinylFile({
|
||||||
path: source.path ? root + '/' + source.path.replace(/\\/g, '/') : 'fake',
|
path: source.path ? root + '/' + source.path.replace(/\\/g, '/') : 'fake',
|
||||||
base: base,
|
base: base,
|
||||||
@@ -105,12 +104,13 @@ function toConcatStream(bundledFileHeader, sources, dest) {
|
|||||||
.pipe(useSourcemaps ? util.loadSourcemaps() : es.through())
|
.pipe(useSourcemaps ? util.loadSourcemaps() : es.through())
|
||||||
.pipe(concat(dest));
|
.pipe(concat(dest));
|
||||||
}
|
}
|
||||||
function toBundleStream(bundledFileHeader, bundles) {
|
function toBundleStream(src, bundledFileHeader, bundles) {
|
||||||
return es.merge(bundles.map(function (bundle) {
|
return es.merge(bundles.map(function (bundle) {
|
||||||
return toConcatStream(bundledFileHeader, bundle.sources, bundle.dest);
|
return toConcatStream(src, bundledFileHeader, bundle.sources, bundle.dest);
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
function optimizeTask(opts) {
|
function optimizeTask(opts) {
|
||||||
|
var src = opts.src;
|
||||||
var entryPoints = opts.entryPoints;
|
var entryPoints = opts.entryPoints;
|
||||||
var otherSources = opts.otherSources;
|
var otherSources = opts.otherSources;
|
||||||
var resources = opts.resources;
|
var resources = opts.resources;
|
||||||
@@ -126,7 +126,7 @@ function optimizeTask(opts) {
|
|||||||
if (err) {
|
if (err) {
|
||||||
return bundlesStream.emit('error', JSON.stringify(err));
|
return bundlesStream.emit('error', JSON.stringify(err));
|
||||||
}
|
}
|
||||||
toBundleStream(bundledFileHeader, result.files).pipe(bundlesStream);
|
toBundleStream(src, bundledFileHeader, result.files).pipe(bundlesStream);
|
||||||
// Remove css inlined resources
|
// Remove css inlined resources
|
||||||
var filteredResources = resources.slice();
|
var filteredResources = resources.slice();
|
||||||
result.cssInlinedResources.forEach(function (resource) {
|
result.cssInlinedResources.forEach(function (resource) {
|
||||||
@@ -135,7 +135,7 @@ function optimizeTask(opts) {
|
|||||||
}
|
}
|
||||||
filteredResources.push('!' + resource);
|
filteredResources.push('!' + resource);
|
||||||
});
|
});
|
||||||
gulp.src(filteredResources, { base: 'out-build' }).pipe(resourcesStream);
|
gulp.src(filteredResources, { base: "" + src }).pipe(resourcesStream);
|
||||||
var bundleInfoArray = [];
|
var bundleInfoArray = [];
|
||||||
if (opts.bundleInfo) {
|
if (opts.bundleInfo) {
|
||||||
bundleInfoArray.push(new VinylFile({
|
bundleInfoArray.push(new VinylFile({
|
||||||
@@ -148,9 +148,9 @@ function optimizeTask(opts) {
|
|||||||
});
|
});
|
||||||
var otherSourcesStream = es.through();
|
var otherSourcesStream = es.through();
|
||||||
var otherSourcesStreamArr = [];
|
var otherSourcesStreamArr = [];
|
||||||
gulp.src(otherSources, { base: 'out-build' })
|
gulp.src(otherSources, { base: "" + src })
|
||||||
.pipe(es.through(function (data) {
|
.pipe(es.through(function (data) {
|
||||||
otherSourcesStreamArr.push(toConcatStream(bundledFileHeader, [data], data.relative));
|
otherSourcesStreamArr.push(toConcatStream(src, bundledFileHeader, [data], data.relative));
|
||||||
}, function () {
|
}, function () {
|
||||||
if (!otherSourcesStreamArr.length) {
|
if (!otherSourcesStreamArr.length) {
|
||||||
setTimeout(function () { otherSourcesStream.emit('end'); }, 0);
|
setTimeout(function () { otherSourcesStream.emit('end'); }, 0);
|
||||||
@@ -159,16 +159,12 @@ function optimizeTask(opts) {
|
|||||||
es.merge(otherSourcesStreamArr).pipe(otherSourcesStream);
|
es.merge(otherSourcesStreamArr).pipe(otherSourcesStream);
|
||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
var result = es.merge(loader(bundledFileHeader, bundleLoader), bundlesStream, otherSourcesStream, resourcesStream, bundleInfoStream);
|
var result = es.merge(loader(src, bundledFileHeader, bundleLoader), bundlesStream, otherSourcesStream, resourcesStream, bundleInfoStream);
|
||||||
return result
|
return result
|
||||||
.pipe(sourcemaps.write('./', {
|
.pipe(sourcemaps.write('./', {
|
||||||
sourceRoot: null,
|
sourceRoot: null,
|
||||||
addComment: true,
|
addComment: true,
|
||||||
includeContent: true
|
includeContent: true
|
||||||
}))
|
|
||||||
.pipe(i18n.processNlsFiles({
|
|
||||||
fileHeader: bundledFileHeader,
|
|
||||||
languages: opts.languages
|
|
||||||
}))
|
}))
|
||||||
.pipe(gulp.dest(out));
|
.pipe(gulp.dest(out));
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -18,11 +18,11 @@ import * as concat from 'gulp-concat';
|
|||||||
import * as VinylFile from 'vinyl';
|
import * as VinylFile from 'vinyl';
|
||||||
import * as bundle from './bundle';
|
import * as bundle from './bundle';
|
||||||
import * as util from './util';
|
import * as util from './util';
|
||||||
import * as i18n from './i18n';
|
|
||||||
import * as gulpUtil from 'gulp-util';
|
import * as gulpUtil from 'gulp-util';
|
||||||
import * as flatmap from 'gulp-flatmap';
|
import * as flatmap from 'gulp-flatmap';
|
||||||
import * as pump from 'pump';
|
import * as pump from 'pump';
|
||||||
import * as sm from 'source-map';
|
import * as sm from 'source-map';
|
||||||
|
import { Language } from './i18n';
|
||||||
|
|
||||||
const REPO_ROOT_PATH = path.join(__dirname, '../..');
|
const REPO_ROOT_PATH = path.join(__dirname, '../..');
|
||||||
|
|
||||||
@@ -52,21 +52,21 @@ declare class FileSourceMap extends VinylFile {
|
|||||||
public sourceMap: sm.RawSourceMap;
|
public sourceMap: sm.RawSourceMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
function loader(bundledFileHeader: string, bundleLoader: boolean): NodeJS.ReadWriteStream {
|
function loader(src: string, bundledFileHeader: string, bundleLoader: boolean): NodeJS.ReadWriteStream {
|
||||||
let sources = [
|
let sources = [
|
||||||
'out-build/vs/loader.js'
|
`${src}/vs/loader.js`
|
||||||
];
|
];
|
||||||
if (bundleLoader) {
|
if (bundleLoader) {
|
||||||
sources = sources.concat([
|
sources = sources.concat([
|
||||||
'out-build/vs/css.js',
|
`${src}/vs/css.js`,
|
||||||
'out-build/vs/nls.js'
|
`${src}/vs/nls.js`
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
let isFirst = true;
|
let isFirst = true;
|
||||||
return (
|
return (
|
||||||
gulp
|
gulp
|
||||||
.src(sources, { base: 'out-build' })
|
.src(sources, { base: `${src}` })
|
||||||
.pipe(es.through(function (data) {
|
.pipe(es.through(function (data) {
|
||||||
if (isFirst) {
|
if (isFirst) {
|
||||||
isFirst = false;
|
isFirst = false;
|
||||||
@@ -89,7 +89,7 @@ function loader(bundledFileHeader: string, bundleLoader: boolean): NodeJS.ReadWr
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function toConcatStream(bundledFileHeader: string, sources: bundle.IFile[], dest: string): NodeJS.ReadWriteStream {
|
function toConcatStream(src: string, bundledFileHeader: string, sources: bundle.IFile[], dest: string): NodeJS.ReadWriteStream {
|
||||||
const useSourcemaps = /\.js$/.test(dest) && !/\.nls\.js$/.test(dest);
|
const useSourcemaps = /\.js$/.test(dest) && !/\.nls\.js$/.test(dest);
|
||||||
|
|
||||||
// If a bundle ends up including in any of the sources our copyright, then
|
// If a bundle ends up including in any of the sources our copyright, then
|
||||||
@@ -112,7 +112,7 @@ function toConcatStream(bundledFileHeader: string, sources: bundle.IFile[], dest
|
|||||||
|
|
||||||
const treatedSources = sources.map(function (source) {
|
const treatedSources = sources.map(function (source) {
|
||||||
const root = source.path ? REPO_ROOT_PATH.replace(/\\/g, '/') : '';
|
const root = source.path ? REPO_ROOT_PATH.replace(/\\/g, '/') : '';
|
||||||
const base = source.path ? root + '/out-build' : '';
|
const base = source.path ? root + `/${src}` : '';
|
||||||
|
|
||||||
return new VinylFile({
|
return new VinylFile({
|
||||||
path: source.path ? root + '/' + source.path.replace(/\\/g, '/') : 'fake',
|
path: source.path ? root + '/' + source.path.replace(/\\/g, '/') : 'fake',
|
||||||
@@ -126,13 +126,17 @@ function toConcatStream(bundledFileHeader: string, sources: bundle.IFile[], dest
|
|||||||
.pipe(concat(dest));
|
.pipe(concat(dest));
|
||||||
}
|
}
|
||||||
|
|
||||||
function toBundleStream(bundledFileHeader: string, bundles: bundle.IConcatFile[]): NodeJS.ReadWriteStream {
|
function toBundleStream(src:string, bundledFileHeader: string, bundles: bundle.IConcatFile[]): NodeJS.ReadWriteStream {
|
||||||
return es.merge(bundles.map(function (bundle) {
|
return es.merge(bundles.map(function (bundle) {
|
||||||
return toConcatStream(bundledFileHeader, bundle.sources, bundle.dest);
|
return toConcatStream(src, bundledFileHeader, bundle.sources, bundle.dest);
|
||||||
}));
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface IOptimizeTaskOpts {
|
export interface IOptimizeTaskOpts {
|
||||||
|
/**
|
||||||
|
* The folder to read files from.
|
||||||
|
*/
|
||||||
|
src: string;
|
||||||
/**
|
/**
|
||||||
* (for AMD files, will get bundled and get Copyright treatment)
|
* (for AMD files, will get bundled and get Copyright treatment)
|
||||||
*/
|
*/
|
||||||
@@ -163,11 +167,13 @@ export interface IOptimizeTaskOpts {
|
|||||||
*/
|
*/
|
||||||
out: string;
|
out: string;
|
||||||
/**
|
/**
|
||||||
* (languages to process)
|
* (out folder name)
|
||||||
*/
|
*/
|
||||||
languages: i18n.Language[];
|
languages?: Language[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export function optimizeTask(opts: IOptimizeTaskOpts): () => NodeJS.ReadWriteStream {
|
export function optimizeTask(opts: IOptimizeTaskOpts): () => NodeJS.ReadWriteStream {
|
||||||
|
const src = opts.src;
|
||||||
const entryPoints = opts.entryPoints;
|
const entryPoints = opts.entryPoints;
|
||||||
const otherSources = opts.otherSources;
|
const otherSources = opts.otherSources;
|
||||||
const resources = opts.resources;
|
const resources = opts.resources;
|
||||||
@@ -184,7 +190,7 @@ export function optimizeTask(opts: IOptimizeTaskOpts): () => NodeJS.ReadWriteStr
|
|||||||
bundle.bundle(entryPoints, loaderConfig, function (err, result) {
|
bundle.bundle(entryPoints, loaderConfig, function (err, result) {
|
||||||
if (err) { return bundlesStream.emit('error', JSON.stringify(err)); }
|
if (err) { return bundlesStream.emit('error', JSON.stringify(err)); }
|
||||||
|
|
||||||
toBundleStream(bundledFileHeader, result.files).pipe(bundlesStream);
|
toBundleStream(src, bundledFileHeader, result.files).pipe(bundlesStream);
|
||||||
|
|
||||||
// Remove css inlined resources
|
// Remove css inlined resources
|
||||||
const filteredResources = resources.slice();
|
const filteredResources = resources.slice();
|
||||||
@@ -194,7 +200,7 @@ export function optimizeTask(opts: IOptimizeTaskOpts): () => NodeJS.ReadWriteStr
|
|||||||
}
|
}
|
||||||
filteredResources.push('!' + resource);
|
filteredResources.push('!' + resource);
|
||||||
});
|
});
|
||||||
gulp.src(filteredResources, { base: 'out-build' }).pipe(resourcesStream);
|
gulp.src(filteredResources, { base: `${src}` }).pipe(resourcesStream);
|
||||||
|
|
||||||
const bundleInfoArray: VinylFile[] = [];
|
const bundleInfoArray: VinylFile[] = [];
|
||||||
if (opts.bundleInfo) {
|
if (opts.bundleInfo) {
|
||||||
@@ -210,9 +216,9 @@ export function optimizeTask(opts: IOptimizeTaskOpts): () => NodeJS.ReadWriteStr
|
|||||||
const otherSourcesStream = es.through();
|
const otherSourcesStream = es.through();
|
||||||
const otherSourcesStreamArr: NodeJS.ReadWriteStream[] = [];
|
const otherSourcesStreamArr: NodeJS.ReadWriteStream[] = [];
|
||||||
|
|
||||||
gulp.src(otherSources, { base: 'out-build' })
|
gulp.src(otherSources, { base: `${src}` })
|
||||||
.pipe(es.through(function (data) {
|
.pipe(es.through(function (data) {
|
||||||
otherSourcesStreamArr.push(toConcatStream(bundledFileHeader, [data], data.relative));
|
otherSourcesStreamArr.push(toConcatStream(src, bundledFileHeader, [data], data.relative));
|
||||||
}, function () {
|
}, function () {
|
||||||
if (!otherSourcesStreamArr.length) {
|
if (!otherSourcesStreamArr.length) {
|
||||||
setTimeout(function () { otherSourcesStream.emit('end'); }, 0);
|
setTimeout(function () { otherSourcesStream.emit('end'); }, 0);
|
||||||
@@ -222,7 +228,7 @@ export function optimizeTask(opts: IOptimizeTaskOpts): () => NodeJS.ReadWriteStr
|
|||||||
}));
|
}));
|
||||||
|
|
||||||
const result = es.merge(
|
const result = es.merge(
|
||||||
loader(bundledFileHeader, bundleLoader),
|
loader(src, bundledFileHeader, bundleLoader),
|
||||||
bundlesStream,
|
bundlesStream,
|
||||||
otherSourcesStream,
|
otherSourcesStream,
|
||||||
resourcesStream,
|
resourcesStream,
|
||||||
@@ -235,10 +241,6 @@ export function optimizeTask(opts: IOptimizeTaskOpts): () => NodeJS.ReadWriteStr
|
|||||||
addComment: true,
|
addComment: true,
|
||||||
includeContent: true
|
includeContent: true
|
||||||
}))
|
}))
|
||||||
.pipe(i18n.processNlsFiles({
|
|
||||||
fileHeader: bundledFileHeader,
|
|
||||||
languages: opts.languages
|
|
||||||
}))
|
|
||||||
.pipe(gulp.dest(out));
|
.pipe(gulp.dest(out));
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,9 +7,93 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|||||||
var ts = require("typescript");
|
var ts = require("typescript");
|
||||||
var fs = require("fs");
|
var fs = require("fs");
|
||||||
var path = require("path");
|
var path = require("path");
|
||||||
|
var tss = require("./treeshaking");
|
||||||
var REPO_ROOT = path.join(__dirname, '../../');
|
var REPO_ROOT = path.join(__dirname, '../../');
|
||||||
var SRC_DIR = path.join(REPO_ROOT, 'src');
|
var SRC_DIR = path.join(REPO_ROOT, 'src');
|
||||||
var OUT_EDITOR = path.join(REPO_ROOT, 'out-editor');
|
var OUT_EDITOR = path.join(REPO_ROOT, 'out-editor');
|
||||||
|
var dirCache = {};
|
||||||
|
function writeFile(filePath, contents) {
|
||||||
|
function ensureDirs(dirPath) {
|
||||||
|
if (dirCache[dirPath]) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
dirCache[dirPath] = true;
|
||||||
|
ensureDirs(path.dirname(dirPath));
|
||||||
|
if (fs.existsSync(dirPath)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
fs.mkdirSync(dirPath);
|
||||||
|
}
|
||||||
|
ensureDirs(path.dirname(filePath));
|
||||||
|
fs.writeFileSync(filePath, contents);
|
||||||
|
}
|
||||||
|
function extractEditor(options) {
|
||||||
|
var result = tss.shake(options);
|
||||||
|
for (var fileName in result) {
|
||||||
|
if (result.hasOwnProperty(fileName)) {
|
||||||
|
writeFile(path.join(options.destRoot, fileName), result[fileName]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var copied = {};
|
||||||
|
var copyFile = function (fileName) {
|
||||||
|
if (copied[fileName]) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
copied[fileName] = true;
|
||||||
|
var srcPath = path.join(options.sourcesRoot, fileName);
|
||||||
|
var dstPath = path.join(options.destRoot, fileName);
|
||||||
|
writeFile(dstPath, fs.readFileSync(srcPath));
|
||||||
|
};
|
||||||
|
var writeOutputFile = function (fileName, contents) {
|
||||||
|
writeFile(path.join(options.destRoot, fileName), contents);
|
||||||
|
};
|
||||||
|
for (var fileName in result) {
|
||||||
|
if (result.hasOwnProperty(fileName)) {
|
||||||
|
var fileContents = result[fileName];
|
||||||
|
var info = ts.preProcessFile(fileContents);
|
||||||
|
for (var i = info.importedFiles.length - 1; i >= 0; i--) {
|
||||||
|
var importedFileName = info.importedFiles[i].fileName;
|
||||||
|
var importedFilePath = void 0;
|
||||||
|
if (/^vs\/css!/.test(importedFileName)) {
|
||||||
|
importedFilePath = importedFileName.substr('vs/css!'.length) + '.css';
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
importedFilePath = importedFileName;
|
||||||
|
}
|
||||||
|
if (/(^\.\/)|(^\.\.\/)/.test(importedFilePath)) {
|
||||||
|
importedFilePath = path.join(path.dirname(fileName), importedFilePath);
|
||||||
|
}
|
||||||
|
if (/\.css$/.test(importedFilePath)) {
|
||||||
|
transportCSS(importedFilePath, copyFile, writeOutputFile);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (fs.existsSync(path.join(options.sourcesRoot, importedFilePath + '.js'))) {
|
||||||
|
copyFile(importedFilePath + '.js');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var tsConfig = JSON.parse(fs.readFileSync(path.join(options.sourcesRoot, 'tsconfig.json')).toString());
|
||||||
|
tsConfig.compilerOptions.noUnusedLocals = false;
|
||||||
|
writeOutputFile('tsconfig.json', JSON.stringify(tsConfig, null, '\t'));
|
||||||
|
[
|
||||||
|
'vs/css.build.js',
|
||||||
|
'vs/css.d.ts',
|
||||||
|
'vs/css.js',
|
||||||
|
'vs/loader.js',
|
||||||
|
'vs/monaco.d.ts',
|
||||||
|
'vs/nls.build.js',
|
||||||
|
'vs/nls.d.ts',
|
||||||
|
'vs/nls.js',
|
||||||
|
'vs/nls.mock.ts',
|
||||||
|
'typings/lib.ie11_safe_es6.d.ts',
|
||||||
|
'typings/thenable.d.ts',
|
||||||
|
'typings/es6-promise.d.ts',
|
||||||
|
'typings/require.d.ts',
|
||||||
|
].forEach(copyFile);
|
||||||
|
}
|
||||||
|
exports.extractEditor = extractEditor;
|
||||||
function createESMSourcesAndResources(options) {
|
function createESMSourcesAndResources(options) {
|
||||||
var OUT_FOLDER = path.join(REPO_ROOT, options.outFolder);
|
var OUT_FOLDER = path.join(REPO_ROOT, options.outFolder);
|
||||||
var OUT_RESOURCES_FOLDER = path.join(REPO_ROOT, options.outResourcesFolder);
|
var OUT_RESOURCES_FOLDER = path.join(REPO_ROOT, options.outResourcesFolder);
|
||||||
@@ -94,7 +178,7 @@ function createESMSourcesAndResources(options) {
|
|||||||
options.entryPoints.forEach(function (entryPoint) { return enqueue(entryPoint); });
|
options.entryPoints.forEach(function (entryPoint) { return enqueue(entryPoint); });
|
||||||
while (queue.length > 0) {
|
while (queue.length > 0) {
|
||||||
var module_1 = queue.shift();
|
var module_1 = queue.shift();
|
||||||
if (transportCSS(options, module_1, enqueue, write)) {
|
if (transportCSS(module_1, enqueue, write)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (transportResource(options, module_1, enqueue, write)) {
|
if (transportResource(options, module_1, enqueue, write)) {
|
||||||
@@ -171,7 +255,7 @@ function createESMSourcesAndResources(options) {
|
|||||||
fs.writeFileSync(path.join(OUT_FOLDER, 'vs/monaco.d.ts'), monacodts);
|
fs.writeFileSync(path.join(OUT_FOLDER, 'vs/monaco.d.ts'), monacodts);
|
||||||
}
|
}
|
||||||
exports.createESMSourcesAndResources = createESMSourcesAndResources;
|
exports.createESMSourcesAndResources = createESMSourcesAndResources;
|
||||||
function transportCSS(options, module, enqueue, write) {
|
function transportCSS(module, enqueue, write) {
|
||||||
if (!/\.css/.test(module)) {
|
if (!/\.css/.test(module)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@@ -179,10 +263,10 @@ function transportCSS(options, module, enqueue, write) {
|
|||||||
var fileContents = fs.readFileSync(filename).toString();
|
var fileContents = fs.readFileSync(filename).toString();
|
||||||
var inlineResources = 'base64'; // see https://github.com/Microsoft/monaco-editor/issues/148
|
var inlineResources = 'base64'; // see https://github.com/Microsoft/monaco-editor/issues/148
|
||||||
var inlineResourcesLimit = 300000; //3000; // see https://github.com/Microsoft/monaco-editor/issues/336
|
var inlineResourcesLimit = 300000; //3000; // see https://github.com/Microsoft/monaco-editor/issues/336
|
||||||
var newContents = _rewriteOrInlineUrls(filename, fileContents, inlineResources === 'base64', inlineResourcesLimit);
|
var newContents = _rewriteOrInlineUrls(fileContents, inlineResources === 'base64', inlineResourcesLimit);
|
||||||
write(module, newContents);
|
write(module, newContents);
|
||||||
return true;
|
return true;
|
||||||
function _rewriteOrInlineUrls(originalFileFSPath, contents, forceBase64, inlineByteLimit) {
|
function _rewriteOrInlineUrls(contents, forceBase64, inlineByteLimit) {
|
||||||
return _replaceURL(contents, function (url) {
|
return _replaceURL(contents, function (url) {
|
||||||
var imagePath = path.join(path.dirname(module), url);
|
var imagePath = path.join(path.dirname(module), url);
|
||||||
var fileContents = fs.readFileSync(path.join(SRC_DIR, imagePath));
|
var fileContents = fs.readFileSync(path.join(SRC_DIR, imagePath));
|
||||||
|
|||||||
@@ -6,11 +6,101 @@
|
|||||||
import * as ts from 'typescript';
|
import * as ts from 'typescript';
|
||||||
import * as fs from 'fs';
|
import * as fs from 'fs';
|
||||||
import * as path from 'path';
|
import * as path from 'path';
|
||||||
|
import * as tss from './treeshaking';
|
||||||
|
|
||||||
const REPO_ROOT = path.join(__dirname, '../../');
|
const REPO_ROOT = path.join(__dirname, '../../');
|
||||||
const SRC_DIR = path.join(REPO_ROOT, 'src');
|
const SRC_DIR = path.join(REPO_ROOT, 'src');
|
||||||
const OUT_EDITOR = path.join(REPO_ROOT, 'out-editor');
|
const OUT_EDITOR = path.join(REPO_ROOT, 'out-editor');
|
||||||
|
|
||||||
|
let dirCache: { [dir: string]: boolean; } = {};
|
||||||
|
|
||||||
|
function writeFile(filePath: string, contents: Buffer | string): void {
|
||||||
|
function ensureDirs(dirPath: string): void {
|
||||||
|
if (dirCache[dirPath]) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
dirCache[dirPath] = true;
|
||||||
|
|
||||||
|
ensureDirs(path.dirname(dirPath));
|
||||||
|
if (fs.existsSync(dirPath)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
fs.mkdirSync(dirPath);
|
||||||
|
}
|
||||||
|
ensureDirs(path.dirname(filePath));
|
||||||
|
fs.writeFileSync(filePath, contents);
|
||||||
|
}
|
||||||
|
|
||||||
|
export function extractEditor(options: tss.ITreeShakingOptions & { destRoot: string }): void {
|
||||||
|
let result = tss.shake(options);
|
||||||
|
for (let fileName in result) {
|
||||||
|
if (result.hasOwnProperty(fileName)) {
|
||||||
|
writeFile(path.join(options.destRoot, fileName), result[fileName]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
let copied: { [fileName:string]: boolean; } = {};
|
||||||
|
const copyFile = (fileName: string) => {
|
||||||
|
if (copied[fileName]) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
copied[fileName] = true;
|
||||||
|
const srcPath = path.join(options.sourcesRoot, fileName);
|
||||||
|
const dstPath = path.join(options.destRoot, fileName);
|
||||||
|
writeFile(dstPath, fs.readFileSync(srcPath));
|
||||||
|
};
|
||||||
|
const writeOutputFile = (fileName: string, contents: string) => {
|
||||||
|
writeFile(path.join(options.destRoot, fileName), contents);
|
||||||
|
};
|
||||||
|
for (let fileName in result) {
|
||||||
|
if (result.hasOwnProperty(fileName)) {
|
||||||
|
const fileContents = result[fileName];
|
||||||
|
const info = ts.preProcessFile(fileContents);
|
||||||
|
|
||||||
|
for (let i = info.importedFiles.length - 1; i >= 0; i--) {
|
||||||
|
const importedFileName = info.importedFiles[i].fileName;
|
||||||
|
|
||||||
|
let importedFilePath: string;
|
||||||
|
if (/^vs\/css!/.test(importedFileName)) {
|
||||||
|
importedFilePath = importedFileName.substr('vs/css!'.length) + '.css';
|
||||||
|
} else {
|
||||||
|
importedFilePath = importedFileName;
|
||||||
|
}
|
||||||
|
if (/(^\.\/)|(^\.\.\/)/.test(importedFilePath)) {
|
||||||
|
importedFilePath = path.join(path.dirname(fileName), importedFilePath);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (/\.css$/.test(importedFilePath)) {
|
||||||
|
transportCSS(importedFilePath, copyFile, writeOutputFile);
|
||||||
|
} else {
|
||||||
|
if (fs.existsSync(path.join(options.sourcesRoot, importedFilePath + '.js'))) {
|
||||||
|
copyFile(importedFilePath + '.js');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const tsConfig = JSON.parse(fs.readFileSync(path.join(options.sourcesRoot, 'tsconfig.json')).toString());
|
||||||
|
tsConfig.compilerOptions.noUnusedLocals = false;
|
||||||
|
writeOutputFile('tsconfig.json', JSON.stringify(tsConfig, null, '\t'));
|
||||||
|
|
||||||
|
[
|
||||||
|
'vs/css.build.js',
|
||||||
|
'vs/css.d.ts',
|
||||||
|
'vs/css.js',
|
||||||
|
'vs/loader.js',
|
||||||
|
'vs/monaco.d.ts',
|
||||||
|
'vs/nls.build.js',
|
||||||
|
'vs/nls.d.ts',
|
||||||
|
'vs/nls.js',
|
||||||
|
'vs/nls.mock.ts',
|
||||||
|
'typings/lib.ie11_safe_es6.d.ts',
|
||||||
|
'typings/thenable.d.ts',
|
||||||
|
'typings/es6-promise.d.ts',
|
||||||
|
'typings/require.d.ts',
|
||||||
|
].forEach(copyFile);
|
||||||
|
}
|
||||||
|
|
||||||
export interface IOptions {
|
export interface IOptions {
|
||||||
entryPoints: string[];
|
entryPoints: string[];
|
||||||
outFolder: string;
|
outFolder: string;
|
||||||
@@ -111,7 +201,7 @@ export function createESMSourcesAndResources(options: IOptions): void {
|
|||||||
|
|
||||||
while (queue.length > 0) {
|
while (queue.length > 0) {
|
||||||
const module = queue.shift();
|
const module = queue.shift();
|
||||||
if (transportCSS(options, module, enqueue, write)) {
|
if (transportCSS(module, enqueue, write)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (transportResource(options, module, enqueue, write)) {
|
if (transportResource(options, module, enqueue, write)) {
|
||||||
@@ -198,7 +288,7 @@ export function createESMSourcesAndResources(options: IOptions): void {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function transportCSS(options: IOptions, module: string, enqueue: (module: string) => void, write: (path: string, contents: string | Buffer) => void): boolean {
|
function transportCSS(module: string, enqueue: (module: string) => void, write: (path: string, contents: string | Buffer) => void): boolean {
|
||||||
|
|
||||||
if (!/\.css/.test(module)) {
|
if (!/\.css/.test(module)) {
|
||||||
return false;
|
return false;
|
||||||
@@ -209,11 +299,11 @@ function transportCSS(options: IOptions, module: string, enqueue: (module: strin
|
|||||||
const inlineResources = 'base64'; // see https://github.com/Microsoft/monaco-editor/issues/148
|
const inlineResources = 'base64'; // see https://github.com/Microsoft/monaco-editor/issues/148
|
||||||
const inlineResourcesLimit = 300000;//3000; // see https://github.com/Microsoft/monaco-editor/issues/336
|
const inlineResourcesLimit = 300000;//3000; // see https://github.com/Microsoft/monaco-editor/issues/336
|
||||||
|
|
||||||
const newContents = _rewriteOrInlineUrls(filename, fileContents, inlineResources === 'base64', inlineResourcesLimit);
|
const newContents = _rewriteOrInlineUrls(fileContents, inlineResources === 'base64', inlineResourcesLimit);
|
||||||
write(module, newContents);
|
write(module, newContents);
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
function _rewriteOrInlineUrls(originalFileFSPath: string, contents: string, forceBase64: boolean, inlineByteLimit: number): string {
|
function _rewriteOrInlineUrls(contents: string, forceBase64: boolean, inlineByteLimit: number): string {
|
||||||
return _replaceURL(contents, (url) => {
|
return _replaceURL(contents, (url) => {
|
||||||
let imagePath = path.join(path.dirname(module), url);
|
let imagePath = path.join(path.dirname(module), url);
|
||||||
let fileContents = fs.readFileSync(path.join(SRC_DIR, imagePath));
|
let fileContents = fs.readFileSync(path.join(SRC_DIR, imagePath));
|
||||||
|
|||||||
@@ -1,56 +0,0 @@
|
|||||||
"use strict";
|
|
||||||
/*---------------------------------------------------------------------------------------------
|
|
||||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
|
||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
|
||||||
*--------------------------------------------------------------------------------------------*/
|
|
||||||
Object.defineProperty(exports, "__esModule", { value: true });
|
|
||||||
var assert = require("assert");
|
|
||||||
var util = require("../util");
|
|
||||||
function getMockTagExists(tags) {
|
|
||||||
return function (tag) { return tags.indexOf(tag) >= 0; };
|
|
||||||
}
|
|
||||||
suite('util tests', function () {
|
|
||||||
test('getPreviousVersion - patch', function () {
|
|
||||||
assert.equal(util.getPreviousVersion('1.2.3', getMockTagExists(['1.2.2', '1.2.1', '1.2.0', '1.1.0'])), '1.2.2');
|
|
||||||
});
|
|
||||||
test('getPreviousVersion - patch invalid', function () {
|
|
||||||
try {
|
|
||||||
util.getPreviousVersion('1.2.2', getMockTagExists(['1.2.0', '1.1.0']));
|
|
||||||
}
|
|
||||||
catch (e) {
|
|
||||||
// expected
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
throw new Error('Expected an exception');
|
|
||||||
});
|
|
||||||
test('getPreviousVersion - minor', function () {
|
|
||||||
assert.equal(util.getPreviousVersion('1.2.0', getMockTagExists(['1.1.0', '1.1.1', '1.1.2', '1.1.3'])), '1.1.3');
|
|
||||||
assert.equal(util.getPreviousVersion('1.2.0', getMockTagExists(['1.1.0', '1.0.0'])), '1.1.0');
|
|
||||||
});
|
|
||||||
test('getPreviousVersion - minor gap', function () {
|
|
||||||
assert.equal(util.getPreviousVersion('1.2.0', getMockTagExists(['1.1.0', '1.1.1', '1.1.3'])), '1.1.1');
|
|
||||||
});
|
|
||||||
test('getPreviousVersion - minor invalid', function () {
|
|
||||||
try {
|
|
||||||
util.getPreviousVersion('1.2.0', getMockTagExists(['1.0.0']));
|
|
||||||
}
|
|
||||||
catch (e) {
|
|
||||||
// expected
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
throw new Error('Expected an exception');
|
|
||||||
});
|
|
||||||
test('getPreviousVersion - major', function () {
|
|
||||||
assert.equal(util.getPreviousVersion('2.0.0', getMockTagExists(['1.0.0', '1.1.0', '1.2.0', '1.2.1', '1.2.2'])), '1.2.2');
|
|
||||||
});
|
|
||||||
test('getPreviousVersion - major invalid', function () {
|
|
||||||
try {
|
|
||||||
util.getPreviousVersion('3.0.0', getMockTagExists(['1.0.0']));
|
|
||||||
}
|
|
||||||
catch (e) {
|
|
||||||
// expected
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
throw new Error('Expected an exception');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
@@ -1,79 +0,0 @@
|
|||||||
/*---------------------------------------------------------------------------------------------
|
|
||||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
|
||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
|
||||||
*--------------------------------------------------------------------------------------------*/
|
|
||||||
|
|
||||||
import assert = require('assert');
|
|
||||||
import util = require('../util');
|
|
||||||
|
|
||||||
function getMockTagExists(tags: string[]) {
|
|
||||||
return (tag: string) => tags.indexOf(tag) >= 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
suite('util tests', () => {
|
|
||||||
test('getPreviousVersion - patch', () => {
|
|
||||||
assert.equal(
|
|
||||||
util.getPreviousVersion('1.2.3', getMockTagExists(['1.2.2', '1.2.1', '1.2.0', '1.1.0'])),
|
|
||||||
'1.2.2'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
test('getPreviousVersion - patch invalid', () => {
|
|
||||||
try {
|
|
||||||
util.getPreviousVersion('1.2.2', getMockTagExists(['1.2.0', '1.1.0']));
|
|
||||||
} catch (e) {
|
|
||||||
// expected
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
throw new Error('Expected an exception');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('getPreviousVersion - minor', () => {
|
|
||||||
assert.equal(
|
|
||||||
util.getPreviousVersion('1.2.0', getMockTagExists(['1.1.0', '1.1.1', '1.1.2', '1.1.3'])),
|
|
||||||
'1.1.3'
|
|
||||||
);
|
|
||||||
|
|
||||||
assert.equal(
|
|
||||||
util.getPreviousVersion('1.2.0', getMockTagExists(['1.1.0', '1.0.0'])),
|
|
||||||
'1.1.0'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
test('getPreviousVersion - minor gap', () => {
|
|
||||||
assert.equal(
|
|
||||||
util.getPreviousVersion('1.2.0', getMockTagExists(['1.1.0', '1.1.1', '1.1.3'])),
|
|
||||||
'1.1.1'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
test('getPreviousVersion - minor invalid', () => {
|
|
||||||
try {
|
|
||||||
util.getPreviousVersion('1.2.0', getMockTagExists(['1.0.0']));
|
|
||||||
} catch (e) {
|
|
||||||
// expected
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
throw new Error('Expected an exception');
|
|
||||||
});
|
|
||||||
|
|
||||||
test('getPreviousVersion - major', () => {
|
|
||||||
assert.equal(
|
|
||||||
util.getPreviousVersion('2.0.0', getMockTagExists(['1.0.0', '1.1.0', '1.2.0', '1.2.1', '1.2.2'])),
|
|
||||||
'1.2.2'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
test('getPreviousVersion - major invalid', () => {
|
|
||||||
try {
|
|
||||||
util.getPreviousVersion('3.0.0', getMockTagExists(['1.0.0']));
|
|
||||||
} catch (e) {
|
|
||||||
// expected
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
throw new Error('Expected an exception');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
682
build/lib/treeshaking.js
Normal file
682
build/lib/treeshaking.js
Normal file
@@ -0,0 +1,682 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
'use strict';
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
var fs = require("fs");
|
||||||
|
var path = require("path");
|
||||||
|
var ts = require("typescript");
|
||||||
|
var TYPESCRIPT_LIB_FOLDER = path.dirname(require.resolve('typescript/lib/lib.d.ts'));
|
||||||
|
var ShakeLevel;
|
||||||
|
(function (ShakeLevel) {
|
||||||
|
ShakeLevel[ShakeLevel["Files"] = 0] = "Files";
|
||||||
|
ShakeLevel[ShakeLevel["InnerFile"] = 1] = "InnerFile";
|
||||||
|
ShakeLevel[ShakeLevel["ClassMembers"] = 2] = "ClassMembers";
|
||||||
|
})(ShakeLevel = exports.ShakeLevel || (exports.ShakeLevel = {}));
|
||||||
|
function shake(options) {
|
||||||
|
var languageService = createTypeScriptLanguageService(options);
|
||||||
|
markNodes(languageService, options);
|
||||||
|
return generateResult(languageService, options.shakeLevel);
|
||||||
|
}
|
||||||
|
exports.shake = shake;
|
||||||
|
//#region Discovery, LanguageService & Setup
|
||||||
|
function createTypeScriptLanguageService(options) {
|
||||||
|
// Discover referenced files
|
||||||
|
var FILES = discoverAndReadFiles(options);
|
||||||
|
// Add fake usage files
|
||||||
|
options.inlineEntryPoints.forEach(function (inlineEntryPoint, index) {
|
||||||
|
FILES["inlineEntryPoint:" + index + ".ts"] = inlineEntryPoint;
|
||||||
|
});
|
||||||
|
// Resolve libs
|
||||||
|
var RESOLVED_LIBS = {};
|
||||||
|
options.libs.forEach(function (filename) {
|
||||||
|
var filepath = path.join(TYPESCRIPT_LIB_FOLDER, filename);
|
||||||
|
RESOLVED_LIBS["defaultLib:" + filename] = fs.readFileSync(filepath).toString();
|
||||||
|
});
|
||||||
|
var host = new TypeScriptLanguageServiceHost(RESOLVED_LIBS, FILES, options.compilerOptions);
|
||||||
|
return ts.createLanguageService(host);
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Read imports and follow them until all files have been handled
|
||||||
|
*/
|
||||||
|
function discoverAndReadFiles(options) {
|
||||||
|
var FILES = {};
|
||||||
|
var in_queue = Object.create(null);
|
||||||
|
var queue = [];
|
||||||
|
var enqueue = function (moduleId) {
|
||||||
|
if (in_queue[moduleId]) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
in_queue[moduleId] = true;
|
||||||
|
queue.push(moduleId);
|
||||||
|
};
|
||||||
|
options.entryPoints.forEach(function (entryPoint) { return enqueue(entryPoint); });
|
||||||
|
while (queue.length > 0) {
|
||||||
|
var moduleId = queue.shift();
|
||||||
|
var dts_filename = path.join(options.sourcesRoot, moduleId + '.d.ts');
|
||||||
|
if (fs.existsSync(dts_filename)) {
|
||||||
|
var dts_filecontents = fs.readFileSync(dts_filename).toString();
|
||||||
|
FILES[moduleId + '.d.ts'] = dts_filecontents;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
var ts_filename = void 0;
|
||||||
|
if (options.redirects[moduleId]) {
|
||||||
|
ts_filename = path.join(options.sourcesRoot, options.redirects[moduleId] + '.ts');
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
ts_filename = path.join(options.sourcesRoot, moduleId + '.ts');
|
||||||
|
}
|
||||||
|
var ts_filecontents = fs.readFileSync(ts_filename).toString();
|
||||||
|
var info = ts.preProcessFile(ts_filecontents);
|
||||||
|
for (var i = info.importedFiles.length - 1; i >= 0; i--) {
|
||||||
|
var importedFileName = info.importedFiles[i].fileName;
|
||||||
|
if (options.importIgnorePattern.test(importedFileName)) {
|
||||||
|
// Ignore vs/css! imports
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
var importedModuleId = importedFileName;
|
||||||
|
if (/(^\.\/)|(^\.\.\/)/.test(importedModuleId)) {
|
||||||
|
importedModuleId = path.join(path.dirname(moduleId), importedModuleId);
|
||||||
|
}
|
||||||
|
enqueue(importedModuleId);
|
||||||
|
}
|
||||||
|
FILES[moduleId + '.ts'] = ts_filecontents;
|
||||||
|
}
|
||||||
|
return FILES;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* A TypeScript language service host
|
||||||
|
*/
|
||||||
|
var TypeScriptLanguageServiceHost = /** @class */ (function () {
|
||||||
|
function TypeScriptLanguageServiceHost(libs, files, compilerOptions) {
|
||||||
|
this._libs = libs;
|
||||||
|
this._files = files;
|
||||||
|
this._compilerOptions = compilerOptions;
|
||||||
|
}
|
||||||
|
// --- language service host ---------------
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getCompilationSettings = function () {
|
||||||
|
return this._compilerOptions;
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptFileNames = function () {
|
||||||
|
return ([]
|
||||||
|
.concat(Object.keys(this._libs))
|
||||||
|
.concat(Object.keys(this._files)));
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptVersion = function (fileName) {
|
||||||
|
return '1';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getProjectVersion = function () {
|
||||||
|
return '1';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptSnapshot = function (fileName) {
|
||||||
|
if (this._files.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._files[fileName]);
|
||||||
|
}
|
||||||
|
else if (this._libs.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._libs[fileName]);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return ts.ScriptSnapshot.fromString('');
|
||||||
|
}
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptKind = function (fileName) {
|
||||||
|
return ts.ScriptKind.TS;
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getCurrentDirectory = function () {
|
||||||
|
return '';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getDefaultLibFileName = function (options) {
|
||||||
|
return 'defaultLib:lib.d.ts';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.isDefaultLibFileName = function (fileName) {
|
||||||
|
return fileName === this.getDefaultLibFileName(this._compilerOptions);
|
||||||
|
};
|
||||||
|
return TypeScriptLanguageServiceHost;
|
||||||
|
}());
|
||||||
|
//#endregion
|
||||||
|
//#region Tree Shaking
|
||||||
|
var NodeColor;
|
||||||
|
(function (NodeColor) {
|
||||||
|
NodeColor[NodeColor["White"] = 0] = "White";
|
||||||
|
NodeColor[NodeColor["Gray"] = 1] = "Gray";
|
||||||
|
NodeColor[NodeColor["Black"] = 2] = "Black";
|
||||||
|
})(NodeColor || (NodeColor = {}));
|
||||||
|
function getColor(node) {
|
||||||
|
return node.$$$color || 0 /* White */;
|
||||||
|
}
|
||||||
|
function setColor(node, color) {
|
||||||
|
node.$$$color = color;
|
||||||
|
}
|
||||||
|
function nodeOrParentIsBlack(node) {
|
||||||
|
while (node) {
|
||||||
|
var color = getColor(node);
|
||||||
|
if (color === 2 /* Black */) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
node = node.parent;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
function nodeOrChildIsBlack(node) {
|
||||||
|
if (getColor(node) === 2 /* Black */) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
for (var _i = 0, _a = node.getChildren(); _i < _a.length; _i++) {
|
||||||
|
var child = _a[_i];
|
||||||
|
if (nodeOrChildIsBlack(child)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
function markNodes(languageService, options) {
|
||||||
|
var program = languageService.getProgram();
|
||||||
|
if (options.shakeLevel === 0 /* Files */) {
|
||||||
|
// Mark all source files Black
|
||||||
|
program.getSourceFiles().forEach(function (sourceFile) {
|
||||||
|
setColor(sourceFile, 2 /* Black */);
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var black_queue = [];
|
||||||
|
var gray_queue = [];
|
||||||
|
var sourceFilesLoaded = {};
|
||||||
|
function enqueueTopLevelModuleStatements(sourceFile) {
|
||||||
|
sourceFile.forEachChild(function (node) {
|
||||||
|
if (ts.isImportDeclaration(node)) {
|
||||||
|
if (!node.importClause && ts.isStringLiteral(node.moduleSpecifier)) {
|
||||||
|
setColor(node, 2 /* Black */);
|
||||||
|
enqueueImport(node, node.moduleSpecifier.text);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (ts.isExportDeclaration(node)) {
|
||||||
|
if (ts.isStringLiteral(node.moduleSpecifier)) {
|
||||||
|
setColor(node, 2 /* Black */);
|
||||||
|
enqueueImport(node, node.moduleSpecifier.text);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (ts.isExpressionStatement(node)
|
||||||
|
|| ts.isIfStatement(node)
|
||||||
|
|| ts.isIterationStatement(node, true)
|
||||||
|
|| ts.isExportAssignment(node)) {
|
||||||
|
enqueue_black(node);
|
||||||
|
}
|
||||||
|
if (ts.isImportEqualsDeclaration(node)) {
|
||||||
|
if (/export/.test(node.getFullText(sourceFile))) {
|
||||||
|
// e.g. "export import Severity = BaseSeverity;"
|
||||||
|
enqueue_black(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
function enqueue_gray(node) {
|
||||||
|
if (nodeOrParentIsBlack(node) || getColor(node) === 1 /* Gray */) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
setColor(node, 1 /* Gray */);
|
||||||
|
gray_queue.push(node);
|
||||||
|
}
|
||||||
|
function enqueue_black(node) {
|
||||||
|
var previousColor = getColor(node);
|
||||||
|
if (previousColor === 2 /* Black */) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (previousColor === 1 /* Gray */) {
|
||||||
|
// remove from gray queue
|
||||||
|
gray_queue.splice(gray_queue.indexOf(node), 1);
|
||||||
|
setColor(node, 0 /* White */);
|
||||||
|
// add to black queue
|
||||||
|
enqueue_black(node);
|
||||||
|
// // move from one queue to the other
|
||||||
|
// black_queue.push(node);
|
||||||
|
// setColor(node, NodeColor.Black);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (nodeOrParentIsBlack(node)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var fileName = node.getSourceFile().fileName;
|
||||||
|
if (/^defaultLib:/.test(fileName) || /\.d\.ts$/.test(fileName)) {
|
||||||
|
setColor(node, 2 /* Black */);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var sourceFile = node.getSourceFile();
|
||||||
|
if (!sourceFilesLoaded[sourceFile.fileName]) {
|
||||||
|
sourceFilesLoaded[sourceFile.fileName] = true;
|
||||||
|
enqueueTopLevelModuleStatements(sourceFile);
|
||||||
|
}
|
||||||
|
if (ts.isSourceFile(node)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
setColor(node, 2 /* Black */);
|
||||||
|
black_queue.push(node);
|
||||||
|
if (options.shakeLevel === 2 /* ClassMembers */ && (ts.isMethodDeclaration(node) || ts.isMethodSignature(node) || ts.isPropertySignature(node) || ts.isGetAccessor(node) || ts.isSetAccessor(node))) {
|
||||||
|
var references = languageService.getReferencesAtPosition(node.getSourceFile().fileName, node.name.pos + node.name.getLeadingTriviaWidth());
|
||||||
|
if (references) {
|
||||||
|
for (var i = 0, len = references.length; i < len; i++) {
|
||||||
|
var reference = references[i];
|
||||||
|
var referenceSourceFile = program.getSourceFile(reference.fileName);
|
||||||
|
var referenceNode = getTokenAtPosition(referenceSourceFile, reference.textSpan.start, false, false);
|
||||||
|
if (ts.isMethodDeclaration(referenceNode.parent)
|
||||||
|
|| ts.isPropertyDeclaration(referenceNode.parent)
|
||||||
|
|| ts.isGetAccessor(referenceNode.parent)
|
||||||
|
|| ts.isSetAccessor(referenceNode.parent)) {
|
||||||
|
enqueue_gray(referenceNode.parent);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
function enqueueFile(filename) {
|
||||||
|
var sourceFile = program.getSourceFile(filename);
|
||||||
|
if (!sourceFile) {
|
||||||
|
console.warn("Cannot find source file " + filename);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
enqueue_black(sourceFile);
|
||||||
|
}
|
||||||
|
function enqueueImport(node, importText) {
|
||||||
|
if (options.importIgnorePattern.test(importText)) {
|
||||||
|
// this import should be ignored
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var nodeSourceFile = node.getSourceFile();
|
||||||
|
var fullPath;
|
||||||
|
if (/(^\.\/)|(^\.\.\/)/.test(importText)) {
|
||||||
|
fullPath = path.join(path.dirname(nodeSourceFile.fileName), importText) + '.ts';
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
fullPath = importText + '.ts';
|
||||||
|
}
|
||||||
|
enqueueFile(fullPath);
|
||||||
|
}
|
||||||
|
options.entryPoints.forEach(function (moduleId) { return enqueueFile(moduleId + '.ts'); });
|
||||||
|
// Add fake usage files
|
||||||
|
options.inlineEntryPoints.forEach(function (_, index) { return enqueueFile("inlineEntryPoint:" + index + ".ts"); });
|
||||||
|
var step = 0;
|
||||||
|
var checker = program.getTypeChecker();
|
||||||
|
var _loop_1 = function () {
|
||||||
|
++step;
|
||||||
|
var node = void 0;
|
||||||
|
if (step % 100 === 0) {
|
||||||
|
console.log(step + "/" + (step + black_queue.length + gray_queue.length) + " (" + black_queue.length + ", " + gray_queue.length + ")");
|
||||||
|
}
|
||||||
|
if (black_queue.length === 0) {
|
||||||
|
for (var i = 0; i < gray_queue.length; i++) {
|
||||||
|
var node_1 = gray_queue[i];
|
||||||
|
var nodeParent = node_1.parent;
|
||||||
|
if ((ts.isClassDeclaration(nodeParent) || ts.isInterfaceDeclaration(nodeParent)) && nodeOrChildIsBlack(nodeParent)) {
|
||||||
|
gray_queue.splice(i, 1);
|
||||||
|
black_queue.push(node_1);
|
||||||
|
setColor(node_1, 2 /* Black */);
|
||||||
|
i--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (black_queue.length > 0) {
|
||||||
|
node = black_queue.shift();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return "break";
|
||||||
|
}
|
||||||
|
var nodeSourceFile = node.getSourceFile();
|
||||||
|
var loop = function (node) {
|
||||||
|
var _a = getRealNodeSymbol(checker, node), symbol = _a[0], symbolImportNode = _a[1];
|
||||||
|
if (symbolImportNode) {
|
||||||
|
setColor(symbolImportNode, 2 /* Black */);
|
||||||
|
}
|
||||||
|
if (symbol && !nodeIsInItsOwnDeclaration(nodeSourceFile, node, symbol)) {
|
||||||
|
for (var i = 0, len = symbol.declarations.length; i < len; i++) {
|
||||||
|
var declaration = symbol.declarations[i];
|
||||||
|
if (ts.isSourceFile(declaration)) {
|
||||||
|
// Do not enqueue full source files
|
||||||
|
// (they can be the declaration of a module import)
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (options.shakeLevel === 2 /* ClassMembers */ && (ts.isClassDeclaration(declaration) || ts.isInterfaceDeclaration(declaration))) {
|
||||||
|
enqueue_black(declaration.name);
|
||||||
|
for (var j = 0; j < declaration.members.length; j++) {
|
||||||
|
var member = declaration.members[j];
|
||||||
|
var memberName = member.name ? member.name.getText() : null;
|
||||||
|
if (ts.isConstructorDeclaration(member)
|
||||||
|
|| ts.isConstructSignatureDeclaration(member)
|
||||||
|
|| ts.isIndexSignatureDeclaration(member)
|
||||||
|
|| ts.isCallSignatureDeclaration(member)
|
||||||
|
|| memberName === 'toJSON'
|
||||||
|
|| memberName === 'toString'
|
||||||
|
|| memberName === 'dispose' // TODO: keeping all `dispose` methods
|
||||||
|
) {
|
||||||
|
enqueue_black(member);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// queue the heritage clauses
|
||||||
|
if (declaration.heritageClauses) {
|
||||||
|
for (var _i = 0, _b = declaration.heritageClauses; _i < _b.length; _i++) {
|
||||||
|
var heritageClause = _b[_i];
|
||||||
|
enqueue_black(heritageClause);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
enqueue_black(declaration);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
node.forEachChild(loop);
|
||||||
|
};
|
||||||
|
node.forEachChild(loop);
|
||||||
|
};
|
||||||
|
while (black_queue.length > 0 || gray_queue.length > 0) {
|
||||||
|
var state_1 = _loop_1();
|
||||||
|
if (state_1 === "break")
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
function nodeIsInItsOwnDeclaration(nodeSourceFile, node, symbol) {
|
||||||
|
for (var i = 0, len = symbol.declarations.length; i < len; i++) {
|
||||||
|
var declaration = symbol.declarations[i];
|
||||||
|
var declarationSourceFile = declaration.getSourceFile();
|
||||||
|
if (nodeSourceFile === declarationSourceFile) {
|
||||||
|
if (declaration.pos <= node.pos && node.end <= declaration.end) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
function generateResult(languageService, shakeLevel) {
|
||||||
|
var program = languageService.getProgram();
|
||||||
|
var result = {};
|
||||||
|
var writeFile = function (filePath, contents) {
|
||||||
|
result[filePath] = contents;
|
||||||
|
};
|
||||||
|
program.getSourceFiles().forEach(function (sourceFile) {
|
||||||
|
var fileName = sourceFile.fileName;
|
||||||
|
if (/^defaultLib:/.test(fileName)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var destination = fileName;
|
||||||
|
if (/\.d\.ts$/.test(fileName)) {
|
||||||
|
if (nodeOrChildIsBlack(sourceFile)) {
|
||||||
|
writeFile(destination, sourceFile.text);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var text = sourceFile.text;
|
||||||
|
var result = '';
|
||||||
|
function keep(node) {
|
||||||
|
result += text.substring(node.pos, node.end);
|
||||||
|
}
|
||||||
|
function write(data) {
|
||||||
|
result += data;
|
||||||
|
}
|
||||||
|
function writeMarkedNodes(node) {
|
||||||
|
if (getColor(node) === 2 /* Black */) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
// Always keep certain top-level statements
|
||||||
|
if (ts.isSourceFile(node.parent)) {
|
||||||
|
if (ts.isExpressionStatement(node) && ts.isStringLiteral(node.expression) && node.expression.text === 'use strict') {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
if (ts.isVariableStatement(node) && nodeOrChildIsBlack(node)) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Keep the entire import in import * as X cases
|
||||||
|
if (ts.isImportDeclaration(node)) {
|
||||||
|
if (node.importClause && node.importClause.namedBindings) {
|
||||||
|
if (ts.isNamespaceImport(node.importClause.namedBindings)) {
|
||||||
|
if (getColor(node.importClause.namedBindings) === 2 /* Black */) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
var survivingImports = [];
|
||||||
|
for (var i = 0; i < node.importClause.namedBindings.elements.length; i++) {
|
||||||
|
var importNode = node.importClause.namedBindings.elements[i];
|
||||||
|
if (getColor(importNode) === 2 /* Black */) {
|
||||||
|
survivingImports.push(importNode.getFullText(sourceFile));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var leadingTriviaWidth = node.getLeadingTriviaWidth();
|
||||||
|
var leadingTrivia = sourceFile.text.substr(node.pos, leadingTriviaWidth);
|
||||||
|
if (survivingImports.length > 0) {
|
||||||
|
if (node.importClause && getColor(node.importClause) === 2 /* Black */) {
|
||||||
|
return write(leadingTrivia + "import " + node.importClause.name.text + ", {" + survivingImports.join(',') + " } from" + node.moduleSpecifier.getFullText(sourceFile) + ";");
|
||||||
|
}
|
||||||
|
return write(leadingTrivia + "import {" + survivingImports.join(',') + " } from" + node.moduleSpecifier.getFullText(sourceFile) + ";");
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (node.importClause && getColor(node.importClause) === 2 /* Black */) {
|
||||||
|
return write(leadingTrivia + "import " + node.importClause.name.text + " from" + node.moduleSpecifier.getFullText(sourceFile) + ";");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (node.importClause && getColor(node.importClause) === 2 /* Black */) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (shakeLevel === 2 /* ClassMembers */ && (ts.isClassDeclaration(node) || ts.isInterfaceDeclaration(node)) && nodeOrChildIsBlack(node)) {
|
||||||
|
var toWrite = node.getFullText();
|
||||||
|
for (var i = node.members.length - 1; i >= 0; i--) {
|
||||||
|
var member = node.members[i];
|
||||||
|
if (getColor(member) === 2 /* Black */) {
|
||||||
|
// keep method
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (/^_(.*)Brand$/.test(member.name.getText())) {
|
||||||
|
// TODO: keep all members ending with `Brand`...
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
var pos = member.pos - node.pos;
|
||||||
|
var end = member.end - node.pos;
|
||||||
|
toWrite = toWrite.substring(0, pos) + toWrite.substring(end);
|
||||||
|
}
|
||||||
|
return write(toWrite);
|
||||||
|
}
|
||||||
|
if (ts.isFunctionDeclaration(node)) {
|
||||||
|
// Do not go inside functions if they haven't been marked
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
node.forEachChild(writeMarkedNodes);
|
||||||
|
}
|
||||||
|
if (getColor(sourceFile) !== 2 /* Black */) {
|
||||||
|
if (!nodeOrChildIsBlack(sourceFile)) {
|
||||||
|
// none of the elements are reachable => don't write this file at all!
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
sourceFile.forEachChild(writeMarkedNodes);
|
||||||
|
result += sourceFile.endOfFileToken.getFullText(sourceFile);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
result = text;
|
||||||
|
}
|
||||||
|
writeFile(destination, result);
|
||||||
|
});
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
//#endregion
|
||||||
|
//#region Utils
|
||||||
|
/**
|
||||||
|
* Returns the node's symbol and the `import` node (if the symbol resolved from a different module)
|
||||||
|
*/
|
||||||
|
function getRealNodeSymbol(checker, node) {
|
||||||
|
/**
|
||||||
|
* Returns the containing object literal property declaration given a possible name node, e.g. "a" in x = { "a": 1 }
|
||||||
|
*/
|
||||||
|
/* @internal */
|
||||||
|
function getContainingObjectLiteralElement(node) {
|
||||||
|
switch (node.kind) {
|
||||||
|
case ts.SyntaxKind.StringLiteral:
|
||||||
|
case ts.SyntaxKind.NumericLiteral:
|
||||||
|
if (node.parent.kind === ts.SyntaxKind.ComputedPropertyName) {
|
||||||
|
return ts.isObjectLiteralElement(node.parent.parent) ? node.parent.parent : undefined;
|
||||||
|
}
|
||||||
|
// falls through
|
||||||
|
case ts.SyntaxKind.Identifier:
|
||||||
|
return ts.isObjectLiteralElement(node.parent) &&
|
||||||
|
(node.parent.parent.kind === ts.SyntaxKind.ObjectLiteralExpression || node.parent.parent.kind === ts.SyntaxKind.JsxAttributes) &&
|
||||||
|
node.parent.name === node ? node.parent : undefined;
|
||||||
|
}
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
function getPropertySymbolsFromType(type, propName) {
|
||||||
|
function getTextOfPropertyName(name) {
|
||||||
|
function isStringOrNumericLiteral(node) {
|
||||||
|
var kind = node.kind;
|
||||||
|
return kind === ts.SyntaxKind.StringLiteral
|
||||||
|
|| kind === ts.SyntaxKind.NumericLiteral;
|
||||||
|
}
|
||||||
|
switch (name.kind) {
|
||||||
|
case ts.SyntaxKind.Identifier:
|
||||||
|
return name.text;
|
||||||
|
case ts.SyntaxKind.StringLiteral:
|
||||||
|
case ts.SyntaxKind.NumericLiteral:
|
||||||
|
return name.text;
|
||||||
|
case ts.SyntaxKind.ComputedPropertyName:
|
||||||
|
return isStringOrNumericLiteral(name.expression) ? name.expression.text : undefined;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var name = getTextOfPropertyName(propName);
|
||||||
|
if (name && type) {
|
||||||
|
var result = [];
|
||||||
|
var symbol_1 = type.getProperty(name);
|
||||||
|
if (type.flags & ts.TypeFlags.Union) {
|
||||||
|
for (var _i = 0, _a = type.types; _i < _a.length; _i++) {
|
||||||
|
var t = _a[_i];
|
||||||
|
var symbol_2 = t.getProperty(name);
|
||||||
|
if (symbol_2) {
|
||||||
|
result.push(symbol_2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
if (symbol_1) {
|
||||||
|
result.push(symbol_1);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
function getPropertySymbolsFromContextualType(typeChecker, node) {
|
||||||
|
var objectLiteral = node.parent;
|
||||||
|
var contextualType = typeChecker.getContextualType(objectLiteral);
|
||||||
|
return getPropertySymbolsFromType(contextualType, node.name);
|
||||||
|
}
|
||||||
|
// Go to the original declaration for cases:
|
||||||
|
//
|
||||||
|
// (1) when the aliased symbol was declared in the location(parent).
|
||||||
|
// (2) when the aliased symbol is originating from an import.
|
||||||
|
//
|
||||||
|
function shouldSkipAlias(node, declaration) {
|
||||||
|
if (node.kind !== ts.SyntaxKind.Identifier) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (node.parent === declaration) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
switch (declaration.kind) {
|
||||||
|
case ts.SyntaxKind.ImportClause:
|
||||||
|
case ts.SyntaxKind.ImportEqualsDeclaration:
|
||||||
|
return true;
|
||||||
|
case ts.SyntaxKind.ImportSpecifier:
|
||||||
|
return declaration.parent.kind === ts.SyntaxKind.NamedImports;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!ts.isShorthandPropertyAssignment(node)) {
|
||||||
|
if (node.getChildCount() !== 0) {
|
||||||
|
return [null, null];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var symbol = checker.getSymbolAtLocation(node);
|
||||||
|
var importNode = null;
|
||||||
|
if (symbol && symbol.flags & ts.SymbolFlags.Alias && shouldSkipAlias(node, symbol.declarations[0])) {
|
||||||
|
var aliased = checker.getAliasedSymbol(symbol);
|
||||||
|
if (aliased.declarations) {
|
||||||
|
// We should mark the import as visited
|
||||||
|
importNode = symbol.declarations[0];
|
||||||
|
symbol = aliased;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (symbol) {
|
||||||
|
// Because name in short-hand property assignment has two different meanings: property name and property value,
|
||||||
|
// using go-to-definition at such position should go to the variable declaration of the property value rather than
|
||||||
|
// go to the declaration of the property name (in this case stay at the same position). However, if go-to-definition
|
||||||
|
// is performed at the location of property access, we would like to go to definition of the property in the short-hand
|
||||||
|
// assignment. This case and others are handled by the following code.
|
||||||
|
if (node.parent.kind === ts.SyntaxKind.ShorthandPropertyAssignment) {
|
||||||
|
symbol = checker.getShorthandAssignmentValueSymbol(symbol.valueDeclaration);
|
||||||
|
}
|
||||||
|
// If the node is the name of a BindingElement within an ObjectBindingPattern instead of just returning the
|
||||||
|
// declaration the symbol (which is itself), we should try to get to the original type of the ObjectBindingPattern
|
||||||
|
// and return the property declaration for the referenced property.
|
||||||
|
// For example:
|
||||||
|
// import('./foo').then(({ b/*goto*/ar }) => undefined); => should get use to the declaration in file "./foo"
|
||||||
|
//
|
||||||
|
// function bar<T>(onfulfilled: (value: T) => void) { //....}
|
||||||
|
// interface Test {
|
||||||
|
// pr/*destination*/op1: number
|
||||||
|
// }
|
||||||
|
// bar<Test>(({pr/*goto*/op1})=>{});
|
||||||
|
if (ts.isPropertyName(node) && ts.isBindingElement(node.parent) && ts.isObjectBindingPattern(node.parent.parent) &&
|
||||||
|
(node === (node.parent.propertyName || node.parent.name))) {
|
||||||
|
var type = checker.getTypeAtLocation(node.parent.parent);
|
||||||
|
if (type) {
|
||||||
|
var propSymbols = getPropertySymbolsFromType(type, node);
|
||||||
|
if (propSymbols) {
|
||||||
|
symbol = propSymbols[0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// If the current location we want to find its definition is in an object literal, try to get the contextual type for the
|
||||||
|
// object literal, lookup the property symbol in the contextual type, and use this for goto-definition.
|
||||||
|
// For example
|
||||||
|
// interface Props{
|
||||||
|
// /*first*/prop1: number
|
||||||
|
// prop2: boolean
|
||||||
|
// }
|
||||||
|
// function Foo(arg: Props) {}
|
||||||
|
// Foo( { pr/*1*/op1: 10, prop2: false })
|
||||||
|
var element = getContainingObjectLiteralElement(node);
|
||||||
|
if (element && checker.getContextualType(element.parent)) {
|
||||||
|
var propertySymbols = getPropertySymbolsFromContextualType(checker, element);
|
||||||
|
if (propertySymbols) {
|
||||||
|
symbol = propertySymbols[0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (symbol && symbol.declarations) {
|
||||||
|
return [symbol, importNode];
|
||||||
|
}
|
||||||
|
return [null, null];
|
||||||
|
}
|
||||||
|
/** Get the token whose text contains the position */
|
||||||
|
function getTokenAtPosition(sourceFile, position, allowPositionInLeadingTrivia, includeEndPosition) {
|
||||||
|
var current = sourceFile;
|
||||||
|
outer: while (true) {
|
||||||
|
// find the child that contains 'position'
|
||||||
|
for (var _i = 0, _a = current.getChildren(); _i < _a.length; _i++) {
|
||||||
|
var child = _a[_i];
|
||||||
|
var start = allowPositionInLeadingTrivia ? child.getFullStart() : child.getStart(sourceFile, /*includeJsDoc*/ true);
|
||||||
|
if (start > position) {
|
||||||
|
// If this child begins after position, then all subsequent children will as well.
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
var end = child.getEnd();
|
||||||
|
if (position < end || (position === end && (child.kind === ts.SyntaxKind.EndOfFileToken || includeEndPosition))) {
|
||||||
|
current = child;
|
||||||
|
continue outer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return current;
|
||||||
|
}
|
||||||
|
}
|
||||||
817
build/lib/treeshaking.ts
Normal file
817
build/lib/treeshaking.ts
Normal file
@@ -0,0 +1,817 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
'use strict';
|
||||||
|
|
||||||
|
import * as fs from 'fs';
|
||||||
|
import * as path from 'path';
|
||||||
|
import * as ts from 'typescript';
|
||||||
|
|
||||||
|
const TYPESCRIPT_LIB_FOLDER = path.dirname(require.resolve('typescript/lib/lib.d.ts'));
|
||||||
|
|
||||||
|
export const enum ShakeLevel {
|
||||||
|
Files = 0,
|
||||||
|
InnerFile = 1,
|
||||||
|
ClassMembers = 2
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface ITreeShakingOptions {
|
||||||
|
/**
|
||||||
|
* The full path to the root where sources are.
|
||||||
|
*/
|
||||||
|
sourcesRoot: string;
|
||||||
|
/**
|
||||||
|
* Module ids.
|
||||||
|
* e.g. `vs/editor/editor.main` or `index`
|
||||||
|
*/
|
||||||
|
entryPoints: string[];
|
||||||
|
/**
|
||||||
|
* Inline usages.
|
||||||
|
*/
|
||||||
|
inlineEntryPoints: string[];
|
||||||
|
/**
|
||||||
|
* TypeScript libs.
|
||||||
|
* e.g. `lib.d.ts`, `lib.es2015.collection.d.ts`
|
||||||
|
*/
|
||||||
|
libs: string[];
|
||||||
|
/**
|
||||||
|
* TypeScript compiler options.
|
||||||
|
*/
|
||||||
|
compilerOptions: ts.CompilerOptions;
|
||||||
|
/**
|
||||||
|
* The shake level to perform.
|
||||||
|
*/
|
||||||
|
shakeLevel: ShakeLevel;
|
||||||
|
/**
|
||||||
|
* regex pattern to ignore certain imports e.g. `vs/css!` imports
|
||||||
|
*/
|
||||||
|
importIgnorePattern: RegExp;
|
||||||
|
|
||||||
|
redirects: { [module: string]: string; };
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface ITreeShakingResult {
|
||||||
|
[file: string]: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function shake(options: ITreeShakingOptions): ITreeShakingResult {
|
||||||
|
const languageService = createTypeScriptLanguageService(options);
|
||||||
|
|
||||||
|
markNodes(languageService, options);
|
||||||
|
|
||||||
|
return generateResult(languageService, options.shakeLevel);
|
||||||
|
}
|
||||||
|
|
||||||
|
//#region Discovery, LanguageService & Setup
|
||||||
|
function createTypeScriptLanguageService(options: ITreeShakingOptions): ts.LanguageService {
|
||||||
|
// Discover referenced files
|
||||||
|
const FILES = discoverAndReadFiles(options);
|
||||||
|
|
||||||
|
// Add fake usage files
|
||||||
|
options.inlineEntryPoints.forEach((inlineEntryPoint, index) => {
|
||||||
|
FILES[`inlineEntryPoint:${index}.ts`] = inlineEntryPoint;
|
||||||
|
});
|
||||||
|
|
||||||
|
// Resolve libs
|
||||||
|
const RESOLVED_LIBS: ILibMap = {};
|
||||||
|
options.libs.forEach((filename) => {
|
||||||
|
const filepath = path.join(TYPESCRIPT_LIB_FOLDER, filename);
|
||||||
|
RESOLVED_LIBS[`defaultLib:${filename}`] = fs.readFileSync(filepath).toString();
|
||||||
|
});
|
||||||
|
|
||||||
|
const host = new TypeScriptLanguageServiceHost(RESOLVED_LIBS, FILES, options.compilerOptions);
|
||||||
|
return ts.createLanguageService(host);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Read imports and follow them until all files have been handled
|
||||||
|
*/
|
||||||
|
function discoverAndReadFiles(options: ITreeShakingOptions): IFileMap {
|
||||||
|
const FILES: IFileMap = {};
|
||||||
|
|
||||||
|
const in_queue: { [module: string]: boolean; } = Object.create(null);
|
||||||
|
const queue: string[] = [];
|
||||||
|
|
||||||
|
const enqueue = (moduleId: string) => {
|
||||||
|
if (in_queue[moduleId]) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
in_queue[moduleId] = true;
|
||||||
|
queue.push(moduleId);
|
||||||
|
};
|
||||||
|
|
||||||
|
options.entryPoints.forEach((entryPoint) => enqueue(entryPoint));
|
||||||
|
|
||||||
|
while (queue.length > 0) {
|
||||||
|
const moduleId = queue.shift();
|
||||||
|
const dts_filename = path.join(options.sourcesRoot, moduleId + '.d.ts');
|
||||||
|
if (fs.existsSync(dts_filename)) {
|
||||||
|
const dts_filecontents = fs.readFileSync(dts_filename).toString();
|
||||||
|
FILES[moduleId + '.d.ts'] = dts_filecontents;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
let ts_filename: string;
|
||||||
|
if (options.redirects[moduleId]) {
|
||||||
|
ts_filename = path.join(options.sourcesRoot, options.redirects[moduleId] + '.ts');
|
||||||
|
} else {
|
||||||
|
ts_filename = path.join(options.sourcesRoot, moduleId + '.ts');
|
||||||
|
}
|
||||||
|
const ts_filecontents = fs.readFileSync(ts_filename).toString();
|
||||||
|
const info = ts.preProcessFile(ts_filecontents);
|
||||||
|
for (let i = info.importedFiles.length - 1; i >= 0; i--) {
|
||||||
|
const importedFileName = info.importedFiles[i].fileName;
|
||||||
|
|
||||||
|
if (options.importIgnorePattern.test(importedFileName)) {
|
||||||
|
// Ignore vs/css! imports
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
let importedModuleId = importedFileName;
|
||||||
|
if (/(^\.\/)|(^\.\.\/)/.test(importedModuleId)) {
|
||||||
|
importedModuleId = path.join(path.dirname(moduleId), importedModuleId);
|
||||||
|
}
|
||||||
|
enqueue(importedModuleId);
|
||||||
|
}
|
||||||
|
|
||||||
|
FILES[moduleId + '.ts'] = ts_filecontents;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FILES;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface ILibMap { [libName: string]: string; }
|
||||||
|
interface IFileMap { [fileName: string]: string; }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A TypeScript language service host
|
||||||
|
*/
|
||||||
|
class TypeScriptLanguageServiceHost implements ts.LanguageServiceHost {
|
||||||
|
|
||||||
|
private readonly _libs: ILibMap;
|
||||||
|
private readonly _files: IFileMap;
|
||||||
|
private readonly _compilerOptions: ts.CompilerOptions;
|
||||||
|
|
||||||
|
constructor(libs: ILibMap, files: IFileMap, compilerOptions: ts.CompilerOptions) {
|
||||||
|
this._libs = libs;
|
||||||
|
this._files = files;
|
||||||
|
this._compilerOptions = compilerOptions;
|
||||||
|
}
|
||||||
|
|
||||||
|
// --- language service host ---------------
|
||||||
|
|
||||||
|
getCompilationSettings(): ts.CompilerOptions {
|
||||||
|
return this._compilerOptions;
|
||||||
|
}
|
||||||
|
getScriptFileNames(): string[] {
|
||||||
|
return (
|
||||||
|
[]
|
||||||
|
.concat(Object.keys(this._libs))
|
||||||
|
.concat(Object.keys(this._files))
|
||||||
|
);
|
||||||
|
}
|
||||||
|
getScriptVersion(fileName: string): string {
|
||||||
|
return '1';
|
||||||
|
}
|
||||||
|
getProjectVersion(): string {
|
||||||
|
return '1';
|
||||||
|
}
|
||||||
|
getScriptSnapshot(fileName: string): ts.IScriptSnapshot {
|
||||||
|
if (this._files.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._files[fileName]);
|
||||||
|
} else if (this._libs.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._libs[fileName]);
|
||||||
|
} else {
|
||||||
|
return ts.ScriptSnapshot.fromString('');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
getScriptKind(fileName: string): ts.ScriptKind {
|
||||||
|
return ts.ScriptKind.TS;
|
||||||
|
}
|
||||||
|
getCurrentDirectory(): string {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
getDefaultLibFileName(options: ts.CompilerOptions): string {
|
||||||
|
return 'defaultLib:lib.d.ts';
|
||||||
|
}
|
||||||
|
isDefaultLibFileName(fileName: string): boolean {
|
||||||
|
return fileName === this.getDefaultLibFileName(this._compilerOptions);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
//#endregion
|
||||||
|
|
||||||
|
//#region Tree Shaking
|
||||||
|
|
||||||
|
const enum NodeColor {
|
||||||
|
White = 0,
|
||||||
|
Gray = 1,
|
||||||
|
Black = 2
|
||||||
|
}
|
||||||
|
|
||||||
|
function getColor(node: ts.Node): NodeColor {
|
||||||
|
return (<any>node).$$$color || NodeColor.White;
|
||||||
|
}
|
||||||
|
function setColor(node: ts.Node, color: NodeColor): void {
|
||||||
|
(<any>node).$$$color = color;
|
||||||
|
}
|
||||||
|
function nodeOrParentIsBlack(node: ts.Node): boolean {
|
||||||
|
while (node) {
|
||||||
|
const color = getColor(node);
|
||||||
|
if (color === NodeColor.Black) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
node = node.parent;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
function nodeOrChildIsBlack(node: ts.Node): boolean {
|
||||||
|
if (getColor(node) === NodeColor.Black) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
for (const child of node.getChildren()) {
|
||||||
|
if (nodeOrChildIsBlack(child)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
function markNodes(languageService: ts.LanguageService, options: ITreeShakingOptions) {
|
||||||
|
const program = languageService.getProgram();
|
||||||
|
|
||||||
|
if (options.shakeLevel === ShakeLevel.Files) {
|
||||||
|
// Mark all source files Black
|
||||||
|
program.getSourceFiles().forEach((sourceFile) => {
|
||||||
|
setColor(sourceFile, NodeColor.Black);
|
||||||
|
});
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const black_queue: ts.Node[] = [];
|
||||||
|
const gray_queue: ts.Node[] = [];
|
||||||
|
const sourceFilesLoaded: { [fileName: string]: boolean } = {};
|
||||||
|
|
||||||
|
function enqueueTopLevelModuleStatements(sourceFile: ts.SourceFile): void {
|
||||||
|
|
||||||
|
sourceFile.forEachChild((node: ts.Node) => {
|
||||||
|
|
||||||
|
if (ts.isImportDeclaration(node)) {
|
||||||
|
if (!node.importClause && ts.isStringLiteral(node.moduleSpecifier)) {
|
||||||
|
setColor(node, NodeColor.Black);
|
||||||
|
enqueueImport(node, node.moduleSpecifier.text);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ts.isExportDeclaration(node)) {
|
||||||
|
if (ts.isStringLiteral(node.moduleSpecifier)) {
|
||||||
|
setColor(node, NodeColor.Black);
|
||||||
|
enqueueImport(node, node.moduleSpecifier.text);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (
|
||||||
|
ts.isExpressionStatement(node)
|
||||||
|
|| ts.isIfStatement(node)
|
||||||
|
|| ts.isIterationStatement(node, true)
|
||||||
|
|| ts.isExportAssignment(node)
|
||||||
|
) {
|
||||||
|
enqueue_black(node);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ts.isImportEqualsDeclaration(node)) {
|
||||||
|
if (/export/.test(node.getFullText(sourceFile))) {
|
||||||
|
// e.g. "export import Severity = BaseSeverity;"
|
||||||
|
enqueue_black(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function enqueue_gray(node: ts.Node): void {
|
||||||
|
if (nodeOrParentIsBlack(node) || getColor(node) === NodeColor.Gray) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
setColor(node, NodeColor.Gray);
|
||||||
|
gray_queue.push(node);
|
||||||
|
}
|
||||||
|
|
||||||
|
function enqueue_black(node: ts.Node): void {
|
||||||
|
const previousColor = getColor(node);
|
||||||
|
|
||||||
|
if (previousColor === NodeColor.Black) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (previousColor === NodeColor.Gray) {
|
||||||
|
// remove from gray queue
|
||||||
|
gray_queue.splice(gray_queue.indexOf(node), 1);
|
||||||
|
setColor(node, NodeColor.White);
|
||||||
|
|
||||||
|
// add to black queue
|
||||||
|
enqueue_black(node);
|
||||||
|
|
||||||
|
// // move from one queue to the other
|
||||||
|
// black_queue.push(node);
|
||||||
|
// setColor(node, NodeColor.Black);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (nodeOrParentIsBlack(node)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const fileName = node.getSourceFile().fileName;
|
||||||
|
if (/^defaultLib:/.test(fileName) || /\.d\.ts$/.test(fileName)) {
|
||||||
|
setColor(node, NodeColor.Black);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const sourceFile = node.getSourceFile();
|
||||||
|
if (!sourceFilesLoaded[sourceFile.fileName]) {
|
||||||
|
sourceFilesLoaded[sourceFile.fileName] = true;
|
||||||
|
enqueueTopLevelModuleStatements(sourceFile);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ts.isSourceFile(node)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
setColor(node, NodeColor.Black);
|
||||||
|
black_queue.push(node);
|
||||||
|
|
||||||
|
if (options.shakeLevel === ShakeLevel.ClassMembers && (ts.isMethodDeclaration(node) || ts.isMethodSignature(node) || ts.isPropertySignature(node) || ts.isGetAccessor(node) || ts.isSetAccessor(node))) {
|
||||||
|
const references = languageService.getReferencesAtPosition(node.getSourceFile().fileName, node.name.pos + node.name.getLeadingTriviaWidth());
|
||||||
|
if (references) {
|
||||||
|
for (let i = 0, len = references.length; i < len; i++) {
|
||||||
|
const reference = references[i];
|
||||||
|
const referenceSourceFile = program.getSourceFile(reference.fileName);
|
||||||
|
const referenceNode = getTokenAtPosition(referenceSourceFile, reference.textSpan.start, false, false);
|
||||||
|
if (
|
||||||
|
ts.isMethodDeclaration(referenceNode.parent)
|
||||||
|
|| ts.isPropertyDeclaration(referenceNode.parent)
|
||||||
|
|| ts.isGetAccessor(referenceNode.parent)
|
||||||
|
|| ts.isSetAccessor(referenceNode.parent)
|
||||||
|
) {
|
||||||
|
enqueue_gray(referenceNode.parent);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function enqueueFile(filename: string): void {
|
||||||
|
const sourceFile = program.getSourceFile(filename);
|
||||||
|
if (!sourceFile) {
|
||||||
|
console.warn(`Cannot find source file ${filename}`);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
enqueue_black(sourceFile);
|
||||||
|
}
|
||||||
|
|
||||||
|
function enqueueImport(node: ts.Node, importText: string): void {
|
||||||
|
if (options.importIgnorePattern.test(importText)) {
|
||||||
|
// this import should be ignored
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const nodeSourceFile = node.getSourceFile();
|
||||||
|
let fullPath: string;
|
||||||
|
if (/(^\.\/)|(^\.\.\/)/.test(importText)) {
|
||||||
|
fullPath = path.join(path.dirname(nodeSourceFile.fileName), importText) + '.ts';
|
||||||
|
} else {
|
||||||
|
fullPath = importText + '.ts';
|
||||||
|
}
|
||||||
|
enqueueFile(fullPath);
|
||||||
|
}
|
||||||
|
|
||||||
|
options.entryPoints.forEach(moduleId => enqueueFile(moduleId + '.ts'));
|
||||||
|
// Add fake usage files
|
||||||
|
options.inlineEntryPoints.forEach((_, index) => enqueueFile(`inlineEntryPoint:${index}.ts`));
|
||||||
|
|
||||||
|
let step = 0;
|
||||||
|
|
||||||
|
const checker = program.getTypeChecker();
|
||||||
|
while (black_queue.length > 0 || gray_queue.length > 0) {
|
||||||
|
++step;
|
||||||
|
let node: ts.Node;
|
||||||
|
|
||||||
|
if (step % 100 === 0) {
|
||||||
|
console.log(`${step}/${step+black_queue.length+gray_queue.length} (${black_queue.length}, ${gray_queue.length})`);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (black_queue.length === 0) {
|
||||||
|
for (let i = 0; i < gray_queue.length; i++) {
|
||||||
|
const node = gray_queue[i];
|
||||||
|
const nodeParent = node.parent;
|
||||||
|
if ((ts.isClassDeclaration(nodeParent) || ts.isInterfaceDeclaration(nodeParent)) && nodeOrChildIsBlack(nodeParent)) {
|
||||||
|
gray_queue.splice(i, 1);
|
||||||
|
black_queue.push(node);
|
||||||
|
setColor(node, NodeColor.Black);
|
||||||
|
i--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (black_queue.length > 0) {
|
||||||
|
node = black_queue.shift();
|
||||||
|
} else {
|
||||||
|
// only gray nodes remaining...
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
const nodeSourceFile = node.getSourceFile();
|
||||||
|
|
||||||
|
const loop = (node: ts.Node) => {
|
||||||
|
const [symbol, symbolImportNode] = getRealNodeSymbol(checker, node);
|
||||||
|
if (symbolImportNode) {
|
||||||
|
setColor(symbolImportNode, NodeColor.Black);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (symbol && !nodeIsInItsOwnDeclaration(nodeSourceFile, node, symbol)) {
|
||||||
|
for (let i = 0, len = symbol.declarations.length; i < len; i++) {
|
||||||
|
const declaration = symbol.declarations[i];
|
||||||
|
if (ts.isSourceFile(declaration)) {
|
||||||
|
// Do not enqueue full source files
|
||||||
|
// (they can be the declaration of a module import)
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (options.shakeLevel === ShakeLevel.ClassMembers && (ts.isClassDeclaration(declaration) || ts.isInterfaceDeclaration(declaration))) {
|
||||||
|
enqueue_black(declaration.name);
|
||||||
|
|
||||||
|
for (let j = 0; j < declaration.members.length; j++) {
|
||||||
|
const member = declaration.members[j];
|
||||||
|
const memberName = member.name ? member.name.getText() : null;
|
||||||
|
if (
|
||||||
|
ts.isConstructorDeclaration(member)
|
||||||
|
|| ts.isConstructSignatureDeclaration(member)
|
||||||
|
|| ts.isIndexSignatureDeclaration(member)
|
||||||
|
|| ts.isCallSignatureDeclaration(member)
|
||||||
|
|| memberName === 'toJSON'
|
||||||
|
|| memberName === 'toString'
|
||||||
|
|| memberName === 'dispose'// TODO: keeping all `dispose` methods
|
||||||
|
) {
|
||||||
|
enqueue_black(member);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// queue the heritage clauses
|
||||||
|
if (declaration.heritageClauses) {
|
||||||
|
for (let heritageClause of declaration.heritageClauses) {
|
||||||
|
enqueue_black(heritageClause);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
enqueue_black(declaration);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
node.forEachChild(loop);
|
||||||
|
};
|
||||||
|
node.forEachChild(loop);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function nodeIsInItsOwnDeclaration(nodeSourceFile: ts.SourceFile, node: ts.Node, symbol: ts.Symbol): boolean {
|
||||||
|
for (let i = 0, len = symbol.declarations.length; i < len; i++) {
|
||||||
|
const declaration = symbol.declarations[i];
|
||||||
|
const declarationSourceFile = declaration.getSourceFile();
|
||||||
|
|
||||||
|
if (nodeSourceFile === declarationSourceFile) {
|
||||||
|
if (declaration.pos <= node.pos && node.end <= declaration.end) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
function generateResult(languageService: ts.LanguageService, shakeLevel: ShakeLevel): ITreeShakingResult {
|
||||||
|
const program = languageService.getProgram();
|
||||||
|
|
||||||
|
let result: ITreeShakingResult = {};
|
||||||
|
const writeFile = (filePath: string, contents: string): void => {
|
||||||
|
result[filePath] = contents;
|
||||||
|
};
|
||||||
|
|
||||||
|
program.getSourceFiles().forEach((sourceFile) => {
|
||||||
|
const fileName = sourceFile.fileName;
|
||||||
|
if (/^defaultLib:/.test(fileName)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const destination = fileName;
|
||||||
|
if (/\.d\.ts$/.test(fileName)) {
|
||||||
|
if (nodeOrChildIsBlack(sourceFile)) {
|
||||||
|
writeFile(destination, sourceFile.text);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let text = sourceFile.text;
|
||||||
|
let result = '';
|
||||||
|
|
||||||
|
function keep(node: ts.Node): void {
|
||||||
|
result += text.substring(node.pos, node.end);
|
||||||
|
}
|
||||||
|
function write(data: string): void {
|
||||||
|
result += data;
|
||||||
|
}
|
||||||
|
|
||||||
|
function writeMarkedNodes(node: ts.Node): void {
|
||||||
|
if (getColor(node) === NodeColor.Black) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Always keep certain top-level statements
|
||||||
|
if (ts.isSourceFile(node.parent)) {
|
||||||
|
if (ts.isExpressionStatement(node) && ts.isStringLiteral(node.expression) && node.expression.text === 'use strict') {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ts.isVariableStatement(node) && nodeOrChildIsBlack(node)) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Keep the entire import in import * as X cases
|
||||||
|
if (ts.isImportDeclaration(node)) {
|
||||||
|
if (node.importClause && node.importClause.namedBindings) {
|
||||||
|
if (ts.isNamespaceImport(node.importClause.namedBindings)) {
|
||||||
|
if (getColor(node.importClause.namedBindings) === NodeColor.Black) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
let survivingImports: string[] = [];
|
||||||
|
for (let i = 0; i < node.importClause.namedBindings.elements.length; i++) {
|
||||||
|
const importNode = node.importClause.namedBindings.elements[i];
|
||||||
|
if (getColor(importNode) === NodeColor.Black) {
|
||||||
|
survivingImports.push(importNode.getFullText(sourceFile));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const leadingTriviaWidth = node.getLeadingTriviaWidth();
|
||||||
|
const leadingTrivia = sourceFile.text.substr(node.pos, leadingTriviaWidth);
|
||||||
|
if (survivingImports.length > 0) {
|
||||||
|
if (node.importClause && getColor(node.importClause) === NodeColor.Black) {
|
||||||
|
return write(`${leadingTrivia}import ${node.importClause.name.text}, {${survivingImports.join(',')} } from${node.moduleSpecifier.getFullText(sourceFile)};`);
|
||||||
|
}
|
||||||
|
return write(`${leadingTrivia}import {${survivingImports.join(',')} } from${node.moduleSpecifier.getFullText(sourceFile)};`);
|
||||||
|
} else {
|
||||||
|
if (node.importClause && getColor(node.importClause) === NodeColor.Black) {
|
||||||
|
return write(`${leadingTrivia}import ${node.importClause.name.text} from${node.moduleSpecifier.getFullText(sourceFile)};`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (node.importClause && getColor(node.importClause) === NodeColor.Black) {
|
||||||
|
return keep(node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (shakeLevel === ShakeLevel.ClassMembers && (ts.isClassDeclaration(node) || ts.isInterfaceDeclaration(node)) && nodeOrChildIsBlack(node)) {
|
||||||
|
let toWrite = node.getFullText();
|
||||||
|
for (let i = node.members.length - 1; i >= 0; i--) {
|
||||||
|
const member = node.members[i];
|
||||||
|
if (getColor(member) === NodeColor.Black) {
|
||||||
|
// keep method
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (/^_(.*)Brand$/.test(member.name.getText())) {
|
||||||
|
// TODO: keep all members ending with `Brand`...
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
let pos = member.pos - node.pos;
|
||||||
|
let end = member.end - node.pos;
|
||||||
|
toWrite = toWrite.substring(0, pos) + toWrite.substring(end);
|
||||||
|
}
|
||||||
|
return write(toWrite);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ts.isFunctionDeclaration(node)) {
|
||||||
|
// Do not go inside functions if they haven't been marked
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
node.forEachChild(writeMarkedNodes);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (getColor(sourceFile) !== NodeColor.Black) {
|
||||||
|
if (!nodeOrChildIsBlack(sourceFile)) {
|
||||||
|
// none of the elements are reachable => don't write this file at all!
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
sourceFile.forEachChild(writeMarkedNodes);
|
||||||
|
result += sourceFile.endOfFileToken.getFullText(sourceFile);
|
||||||
|
} else {
|
||||||
|
result = text;
|
||||||
|
}
|
||||||
|
|
||||||
|
writeFile(destination, result);
|
||||||
|
});
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
//#endregion
|
||||||
|
|
||||||
|
//#region Utils
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the node's symbol and the `import` node (if the symbol resolved from a different module)
|
||||||
|
*/
|
||||||
|
function getRealNodeSymbol(checker: ts.TypeChecker, node: ts.Node): [ts.Symbol, ts.Declaration] {
|
||||||
|
/**
|
||||||
|
* Returns the containing object literal property declaration given a possible name node, e.g. "a" in x = { "a": 1 }
|
||||||
|
*/
|
||||||
|
/* @internal */
|
||||||
|
function getContainingObjectLiteralElement(node: ts.Node): ts.ObjectLiteralElement | undefined {
|
||||||
|
switch (node.kind) {
|
||||||
|
case ts.SyntaxKind.StringLiteral:
|
||||||
|
case ts.SyntaxKind.NumericLiteral:
|
||||||
|
if (node.parent.kind === ts.SyntaxKind.ComputedPropertyName) {
|
||||||
|
return ts.isObjectLiteralElement(node.parent.parent) ? node.parent.parent : undefined;
|
||||||
|
}
|
||||||
|
// falls through
|
||||||
|
case ts.SyntaxKind.Identifier:
|
||||||
|
return ts.isObjectLiteralElement(node.parent) &&
|
||||||
|
(node.parent.parent.kind === ts.SyntaxKind.ObjectLiteralExpression || node.parent.parent.kind === ts.SyntaxKind.JsxAttributes) &&
|
||||||
|
node.parent.name === node ? node.parent : undefined;
|
||||||
|
}
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getPropertySymbolsFromType(type: ts.Type, propName: ts.PropertyName) {
|
||||||
|
function getTextOfPropertyName(name: ts.PropertyName): string {
|
||||||
|
|
||||||
|
function isStringOrNumericLiteral(node: ts.Node): node is ts.StringLiteral | ts.NumericLiteral {
|
||||||
|
const kind = node.kind;
|
||||||
|
return kind === ts.SyntaxKind.StringLiteral
|
||||||
|
|| kind === ts.SyntaxKind.NumericLiteral;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (name.kind) {
|
||||||
|
case ts.SyntaxKind.Identifier:
|
||||||
|
return name.text;
|
||||||
|
case ts.SyntaxKind.StringLiteral:
|
||||||
|
case ts.SyntaxKind.NumericLiteral:
|
||||||
|
return name.text;
|
||||||
|
case ts.SyntaxKind.ComputedPropertyName:
|
||||||
|
return isStringOrNumericLiteral(name.expression) ? name.expression.text : undefined!;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const name = getTextOfPropertyName(propName);
|
||||||
|
if (name && type) {
|
||||||
|
const result: ts.Symbol[] = [];
|
||||||
|
const symbol = type.getProperty(name);
|
||||||
|
if (type.flags & ts.TypeFlags.Union) {
|
||||||
|
for (const t of (<ts.UnionType>type).types) {
|
||||||
|
const symbol = t.getProperty(name);
|
||||||
|
if (symbol) {
|
||||||
|
result.push(symbol);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (symbol) {
|
||||||
|
result.push(symbol);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getPropertySymbolsFromContextualType(typeChecker: ts.TypeChecker, node: ts.ObjectLiteralElement): ts.Symbol[] {
|
||||||
|
const objectLiteral = <ts.ObjectLiteralExpression | ts.JsxAttributes>node.parent;
|
||||||
|
const contextualType = typeChecker.getContextualType(objectLiteral)!;
|
||||||
|
return getPropertySymbolsFromType(contextualType, node.name!)!;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Go to the original declaration for cases:
|
||||||
|
//
|
||||||
|
// (1) when the aliased symbol was declared in the location(parent).
|
||||||
|
// (2) when the aliased symbol is originating from an import.
|
||||||
|
//
|
||||||
|
function shouldSkipAlias(node: ts.Node, declaration: ts.Node): boolean {
|
||||||
|
if (node.kind !== ts.SyntaxKind.Identifier) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (node.parent === declaration) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
switch (declaration.kind) {
|
||||||
|
case ts.SyntaxKind.ImportClause:
|
||||||
|
case ts.SyntaxKind.ImportEqualsDeclaration:
|
||||||
|
return true;
|
||||||
|
case ts.SyntaxKind.ImportSpecifier:
|
||||||
|
return declaration.parent.kind === ts.SyntaxKind.NamedImports;
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!ts.isShorthandPropertyAssignment(node)) {
|
||||||
|
if (node.getChildCount() !== 0) {
|
||||||
|
return [null, null];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
let symbol = checker.getSymbolAtLocation(node);
|
||||||
|
let importNode: ts.Declaration = null;
|
||||||
|
if (symbol && symbol.flags & ts.SymbolFlags.Alias && shouldSkipAlias(node, symbol.declarations[0])) {
|
||||||
|
const aliased = checker.getAliasedSymbol(symbol);
|
||||||
|
if (aliased.declarations) {
|
||||||
|
// We should mark the import as visited
|
||||||
|
importNode = symbol.declarations[0];
|
||||||
|
symbol = aliased;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (symbol) {
|
||||||
|
// Because name in short-hand property assignment has two different meanings: property name and property value,
|
||||||
|
// using go-to-definition at such position should go to the variable declaration of the property value rather than
|
||||||
|
// go to the declaration of the property name (in this case stay at the same position). However, if go-to-definition
|
||||||
|
// is performed at the location of property access, we would like to go to definition of the property in the short-hand
|
||||||
|
// assignment. This case and others are handled by the following code.
|
||||||
|
if (node.parent.kind === ts.SyntaxKind.ShorthandPropertyAssignment) {
|
||||||
|
symbol = checker.getShorthandAssignmentValueSymbol(symbol.valueDeclaration);
|
||||||
|
}
|
||||||
|
|
||||||
|
// If the node is the name of a BindingElement within an ObjectBindingPattern instead of just returning the
|
||||||
|
// declaration the symbol (which is itself), we should try to get to the original type of the ObjectBindingPattern
|
||||||
|
// and return the property declaration for the referenced property.
|
||||||
|
// For example:
|
||||||
|
// import('./foo').then(({ b/*goto*/ar }) => undefined); => should get use to the declaration in file "./foo"
|
||||||
|
//
|
||||||
|
// function bar<T>(onfulfilled: (value: T) => void) { //....}
|
||||||
|
// interface Test {
|
||||||
|
// pr/*destination*/op1: number
|
||||||
|
// }
|
||||||
|
// bar<Test>(({pr/*goto*/op1})=>{});
|
||||||
|
if (ts.isPropertyName(node) && ts.isBindingElement(node.parent) && ts.isObjectBindingPattern(node.parent.parent) &&
|
||||||
|
(node === (node.parent.propertyName || node.parent.name))) {
|
||||||
|
const type = checker.getTypeAtLocation(node.parent.parent);
|
||||||
|
if (type) {
|
||||||
|
const propSymbols = getPropertySymbolsFromType(type, node);
|
||||||
|
if (propSymbols) {
|
||||||
|
symbol = propSymbols[0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// If the current location we want to find its definition is in an object literal, try to get the contextual type for the
|
||||||
|
// object literal, lookup the property symbol in the contextual type, and use this for goto-definition.
|
||||||
|
// For example
|
||||||
|
// interface Props{
|
||||||
|
// /*first*/prop1: number
|
||||||
|
// prop2: boolean
|
||||||
|
// }
|
||||||
|
// function Foo(arg: Props) {}
|
||||||
|
// Foo( { pr/*1*/op1: 10, prop2: false })
|
||||||
|
const element = getContainingObjectLiteralElement(node);
|
||||||
|
if (element && checker.getContextualType(element.parent as ts.Expression)) {
|
||||||
|
const propertySymbols = getPropertySymbolsFromContextualType(checker, element);
|
||||||
|
if (propertySymbols) {
|
||||||
|
symbol = propertySymbols[0];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (symbol && symbol.declarations) {
|
||||||
|
return [symbol, importNode];
|
||||||
|
}
|
||||||
|
|
||||||
|
return [null, null];
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Get the token whose text contains the position */
|
||||||
|
function getTokenAtPosition(sourceFile: ts.SourceFile, position: number, allowPositionInLeadingTrivia: boolean, includeEndPosition: boolean): ts.Node {
|
||||||
|
let current: ts.Node = sourceFile;
|
||||||
|
outer: while (true) {
|
||||||
|
// find the child that contains 'position'
|
||||||
|
for (const child of current.getChildren()) {
|
||||||
|
const start = allowPositionInLeadingTrivia ? child.getFullStart() : child.getStart(sourceFile, /*includeJsDoc*/ true);
|
||||||
|
if (start > position) {
|
||||||
|
// If this child begins after position, then all subsequent children will as well.
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
const end = child.getEnd();
|
||||||
|
if (position < end || (position === end && (child.kind === ts.SyntaxKind.EndOfFileToken || includeEndPosition))) {
|
||||||
|
current = child;
|
||||||
|
continue outer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return current;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//#endregion
|
||||||
73
build/lib/tslint/noStandaloneEditorRule.js
Normal file
73
build/lib/tslint/noStandaloneEditorRule.js
Normal file
@@ -0,0 +1,73 @@
|
|||||||
|
"use strict";
|
||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
var __extends = (this && this.__extends) || (function () {
|
||||||
|
var extendStatics = Object.setPrototypeOf ||
|
||||||
|
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
|
||||||
|
function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
|
||||||
|
return function (d, b) {
|
||||||
|
extendStatics(d, b);
|
||||||
|
function __() { this.constructor = d; }
|
||||||
|
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
|
||||||
|
};
|
||||||
|
})();
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
var ts = require("typescript");
|
||||||
|
var Lint = require("tslint");
|
||||||
|
var path_1 = require("path");
|
||||||
|
var Rule = /** @class */ (function (_super) {
|
||||||
|
__extends(Rule, _super);
|
||||||
|
function Rule() {
|
||||||
|
return _super !== null && _super.apply(this, arguments) || this;
|
||||||
|
}
|
||||||
|
Rule.prototype.apply = function (sourceFile) {
|
||||||
|
if (/vs(\/|\\)editor/.test(sourceFile.fileName)) {
|
||||||
|
// the vs/editor folder is allowed to use the standalone editor
|
||||||
|
return [];
|
||||||
|
}
|
||||||
|
return this.applyWithWalker(new NoStandaloneEditorRuleWalker(sourceFile, this.getOptions()));
|
||||||
|
};
|
||||||
|
return Rule;
|
||||||
|
}(Lint.Rules.AbstractRule));
|
||||||
|
exports.Rule = Rule;
|
||||||
|
var NoStandaloneEditorRuleWalker = /** @class */ (function (_super) {
|
||||||
|
__extends(NoStandaloneEditorRuleWalker, _super);
|
||||||
|
function NoStandaloneEditorRuleWalker(file, opts) {
|
||||||
|
return _super.call(this, file, opts) || this;
|
||||||
|
}
|
||||||
|
NoStandaloneEditorRuleWalker.prototype.visitImportEqualsDeclaration = function (node) {
|
||||||
|
if (node.moduleReference.kind === ts.SyntaxKind.ExternalModuleReference) {
|
||||||
|
this._validateImport(node.moduleReference.expression.getText(), node);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
NoStandaloneEditorRuleWalker.prototype.visitImportDeclaration = function (node) {
|
||||||
|
this._validateImport(node.moduleSpecifier.getText(), node);
|
||||||
|
};
|
||||||
|
NoStandaloneEditorRuleWalker.prototype.visitCallExpression = function (node) {
|
||||||
|
_super.prototype.visitCallExpression.call(this, node);
|
||||||
|
// import('foo') statements inside the code
|
||||||
|
if (node.expression.kind === ts.SyntaxKind.ImportKeyword) {
|
||||||
|
var path = node.arguments[0];
|
||||||
|
this._validateImport(path.getText(), node);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
NoStandaloneEditorRuleWalker.prototype._validateImport = function (path, node) {
|
||||||
|
// remove quotes
|
||||||
|
path = path.slice(1, -1);
|
||||||
|
// resolve relative paths
|
||||||
|
if (path[0] === '.') {
|
||||||
|
path = path_1.join(this.getSourceFile().fileName, path);
|
||||||
|
}
|
||||||
|
if (/vs(\/|\\)editor(\/|\\)standalone/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)common(\/|\\)standalone/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)editor.api/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)editor.main/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)editor.worker/.test(path)) {
|
||||||
|
// {{SQL CARBON EDIT}}
|
||||||
|
//this.addFailure(this.createFailure(node.getStart(), node.getWidth(), `Not allowed to import standalone editor modules. See https://github.com/Microsoft/vscode/wiki/Code-Organization`));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
return NoStandaloneEditorRuleWalker;
|
||||||
|
}(Lint.RuleWalker));
|
||||||
66
build/lib/tslint/noStandaloneEditorRule.ts
Normal file
66
build/lib/tslint/noStandaloneEditorRule.ts
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
import * as ts from 'typescript';
|
||||||
|
import * as Lint from 'tslint';
|
||||||
|
import { join } from 'path';
|
||||||
|
|
||||||
|
export class Rule extends Lint.Rules.AbstractRule {
|
||||||
|
public apply(sourceFile: ts.SourceFile): Lint.RuleFailure[] {
|
||||||
|
if (/vs(\/|\\)editor/.test(sourceFile.fileName)) {
|
||||||
|
// the vs/editor folder is allowed to use the standalone editor
|
||||||
|
return [];
|
||||||
|
}
|
||||||
|
return this.applyWithWalker(new NoStandaloneEditorRuleWalker(sourceFile, this.getOptions()));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class NoStandaloneEditorRuleWalker extends Lint.RuleWalker {
|
||||||
|
|
||||||
|
constructor(file: ts.SourceFile, opts: Lint.IOptions) {
|
||||||
|
super(file, opts);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected visitImportEqualsDeclaration(node: ts.ImportEqualsDeclaration): void {
|
||||||
|
if (node.moduleReference.kind === ts.SyntaxKind.ExternalModuleReference) {
|
||||||
|
this._validateImport(node.moduleReference.expression.getText(), node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
protected visitImportDeclaration(node: ts.ImportDeclaration): void {
|
||||||
|
this._validateImport(node.moduleSpecifier.getText(), node);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected visitCallExpression(node: ts.CallExpression): void {
|
||||||
|
super.visitCallExpression(node);
|
||||||
|
|
||||||
|
// import('foo') statements inside the code
|
||||||
|
if (node.expression.kind === ts.SyntaxKind.ImportKeyword) {
|
||||||
|
const [path] = node.arguments;
|
||||||
|
this._validateImport(path.getText(), node);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private _validateImport(path: string, node: ts.Node): void {
|
||||||
|
// remove quotes
|
||||||
|
path = path.slice(1, -1);
|
||||||
|
|
||||||
|
// resolve relative paths
|
||||||
|
if (path[0] === '.') {
|
||||||
|
path = join(this.getSourceFile().fileName, path);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (
|
||||||
|
/vs(\/|\\)editor(\/|\\)standalone/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)common(\/|\\)standalone/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)editor.api/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)editor.main/.test(path)
|
||||||
|
|| /vs(\/|\\)editor(\/|\\)editor.worker/.test(path)
|
||||||
|
) {
|
||||||
|
// {{SQL CARBON EDIT}}
|
||||||
|
//this.addFailure(this.createFailure(node.getStart(), node.getWidth(), `Not allowed to import standalone editor modules. See https://github.com/Microsoft/vscode/wiki/Code-Organization`));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -14,7 +14,6 @@ var fs = require("fs");
|
|||||||
var _rimraf = require("rimraf");
|
var _rimraf = require("rimraf");
|
||||||
var git = require("./git");
|
var git = require("./git");
|
||||||
var VinylFile = require("vinyl");
|
var VinylFile = require("vinyl");
|
||||||
var cp = require("child_process");
|
|
||||||
var NoCancellationToken = { isCancellationRequested: function () { return false; } };
|
var NoCancellationToken = { isCancellationRequested: function () { return false; } };
|
||||||
function incremental(streamProvider, initial, supportsCancellation) {
|
function incremental(streamProvider, initial, supportsCancellation) {
|
||||||
var input = es.through();
|
var input = es.through();
|
||||||
@@ -211,62 +210,6 @@ function filter(fn) {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
exports.filter = filter;
|
exports.filter = filter;
|
||||||
function tagExists(tagName) {
|
|
||||||
try {
|
|
||||||
cp.execSync("git rev-parse " + tagName, { stdio: 'ignore' });
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
catch (e) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/**
|
|
||||||
* Returns the version previous to the given version. Throws if a git tag for that version doesn't exist.
|
|
||||||
* Given 1.17.2, return 1.17.1
|
|
||||||
* 1.18.0 => 1.17.2. (or the highest 1.17.x)
|
|
||||||
* 2.0.0 => 1.18.0 (or the highest 1.x)
|
|
||||||
*/
|
|
||||||
function getPreviousVersion(versionStr, _tagExists) {
|
|
||||||
if (_tagExists === void 0) { _tagExists = tagExists; }
|
|
||||||
function getLatestTagFromBase(semverArr, componentToTest) {
|
|
||||||
var baseVersion = semverArr.join('.');
|
|
||||||
if (!_tagExists(baseVersion)) {
|
|
||||||
throw new Error('Failed to find git tag for base version, ' + baseVersion);
|
|
||||||
}
|
|
||||||
var goodTag;
|
|
||||||
do {
|
|
||||||
goodTag = semverArr.join('.');
|
|
||||||
semverArr[componentToTest]++;
|
|
||||||
} while (_tagExists(semverArr.join('.')));
|
|
||||||
return goodTag;
|
|
||||||
}
|
|
||||||
var semverArr = versionStringToNumberArray(versionStr);
|
|
||||||
if (semverArr[2] > 0) {
|
|
||||||
semverArr[2]--;
|
|
||||||
var previous = semverArr.join('.');
|
|
||||||
if (!_tagExists(previous)) {
|
|
||||||
throw new Error('Failed to find git tag for previous version, ' + previous);
|
|
||||||
}
|
|
||||||
return previous;
|
|
||||||
}
|
|
||||||
else if (semverArr[1] > 0) {
|
|
||||||
semverArr[1]--;
|
|
||||||
return getLatestTagFromBase(semverArr, 2);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
semverArr[0]--;
|
|
||||||
// Find 1.x.0 for latest x
|
|
||||||
var latestMinorVersion = getLatestTagFromBase(semverArr, 1);
|
|
||||||
// Find 1.x.y for latest y
|
|
||||||
return getLatestTagFromBase(versionStringToNumberArray(latestMinorVersion), 2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
exports.getPreviousVersion = getPreviousVersion;
|
|
||||||
function versionStringToNumberArray(versionStr) {
|
|
||||||
return versionStr
|
|
||||||
.split('.')
|
|
||||||
.map(function (s) { return parseInt(s); });
|
|
||||||
}
|
|
||||||
function versionStringToNumber(versionStr) {
|
function versionStringToNumber(versionStr) {
|
||||||
var semverRegex = /(\d+)\.(\d+)\.(\d+)/;
|
var semverRegex = /(\d+)\.(\d+)\.(\d+)/;
|
||||||
var match = versionStr.match(semverRegex);
|
var match = versionStr.match(semverRegex);
|
||||||
|
|||||||
@@ -17,7 +17,6 @@ import * as git from './git';
|
|||||||
import * as VinylFile from 'vinyl';
|
import * as VinylFile from 'vinyl';
|
||||||
import { ThroughStream } from 'through';
|
import { ThroughStream } from 'through';
|
||||||
import * as sm from 'source-map';
|
import * as sm from 'source-map';
|
||||||
import * as cp from 'child_process';
|
|
||||||
|
|
||||||
export interface ICancellationToken {
|
export interface ICancellationToken {
|
||||||
isCancellationRequested(): boolean;
|
isCancellationRequested(): boolean;
|
||||||
@@ -271,66 +270,6 @@ export function filter(fn: (data: any) => boolean): FilterStream {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
function tagExists(tagName: string): boolean {
|
|
||||||
try {
|
|
||||||
cp.execSync(`git rev-parse ${tagName}`, { stdio: 'ignore' });
|
|
||||||
return true;
|
|
||||||
} catch (e) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns the version previous to the given version. Throws if a git tag for that version doesn't exist.
|
|
||||||
* Given 1.17.2, return 1.17.1
|
|
||||||
* 1.18.0 => 1.17.2. (or the highest 1.17.x)
|
|
||||||
* 2.0.0 => 1.18.0 (or the highest 1.x)
|
|
||||||
*/
|
|
||||||
export function getPreviousVersion(versionStr: string, _tagExists = tagExists) {
|
|
||||||
function getLatestTagFromBase(semverArr: number[], componentToTest: number): string {
|
|
||||||
const baseVersion = semverArr.join('.');
|
|
||||||
if (!_tagExists(baseVersion)) {
|
|
||||||
throw new Error('Failed to find git tag for base version, ' + baseVersion);
|
|
||||||
}
|
|
||||||
|
|
||||||
let goodTag;
|
|
||||||
do {
|
|
||||||
goodTag = semverArr.join('.');
|
|
||||||
semverArr[componentToTest]++;
|
|
||||||
} while (_tagExists(semverArr.join('.')));
|
|
||||||
|
|
||||||
return goodTag;
|
|
||||||
}
|
|
||||||
|
|
||||||
const semverArr = versionStringToNumberArray(versionStr);
|
|
||||||
if (semverArr[2] > 0) {
|
|
||||||
semverArr[2]--;
|
|
||||||
const previous = semverArr.join('.');
|
|
||||||
if (!_tagExists(previous)) {
|
|
||||||
throw new Error('Failed to find git tag for previous version, ' + previous);
|
|
||||||
}
|
|
||||||
|
|
||||||
return previous;
|
|
||||||
} else if (semverArr[1] > 0) {
|
|
||||||
semverArr[1]--;
|
|
||||||
return getLatestTagFromBase(semverArr, 2);
|
|
||||||
} else {
|
|
||||||
semverArr[0]--;
|
|
||||||
|
|
||||||
// Find 1.x.0 for latest x
|
|
||||||
const latestMinorVersion = getLatestTagFromBase(semverArr, 1);
|
|
||||||
|
|
||||||
// Find 1.x.y for latest y
|
|
||||||
return getLatestTagFromBase(versionStringToNumberArray(latestMinorVersion), 2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function versionStringToNumberArray(versionStr: string): number[] {
|
|
||||||
return versionStr
|
|
||||||
.split('.')
|
|
||||||
.map(s => parseInt(s));
|
|
||||||
}
|
|
||||||
|
|
||||||
export function versionStringToNumber(versionStr: string) {
|
export function versionStringToNumber(versionStr: string) {
|
||||||
const semverRegex = /(\d+)\.(\d+)\.(\d+)/;
|
const semverRegex = /(\d+)\.(\d+)\.(\d+)/;
|
||||||
const match = versionStr.match(semverRegex);
|
const match = versionStr.match(semverRegex);
|
||||||
|
|||||||
@@ -134,7 +134,25 @@ function getTopLevelDeclaration(sourceFile, typeName) {
|
|||||||
function getNodeText(sourceFile, node) {
|
function getNodeText(sourceFile, node) {
|
||||||
return sourceFile.getFullText().substring(node.pos, node.end);
|
return sourceFile.getFullText().substring(node.pos, node.end);
|
||||||
}
|
}
|
||||||
function getMassagedTopLevelDeclarationText(sourceFile, declaration) {
|
function hasModifier(modifiers, kind) {
|
||||||
|
if (modifiers) {
|
||||||
|
for (var i = 0; i < modifiers.length; i++) {
|
||||||
|
var mod = modifiers[i];
|
||||||
|
if (mod.kind === kind) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
function isStatic(member) {
|
||||||
|
return hasModifier(member.modifiers, ts.SyntaxKind.StaticKeyword);
|
||||||
|
}
|
||||||
|
function isDefaultExport(declaration) {
|
||||||
|
return (hasModifier(declaration.modifiers, ts.SyntaxKind.DefaultKeyword)
|
||||||
|
&& hasModifier(declaration.modifiers, ts.SyntaxKind.ExportKeyword));
|
||||||
|
}
|
||||||
|
function getMassagedTopLevelDeclarationText(sourceFile, declaration, importName, usage) {
|
||||||
var result = getNodeText(sourceFile, declaration);
|
var result = getNodeText(sourceFile, declaration);
|
||||||
// if (result.indexOf('MonacoWorker') >= 0) {
|
// if (result.indexOf('MonacoWorker') >= 0) {
|
||||||
// console.log('here!');
|
// console.log('here!');
|
||||||
@@ -142,6 +160,18 @@ function getMassagedTopLevelDeclarationText(sourceFile, declaration) {
|
|||||||
// }
|
// }
|
||||||
if (declaration.kind === ts.SyntaxKind.InterfaceDeclaration || declaration.kind === ts.SyntaxKind.ClassDeclaration) {
|
if (declaration.kind === ts.SyntaxKind.InterfaceDeclaration || declaration.kind === ts.SyntaxKind.ClassDeclaration) {
|
||||||
var interfaceDeclaration = declaration;
|
var interfaceDeclaration = declaration;
|
||||||
|
var staticTypeName_1 = (isDefaultExport(interfaceDeclaration)
|
||||||
|
? importName + ".default"
|
||||||
|
: importName + "." + declaration.name.text);
|
||||||
|
var instanceTypeName_1 = staticTypeName_1;
|
||||||
|
var typeParametersCnt = (interfaceDeclaration.typeParameters ? interfaceDeclaration.typeParameters.length : 0);
|
||||||
|
if (typeParametersCnt > 0) {
|
||||||
|
var arr = [];
|
||||||
|
for (var i = 0; i < typeParametersCnt; i++) {
|
||||||
|
arr.push('any');
|
||||||
|
}
|
||||||
|
instanceTypeName_1 = instanceTypeName_1 + "<" + arr.join(',') + ">";
|
||||||
|
}
|
||||||
var members = interfaceDeclaration.members;
|
var members = interfaceDeclaration.members;
|
||||||
members.forEach(function (member) {
|
members.forEach(function (member) {
|
||||||
try {
|
try {
|
||||||
@@ -151,6 +181,15 @@ function getMassagedTopLevelDeclarationText(sourceFile, declaration) {
|
|||||||
result = result.replace(memberText, '');
|
result = result.replace(memberText, '');
|
||||||
// console.log('AFTER: ', result);
|
// console.log('AFTER: ', result);
|
||||||
}
|
}
|
||||||
|
else {
|
||||||
|
var memberName = member.name.text;
|
||||||
|
if (isStatic(member)) {
|
||||||
|
usage.push("a = " + staticTypeName_1 + "." + memberName + ";");
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
usage.push("a = (<" + instanceTypeName_1 + ">b)." + memberName + ";");
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
catch (err) {
|
catch (err) {
|
||||||
// life..
|
// life..
|
||||||
@@ -211,6 +250,16 @@ function generateDeclarationFile(out, inputFiles, recipe) {
|
|||||||
var endl = /\r\n/.test(recipe) ? '\r\n' : '\n';
|
var endl = /\r\n/.test(recipe) ? '\r\n' : '\n';
|
||||||
var lines = recipe.split(endl);
|
var lines = recipe.split(endl);
|
||||||
var result = [];
|
var result = [];
|
||||||
|
var usageCounter = 0;
|
||||||
|
var usageImports = [];
|
||||||
|
var usage = [];
|
||||||
|
usage.push("var a;");
|
||||||
|
usage.push("var b;");
|
||||||
|
var generateUsageImport = function (moduleId) {
|
||||||
|
var importName = 'm' + (++usageCounter);
|
||||||
|
usageImports.push("import * as " + importName + " from '" + moduleId.replace(/\.d\.ts$/, '') + "';");
|
||||||
|
return importName;
|
||||||
|
};
|
||||||
lines.forEach(function (line) {
|
lines.forEach(function (line) {
|
||||||
var m1 = line.match(/^\s*#include\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
var m1 = line.match(/^\s*#include\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
||||||
if (m1) {
|
if (m1) {
|
||||||
@@ -220,6 +269,7 @@ function generateDeclarationFile(out, inputFiles, recipe) {
|
|||||||
if (!sourceFile_1) {
|
if (!sourceFile_1) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
var importName_1 = generateUsageImport(moduleId);
|
||||||
var replacer_1 = createReplacer(m1[2]);
|
var replacer_1 = createReplacer(m1[2]);
|
||||||
var typeNames = m1[3].split(/,/);
|
var typeNames = m1[3].split(/,/);
|
||||||
typeNames.forEach(function (typeName) {
|
typeNames.forEach(function (typeName) {
|
||||||
@@ -232,7 +282,7 @@ function generateDeclarationFile(out, inputFiles, recipe) {
|
|||||||
logErr('Cannot find type ' + typeName);
|
logErr('Cannot find type ' + typeName);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
result.push(replacer_1(getMassagedTopLevelDeclarationText(sourceFile_1, declaration)));
|
result.push(replacer_1(getMassagedTopLevelDeclarationText(sourceFile_1, declaration, importName_1, usage)));
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -244,6 +294,7 @@ function generateDeclarationFile(out, inputFiles, recipe) {
|
|||||||
if (!sourceFile_2) {
|
if (!sourceFile_2) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
var importName_2 = generateUsageImport(moduleId);
|
||||||
var replacer_2 = createReplacer(m2[2]);
|
var replacer_2 = createReplacer(m2[2]);
|
||||||
var typeNames = m2[3].split(/,/);
|
var typeNames = m2[3].split(/,/);
|
||||||
var typesToExcludeMap_1 = {};
|
var typesToExcludeMap_1 = {};
|
||||||
@@ -271,7 +322,7 @@ function generateDeclarationFile(out, inputFiles, recipe) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
result.push(replacer_2(getMassagedTopLevelDeclarationText(sourceFile_2, declaration)));
|
result.push(replacer_2(getMassagedTopLevelDeclarationText(sourceFile_2, declaration, importName_2, usage)));
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -282,9 +333,12 @@ function generateDeclarationFile(out, inputFiles, recipe) {
|
|||||||
resultTxt = resultTxt.replace(/\bEvent</g, 'IEvent<');
|
resultTxt = resultTxt.replace(/\bEvent</g, 'IEvent<');
|
||||||
resultTxt = resultTxt.replace(/\bTPromise</g, 'Promise<');
|
resultTxt = resultTxt.replace(/\bTPromise</g, 'Promise<');
|
||||||
resultTxt = format(resultTxt);
|
resultTxt = format(resultTxt);
|
||||||
return resultTxt;
|
return [
|
||||||
|
resultTxt,
|
||||||
|
usageImports.join('\n') + "\n\n" + usage.join('\n')
|
||||||
|
];
|
||||||
}
|
}
|
||||||
function getFilesToWatch(out) {
|
function getIncludesInRecipe() {
|
||||||
var recipe = fs.readFileSync(RECIPE_PATH).toString();
|
var recipe = fs.readFileSync(RECIPE_PATH).toString();
|
||||||
var lines = recipe.split(/\r\n|\n|\r/);
|
var lines = recipe.split(/\r\n|\n|\r/);
|
||||||
var result = [];
|
var result = [];
|
||||||
@@ -292,24 +346,27 @@ function getFilesToWatch(out) {
|
|||||||
var m1 = line.match(/^\s*#include\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
var m1 = line.match(/^\s*#include\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
||||||
if (m1) {
|
if (m1) {
|
||||||
var moduleId = m1[1];
|
var moduleId = m1[1];
|
||||||
result.push(moduleIdToPath(out, moduleId));
|
result.push(moduleId);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
var m2 = line.match(/^\s*#includeAll\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
var m2 = line.match(/^\s*#includeAll\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
||||||
if (m2) {
|
if (m2) {
|
||||||
var moduleId = m2[1];
|
var moduleId = m2[1];
|
||||||
result.push(moduleIdToPath(out, moduleId));
|
result.push(moduleId);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
function getFilesToWatch(out) {
|
||||||
|
return getIncludesInRecipe().map(function (moduleId) { return moduleIdToPath(out, moduleId); });
|
||||||
|
}
|
||||||
exports.getFilesToWatch = getFilesToWatch;
|
exports.getFilesToWatch = getFilesToWatch;
|
||||||
function run(out, inputFiles) {
|
function run(out, inputFiles) {
|
||||||
log('Starting monaco.d.ts generation');
|
log('Starting monaco.d.ts generation');
|
||||||
SOURCE_FILE_MAP = {};
|
SOURCE_FILE_MAP = {};
|
||||||
var recipe = fs.readFileSync(RECIPE_PATH).toString();
|
var recipe = fs.readFileSync(RECIPE_PATH).toString();
|
||||||
var result = generateDeclarationFile(out, inputFiles, recipe);
|
var _a = generateDeclarationFile(out, inputFiles, recipe), result = _a[0], usageContent = _a[1];
|
||||||
var currentContent = fs.readFileSync(DECLARATION_PATH).toString();
|
var currentContent = fs.readFileSync(DECLARATION_PATH).toString();
|
||||||
log('Finished monaco.d.ts generation');
|
log('Finished monaco.d.ts generation');
|
||||||
var one = currentContent.replace(/\r\n/gm, '\n');
|
var one = currentContent.replace(/\r\n/gm, '\n');
|
||||||
@@ -317,6 +374,7 @@ function run(out, inputFiles) {
|
|||||||
var isTheSame = one === other;
|
var isTheSame = one === other;
|
||||||
return {
|
return {
|
||||||
content: result,
|
content: result,
|
||||||
|
usageContent: usageContent,
|
||||||
filePath: DECLARATION_PATH,
|
filePath: DECLARATION_PATH,
|
||||||
isTheSame: isTheSame
|
isTheSame: isTheSame
|
||||||
};
|
};
|
||||||
@@ -326,3 +384,78 @@ function complainErrors() {
|
|||||||
logErr('Not running monaco.d.ts generation due to compile errors');
|
logErr('Not running monaco.d.ts generation due to compile errors');
|
||||||
}
|
}
|
||||||
exports.complainErrors = complainErrors;
|
exports.complainErrors = complainErrors;
|
||||||
|
var TypeScriptLanguageServiceHost = /** @class */ (function () {
|
||||||
|
function TypeScriptLanguageServiceHost(libs, files, compilerOptions) {
|
||||||
|
this._libs = libs;
|
||||||
|
this._files = files;
|
||||||
|
this._compilerOptions = compilerOptions;
|
||||||
|
}
|
||||||
|
// --- language service host ---------------
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getCompilationSettings = function () {
|
||||||
|
return this._compilerOptions;
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptFileNames = function () {
|
||||||
|
return ([]
|
||||||
|
.concat(Object.keys(this._libs))
|
||||||
|
.concat(Object.keys(this._files)));
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptVersion = function (fileName) {
|
||||||
|
return '1';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getProjectVersion = function () {
|
||||||
|
return '1';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptSnapshot = function (fileName) {
|
||||||
|
if (this._files.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._files[fileName]);
|
||||||
|
}
|
||||||
|
else if (this._libs.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._libs[fileName]);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
return ts.ScriptSnapshot.fromString('');
|
||||||
|
}
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getScriptKind = function (fileName) {
|
||||||
|
return ts.ScriptKind.TS;
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getCurrentDirectory = function () {
|
||||||
|
return '';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.getDefaultLibFileName = function (options) {
|
||||||
|
return 'defaultLib:es5';
|
||||||
|
};
|
||||||
|
TypeScriptLanguageServiceHost.prototype.isDefaultLibFileName = function (fileName) {
|
||||||
|
return fileName === this.getDefaultLibFileName(this._compilerOptions);
|
||||||
|
};
|
||||||
|
return TypeScriptLanguageServiceHost;
|
||||||
|
}());
|
||||||
|
function execute() {
|
||||||
|
var OUTPUT_FILES = {};
|
||||||
|
var SRC_FILES = {};
|
||||||
|
var SRC_FILE_TO_EXPECTED_NAME = {};
|
||||||
|
getIncludesInRecipe().forEach(function (moduleId) {
|
||||||
|
if (/\.d\.ts$/.test(moduleId)) {
|
||||||
|
var fileName_1 = path.join(SRC, moduleId);
|
||||||
|
OUTPUT_FILES[moduleIdToPath('src', moduleId)] = fs.readFileSync(fileName_1).toString();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
var fileName = path.join(SRC, moduleId) + '.ts';
|
||||||
|
SRC_FILES[fileName] = fs.readFileSync(fileName).toString();
|
||||||
|
SRC_FILE_TO_EXPECTED_NAME[fileName] = moduleIdToPath('src', moduleId);
|
||||||
|
});
|
||||||
|
var languageService = ts.createLanguageService(new TypeScriptLanguageServiceHost({}, SRC_FILES, {}));
|
||||||
|
var t1 = Date.now();
|
||||||
|
Object.keys(SRC_FILES).forEach(function (fileName) {
|
||||||
|
var t = Date.now();
|
||||||
|
var emitOutput = languageService.getEmitOutput(fileName, true);
|
||||||
|
OUTPUT_FILES[SRC_FILE_TO_EXPECTED_NAME[fileName]] = emitOutput.outputFiles[0].text;
|
||||||
|
// console.log(`Generating .d.ts for ${fileName} took ${Date.now() - t} ms`);
|
||||||
|
});
|
||||||
|
console.log("Generating .d.ts took " + (Date.now() - t1) + " ms");
|
||||||
|
// console.log(result.filePath);
|
||||||
|
// fs.writeFileSync(result.filePath, result.content.replace(/\r\n/gm, '\n'));
|
||||||
|
// fs.writeFileSync(path.join(SRC, 'user.ts'), result.usageContent.replace(/\r\n/gm, '\n'));
|
||||||
|
return run('src', OUTPUT_FILES);
|
||||||
|
}
|
||||||
|
exports.execute = execute;
|
||||||
|
|||||||
@@ -153,8 +153,30 @@ function getNodeText(sourceFile: ts.SourceFile, node: { pos: number; end: number
|
|||||||
return sourceFile.getFullText().substring(node.pos, node.end);
|
return sourceFile.getFullText().substring(node.pos, node.end);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function hasModifier(modifiers: ts.NodeArray<ts.Modifier>, kind: ts.SyntaxKind): boolean {
|
||||||
|
if (modifiers) {
|
||||||
|
for (let i = 0; i < modifiers.length; i++) {
|
||||||
|
let mod = modifiers[i];
|
||||||
|
if (mod.kind === kind) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
function getMassagedTopLevelDeclarationText(sourceFile: ts.SourceFile, declaration: TSTopLevelDeclare): string {
|
function isStatic(member: ts.ClassElement | ts.TypeElement): boolean {
|
||||||
|
return hasModifier(member.modifiers, ts.SyntaxKind.StaticKeyword);
|
||||||
|
}
|
||||||
|
|
||||||
|
function isDefaultExport(declaration: ts.InterfaceDeclaration | ts.ClassDeclaration): boolean {
|
||||||
|
return (
|
||||||
|
hasModifier(declaration.modifiers, ts.SyntaxKind.DefaultKeyword)
|
||||||
|
&& hasModifier(declaration.modifiers, ts.SyntaxKind.ExportKeyword)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getMassagedTopLevelDeclarationText(sourceFile: ts.SourceFile, declaration: TSTopLevelDeclare, importName: string, usage: string[]): string {
|
||||||
let result = getNodeText(sourceFile, declaration);
|
let result = getNodeText(sourceFile, declaration);
|
||||||
// if (result.indexOf('MonacoWorker') >= 0) {
|
// if (result.indexOf('MonacoWorker') >= 0) {
|
||||||
// console.log('here!');
|
// console.log('here!');
|
||||||
@@ -163,7 +185,23 @@ function getMassagedTopLevelDeclarationText(sourceFile: ts.SourceFile, declarati
|
|||||||
if (declaration.kind === ts.SyntaxKind.InterfaceDeclaration || declaration.kind === ts.SyntaxKind.ClassDeclaration) {
|
if (declaration.kind === ts.SyntaxKind.InterfaceDeclaration || declaration.kind === ts.SyntaxKind.ClassDeclaration) {
|
||||||
let interfaceDeclaration = <ts.InterfaceDeclaration | ts.ClassDeclaration>declaration;
|
let interfaceDeclaration = <ts.InterfaceDeclaration | ts.ClassDeclaration>declaration;
|
||||||
|
|
||||||
let members: ts.NodeArray<ts.Node> = interfaceDeclaration.members;
|
const staticTypeName = (
|
||||||
|
isDefaultExport(interfaceDeclaration)
|
||||||
|
? `${importName}.default`
|
||||||
|
: `${importName}.${declaration.name.text}`
|
||||||
|
);
|
||||||
|
|
||||||
|
let instanceTypeName = staticTypeName;
|
||||||
|
const typeParametersCnt = (interfaceDeclaration.typeParameters ? interfaceDeclaration.typeParameters.length : 0);
|
||||||
|
if (typeParametersCnt > 0) {
|
||||||
|
let arr: string[] = [];
|
||||||
|
for (let i = 0; i < typeParametersCnt; i++) {
|
||||||
|
arr.push('any');
|
||||||
|
}
|
||||||
|
instanceTypeName = `${instanceTypeName}<${arr.join(',')}>`;
|
||||||
|
}
|
||||||
|
|
||||||
|
const members: ts.NodeArray<ts.ClassElement | ts.TypeElement> = interfaceDeclaration.members;
|
||||||
members.forEach((member) => {
|
members.forEach((member) => {
|
||||||
try {
|
try {
|
||||||
let memberText = getNodeText(sourceFile, member);
|
let memberText = getNodeText(sourceFile, member);
|
||||||
@@ -171,6 +209,13 @@ function getMassagedTopLevelDeclarationText(sourceFile: ts.SourceFile, declarati
|
|||||||
// console.log('BEFORE: ', result);
|
// console.log('BEFORE: ', result);
|
||||||
result = result.replace(memberText, '');
|
result = result.replace(memberText, '');
|
||||||
// console.log('AFTER: ', result);
|
// console.log('AFTER: ', result);
|
||||||
|
} else {
|
||||||
|
const memberName = (<ts.Identifier | ts.StringLiteral>member.name).text;
|
||||||
|
if (isStatic(member)) {
|
||||||
|
usage.push(`a = ${staticTypeName}.${memberName};`);
|
||||||
|
} else {
|
||||||
|
usage.push(`a = (<${instanceTypeName}>b).${memberName};`);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
// life..
|
// life..
|
||||||
@@ -237,11 +282,24 @@ function createReplacer(data: string): (str: string) => string {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
function generateDeclarationFile(out: string, inputFiles: { [file: string]: string; }, recipe: string): string {
|
function generateDeclarationFile(out: string, inputFiles: { [file: string]: string; }, recipe: string): [string, string] {
|
||||||
const endl = /\r\n/.test(recipe) ? '\r\n' : '\n';
|
const endl = /\r\n/.test(recipe) ? '\r\n' : '\n';
|
||||||
|
|
||||||
let lines = recipe.split(endl);
|
let lines = recipe.split(endl);
|
||||||
let result = [];
|
let result: string[] = [];
|
||||||
|
|
||||||
|
let usageCounter = 0;
|
||||||
|
let usageImports: string[] = [];
|
||||||
|
let usage: string[] = [];
|
||||||
|
|
||||||
|
usage.push(`var a;`);
|
||||||
|
usage.push(`var b;`);
|
||||||
|
|
||||||
|
const generateUsageImport = (moduleId: string) => {
|
||||||
|
let importName = 'm' + (++usageCounter);
|
||||||
|
usageImports.push(`import * as ${importName} from '${moduleId.replace(/\.d\.ts$/, '')}';`);
|
||||||
|
return importName;
|
||||||
|
};
|
||||||
|
|
||||||
lines.forEach(line => {
|
lines.forEach(line => {
|
||||||
|
|
||||||
@@ -254,6 +312,8 @@ function generateDeclarationFile(out: string, inputFiles: { [file: string]: stri
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const importName = generateUsageImport(moduleId);
|
||||||
|
|
||||||
let replacer = createReplacer(m1[2]);
|
let replacer = createReplacer(m1[2]);
|
||||||
|
|
||||||
let typeNames = m1[3].split(/,/);
|
let typeNames = m1[3].split(/,/);
|
||||||
@@ -267,7 +327,7 @@ function generateDeclarationFile(out: string, inputFiles: { [file: string]: stri
|
|||||||
logErr('Cannot find type ' + typeName);
|
logErr('Cannot find type ' + typeName);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
result.push(replacer(getMassagedTopLevelDeclarationText(sourceFile, declaration)));
|
result.push(replacer(getMassagedTopLevelDeclarationText(sourceFile, declaration, importName, usage)));
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -281,6 +341,8 @@ function generateDeclarationFile(out: string, inputFiles: { [file: string]: stri
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const importName = generateUsageImport(moduleId);
|
||||||
|
|
||||||
let replacer = createReplacer(m2[2]);
|
let replacer = createReplacer(m2[2]);
|
||||||
|
|
||||||
let typeNames = m2[3].split(/,/);
|
let typeNames = m2[3].split(/,/);
|
||||||
@@ -309,7 +371,7 @@ function generateDeclarationFile(out: string, inputFiles: { [file: string]: stri
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
result.push(replacer(getMassagedTopLevelDeclarationText(sourceFile, declaration)));
|
result.push(replacer(getMassagedTopLevelDeclarationText(sourceFile, declaration, importName, usage)));
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -324,10 +386,13 @@ function generateDeclarationFile(out: string, inputFiles: { [file: string]: stri
|
|||||||
|
|
||||||
resultTxt = format(resultTxt);
|
resultTxt = format(resultTxt);
|
||||||
|
|
||||||
return resultTxt;
|
return [
|
||||||
|
resultTxt,
|
||||||
|
`${usageImports.join('\n')}\n\n${usage.join('\n')}`
|
||||||
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getFilesToWatch(out: string): string[] {
|
function getIncludesInRecipe(): string[] {
|
||||||
let recipe = fs.readFileSync(RECIPE_PATH).toString();
|
let recipe = fs.readFileSync(RECIPE_PATH).toString();
|
||||||
let lines = recipe.split(/\r\n|\n|\r/);
|
let lines = recipe.split(/\r\n|\n|\r/);
|
||||||
let result = [];
|
let result = [];
|
||||||
@@ -337,14 +402,14 @@ export function getFilesToWatch(out: string): string[] {
|
|||||||
let m1 = line.match(/^\s*#include\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
let m1 = line.match(/^\s*#include\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
||||||
if (m1) {
|
if (m1) {
|
||||||
let moduleId = m1[1];
|
let moduleId = m1[1];
|
||||||
result.push(moduleIdToPath(out, moduleId));
|
result.push(moduleId);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
let m2 = line.match(/^\s*#includeAll\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
let m2 = line.match(/^\s*#includeAll\(([^;)]*)(;[^)]*)?\)\:(.*)$/);
|
||||||
if (m2) {
|
if (m2) {
|
||||||
let moduleId = m2[1];
|
let moduleId = m2[1];
|
||||||
result.push(moduleIdToPath(out, moduleId));
|
result.push(moduleId);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@@ -352,8 +417,13 @@ export function getFilesToWatch(out: string): string[] {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function getFilesToWatch(out: string): string[] {
|
||||||
|
return getIncludesInRecipe().map((moduleId) => moduleIdToPath(out, moduleId));
|
||||||
|
}
|
||||||
|
|
||||||
export interface IMonacoDeclarationResult {
|
export interface IMonacoDeclarationResult {
|
||||||
content: string;
|
content: string;
|
||||||
|
usageContent: string;
|
||||||
filePath: string;
|
filePath: string;
|
||||||
isTheSame: boolean;
|
isTheSame: boolean;
|
||||||
}
|
}
|
||||||
@@ -363,7 +433,7 @@ export function run(out: string, inputFiles: { [file: string]: string; }): IMona
|
|||||||
SOURCE_FILE_MAP = {};
|
SOURCE_FILE_MAP = {};
|
||||||
|
|
||||||
let recipe = fs.readFileSync(RECIPE_PATH).toString();
|
let recipe = fs.readFileSync(RECIPE_PATH).toString();
|
||||||
let result = generateDeclarationFile(out, inputFiles, recipe);
|
let [result, usageContent] = generateDeclarationFile(out, inputFiles, recipe);
|
||||||
|
|
||||||
let currentContent = fs.readFileSync(DECLARATION_PATH).toString();
|
let currentContent = fs.readFileSync(DECLARATION_PATH).toString();
|
||||||
log('Finished monaco.d.ts generation');
|
log('Finished monaco.d.ts generation');
|
||||||
@@ -374,6 +444,7 @@ export function run(out: string, inputFiles: { [file: string]: string; }): IMona
|
|||||||
|
|
||||||
return {
|
return {
|
||||||
content: result,
|
content: result,
|
||||||
|
usageContent: usageContent,
|
||||||
filePath: DECLARATION_PATH,
|
filePath: DECLARATION_PATH,
|
||||||
isTheSame
|
isTheSame
|
||||||
};
|
};
|
||||||
@@ -382,3 +453,96 @@ export function run(out: string, inputFiles: { [file: string]: string; }): IMona
|
|||||||
export function complainErrors() {
|
export function complainErrors() {
|
||||||
logErr('Not running monaco.d.ts generation due to compile errors');
|
logErr('Not running monaco.d.ts generation due to compile errors');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
interface ILibMap { [libName: string]: string; }
|
||||||
|
interface IFileMap { [fileName: string]: string; }
|
||||||
|
|
||||||
|
class TypeScriptLanguageServiceHost implements ts.LanguageServiceHost {
|
||||||
|
|
||||||
|
private readonly _libs: ILibMap;
|
||||||
|
private readonly _files: IFileMap;
|
||||||
|
private readonly _compilerOptions: ts.CompilerOptions;
|
||||||
|
|
||||||
|
constructor(libs: ILibMap, files: IFileMap, compilerOptions: ts.CompilerOptions) {
|
||||||
|
this._libs = libs;
|
||||||
|
this._files = files;
|
||||||
|
this._compilerOptions = compilerOptions;
|
||||||
|
}
|
||||||
|
|
||||||
|
// --- language service host ---------------
|
||||||
|
|
||||||
|
getCompilationSettings(): ts.CompilerOptions {
|
||||||
|
return this._compilerOptions;
|
||||||
|
}
|
||||||
|
getScriptFileNames(): string[] {
|
||||||
|
return (
|
||||||
|
[]
|
||||||
|
.concat(Object.keys(this._libs))
|
||||||
|
.concat(Object.keys(this._files))
|
||||||
|
);
|
||||||
|
}
|
||||||
|
getScriptVersion(fileName: string): string {
|
||||||
|
return '1';
|
||||||
|
}
|
||||||
|
getProjectVersion(): string {
|
||||||
|
return '1';
|
||||||
|
}
|
||||||
|
getScriptSnapshot(fileName: string): ts.IScriptSnapshot {
|
||||||
|
if (this._files.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._files[fileName]);
|
||||||
|
} else if (this._libs.hasOwnProperty(fileName)) {
|
||||||
|
return ts.ScriptSnapshot.fromString(this._libs[fileName]);
|
||||||
|
} else {
|
||||||
|
return ts.ScriptSnapshot.fromString('');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
getScriptKind(fileName: string): ts.ScriptKind {
|
||||||
|
return ts.ScriptKind.TS;
|
||||||
|
}
|
||||||
|
getCurrentDirectory(): string {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
getDefaultLibFileName(options: ts.CompilerOptions): string {
|
||||||
|
return 'defaultLib:es5';
|
||||||
|
}
|
||||||
|
isDefaultLibFileName(fileName: string): boolean {
|
||||||
|
return fileName === this.getDefaultLibFileName(this._compilerOptions);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export function execute(): IMonacoDeclarationResult {
|
||||||
|
|
||||||
|
const OUTPUT_FILES: { [file: string]: string; } = {};
|
||||||
|
const SRC_FILES: IFileMap = {};
|
||||||
|
const SRC_FILE_TO_EXPECTED_NAME: { [filename: string]: string; } = {};
|
||||||
|
getIncludesInRecipe().forEach((moduleId) => {
|
||||||
|
if (/\.d\.ts$/.test(moduleId)) {
|
||||||
|
let fileName = path.join(SRC, moduleId);
|
||||||
|
OUTPUT_FILES[moduleIdToPath('src', moduleId)] = fs.readFileSync(fileName).toString();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let fileName = path.join(SRC, moduleId) + '.ts';
|
||||||
|
SRC_FILES[fileName] = fs.readFileSync(fileName).toString();
|
||||||
|
SRC_FILE_TO_EXPECTED_NAME[fileName] = moduleIdToPath('src', moduleId);
|
||||||
|
});
|
||||||
|
|
||||||
|
const languageService = ts.createLanguageService(new TypeScriptLanguageServiceHost({}, SRC_FILES, {}));
|
||||||
|
|
||||||
|
var t1 = Date.now();
|
||||||
|
Object.keys(SRC_FILES).forEach((fileName) => {
|
||||||
|
var t = Date.now();
|
||||||
|
const emitOutput = languageService.getEmitOutput(fileName, true);
|
||||||
|
OUTPUT_FILES[SRC_FILE_TO_EXPECTED_NAME[fileName]] = emitOutput.outputFiles[0].text;
|
||||||
|
// console.log(`Generating .d.ts for ${fileName} took ${Date.now() - t} ms`);
|
||||||
|
});
|
||||||
|
console.log(`Generating .d.ts took ${Date.now() - t1} ms`);
|
||||||
|
|
||||||
|
// console.log(result.filePath);
|
||||||
|
// fs.writeFileSync(result.filePath, result.content.replace(/\r\n/gm, '\n'));
|
||||||
|
// fs.writeFileSync(path.join(SRC, 'user.ts'), result.usageContent.replace(/\r\n/gm, '\n'));
|
||||||
|
|
||||||
|
return run('src', OUTPUT_FILES);
|
||||||
|
}
|
||||||
|
|||||||
@@ -32,6 +32,10 @@ declare namespace monaco {
|
|||||||
Error = 3,
|
Error = 3,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export enum MarkerTag {
|
||||||
|
Unnecessary = 1,
|
||||||
|
}
|
||||||
|
|
||||||
export enum MarkerSeverity {
|
export enum MarkerSeverity {
|
||||||
Hint = 1,
|
Hint = 1,
|
||||||
Info = 2,
|
Info = 2,
|
||||||
|
|||||||
82
build/monaco/monaco.usage.recipe
Normal file
82
build/monaco/monaco.usage.recipe
Normal file
@@ -0,0 +1,82 @@
|
|||||||
|
|
||||||
|
// This file is adding references to various symbols which should not be removed via tree shaking
|
||||||
|
|
||||||
|
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||||
|
import { IContextViewService } from 'vs/platform/contextview/browser/contextView';
|
||||||
|
import { IHighlight } from 'vs/base/parts/quickopen/browser/quickOpenModel';
|
||||||
|
import { IWorkspaceContextService } from 'vs/platform/workspace/common/workspace';
|
||||||
|
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
||||||
|
import { CountBadge } from 'vs/base/browser/ui/countBadge/countBadge';
|
||||||
|
import { SimpleWorkerClient, create as create1 } from 'vs/base/common/worker/simpleWorker';
|
||||||
|
import { create as create2 } from 'vs/editor/common/services/editorSimpleWorker';
|
||||||
|
import { QuickOpenWidget } from 'vs/base/parts/quickopen/browser/quickOpenWidget';
|
||||||
|
import { SyncDescriptor0, SyncDescriptor1, SyncDescriptor2, SyncDescriptor3, SyncDescriptor4, SyncDescriptor5, SyncDescriptor6, SyncDescriptor7, SyncDescriptor8 } from 'vs/platform/instantiation/common/descriptors';
|
||||||
|
import { PolyfillPromise } from 'vs/base/common/winjs.polyfill.promise';
|
||||||
|
import { DiffNavigator } from 'vs/editor/browser/widget/diffNavigator';
|
||||||
|
import * as editorAPI from 'vs/editor/editor.api';
|
||||||
|
|
||||||
|
(function () {
|
||||||
|
var a: any;
|
||||||
|
var b: any;
|
||||||
|
a = (<IContextViewService>b).layout; // IContextViewProvider
|
||||||
|
a = (<IWorkspaceContextService>b).getWorkspaceFolder; // IWorkspaceFolderProvider
|
||||||
|
a = (<IWorkspaceContextService>b).getWorkspace; // IWorkspaceFolderProvider
|
||||||
|
a = (<CountBadge>b).style; // IThemable
|
||||||
|
a = (<QuickOpenWidget>b).style; // IThemable
|
||||||
|
a = (<IEnvironmentService>b).userHome; // IUserHomeProvider
|
||||||
|
a = (<DiffNavigator>b).previous; // IDiffNavigator
|
||||||
|
a = (<ServiceIdentifier<any>>b).type;
|
||||||
|
a = (<IHighlight>b).start;
|
||||||
|
a = (<IHighlight>b).end;
|
||||||
|
a = (<SimpleWorkerClient<any>>b).getProxyObject; // IWorkerClient
|
||||||
|
a = create1;
|
||||||
|
a = create2;
|
||||||
|
|
||||||
|
// promise polyfill
|
||||||
|
a = PolyfillPromise.all;
|
||||||
|
a = PolyfillPromise.race;
|
||||||
|
a = PolyfillPromise.resolve;
|
||||||
|
a = PolyfillPromise.reject;
|
||||||
|
a = (<PolyfillPromise>b).then;
|
||||||
|
a = (<PolyfillPromise>b).catch;
|
||||||
|
|
||||||
|
// injection madness
|
||||||
|
a = (<SyncDescriptor0<any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor0<any>>b).bind;
|
||||||
|
a = (<SyncDescriptor1<any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor1<any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor1<any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor1<any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor2<any, any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor2<any, any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor3<any, any, any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor3<any, any, any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor4<any, any, any, any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor4<any, any, any, any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor5<any, any, any, any, any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor5<any, any, any, any, any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor6<any, any, any, any, any, any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor6<any, any, any, any, any, any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor7<any, any, any, any, any, any, any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor7<any, any, any, any, any, any, any, any>>b).bind;
|
||||||
|
a = (<SyncDescriptor8<any, any, any, any, any, any, any, any, any>>b).ctor;
|
||||||
|
a = (<SyncDescriptor8<any, any, any, any, any, any, any, any, any>>b).bind;
|
||||||
|
|
||||||
|
// exported API
|
||||||
|
a = editorAPI.CancellationTokenSource;
|
||||||
|
a = editorAPI.Emitter;
|
||||||
|
a = editorAPI.KeyCode;
|
||||||
|
a = editorAPI.KeyMod;
|
||||||
|
a = editorAPI.Position;
|
||||||
|
a = editorAPI.Range;
|
||||||
|
a = editorAPI.Selection;
|
||||||
|
a = editorAPI.SelectionDirection;
|
||||||
|
a = editorAPI.Severity;
|
||||||
|
a = editorAPI.MarkerSeverity;
|
||||||
|
a = editorAPI.MarkerTag;
|
||||||
|
a = editorAPI.Promise;
|
||||||
|
a = editorAPI.Uri;
|
||||||
|
a = editorAPI.Token;
|
||||||
|
a = editorAPI.editor;
|
||||||
|
a = editorAPI.languages;
|
||||||
|
})();
|
||||||
@@ -20,7 +20,6 @@ function yarnInstall(location, opts) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// {{SQL CARBON EDIT}}
|
|
||||||
yarnInstall('extensions'); // node modules shared by all extensions
|
yarnInstall('extensions'); // node modules shared by all extensions
|
||||||
|
|
||||||
const allExtensionFolders = fs.readdirSync('extensions');
|
const allExtensionFolders = fs.readdirSync('extensions');
|
||||||
|
|||||||
@@ -83,7 +83,7 @@ exports.update = function (repoId, repoPath, dest, modifyGrammar, version = 'mas
|
|||||||
grammar = plist.parse(content);
|
grammar = plist.parse(content);
|
||||||
} else if (ext === '.cson') {
|
} else if (ext === '.cson') {
|
||||||
grammar = cson.parse(content);
|
grammar = cson.parse(content);
|
||||||
} else if (ext === '.json') {
|
} else if (ext === '.json' || ext === '.JSON-tmLanguage') {
|
||||||
grammar = JSON.parse(content);
|
grammar = JSON.parse(content);
|
||||||
} else {
|
} else {
|
||||||
return Promise.reject(new Error('Unknown file extension: ' + ext));
|
return Promise.reject(new Error('Unknown file extension: ' + ext));
|
||||||
|
|||||||
@@ -43,7 +43,12 @@ function update(idOrPath) {
|
|||||||
let apiToken = process.env.TRANSIFEX_API_TOKEN;
|
let apiToken = process.env.TRANSIFEX_API_TOKEN;
|
||||||
let languageId = localization.transifexId || localization.languageId;
|
let languageId = localization.transifexId || localization.languageId;
|
||||||
let translationDataFolder = path.join(locExtFolder, 'translations');
|
let translationDataFolder = path.join(locExtFolder, 'translations');
|
||||||
|
if (languageId === "zh-cn") {
|
||||||
|
languageId = "zh-hans";
|
||||||
|
}
|
||||||
|
if (languageId === "zh-tw") {
|
||||||
|
languageId = "zh-hant";
|
||||||
|
}
|
||||||
if (fs.existsSync(translationDataFolder) && fs.existsSync(path.join(translationDataFolder, 'main.i18n.json'))) {
|
if (fs.existsSync(translationDataFolder) && fs.existsSync(path.join(translationDataFolder, 'main.i18n.json'))) {
|
||||||
console.log('Clearing \'' + translationDataFolder + '\'...');
|
console.log('Clearing \'' + translationDataFolder + '\'...');
|
||||||
rimraf.sync(translationDataFolder);
|
rimraf.sync(translationDataFolder);
|
||||||
|
|||||||
@@ -13,11 +13,11 @@
|
|||||||
"azure-storage": "^2.1.0",
|
"azure-storage": "^2.1.0",
|
||||||
"decompress": "^4.2.0",
|
"decompress": "^4.2.0",
|
||||||
"documentdb": "1.13.0",
|
"documentdb": "1.13.0",
|
||||||
"service-downloader": "github:anthonydresser/service-downloader#0.1.2",
|
"service-downloader": "github:anthonydresser/service-downloader#0.1.5",
|
||||||
"fs-extra-promise": "^1.0.1",
|
"fs-extra-promise": "^1.0.1",
|
||||||
"mime": "^1.3.4",
|
"mime": "^1.3.4",
|
||||||
"minimist": "^1.2.0",
|
"minimist": "^1.2.0",
|
||||||
"typescript": "2.8.1",
|
"typescript": "2.9.2",
|
||||||
"vscode": "^1.0.1",
|
"vscode": "^1.0.1",
|
||||||
"xml2js": "^0.4.17",
|
"xml2js": "^0.4.17",
|
||||||
"github-releases": "^0.4.1",
|
"github-releases": "^0.4.1",
|
||||||
|
|||||||
@@ -1,43 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
set -e
|
|
||||||
|
|
||||||
# set agent specific npm cache
|
|
||||||
if [ -n "$AGENT_WORKFOLDER" ]
|
|
||||||
then
|
|
||||||
export npm_config_cache="$AGENT_WORKFOLDER/npm-cache"
|
|
||||||
echo "Using npm cache: $npm_config_cache"
|
|
||||||
|
|
||||||
export YARN_CACHE_FOLDER="$AGENT_WORKFOLDER/yarn-cache"
|
|
||||||
echo "Using yarn cache: $YARN_CACHE_FOLDER"
|
|
||||||
fi
|
|
||||||
|
|
||||||
SUMMARY="Task;Duration"$'\n'
|
|
||||||
step() {
|
|
||||||
START=$SECONDS
|
|
||||||
TASK=$1; shift
|
|
||||||
echo ""
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
echo "Start: $TASK"
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
"$@"
|
|
||||||
|
|
||||||
# Calculate total duration
|
|
||||||
TOTAL=$(echo "$SECONDS - $START" | bc)
|
|
||||||
M=$(echo "$TOTAL / 60" | bc)
|
|
||||||
S=$(echo "$TOTAL % 60" | bc)
|
|
||||||
DURATION="$(printf "%02d" $M):$(printf "%02d" $S)"
|
|
||||||
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
echo "End: $TASK, Total: $DURATION"
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
SUMMARY="$SUMMARY$TASK;$DURATION"$'\n'
|
|
||||||
}
|
|
||||||
|
|
||||||
done_steps() {
|
|
||||||
echo ""
|
|
||||||
echo "Build Summary"
|
|
||||||
echo "============="
|
|
||||||
echo "${SUMMARY}" | column -t -s';'
|
|
||||||
}
|
|
||||||
|
|
||||||
trap done_steps EXIT
|
|
||||||
@@ -1,18 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
set -e
|
|
||||||
|
|
||||||
# setup nvm
|
|
||||||
if [[ "$OSTYPE" == "darwin"* ]]; then
|
|
||||||
export NVM_DIR=~/.nvm
|
|
||||||
source $(brew --prefix nvm)/nvm.sh --no-use
|
|
||||||
else
|
|
||||||
source $NVM_DIR/nvm.sh --no-use
|
|
||||||
fi
|
|
||||||
|
|
||||||
# install node
|
|
||||||
NODE_VERSION=8.9.1
|
|
||||||
nvm install $NODE_VERSION
|
|
||||||
nvm use $NODE_VERSION
|
|
||||||
|
|
||||||
# install yarn
|
|
||||||
npm i -g yarn
|
|
||||||
@@ -2,99 +2,14 @@ phases:
|
|||||||
- phase: Windows
|
- phase: Windows
|
||||||
queue: Hosted VS2017
|
queue: Hosted VS2017
|
||||||
steps:
|
steps:
|
||||||
- task: NodeTool@0
|
- template: win32/continuous-build-win32.yml
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
- powershell: |
|
|
||||||
$ErrorActionPreference = "Stop"
|
|
||||||
yarn
|
|
||||||
.\node_modules\.bin\gulp electron
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
.\node_modules\.bin\tsc -p .\src\tsconfig.monaco.json --noEmit
|
|
||||||
npm run compile
|
|
||||||
node build/lib/builtInExtensions.js
|
|
||||||
name: build
|
|
||||||
- powershell: |
|
|
||||||
$ErrorActionPreference = "Stop"
|
|
||||||
.\scripts\test.bat --tfs
|
|
||||||
.\scripts\test-integration.bat
|
|
||||||
yarn smoketest --screenshots "$(Build.ArtifactStagingDirectory)\artifacts" --log "$(Build.ArtifactStagingDirectory)\artifacts\smoketest.log"
|
|
||||||
name: test
|
|
||||||
- task: PublishBuildArtifacts@1
|
|
||||||
inputs:
|
|
||||||
PathtoPublish: '$(Build.ArtifactStagingDirectory)/artifacts'
|
|
||||||
ArtifactName: build-artifacts-win32
|
|
||||||
publishLocation: Container
|
|
||||||
condition: succeededOrFailed()
|
|
||||||
|
|
||||||
- phase: Linux
|
- phase: Linux
|
||||||
queue: Hosted Linux Preview
|
queue: Hosted Linux Preview
|
||||||
steps:
|
steps:
|
||||||
- script: |
|
- template: linux/continuous-build-linux.yml
|
||||||
set -e
|
|
||||||
apt-get update
|
|
||||||
apt-get install -y libxkbfile-dev pkg-config libsecret-1-dev libxss1 libgconf-2-4 dbus xvfb libgtk-3-0
|
|
||||||
cp build/tfs/linux/x64/xvfb.init /etc/init.d/xvfb
|
|
||||||
chmod +x /etc/init.d/xvfb
|
|
||||||
update-rc.d xvfb defaults
|
|
||||||
ln -sf /bin/dbus-daemon /usr/bin/dbus-daemon
|
|
||||||
service xvfb start
|
|
||||||
service dbus start
|
|
||||||
- task: NodeTool@0
|
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
yarn
|
|
||||||
npm run gulp -- electron-x64
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
./node_modules/.bin/tsc -p ./src/tsconfig.monaco.json --noEmit
|
|
||||||
npm run compile
|
|
||||||
node build/lib/builtInExtensions.js
|
|
||||||
name: build
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
DISPLAY=:10 ./scripts/test.sh --tfs
|
|
||||||
# DISPLAY=:10 ./scripts/test-integration.sh
|
|
||||||
name: test
|
|
||||||
|
|
||||||
- phase: macOS
|
- phase: macOS
|
||||||
queue: Hosted macOS Preview
|
queue: Hosted macOS Preview
|
||||||
steps:
|
steps:
|
||||||
- task: NodeTool@0
|
- template: darwin/continuous-build-darwin.yml
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
yarn
|
|
||||||
npm run gulp -- electron-x64
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
./node_modules/.bin/tsc -p ./src/tsconfig.monaco.json --noEmit
|
|
||||||
npm run compile
|
|
||||||
node build/lib/builtInExtensions.js
|
|
||||||
name: build
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
./scripts/test.sh --tfs
|
|
||||||
./scripts/test-integration.sh
|
|
||||||
yarn smoketest --screenshots "$(Build.ArtifactStagingDirectory)/artifacts" --log "$(Build.ArtifactStagingDirectory)/artifacts/smoketest.log"
|
|
||||||
name: test
|
|
||||||
- task: PublishBuildArtifacts@1
|
|
||||||
inputs:
|
|
||||||
PathtoPublish: '$(Build.ArtifactStagingDirectory)/artifacts'
|
|
||||||
ArtifactName: build-artifacts-darwin
|
|
||||||
publishLocation: Container
|
|
||||||
condition: succeededOrFailed()
|
|
||||||
@@ -1,58 +0,0 @@
|
|||||||
#!/bin/sh
|
|
||||||
|
|
||||||
. ./build/tfs/common/node.sh
|
|
||||||
. ./scripts/env.sh
|
|
||||||
. ./build/tfs/common/common.sh
|
|
||||||
|
|
||||||
export VSCODE_MIXIN_PASSWORD="$1"
|
|
||||||
export AZURE_STORAGE_ACCESS_KEY="$2"
|
|
||||||
export AZURE_STORAGE_ACCESS_KEY_2="$3"
|
|
||||||
export MOONCAKE_STORAGE_ACCESS_KEY="$4"
|
|
||||||
export AZURE_DOCUMENTDB_MASTERKEY="$5"
|
|
||||||
VSO_PAT="$6"
|
|
||||||
|
|
||||||
echo "machine monacotools.visualstudio.com password $VSO_PAT" > ~/.netrc
|
|
||||||
|
|
||||||
step "Install dependencies" \
|
|
||||||
yarn
|
|
||||||
|
|
||||||
step "Hygiene" \
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
|
|
||||||
step "Monaco Editor Check" \
|
|
||||||
./node_modules/.bin/tsc -p ./src/tsconfig.monaco.json --noEmit
|
|
||||||
|
|
||||||
step "Mix in repository from vscode-distro" \
|
|
||||||
npm run gulp -- mixin
|
|
||||||
|
|
||||||
step "Install distro dependencies" \
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
|
|
||||||
step "Build minified & upload source maps" \
|
|
||||||
npm run gulp -- vscode-darwin-min upload-vscode-sourcemaps
|
|
||||||
|
|
||||||
# step "Create loader snapshot"
|
|
||||||
# node build/lib/snapshotLoader.js
|
|
||||||
|
|
||||||
step "Run unit tests" \
|
|
||||||
./scripts/test.sh --build --reporter dot
|
|
||||||
|
|
||||||
step "Run integration tests" \
|
|
||||||
./scripts/test-integration.sh
|
|
||||||
|
|
||||||
# function smoketest {
|
|
||||||
# ARTIFACTS="$AGENT_BUILDDIRECTORY/smoketest-artifacts"
|
|
||||||
# rm -rf $ARTIFACTS
|
|
||||||
|
|
||||||
# [[ "$VSCODE_QUALITY" == "insider" ]] && VSCODE_APPNAME="Visual Studio Code - Insiders" || VSCODE_APPNAME="Visual Studio Code"
|
|
||||||
# npm run smoketest -- --build "$AGENT_BUILDDIRECTORY/VSCode-darwin/$VSCODE_APPNAME.app" --log $ARTIFACTS
|
|
||||||
# }
|
|
||||||
|
|
||||||
# step "Run smoke test" \
|
|
||||||
# smoketest
|
|
||||||
|
|
||||||
step "Publish release" \
|
|
||||||
./build/tfs/darwin/release.sh
|
|
||||||
|
|
||||||
step "Generate and upload configuration.json" \
|
|
||||||
npm run gulp -- upload-vscode-configuration
|
|
||||||
48
build/tfs/darwin/continuous-build-darwin.yml
Normal file
48
build/tfs/darwin/continuous-build-darwin.yml
Normal file
@@ -0,0 +1,48 @@
|
|||||||
|
steps:
|
||||||
|
- task: NodeTool@0
|
||||||
|
inputs:
|
||||||
|
versionSpec: "8.9.1"
|
||||||
|
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
||||||
|
inputs:
|
||||||
|
versionSpec: "1.3.2"
|
||||||
|
- script: |
|
||||||
|
yarn
|
||||||
|
displayName: Install Dependencies
|
||||||
|
- script: |
|
||||||
|
yarn gulp electron-x64
|
||||||
|
displayName: Download Electron
|
||||||
|
- script: |
|
||||||
|
yarn gulp hygiene
|
||||||
|
displayName: Run Hygiene Checks
|
||||||
|
- script: |
|
||||||
|
yarn check-monaco-editor-compilation
|
||||||
|
displayName: Run Monaco Editor Checks
|
||||||
|
- script: |
|
||||||
|
yarn compile
|
||||||
|
displayName: Compile Sources
|
||||||
|
- script: |
|
||||||
|
yarn download-builtin-extensions
|
||||||
|
displayName: Download Built-in Extensions
|
||||||
|
- script: |
|
||||||
|
./scripts/test.sh --tfs "Unit Tests"
|
||||||
|
displayName: Run Unit Tests
|
||||||
|
- script: |
|
||||||
|
./scripts/test-integration.sh --tfs "Integration Tests"
|
||||||
|
displayName: Run Integration Tests
|
||||||
|
- script: |
|
||||||
|
yarn smoketest --screenshots "$(Build.ArtifactStagingDirectory)/artifacts" --log "$(Build.ArtifactStagingDirectory)/artifacts/smoketest.log"
|
||||||
|
displayName: Run Smoke Tests
|
||||||
|
continueOnError: true
|
||||||
|
- task: PublishBuildArtifacts@1
|
||||||
|
displayName: Publish Smoketest Artifacts
|
||||||
|
inputs:
|
||||||
|
PathtoPublish: '$(Build.ArtifactStagingDirectory)/artifacts'
|
||||||
|
ArtifactName: build-artifacts-darwin
|
||||||
|
publishLocation: Container
|
||||||
|
condition: eq(variables['System.PullRequest.IsFork'], 'False')
|
||||||
|
- task: PublishTestResults@2
|
||||||
|
displayName: Publish Tests Results
|
||||||
|
inputs:
|
||||||
|
testResultsFiles: '*-results.xml'
|
||||||
|
searchFolder: '$(Build.ArtifactStagingDirectory)/test-results'
|
||||||
|
condition: succeededOrFailed()
|
||||||
106
build/tfs/darwin/enqueue.js
Normal file
106
build/tfs/darwin/enqueue.js
Normal file
@@ -0,0 +1,106 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
'use strict';
|
||||||
|
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
||||||
|
return new (P || (P = Promise))(function (resolve, reject) {
|
||||||
|
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
||||||
|
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
||||||
|
function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
|
||||||
|
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
||||||
|
});
|
||||||
|
};
|
||||||
|
var __generator = (this && this.__generator) || function (thisArg, body) {
|
||||||
|
var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;
|
||||||
|
return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
|
||||||
|
function verb(n) { return function (v) { return step([n, v]); }; }
|
||||||
|
function step(op) {
|
||||||
|
if (f) throw new TypeError("Generator is already executing.");
|
||||||
|
while (_) try {
|
||||||
|
if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
|
||||||
|
if (y = 0, t) op = [op[0] & 2, t.value];
|
||||||
|
switch (op[0]) {
|
||||||
|
case 0: case 1: t = op; break;
|
||||||
|
case 4: _.label++; return { value: op[1], done: false };
|
||||||
|
case 5: _.label++; y = op[1]; op = [0]; continue;
|
||||||
|
case 7: op = _.ops.pop(); _.trys.pop(); continue;
|
||||||
|
default:
|
||||||
|
if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
|
||||||
|
if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
|
||||||
|
if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
|
||||||
|
if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
|
||||||
|
if (t[2]) _.ops.pop();
|
||||||
|
_.trys.pop(); continue;
|
||||||
|
}
|
||||||
|
op = body.call(thisArg, _);
|
||||||
|
} catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
|
||||||
|
if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
|
||||||
|
}
|
||||||
|
};
|
||||||
|
Object.defineProperty(exports, "__esModule", { value: true });
|
||||||
|
var child_process_1 = require("child_process");
|
||||||
|
var documentdb_1 = require("documentdb");
|
||||||
|
var azure = require("azure-storage");
|
||||||
|
function queueSigningRequest(quality, commit) {
|
||||||
|
var retryOperations = new azure.ExponentialRetryPolicyFilter();
|
||||||
|
var queueSvc = azure
|
||||||
|
.createQueueService(process.env['AZURE_STORAGE_ACCOUNT_2'], process.env['AZURE_STORAGE_ACCESS_KEY_2'])
|
||||||
|
.withFilter(retryOperations);
|
||||||
|
queueSvc.messageEncoder = new azure.QueueMessageEncoder.TextBase64QueueMessageEncoder();
|
||||||
|
var message = quality + "/" + commit;
|
||||||
|
return new Promise(function (c, e) { return queueSvc.createMessage('sign-darwin', message, function (err) { return err ? e(err) : c(); }); });
|
||||||
|
}
|
||||||
|
function isBuildSigned(quality, commit) {
|
||||||
|
var client = new documentdb_1.DocumentClient(process.env['AZURE_DOCUMENTDB_ENDPOINT'], { masterKey: process.env['AZURE_DOCUMENTDB_MASTERKEY'] });
|
||||||
|
var collection = 'dbs/builds/colls/' + quality;
|
||||||
|
var updateQuery = {
|
||||||
|
query: 'SELECT TOP 1 * FROM c WHERE c.id = @id',
|
||||||
|
parameters: [{ name: '@id', value: commit }]
|
||||||
|
};
|
||||||
|
return new Promise(function (c, e) {
|
||||||
|
client.queryDocuments(collection, updateQuery).toArray(function (err, results) {
|
||||||
|
if (err) {
|
||||||
|
return e(err);
|
||||||
|
}
|
||||||
|
if (results.length !== 1) {
|
||||||
|
return c(false);
|
||||||
|
}
|
||||||
|
var release = results[0];
|
||||||
|
var assets = release.assets;
|
||||||
|
var isSigned = assets.some(function (a) { return a.platform === 'darwin' && a.type === 'archive'; });
|
||||||
|
c(isSigned);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
// async function waitForSignedBuild(quality: string, commit: string): Promise<void> {
|
||||||
|
// let retries = 0;
|
||||||
|
// while (retries < 180) {
|
||||||
|
// if (await isBuildSigned(quality, commit)) {
|
||||||
|
// return;
|
||||||
|
// }
|
||||||
|
// await new Promise<void>(c => setTimeout(c, 10000));
|
||||||
|
// retries++;
|
||||||
|
// }
|
||||||
|
// throw new Error('Timed out waiting for signed build');
|
||||||
|
// }
|
||||||
|
function main(quality) {
|
||||||
|
return __awaiter(this, void 0, void 0, function () {
|
||||||
|
var commit;
|
||||||
|
return __generator(this, function (_a) {
|
||||||
|
switch (_a.label) {
|
||||||
|
case 0:
|
||||||
|
commit = child_process_1.execSync('git rev-parse HEAD', { encoding: 'utf8' }).trim();
|
||||||
|
console.log("Queueing signing request for '" + quality + "/" + commit + "'...");
|
||||||
|
return [4 /*yield*/, queueSigningRequest(quality, commit)];
|
||||||
|
case 1:
|
||||||
|
_a.sent();
|
||||||
|
return [2 /*return*/];
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
main(process.argv[2]).catch(function (err) {
|
||||||
|
console.error(err);
|
||||||
|
process.exit(1);
|
||||||
|
});
|
||||||
@@ -1,5 +1,4 @@
|
|||||||
steps:
|
steps:
|
||||||
|
|
||||||
- task: NodeTool@0
|
- task: NodeTool@0
|
||||||
inputs:
|
inputs:
|
||||||
versionSpec: "8.9.1"
|
versionSpec: "8.9.1"
|
||||||
@@ -9,22 +8,31 @@ steps:
|
|||||||
versionSpec: "1.3.2"
|
versionSpec: "1.3.2"
|
||||||
|
|
||||||
- script: |
|
- script: |
|
||||||
|
set -e
|
||||||
echo "machine monacotools.visualstudio.com password $(VSO_PAT)" > ~/.netrc
|
echo "machine monacotools.visualstudio.com password $(VSO_PAT)" > ~/.netrc
|
||||||
yarn
|
yarn
|
||||||
npm run gulp -- hygiene
|
npm run gulp -- hygiene
|
||||||
npm run monaco-compile-check
|
npm run monaco-compile-check
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- mixin electron
|
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- mixin
|
||||||
node build/tfs/common/installDistro.js
|
node build/tfs/common/installDistro.js
|
||||||
|
node build/lib/builtInExtensions.js
|
||||||
|
|
||||||
- script: |
|
- script: |
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- vscode-darwin-min
|
set -e
|
||||||
|
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" \
|
||||||
|
AZURE_STORAGE_ACCESS_KEY="$(AZURE_STORAGE_ACCESS_KEY)" \
|
||||||
|
npm run gulp -- vscode-darwin-min upload-vscode-sourcemaps
|
||||||
name: build
|
name: build
|
||||||
|
|
||||||
- script: |
|
- script: |
|
||||||
./scripts/test.sh --build --tfs
|
set -e
|
||||||
|
./scripts/test.sh --build --tfs "Unit Tests"
|
||||||
|
APP_NAME="`ls $(agent.builddirectory)/VSCode-darwin | head -n 1`"
|
||||||
|
# yarn smoketest -- --build "$(agent.builddirectory)/VSCode-darwin/$APP_NAME"
|
||||||
name: test
|
name: test
|
||||||
|
|
||||||
- script: |
|
- script: |
|
||||||
|
set -e
|
||||||
# archive the unsigned build
|
# archive the unsigned build
|
||||||
pushd ../VSCode-darwin && zip -r -X -y ../VSCode-darwin-unsigned.zip * && popd
|
pushd ../VSCode-darwin && zip -r -X -y ../VSCode-darwin-unsigned.zip * && popd
|
||||||
|
|
||||||
@@ -43,9 +51,13 @@ steps:
|
|||||||
false \
|
false \
|
||||||
../VSCode-darwin-unsigned.zip
|
../VSCode-darwin-unsigned.zip
|
||||||
|
|
||||||
|
# publish hockeyapp symbols
|
||||||
|
node build/tfs/common/symbols.js "$(VSCODE_MIXIN_PASSWORD)" "$(VSCODE_HOCKEYAPP_TOKEN)" "$(VSCODE_ARCH)" "$(VSCODE_HOCKEYAPP_ID_MACOS)"
|
||||||
|
|
||||||
# enqueue the unsigned build
|
# enqueue the unsigned build
|
||||||
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
||||||
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
||||||
node build/tfs/common/enqueue.js "$(VSCODE_QUALITY)"
|
node build/tfs/darwin/enqueue.js "$(VSCODE_QUALITY)"
|
||||||
|
|
||||||
|
AZURE_STORAGE_ACCESS_KEY="$(AZURE_STORAGE_ACCESS_KEY)" \
|
||||||
npm run gulp -- upload-vscode-configuration
|
npm run gulp -- upload-vscode-configuration
|
||||||
@@ -1,22 +0,0 @@
|
|||||||
#!/bin/sh
|
|
||||||
|
|
||||||
. ./scripts/env.sh
|
|
||||||
. ./build/tfs/common/common.sh
|
|
||||||
|
|
||||||
REPO=`pwd`
|
|
||||||
ZIP=$REPO/../VSCode-darwin-selfsigned.zip
|
|
||||||
UNSIGNEDZIP=$REPO/../VSCode-darwin-unsigned.zip
|
|
||||||
BUILD=$REPO/../VSCode-darwin
|
|
||||||
PACKAGEJSON=`ls $BUILD/*.app/Contents/Resources/app/package.json`
|
|
||||||
VERSION=`node -p "require(\"$PACKAGEJSON\").version"`
|
|
||||||
|
|
||||||
rm -rf $UNSIGNEDZIP
|
|
||||||
(cd $BUILD && \
|
|
||||||
step "Create unsigned archive" \
|
|
||||||
zip -r -X -y $UNSIGNEDZIP *)
|
|
||||||
|
|
||||||
step "Upload unsigned archive" \
|
|
||||||
node build/tfs/common/publish.js $VSCODE_QUALITY darwin archive-unsigned VSCode-darwin-$VSCODE_QUALITY-unsigned.zip $VERSION false $UNSIGNEDZIP
|
|
||||||
|
|
||||||
step "Sign build" \
|
|
||||||
node build/tfs/common/enqueue.js $VSCODE_QUALITY
|
|
||||||
@@ -1,3 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
set -e
|
|
||||||
./build/tfs/linux/build.sh ia32 "$@"
|
|
||||||
@@ -1,3 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
set -e
|
|
||||||
./build/tfs/linux/build.sh x64 "$@"
|
|
||||||
@@ -1,64 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
|
|
||||||
. ./build/tfs/common/node.sh
|
|
||||||
. ./scripts/env.sh
|
|
||||||
. ./build/tfs/common/common.sh
|
|
||||||
|
|
||||||
export ARCH="$1"
|
|
||||||
export npm_config_arch="$ARCH"
|
|
||||||
export VSCODE_MIXIN_PASSWORD="$2"
|
|
||||||
export AZURE_STORAGE_ACCESS_KEY="$3"
|
|
||||||
export AZURE_STORAGE_ACCESS_KEY_2="$4"
|
|
||||||
export MOONCAKE_STORAGE_ACCESS_KEY="$5"
|
|
||||||
export AZURE_DOCUMENTDB_MASTERKEY="$6"
|
|
||||||
export LINUX_REPO_PASSWORD="$7"
|
|
||||||
VSO_PAT="$8"
|
|
||||||
|
|
||||||
echo "machine monacotools.visualstudio.com password $VSO_PAT" > ~/.netrc
|
|
||||||
|
|
||||||
step "Install dependencies" \
|
|
||||||
yarn
|
|
||||||
|
|
||||||
step "Hygiene" \
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
|
|
||||||
step "Monaco Editor Check" \
|
|
||||||
./node_modules/.bin/tsc -p ./src/tsconfig.monaco.json --noEmit
|
|
||||||
|
|
||||||
step "Mix in repository from vscode-distro" \
|
|
||||||
npm run gulp -- mixin
|
|
||||||
|
|
||||||
step "Get Electron" \
|
|
||||||
npm run gulp -- "electron-$ARCH"
|
|
||||||
|
|
||||||
step "Install distro dependencies" \
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
|
|
||||||
step "Build minified" \
|
|
||||||
npm run gulp -- "vscode-linux-$ARCH-min"
|
|
||||||
|
|
||||||
# step "Create loader snapshot"
|
|
||||||
# node build/lib/snapshotLoader.js --arch=$ARCH
|
|
||||||
|
|
||||||
step "Run unit tests" \
|
|
||||||
./scripts/test.sh --build --reporter dot
|
|
||||||
|
|
||||||
# function smoketest {
|
|
||||||
# id -u testuser &>/dev/null || (useradd -m testuser; chpasswd <<< testuser:testpassword)
|
|
||||||
# sudo -i -u testuser -- sh -c 'git config --global user.name "VS Code Agent" && git config --global user.email "monacotools@microsoft.com"'
|
|
||||||
|
|
||||||
# ARTIFACTS="$AGENT_BUILDDIRECTORY/smoketest-artifacts"
|
|
||||||
# rm -rf $ARTIFACTS
|
|
||||||
# mkdir -p $ARTIFACTS
|
|
||||||
# chown -R testuser $ARTIFACTS
|
|
||||||
|
|
||||||
# ps -o pid= -u testuser | xargs sudo kill -9
|
|
||||||
# DISPLAY=:10 sudo -i -u testuser -- sh -c "cd $BUILD_SOURCESDIRECTORY/test/smoke && ./node_modules/.bin/mocha --build $AGENT_BUILDDIRECTORY/VSCode-linux-$ARCH --log $ARTIFACTS"
|
|
||||||
# # DISPLAY=:10 sudo -i -u testuser -- sh -c "cd /vso/work/1/s/test/smoke && ./node_modules/.bin/mocha --build /vso/work/1/VSCode-linux-ia32"
|
|
||||||
# }
|
|
||||||
|
|
||||||
# step "Run smoke test" \
|
|
||||||
# smoketest
|
|
||||||
|
|
||||||
step "Publish release" \
|
|
||||||
./build/tfs/linux/release.sh
|
|
||||||
@@ -1,103 +0,0 @@
|
|||||||
steps:
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
# dependencies
|
|
||||||
dpkg --add-architecture i386
|
|
||||||
apt-get update
|
|
||||||
|
|
||||||
DEPS=" \
|
|
||||||
gcc-multilib g++-multilib \
|
|
||||||
pkg-config \
|
|
||||||
dbus \
|
|
||||||
xvfb \
|
|
||||||
fakeroot \
|
|
||||||
bc \
|
|
||||||
bsdmainutils \
|
|
||||||
rpm \
|
|
||||||
"
|
|
||||||
|
|
||||||
if [[ "$(VSCODE_ARCH)" == "x64" ]]; then
|
|
||||||
DEPS="$DEPS \
|
|
||||||
dpkg-dev \
|
|
||||||
libgconf-2-4 \
|
|
||||||
libnss3 \
|
|
||||||
libasound2 \
|
|
||||||
libxtst6 \
|
|
||||||
libx11-dev \
|
|
||||||
libxkbfile-dev \
|
|
||||||
libxss1 \
|
|
||||||
libx11-xcb-dev \
|
|
||||||
libsecret-1-dev \
|
|
||||||
"
|
|
||||||
else
|
|
||||||
DEPS="$DEPS \
|
|
||||||
dpkg-dev:i386 \
|
|
||||||
libgconf-2-4:i386 \
|
|
||||||
libnss3:i386 \
|
|
||||||
libasound2:i386 \
|
|
||||||
libxtst6:i386 \
|
|
||||||
libnotify4:i386 \
|
|
||||||
libx11-dev:i386 \
|
|
||||||
libxkbfile-dev:i386 \
|
|
||||||
libxss1:i386 \
|
|
||||||
libx11-xcb-dev:i386 \
|
|
||||||
libgl1-mesa-glx:i386 libgl1-mesa-dri:i386 \
|
|
||||||
libgirepository-1.0-1:i386 \
|
|
||||||
gir1.2-glib-2.0:i386 \
|
|
||||||
gir1.2-secret-1:i386 \
|
|
||||||
libsecret-1-dev:i386 \
|
|
||||||
libgtk2.0-0:i386 \
|
|
||||||
"
|
|
||||||
fi
|
|
||||||
|
|
||||||
apt-get install -y $DEPS
|
|
||||||
|
|
||||||
# setup xvfb
|
|
||||||
cp build/tfs/linux/$(VSCODE_ARCH)/xvfb.init /etc/init.d/xvfb
|
|
||||||
chmod +x /etc/init.d/xvfb
|
|
||||||
update-rc.d xvfb defaults
|
|
||||||
service xvfb start
|
|
||||||
|
|
||||||
# setup dbus
|
|
||||||
ln -sf /bin/dbus-daemon /usr/bin/dbus-daemon
|
|
||||||
service dbus start
|
|
||||||
|
|
||||||
- task: NodeTool@0
|
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
export npm_config_arch="$(VSCODE_ARCH)"
|
|
||||||
if [[ "$(VSCODE_ARCH)" == "ia32" ]]; then
|
|
||||||
export PKG_CONFIG_PATH="/usr/lib/i386-linux-gnu/pkgconfig"
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "machine monacotools.visualstudio.com password $(VSO_PAT)" > ~/.netrc
|
|
||||||
yarn
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
npm run monaco-compile-check
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- mixin
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- vscode-linux-$(VSCODE_ARCH)-min
|
|
||||||
name: build
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
npm run gulp -- "electron-$(VSCODE_ARCH)"
|
|
||||||
DISPLAY=:10 ./scripts/test.sh --build --tfs
|
|
||||||
name: test
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-deb"
|
|
||||||
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-rpm"
|
|
||||||
#npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-snap"
|
|
||||||
|
|
||||||
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
|
||||||
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
|
||||||
MOONCAKE_STORAGE_ACCESS_KEY="$(MOONCAKE_STORAGE_ACCESS_KEY)" \
|
|
||||||
./build/tfs/linux/release2.sh "$(VSCODE_ARCH)" "$(LINUX_REPO_PASSWORD)"
|
|
||||||
44
build/tfs/linux/continuous-build-linux.yml
Normal file
44
build/tfs/linux/continuous-build-linux.yml
Normal file
@@ -0,0 +1,44 @@
|
|||||||
|
steps:
|
||||||
|
- script: |
|
||||||
|
set -e
|
||||||
|
apt-get update
|
||||||
|
apt-get install -y libxkbfile-dev pkg-config libsecret-1-dev libxss1 libgconf-2-4 dbus xvfb libgtk-3-0
|
||||||
|
cp build/tfs/linux/x64/xvfb.init /etc/init.d/xvfb
|
||||||
|
chmod +x /etc/init.d/xvfb
|
||||||
|
update-rc.d xvfb defaults
|
||||||
|
ln -sf /bin/dbus-daemon /usr/bin/dbus-daemon
|
||||||
|
service xvfb start
|
||||||
|
service dbus start
|
||||||
|
- task: NodeTool@0
|
||||||
|
inputs:
|
||||||
|
versionSpec: "8.9.1"
|
||||||
|
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
||||||
|
inputs:
|
||||||
|
versionSpec: "1.3.2"
|
||||||
|
- script: |
|
||||||
|
yarn
|
||||||
|
displayName: Install Dependencies
|
||||||
|
- script: |
|
||||||
|
yarn gulp electron-x64
|
||||||
|
displayName: Download Electron
|
||||||
|
- script: |
|
||||||
|
yarn gulp hygiene
|
||||||
|
displayName: Run Hygiene Checks
|
||||||
|
- script: |
|
||||||
|
yarn check-monaco-editor-compilation
|
||||||
|
displayName: Run Monaco Editor Checks
|
||||||
|
- script: |
|
||||||
|
yarn compile
|
||||||
|
displayName: Compile Sources
|
||||||
|
- script: |
|
||||||
|
yarn download-builtin-extensions
|
||||||
|
displayName: Download Built-in Extensions
|
||||||
|
- script: |
|
||||||
|
DISPLAY=:10 ./scripts/test.sh --tfs "Unit Tests"
|
||||||
|
displayName: Run Unit Tests
|
||||||
|
- task: PublishTestResults@2
|
||||||
|
displayName: Publish Tests Results
|
||||||
|
inputs:
|
||||||
|
testResultsFiles: '*-results.xml'
|
||||||
|
searchFolder: '$(Build.ArtifactStagingDirectory)/test-results'
|
||||||
|
condition: succeededOrFailed()
|
||||||
@@ -39,4 +39,11 @@ function getConfig(quality: string): Promise<Config> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
getConfig(process.argv[2])
|
getConfig(process.argv[2])
|
||||||
.then(c => console.log(c.frozen), e => console.error(e));
|
.then(config => {
|
||||||
|
console.log(config.frozen);
|
||||||
|
process.exit(0);
|
||||||
|
})
|
||||||
|
.catch(err => {
|
||||||
|
console.error(err);
|
||||||
|
process.exit(1);
|
||||||
|
});
|
||||||
118
build/tfs/linux/product-build-linux.yml
Normal file
118
build/tfs/linux/product-build-linux.yml
Normal file
@@ -0,0 +1,118 @@
|
|||||||
|
steps:
|
||||||
|
- task: NodeTool@0
|
||||||
|
inputs:
|
||||||
|
versionSpec: "8.9.1"
|
||||||
|
|
||||||
|
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
||||||
|
inputs:
|
||||||
|
versionSpec: "1.3.2"
|
||||||
|
|
||||||
|
- script: |
|
||||||
|
set -e
|
||||||
|
export npm_config_arch="$(VSCODE_ARCH)"
|
||||||
|
if [[ "$(VSCODE_ARCH)" == "ia32" ]]; then
|
||||||
|
export PKG_CONFIG_PATH="/usr/lib/i386-linux-gnu/pkgconfig"
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "machine monacotools.visualstudio.com password $(VSO_PAT)" > ~/.netrc
|
||||||
|
yarn
|
||||||
|
npm run gulp -- hygiene
|
||||||
|
npm run monaco-compile-check
|
||||||
|
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- mixin
|
||||||
|
node build/tfs/common/installDistro.js
|
||||||
|
node build/lib/builtInExtensions.js
|
||||||
|
|
||||||
|
- script: |
|
||||||
|
set -e
|
||||||
|
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- vscode-linux-$(VSCODE_ARCH)-min
|
||||||
|
name: build
|
||||||
|
|
||||||
|
- script: |
|
||||||
|
set -e
|
||||||
|
npm run gulp -- "electron-$(VSCODE_ARCH)"
|
||||||
|
DISPLAY=:10 ./scripts/test.sh --build --tfs "Unit Tests"
|
||||||
|
# yarn smoketest -- --build "$(agent.builddirectory)/VSCode-linux-$(VSCODE_ARCH)"
|
||||||
|
name: test
|
||||||
|
|
||||||
|
- script: |
|
||||||
|
set -e
|
||||||
|
REPO="$(pwd)"
|
||||||
|
ROOT="$REPO/.."
|
||||||
|
ARCH="$(VSCODE_ARCH)"
|
||||||
|
|
||||||
|
# Publish tarball
|
||||||
|
PLATFORM_LINUX="linux-$(VSCODE_ARCH)"
|
||||||
|
[[ "$ARCH" == "ia32" ]] && DEB_ARCH="i386" || DEB_ARCH="amd64"
|
||||||
|
[[ "$ARCH" == "ia32" ]] && RPM_ARCH="i386" || RPM_ARCH="x86_64"
|
||||||
|
BUILDNAME="VSCode-$PLATFORM_LINUX"
|
||||||
|
BUILD="$ROOT/$BUILDNAME"
|
||||||
|
BUILD_VERSION="$(date +%s)"
|
||||||
|
[ -z "$VSCODE_QUALITY" ] && TARBALL_FILENAME="code-$BUILD_VERSION.tar.gz" || TARBALL_FILENAME="code-$VSCODE_QUALITY-$BUILD_VERSION.tar.gz"
|
||||||
|
TARBALL_PATH="$ROOT/$TARBALL_FILENAME"
|
||||||
|
PACKAGEJSON="$BUILD/resources/app/package.json"
|
||||||
|
VERSION=$(node -p "require(\"$PACKAGEJSON\").version")
|
||||||
|
|
||||||
|
rm -rf $ROOT/code-*.tar.*
|
||||||
|
(cd $ROOT && tar -czf $TARBALL_PATH $BUILDNAME)
|
||||||
|
|
||||||
|
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
||||||
|
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
||||||
|
MOONCAKE_STORAGE_ACCESS_KEY="$(MOONCAKE_STORAGE_ACCESS_KEY)" \
|
||||||
|
node build/tfs/common/publish.js "$VSCODE_QUALITY" "$PLATFORM_LINUX" archive-unsigned "$TARBALL_FILENAME" "$VERSION" true "$TARBALL_PATH"
|
||||||
|
|
||||||
|
# Publish hockeyapp symbols
|
||||||
|
node build/tfs/common/symbols.js "$(VSCODE_MIXIN_PASSWORD)" "$(VSCODE_HOCKEYAPP_TOKEN)" "$(VSCODE_ARCH)" "$(VSCODE_HOCKEYAPP_ID_LINUX64)"
|
||||||
|
|
||||||
|
# Publish DEB
|
||||||
|
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-deb"
|
||||||
|
PLATFORM_DEB="linux-deb-$ARCH"
|
||||||
|
[[ "$ARCH" == "ia32" ]] && DEB_ARCH="i386" || DEB_ARCH="amd64"
|
||||||
|
DEB_FILENAME="$(ls $REPO/.build/linux/deb/$DEB_ARCH/deb/)"
|
||||||
|
DEB_PATH="$REPO/.build/linux/deb/$DEB_ARCH/deb/$DEB_FILENAME"
|
||||||
|
|
||||||
|
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
||||||
|
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
||||||
|
MOONCAKE_STORAGE_ACCESS_KEY="$(MOONCAKE_STORAGE_ACCESS_KEY)" \
|
||||||
|
node build/tfs/common/publish.js "$VSCODE_QUALITY" "$PLATFORM_DEB" package "$DEB_FILENAME" "$VERSION" true "$DEB_PATH"
|
||||||
|
|
||||||
|
# Publish RPM
|
||||||
|
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-rpm"
|
||||||
|
PLATFORM_RPM="linux-rpm-$ARCH"
|
||||||
|
[[ "$ARCH" == "ia32" ]] && RPM_ARCH="i386" || RPM_ARCH="x86_64"
|
||||||
|
RPM_FILENAME="$(ls $REPO/.build/linux/rpm/$RPM_ARCH/ | grep .rpm)"
|
||||||
|
RPM_PATH="$REPO/.build/linux/rpm/$RPM_ARCH/$RPM_FILENAME"
|
||||||
|
|
||||||
|
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
||||||
|
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
||||||
|
MOONCAKE_STORAGE_ACCESS_KEY="$(MOONCAKE_STORAGE_ACCESS_KEY)" \
|
||||||
|
node build/tfs/common/publish.js "$VSCODE_QUALITY" "$PLATFORM_RPM" package "$RPM_FILENAME" "$VERSION" true "$RPM_PATH"
|
||||||
|
|
||||||
|
# SNAP_FILENAME="$(ls $REPO/.build/linux/snap/$ARCH/ | grep .snap)"
|
||||||
|
# SNAP_PATH="$REPO/.build/linux/snap/$ARCH/$SNAP_FILENAME"
|
||||||
|
|
||||||
|
# Publish to MS repo
|
||||||
|
IS_FROZEN="$(AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" node build/tfs/linux/frozen-check.js $VSCODE_QUALITY)"
|
||||||
|
|
||||||
|
if [ -z "$VSCODE_QUALITY" ]; then
|
||||||
|
echo "VSCODE_QUALITY is not set, skipping repo package publish"
|
||||||
|
elif [ "$IS_FROZEN" = "true" ]; then
|
||||||
|
echo "$VSCODE_QUALITY is frozen, skipping repo package publish"
|
||||||
|
else
|
||||||
|
if [ "$BUILD_SOURCEBRANCH" = "master" ] || [ "$BUILD_SOURCEBRANCH" = "refs/heads/master" ] || [ "$VSCODE_PUBLISH_LINUX" = "true" ]; then
|
||||||
|
if [[ $BUILD_QUEUEDBY = *"Project Collection Service Accounts"* || $BUILD_QUEUEDBY = *"Microsoft.VisualStudio.Services.TFS"* ]]; then
|
||||||
|
# Write config files needed by API, use eval to force environment variable expansion
|
||||||
|
pushd build/tfs/linux
|
||||||
|
# Submit to apt repo
|
||||||
|
# if [ "$DEB_ARCH" = "amd64" ]; then
|
||||||
|
# echo "{ \"server\": \"azure-apt-cat.cloudapp.net\", \"protocol\": \"https\", \"port\": \"443\", \"repositoryId\": \"58a4adf642421134a1a48d1a\", \"username\": \"vscode\", \"password\": \"$(LINUX_REPO_PASSWORD)\" }" > apt-config.json
|
||||||
|
# ./repoapi_client.sh -config apt-config.json -addfile $DEB_PATH
|
||||||
|
# fi
|
||||||
|
# Submit to yum repo (disabled as it's manual until signing is automated)
|
||||||
|
# eval echo '{ \"server\": \"azure-apt-cat.cloudapp.net\", \"protocol\": \"https\", \"port\": \"443\", \"repositoryId\": \"58a4ae3542421134a1a48d1b\", \"username\": \"vscode\", \"password\": \"$(LINUX_REPO_PASSWORD)\" }' > yum-config.json
|
||||||
|
|
||||||
|
# ./repoapi_client.sh -config yum-config.json -addfile $RPM_PATH
|
||||||
|
popd
|
||||||
|
echo "To check repo publish status run ./repoapi_client.sh -config config.json -check <id>"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
fi
|
||||||
@@ -1,81 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
|
|
||||||
. ./scripts/env.sh
|
|
||||||
. ./build/tfs/common/common.sh
|
|
||||||
|
|
||||||
step "Build Debian package" \
|
|
||||||
npm run gulp -- "vscode-linux-$ARCH-build-deb"
|
|
||||||
|
|
||||||
step "Build RPM package" \
|
|
||||||
npm run gulp -- "vscode-linux-$ARCH-build-rpm"
|
|
||||||
|
|
||||||
# step "Build snap package" \
|
|
||||||
# npm run gulp -- "vscode-linux-$ARCH-build-snap"
|
|
||||||
|
|
||||||
# Variables
|
|
||||||
PLATFORM_LINUX="linux-$ARCH"
|
|
||||||
PLATFORM_DEB="linux-deb-$ARCH"
|
|
||||||
PLATFORM_RPM="linux-rpm-$ARCH"
|
|
||||||
[[ "$ARCH" == "ia32" ]] && DEB_ARCH="i386" || DEB_ARCH="amd64"
|
|
||||||
[[ "$ARCH" == "ia32" ]] && RPM_ARCH="i386" || RPM_ARCH="x86_64"
|
|
||||||
REPO="`pwd`"
|
|
||||||
ROOT="$REPO/.."
|
|
||||||
BUILDNAME="VSCode-$PLATFORM_LINUX"
|
|
||||||
BUILD="$ROOT/$BUILDNAME"
|
|
||||||
BUILD_VERSION="$(ls $REPO/.build/linux/deb/$DEB_ARCH/deb/ | sed -e 's/code-[a-z]*_//g' -e 's/\.deb$//g')"
|
|
||||||
[ -z "$VSCODE_QUALITY" ] && TARBALL_FILENAME="code-$BUILD_VERSION.tar.gz" || TARBALL_FILENAME="code-$VSCODE_QUALITY-$BUILD_VERSION.tar.gz"
|
|
||||||
TARBALL_PATH="$ROOT/$TARBALL_FILENAME"
|
|
||||||
PACKAGEJSON="$BUILD/resources/app/package.json"
|
|
||||||
VERSION=$(node -p "require(\"$PACKAGEJSON\").version")
|
|
||||||
|
|
||||||
rm -rf $ROOT/code-*.tar.*
|
|
||||||
(cd $ROOT && \
|
|
||||||
step "Create tar.gz archive" \
|
|
||||||
tar -czf $TARBALL_PATH $BUILDNAME)
|
|
||||||
|
|
||||||
step "Publish tar.gz archive" \
|
|
||||||
node build/tfs/common/publish.js $VSCODE_QUALITY $PLATFORM_LINUX archive-unsigned $TARBALL_FILENAME $VERSION true $TARBALL_PATH
|
|
||||||
|
|
||||||
DEB_FILENAME="$(ls $REPO/.build/linux/deb/$DEB_ARCH/deb/)"
|
|
||||||
DEB_PATH="$REPO/.build/linux/deb/$DEB_ARCH/deb/$DEB_FILENAME"
|
|
||||||
|
|
||||||
step "Publish Debian package" \
|
|
||||||
node build/tfs/common/publish.js $VSCODE_QUALITY $PLATFORM_DEB package $DEB_FILENAME $VERSION true $DEB_PATH
|
|
||||||
|
|
||||||
RPM_FILENAME="$(ls $REPO/.build/linux/rpm/$RPM_ARCH/ | grep .rpm)"
|
|
||||||
RPM_PATH="$REPO/.build/linux/rpm/$RPM_ARCH/$RPM_FILENAME"
|
|
||||||
|
|
||||||
step "Publish RPM package" \
|
|
||||||
node build/tfs/common/publish.js $VSCODE_QUALITY $PLATFORM_RPM package $RPM_FILENAME $VERSION true $RPM_PATH
|
|
||||||
|
|
||||||
# SNAP_FILENAME="$(ls $REPO/.build/linux/snap/$ARCH/ | grep .snap)"
|
|
||||||
# SNAP_PATH="$REPO/.build/linux/snap/$ARCH/$SNAP_FILENAME"
|
|
||||||
|
|
||||||
IS_FROZEN="$(node build/tfs/linux/frozen-check.js $VSCODE_QUALITY)"
|
|
||||||
|
|
||||||
if [ -z "$VSCODE_QUALITY" ]; then
|
|
||||||
echo "VSCODE_QUALITY is not set, skipping repo package publish"
|
|
||||||
elif [ "$IS_FROZEN" = "true" ]; then
|
|
||||||
echo "$VSCODE_QUALITY is frozen, skipping repo package publish"
|
|
||||||
else
|
|
||||||
if [ "$BUILD_SOURCEBRANCH" = "master" ] || [ "$BUILD_SOURCEBRANCH" = "refs/heads/master" ]; then
|
|
||||||
if [[ $BUILD_QUEUEDBY = *"Project Collection Service Accounts"* || $BUILD_QUEUEDBY = *"Microsoft.VisualStudio.Services.TFS"* ]]; then
|
|
||||||
# Write config files needed by API, use eval to force environment variable expansion
|
|
||||||
DIRNAME=$(dirname $(readlink -f $0))
|
|
||||||
pushd $DIRNAME
|
|
||||||
# Submit to apt repo
|
|
||||||
if [ "$DEB_ARCH" = "amd64" ]; then
|
|
||||||
eval echo '{ \"server\": \"azure-apt-cat.cloudapp.net\", \"protocol\": \"https\", \"port\": \"443\", \"repositoryId\": \"58a4adf642421134a1a48d1a\", \"username\": \"$LINUX_REPO_USERNAME\", \"password\": \"$LINUX_REPO_PASSWORD\" }' > apt-config.json
|
|
||||||
|
|
||||||
step "Publish to repositories" \
|
|
||||||
./repoapi_client.sh -config apt-config.json -addfile $DEB_PATH
|
|
||||||
fi
|
|
||||||
# Submit to yum repo (disabled as it's manual until signing is automated)
|
|
||||||
# eval echo '{ \"server\": \"azure-apt-cat.cloudapp.net\", \"protocol\": \"https\", \"port\": \"443\", \"repositoryId\": \"58a4ae3542421134a1a48d1b\", \"username\": \"$LINUX_REPO_USERNAME\", \"password\": \"$LINUX_REPO_PASSWORD\" }' > yum-config.json
|
|
||||||
|
|
||||||
# ./repoapi_client.sh -config yum-config.json -addfile $RPM_PATH
|
|
||||||
popd
|
|
||||||
echo "To check repo publish status run ./repoapi_client.sh -config config.json -check <id>"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
@@ -1,67 +0,0 @@
|
|||||||
#!/bin/bash
|
|
||||||
set -e
|
|
||||||
|
|
||||||
# Arguments
|
|
||||||
ARCH="$1"
|
|
||||||
LINUX_REPO_PASSWORD="$2"
|
|
||||||
|
|
||||||
# Variables
|
|
||||||
PLATFORM_LINUX="linux-$ARCH"
|
|
||||||
PLATFORM_DEB="linux-deb-$ARCH"
|
|
||||||
PLATFORM_RPM="linux-rpm-$ARCH"
|
|
||||||
[[ "$ARCH" == "ia32" ]] && DEB_ARCH="i386" || DEB_ARCH="amd64"
|
|
||||||
[[ "$ARCH" == "ia32" ]] && RPM_ARCH="i386" || RPM_ARCH="x86_64"
|
|
||||||
REPO="`pwd`"
|
|
||||||
ROOT="$REPO/.."
|
|
||||||
BUILDNAME="VSCode-$PLATFORM_LINUX"
|
|
||||||
BUILD="$ROOT/$BUILDNAME"
|
|
||||||
BUILD_VERSION="$(ls $REPO/.build/linux/deb/$DEB_ARCH/deb/ | sed -e 's/code-[a-z]*_//g' -e 's/\.deb$//g')"
|
|
||||||
[ -z "$VSCODE_QUALITY" ] && TARBALL_FILENAME="code-$BUILD_VERSION.tar.gz" || TARBALL_FILENAME="code-$VSCODE_QUALITY-$BUILD_VERSION.tar.gz"
|
|
||||||
TARBALL_PATH="$ROOT/$TARBALL_FILENAME"
|
|
||||||
PACKAGEJSON="$BUILD/resources/app/package.json"
|
|
||||||
VERSION=$(node -p "require(\"$PACKAGEJSON\").version")
|
|
||||||
|
|
||||||
rm -rf $ROOT/code-*.tar.*
|
|
||||||
(cd $ROOT && tar -czf $TARBALL_PATH $BUILDNAME)
|
|
||||||
|
|
||||||
node build/tfs/common/publish.js $VSCODE_QUALITY $PLATFORM_LINUX archive-unsigned $TARBALL_FILENAME $VERSION true $TARBALL_PATH
|
|
||||||
|
|
||||||
DEB_FILENAME="$(ls $REPO/.build/linux/deb/$DEB_ARCH/deb/)"
|
|
||||||
DEB_PATH="$REPO/.build/linux/deb/$DEB_ARCH/deb/$DEB_FILENAME"
|
|
||||||
|
|
||||||
node build/tfs/common/publish.js $VSCODE_QUALITY $PLATFORM_DEB package $DEB_FILENAME $VERSION true $DEB_PATH
|
|
||||||
|
|
||||||
RPM_FILENAME="$(ls $REPO/.build/linux/rpm/$RPM_ARCH/ | grep .rpm)"
|
|
||||||
RPM_PATH="$REPO/.build/linux/rpm/$RPM_ARCH/$RPM_FILENAME"
|
|
||||||
|
|
||||||
node build/tfs/common/publish.js $VSCODE_QUALITY $PLATFORM_RPM package $RPM_FILENAME $VERSION true $RPM_PATH
|
|
||||||
|
|
||||||
# SNAP_FILENAME="$(ls $REPO/.build/linux/snap/$ARCH/ | grep .snap)"
|
|
||||||
# SNAP_PATH="$REPO/.build/linux/snap/$ARCH/$SNAP_FILENAME"
|
|
||||||
|
|
||||||
IS_FROZEN="$(node build/tfs/linux/frozen-check.js $VSCODE_QUALITY)"
|
|
||||||
|
|
||||||
if [ -z "$VSCODE_QUALITY" ]; then
|
|
||||||
echo "VSCODE_QUALITY is not set, skipping repo package publish"
|
|
||||||
elif [ "$IS_FROZEN" = "true" ]; then
|
|
||||||
echo "$VSCODE_QUALITY is frozen, skipping repo package publish"
|
|
||||||
else
|
|
||||||
if [ "$BUILD_SOURCEBRANCH" = "master" ] || [ "$BUILD_SOURCEBRANCH" = "refs/heads/master" ]; then
|
|
||||||
if [[ $BUILD_QUEUEDBY = *"Project Collection Service Accounts"* || $BUILD_QUEUEDBY = *"Microsoft.VisualStudio.Services.TFS"* ]]; then
|
|
||||||
# Write config files needed by API, use eval to force environment variable expansion
|
|
||||||
pushd build/tfs/linux
|
|
||||||
# Submit to apt repo
|
|
||||||
if [ "$DEB_ARCH" = "amd64" ]; then
|
|
||||||
eval echo '{ \"server\": \"azure-apt-cat.cloudapp.net\", \"protocol\": \"https\", \"port\": \"443\", \"repositoryId\": \"58a4adf642421134a1a48d1a\", \"username\": \"vscode\", \"password\": \"$LINUX_REPO_PASSWORD\" }' > apt-config.json
|
|
||||||
|
|
||||||
./repoapi_client.sh -config apt-config.json -addfile $DEB_PATH
|
|
||||||
fi
|
|
||||||
# Submit to yum repo (disabled as it's manual until signing is automated)
|
|
||||||
# eval echo '{ \"server\": \"azure-apt-cat.cloudapp.net\", \"protocol\": \"https\", \"port\": \"443\", \"repositoryId\": \"58a4ae3542421134a1a48d1b\", \"username\": \"vscode\", \"password\": \"$LINUX_REPO_PASSWORD\" }' > yum-config.json
|
|
||||||
|
|
||||||
# ./repoapi_client.sh -config yum-config.json -addfile $RPM_PATH
|
|
||||||
popd
|
|
||||||
echo "To check repo publish status run ./repoapi_client.sh -config config.json -check <id>"
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
fi
|
|
||||||
@@ -1,413 +1,38 @@
|
|||||||
phases:
|
phases:
|
||||||
- phase: Windows
|
- phase: Windows
|
||||||
condition: eq(variables['VSCODE_BUILD_WIN32'], 'true')
|
condition: eq(variables['VSCODE_BUILD_WIN32'], 'true')
|
||||||
queue:
|
queue: Hosted VS2017
|
||||||
name: Hosted VS2017
|
variables:
|
||||||
parallel: 2
|
|
||||||
matrix:
|
|
||||||
x64:
|
|
||||||
VSCODE_ARCH: x64
|
VSCODE_ARCH: x64
|
||||||
ia32:
|
|
||||||
VSCODE_ARCH: ia32
|
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- task: NodeTool@0
|
- template: win32/product-build-win32.yml
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
- phase: Windows32
|
||||||
inputs:
|
condition: eq(variables['VSCODE_BUILD_WIN32_32BIT'], 'true')
|
||||||
versionSpec: "1.3.2"
|
queue: Hosted VS2017
|
||||||
|
variables:
|
||||||
- powershell: |
|
VSCODE_ARCH: ia32
|
||||||
$ErrorActionPreference = "Stop"
|
steps:
|
||||||
"machine monacotools.visualstudio.com password $(VSO_PAT)" | Out-File "$env:USERPROFILE\_netrc" -Encoding ASCII
|
- template: win32/product-build-win32.yml
|
||||||
$env:npm_config_arch="$(VSCODE_ARCH)"
|
|
||||||
$env:CHILD_CONCURRENCY="1"
|
|
||||||
yarn
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
npm run monaco-compile-check
|
|
||||||
$env:VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)"
|
|
||||||
npm run gulp -- mixin
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
node build/lib/builtInExtensions.js
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
$ErrorActionPreference = "Stop"
|
|
||||||
$env:VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)"
|
|
||||||
npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-min"
|
|
||||||
npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-copy-inno-updater"
|
|
||||||
name: build
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
$ErrorActionPreference = "Stop"
|
|
||||||
npm run gulp -- "electron-$(VSCODE_ARCH)"
|
|
||||||
.\scripts\test.bat --build --tfs
|
|
||||||
# yarn smoketest -- --build "$(agent.builddirectory)\VSCode-win32-$(VSCODE_ARCH)"
|
|
||||||
name: test
|
|
||||||
|
|
||||||
- task: SFP.build-tasks.custom-build-task-1.EsrpCodeSigning@1
|
|
||||||
inputs:
|
|
||||||
ConnectedServiceName: 'ESRP CodeSign'
|
|
||||||
FolderPath: '$(agent.builddirectory)/VSCode-win32-$(VSCODE_ARCH)'
|
|
||||||
Pattern: '*.dll,*.exe,*.node'
|
|
||||||
signConfigType: inlineSignParams
|
|
||||||
inlineOperation: |
|
|
||||||
[
|
|
||||||
{
|
|
||||||
"keyCode": "CP-229803",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "VS Code"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "https://code.visualstudio.com/"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/t \"http://ts4096.gtm.microsoft.com/TSS/AuthenticodeTS\""
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "VS Code"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "https://code.visualstudio.com/"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "Append",
|
|
||||||
"parameterValue": "/as"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "FileDigest",
|
|
||||||
"parameterValue": "/fd \"SHA256\""
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/tr \"http://rfc3161.gtm.corp.microsoft.com/TSS/HttpTspServer\" /td sha256"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolVerify",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "VerifyAll",
|
|
||||||
"parameterValue": "/all"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
SessionTimeout: 120
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
$ErrorActionPreference = "Stop"
|
|
||||||
npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-archive" "vscode-win32-$(VSCODE_ARCH)-setup"
|
|
||||||
|
|
||||||
- task: SFP.build-tasks.custom-build-task-1.EsrpCodeSigning@1
|
|
||||||
inputs:
|
|
||||||
ConnectedServiceName: 'ESRP CodeSign'
|
|
||||||
FolderPath: '$(agent.builddirectory)'
|
|
||||||
Pattern: VSCodeSetup.exe
|
|
||||||
signConfigType: inlineSignParams
|
|
||||||
inlineOperation: |
|
|
||||||
[
|
|
||||||
{
|
|
||||||
"keyCode": "CP-229803",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "VS Code"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "https://code.visualstudio.com/"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/t \"http://ts4096.gtm.microsoft.com/TSS/AuthenticodeTS\""
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "VS Code"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "https://code.visualstudio.com/"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "Append",
|
|
||||||
"parameterValue": "/as"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "FileDigest",
|
|
||||||
"parameterValue": "/fd \"SHA256\""
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/tr \"http://rfc3161.gtm.corp.microsoft.com/TSS/HttpTspServer\" /td sha256"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolVerify",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "VerifyAll",
|
|
||||||
"parameterValue": "/all"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
SessionTimeout: 120
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
$ErrorActionPreference = "Stop"
|
|
||||||
$Repo = "$(pwd)"
|
|
||||||
$Root = "$Repo\.."
|
|
||||||
$Exe = "$Repo\.build\win32-$(VSCODE_ARCH)\setup\VSCodeSetup.exe"
|
|
||||||
$Zip = "$Repo\.build\win32-$(VSCODE_ARCH)\archive\VSCode-win32-$(VSCODE_ARCH).zip"
|
|
||||||
$Build = "$Root\VSCode-win32-$(VSCODE_ARCH)"
|
|
||||||
|
|
||||||
# get version
|
|
||||||
$PackageJson = Get-Content -Raw -Path "$Build\resources\app\package.json" | ConvertFrom-Json
|
|
||||||
$Version = $PackageJson.version
|
|
||||||
$Quality = "$env:VSCODE_QUALITY"
|
|
||||||
$env:AZURE_STORAGE_ACCESS_KEY_2 = "$(AZURE_STORAGE_ACCESS_KEY_2)"
|
|
||||||
$env:MOONCAKE_STORAGE_ACCESS_KEY = "$(MOONCAKE_STORAGE_ACCESS_KEY)"
|
|
||||||
$env:AZURE_DOCUMENTDB_MASTERKEY = "$(AZURE_DOCUMENTDB_MASTERKEY)"
|
|
||||||
|
|
||||||
$assetPlatform = if ("$(VSCODE_ARCH)" -eq "ia32") { "win32" } else { "win32-x64" }
|
|
||||||
|
|
||||||
node build/tfs/common/publish.js $Quality "$global:assetPlatform-archive" archive "VSCode-win32-$(VSCODE_ARCH)-$Version.zip" $Version true $Zip
|
|
||||||
node build/tfs/common/publish.js $Quality "$global:assetPlatform" setup "VSCodeSetup-$(VSCODE_ARCH)-$Version.exe" $Version true $Exe
|
|
||||||
|
|
||||||
# publish hockeyapp symbols
|
|
||||||
$hockeyAppId = if ("$(VSCODE_ARCH)" -eq "ia32") { "$(VSCODE_HOCKEYAPP_ID_WIN32)" } else { "$(VSCODE_HOCKEYAPP_ID_WIN64)" }
|
|
||||||
node build/tfs/common/symbols.js "$(VSCODE_MIXIN_PASSWORD)" "$(VSCODE_HOCKEYAPP_TOKEN)" "$(VSCODE_ARCH)" $hockeyAppId
|
|
||||||
|
|
||||||
- phase: Linux
|
- phase: Linux
|
||||||
condition: eq(variables['VSCODE_BUILD_LINUX'], 'true')
|
condition: eq(variables['VSCODE_BUILD_LINUX'], 'true')
|
||||||
queue: linux-x64
|
queue: linux-x64
|
||||||
variables:
|
variables:
|
||||||
VSCODE_ARCH: x64
|
VSCODE_ARCH: x64
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- task: NodeTool@0
|
- template: linux/product-build-linux.yml
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
export npm_config_arch="$(VSCODE_ARCH)"
|
|
||||||
if [[ "$(VSCODE_ARCH)" == "ia32" ]]; then
|
|
||||||
export PKG_CONFIG_PATH="/usr/lib/i386-linux-gnu/pkgconfig"
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "machine monacotools.visualstudio.com password $(VSO_PAT)" > ~/.netrc
|
|
||||||
yarn
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
npm run monaco-compile-check
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- mixin
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
node build/lib/builtInExtensions.js
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- vscode-linux-$(VSCODE_ARCH)-min
|
|
||||||
name: build
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
npm run gulp -- "electron-$(VSCODE_ARCH)"
|
|
||||||
DISPLAY=:10 ./scripts/test.sh --build --tfs
|
|
||||||
# yarn smoketest -- --build "$(agent.builddirectory)/VSCode-linux-$(VSCODE_ARCH)"
|
|
||||||
name: test
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-deb"
|
|
||||||
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-rpm"
|
|
||||||
#npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-snap"
|
|
||||||
|
|
||||||
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
|
||||||
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
|
||||||
MOONCAKE_STORAGE_ACCESS_KEY="$(MOONCAKE_STORAGE_ACCESS_KEY)" \
|
|
||||||
./build/tfs/linux/release2.sh "$(VSCODE_ARCH)" "$(LINUX_REPO_PASSWORD)"
|
|
||||||
|
|
||||||
# publish hockeyapp symbols
|
|
||||||
node build/tfs/common/symbols.js "$(VSCODE_MIXIN_PASSWORD)" "$(VSCODE_HOCKEYAPP_TOKEN)" "$(VSCODE_ARCH)" "$(VSCODE_HOCKEYAPP_ID_LINUX64)"
|
|
||||||
|
|
||||||
- phase: Linux32
|
- phase: Linux32
|
||||||
condition: eq(variables['VSCODE_BUILD_LINUX'], 'true')
|
condition: eq(variables['VSCODE_BUILD_LINUX_32BIT'], 'true')
|
||||||
queue: linux-ia32
|
queue: linux-ia32
|
||||||
variables:
|
variables:
|
||||||
VSCODE_ARCH: ia32
|
VSCODE_ARCH: ia32
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- task: NodeTool@0
|
- template: linux/product-build-linux.yml
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
export npm_config_arch="$(VSCODE_ARCH)"
|
|
||||||
if [[ "$(VSCODE_ARCH)" == "ia32" ]]; then
|
|
||||||
export PKG_CONFIG_PATH="/usr/lib/i386-linux-gnu/pkgconfig"
|
|
||||||
fi
|
|
||||||
|
|
||||||
echo "machine monacotools.visualstudio.com password $(VSO_PAT)" > ~/.netrc
|
|
||||||
yarn
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
npm run monaco-compile-check
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- mixin
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
node build/lib/builtInExtensions.js
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- vscode-linux-$(VSCODE_ARCH)-min
|
|
||||||
name: build
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
npm run gulp -- "electron-$(VSCODE_ARCH)"
|
|
||||||
DISPLAY=:10 ./scripts/test.sh --build --tfs
|
|
||||||
# yarn smoketest -- --build "$(agent.builddirectory)/VSCode-linux-$(VSCODE_ARCH)"
|
|
||||||
name: test
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-deb"
|
|
||||||
npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-rpm"
|
|
||||||
#npm run gulp -- "vscode-linux-$(VSCODE_ARCH)-build-snap"
|
|
||||||
|
|
||||||
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
|
||||||
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
|
||||||
MOONCAKE_STORAGE_ACCESS_KEY="$(MOONCAKE_STORAGE_ACCESS_KEY)" \
|
|
||||||
./build/tfs/linux/release2.sh "$(VSCODE_ARCH)" "$(LINUX_REPO_PASSWORD)"
|
|
||||||
|
|
||||||
# publish hockeyapp symbols
|
|
||||||
node build/tfs/common/symbols.js "$(VSCODE_MIXIN_PASSWORD)" "$(VSCODE_HOCKEYAPP_TOKEN)" "$(VSCODE_ARCH)" "$(VSCODE_HOCKEYAPP_ID_LINUX32)"
|
|
||||||
|
|
||||||
- phase: macOS
|
- phase: macOS
|
||||||
condition: eq(variables['VSCODE_BUILD_MACOS'], 'true')
|
condition: eq(variables['VSCODE_BUILD_MACOS'], 'true')
|
||||||
queue: Hosted macOS Preview
|
queue: Hosted macOS Preview
|
||||||
steps:
|
steps:
|
||||||
- task: NodeTool@0
|
- template: darwin/product-build-darwin.yml
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
echo "machine monacotools.visualstudio.com password $(VSO_PAT)" > ~/.netrc
|
|
||||||
yarn
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
npm run monaco-compile-check
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" npm run gulp -- mixin
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
node build/lib/builtInExtensions.js
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)" \
|
|
||||||
AZURE_STORAGE_ACCESS_KEY="$(AZURE_STORAGE_ACCESS_KEY)" \
|
|
||||||
npm run gulp -- vscode-darwin-min upload-vscode-sourcemaps
|
|
||||||
name: build
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
./scripts/test.sh --build --tfs
|
|
||||||
APP_NAME="`ls $(agent.builddirectory)/VSCode-darwin | head -n 1`"
|
|
||||||
# yarn smoketest -- --build "$(agent.builddirectory)/VSCode-darwin/$APP_NAME"
|
|
||||||
name: test
|
|
||||||
|
|
||||||
- script: |
|
|
||||||
set -e
|
|
||||||
# archive the unsigned build
|
|
||||||
pushd ../VSCode-darwin && zip -r -X -y ../VSCode-darwin-unsigned.zip * && popd
|
|
||||||
|
|
||||||
# publish the unsigned build
|
|
||||||
PACKAGEJSON=`ls ../VSCode-darwin/*.app/Contents/Resources/app/package.json`
|
|
||||||
VERSION=`node -p "require(\"$PACKAGEJSON\").version"`
|
|
||||||
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
|
||||||
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
|
||||||
MOONCAKE_STORAGE_ACCESS_KEY="$(MOONCAKE_STORAGE_ACCESS_KEY)" \
|
|
||||||
node build/tfs/common/publish.js \
|
|
||||||
"$(VSCODE_QUALITY)" \
|
|
||||||
darwin \
|
|
||||||
archive-unsigned \
|
|
||||||
"VSCode-darwin-$(VSCODE_QUALITY)-unsigned.zip" \
|
|
||||||
$VERSION \
|
|
||||||
false \
|
|
||||||
../VSCode-darwin-unsigned.zip
|
|
||||||
|
|
||||||
# publish hockeyapp symbols
|
|
||||||
node build/tfs/common/symbols.js "$(VSCODE_MIXIN_PASSWORD)" "$(VSCODE_HOCKEYAPP_TOKEN)" "$(VSCODE_ARCH)" "$(VSCODE_HOCKEYAPP_ID_MACOS)"
|
|
||||||
|
|
||||||
# enqueue the unsigned build
|
|
||||||
AZURE_DOCUMENTDB_MASTERKEY="$(AZURE_DOCUMENTDB_MASTERKEY)" \
|
|
||||||
AZURE_STORAGE_ACCESS_KEY_2="$(AZURE_STORAGE_ACCESS_KEY_2)" \
|
|
||||||
node build/tfs/common/enqueue.js "$(VSCODE_QUALITY)"
|
|
||||||
|
|
||||||
AZURE_STORAGE_ACCESS_KEY="$(AZURE_STORAGE_ACCESS_KEY)" \
|
|
||||||
npm run gulp -- upload-vscode-configuration
|
|
||||||
@@ -1,71 +0,0 @@
|
|||||||
Param(
|
|
||||||
[string]$arch,
|
|
||||||
[string]$mixinPassword,
|
|
||||||
[string]$vsoPAT
|
|
||||||
)
|
|
||||||
|
|
||||||
. .\build\tfs\win32\node.ps1
|
|
||||||
. .\scripts\env.ps1
|
|
||||||
. .\build\tfs\win32\lib.ps1
|
|
||||||
|
|
||||||
# Create a _netrc file to download distro dependencies
|
|
||||||
# In order to get _netrc to work, we need a HOME variable setup
|
|
||||||
"machine monacotools.visualstudio.com password ${vsoPAT}" | Out-File "$env:HOME\_netrc" -Encoding ASCII
|
|
||||||
|
|
||||||
# Set the right architecture
|
|
||||||
$env:npm_config_arch="$arch"
|
|
||||||
$env:CHILD_CONCURRENCY="1"
|
|
||||||
|
|
||||||
step "Install dependencies" {
|
|
||||||
exec { & yarn }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Hygiene" {
|
|
||||||
exec { & npm run gulp -- hygiene }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Monaco Editor Check" {
|
|
||||||
exec { & .\node_modules\.bin\tsc -p .\src\tsconfig.monaco.json --noEmit }
|
|
||||||
}
|
|
||||||
|
|
||||||
$env:VSCODE_MIXIN_PASSWORD = $mixinPassword
|
|
||||||
step "Mix in repository from vscode-distro" {
|
|
||||||
exec { & npm run gulp -- mixin }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Get Electron" {
|
|
||||||
exec { & npm run gulp -- "electron-$global:arch" }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Install distro dependencies" {
|
|
||||||
exec { & node build\tfs\common\installDistro.js }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Build minified" {
|
|
||||||
exec { & npm run gulp -- "vscode-win32-$global:arch-min" }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Copy Inno updater" {
|
|
||||||
exec { & npm run gulp -- "vscode-win32-$global:arch-copy-inno-updater" }
|
|
||||||
}
|
|
||||||
|
|
||||||
# step "Create loader snapshot" {
|
|
||||||
# exec { & node build\lib\snapshotLoader.js --arch=$global:arch }
|
|
||||||
# }
|
|
||||||
|
|
||||||
step "Run unit tests" {
|
|
||||||
exec { & .\scripts\test.bat --build --reporter dot }
|
|
||||||
}
|
|
||||||
|
|
||||||
# step "Run integration tests" {
|
|
||||||
# exec { & .\scripts\test-integration.bat }
|
|
||||||
# }
|
|
||||||
|
|
||||||
# step "Run smoke test" {
|
|
||||||
# $Artifacts = "$env:AGENT_BUILDDIRECTORY\smoketest-artifacts"
|
|
||||||
# Remove-Item -Recurse -Force -ErrorAction Ignore $Artifacts
|
|
||||||
|
|
||||||
# exec { & npm run smoketest -- --build "$env:AGENT_BUILDDIRECTORY\VSCode-win32-$global:arch" --log "$Artifacts" }
|
|
||||||
# }
|
|
||||||
|
|
||||||
done
|
|
||||||
@@ -1,12 +0,0 @@
|
|||||||
Param(
|
|
||||||
[string]$arch
|
|
||||||
)
|
|
||||||
|
|
||||||
. .\build\tfs\win32\node.ps1
|
|
||||||
. .\build\tfs\win32\lib.ps1
|
|
||||||
|
|
||||||
step "Create archive and setup package" {
|
|
||||||
exec { & npm run gulp -- "vscode-win32-$global:arch-archive" "vscode-win32-$global:arch-setup" }
|
|
||||||
}
|
|
||||||
|
|
||||||
done
|
|
||||||
@@ -1,35 +0,0 @@
|
|||||||
Param(
|
|
||||||
[string]$arch,
|
|
||||||
[string]$storageKey,
|
|
||||||
[string]$mooncakeStorageKey,
|
|
||||||
[string]$documentDbKey
|
|
||||||
)
|
|
||||||
|
|
||||||
. .\build\tfs\win32\node.ps1
|
|
||||||
. .\build\tfs\win32\lib.ps1
|
|
||||||
|
|
||||||
$Repo = "$(pwd)"
|
|
||||||
$Root = "$Repo\.."
|
|
||||||
$Exe = "$Repo\.build\win32-$arch\setup\VSCodeSetup.exe"
|
|
||||||
$Zip = "$Repo\.build\win32-$arch\archive\VSCode-win32-$arch.zip"
|
|
||||||
$Build = "$Root\VSCode-win32-$arch"
|
|
||||||
|
|
||||||
# get version
|
|
||||||
$PackageJson = Get-Content -Raw -Path "$Build\resources\app\package.json" | ConvertFrom-Json
|
|
||||||
$Version = $PackageJson.version
|
|
||||||
$Quality = "$env:VSCODE_QUALITY"
|
|
||||||
$env:AZURE_STORAGE_ACCESS_KEY_2 = $storageKey
|
|
||||||
$env:MOONCAKE_STORAGE_ACCESS_KEY = $mooncakeStorageKey
|
|
||||||
$env:AZURE_DOCUMENTDB_MASTERKEY = $documentDbKey
|
|
||||||
|
|
||||||
$assetPlatform = if ($arch -eq "ia32") { "win32" } else { "win32-x64" }
|
|
||||||
|
|
||||||
step "Publish archive" {
|
|
||||||
exec { & node build/tfs/common/publish.js $Quality "$global:assetPlatform-archive" archive "VSCode-win32-$global:arch-$Version.zip" $Version true $Zip }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Publish setup package" {
|
|
||||||
exec { & node build/tfs/common/publish.js $Quality "$global:assetPlatform" setup "VSCodeSetup-$global:arch-$Version.exe" $Version true $Exe }
|
|
||||||
}
|
|
||||||
|
|
||||||
done
|
|
||||||
6
build/tfs/win32/ESRPClient/NuGet.config
Normal file
6
build/tfs/win32/ESRPClient/NuGet.config
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<configuration>
|
||||||
|
<packageSources>
|
||||||
|
<add key="ESRP" value="https://microsoft.pkgs.visualstudio.com/_packaging/ESRP/nuget/v3/index.json" />
|
||||||
|
</packageSources>
|
||||||
|
</configuration>
|
||||||
4
build/tfs/win32/ESRPClient/packages.config
Normal file
4
build/tfs/win32/ESRPClient/packages.config
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<packages>
|
||||||
|
<package id="EsrpClient" version="1.0.27" />
|
||||||
|
</packages>
|
||||||
@@ -1,212 +0,0 @@
|
|||||||
steps:
|
|
||||||
|
|
||||||
- task: NodeTool@0
|
|
||||||
inputs:
|
|
||||||
versionSpec: "8.9.1"
|
|
||||||
|
|
||||||
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
|
||||||
inputs:
|
|
||||||
versionSpec: "1.3.2"
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
"machine monacotools.visualstudio.com password $(VSO_PAT)" | Out-File "$env:USERPROFILE\_netrc" -Encoding ASCII
|
|
||||||
$env:npm_config_arch="$(VSCODE_ARCH)"
|
|
||||||
$env:CHILD_CONCURRENCY="1"
|
|
||||||
yarn
|
|
||||||
npm run gulp -- hygiene
|
|
||||||
npm run monaco-compile-check
|
|
||||||
$env:VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)"
|
|
||||||
npm run gulp -- mixin
|
|
||||||
node build/tfs/common/installDistro.js
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
$env:VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)"
|
|
||||||
npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-min"
|
|
||||||
npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-copy-inno-updater"
|
|
||||||
name: build
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
npm run gulp -- "electron-$(VSCODE_ARCH)"
|
|
||||||
.\scripts\test.bat --build --tfs
|
|
||||||
name: test
|
|
||||||
|
|
||||||
- task: SFP.build-tasks.custom-build-task-1.EsrpCodeSigning@1
|
|
||||||
inputs:
|
|
||||||
ConnectedServiceName: 'ESRP CodeSign'
|
|
||||||
FolderPath: '$(agent.builddirectory)/VSCode-win32-$(VSCODE_ARCH)'
|
|
||||||
Pattern: '*.dll,*.exe,*.node'
|
|
||||||
signConfigType: inlineSignParams
|
|
||||||
inlineOperation: |
|
|
||||||
[
|
|
||||||
{
|
|
||||||
"keyCode": "CP-229803",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "Microsoft"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "http://www.microsoft.com"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/t \"http://ts4096.gtm.microsoft.com/TSS/AuthenticodeTS\""
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "Microsoft"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "http://www.microsoft.com"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "Append",
|
|
||||||
"parameterValue": "/as"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "FileDigest",
|
|
||||||
"parameterValue": "/fd \"SHA256\""
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/tr \"http://rfc3161.gtm.corp.microsoft.com/TSS/HttpTspServer\" /td sha256"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolVerify",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "VerifyAll",
|
|
||||||
"parameterValue": "/all"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
SessionTimeout: 120
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-archive" "vscode-win32-$(VSCODE_ARCH)-setup"
|
|
||||||
|
|
||||||
- task: SFP.build-tasks.custom-build-task-1.EsrpCodeSigning@1
|
|
||||||
inputs:
|
|
||||||
ConnectedServiceName: 'ESRP CodeSign'
|
|
||||||
FolderPath: '$(agent.builddirectory)'
|
|
||||||
Pattern: VSCodeSetup.exe
|
|
||||||
signConfigType: inlineSignParams
|
|
||||||
inlineOperation: |
|
|
||||||
[
|
|
||||||
{
|
|
||||||
"keyCode": "CP-229803",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "Microsoft"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "http://www.microsoft.com"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/t \"http://ts4096.gtm.microsoft.com/TSS/AuthenticodeTS\""
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolSign",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "OpusName",
|
|
||||||
"parameterValue": "Microsoft"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "OpusInfo",
|
|
||||||
"parameterValue": "http://www.microsoft.com"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "Append",
|
|
||||||
"parameterValue": "/as"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "FileDigest",
|
|
||||||
"parameterValue": "/fd \"SHA256\""
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "PageHash",
|
|
||||||
"parameterValue": "/NPH"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"parameterName": "TimeStamp",
|
|
||||||
"parameterValue": "/tr \"http://rfc3161.gtm.corp.microsoft.com/TSS/HttpTspServer\" /td sha256"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"keyCode": "CP-230012",
|
|
||||||
"operationSetCode": "SigntoolVerify",
|
|
||||||
"parameters": [
|
|
||||||
{
|
|
||||||
"parameterName": "VerifyAll",
|
|
||||||
"parameterValue": "/all"
|
|
||||||
}
|
|
||||||
],
|
|
||||||
"toolName": "sign",
|
|
||||||
"toolVersion": "1.0"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
SessionTimeout: 120
|
|
||||||
|
|
||||||
- powershell: |
|
|
||||||
$Repo = "$(pwd)"
|
|
||||||
$Root = "$Repo\.."
|
|
||||||
$Exe = "$Repo\.build\win32-$(VSCODE_ARCH)\setup\VSCodeSetup.exe"
|
|
||||||
$Zip = "$Repo\.build\win32-$(VSCODE_ARCH)\archive\VSCode-win32-$(VSCODE_ARCH).zip"
|
|
||||||
$Build = "$Root\VSCode-win32-$(VSCODE_ARCH)"
|
|
||||||
|
|
||||||
# get version
|
|
||||||
$PackageJson = Get-Content -Raw -Path "$Build\resources\app\package.json" | ConvertFrom-Json
|
|
||||||
$Version = $PackageJson.version
|
|
||||||
$Quality = "$env:VSCODE_QUALITY"
|
|
||||||
$env:AZURE_STORAGE_ACCESS_KEY_2 = "$(AZURE_STORAGE_ACCESS_KEY_2)"
|
|
||||||
$env:MOONCAKE_STORAGE_ACCESS_KEY = "$(MOONCAKE_STORAGE_ACCESS_KEY)"
|
|
||||||
$env:AZURE_DOCUMENTDB_MASTERKEY = "$(AZURE_DOCUMENTDB_MASTERKEY)"
|
|
||||||
|
|
||||||
$assetPlatform = if ("$(VSCODE_ARCH)" -eq "ia32") { "win32" } else { "win32-x64" }
|
|
||||||
|
|
||||||
node build/tfs/common/publish.js $Quality "$global:assetPlatform-archive" archive "VSCode-win32-$(VSCODE_ARCH)-$Version.zip" $Version true $Zip
|
|
||||||
node build/tfs/common/publish.js $Quality "$global:assetPlatform" setup "VSCodeSetup-$(VSCODE_ARCH)-$Version.exe" $Version true $Exe
|
|
||||||
@@ -1,86 +0,0 @@
|
|||||||
Param(
|
|
||||||
[string]$arch,
|
|
||||||
[string]$mixinPassword,
|
|
||||||
[string]$vsoPAT,
|
|
||||||
[string]$storageKey,
|
|
||||||
[string]$mooncakeStorageKey,
|
|
||||||
[string]$documentDbKey
|
|
||||||
)
|
|
||||||
|
|
||||||
. .\build\tfs\win32\node.ps1
|
|
||||||
. .\scripts\env.ps1
|
|
||||||
. .\build\tfs\win32\lib.ps1
|
|
||||||
|
|
||||||
# Create a _netrc file to download distro dependencies
|
|
||||||
# In order to get _netrc to work, we need a HOME variable setup
|
|
||||||
"machine monacotools.visualstudio.com password ${vsoPAT}" | Out-File "$env:HOME\_netrc" -Encoding ASCII
|
|
||||||
|
|
||||||
# Set the right architecture
|
|
||||||
$env:npm_config_arch="$arch"
|
|
||||||
$env:CHILD_CONCURRENCY="1"
|
|
||||||
|
|
||||||
step "Install dependencies" {
|
|
||||||
exec { & yarn }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Hygiene" {
|
|
||||||
exec { & npm run gulp -- hygiene }
|
|
||||||
}
|
|
||||||
|
|
||||||
$env:VSCODE_MIXIN_PASSWORD = $mixinPassword
|
|
||||||
step "Mix in repository from vscode-distro" {
|
|
||||||
exec { & npm run gulp -- mixin }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Get Electron" {
|
|
||||||
exec { & npm run gulp -- "electron-$global:arch" }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Install distro dependencies" {
|
|
||||||
exec { & node build\tfs\common\installDistro.js }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Build minified" {
|
|
||||||
exec { & npm run gulp -- "vscode-win32-$global:arch-min" }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Run unit tests" {
|
|
||||||
exec { & .\scripts\test.bat --build --reporter dot }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Run smoke test" {
|
|
||||||
$Artifacts = "$env:AGENT_BUILDDIRECTORY\smoketest-artifacts"
|
|
||||||
Remove-Item -Recurse -Force -ErrorAction Ignore $Artifacts
|
|
||||||
|
|
||||||
exec { & npm run smoketest -- --build "$env:AGENT_BUILDDIRECTORY\VSCode-win32-$global:arch" --log "$Artifacts" }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Create archive and setup package" {
|
|
||||||
exec { & npm run gulp -- "vscode-win32-$global:arch-archive" "vscode-win32-$global:arch-setup" }
|
|
||||||
}
|
|
||||||
|
|
||||||
$Repo = "$(pwd)"
|
|
||||||
$Root = "$Repo\.."
|
|
||||||
$Exe = "$Repo\.build\win32-$arch\setup\VSCodeSetup.exe"
|
|
||||||
$Zip = "$Repo\.build\win32-$arch\archive\VSCode-win32-$arch.zip"
|
|
||||||
$Build = "$Root\VSCode-win32-$arch"
|
|
||||||
|
|
||||||
# get version
|
|
||||||
$PackageJson = Get-Content -Raw -Path "$Build\resources\app\package.json" | ConvertFrom-Json
|
|
||||||
$Version = $PackageJson.version
|
|
||||||
$Quality = "$env:VSCODE_QUALITY"
|
|
||||||
$env:AZURE_STORAGE_ACCESS_KEY_2 = $storageKey
|
|
||||||
$env:MOONCAKE_STORAGE_ACCESS_KEY = $mooncakeStorageKey
|
|
||||||
$env:AZURE_DOCUMENTDB_MASTERKEY = $documentDbKey
|
|
||||||
|
|
||||||
$assetPlatform = if ($arch -eq "ia32") { "win32" } else { "win32-x64" }
|
|
||||||
|
|
||||||
step "Publish UNSIGNED archive" {
|
|
||||||
exec { & node build/tfs/common/publish.js $Quality "$global:assetPlatform-archive" archive-unsigned "VSCode-win32-$global:arch-$Version-unsigned.zip" $Version false $Zip }
|
|
||||||
}
|
|
||||||
|
|
||||||
step "Publish UNSIGNED setup package" {
|
|
||||||
exec { & node build/tfs/common/publish.js $Quality "$global:assetPlatform" setup-unsigned "VSCodeSetup-$global:arch-$Version-unsigned.exe" $Version false $Exe }
|
|
||||||
}
|
|
||||||
|
|
||||||
done
|
|
||||||
66
build/tfs/win32/continuous-build-win32.yml
Normal file
66
build/tfs/win32/continuous-build-win32.yml
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
steps:
|
||||||
|
- task: NodeTool@0
|
||||||
|
inputs:
|
||||||
|
versionSpec: "8.9.1"
|
||||||
|
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
||||||
|
inputs:
|
||||||
|
versionSpec: "1.3.2"
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { yarn }
|
||||||
|
displayName: Install Dependencies
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { yarn gulp electron }
|
||||||
|
displayName: Download Electron
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { yarn gulp hygiene }
|
||||||
|
displayName: Run Hygiene Checks
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { yarn check-monaco-editor-compilation }
|
||||||
|
displayName: Run Monaco Editor Checks
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { yarn compile }
|
||||||
|
displayName: Compile Sources
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { yarn download-builtin-extensions }
|
||||||
|
displayName: Download Built-in Extensions
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { .\scripts\test.bat --tfs "Unit Tests" }
|
||||||
|
displayName: Run Unit Tests
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { .\scripts\test-integration.bat --tfs "Integration Tests" }
|
||||||
|
displayName: Run Integration Tests
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { yarn smoketest --screenshots "$(Build.ArtifactStagingDirectory)\artifacts" --log "$(Build.ArtifactStagingDirectory)\artifacts\smoketest.log" }
|
||||||
|
displayName: Run Smoke Tests
|
||||||
|
continueOnError: true
|
||||||
|
- task: PublishBuildArtifacts@1
|
||||||
|
displayName: Publish Smoketest Artifacts
|
||||||
|
inputs:
|
||||||
|
PathtoPublish: '$(Build.ArtifactStagingDirectory)/artifacts'
|
||||||
|
ArtifactName: build-artifacts-win32
|
||||||
|
publishLocation: Container
|
||||||
|
condition: eq(variables['System.PullRequest.IsFork'], 'False')
|
||||||
|
- task: PublishTestResults@2
|
||||||
|
displayName: Publish Tests Results
|
||||||
|
inputs:
|
||||||
|
testResultsFiles: '*-results.xml'
|
||||||
|
searchFolder: '$(Build.ArtifactStagingDirectory)/test-results'
|
||||||
|
condition: succeededOrFailed()
|
||||||
24
build/tfs/win32/exec.ps1
Normal file
24
build/tfs/win32/exec.ps1
Normal file
@@ -0,0 +1,24 @@
|
|||||||
|
# Taken from psake https://github.com/psake/psake
|
||||||
|
|
||||||
|
<#
|
||||||
|
.SYNOPSIS
|
||||||
|
This is a helper function that runs a scriptblock and checks the PS variable $lastexitcode
|
||||||
|
to see if an error occcured. If an error is detected then an exception is thrown.
|
||||||
|
This function allows you to run command-line programs without having to
|
||||||
|
explicitly check the $lastexitcode variable.
|
||||||
|
|
||||||
|
.EXAMPLE
|
||||||
|
exec { svn info $repository_trunk } "Error executing SVN. Please verify SVN command-line client is installed"
|
||||||
|
#>
|
||||||
|
function Exec
|
||||||
|
{
|
||||||
|
[CmdletBinding()]
|
||||||
|
param(
|
||||||
|
[Parameter(Position=0,Mandatory=1)][scriptblock]$cmd,
|
||||||
|
[Parameter(Position=1,Mandatory=0)][string]$errorMessage = ($msgs.error_bad_command -f $cmd)
|
||||||
|
)
|
||||||
|
& $cmd
|
||||||
|
if ($lastexitcode -ne 0) {
|
||||||
|
throw ("Exec: " + $errorMessage)
|
||||||
|
}
|
||||||
|
}
|
||||||
14
build/tfs/win32/import-esrp-auth-cert.ps1
Normal file
14
build/tfs/win32/import-esrp-auth-cert.ps1
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
Param(
|
||||||
|
[string]$AuthCertificateBase64,
|
||||||
|
[string]$AuthCertificateKey
|
||||||
|
)
|
||||||
|
|
||||||
|
# Import auth certificate
|
||||||
|
$AuthCertificateFileName = [System.IO.Path]::GetTempFileName()
|
||||||
|
$AuthCertificateBytes = [Convert]::FromBase64String($AuthCertificateBase64)
|
||||||
|
[IO.File]::WriteAllBytes($AuthCertificateFileName, $AuthCertificateBytes)
|
||||||
|
$AuthCertificate = Import-PfxCertificate -FilePath $AuthCertificateFileName -CertStoreLocation Cert:\LocalMachine\My -Password (ConvertTo-SecureString $AuthCertificateKey -AsPlainText -Force)
|
||||||
|
rm $AuthCertificateFileName
|
||||||
|
$ESRPAuthCertificateSubjectName = $AuthCertificate.Subject
|
||||||
|
|
||||||
|
Write-Output ("##vso[task.setvariable variable=ESRPAuthCertificateSubjectName;]$ESRPAuthCertificateSubjectName")
|
||||||
@@ -1,48 +0,0 @@
|
|||||||
# stop when there's an error
|
|
||||||
$ErrorActionPreference = 'Stop'
|
|
||||||
|
|
||||||
$env:HOME=$env:USERPROFILE
|
|
||||||
|
|
||||||
if (Test-Path env:AGENT_WORKFOLDER) {
|
|
||||||
$env:HOME="${env:AGENT_WORKFOLDER}\home"
|
|
||||||
$env:npm_config_cache="${env:HOME}\npm-cache"
|
|
||||||
$env:YARN_CACHE_FOLDER="${env:HOME}\yarn-cache"
|
|
||||||
$env:npm_config_devdir="${env:HOME}\npm-devdir"
|
|
||||||
New-Item -Path "$env:HOME" -Type directory -Force | out-null
|
|
||||||
New-Item -Path "$env:npm_config_cache" -Type directory -Force | out-null
|
|
||||||
}
|
|
||||||
|
|
||||||
# throw when a process exits with something other than 0
|
|
||||||
function exec([scriptblock]$cmd, [string]$errorMessage = "Error executing command: " + $cmd) {
|
|
||||||
& $cmd
|
|
||||||
if ($LastExitCode -ne 0) {
|
|
||||||
throw $errorMessage
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$Summary = @()
|
|
||||||
function step($Task, $Step) {
|
|
||||||
echo ""
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
echo "Start: $Task"
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
echo ""
|
|
||||||
|
|
||||||
$Stopwatch = [Diagnostics.Stopwatch]::StartNew()
|
|
||||||
Invoke-Command $Step
|
|
||||||
$Stopwatch.Stop()
|
|
||||||
$Formatted = "{0:g}" -f $Stopwatch.Elapsed
|
|
||||||
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
echo "End: $Task, Total: $Formatted"
|
|
||||||
echo "*****************************************************************************"
|
|
||||||
|
|
||||||
$global:Summary += @{ "$Task" = $Formatted }
|
|
||||||
}
|
|
||||||
|
|
||||||
function done() {
|
|
||||||
echo ""
|
|
||||||
echo "Build Summary"
|
|
||||||
echo "============="
|
|
||||||
$global:Summary | Format-Table @{L="Task";E={$_.Name}}, @{L="Duration";E={$_.Value}}
|
|
||||||
}
|
|
||||||
@@ -1,7 +0,0 @@
|
|||||||
# install node
|
|
||||||
$env:Path = $env:NVM_HOME + ";" + $env:NVM_SYMLINK + ";" + $env:Path
|
|
||||||
$NodeVersion = "8.9.1"
|
|
||||||
# nvm install $NodeVersion
|
|
||||||
# nvm use $NodeVersion
|
|
||||||
# npm install -g yarn
|
|
||||||
$env:Path = $env:NVM_HOME + "\v" + $NodeVersion + ";" + $env:Path
|
|
||||||
166
build/tfs/win32/product-build-win32.yml
Normal file
166
build/tfs/win32/product-build-win32.yml
Normal file
@@ -0,0 +1,166 @@
|
|||||||
|
steps:
|
||||||
|
- task: NodeTool@0
|
||||||
|
inputs:
|
||||||
|
versionSpec: "8.9.1"
|
||||||
|
|
||||||
|
- task: geeklearningio.gl-vsts-tasks-yarn.yarn-installer-task.YarnInstaller@2
|
||||||
|
inputs:
|
||||||
|
versionSpec: "1.3.2"
|
||||||
|
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
"machine monacotools.visualstudio.com password $(VSO_PAT)" | Out-File "$env:USERPROFILE\_netrc" -Encoding ASCII
|
||||||
|
$env:npm_config_arch="$(VSCODE_ARCH)"
|
||||||
|
$env:CHILD_CONCURRENCY="1"
|
||||||
|
$env:VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)"
|
||||||
|
exec { yarn }
|
||||||
|
exec { npm run gulp -- hygiene }
|
||||||
|
exec { npm run monaco-compile-check }
|
||||||
|
exec { npm run gulp -- mixin }
|
||||||
|
exec { node build/tfs/common/installDistro.js }
|
||||||
|
exec { node build/lib/builtInExtensions.js }
|
||||||
|
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
$env:VSCODE_MIXIN_PASSWORD="$(VSCODE_MIXIN_PASSWORD)"
|
||||||
|
exec { npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-min" }
|
||||||
|
exec { npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-copy-inno-updater" }
|
||||||
|
name: build
|
||||||
|
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { npm run gulp -- "electron-$(VSCODE_ARCH)" }
|
||||||
|
exec { .\scripts\test.bat --build --tfs "Unit Tests" }
|
||||||
|
# yarn smoketest -- --build "$(agent.builddirectory)\VSCode-win32-$(VSCODE_ARCH)"
|
||||||
|
name: test
|
||||||
|
|
||||||
|
- task: SFP.build-tasks.custom-build-task-1.EsrpCodeSigning@1
|
||||||
|
inputs:
|
||||||
|
ConnectedServiceName: 'ESRP CodeSign'
|
||||||
|
FolderPath: '$(agent.builddirectory)/VSCode-win32-$(VSCODE_ARCH)'
|
||||||
|
Pattern: '*.dll,*.exe,*.node'
|
||||||
|
signConfigType: inlineSignParams
|
||||||
|
inlineOperation: |
|
||||||
|
[
|
||||||
|
{
|
||||||
|
"keyCode": "CP-229803",
|
||||||
|
"operationSetCode": "SigntoolSign",
|
||||||
|
"parameters": [
|
||||||
|
{
|
||||||
|
"parameterName": "OpusName",
|
||||||
|
"parameterValue": "VS Code"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "OpusInfo",
|
||||||
|
"parameterValue": "https://code.visualstudio.com/"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "PageHash",
|
||||||
|
"parameterValue": "/NPH"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "TimeStamp",
|
||||||
|
"parameterValue": "/t \"http://ts4096.gtm.microsoft.com/TSS/AuthenticodeTS\""
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"toolName": "sign",
|
||||||
|
"toolVersion": "1.0"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"keyCode": "CP-230012",
|
||||||
|
"operationSetCode": "SigntoolSign",
|
||||||
|
"parameters": [
|
||||||
|
{
|
||||||
|
"parameterName": "OpusName",
|
||||||
|
"parameterValue": "VS Code"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "OpusInfo",
|
||||||
|
"parameterValue": "https://code.visualstudio.com/"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "Append",
|
||||||
|
"parameterValue": "/as"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "FileDigest",
|
||||||
|
"parameterValue": "/fd \"SHA256\""
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "PageHash",
|
||||||
|
"parameterValue": "/NPH"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"parameterName": "TimeStamp",
|
||||||
|
"parameterValue": "/tr \"http://rfc3161.gtm.corp.microsoft.com/TSS/HttpTspServer\" /td sha256"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"toolName": "sign",
|
||||||
|
"toolVersion": "1.0"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"keyCode": "CP-230012",
|
||||||
|
"operationSetCode": "SigntoolVerify",
|
||||||
|
"parameters": [
|
||||||
|
{
|
||||||
|
"parameterName": "VerifyAll",
|
||||||
|
"parameterValue": "/all"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"toolName": "sign",
|
||||||
|
"toolVersion": "1.0"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
SessionTimeout: 120
|
||||||
|
|
||||||
|
- task: NuGetCommand@2
|
||||||
|
displayName: Install ESRPClient.exe
|
||||||
|
inputs:
|
||||||
|
restoreSolution: 'build\tfs\win32\ESRPClient\packages.config'
|
||||||
|
feedsToUse: config
|
||||||
|
nugetConfigPath: 'build\tfs\win32\ESRPClient\NuGet.config'
|
||||||
|
externalFeedCredentials: 3fc0b7f7-da09-4ae7-a9c8-d69824b1819b
|
||||||
|
restoreDirectory: packages
|
||||||
|
|
||||||
|
- task: ESRPImportCertTask@1
|
||||||
|
displayName: Import ESRP Request Signing Certificate
|
||||||
|
inputs:
|
||||||
|
ESRP: 'ESRP CodeSign'
|
||||||
|
|
||||||
|
- powershell: |
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
.\build\tfs\win32\import-esrp-auth-cert.ps1 -AuthCertificateBase64 $(ESRP_AUTH_CERTIFICATE) -AuthCertificateKey $(ESRP_AUTH_CERTIFICATE_KEY)
|
||||||
|
displayName: Import ESRP Auth Certificate
|
||||||
|
|
||||||
|
- powershell: |
|
||||||
|
. build/tfs/win32/exec.ps1
|
||||||
|
$ErrorActionPreference = "Stop"
|
||||||
|
exec { npm run gulp -- "vscode-win32-$(VSCODE_ARCH)-archive" "vscode-win32-$(VSCODE_ARCH)-system-setup" "vscode-win32-$(VSCODE_ARCH)-user-setup" }
|
||||||
|
|
||||||
|
$Repo = "$(pwd)"
|
||||||
|
$Root = "$Repo\.."
|
||||||
|
$SystemExe = "$Repo\.build\win32-$(VSCODE_ARCH)\system-setup\VSCodeSetup.exe"
|
||||||
|
$UserExe = "$Repo\.build\win32-$(VSCODE_ARCH)\user-setup\VSCodeSetup.exe"
|
||||||
|
$Zip = "$Repo\.build\win32-$(VSCODE_ARCH)\archive\VSCode-win32-$(VSCODE_ARCH).zip"
|
||||||
|
$Build = "$Root\VSCode-win32-$(VSCODE_ARCH)"
|
||||||
|
|
||||||
|
# get version
|
||||||
|
$PackageJson = Get-Content -Raw -Path "$Build\resources\app\package.json" | ConvertFrom-Json
|
||||||
|
$Version = $PackageJson.version
|
||||||
|
$Quality = "$env:VSCODE_QUALITY"
|
||||||
|
$env:AZURE_STORAGE_ACCESS_KEY_2 = "$(AZURE_STORAGE_ACCESS_KEY_2)"
|
||||||
|
$env:MOONCAKE_STORAGE_ACCESS_KEY = "$(MOONCAKE_STORAGE_ACCESS_KEY)"
|
||||||
|
$env:AZURE_DOCUMENTDB_MASTERKEY = "$(AZURE_DOCUMENTDB_MASTERKEY)"
|
||||||
|
|
||||||
|
$assetPlatform = if ("$(VSCODE_ARCH)" -eq "ia32") { "win32" } else { "win32-x64" }
|
||||||
|
|
||||||
|
exec { node build/tfs/common/publish.js $Quality "$global:assetPlatform-archive" archive "VSCode-win32-$(VSCODE_ARCH)-$Version.zip" $Version true $Zip }
|
||||||
|
exec { node build/tfs/common/publish.js $Quality "$global:assetPlatform" setup "VSCodeSetup-$(VSCODE_ARCH)-$Version.exe" $Version true $SystemExe }
|
||||||
|
exec { node build/tfs/common/publish.js $Quality "$global:assetPlatform-user" setup "VSCodeUserSetup-$(VSCODE_ARCH)-$Version.exe" $Version true $UserExe }
|
||||||
|
|
||||||
|
# publish hockeyapp symbols
|
||||||
|
$hockeyAppId = if ("$(VSCODE_ARCH)" -eq "ia32") { "$(VSCODE_HOCKEYAPP_ID_WIN32)" } else { "$(VSCODE_HOCKEYAPP_ID_WIN64)" }
|
||||||
|
exec { node build/tfs/common/symbols.js "$(VSCODE_MIXIN_PASSWORD)" "$(VSCODE_HOCKEYAPP_TOKEN)" "$(VSCODE_ARCH)" $hockeyAppId }
|
||||||
82
build/tfs/win32/sign.ps1
Normal file
82
build/tfs/win32/sign.ps1
Normal file
@@ -0,0 +1,82 @@
|
|||||||
|
function Create-TmpJson($Obj) {
|
||||||
|
$FileName = [System.IO.Path]::GetTempFileName()
|
||||||
|
ConvertTo-Json -Depth 100 $Obj | Out-File -Encoding UTF8 $FileName
|
||||||
|
return $FileName
|
||||||
|
}
|
||||||
|
|
||||||
|
$Auth = Create-TmpJson @{
|
||||||
|
Version = "1.0.0"
|
||||||
|
AuthenticationType = "AAD_CERT"
|
||||||
|
ClientId = $env:ESRPClientId
|
||||||
|
AuthCert = @{
|
||||||
|
SubjectName = $env:ESRPAuthCertificateSubjectName
|
||||||
|
StoreLocation = "LocalMachine"
|
||||||
|
StoreName = "My"
|
||||||
|
}
|
||||||
|
RequestSigningCert = @{
|
||||||
|
SubjectName = $env:ESRPCertificateSubjectName
|
||||||
|
StoreLocation = "LocalMachine"
|
||||||
|
StoreName = "My"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$Policy = Create-TmpJson @{
|
||||||
|
Version = "1.0.0"
|
||||||
|
}
|
||||||
|
|
||||||
|
$Input = Create-TmpJson @{
|
||||||
|
Version = "1.0.0"
|
||||||
|
SignBatches = @(
|
||||||
|
@{
|
||||||
|
SourceLocationType = "UNC"
|
||||||
|
SignRequestFiles = @(
|
||||||
|
@{
|
||||||
|
SourceLocation = $args[0]
|
||||||
|
}
|
||||||
|
)
|
||||||
|
SigningInfo = @{
|
||||||
|
Operations = @(
|
||||||
|
@{
|
||||||
|
KeyCode = "CP-229803"
|
||||||
|
OperationCode = "SigntoolSign"
|
||||||
|
Parameters = @{
|
||||||
|
OpusName = "VS Code"
|
||||||
|
OpusInfo = "https://code.visualstudio.com/"
|
||||||
|
PageHash = "/NPH"
|
||||||
|
TimeStamp = "/t `"http://ts4096.gtm.microsoft.com/TSS/AuthenticodeTS`""
|
||||||
|
}
|
||||||
|
ToolName = "sign"
|
||||||
|
ToolVersion = "1.0"
|
||||||
|
},
|
||||||
|
@{
|
||||||
|
KeyCode = "CP-230012"
|
||||||
|
OperationCode = "SigntoolSign"
|
||||||
|
Parameters = @{
|
||||||
|
OpusName = "VS Code"
|
||||||
|
OpusInfo = "https://code.visualstudio.com/"
|
||||||
|
Append = "/as"
|
||||||
|
FileDigest = "/fd `"SHA256`""
|
||||||
|
PageHash = "/NPH"
|
||||||
|
TimeStamp = "/tr `"http://rfc3161.gtm.corp.microsoft.com/TSS/HttpTspServer`" /td sha256"
|
||||||
|
}
|
||||||
|
ToolName = "sign"
|
||||||
|
ToolVersion = "1.0"
|
||||||
|
},
|
||||||
|
@{
|
||||||
|
KeyCode = "CP-230012"
|
||||||
|
OperationCode = "SigntoolVerify"
|
||||||
|
Parameters = @{
|
||||||
|
VerifyAll = "/all"
|
||||||
|
}
|
||||||
|
ToolName = "sign"
|
||||||
|
ToolVersion = "1.0"
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
$Output = [System.IO.Path]::GetTempFileName()
|
||||||
|
# $ScriptPath = Split-Path -Path $MyInvocation.MyCommand.Definition -Parent
|
||||||
|
# & "$ScriptPath\ESRPClient\packages\EsrpClient.1.0.27\tools\ESRPClient.exe" Sign -a $Auth -p $Policy -i $Input -o $Output
|
||||||
@@ -6,6 +6,7 @@
|
|||||||
"removeComments": false,
|
"removeComments": false,
|
||||||
"preserveConstEnums": true,
|
"preserveConstEnums": true,
|
||||||
"sourceMap": false,
|
"sourceMap": false,
|
||||||
|
"resolveJsonModule": true,
|
||||||
"experimentalDecorators": true,
|
"experimentalDecorators": true,
|
||||||
// enable JavaScript type checking for the language service
|
// enable JavaScript type checking for the language service
|
||||||
// use the tsconfig.build.json for compiling wich disable JavaScript
|
// use the tsconfig.build.json for compiling wich disable JavaScript
|
||||||
|
|||||||
1
build/win32/.gitignore
vendored
Normal file
1
build/win32/.gitignore
vendored
Normal file
@@ -0,0 +1 @@
|
|||||||
|
code-processed.iss
|
||||||
@@ -37,7 +37,7 @@
|
|||||||
"version": "1.2.1",
|
"version": "1.2.1",
|
||||||
"repositoryUrl": "https://github.com/BurntSushi/byteorder",
|
"repositoryUrl": "https://github.com/BurntSushi/byteorder",
|
||||||
"licenseDetail": [
|
"licenseDetail": [
|
||||||
"The Source EULA",
|
"The MIT License (MIT)",
|
||||||
"",
|
"",
|
||||||
"Copyright (c) 2015 Andrew Gallant",
|
"Copyright (c) 2015 Andrew Gallant",
|
||||||
"",
|
"",
|
||||||
@@ -66,7 +66,7 @@
|
|||||||
"version": "0.2.0",
|
"version": "0.2.0",
|
||||||
"repositoryUrl": "https://github.com/Sgeo/take_mut",
|
"repositoryUrl": "https://github.com/Sgeo/take_mut",
|
||||||
"licenseDetail": [
|
"licenseDetail": [
|
||||||
"The Source EULA",
|
"The MIT License (MIT)",
|
||||||
"",
|
"",
|
||||||
"Copyright (c) 2016 Sgeo",
|
"Copyright (c) 2016 Sgeo",
|
||||||
"",
|
"",
|
||||||
@@ -128,7 +128,7 @@
|
|||||||
"version": "0.4.0",
|
"version": "0.4.0",
|
||||||
"repositoryUrl": "https://github.com/chronotope/chrono",
|
"repositoryUrl": "https://github.com/chronotope/chrono",
|
||||||
"licenseDetail": [
|
"licenseDetail": [
|
||||||
"Rust-chrono is dual-licensed under The Source EULA [1] and",
|
"Rust-chrono is dual-licensed under The MIT License [1] and",
|
||||||
"Apache 2.0 License [2]. Copyright (c) 2014--2017, Kang Seonghoon and",
|
"Apache 2.0 License [2]. Copyright (c) 2014--2017, Kang Seonghoon and",
|
||||||
"contributors.",
|
"contributors.",
|
||||||
"",
|
"",
|
||||||
@@ -138,7 +138,7 @@
|
|||||||
"[1]: <http://opensource.org/licenses/MIT>, which is reproduced below:",
|
"[1]: <http://opensource.org/licenses/MIT>, which is reproduced below:",
|
||||||
"",
|
"",
|
||||||
"~~~~",
|
"~~~~",
|
||||||
"The Source EULA",
|
"The MIT License (MIT)",
|
||||||
"",
|
"",
|
||||||
"Copyright (c) 2014, Kang Seonghoon.",
|
"Copyright (c) 2014, Kang Seonghoon.",
|
||||||
"",
|
"",
|
||||||
@@ -545,33 +545,6 @@
|
|||||||
],
|
],
|
||||||
"isProd": true
|
"isProd": true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
"name": "retep998/winapi-rs",
|
|
||||||
"version": "0.3.4",
|
|
||||||
"repositoryUrl": "https://github.com/retep998/winapi-rs",
|
|
||||||
"licenseDetail": [
|
|
||||||
"Copyright (c) 2015 The winapi-rs Developers",
|
|
||||||
"",
|
|
||||||
"Permission is hereby granted, free of charge, to any person obtaining a copy",
|
|
||||||
"of this software and associated documentation files (the \"Software\"), to deal",
|
|
||||||
"in the Software without restriction, including without limitation the rights",
|
|
||||||
"to use, copy, modify, merge, publish, distribute, sublicense, and/or sell",
|
|
||||||
"copies of the Software, and to permit persons to whom the Software is",
|
|
||||||
"furnished to do so, subject to the following conditions:",
|
|
||||||
"",
|
|
||||||
"The above copyright notice and this permission notice shall be included in all",
|
|
||||||
"copies or substantial portions of the Software.",
|
|
||||||
"",
|
|
||||||
"THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR",
|
|
||||||
"IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,",
|
|
||||||
"FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE",
|
|
||||||
"AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER",
|
|
||||||
"LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,",
|
|
||||||
"OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE",
|
|
||||||
"SOFTWARE."
|
|
||||||
],
|
|
||||||
"isProd": true
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"name": "retep998/winapi-rs",
|
"name": "retep998/winapi-rs",
|
||||||
"version": "0.2.8",
|
"version": "0.2.8",
|
||||||
@@ -707,6 +680,33 @@
|
|||||||
],
|
],
|
||||||
"isProd": true
|
"isProd": true
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "retep998/winapi-rs",
|
||||||
|
"version": "0.3.4",
|
||||||
|
"repositoryUrl": "https://github.com/retep998/winapi-rs",
|
||||||
|
"licenseDetail": [
|
||||||
|
"Copyright (c) 2015 The winapi-rs Developers",
|
||||||
|
"",
|
||||||
|
"Permission is hereby granted, free of charge, to any person obtaining a copy",
|
||||||
|
"of this software and associated documentation files (the \"Software\"), to deal",
|
||||||
|
"in the Software without restriction, including without limitation the rights",
|
||||||
|
"to use, copy, modify, merge, publish, distribute, sublicense, and/or sell",
|
||||||
|
"copies of the Software, and to permit persons to whom the Software is",
|
||||||
|
"furnished to do so, subject to the following conditions:",
|
||||||
|
"",
|
||||||
|
"The above copyright notice and this permission notice shall be included in all",
|
||||||
|
"copies or substantial portions of the Software.",
|
||||||
|
"",
|
||||||
|
"THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR",
|
||||||
|
"IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,",
|
||||||
|
"FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE",
|
||||||
|
"AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER",
|
||||||
|
"LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,",
|
||||||
|
"OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE",
|
||||||
|
"SOFTWARE."
|
||||||
|
],
|
||||||
|
"isProd": true
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "rust-lang-nursery/lazy-static.rs",
|
"name": "rust-lang-nursery/lazy-static.rs",
|
||||||
"version": "1.0.0",
|
"version": "1.0.0",
|
||||||
|
|||||||
@@ -12,7 +12,6 @@ AppPublisherURL=https://github.com/Microsoft/sqlopsstudio
|
|||||||
AppSupportURL=https://github.com/Microsoft/sqlopsstudio
|
AppSupportURL=https://github.com/Microsoft/sqlopsstudio
|
||||||
AppUpdatesURL=https://github.com/Microsoft/sqlopsstudio
|
AppUpdatesURL=https://github.com/Microsoft/sqlopsstudio
|
||||||
|
|
||||||
DefaultDirName={pf}\{#DirName}
|
|
||||||
DefaultGroupName={#NameLong}
|
DefaultGroupName={#NameLong}
|
||||||
AllowNoIcons=yes
|
AllowNoIcons=yes
|
||||||
OutputDir={#OutputDir}
|
OutputDir={#OutputDir}
|
||||||
@@ -35,6 +34,13 @@ ShowLanguageDialog=auto
|
|||||||
ArchitecturesAllowed={#ArchitecturesAllowed}
|
ArchitecturesAllowed={#ArchitecturesAllowed}
|
||||||
ArchitecturesInstallIn64BitMode={#ArchitecturesInstallIn64BitMode}
|
ArchitecturesInstallIn64BitMode={#ArchitecturesInstallIn64BitMode}
|
||||||
|
|
||||||
|
#if "user" == InstallTarget
|
||||||
|
DefaultDirName={userpf}\{#DirName}
|
||||||
|
PrivilegesRequired=lowest
|
||||||
|
#else
|
||||||
|
DefaultDirName={pf}\{#DirName}
|
||||||
|
#endif
|
||||||
|
|
||||||
[Languages]
|
[Languages]
|
||||||
Name: "english"; MessagesFile: "compiler:Default.isl,{#RepoDir}\build\win32\i18n\messages.en.isl" {#LocalizedLanguageFile}
|
Name: "english"; MessagesFile: "compiler:Default.isl,{#RepoDir}\build\win32\i18n\messages.en.isl" {#LocalizedLanguageFile}
|
||||||
Name: "german"; MessagesFile: "compiler:Languages\German.isl,{#RepoDir}\build\win32\i18n\messages.de.isl" {#LocalizedLanguageFile("deu")}
|
Name: "german"; MessagesFile: "compiler:Languages\German.isl,{#RepoDir}\build\win32\i18n\messages.de.isl" {#LocalizedLanguageFile("deu")}
|
||||||
@@ -60,16 +66,19 @@ Type: files; Name: "{app}\resources\app\Credits_45.0.2454.85.html"; Check: IsNot
|
|||||||
Type: filesandordirs; Name: "{app}\_"
|
Type: filesandordirs; Name: "{app}\_"
|
||||||
|
|
||||||
[Tasks]
|
[Tasks]
|
||||||
|
Name: "desktopicon"; Description: "{cm:CreateDesktopIcon}"; GroupDescription: "{cm:AdditionalIcons}"; Flags: checkedonce; Check: IsNotUpdate
|
||||||
Name: "quicklaunchicon"; Description: "{cm:CreateQuickLaunchIcon}"; GroupDescription: "{cm:AdditionalIcons}"; Flags: unchecked; OnlyBelowVersion: 0,6.1
|
Name: "quicklaunchicon"; Description: "{cm:CreateQuickLaunchIcon}"; GroupDescription: "{cm:AdditionalIcons}"; Flags: unchecked; OnlyBelowVersion: 0,6.1
|
||||||
|
Name: "associatewithfiles"; Description: "{cm:AssociateWithFiles,{#NameShort}}"; GroupDescription: "{cm:Other}"; Flags: unchecked
|
||||||
Name: "addtopath"; Description: "{cm:AddToPath}"; GroupDescription: "{cm:Other}"
|
Name: "addtopath"; Description: "{cm:AddToPath}"; GroupDescription: "{cm:Other}"
|
||||||
Name: "runcode"; Description: "{cm:RunAfter,{#NameShort}}"; GroupDescription: "{cm:Other}"; Check: WizardSilent
|
Name: "runcode"; Description: "{cm:RunAfter,{#NameShort}}"; GroupDescription: "{cm:Other}"; Check: WizardSilent
|
||||||
|
|
||||||
[Files]
|
[Files]
|
||||||
Source: "*"; DestDir: "{app}"; Flags: ignoreversion recursesubdirs createallsubdirs
|
Source: "*"; Excludes: "\tools,\tools\*,\resources\app\product.json"; DestDir: "{code:GetDestDir}"; Flags: ignoreversion recursesubdirs createallsubdirs
|
||||||
|
Source: "{#ProductJsonPath}"; DestDir: "{code:GetDestDir}\resources\app"; Flags: ignoreversion
|
||||||
|
|
||||||
[Icons]
|
[Icons]
|
||||||
Name: "{group}\{#NameLong}"; Filename: "{app}\{#ExeBasename}.exe"; AppUserModelID: "{#AppUserId}"
|
Name: "{group}\{#NameLong}"; Filename: "{app}\{#ExeBasename}.exe"; AppUserModelID: "{#AppUserId}"
|
||||||
Name: "{commondesktop}\{#NameLong}"; Filename: "{app}\{#ExeBasename}.exe"; AppUserModelID: "{#AppUserId}"
|
Name: "{commondesktop}\{#NameLong}"; Filename: "{app}\{#ExeBasename}.exe"; Tasks: desktopicon; AppUserModelID: "{#AppUserId}"
|
||||||
Name: "{userappdata}\Microsoft\Internet Explorer\Quick Launch\{#NameLong}"; Filename: "{app}\{#ExeBasename}.exe"; Tasks: quicklaunchicon; AppUserModelID: "{#AppUserId}"
|
Name: "{userappdata}\Microsoft\Internet Explorer\Quick Launch\{#NameLong}"; Filename: "{app}\{#ExeBasename}.exe"; Tasks: quicklaunchicon; AppUserModelID: "{#AppUserId}"
|
||||||
|
|
||||||
[Run]
|
[Run]
|
||||||
@@ -77,11 +86,37 @@ Filename: "{app}\{#ExeBasename}.exe"; Description: "{cm:LaunchProgram,{#NameLong
|
|||||||
Filename: "{app}\{#ExeBasename}.exe"; Description: "{cm:LaunchProgram,{#NameLong}}"; Flags: nowait postinstall; Check: WizardNotSilent
|
Filename: "{app}\{#ExeBasename}.exe"; Description: "{cm:LaunchProgram,{#NameLong}}"; Flags: nowait postinstall; Check: WizardNotSilent
|
||||||
|
|
||||||
[Registry]
|
[Registry]
|
||||||
|
#if "user" == InstallTarget
|
||||||
|
#define SoftwareClassesRootKey "HKCU"
|
||||||
|
#else
|
||||||
|
#define SoftwareClassesRootKey "HKLM"
|
||||||
|
#endif
|
||||||
Root: HKCR; Subkey: "{#RegValueName}SourceFile"; ValueType: string; ValueName: ""; ValueData: "{cm:SourceFile,{#NameLong}}"; Flags: uninsdeletekey
|
Root: HKCR; Subkey: "{#RegValueName}SourceFile"; ValueType: string; ValueName: ""; ValueData: "{cm:SourceFile,{#NameLong}}"; Flags: uninsdeletekey
|
||||||
Root: HKCR; Subkey: "{#RegValueName}SourceFile\DefaultIcon"; ValueType: string; ValueName: ""; ValueData: "{app}\resources\app\resources\win32\code_file.ico"
|
Root: HKCR; Subkey: "{#RegValueName}SourceFile\DefaultIcon"; ValueType: string; ValueName: ""; ValueData: "{app}\resources\app\resources\win32\code_file.ico"
|
||||||
Root: HKCR; Subkey: "{#RegValueName}SourceFile\shell\open\command"; ValueType: string; ValueName: ""; ValueData: """{app}\{#ExeBasename}.exe"" ""%1"""
|
Root: HKCR; Subkey: "{#RegValueName}SourceFile\shell\open\command"; ValueType: string; ValueName: ""; ValueData: """{app}\{#ExeBasename}.exe"" ""%1"""
|
||||||
Root: HKCU; Subkey: "Environment"; ValueType: expandsz; ValueName: "Path"; ValueData: "{olddata};{app}\bin"; Tasks: addtopath; Check: NeedsAddPath(ExpandConstant('{app}\bin'))
|
Root: HKCU; Subkey: "Environment"; ValueType: expandsz; ValueName: "Path"; ValueData: "{olddata};{app}\bin"; Tasks: addtopath; Check: NeedsAddPath(ExpandConstant('{app}\bin'))
|
||||||
|
|
||||||
|
Root: HKCU; Subkey: "Software\Classes\.sql\OpenWithProgids"; ValueType: none; ValueName: "{#RegValueName}"; Flags: deletevalue uninsdeletevalue; Tasks: associatewithfiles
|
||||||
|
Root: HKCU; Subkey: "Software\Classes\.sql\OpenWithProgids"; ValueType: string; ValueName: "{#RegValueName}.sql"; ValueData: ""; Flags: uninsdeletevalue; Tasks: associatewithfiles
|
||||||
|
Root: HKCU; Subkey: "Software\Classes\{#RegValueName}.sql"; ValueType: string; ValueName: ""; ValueData: "{cm:SourceFile,SQL}"; Flags: uninsdeletekey; Tasks: associatewithfiles
|
||||||
|
Root: HKCU; Subkey: "Software\Classes\{#RegValueName}.sql"; ValueType: string; ValueName: "AppUserModelID"; ValueData: "{#AppUserId}"; Flags: uninsdeletekey; Tasks: associatewithfiles
|
||||||
|
Root: HKCU; Subkey: "Software\Classes\{#RegValueName}.sql\DefaultIcon"; ValueType: string; ValueName: ""; ValueData: "{app}\resources\app\resources\win32\code_file.ico"; Tasks: associatewithfiles
|
||||||
|
Root: HKCU; Subkey: "Software\Classes\{#RegValueName}.sql\shell\open\command"; ValueType: string; ValueName: ""; ValueData: """{app}\{#ExeBasename}.exe"" ""%1"""; Tasks: associatewithfiles
|
||||||
|
; Environment
|
||||||
|
#if "user" == InstallTarget
|
||||||
|
#define EnvironmentRootKey "HKCU"
|
||||||
|
#define EnvironmentKey "Environment"
|
||||||
|
#define Uninstall64RootKey "HKCU64"
|
||||||
|
#define Uninstall32RootKey "HKCU32"
|
||||||
|
#else
|
||||||
|
#define EnvironmentRootKey "HKLM"
|
||||||
|
#define EnvironmentKey "System\CurrentControlSet\Control\Session Manager\Environment"
|
||||||
|
#define Uninstall64RootKey "HKLM64"
|
||||||
|
#define Uninstall32RootKey "HKLM32"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
Root: {#EnvironmentRootKey}; Subkey: "{#EnvironmentKey}"; ValueType: expandsz; ValueName: "Path"; ValueData: "{olddata};{app}\bin"; Tasks: addtopath; Check: NeedsAddPath(ExpandConstant('{app}\bin'))
|
||||||
|
|
||||||
[Code]
|
[Code]
|
||||||
// Don't allow installing conflicting architectures
|
// Don't allow installing conflicting architectures
|
||||||
function InitializeSetup(): Boolean;
|
function InitializeSetup(): Boolean;
|
||||||
@@ -92,15 +127,33 @@ var
|
|||||||
begin
|
begin
|
||||||
Result := True;
|
Result := True;
|
||||||
|
|
||||||
if IsWin64 then begin
|
#if "user" == InstallTarget
|
||||||
RegKey := 'SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\' + copy('{#IncompatibleAppId}', 2, 38) + '_is1';
|
#if "ia32" == Arch
|
||||||
|
#define IncompatibleArchRootKey "HKLM32"
|
||||||
|
#else
|
||||||
|
#define IncompatibleArchRootKey "HKLM64"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if not WizardSilent() then begin
|
||||||
|
RegKey := 'SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\' + copy('{#IncompatibleTargetAppId}', 2, 38) + '_is1';
|
||||||
|
|
||||||
|
if RegKeyExists({#IncompatibleArchRootKey}, RegKey) then begin
|
||||||
|
if MsgBox('{#NameShort} is already installed on this system for all users. We recommend first uninstalling that version before installing this one. Are you sure you want to continue the installation?', mbConfirmation, MB_YESNO) = IDNO then begin
|
||||||
|
Result := false;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
end;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if Result and IsWin64 then begin
|
||||||
|
RegKey := 'SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\' + copy('{#IncompatibleArchAppId}', 2, 38) + '_is1';
|
||||||
|
|
||||||
if '{#Arch}' = 'ia32' then begin
|
if '{#Arch}' = 'ia32' then begin
|
||||||
Result := not RegKeyExists(HKLM64, RegKey);
|
Result := not RegKeyExists({#Uninstall64RootKey}, RegKey);
|
||||||
ThisArch := '32';
|
ThisArch := '32';
|
||||||
AltArch := '64';
|
AltArch := '64';
|
||||||
end else begin
|
end else begin
|
||||||
Result := not RegKeyExists(HKLM32, RegKey);
|
Result := not RegKeyExists({#Uninstall32RootKey}, RegKey);
|
||||||
ThisArch := '64';
|
ThisArch := '64';
|
||||||
AltArch := '32';
|
AltArch := '32';
|
||||||
end;
|
end;
|
||||||
@@ -209,7 +262,7 @@ function NeedsAddPath(Param: string): boolean;
|
|||||||
var
|
var
|
||||||
OrigPath: string;
|
OrigPath: string;
|
||||||
begin
|
begin
|
||||||
if not RegQueryStringValue(HKEY_CURRENT_USER, 'Environment', 'Path', OrigPath)
|
if not RegQueryStringValue({#EnvironmentRootKey}, '{#EnvironmentKey}', 'Path', OrigPath)
|
||||||
then begin
|
then begin
|
||||||
Result := True;
|
Result := True;
|
||||||
exit;
|
exit;
|
||||||
@@ -228,7 +281,7 @@ begin
|
|||||||
if not CurUninstallStep = usUninstall then begin
|
if not CurUninstallStep = usUninstall then begin
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
if not RegQueryStringValue(HKEY_CURRENT_USER, 'Environment', 'Path', Path)
|
if not RegQueryStringValue({#EnvironmentRootKey}, '{#EnvironmentKey}', 'Path', Path)
|
||||||
then begin
|
then begin
|
||||||
exit;
|
exit;
|
||||||
end;
|
end;
|
||||||
@@ -244,5 +297,9 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
RegWriteExpandStringValue(HKEY_CURRENT_USER, 'Environment', 'Path', NewPath);
|
RegWriteExpandStringValue({#EnvironmentRootKey}, '{#EnvironmentKey}', 'Path', NewPath);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
#ifdef Debug
|
||||||
|
#expr SaveToFile(AddBackslash(SourcePath) + "code-processed.iss")
|
||||||
|
#endif
|
||||||
|
|||||||
Binary file not shown.
@@ -1002,7 +1002,7 @@ hoek@4.x.x:
|
|||||||
version "4.2.1"
|
version "4.2.1"
|
||||||
resolved "https://registry.yarnpkg.com/hoek/-/hoek-4.2.1.tgz#9634502aa12c445dd5a7c5734b572bb8738aacbb"
|
resolved "https://registry.yarnpkg.com/hoek/-/hoek-4.2.1.tgz#9634502aa12c445dd5a7c5734b572bb8738aacbb"
|
||||||
|
|
||||||
http-proxy-agent@^2.0.0:
|
http-proxy-agent@^2.1.0:
|
||||||
version "2.1.0"
|
version "2.1.0"
|
||||||
resolved "https://registry.yarnpkg.com/http-proxy-agent/-/http-proxy-agent-2.1.0.tgz#e4821beef5b2142a2026bd73926fe537631c5405"
|
resolved "https://registry.yarnpkg.com/http-proxy-agent/-/http-proxy-agent-2.1.0.tgz#e4821beef5b2142a2026bd73926fe537631c5405"
|
||||||
dependencies:
|
dependencies:
|
||||||
@@ -1025,7 +1025,7 @@ http-signature@~1.2.0:
|
|||||||
jsprim "^1.2.2"
|
jsprim "^1.2.2"
|
||||||
sshpk "^1.7.0"
|
sshpk "^1.7.0"
|
||||||
|
|
||||||
https-proxy-agent@^2.1.1:
|
https-proxy-agent@^2.2.1:
|
||||||
version "2.2.1"
|
version "2.2.1"
|
||||||
resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-2.2.1.tgz#51552970fa04d723e04c56d04178c3f92592bbc0"
|
resolved "https://registry.yarnpkg.com/https-proxy-agent/-/https-proxy-agent-2.2.1.tgz#51552970fa04d723e04c56d04178c3f92592bbc0"
|
||||||
dependencies:
|
dependencies:
|
||||||
@@ -1843,14 +1843,14 @@ semver@^5.4.1:
|
|||||||
version "5.5.0"
|
version "5.5.0"
|
||||||
resolved "https://registry.yarnpkg.com/semver/-/semver-5.5.0.tgz#dc4bbc7a6ca9d916dee5d43516f0092b58f7b8ab"
|
resolved "https://registry.yarnpkg.com/semver/-/semver-5.5.0.tgz#dc4bbc7a6ca9d916dee5d43516f0092b58f7b8ab"
|
||||||
|
|
||||||
"service-downloader@github:anthonydresser/service-downloader#0.1.2":
|
"service-downloader@github:anthonydresser/service-downloader#0.1.5":
|
||||||
version "0.1.2"
|
version "0.1.5"
|
||||||
resolved "https://codeload.github.com/anthonydresser/service-downloader/tar.gz/2aa9b336b6442e17e24693ddc907030575539798"
|
resolved "https://codeload.github.com/anthonydresser/service-downloader/tar.gz/6ebb0465573cc140e461a22f334260f55ef45546"
|
||||||
dependencies:
|
dependencies:
|
||||||
decompress "^4.2.0"
|
decompress "^4.2.0"
|
||||||
eventemitter2 "^5.0.1"
|
eventemitter2 "^5.0.1"
|
||||||
http-proxy-agent "^2.0.0"
|
http-proxy-agent "^2.1.0"
|
||||||
https-proxy-agent "^2.1.1"
|
https-proxy-agent "^2.2.1"
|
||||||
mkdirp "^0.5.1"
|
mkdirp "^0.5.1"
|
||||||
tmp "^0.0.33"
|
tmp "^0.0.33"
|
||||||
|
|
||||||
@@ -2057,9 +2057,9 @@ tweetnacl@^0.14.3, tweetnacl@~0.14.0:
|
|||||||
version "0.14.5"
|
version "0.14.5"
|
||||||
resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64"
|
resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64"
|
||||||
|
|
||||||
typescript@2.8.1:
|
typescript@2.9.2:
|
||||||
version "2.8.1"
|
version "2.9.2"
|
||||||
resolved "https://registry.yarnpkg.com/typescript/-/typescript-2.8.1.tgz#6160e4f8f195d5ba81d4876f9c0cc1fbc0820624"
|
resolved "https://registry.yarnpkg.com/typescript/-/typescript-2.9.2.tgz#1cbf61d05d6b96269244eb6a3bce4bd914e0f00c"
|
||||||
|
|
||||||
unbzip2-stream@^1.0.9:
|
unbzip2-stream@^1.0.9:
|
||||||
version "1.2.5"
|
version "1.2.5"
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ let localize = nls.loadMessageBundle();
|
|||||||
|
|
||||||
export class AzureAccountProviderService implements vscode.Disposable {
|
export class AzureAccountProviderService implements vscode.Disposable {
|
||||||
// CONSTANTS ///////////////////////////////////////////////////////////////
|
// CONSTANTS ///////////////////////////////////////////////////////////////
|
||||||
private static CommandClearTokenCache = 'accounts.azure.clearTokenCache';
|
private static CommandClearTokenCache = 'accounts.clearTokenCache';
|
||||||
private static ConfigurationSection = 'accounts.azure';
|
private static ConfigurationSection = 'accounts.azure';
|
||||||
private static CredentialNamespace = 'azureAccountProviderCredentials';
|
private static CredentialNamespace = 'azureAccountProviderCredentials';
|
||||||
|
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
"name": "agent",
|
"name": "agent",
|
||||||
"displayName": "SQL Server Agent",
|
"displayName": "SQL Server Agent",
|
||||||
"description": "Manage and troubleshoot SQL Server Agent jobs",
|
"description": "Manage and troubleshoot SQL Server Agent jobs",
|
||||||
"version": "0.31.1",
|
"version": "0.32.7",
|
||||||
"publisher": "Microsoft",
|
"publisher": "Microsoft",
|
||||||
"preview": true,
|
"preview": true,
|
||||||
"license": "https://raw.githubusercontent.com/Microsoft/sqlopsstudio/master/LICENSE.txt",
|
"license": "https://raw.githubusercontent.com/Microsoft/sqlopsstudio/master/LICENSE.txt",
|
||||||
|
|||||||
@@ -13,6 +13,11 @@ import { IAgentDialogData, AgentDialogMode } from '../interfaces';
|
|||||||
const localize = nls.loadMessageBundle();
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
export class AlertData implements IAgentDialogData {
|
export class AlertData implements IAgentDialogData {
|
||||||
|
public static readonly AlertTypeSqlServerEventString: string = localize('alertData.DefaultAlertTypString', 'SQL Server event alert');
|
||||||
|
public static readonly AlertTypePerformanceConditionString: string = localize('alertDialog.PerformanceCondition', 'SQL Server performance condition alert');
|
||||||
|
public static readonly AlertTypeWmiEventString: string = localize('alertDialog.WmiEvent', 'WMI event alert');
|
||||||
|
public static readonly DefaultAlertTypeString: string = AlertData.AlertTypeSqlServerEventString;
|
||||||
|
|
||||||
ownerUri: string;
|
ownerUri: string;
|
||||||
dialogMode: AgentDialogMode = AgentDialogMode.CREATE;
|
dialogMode: AgentDialogMode = AgentDialogMode.CREATE;
|
||||||
id: number;
|
id: number;
|
||||||
@@ -23,7 +28,7 @@ export class AlertData implements IAgentDialogData {
|
|||||||
eventSource: string;
|
eventSource: string;
|
||||||
hasNotification: number;
|
hasNotification: number;
|
||||||
includeEventDescription: string;
|
includeEventDescription: string;
|
||||||
isEnabled: boolean;
|
isEnabled: boolean = true;
|
||||||
jobId: string;
|
jobId: string;
|
||||||
jobName: string;
|
jobName: string;
|
||||||
lastOccurrenceDate: string;
|
lastOccurrenceDate: string;
|
||||||
@@ -36,7 +41,7 @@ export class AlertData implements IAgentDialogData {
|
|||||||
databaseName: string;
|
databaseName: string;
|
||||||
countResetDate: string;
|
countResetDate: string;
|
||||||
categoryName: string;
|
categoryName: string;
|
||||||
alertType: string;
|
alertType: string = AlertData.DefaultAlertTypeString;
|
||||||
wmiEventNamespace: string;
|
wmiEventNamespace: string;
|
||||||
wmiEventQuery: string;
|
wmiEventQuery: string;
|
||||||
|
|
||||||
@@ -109,9 +114,19 @@ export class AlertData implements IAgentDialogData {
|
|||||||
databaseName: this.databaseName,
|
databaseName: this.databaseName,
|
||||||
countResetDate: this.countResetDate,
|
countResetDate: this.countResetDate,
|
||||||
categoryName: this.categoryName,
|
categoryName: this.categoryName,
|
||||||
alertType: sqlops.AlertType.sqlServerEvent, //this.alertType,
|
alertType: AlertData.getAlertTypeFromString(this.alertType),
|
||||||
wmiEventNamespace: this.wmiEventNamespace,
|
wmiEventNamespace: this.wmiEventNamespace,
|
||||||
wmiEventQuery: this.wmiEventQuery
|
wmiEventQuery: this.wmiEventQuery
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static getAlertTypeFromString(alertTypeString: string): sqlops.AlertType {
|
||||||
|
if (alertTypeString === AlertData.AlertTypePerformanceConditionString) {
|
||||||
|
return sqlops.AlertType.sqlServerPerformanceCondition;
|
||||||
|
} else if (alertTypeString === AlertData.AlertTypeWmiEventString) {
|
||||||
|
return sqlops.AlertType.wmiEvent;
|
||||||
|
} else {
|
||||||
|
return sqlops.AlertType.sqlServerEvent;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -4,18 +4,22 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
|
import * as nls from 'vscode-nls';
|
||||||
import * as sqlops from 'sqlops';
|
import * as sqlops from 'sqlops';
|
||||||
|
import * as vscode from 'vscode';
|
||||||
import { AgentUtils } from '../agentUtils';
|
import { AgentUtils } from '../agentUtils';
|
||||||
import { IAgentDialogData, AgentDialogMode } from '../interfaces';
|
import { IAgentDialogData, AgentDialogMode } from '../interfaces';
|
||||||
|
|
||||||
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
export class JobData implements IAgentDialogData {
|
export class JobData implements IAgentDialogData {
|
||||||
|
|
||||||
private readonly JobCompletionActionCondition_Always: string = 'When the job completes';
|
private readonly JobCompletionActionCondition_Always: string = localize('jobData.whenJobCompletes', 'When the job completes');
|
||||||
private readonly JobCompletionActionCondition_OnFailure: string = 'When the job fails';
|
private readonly JobCompletionActionCondition_OnFailure: string = localize('jobData.whenJobFails', 'When the job fails');
|
||||||
private readonly JobCompletionActionCondition_OnSuccess: string = 'When the job succeeds';
|
private readonly JobCompletionActionCondition_OnSuccess: string = localize('jobData.whenJobSucceeds', 'When the job succeeds');
|
||||||
|
|
||||||
// Error Messages
|
// Error Messages
|
||||||
private readonly CreateJobErrorMessage_NameIsEmpty = 'Job name must be provided';
|
private readonly CreateJobErrorMessage_NameIsEmpty = localize('jobData.jobNameRequired', 'Job name must be provided');
|
||||||
|
|
||||||
private _ownerUri: string;
|
private _ownerUri: string;
|
||||||
private _jobCategories: string[];
|
private _jobCategories: string[];
|
||||||
@@ -25,6 +29,7 @@ export class JobData implements IAgentDialogData {
|
|||||||
|
|
||||||
public dialogMode: AgentDialogMode = AgentDialogMode.CREATE;
|
public dialogMode: AgentDialogMode = AgentDialogMode.CREATE;
|
||||||
public name: string;
|
public name: string;
|
||||||
|
public originalName: string;
|
||||||
public enabled: boolean = true;
|
public enabled: boolean = true;
|
||||||
public description: string;
|
public description: string;
|
||||||
public category: string;
|
public category: string;
|
||||||
@@ -40,8 +45,21 @@ export class JobData implements IAgentDialogData {
|
|||||||
public jobSchedules: sqlops.AgentJobScheduleInfo[];
|
public jobSchedules: sqlops.AgentJobScheduleInfo[];
|
||||||
public alerts: sqlops.AgentAlertInfo[];
|
public alerts: sqlops.AgentAlertInfo[];
|
||||||
|
|
||||||
constructor(ownerUri: string, private _agentService: sqlops.AgentServicesProvider = null) {
|
constructor(
|
||||||
|
ownerUri: string,
|
||||||
|
jobInfo: sqlops.AgentJobInfo = undefined,
|
||||||
|
private _agentService: sqlops.AgentServicesProvider = undefined) {
|
||||||
|
|
||||||
this._ownerUri = ownerUri;
|
this._ownerUri = ownerUri;
|
||||||
|
if (jobInfo) {
|
||||||
|
this.dialogMode = AgentDialogMode.EDIT;
|
||||||
|
this.name = jobInfo.name;
|
||||||
|
this.originalName = jobInfo.name;
|
||||||
|
this.owner = jobInfo.owner;
|
||||||
|
this.category = jobInfo.category;
|
||||||
|
this.description = jobInfo.description;
|
||||||
|
this.enabled = jobInfo.enabled;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public get jobCategories(): string[] {
|
public get jobCategories(): string[] {
|
||||||
@@ -92,7 +110,39 @@ export class JobData implements IAgentDialogData {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public async save() {
|
public async save() {
|
||||||
await this._agentService.createJob(this.ownerUri, {
|
let jobInfo: sqlops.AgentJobInfo = this.toAgentJobInfo();
|
||||||
|
let result = this.dialogMode === AgentDialogMode.CREATE
|
||||||
|
? await this._agentService.createJob(this.ownerUri, jobInfo)
|
||||||
|
: await this._agentService.updateJob(this.ownerUri, this.originalName, jobInfo);
|
||||||
|
|
||||||
|
if (!result || !result.success) {
|
||||||
|
vscode.window.showErrorMessage(
|
||||||
|
localize('jobData.saveErrorMessage', "Job update failed '{0}'", result.errorMessage ? result.errorMessage : 'Unknown'));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public validate(): { valid: boolean, errorMessages: string[] } {
|
||||||
|
let validationErrors: string[] = [];
|
||||||
|
|
||||||
|
if (!(this.name && this.name.trim())) {
|
||||||
|
validationErrors.push(this.CreateJobErrorMessage_NameIsEmpty);
|
||||||
|
}
|
||||||
|
|
||||||
|
return {
|
||||||
|
valid: validationErrors.length === 0,
|
||||||
|
errorMessages: validationErrors
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public addJobSchedule(schedule: sqlops.AgentJobScheduleInfo) {
|
||||||
|
let existingSchedule = this.jobSchedules.find(item => item.name === schedule.name);
|
||||||
|
if (!existingSchedule) {
|
||||||
|
this.jobSchedules.push(schedule);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public toAgentJobInfo(): sqlops.AgentJobInfo {
|
||||||
|
return {
|
||||||
name: this.name,
|
name: this.name,
|
||||||
owner: this.owner,
|
owner: this.owner,
|
||||||
description: this.description,
|
description: this.description,
|
||||||
@@ -122,30 +172,6 @@ export class JobData implements IAgentDialogData {
|
|||||||
lastRun: '',
|
lastRun: '',
|
||||||
nextRun: '',
|
nextRun: '',
|
||||||
jobId: ''
|
jobId: ''
|
||||||
}).then(result => {
|
|
||||||
if (!result.success) {
|
|
||||||
console.info(result.errorMessage);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public validate(): { valid: boolean, errorMessages: string[] } {
|
|
||||||
let validationErrors: string[] = [];
|
|
||||||
|
|
||||||
if (!(this.name && this.name.trim())) {
|
|
||||||
validationErrors.push(this.CreateJobErrorMessage_NameIsEmpty);
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
|
||||||
valid: validationErrors.length === 0,
|
|
||||||
errorMessages: validationErrors
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
public addJobSchedule(schedule: sqlops.AgentJobScheduleInfo) {
|
|
||||||
let existingSchedule = this.jobSchedules.find(item => item.name === schedule.name);
|
|
||||||
if (!existingSchedule) {
|
|
||||||
this.jobSchedules.push(schedule);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
@@ -29,8 +29,14 @@ export class OperatorData implements IAgentDialogData {
|
|||||||
weekdayPagerStartTime: string;
|
weekdayPagerStartTime: string;
|
||||||
weekdayPagerEndTime: string;
|
weekdayPagerEndTime: string;
|
||||||
|
|
||||||
constructor(ownerUri:string) {
|
constructor(ownerUri:string, operatorInfo: sqlops.AgentOperatorInfo) {
|
||||||
this.ownerUri = ownerUri;
|
this.ownerUri = ownerUri;
|
||||||
|
|
||||||
|
if (operatorInfo) {
|
||||||
|
this.dialogMode = AgentDialogMode.EDIT;
|
||||||
|
this.name = operatorInfo.name;
|
||||||
|
this.enabled = operatorInfo.enabled;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public async initialize() {
|
public async initialize() {
|
||||||
|
|||||||
@@ -19,8 +19,14 @@ export class ProxyData implements IAgentDialogData {
|
|||||||
credentialId: number;
|
credentialId: number;
|
||||||
isEnabled: boolean;
|
isEnabled: boolean;
|
||||||
|
|
||||||
constructor(ownerUri:string) {
|
constructor(ownerUri:string, proxyInfo: sqlops.AgentProxyInfo) {
|
||||||
this.ownerUri = ownerUri;
|
this.ownerUri = ownerUri;
|
||||||
|
|
||||||
|
if (proxyInfo) {
|
||||||
|
this.accountName = proxyInfo.accountName;
|
||||||
|
this.credentialName = proxyInfo.credentialName;
|
||||||
|
this.description = proxyInfo.description;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public async initialize() {
|
public async initialize() {
|
||||||
|
|||||||
@@ -10,6 +10,8 @@ import * as sqlops from 'sqlops';
|
|||||||
import { AgentDialog } from './agentDialog';
|
import { AgentDialog } from './agentDialog';
|
||||||
import { AgentUtils } from '../agentUtils';
|
import { AgentUtils } from '../agentUtils';
|
||||||
import { AlertData } from '../data/alertData';
|
import { AlertData } from '../data/alertData';
|
||||||
|
import { OperatorDialog } from './operatorDialog';
|
||||||
|
import { JobDialog } from './jobDialog';
|
||||||
|
|
||||||
const localize = nls.loadMessageBundle();
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
@@ -21,6 +23,7 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
private static readonly GeneralTabText: string = localize('alertDialog.General', 'General');
|
private static readonly GeneralTabText: string = localize('alertDialog.General', 'General');
|
||||||
private static readonly ResponseTabText: string = localize('alertDialog.Response', 'Response');
|
private static readonly ResponseTabText: string = localize('alertDialog.Response', 'Response');
|
||||||
private static readonly OptionsTabText: string = localize('alertDialog.Options', 'Options');
|
private static readonly OptionsTabText: string = localize('alertDialog.Options', 'Options');
|
||||||
|
private static readonly EventAlertText: string = localize('alertDialog.eventAlert', 'Event alert definition');
|
||||||
|
|
||||||
// General tab strings
|
// General tab strings
|
||||||
private static readonly NameLabel: string = localize('alertDialog.Name', 'Name');
|
private static readonly NameLabel: string = localize('alertDialog.Name', 'Name');
|
||||||
@@ -31,9 +34,6 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
private static readonly SeverityLabel: string = localize('alertDialog.Severity', 'Severity');
|
private static readonly SeverityLabel: string = localize('alertDialog.Severity', 'Severity');
|
||||||
private static readonly RaiseIfMessageContainsLabel: string = localize('alertDialog.RaiseAlertContains', 'Raise alert when message contains');
|
private static readonly RaiseIfMessageContainsLabel: string = localize('alertDialog.RaiseAlertContains', 'Raise alert when message contains');
|
||||||
private static readonly MessageTextLabel: string = localize('alertDialog.MessageText', 'Message text');
|
private static readonly MessageTextLabel: string = localize('alertDialog.MessageText', 'Message text');
|
||||||
private static readonly AlertTypeSqlServerEventString: string = localize('alertDialog.SqlServerEventAlert', 'SQL Server event alert');
|
|
||||||
private static readonly AlertTypePerformanceConditionString: string = localize('alertDialog.PerformanceCondition', 'SQL Server performance condition alert');
|
|
||||||
private static readonly AlertTypeWmiEventString: string = localize('alertDialog.WmiEvent', 'WMI event alert');
|
|
||||||
private static readonly AlertSeverity001Label: string = localize('alertDialog.Severity001', '001 - Miscellaneous System Information');
|
private static readonly AlertSeverity001Label: string = localize('alertDialog.Severity001', '001 - Miscellaneous System Information');
|
||||||
private static readonly AlertSeverity002Label: string = localize('alertDialog.Severity002', '002 - Reserved');
|
private static readonly AlertSeverity002Label: string = localize('alertDialog.Severity002', '002 - Reserved');
|
||||||
private static readonly AlertSeverity003Label: string = localize('alertDialog.Severity003', '003 - Reserved');
|
private static readonly AlertSeverity003Label: string = localize('alertDialog.Severity003', '003 - Reserved');
|
||||||
@@ -59,11 +59,13 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
private static readonly AlertSeverity023Label: string = localize('alertDialog.Severity023', '023 - Fatal Error: Database Integrity Suspect');
|
private static readonly AlertSeverity023Label: string = localize('alertDialog.Severity023', '023 - Fatal Error: Database Integrity Suspect');
|
||||||
private static readonly AlertSeverity024Label: string = localize('alertDialog.Severity024', '024 - Fatal Error: Hardware Error');
|
private static readonly AlertSeverity024Label: string = localize('alertDialog.Severity024', '024 - Fatal Error: Hardware Error');
|
||||||
private static readonly AlertSeverity025Label: string = localize('alertDialog.Severity025', '025 - Fatal Error');
|
private static readonly AlertSeverity025Label: string = localize('alertDialog.Severity025', '025 - Fatal Error');
|
||||||
|
private static readonly AllDatabases: string = localize('alertDialog.AllDatabases', '<all databases>');
|
||||||
|
|
||||||
private static readonly AlertTypes: string[] = [
|
private static readonly AlertTypes: string[] = [
|
||||||
AlertDialog.AlertTypeSqlServerEventString,
|
AlertData.AlertTypeSqlServerEventString,
|
||||||
AlertDialog.AlertTypePerformanceConditionString,
|
// Disabled until next release
|
||||||
AlertDialog.AlertTypeWmiEventString
|
// AlertData.AlertTypePerformanceConditionString,
|
||||||
|
// AlertData.AlertTypeWmiEventString
|
||||||
];
|
];
|
||||||
|
|
||||||
private static readonly AlertSeverities: string[] = [
|
private static readonly AlertSeverities: string[] = [
|
||||||
@@ -124,6 +126,10 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
private severityDropDown: sqlops.DropDownComponent;
|
private severityDropDown: sqlops.DropDownComponent;
|
||||||
private databaseDropDown: sqlops.DropDownComponent;
|
private databaseDropDown: sqlops.DropDownComponent;
|
||||||
private enabledCheckBox: sqlops.CheckBoxComponent;
|
private enabledCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private errorNumberRadioButton: sqlops.RadioButtonComponent;
|
||||||
|
private severityRadioButton: sqlops.RadioButtonComponent;
|
||||||
|
private errorNumberTextBox: sqlops.InputBoxComponent;
|
||||||
|
|
||||||
private raiseAlertMessageCheckBox: sqlops.CheckBoxComponent;
|
private raiseAlertMessageCheckBox: sqlops.CheckBoxComponent;
|
||||||
private raiseAlertMessageTextBox: sqlops.InputBoxComponent;
|
private raiseAlertMessageTextBox: sqlops.InputBoxComponent;
|
||||||
|
|
||||||
@@ -142,58 +148,115 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
private delayMinutesTextBox: sqlops.InputBoxComponent;
|
private delayMinutesTextBox: sqlops.InputBoxComponent;
|
||||||
private delaySecondsTextBox: sqlops.InputBoxComponent;
|
private delaySecondsTextBox: sqlops.InputBoxComponent;
|
||||||
|
|
||||||
constructor(ownerUri: string, alertInfo: sqlops.AgentAlertInfo = null) {
|
private jobs: string[];
|
||||||
|
private databases: string[];
|
||||||
|
|
||||||
|
constructor(ownerUri: string, alertInfo: sqlops.AgentAlertInfo = undefined, jobs: string[]) {
|
||||||
super(ownerUri,
|
super(ownerUri,
|
||||||
new AlertData(ownerUri, alertInfo),
|
new AlertData(ownerUri, alertInfo),
|
||||||
alertInfo ? AlertDialog.EditDialogTitle : AlertDialog.CreateDialogTitle);
|
alertInfo ? AlertDialog.EditDialogTitle : AlertDialog.CreateDialogTitle);
|
||||||
|
this.jobs = jobs;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async initializeDialog(dialog: sqlops.window.modelviewdialog.Dialog) {
|
protected async initializeDialog(dialog: sqlops.window.modelviewdialog.Dialog) {
|
||||||
let databases = await AgentUtils.getDatabases(this.ownerUri);
|
this.databases = await AgentUtils.getDatabases(this.ownerUri);
|
||||||
|
this.databases.unshift(AlertDialog.AllDatabases);
|
||||||
|
|
||||||
this.generalTab = sqlops.window.modelviewdialog.createTab(AlertDialog.GeneralTabText);
|
this.generalTab = sqlops.window.modelviewdialog.createTab(AlertDialog.GeneralTabText);
|
||||||
this.responseTab = sqlops.window.modelviewdialog.createTab(AlertDialog.ResponseTabText);
|
this.responseTab = sqlops.window.modelviewdialog.createTab(AlertDialog.ResponseTabText);
|
||||||
this.optionsTab = sqlops.window.modelviewdialog.createTab(AlertDialog.OptionsTabText);
|
this.optionsTab = sqlops.window.modelviewdialog.createTab(AlertDialog.OptionsTabText);
|
||||||
|
|
||||||
this.initializeGeneralTab(databases);
|
this.initializeGeneralTab(this.databases, dialog);
|
||||||
this.initializeResponseTab();
|
this.initializeResponseTab();
|
||||||
this.initializeOptionsTab();
|
this.initializeOptionsTab();
|
||||||
|
|
||||||
dialog.content = [this.generalTab, this.responseTab, this.optionsTab];
|
dialog.content = [this.generalTab, this.responseTab, this.optionsTab];
|
||||||
}
|
}
|
||||||
|
|
||||||
private initializeGeneralTab(databases: string[]) {
|
private initializeGeneralTab(databases: string[], dialog: sqlops.window.modelviewdialog.Dialog) {
|
||||||
this.generalTab.registerContent(async view => {
|
this.generalTab.registerContent(async view => {
|
||||||
|
// create controls
|
||||||
this.nameTextBox = view.modelBuilder.inputBox().component();
|
this.nameTextBox = view.modelBuilder.inputBox().component();
|
||||||
|
this.nameTextBox.required = true;
|
||||||
|
this.nameTextBox.onTextChanged(() => {
|
||||||
|
if (this.nameTextBox.value.length > 0) {
|
||||||
|
dialog.okButton.enabled = true;
|
||||||
|
} else {
|
||||||
|
dialog.okButton.enabled = false;
|
||||||
|
}
|
||||||
|
});
|
||||||
this.enabledCheckBox = view.modelBuilder.checkBox()
|
this.enabledCheckBox = view.modelBuilder.checkBox()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: AlertDialog.EnabledCheckboxLabel
|
label: AlertDialog.EnabledCheckboxLabel
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.enabledCheckBox.checked = true;
|
||||||
|
|
||||||
this.databaseDropDown = view.modelBuilder.dropDown()
|
this.databaseDropDown = view.modelBuilder.dropDown()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
value: databases[0],
|
value: databases[0],
|
||||||
values: databases
|
values: databases,
|
||||||
|
width: '100%'
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
this.typeDropDown = view.modelBuilder.dropDown()
|
this.typeDropDown = view.modelBuilder.dropDown()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
value: AlertDialog.AlertTypes[0],
|
value: '',
|
||||||
values: AlertDialog.AlertTypes
|
values: AlertDialog.AlertTypes,
|
||||||
|
width: '100%'
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.severityRadioButton = view.modelBuilder.radioButton()
|
||||||
|
.withProperties({
|
||||||
|
value: 'serverity',
|
||||||
|
name: 'alertTypeOptions',
|
||||||
|
label: AlertDialog.SeverityLabel,
|
||||||
|
checked: true
|
||||||
|
}).component();
|
||||||
|
this.severityRadioButton.checked = true;
|
||||||
|
|
||||||
this.severityDropDown = view.modelBuilder.dropDown()
|
this.severityDropDown = view.modelBuilder.dropDown()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
value: AlertDialog.AlertSeverities[0],
|
value: AlertDialog.AlertSeverities[0],
|
||||||
values: AlertDialog.AlertSeverities
|
values: AlertDialog.AlertSeverities,
|
||||||
|
width: '100%'
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.errorNumberRadioButton = view.modelBuilder.radioButton()
|
||||||
|
.withProperties({
|
||||||
|
value: 'errorNumber',
|
||||||
|
name: 'alertTypeOptions',
|
||||||
|
label: AlertDialog.ErrorNumberLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.errorNumberTextBox = view.modelBuilder.inputBox()
|
||||||
|
.withProperties({
|
||||||
|
width: '100%'
|
||||||
|
})
|
||||||
|
.component();
|
||||||
|
this.errorNumberTextBox.enabled = false;
|
||||||
|
|
||||||
|
this.errorNumberRadioButton.onDidClick(() => {
|
||||||
|
this.errorNumberTextBox.enabled = true;
|
||||||
|
this.severityDropDown.enabled = false;
|
||||||
|
});
|
||||||
|
|
||||||
|
this.severityRadioButton.onDidClick(() => {
|
||||||
|
this.errorNumberTextBox.enabled = false;
|
||||||
|
this.severityDropDown.enabled = true;
|
||||||
|
});
|
||||||
|
|
||||||
this.raiseAlertMessageCheckBox = view.modelBuilder.checkBox()
|
this.raiseAlertMessageCheckBox = view.modelBuilder.checkBox()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: AlertDialog.RaiseIfMessageContainsLabel
|
label: AlertDialog.RaiseIfMessageContainsLabel
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
this.raiseAlertMessageTextBox = view.modelBuilder.inputBox().component();
|
this.raiseAlertMessageTextBox = view.modelBuilder.inputBox().component();
|
||||||
|
this.raiseAlertMessageTextBox.enabled = false;
|
||||||
|
|
||||||
|
this.raiseAlertMessageCheckBox.onChanged(() => {
|
||||||
|
this.raiseAlertMessageTextBox.enabled = this.raiseAlertMessageCheckBox.checked;
|
||||||
|
});
|
||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
@@ -206,24 +269,61 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
component: this.typeDropDown,
|
component: this.typeDropDown,
|
||||||
title: AlertDialog.TypeLabel
|
title: AlertDialog.TypeLabel
|
||||||
}, {
|
}, {
|
||||||
|
components: [{
|
||||||
component: this.databaseDropDown,
|
component: this.databaseDropDown,
|
||||||
title: AlertDialog.DatabaseLabel
|
title: AlertDialog.DatabaseLabel
|
||||||
}, {
|
},
|
||||||
|
{
|
||||||
|
component: this.severityRadioButton,
|
||||||
|
title: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
component: this.severityDropDown,
|
component: this.severityDropDown,
|
||||||
title: AlertDialog.SeverityLabel
|
title: ''
|
||||||
}, {
|
},
|
||||||
|
{
|
||||||
|
component: this.errorNumberRadioButton,
|
||||||
|
title: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
|
component: this.errorNumberTextBox,
|
||||||
|
title: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
component: this.raiseAlertMessageCheckBox,
|
component: this.raiseAlertMessageCheckBox,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: this.raiseAlertMessageTextBox,
|
component: this.raiseAlertMessageTextBox,
|
||||||
title: AlertDialog.MessageTextLabel
|
title: AlertDialog.MessageTextLabel
|
||||||
|
}],
|
||||||
|
title: AlertDialog.EventAlertText
|
||||||
}
|
}
|
||||||
]).withLayout({ width: '100%' }).component();
|
]).withLayout({ width: '100%' }).component();
|
||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
|
|
||||||
|
// initialize control values
|
||||||
this.nameTextBox.value = this.model.name;
|
this.nameTextBox.value = this.model.name;
|
||||||
|
this.raiseAlertMessageTextBox.value = this.model.eventDescriptionKeyword;
|
||||||
|
this.typeDropDown.value = this.model.alertType;
|
||||||
this.enabledCheckBox.checked = this.model.isEnabled;
|
this.enabledCheckBox.checked = this.model.isEnabled;
|
||||||
|
|
||||||
|
if (this.model.messageId > 0) {
|
||||||
|
this.errorNumberRadioButton.checked = true;
|
||||||
|
this.errorNumberTextBox.value = this.model.messageId.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.model.severity > 0) {
|
||||||
|
this.severityRadioButton.checked = true;
|
||||||
|
this.severityDropDown.value = this.severityDropDown.values[this.model.severity-1];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.model.databaseName) {
|
||||||
|
let idx = this.databases.indexOf(this.model.databaseName);
|
||||||
|
if (idx >= 0) {
|
||||||
|
this.databaseDropDown.value = this.databases[idx];
|
||||||
|
}
|
||||||
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -234,18 +334,51 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
label: AlertDialog.ExecuteJobCheckBoxLabel
|
label: AlertDialog.ExecuteJobCheckBoxLabel
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
this.executeJobTextBox = view.modelBuilder.inputBox().component();
|
this.executeJobTextBox = view.modelBuilder.inputBox()
|
||||||
|
.withProperties({ width: 375 })
|
||||||
|
.component();
|
||||||
|
this.executeJobTextBox.enabled = false;
|
||||||
this.newJobButton = view.modelBuilder.button().withProperties({
|
this.newJobButton = view.modelBuilder.button().withProperties({
|
||||||
label: AlertDialog.NewJobButtonLabel,
|
label: AlertDialog.NewJobButtonLabel,
|
||||||
width: 80
|
width: 80
|
||||||
}).component();
|
}).component();
|
||||||
|
this.newJobButton.enabled = false;
|
||||||
|
this.newJobButton.onDidClick(() => {
|
||||||
|
let jobDialog = new JobDialog(this.ownerUri);
|
||||||
|
jobDialog.openDialog();
|
||||||
|
});
|
||||||
|
|
||||||
|
this.executeJobCheckBox.onChanged(() => {
|
||||||
|
if (this.executeJobCheckBox.checked) {
|
||||||
|
this.executeJobTextBox.enabled = true;
|
||||||
|
this.newJobButton.enabled = true;
|
||||||
|
} else {
|
||||||
|
this.executeJobTextBox.enabled = false;
|
||||||
|
this.newJobButton.enabled = false;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
let executeJobContainer = view.modelBuilder.formContainer()
|
||||||
|
.withFormItems([{
|
||||||
|
component: this.executeJobTextBox,
|
||||||
|
title: AlertDialog.ExecuteJobTextBoxLabel
|
||||||
|
}, {
|
||||||
|
component: this.newJobButton,
|
||||||
|
title: AlertDialog.NewJobButtonLabel
|
||||||
|
}], { componentWidth: '100%'}).component();
|
||||||
|
|
||||||
|
let previewTag = view.modelBuilder.text()
|
||||||
|
.withProperties({
|
||||||
|
value: 'Feature Preview'
|
||||||
|
}).component();
|
||||||
|
|
||||||
this.notifyOperatorsCheckBox = view.modelBuilder.checkBox()
|
this.notifyOperatorsCheckBox = view.modelBuilder.checkBox()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: AlertDialog.NotifyOperatorsTextBoxLabel
|
label: AlertDialog.NotifyOperatorsTextBoxLabel
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.notifyOperatorsCheckBox.enabled = false;
|
||||||
|
|
||||||
this.operatorsTable = view.modelBuilder.table()
|
this.operatorsTable = view.modelBuilder.table()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
columns: [
|
||||||
@@ -254,32 +387,60 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
AlertDialog.OperatorPagerColumnLabel
|
AlertDialog.OperatorPagerColumnLabel
|
||||||
],
|
],
|
||||||
data: [],
|
data: [],
|
||||||
height: 500
|
height: 500,
|
||||||
|
width: 375
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
this.newOperatorButton = view.modelBuilder.button().withProperties({
|
this.newOperatorButton = view.modelBuilder.button().withProperties({
|
||||||
label: this.newOperatorButton,
|
label: AlertDialog.NewOperatorButtonLabel,
|
||||||
width: 80
|
width: 80
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.operatorsTable.enabled = false;
|
||||||
|
this.newOperatorButton.enabled = false;
|
||||||
|
|
||||||
|
this.newOperatorButton.onDidClick(() => {
|
||||||
|
let operatorDialog = new OperatorDialog(this.ownerUri);
|
||||||
|
operatorDialog.openDialog();
|
||||||
|
});
|
||||||
|
|
||||||
|
this.notifyOperatorsCheckBox.onChanged(() => {
|
||||||
|
if (this.notifyOperatorsCheckBox.checked) {
|
||||||
|
this.operatorsTable.enabled = true;
|
||||||
|
this.newOperatorButton.enabled = true;
|
||||||
|
} else {
|
||||||
|
this.operatorsTable.enabled = false;
|
||||||
|
this.newOperatorButton.enabled = false;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
let notifyOperatorContainer = view.modelBuilder.formContainer()
|
||||||
|
.withFormItems([{
|
||||||
|
component: this.operatorsTable,
|
||||||
|
title: AlertDialog.OperatorListLabel
|
||||||
|
}, {
|
||||||
|
component: this.newOperatorButton,
|
||||||
|
title: ''
|
||||||
|
}], { componentWidth: '100%'}).component();
|
||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.executeJobCheckBox,
|
component: this.executeJobCheckBox,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: this.executeJobTextBox,
|
component: executeJobContainer,
|
||||||
title: AlertDialog.ExecuteJobTextBoxLabel
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: this.newJobButton,
|
component: previewTag,
|
||||||
title: AlertDialog.NewJobButtonLabel
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: this.notifyOperatorsCheckBox,
|
component: this.notifyOperatorsCheckBox,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: this.operatorsTable,
|
component: notifyOperatorContainer,
|
||||||
title: AlertDialog.OperatorListLabel,
|
title: ''
|
||||||
actions: [this.newOperatorButton]
|
}])
|
||||||
}]).withLayout({ width: '100%' }).component();
|
.withLayout({ width: '100%' }).component();
|
||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
});
|
});
|
||||||
@@ -300,9 +461,19 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
|
|
||||||
this.additionalMessageTextBox = view.modelBuilder.inputBox().component();
|
this.additionalMessageTextBox = view.modelBuilder.inputBox().component();
|
||||||
|
|
||||||
this.delayMinutesTextBox = view.modelBuilder.inputBox().component();
|
this.delayMinutesTextBox = view.modelBuilder.inputBox()
|
||||||
|
.withProperties({
|
||||||
|
inputType: 'number',
|
||||||
|
placeHolder: 0
|
||||||
|
})
|
||||||
|
.component();
|
||||||
|
|
||||||
this.delaySecondsTextBox = view.modelBuilder.inputBox().component();
|
this.delaySecondsTextBox = view.modelBuilder.inputBox()
|
||||||
|
.withProperties({
|
||||||
|
inputType: 'number',
|
||||||
|
placeHolder: 0
|
||||||
|
})
|
||||||
|
.component();
|
||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
@@ -343,13 +514,25 @@ export class AlertDialog extends AgentDialog<AlertData> {
|
|||||||
this.model.isEnabled = this.enabledCheckBox.checked;
|
this.model.isEnabled = this.enabledCheckBox.checked;
|
||||||
|
|
||||||
this.model.alertType = this.getDropdownValue(this.typeDropDown);
|
this.model.alertType = this.getDropdownValue(this.typeDropDown);
|
||||||
this.model.databaseName = this.getDropdownValue(this.databaseDropDown);
|
let databaseName = this.getDropdownValue(this.databaseDropDown);
|
||||||
this.model.severity = this.getSeverityNumber();
|
this.model.databaseName = (databaseName !== AlertDialog.AllDatabases) ? databaseName : undefined;
|
||||||
this.model.messageId = undefined;
|
|
||||||
|
if (this.severityRadioButton.checked) {
|
||||||
|
this.model.severity = this.getSeverityNumber();
|
||||||
|
this.model.messageId = 0;
|
||||||
|
} else {
|
||||||
|
this.model.severity = 0;
|
||||||
|
this.model.messageId = +this.errorNumberTextBox.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.raiseAlertMessageCheckBox.checked) {
|
||||||
|
this.model.eventDescriptionKeyword = this.raiseAlertMessageTextBox.value;
|
||||||
|
} else {
|
||||||
|
this.model.eventDescriptionKeyword = '';
|
||||||
|
}
|
||||||
|
let minutes = this.delayMinutesTextBox.value ? +this.delayMinutesTextBox.value : 0;
|
||||||
|
let seconds = this.delaySecondsTextBox.value ? +this.delaySecondsTextBox : 0;
|
||||||
|
this.model.delayBetweenResponses = minutes + seconds;
|
||||||
|
|
||||||
let raiseIfError = this.raiseAlertMessageCheckBox.checked;
|
|
||||||
if (raiseIfError) {
|
|
||||||
let messageText = this.raiseAlertMessageTextBox.value;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
'use strict';
|
'use strict';
|
||||||
|
import * as nls from 'vscode-nls';
|
||||||
import * as sqlops from 'sqlops';
|
import * as sqlops from 'sqlops';
|
||||||
import { JobData } from '../data/jobData';
|
import { JobData } from '../data/jobData';
|
||||||
import { JobStepDialog } from './jobStepDialog';
|
import { JobStepDialog } from './jobStepDialog';
|
||||||
@@ -10,50 +11,57 @@ import { PickScheduleDialog } from './pickScheduleDialog';
|
|||||||
import { AlertDialog } from './alertDialog';
|
import { AlertDialog } from './alertDialog';
|
||||||
import { AgentDialog } from './agentDialog';
|
import { AgentDialog } from './agentDialog';
|
||||||
|
|
||||||
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
export class JobDialog extends AgentDialog<JobData> {
|
export class JobDialog extends AgentDialog<JobData> {
|
||||||
|
|
||||||
// TODO: localize
|
// TODO: localize
|
||||||
// Top level
|
// Top level
|
||||||
private static readonly DialogTitle: string = 'New Job';
|
private static readonly CreateDialogTitle: string = localize('jobDialog.newJob', 'New Job');
|
||||||
private readonly GeneralTabText: string = 'General';
|
private static readonly EditDialogTitle: string = localize('jobDialog.editJob', 'Edit Job');
|
||||||
private readonly StepsTabText: string = 'Steps';
|
private readonly GeneralTabText: string = localize('jobDialog.general', 'General');
|
||||||
private readonly SchedulesTabText: string = 'Schedules';
|
private readonly StepsTabText: string = localize('jobDialog.steps', 'Steps');
|
||||||
private readonly AlertsTabText: string = 'Alerts';
|
private readonly SchedulesTabText: string = localize('jobDialog.schedules', 'Schedules');
|
||||||
private readonly NotificationsTabText: string = 'Notifications';
|
private readonly AlertsTabText: string = localize('jobDialog.alerts', 'Alerts');
|
||||||
|
private readonly NotificationsTabText: string = localize('jobDialog.notifications', 'Notifications');
|
||||||
|
private readonly BlankJobNameErrorText: string = localize('jobDialog.blankJobNameError', 'The name of the job cannot be blank.');
|
||||||
|
|
||||||
// General tab strings
|
// General tab strings
|
||||||
private readonly NameTextBoxLabel: string = 'Name';
|
private readonly NameTextBoxLabel: string = localize('jobDialog.name', 'Name');
|
||||||
private readonly OwnerTextBoxLabel: string = 'Owner';
|
private readonly OwnerTextBoxLabel: string = localize('jobDialog.owner', 'Owner');
|
||||||
private readonly CategoryDropdownLabel: string = 'Category';
|
private readonly CategoryDropdownLabel: string = localize('jobDialog.category', 'Category');
|
||||||
private readonly DescriptionTextBoxLabel: string = 'Description';
|
private readonly DescriptionTextBoxLabel: string = localize('jobDialog.description', 'Description');
|
||||||
private readonly EnabledCheckboxLabel: string = 'Enabled';
|
private readonly EnabledCheckboxLabel: string = localize('jobDialog.enabled', 'Enabled');
|
||||||
|
|
||||||
// Steps tab strings
|
// Steps tab strings
|
||||||
private readonly JobStepsTopLabelString: string = 'Job step list';
|
private readonly JobStepsTopLabelString: string = localize('jobDialog.jobStepList', 'Job step list');
|
||||||
private readonly StepsTable_StepColumnString: string = 'Step';
|
private readonly StepsTable_StepColumnString: string = localize('jobDialog.step', 'Step');
|
||||||
private readonly StepsTable_NameColumnString: string = 'Name';
|
private readonly StepsTable_NameColumnString: string = localize('jobDialog.name', 'Name');
|
||||||
private readonly StepsTable_TypeColumnString: string = 'Type';
|
private readonly StepsTable_TypeColumnString: string = localize('jobDialog.type', 'Type');
|
||||||
private readonly StepsTable_SuccessColumnString: string = 'On Success';
|
private readonly StepsTable_SuccessColumnString: string = localize('jobDialog.onSuccess', 'On Success');
|
||||||
private readonly StepsTable_FailureColumnString: string = 'On Failure';
|
private readonly StepsTable_FailureColumnString: string = localize('jobDialog.onFailure', 'On Failure');
|
||||||
private readonly NewStepButtonString: string = 'New...';
|
private readonly NewStepButtonString: string = localize('jobDialog.new', 'New...');
|
||||||
private readonly InsertStepButtonString: string = 'Insert...';
|
private readonly EditStepButtonString: string = localize('jobDialog.edit', 'Edit');
|
||||||
private readonly EditStepButtonString: string = 'Edit';
|
private readonly DeleteStepButtonString: string = localize('jobDialog.delete', 'Delete');
|
||||||
private readonly DeleteStepButtonString: string = 'Delete';
|
private readonly MoveStepUpButtonString: string = localize('jobDialog.moveUp', 'Move Step Up');
|
||||||
|
private readonly MoveStepDownButtonString: string = localize('jobDialog.moveDown', 'Move Step Up');
|
||||||
|
|
||||||
// Notifications tab strings
|
// Notifications tab strings
|
||||||
private readonly NotificationsTabTopLabelString: string = 'Actions to perform when the job completes';
|
private readonly NotificationsTabTopLabelString: string = localize('jobDialog.notificationsTabTop', 'Actions to perform when the job completes');
|
||||||
private readonly EmailCheckBoxString: string = 'Email';
|
private readonly EmailCheckBoxString: string = localize('jobDialog.email', 'Email');
|
||||||
private readonly PagerCheckBoxString: string = 'Page';
|
private readonly PagerCheckBoxString: string = localize('jobDialog.page', 'Page');
|
||||||
private readonly EventLogCheckBoxString: string = 'Write to the Windows Application event log';
|
private readonly EventLogCheckBoxString: string = localize('jobDialog.eventLogCheckBoxLabel', 'Write to the Windows Application event log');
|
||||||
private readonly DeleteJobCheckBoxString: string = 'Automatically delete job';
|
private readonly DeleteJobCheckBoxString: string = localize('jobDialog.deleteJobLabel', 'Automatically delete job');
|
||||||
|
|
||||||
// Schedules tab strings
|
// Schedules tab strings
|
||||||
private readonly SchedulesTopLabelString: string = 'Schedules list';
|
private readonly SchedulesTopLabelString: string = localize('jobDialog.schedulesaLabel', 'Schedules list');
|
||||||
private readonly PickScheduleButtonString: string = 'Pick Schedule';
|
private readonly PickScheduleButtonString: string = localize('jobDialog.pickSchedule', 'Pick Schedule');
|
||||||
|
private readonly ScheduleNameLabelString: string = localize('jobDialog.scheduleNameLabel', 'Schedule Name');
|
||||||
|
|
||||||
// Alerts tab strings
|
// Alerts tab strings
|
||||||
private readonly AlertsTopLabelString: string = 'Alerts list';
|
private readonly AlertsTopLabelString: string = localize('jobDialog.alertsList', 'Alerts list');
|
||||||
private readonly NewAlertButtonString: string = 'New Alert';
|
private readonly NewAlertButtonString: string = localize('jobDialog.newAlert', 'New Alert');
|
||||||
|
private readonly AlertNameLabelString: string = localize('jobDialog.alertNameLabel', 'Alert Name');
|
||||||
|
|
||||||
// UI Components
|
// UI Components
|
||||||
private generalTab: sqlops.window.modelviewdialog.DialogTab;
|
private generalTab: sqlops.window.modelviewdialog.DialogTab;
|
||||||
@@ -72,7 +80,8 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
// Steps tab controls
|
// Steps tab controls
|
||||||
private stepsTable: sqlops.TableComponent;
|
private stepsTable: sqlops.TableComponent;
|
||||||
private newStepButton: sqlops.ButtonComponent;
|
private newStepButton: sqlops.ButtonComponent;
|
||||||
private insertStepButton: sqlops.ButtonComponent;
|
private moveStepUpButton: sqlops.ButtonComponent;
|
||||||
|
private moveStepDownButton: sqlops.ButtonComponent;
|
||||||
private editStepButton: sqlops.ButtonComponent;
|
private editStepButton: sqlops.ButtonComponent;
|
||||||
private deleteStepButton: sqlops.ButtonComponent;
|
private deleteStepButton: sqlops.ButtonComponent;
|
||||||
|
|
||||||
@@ -97,8 +106,11 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
private alertsTable: sqlops.TableComponent;
|
private alertsTable: sqlops.TableComponent;
|
||||||
private newAlertButton: sqlops.ButtonComponent;
|
private newAlertButton: sqlops.ButtonComponent;
|
||||||
|
|
||||||
constructor(ownerUri: string) {
|
constructor(ownerUri: string, jobInfo: sqlops.AgentJobInfo = undefined) {
|
||||||
super(ownerUri, new JobData(ownerUri), JobDialog.DialogTitle);
|
super(
|
||||||
|
ownerUri,
|
||||||
|
new JobData(ownerUri, jobInfo),
|
||||||
|
jobInfo ? JobDialog.EditDialogTitle : JobDialog.CreateDialogTitle);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async initializeDialog() {
|
protected async initializeDialog() {
|
||||||
@@ -113,7 +125,6 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
this.initializeSchedulesTab();
|
this.initializeSchedulesTab();
|
||||||
this.initializeNotificationsTab();
|
this.initializeNotificationsTab();
|
||||||
this.dialog.content = [this.generalTab, this.stepsTab, this.schedulesTab, this.alertsTab, this.notificationsTab];
|
this.dialog.content = [this.generalTab, this.stepsTab, this.schedulesTab, this.alertsTab, this.notificationsTab];
|
||||||
|
|
||||||
this.dialog.registerCloseValidator(() => {
|
this.dialog.registerCloseValidator(() => {
|
||||||
this.updateModel();
|
this.updateModel();
|
||||||
let validationResult = this.model.validate();
|
let validationResult = this.model.validate();
|
||||||
@@ -129,6 +140,12 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
private initializeGeneralTab() {
|
private initializeGeneralTab() {
|
||||||
this.generalTab.registerContent(async view => {
|
this.generalTab.registerContent(async view => {
|
||||||
this.nameTextBox = view.modelBuilder.inputBox().component();
|
this.nameTextBox = view.modelBuilder.inputBox().component();
|
||||||
|
this.nameTextBox.required = true;
|
||||||
|
this.nameTextBox.onTextChanged(() => {
|
||||||
|
if (this.nameTextBox.value && this.nameTextBox.value.length > 0) {
|
||||||
|
this.dialog.message = null;
|
||||||
|
}
|
||||||
|
});
|
||||||
this.ownerTextBox = view.modelBuilder.inputBox().component();
|
this.ownerTextBox = view.modelBuilder.inputBox().component();
|
||||||
this.categoryDropdown = view.modelBuilder.dropDown().component();
|
this.categoryDropdown = view.modelBuilder.dropDown().component();
|
||||||
this.descriptionTextBox = view.modelBuilder.inputBox().withProperties({
|
this.descriptionTextBox = view.modelBuilder.inputBox().withProperties({
|
||||||
@@ -159,16 +176,27 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
|
|
||||||
|
this.nameTextBox.value = this.model.name;
|
||||||
this.ownerTextBox.value = this.model.defaultOwner;
|
this.ownerTextBox.value = this.model.defaultOwner;
|
||||||
this.categoryDropdown.values = this.model.jobCategories;
|
this.categoryDropdown.values = this.model.jobCategories;
|
||||||
this.categoryDropdown.value = this.model.jobCategories[0];
|
|
||||||
|
let idx: number = undefined;
|
||||||
|
if (this.model.category && this.model.category !== '') {
|
||||||
|
idx = this.model.jobCategories.indexOf(this.model.category);
|
||||||
|
}
|
||||||
|
this.categoryDropdown.value = this.model.jobCategories[idx > 0 ? idx : 0];
|
||||||
|
|
||||||
this.enabledCheckBox.checked = this.model.enabled;
|
this.enabledCheckBox.checked = this.model.enabled;
|
||||||
this.descriptionTextBox.value = '';
|
this.descriptionTextBox.value = this.model.description;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
private initializeStepsTab() {
|
private initializeStepsTab() {
|
||||||
this.stepsTab.registerContent(async view => {
|
this.stepsTab.registerContent(async view => {
|
||||||
|
let previewTag = view.modelBuilder.text()
|
||||||
|
.withProperties({
|
||||||
|
value: 'Feature Preview'
|
||||||
|
}).component();
|
||||||
this.stepsTable = view.modelBuilder.table()
|
this.stepsTable = view.modelBuilder.table()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
columns: [
|
||||||
@@ -179,24 +207,38 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
this.StepsTable_FailureColumnString
|
this.StepsTable_FailureColumnString
|
||||||
],
|
],
|
||||||
data: [],
|
data: [],
|
||||||
height: 800
|
height: 430
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.moveStepUpButton = view.modelBuilder.button()
|
||||||
|
.withProperties({
|
||||||
|
label: this.MoveStepUpButtonString,
|
||||||
|
width: 80
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.moveStepDownButton = view.modelBuilder.button()
|
||||||
|
.withProperties({
|
||||||
|
label: this.MoveStepDownButtonString,
|
||||||
|
width: 80
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.moveStepUpButton.enabled = false;
|
||||||
|
this.moveStepDownButton.enabled = false;
|
||||||
|
|
||||||
this.newStepButton = view.modelBuilder.button().withProperties({
|
this.newStepButton = view.modelBuilder.button().withProperties({
|
||||||
label: this.NewStepButtonString,
|
label: this.NewStepButtonString,
|
||||||
width: 80
|
width: 80
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
this.newStepButton.onDidClick((e)=>{
|
this.newStepButton.onDidClick((e)=>{
|
||||||
let stepDialog = new JobStepDialog(this.model.ownerUri, '', '', 1, this.model);
|
if (this.nameTextBox.value && this.nameTextBox.value.length > 0) {
|
||||||
|
let stepDialog = new JobStepDialog(this.model.ownerUri, this.nameTextBox.value, '' , 1, this.model);
|
||||||
stepDialog.openNewStepDialog();
|
stepDialog.openNewStepDialog();
|
||||||
|
} else {
|
||||||
|
this.dialog.message = { text: this.BlankJobNameErrorText };
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
this.insertStepButton = view.modelBuilder.button().withProperties({
|
|
||||||
label: this.InsertStepButtonString,
|
|
||||||
width: 80
|
|
||||||
}).component();
|
|
||||||
|
|
||||||
this.editStepButton = view.modelBuilder.button().withProperties({
|
this.editStepButton = view.modelBuilder.button().withProperties({
|
||||||
label: this.EditStepButtonString,
|
label: this.EditStepButtonString,
|
||||||
width: 80
|
width: 80
|
||||||
@@ -207,11 +249,17 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
width: 80
|
width: 80
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.stepsTable.enabled = false;
|
||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
|
component: previewTag,
|
||||||
|
title: ''
|
||||||
|
},
|
||||||
|
{
|
||||||
component: this.stepsTable,
|
component: this.stepsTable,
|
||||||
title: this.JobStepsTopLabelString,
|
title: this.JobStepsTopLabelString,
|
||||||
actions: [this.newStepButton, this.insertStepButton, this.editStepButton, this.deleteStepButton]
|
actions: [this.moveStepUpButton, this.moveStepDownButton, this.newStepButton, this.editStepButton, this.deleteStepButton]
|
||||||
}]).withLayout({ width: '100%' }).component();
|
}]).withLayout({ width: '100%' }).component();
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
});
|
});
|
||||||
@@ -219,13 +267,17 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
|
|
||||||
private initializeAlertsTab() {
|
private initializeAlertsTab() {
|
||||||
this.alertsTab.registerContent(async view => {
|
this.alertsTab.registerContent(async view => {
|
||||||
|
let previewTag = view.modelBuilder.text()
|
||||||
|
.withProperties({
|
||||||
|
value: 'Feature Preview'
|
||||||
|
}).component();
|
||||||
this.alertsTable = view.modelBuilder.table()
|
this.alertsTable = view.modelBuilder.table()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
columns: [
|
||||||
'Alert Name'
|
this.AlertNameLabelString
|
||||||
],
|
],
|
||||||
data: [],
|
data: [],
|
||||||
height: 600,
|
height: 430,
|
||||||
width: 400
|
width: 400
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
@@ -235,7 +287,7 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
this.newAlertButton.onDidClick((e)=>{
|
this.newAlertButton.onDidClick((e)=>{
|
||||||
let alertDialog = new AlertDialog(this.model.ownerUri);
|
let alertDialog = new AlertDialog(this.model.ownerUri, null, []);
|
||||||
alertDialog.onSuccess((dialogModel) => {
|
alertDialog.onSuccess((dialogModel) => {
|
||||||
});
|
});
|
||||||
alertDialog.openDialog();
|
alertDialog.openDialog();
|
||||||
@@ -243,6 +295,9 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
|
component: previewTag,
|
||||||
|
title: ''
|
||||||
|
}, {
|
||||||
component: this.alertsTable,
|
component: this.alertsTable,
|
||||||
title: this.AlertsTopLabelString,
|
title: this.AlertsTopLabelString,
|
||||||
actions: [this.newAlertButton]
|
actions: [this.newAlertButton]
|
||||||
@@ -257,11 +312,11 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
this.schedulesTable = view.modelBuilder.table()
|
this.schedulesTable = view.modelBuilder.table()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
columns: [
|
||||||
'Schedule Name'
|
this.ScheduleNameLabelString
|
||||||
],
|
],
|
||||||
data: [],
|
data: [],
|
||||||
height: 600,
|
height: 430,
|
||||||
width: 400
|
width: 420
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
this.pickScheduleButton = view.modelBuilder.button().withProperties({
|
this.pickScheduleButton = view.modelBuilder.button().withProperties({
|
||||||
@@ -361,21 +416,23 @@ export class JobDialog extends AgentDialog<JobData> {
|
|||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer().withFormItems([
|
let formModel = view.modelBuilder.formContainer().withFormItems([
|
||||||
{
|
{
|
||||||
component: this.notificationsTabTopLabel,
|
components:
|
||||||
title: ''
|
[{
|
||||||
}, {
|
|
||||||
component: emailContainer,
|
component: emailContainer,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
},
|
||||||
|
{
|
||||||
component: pagerContainer,
|
component: pagerContainer,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
},
|
||||||
|
{
|
||||||
component: eventLogContainer,
|
component: eventLogContainer,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
},
|
||||||
|
{
|
||||||
component: deleteJobContainer,
|
component: deleteJobContainer,
|
||||||
title: ''
|
title: ''
|
||||||
}]).withLayout({ width: '100%' }).component();
|
}], title: this.NotificationsTabTopLabelString}]).withLayout({ width: '100%' }).component();
|
||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
this.emailConditionDropdown.values = this.model.JobCompletionActionConditions;
|
this.emailConditionDropdown.values = this.model.JobCompletionActionConditions;
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
'use strict';
|
'use strict';
|
||||||
|
import * as nls from 'vscode-nls';
|
||||||
import * as sqlops from 'sqlops';
|
import * as sqlops from 'sqlops';
|
||||||
import * as vscode from 'vscode';
|
import * as vscode from 'vscode';
|
||||||
import { JobStepData } from '../data/jobStepData';
|
import { JobStepData } from '../data/jobStepData';
|
||||||
@@ -10,31 +11,58 @@ import { AgentUtils } from '../agentUtils';
|
|||||||
import { JobData } from '../data/jobData';
|
import { JobData } from '../data/jobData';
|
||||||
const path = require('path');
|
const path = require('path');
|
||||||
|
|
||||||
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
export class JobStepDialog {
|
export class JobStepDialog {
|
||||||
|
|
||||||
// TODO: localize
|
// TODO: localize
|
||||||
// Top level
|
// Top level
|
||||||
//
|
//
|
||||||
private static readonly DialogTitle: string = 'New Job Step';
|
private readonly DialogTitle: string = localize('jobStepDialog.newJobStep', 'New Job Step');
|
||||||
private static readonly FileBrowserDialogTitle: string = 'Locate Database Files - ';
|
private readonly FileBrowserDialogTitle: string = localize('jobStepDialog.fileBrowserTitle', 'Locate Database Files - ');
|
||||||
private static readonly OkButtonText: string = 'OK';
|
private readonly OkButtonText: string = localize('jobStepDialog.ok', 'OK');
|
||||||
private static readonly CancelButtonText: string = 'Cancel';
|
private readonly CancelButtonText: string = localize('jobStepDialog.cancel', 'Cancel');
|
||||||
private static readonly GeneralTabText: string = 'General';
|
private readonly GeneralTabText: string = localize('jobStepDialog.general', 'General');
|
||||||
private static readonly AdvancedTabText: string = 'Advanced';
|
private readonly AdvancedTabText: string = localize('jobStepDialog.advanced', 'Advanced');
|
||||||
private static readonly OpenCommandText: string = 'Open...';
|
private readonly OpenCommandText: string = localize('jobStepDialog.open', 'Open...');
|
||||||
private static readonly ParseCommandText: string = 'Parse';
|
private readonly ParseCommandText: string = localize('jobStepDialog.parse','Parse');
|
||||||
private static readonly NextButtonText: string = 'Next';
|
private readonly NextButtonText: string = localize('jobStepDialog.next', 'Next');
|
||||||
private static readonly PreviousButtonText: string = 'Previous';
|
private readonly PreviousButtonText: string = localize('jobStepDialog.previous','Previous');
|
||||||
private static readonly SuccessAction: string = 'On success action';
|
private readonly SuccessfulParseText: string = localize('jobStepDialog.successParse', 'The command was successfully parsed.');
|
||||||
private static readonly FailureAction: string = 'On failure action';
|
private readonly FailureParseText: string = localize('jobStepDialog.failParse', 'The command failed.');
|
||||||
|
private readonly BlankStepNameErrorText: string = localize('jobStepDialog.blankStepName', 'The step name cannot be left blank');
|
||||||
|
|
||||||
|
// General Control Titles
|
||||||
|
private readonly StepNameLabelString: string = localize('jobStepDialog.stepNameLabel', 'Step Name');
|
||||||
|
private readonly TypeLabelString: string = localize('jobStepDialog.typeLabel', 'Type');
|
||||||
|
private readonly RunAsLabelString: string = localize('jobStepDialog.runAsLabel', 'Run as');
|
||||||
|
private readonly DatabaseLabelString: string = localize('jobStepDialog.databaseLabel', 'Database');
|
||||||
|
private readonly CommandLabelString: string = localize('jobStepDialog.commandLabel', 'Command');
|
||||||
|
|
||||||
|
// Advanced Control Titles
|
||||||
|
private readonly SuccessActionLabel: string = localize('jobStepDialog.successAction', 'On success action');
|
||||||
|
private readonly FailureActionLabel: string = localize('jobStepDialog.failureAction', 'On failure action');
|
||||||
|
private readonly RunAsUserLabel: string = localize('jobStepDialog.runAsUser', 'Run as user');
|
||||||
|
private readonly RetryAttemptsLabel: string = localize('jobStepDialog.retryAttempts', 'Retry Attempts');
|
||||||
|
private readonly RetryIntervalLabel: string = localize('jobStepDialog.retryInterval', 'Retry Interval (minutes)');
|
||||||
|
private readonly LogToTableLabel: string = localize('jobStepDialog.logToTable', 'Log to table');
|
||||||
|
private readonly AppendExistingTableEntryLabel: string = localize('jobStepDialog.appendExistingTableEntry', 'Append output to exisiting entry in table');
|
||||||
|
private readonly IncludeStepOutputHistoryLabel: string = localize('jobStepDialog.includeStepOutputHistory', 'Include step output in history');
|
||||||
|
private readonly OutputFileNameLabel: string = localize('jobStepDialog.outputFile', 'Output File');
|
||||||
|
private readonly AppendOutputToFileLabel: string = localize('jobStepDialog.appendOutputToFile', 'Append output to existing file');
|
||||||
|
|
||||||
|
// File Browser Control Titles
|
||||||
|
private readonly SelectedPathLabelString: string = localize('jobStepDialog.selectedPath', 'Selected path');
|
||||||
|
private readonly FilesOfTypeLabelString: string = localize('jobStepDialog.filesOfType', 'Files of type');
|
||||||
|
private readonly FileNameLabelString: string = localize('jobStepDialog.fileName', 'File name');
|
||||||
|
private readonly AllFilesLabelString: string = localize('jobStepDialog.allFiles', 'All Files (*)');
|
||||||
|
|
||||||
// Dropdown options
|
// Dropdown options
|
||||||
private static readonly TSQLScript: string = 'Transact-SQL script (T-SQL)';
|
private readonly TSQLScript: string = localize('jobStepDialog.TSQL', 'Transact-SQL script (T-SQL)');
|
||||||
private static readonly AgentServiceAccount: string = 'SQL Server Agent Service Account';
|
private readonly AgentServiceAccount: string = localize('jobStepDialog.agentServiceAccount', 'SQL Server Agent Service Account');
|
||||||
private static readonly NextStep: string = 'Go to the next step';
|
private readonly NextStep: string = localize('jobStepDialog.nextStep', 'Go to the next step');
|
||||||
private static readonly QuitJobReportingSuccess: string = 'Quit the job reporting success';
|
private readonly QuitJobReportingSuccess: string = localize('jobStepDialog.quitJobSuccess', 'Quit the job reporting success');
|
||||||
private static readonly QuitJobReportingFailure: string = 'Quit the job reporting failure';
|
private readonly QuitJobReportingFailure: string = localize('jobStepDialog.quitJobFailure', 'Quit the job reporting failure');
|
||||||
|
|
||||||
// UI Components
|
// UI Components
|
||||||
|
|
||||||
@@ -54,6 +82,7 @@ export class JobStepDialog {
|
|||||||
private retryIntervalBox: sqlops.InputBoxComponent;
|
private retryIntervalBox: sqlops.InputBoxComponent;
|
||||||
private outputFileNameBox: sqlops.InputBoxComponent;
|
private outputFileNameBox: sqlops.InputBoxComponent;
|
||||||
private fileBrowserNameBox: sqlops.InputBoxComponent;
|
private fileBrowserNameBox: sqlops.InputBoxComponent;
|
||||||
|
private userInputBox: sqlops.InputBoxComponent;
|
||||||
|
|
||||||
// Dropdowns
|
// Dropdowns
|
||||||
private typeDropdown: sqlops.DropDownComponent;
|
private typeDropdown: sqlops.DropDownComponent;
|
||||||
@@ -98,33 +127,39 @@ export class JobStepDialog {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private initializeUIComponents() {
|
private initializeUIComponents() {
|
||||||
this.dialog = sqlops.window.modelviewdialog.createDialog(JobStepDialog.DialogTitle);
|
this.dialog = sqlops.window.modelviewdialog.createDialog(this.DialogTitle);
|
||||||
this.generalTab = sqlops.window.modelviewdialog.createTab(JobStepDialog.GeneralTabText);
|
this.generalTab = sqlops.window.modelviewdialog.createTab(this.GeneralTabText);
|
||||||
this.advancedTab = sqlops.window.modelviewdialog.createTab(JobStepDialog.AdvancedTabText);
|
this.advancedTab = sqlops.window.modelviewdialog.createTab(this.AdvancedTabText);
|
||||||
this.dialog.content = [this.generalTab, this.advancedTab];
|
this.dialog.content = [this.generalTab, this.advancedTab];
|
||||||
this.dialog.okButton.onClick(async () => await this.execute());
|
this.dialog.okButton.onClick(async () => await this.execute());
|
||||||
this.dialog.okButton.label = JobStepDialog.OkButtonText;
|
this.dialog.okButton.label = this.OkButtonText;
|
||||||
this.dialog.cancelButton.label = JobStepDialog.CancelButtonText;
|
this.dialog.cancelButton.label = this.CancelButtonText;
|
||||||
}
|
}
|
||||||
|
|
||||||
private createCommands(view, queryProvider: sqlops.QueryProvider) {
|
private createCommands(view, queryProvider: sqlops.QueryProvider) {
|
||||||
this.openButton = view.modelBuilder.button()
|
this.openButton = view.modelBuilder.button()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: JobStepDialog.OpenCommandText,
|
label: this.OpenCommandText,
|
||||||
width: '80px'
|
width: '80px',
|
||||||
|
isFile: true
|
||||||
}).component();
|
}).component();
|
||||||
this.parseButton = view.modelBuilder.button()
|
this.parseButton = view.modelBuilder.button()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: JobStepDialog.ParseCommandText,
|
label: this.ParseCommandText,
|
||||||
width: '80px'
|
width: '80px',
|
||||||
|
isFile: false
|
||||||
}).component();
|
}).component();
|
||||||
|
this.openButton.onDidClick(e => {
|
||||||
|
let queryContent = e;
|
||||||
|
this.commandTextBox.value = queryContent;
|
||||||
|
});
|
||||||
this.parseButton.onDidClick(e => {
|
this.parseButton.onDidClick(e => {
|
||||||
if (this.commandTextBox.value) {
|
if (this.commandTextBox.value) {
|
||||||
queryProvider.parseSyntax(this.ownerUri, this.commandTextBox.value).then(result => {
|
queryProvider.parseSyntax(this.ownerUri, this.commandTextBox.value).then(result => {
|
||||||
if (result && result.parseable) {
|
if (result && result.parseable) {
|
||||||
this.dialog.message = { text: 'The command was successfully parsed.', level: 2};
|
this.dialog.message = { text: this.SuccessfulParseText, level: 2};
|
||||||
} else if (result && !result.parseable) {
|
} else if (result && !result.parseable) {
|
||||||
this.dialog.message = { text: 'The command failed' };
|
this.dialog.message = { text: this.FailureParseText };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -139,13 +174,13 @@ export class JobStepDialog {
|
|||||||
.component();
|
.component();
|
||||||
this.nextButton = view.modelBuilder.button()
|
this.nextButton = view.modelBuilder.button()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: JobStepDialog.NextButtonText,
|
label: this.NextButtonText,
|
||||||
enabled: false,
|
enabled: false,
|
||||||
width: '80px'
|
width: '80px'
|
||||||
}).component();
|
}).component();
|
||||||
this.previousButton = view.modelBuilder.button()
|
this.previousButton = view.modelBuilder.button()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: JobStepDialog.PreviousButtonText,
|
label: this.PreviousButtonText,
|
||||||
enabled: false,
|
enabled: false,
|
||||||
width: '80px'
|
width: '80px'
|
||||||
}).component();
|
}).component();
|
||||||
@@ -157,10 +192,16 @@ export class JobStepDialog {
|
|||||||
.withProperties({
|
.withProperties({
|
||||||
}).component();
|
}).component();
|
||||||
this.nameTextBox.required = true;
|
this.nameTextBox.required = true;
|
||||||
|
this.nameTextBox.onTextChanged(() => {
|
||||||
|
if (this.nameTextBox.value.length > 0) {
|
||||||
|
this.dialog.message = null;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
this.typeDropdown = view.modelBuilder.dropDown()
|
this.typeDropdown = view.modelBuilder.dropDown()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
value: JobStepDialog.TSQLScript,
|
value: this.TSQLScript,
|
||||||
values: [JobStepDialog.TSQLScript]
|
values: [this.TSQLScript]
|
||||||
})
|
})
|
||||||
.component();
|
.component();
|
||||||
this.runAsDropdown = view.modelBuilder.dropDown()
|
this.runAsDropdown = view.modelBuilder.dropDown()
|
||||||
@@ -171,8 +212,8 @@ export class JobStepDialog {
|
|||||||
.component();
|
.component();
|
||||||
this.runAsDropdown.enabled = false;
|
this.runAsDropdown.enabled = false;
|
||||||
this.typeDropdown.onValueChanged((type) => {
|
this.typeDropdown.onValueChanged((type) => {
|
||||||
if (type.selected !== JobStepDialog.TSQLScript) {
|
if (type.selected !== this.TSQLScript) {
|
||||||
this.runAsDropdown.value = JobStepDialog.AgentServiceAccount;
|
this.runAsDropdown.value = this.AgentServiceAccount;
|
||||||
this.runAsDropdown.values = [this.runAsDropdown.value];
|
this.runAsDropdown.values = [this.runAsDropdown.value];
|
||||||
} else {
|
} else {
|
||||||
this.runAsDropdown.value = '';
|
this.runAsDropdown.value = '';
|
||||||
@@ -200,19 +241,19 @@ export class JobStepDialog {
|
|||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.nameTextBox,
|
component: this.nameTextBox,
|
||||||
title: 'Step name'
|
title: this.StepNameLabelString
|
||||||
}, {
|
}, {
|
||||||
component: this.typeDropdown,
|
component: this.typeDropdown,
|
||||||
title: 'Type'
|
title: this.TypeLabelString
|
||||||
}, {
|
}, {
|
||||||
component: this.runAsDropdown,
|
component: this.runAsDropdown,
|
||||||
title: 'Run as'
|
title: this.RunAsLabelString
|
||||||
}, {
|
}, {
|
||||||
component: this.databaseDropdown,
|
component: this.databaseDropdown,
|
||||||
title: 'Database'
|
title: this.DatabaseLabelString
|
||||||
}, {
|
}, {
|
||||||
component: this.commandTextBox,
|
component: this.commandTextBox,
|
||||||
title: 'Command',
|
title: this.CommandLabelString,
|
||||||
actions: [buttonContainer]
|
actions: [buttonContainer]
|
||||||
}], {
|
}], {
|
||||||
horizontal: false,
|
horizontal: false,
|
||||||
@@ -224,81 +265,57 @@ export class JobStepDialog {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
private createRunAsUserOptions(view) {
|
|
||||||
let userInputBox = view.modelBuilder.inputBox()
|
|
||||||
.withProperties({ inputType: 'text', width: '100px' }).component();
|
|
||||||
let viewButton = view.modelBuilder.button()
|
|
||||||
.withProperties({ label: '...', width: '20px' }).component();
|
|
||||||
let viewButtonContainer = view.modelBuilder.flexContainer()
|
|
||||||
.withLayout({ width: 100, textAlign: 'right' })
|
|
||||||
.withItems([viewButton], { flex: '1 1 50%' }).component();
|
|
||||||
let userInputBoxContainer = view.modelBuilder.flexContainer()
|
|
||||||
.withLayout({ width: 200, textAlign: 'left' })
|
|
||||||
.withItems([userInputBox], { flex: '1 1 50%' }).component();
|
|
||||||
let runAsUserContainer = view.modelBuilder.flexContainer()
|
|
||||||
.withLayout({ width: 200 })
|
|
||||||
.withItems([userInputBoxContainer, viewButtonContainer], { flex: '1 1 50%' })
|
|
||||||
.component();
|
|
||||||
let runAsUserForm = view.modelBuilder.formContainer()
|
|
||||||
.withFormItems([{
|
|
||||||
component: runAsUserContainer,
|
|
||||||
title: 'Run as user'
|
|
||||||
}], { horizontal: true, componentWidth: 200 }).component();
|
|
||||||
return runAsUserForm;
|
|
||||||
}
|
|
||||||
|
|
||||||
private createAdvancedTab() {
|
private createAdvancedTab() {
|
||||||
this.advancedTab.registerContent(async (view) => {
|
this.advancedTab.registerContent(async (view) => {
|
||||||
this.successActionDropdown = view.modelBuilder.dropDown()
|
this.successActionDropdown = view.modelBuilder.dropDown()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
value: JobStepDialog.NextStep,
|
width: '100%',
|
||||||
values: [JobStepDialog.NextStep, JobStepDialog.QuitJobReportingSuccess, JobStepDialog.QuitJobReportingFailure]
|
value: this.NextStep,
|
||||||
|
values: [this.NextStep, this.QuitJobReportingSuccess, this.QuitJobReportingFailure]
|
||||||
})
|
})
|
||||||
.component();
|
.component();
|
||||||
let retryFlexContainer = this.createRetryCounters(view);
|
let retryFlexContainer = this.createRetryCounters(view);
|
||||||
|
|
||||||
this.failureActionDropdown = view.modelBuilder.dropDown()
|
this.failureActionDropdown = view.modelBuilder.dropDown()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
value: JobStepDialog.QuitJobReportingFailure,
|
value: this.QuitJobReportingFailure,
|
||||||
values: [JobStepDialog.QuitJobReportingFailure, JobStepDialog.NextStep, JobStepDialog.QuitJobReportingSuccess]
|
values: [this.QuitJobReportingFailure, this.NextStep, this.QuitJobReportingSuccess]
|
||||||
})
|
})
|
||||||
.component();
|
.component();
|
||||||
let optionsGroup = this.createTSQLOptions(view);
|
let optionsGroup = this.createTSQLOptions(view);
|
||||||
let viewButton = view.modelBuilder.button()
|
|
||||||
.withProperties({ label: 'View', width: '50px' }).component();
|
|
||||||
viewButton.enabled = false;
|
|
||||||
this.logToTableCheckbox = view.modelBuilder.checkBox()
|
this.logToTableCheckbox = view.modelBuilder.checkBox()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: 'Log to table'
|
label: this.LogToTableLabel
|
||||||
}).component();
|
}).component();
|
||||||
let appendToExistingEntryInTableCheckbox = view.modelBuilder.checkBox()
|
let appendToExistingEntryInTableCheckbox = view.modelBuilder.checkBox()
|
||||||
.withProperties({ label: 'Append output to existing entry in table' }).component();
|
.withProperties({ label: this.AppendExistingTableEntryLabel }).component();
|
||||||
appendToExistingEntryInTableCheckbox.enabled = false;
|
appendToExistingEntryInTableCheckbox.enabled = false;
|
||||||
this.logToTableCheckbox.onChanged(e => {
|
this.logToTableCheckbox.onChanged(e => {
|
||||||
viewButton.enabled = e;
|
|
||||||
appendToExistingEntryInTableCheckbox.enabled = e;
|
appendToExistingEntryInTableCheckbox.enabled = e;
|
||||||
});
|
});
|
||||||
let appendCheckboxContainer = view.modelBuilder.groupContainer()
|
let appendCheckboxContainer = view.modelBuilder.groupContainer()
|
||||||
.withItems([appendToExistingEntryInTableCheckbox]).component();
|
.withItems([appendToExistingEntryInTableCheckbox]).component();
|
||||||
let logToTableContainer = view.modelBuilder.flexContainer()
|
let logToTableContainer = view.modelBuilder.flexContainer()
|
||||||
.withLayout({ flexFlow: 'row', justifyContent: 'space-between', width: 300 })
|
.withLayout({ flexFlow: 'row', justifyContent: 'space-between', width: 300 })
|
||||||
.withItems([this.logToTableCheckbox, viewButton]).component();
|
.withItems([this.logToTableCheckbox]).component();
|
||||||
let logStepOutputHistoryCheckbox = view.modelBuilder.checkBox()
|
let logStepOutputHistoryCheckbox = view.modelBuilder.checkBox()
|
||||||
.withProperties({ label: 'Include step output in history' }).component();
|
.withProperties({ label: this.IncludeStepOutputHistoryLabel }).component();
|
||||||
let runAsUserOptions = this.createRunAsUserOptions(view);
|
this.userInputBox = view.modelBuilder.inputBox()
|
||||||
|
.withProperties({ inputType: 'text', width: '100%' }).component();
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems(
|
.withFormItems(
|
||||||
[{
|
[{
|
||||||
component: this.successActionDropdown,
|
component: this.successActionDropdown,
|
||||||
title: JobStepDialog.SuccessAction
|
title: this.SuccessActionLabel
|
||||||
}, {
|
}, {
|
||||||
component: retryFlexContainer,
|
component: retryFlexContainer,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: this.failureActionDropdown,
|
component: this.failureActionDropdown,
|
||||||
title: JobStepDialog.FailureAction
|
title: this.FailureActionLabel
|
||||||
}, {
|
}, {
|
||||||
component: optionsGroup,
|
component: optionsGroup,
|
||||||
title: 'Transact-SQL script (T-SQL)'
|
title: this.TSQLScript
|
||||||
}, {
|
}, {
|
||||||
component: logToTableContainer,
|
component: logToTableContainer,
|
||||||
title: ''
|
title: ''
|
||||||
@@ -309,8 +326,8 @@ export class JobStepDialog {
|
|||||||
component: logStepOutputHistoryCheckbox,
|
component: logStepOutputHistoryCheckbox,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: runAsUserOptions,
|
component: this.userInputBox,
|
||||||
title: ''
|
title: this.RunAsUserLabel
|
||||||
}], {
|
}], {
|
||||||
componentWidth: 400
|
componentWidth: 400
|
||||||
}).component();
|
}).component();
|
||||||
@@ -325,22 +342,27 @@ export class JobStepDialog {
|
|||||||
this.retryAttemptsBox = view.modelBuilder.inputBox()
|
this.retryAttemptsBox = view.modelBuilder.inputBox()
|
||||||
.withValidation(component => component.value >= 0)
|
.withValidation(component => component.value >= 0)
|
||||||
.withProperties({
|
.withProperties({
|
||||||
inputType: 'number'
|
inputType: 'number',
|
||||||
|
width: '100%',
|
||||||
|
placeHolder: '0'
|
||||||
})
|
})
|
||||||
.component();
|
.component();
|
||||||
this.retryIntervalBox = view.modelBuilder.inputBox()
|
this.retryIntervalBox = view.modelBuilder.inputBox()
|
||||||
.withValidation(component => component.value >= 0)
|
.withValidation(component => component.value >= 0)
|
||||||
.withProperties({
|
.withProperties({
|
||||||
inputType: 'number'
|
inputType: 'number',
|
||||||
|
width: '100%',
|
||||||
|
placeHolder: '0'
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
let retryAttemptsContainer = view.modelBuilder.formContainer()
|
let retryAttemptsContainer = view.modelBuilder.formContainer()
|
||||||
.withFormItems(
|
.withFormItems(
|
||||||
[{
|
[{
|
||||||
component: this.retryAttemptsBox,
|
component: this.retryAttemptsBox,
|
||||||
title: 'Retry Attempts'
|
title: this.RetryAttemptsLabel
|
||||||
}], {
|
}], {
|
||||||
horizontal: false
|
horizontal: false,
|
||||||
|
componentWidth: '100%'
|
||||||
})
|
})
|
||||||
.component();
|
.component();
|
||||||
|
|
||||||
@@ -348,7 +370,7 @@ export class JobStepDialog {
|
|||||||
.withFormItems(
|
.withFormItems(
|
||||||
[{
|
[{
|
||||||
component: this.retryIntervalBox,
|
component: this.retryIntervalBox,
|
||||||
title: 'Retry Interval (minutes)'
|
title: this.RetryIntervalLabel
|
||||||
}], {
|
}], {
|
||||||
horizontal: false
|
horizontal: false
|
||||||
})
|
})
|
||||||
@@ -362,7 +384,7 @@ export class JobStepDialog {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private openFileBrowserDialog() {
|
private openFileBrowserDialog() {
|
||||||
let fileBrowserTitle = JobStepDialog.FileBrowserDialogTitle + `${this.server}`;
|
let fileBrowserTitle = this.FileBrowserDialogTitle + `${this.server}`;
|
||||||
this.fileBrowserDialog = sqlops.window.modelviewdialog.createDialog(fileBrowserTitle);
|
this.fileBrowserDialog = sqlops.window.modelviewdialog.createDialog(fileBrowserTitle);
|
||||||
let fileBrowserTab = sqlops.window.modelviewdialog.createTab('File Browser');
|
let fileBrowserTab = sqlops.window.modelviewdialog.createTab('File Browser');
|
||||||
this.fileBrowserDialog.content = [fileBrowserTab];
|
this.fileBrowserDialog.content = [fileBrowserTab];
|
||||||
@@ -379,8 +401,8 @@ export class JobStepDialog {
|
|||||||
});
|
});
|
||||||
this.fileTypeDropdown = view.modelBuilder.dropDown()
|
this.fileTypeDropdown = view.modelBuilder.dropDown()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
value: 'All Files (*)',
|
value: this.AllFilesLabelString,
|
||||||
values: ['All Files (*)']
|
values: [this.AllFilesLabelString]
|
||||||
})
|
})
|
||||||
.component();
|
.component();
|
||||||
this.fileBrowserNameBox = view.modelBuilder.inputBox()
|
this.fileBrowserNameBox = view.modelBuilder.inputBox()
|
||||||
@@ -392,13 +414,13 @@ export class JobStepDialog {
|
|||||||
title: ''
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
component: this.selectedPathTextBox,
|
component: this.selectedPathTextBox,
|
||||||
title: 'Selected path:'
|
title: this.SelectedPathLabelString
|
||||||
}, {
|
}, {
|
||||||
component: this.fileTypeDropdown,
|
component: this.fileTypeDropdown,
|
||||||
title: 'Files of type:'
|
title: this.FilesOfTypeLabelString
|
||||||
}, {
|
}, {
|
||||||
component: this.fileBrowserNameBox,
|
component: this.fileBrowserNameBox,
|
||||||
title: 'File name:'
|
title: this.FileNameLabelString
|
||||||
}
|
}
|
||||||
]).component();
|
]).component();
|
||||||
view.initializeModel(fileBrowserContainer);
|
view.initializeModel(fileBrowserContainer);
|
||||||
@@ -406,8 +428,8 @@ export class JobStepDialog {
|
|||||||
this.fileBrowserDialog.okButton.onClick(() => {
|
this.fileBrowserDialog.okButton.onClick(() => {
|
||||||
this.outputFileNameBox.value = path.join(path.dirname(this.selectedPathTextBox.value), this.fileBrowserNameBox.value);
|
this.outputFileNameBox.value = path.join(path.dirname(this.selectedPathTextBox.value), this.fileBrowserNameBox.value);
|
||||||
});
|
});
|
||||||
this.fileBrowserDialog.okButton.label = JobStepDialog.OkButtonText;
|
this.fileBrowserDialog.okButton.label = this.OkButtonText;
|
||||||
this.fileBrowserDialog.cancelButton.label = JobStepDialog.CancelButtonText;
|
this.fileBrowserDialog.cancelButton.label = this.CancelButtonText;
|
||||||
sqlops.window.modelviewdialog.openDialog(this.fileBrowserDialog);
|
sqlops.window.modelviewdialog.openDialog(this.fileBrowserDialog);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -417,21 +439,15 @@ export class JobStepDialog {
|
|||||||
this.outputFileBrowserButton.onDidClick(() => this.openFileBrowserDialog());
|
this.outputFileBrowserButton.onDidClick(() => this.openFileBrowserDialog());
|
||||||
this.outputFileNameBox = view.modelBuilder.inputBox()
|
this.outputFileNameBox = view.modelBuilder.inputBox()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
width: '150px',
|
width: 250,
|
||||||
inputType: 'text'
|
inputType: 'text'
|
||||||
}).component();
|
}).component();
|
||||||
let outputViewButton = view.modelBuilder.button()
|
|
||||||
.withProperties({
|
|
||||||
width: '50px',
|
|
||||||
label: 'View'
|
|
||||||
}).component();
|
|
||||||
outputViewButton.enabled = false;
|
|
||||||
let outputButtonContainer = view.modelBuilder.flexContainer()
|
let outputButtonContainer = view.modelBuilder.flexContainer()
|
||||||
.withLayout({
|
.withLayout({
|
||||||
flexFlow: 'row',
|
flexFlow: 'row',
|
||||||
textAlign: 'right',
|
textAlign: 'right',
|
||||||
width: 120
|
width: '100%'
|
||||||
}).withItems([this.outputFileBrowserButton, outputViewButton], { flex: '1 1 50%' }).component();
|
}).withItems([this.outputFileBrowserButton], { flex: '1 1 50%' }).component();
|
||||||
let outputFlexBox = view.modelBuilder.flexContainer()
|
let outputFlexBox = view.modelBuilder.flexContainer()
|
||||||
.withLayout({
|
.withLayout({
|
||||||
flexFlow: 'row',
|
flexFlow: 'row',
|
||||||
@@ -441,7 +457,7 @@ export class JobStepDialog {
|
|||||||
}).component();
|
}).component();
|
||||||
this.appendToExistingFileCheckbox = view.modelBuilder.checkBox()
|
this.appendToExistingFileCheckbox = view.modelBuilder.checkBox()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
label: 'Append output to existing file'
|
label: this.AppendOutputToFileLabel
|
||||||
}).component();
|
}).component();
|
||||||
this.appendToExistingFileCheckbox.enabled = false;
|
this.appendToExistingFileCheckbox.enabled = false;
|
||||||
this.outputFileNameBox.onTextChanged((input) => {
|
this.outputFileNameBox.onTextChanged((input) => {
|
||||||
@@ -454,15 +470,20 @@ export class JobStepDialog {
|
|||||||
let outputFileForm = view.modelBuilder.formContainer()
|
let outputFileForm = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: outputFlexBox,
|
component: outputFlexBox,
|
||||||
title: 'Output file'
|
title: this.OutputFileNameLabel
|
||||||
}, {
|
}, {
|
||||||
component: this.appendToExistingFileCheckbox,
|
component: this.appendToExistingFileCheckbox,
|
||||||
title: ''
|
title: ''
|
||||||
}], { horizontal: true, componentWidth: 200 }).component();
|
}], { horizontal: false, componentWidth: 200 }).component();
|
||||||
return outputFileForm;
|
return outputFileForm;
|
||||||
}
|
}
|
||||||
|
|
||||||
private async execute() {
|
protected execute() {
|
||||||
|
this.model.stepName = this.nameTextBox.value;
|
||||||
|
if (!this.model.stepName || this.model.stepName.length === 0) {
|
||||||
|
this.dialog.message = this.dialog.message = { text: this.BlankStepNameErrorText };
|
||||||
|
return;
|
||||||
|
}
|
||||||
this.model.jobName = this.jobName;
|
this.model.jobName = this.jobName;
|
||||||
this.model.id = this.stepId;
|
this.model.id = this.stepId;
|
||||||
this.model.server = this.server;
|
this.model.server = this.server;
|
||||||
@@ -471,12 +492,11 @@ export class JobStepDialog {
|
|||||||
this.model.databaseName = this.databaseDropdown.value as string;
|
this.model.databaseName = this.databaseDropdown.value as string;
|
||||||
this.model.script = this.commandTextBox.value;
|
this.model.script = this.commandTextBox.value;
|
||||||
this.model.successAction = this.successActionDropdown.value as string;
|
this.model.successAction = this.successActionDropdown.value as string;
|
||||||
this.model.retryAttempts = +this.retryAttemptsBox.value;
|
this.model.retryAttempts = this.retryAttemptsBox.value ? +this.retryAttemptsBox.value : 0;
|
||||||
this.model.retryInterval = +this.retryIntervalBox.value;
|
this.model.retryInterval = +this.retryIntervalBox.value ? +this.retryIntervalBox.value : 0;
|
||||||
this.model.failureAction = this.failureActionDropdown.value as string;
|
this.model.failureAction = this.failureActionDropdown.value as string;
|
||||||
this.model.outputFileName = this.outputFileNameBox.value;
|
this.model.outputFileName = this.outputFileNameBox.value;
|
||||||
this.model.appendToLogFile = this.appendToExistingFileCheckbox.checked;
|
this.model.appendToLogFile = this.appendToExistingFileCheckbox.checked;
|
||||||
await this.model.save();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public async openNewStepDialog() {
|
public async openNewStepDialog() {
|
||||||
|
|||||||
@@ -16,7 +16,8 @@ const localize = nls.loadMessageBundle();
|
|||||||
export class OperatorDialog extends AgentDialog<OperatorData> {
|
export class OperatorDialog extends AgentDialog<OperatorData> {
|
||||||
|
|
||||||
// Top level
|
// Top level
|
||||||
private static readonly DialogTitle: string = localize('createOperator.createOperator', 'Create Operator');
|
private static readonly CreateDialogTitle: string = localize('createOperator.createOperator', 'Create Operator');
|
||||||
|
private static readonly EditDialogTitle: string = localize('createOperator.editOperator', 'Edit Operator');
|
||||||
private static readonly GeneralTabText: string = localize('createOperator.General', 'General');
|
private static readonly GeneralTabText: string = localize('createOperator.General', 'General');
|
||||||
private static readonly NotificationsTabText: string = localize('createOperator.Notifications', 'Notifications');
|
private static readonly NotificationsTabText: string = localize('createOperator.Notifications', 'Notifications');
|
||||||
|
|
||||||
@@ -32,6 +33,9 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
private static readonly PagerFridayCheckBoxLabel: string = localize('createOperator.PagerFridayCheckBox', 'Friday ');
|
private static readonly PagerFridayCheckBoxLabel: string = localize('createOperator.PagerFridayCheckBox', 'Friday ');
|
||||||
private static readonly PagerSaturdayCheckBoxLabel: string = localize('createOperator.PagerSaturdayCheckBox', 'Saturday');
|
private static readonly PagerSaturdayCheckBoxLabel: string = localize('createOperator.PagerSaturdayCheckBox', 'Saturday');
|
||||||
private static readonly PagerSundayCheckBoxLabel: string = localize('createOperator.PagerSundayCheckBox', 'Sunday');
|
private static readonly PagerSundayCheckBoxLabel: string = localize('createOperator.PagerSundayCheckBox', 'Sunday');
|
||||||
|
private static readonly WorkdayBeginLabel: string = localize('createOperator.workdayBegin', 'Workday begin');
|
||||||
|
private static readonly WorkdayEndLabel: string = localize('createOperator.workdayEnd', 'Workday end');
|
||||||
|
private static readonly PagerDutyScheduleLabel: string = localize('createOperator.PagerDutySchedule', 'Pager on duty schdule');
|
||||||
|
|
||||||
// Notifications tab strings
|
// Notifications tab strings
|
||||||
private static readonly AlertsTableLabel: string = localize('createOperator.AlertListHeading', 'Alert list');
|
private static readonly AlertsTableLabel: string = localize('createOperator.AlertListHeading', 'Alert list');
|
||||||
@@ -65,8 +69,11 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
// Notification tab controls
|
// Notification tab controls
|
||||||
private alertsTable: sqlops.TableComponent;
|
private alertsTable: sqlops.TableComponent;
|
||||||
|
|
||||||
constructor(ownerUri: string) {
|
constructor(ownerUri: string, operatorInfo: sqlops.AgentOperatorInfo = undefined) {
|
||||||
super(ownerUri, new OperatorData(ownerUri), OperatorDialog.DialogTitle);
|
super(
|
||||||
|
ownerUri,
|
||||||
|
new OperatorData(ownerUri, operatorInfo),
|
||||||
|
operatorInfo ? OperatorDialog.EditDialogTitle : OperatorDialog.CreateDialogTitle);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async initializeDialog(dialog: sqlops.window.modelviewdialog.Dialog) {
|
protected async initializeDialog(dialog: sqlops.window.modelviewdialog.Dialog) {
|
||||||
@@ -174,13 +181,13 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
this.weekdayPagerStartTimeInput = view.modelBuilder.inputBox()
|
this.weekdayPagerStartTimeInput = view.modelBuilder.inputBox()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
inputType: 'time',
|
inputType: 'time',
|
||||||
placeHolder: '08:00:00'
|
placeHolder: '08:00:00',
|
||||||
}).component();
|
}).component();
|
||||||
this.weekdayPagerStartTimeInput.enabled = false;
|
this.weekdayPagerStartTimeInput.enabled = false;
|
||||||
let weekdayStartInputContainer = view.modelBuilder.formContainer()
|
let weekdayStartInputContainer = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.weekdayPagerStartTimeInput,
|
component: this.weekdayPagerStartTimeInput,
|
||||||
title: 'Workday begin'
|
title: OperatorDialog.WorkdayBeginLabel
|
||||||
}]).component();
|
}]).component();
|
||||||
|
|
||||||
this.weekdayPagerEndTimeInput = view.modelBuilder.inputBox()
|
this.weekdayPagerEndTimeInput = view.modelBuilder.inputBox()
|
||||||
@@ -192,7 +199,7 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
let weekdayEndInputContainer = view.modelBuilder.formContainer()
|
let weekdayEndInputContainer = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.weekdayPagerEndTimeInput,
|
component: this.weekdayPagerEndTimeInput,
|
||||||
title: 'Workday end'
|
title: OperatorDialog.WorkdayEndLabel
|
||||||
}]).component();
|
}]).component();
|
||||||
|
|
||||||
this.pagerFridayCheckBox = view.modelBuilder.checkBox()
|
this.pagerFridayCheckBox = view.modelBuilder.checkBox()
|
||||||
@@ -216,7 +223,8 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
let pagerFridayCheckboxContainer = view.modelBuilder.flexContainer()
|
let pagerFridayCheckboxContainer = view.modelBuilder.flexContainer()
|
||||||
.withLayout({
|
.withLayout({
|
||||||
flexFlow: 'row',
|
flexFlow: 'row',
|
||||||
alignItems: 'baseline'
|
alignItems: 'baseline',
|
||||||
|
width: '100%'
|
||||||
}).withItems([this.pagerFridayCheckBox, weekdayStartInputContainer, weekdayEndInputContainer])
|
}).withItems([this.pagerFridayCheckBox, weekdayStartInputContainer, weekdayEndInputContainer])
|
||||||
.component();
|
.component();
|
||||||
|
|
||||||
@@ -245,7 +253,7 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
let saturdayStartInputContainer = view.modelBuilder.formContainer()
|
let saturdayStartInputContainer = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.saturdayPagerStartTimeInput,
|
component: this.saturdayPagerStartTimeInput,
|
||||||
title: 'Workday begin'
|
title: OperatorDialog.WorkdayBeginLabel
|
||||||
}]).component();
|
}]).component();
|
||||||
|
|
||||||
this.saturdayPagerEndTimeInput = view.modelBuilder.inputBox()
|
this.saturdayPagerEndTimeInput = view.modelBuilder.inputBox()
|
||||||
@@ -257,7 +265,7 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
let saturdayEndInputContainer = view.modelBuilder.formContainer()
|
let saturdayEndInputContainer = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.saturdayPagerEndTimeInput,
|
component: this.saturdayPagerEndTimeInput,
|
||||||
title: 'Workday end'
|
title: OperatorDialog.WorkdayEndLabel
|
||||||
}]).component();
|
}]).component();
|
||||||
|
|
||||||
let pagerSaturdayCheckboxContainer = view.modelBuilder.flexContainer()
|
let pagerSaturdayCheckboxContainer = view.modelBuilder.flexContainer()
|
||||||
@@ -292,7 +300,7 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
let sundayStartInputContainer = view.modelBuilder.formContainer()
|
let sundayStartInputContainer = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.sundayPagerStartTimeInput,
|
component: this.sundayPagerStartTimeInput,
|
||||||
title: 'Workday begin'
|
title: OperatorDialog.WorkdayBeginLabel
|
||||||
}]).component();
|
}]).component();
|
||||||
|
|
||||||
this.sundayPagerEndTimeInput = view.modelBuilder.inputBox()
|
this.sundayPagerEndTimeInput = view.modelBuilder.inputBox()
|
||||||
@@ -304,7 +312,7 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
let sundayEndInputContainer = view.modelBuilder.formContainer()
|
let sundayEndInputContainer = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.sundayPagerEndTimeInput,
|
component: this.sundayPagerEndTimeInput,
|
||||||
title: 'Workday end'
|
title: OperatorDialog.WorkdayEndLabel
|
||||||
}]).component();
|
}]).component();
|
||||||
|
|
||||||
let pagerSundayCheckboxContainer = view.modelBuilder.flexContainer()
|
let pagerSundayCheckboxContainer = view.modelBuilder.flexContainer()
|
||||||
@@ -314,8 +322,21 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
}).withItems([this.pagerSundayCheckBox, sundayStartInputContainer, sundayEndInputContainer])
|
}).withItems([this.pagerSundayCheckBox, sundayStartInputContainer, sundayEndInputContainer])
|
||||||
.component();
|
.component();
|
||||||
|
|
||||||
let checkBoxContainer = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
|
component: this.nameTextBox,
|
||||||
|
title: OperatorDialog.NameLabel
|
||||||
|
}, {
|
||||||
|
component: this.enabledCheckBox,
|
||||||
|
title: ''
|
||||||
|
}, {
|
||||||
|
component: this.emailNameTextBox,
|
||||||
|
title: OperatorDialog.EmailNameTextLabel
|
||||||
|
}, {
|
||||||
|
component: this.pagerEmailNameTextBox,
|
||||||
|
title: OperatorDialog.PagerEmailNameTextLabel
|
||||||
|
}, {
|
||||||
|
components: [{
|
||||||
component: this.pagerMondayCheckBox,
|
component: this.pagerMondayCheckBox,
|
||||||
title: ''
|
title: ''
|
||||||
}, {
|
}, {
|
||||||
@@ -336,30 +357,8 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
}, {
|
}, {
|
||||||
component: pagerSundayCheckboxContainer,
|
component: pagerSundayCheckboxContainer,
|
||||||
title: ''
|
title: ''
|
||||||
}]).component();
|
}] ,
|
||||||
|
title: OperatorDialog.PagerDutyScheduleLabel
|
||||||
let pagerContainer = view.modelBuilder.flexContainer()
|
|
||||||
.withLayout({
|
|
||||||
flexFlow: 'row'
|
|
||||||
}).withItems([checkBoxContainer])
|
|
||||||
.component();
|
|
||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
|
||||||
.withFormItems([{
|
|
||||||
component: this.nameTextBox,
|
|
||||||
title: OperatorDialog.NameLabel
|
|
||||||
}, {
|
|
||||||
component: this.enabledCheckBox,
|
|
||||||
title: ''
|
|
||||||
}, {
|
|
||||||
component: this.emailNameTextBox,
|
|
||||||
title: OperatorDialog.EmailNameTextLabel
|
|
||||||
}, {
|
|
||||||
component: this.pagerEmailNameTextBox,
|
|
||||||
title: OperatorDialog.PagerEmailNameTextLabel
|
|
||||||
}, {
|
|
||||||
component: pagerContainer,
|
|
||||||
title: ''
|
|
||||||
}]).withLayout({ width: '100%' }).component();
|
}]).withLayout({ width: '100%' }).component();
|
||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
@@ -369,6 +368,10 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
private initializeNotificationTab() {
|
private initializeNotificationTab() {
|
||||||
this.notificationsTab.registerContent(async view => {
|
this.notificationsTab.registerContent(async view => {
|
||||||
|
|
||||||
|
let previewTag = view.modelBuilder.text()
|
||||||
|
.withProperties({
|
||||||
|
value: 'Feature Preview'
|
||||||
|
}).component();
|
||||||
this.alertsTable = view.modelBuilder.table()
|
this.alertsTable = view.modelBuilder.table()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
columns: [
|
||||||
@@ -382,6 +385,9 @@ export class OperatorDialog extends AgentDialog<OperatorData> {
|
|||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
|
component: previewTag,
|
||||||
|
title: ''
|
||||||
|
}, {
|
||||||
component: this.alertsTable,
|
component: this.alertsTable,
|
||||||
title: OperatorDialog.AlertsTableLabel
|
title: OperatorDialog.AlertsTableLabel
|
||||||
}]).withLayout({ width: '100%' }).component();
|
}]).withLayout({ width: '100%' }).component();
|
||||||
|
|||||||
@@ -4,18 +4,22 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
import * as nls from 'vscode-nls';
|
||||||
import * as sqlops from 'sqlops';
|
import * as sqlops from 'sqlops';
|
||||||
import * as vscode from 'vscode';
|
import * as vscode from 'vscode';
|
||||||
import { PickScheduleData } from '../data/pickScheduleData';
|
import { PickScheduleData } from '../data/pickScheduleData';
|
||||||
|
|
||||||
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
export class PickScheduleDialog {
|
export class PickScheduleDialog {
|
||||||
|
|
||||||
// TODO: localize
|
// TODO: localize
|
||||||
// Top level
|
// Top level
|
||||||
private readonly DialogTitle: string = 'Job Schedules';
|
private readonly DialogTitle: string = localize('pickSchedule.jobSchedules', 'Job Schedules');
|
||||||
private readonly OkButtonText: string = 'OK';
|
private readonly OkButtonText: string = localize('pickSchedule.ok', 'OK');
|
||||||
private readonly CancelButtonText: string = 'Cancel';
|
private readonly CancelButtonText: string = localize('pickSchedule.cancel', 'Cancel');
|
||||||
private readonly SchedulesTabText: string = 'Schedules';
|
private readonly ScheduleNameLabelText: string = localize('pickSchedule.scheduleName', 'Schedule Name');
|
||||||
|
private readonly SchedulesLabelText: string = localize('pickSchedule.schedules', 'Schedules');
|
||||||
|
|
||||||
// UI Components
|
// UI Components
|
||||||
private dialog: sqlops.window.modelviewdialog.Dialog;
|
private dialog: sqlops.window.modelviewdialog.Dialog;
|
||||||
@@ -38,7 +42,6 @@ export class PickScheduleDialog {
|
|||||||
this.dialog.cancelButton.onClick(async () => await this.cancel());
|
this.dialog.cancelButton.onClick(async () => await this.cancel());
|
||||||
this.dialog.okButton.label = this.OkButtonText;
|
this.dialog.okButton.label = this.OkButtonText;
|
||||||
this.dialog.cancelButton.label = this.CancelButtonText;
|
this.dialog.cancelButton.label = this.CancelButtonText;
|
||||||
|
|
||||||
sqlops.window.modelviewdialog.openDialog(this.dialog);
|
sqlops.window.modelviewdialog.openDialog(this.dialog);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -47,17 +50,17 @@ export class PickScheduleDialog {
|
|||||||
this.schedulesTable = view.modelBuilder.table()
|
this.schedulesTable = view.modelBuilder.table()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
columns: [
|
||||||
'Schedule Name'
|
this.ScheduleNameLabelText
|
||||||
],
|
],
|
||||||
data: [],
|
data: [],
|
||||||
height: 600,
|
height: '80em',
|
||||||
width: 400
|
width: '40em'
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.schedulesTable,
|
component: this.schedulesTable,
|
||||||
title: 'Schedules'
|
title: this.SchedulesLabelText
|
||||||
}]).withLayout({ width: '100%' }).component();
|
}]).withLayout({ width: '100%' }).component();
|
||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
|
|||||||
@@ -15,32 +15,60 @@ const localize = nls.loadMessageBundle();
|
|||||||
export class ProxyDialog extends AgentDialog<ProxyData> {
|
export class ProxyDialog extends AgentDialog<ProxyData> {
|
||||||
|
|
||||||
// Top level
|
// Top level
|
||||||
private static readonly DialogTitle: string = localize('createProxy.createAlert', 'Create Alert');
|
private static readonly CreateDialogTitle: string = localize('createProxy.createProxy', 'Create Proxy');
|
||||||
|
private static readonly EditDialogTitle: string = localize('createProxy.editProxy', 'Edit Proxy');
|
||||||
private static readonly GeneralTabText: string = localize('createProxy.General', 'General');
|
private static readonly GeneralTabText: string = localize('createProxy.General', 'General');
|
||||||
|
|
||||||
// General tab strings
|
// General tab strings
|
||||||
private static readonly ProxyNameTextBoxLabel: string = localize('createProxy.ProxyName', 'Proxy name');
|
private static readonly ProxyNameTextBoxLabel: string = localize('createProxy.ProxyName', 'Proxy name');
|
||||||
private static readonly CredentialNameTextBoxLabel: string = localize('createProxy.CredentialName', 'Credential name');
|
private static readonly CredentialNameTextBoxLabel: string = localize('createProxy.CredentialName', 'Credential name');
|
||||||
private static readonly DescriptionTextBoxLabel: string = localize('createProxy.Description', 'Description');
|
private static readonly DescriptionTextBoxLabel: string = localize('createProxy.Description', 'Description');
|
||||||
private static readonly SubsystemsTableLabel: string = localize('createProxy.Subsystems', 'Subsystems');
|
private static readonly SubsystemLabel: string = localize('createProxy.SubsystemName', 'Subsystem');
|
||||||
private static readonly SubsystemNameColumnLabel: string = localize('createProxy.SubsystemName', 'Subsystem');
|
private static readonly OperatingSystemLabel: string = localize('createProxy.OperatingSystem', 'Operating system (CmdExec)');
|
||||||
|
private static readonly ReplicationSnapshotLabel: string = localize('createProxy.ReplicationSnapshot', 'Replication Snapshot');
|
||||||
|
private static readonly ReplicationTransactionLogLabel: string = localize('createProxy.ReplicationTransactionLog', 'Replication Transaction-Log Reader');
|
||||||
|
private static readonly ReplicationDistributorLabel: string = localize('createProxy.ReplicationDistributor', 'Replication Distributor');
|
||||||
|
private static readonly ReplicationMergeLabel: string = localize('createProxy.ReplicationMerge', 'Replication Merge');
|
||||||
|
private static readonly ReplicationQueueReaderLabel: string = localize('createProxy.ReplicationQueueReader', 'Replication Queue Reader');
|
||||||
|
private static readonly SSASQueryLabel: string = localize('createProxy.SSASQueryLabel', 'SQL Server Analysis Services Query');
|
||||||
|
private static readonly SSASCommandLabel: string = localize('createProxy.SSASCommandLabel', 'SQL Server Analysis Services Command');
|
||||||
|
private static readonly SSISPackageLabel: string = localize('createProxy.SSISPackage', 'SQL Server Integration Services Package');
|
||||||
|
private static readonly PowerShellLabel: string = localize('createProxy.PowerShell', 'PowerShell');
|
||||||
|
private static readonly SubSystemHeadingLabel: string = localize('createProxy.subSystemHeading', 'Active to the following subsytems');
|
||||||
|
|
||||||
// UI Components
|
// UI Components
|
||||||
private generalTab: sqlops.window.modelviewdialog.DialogTab;
|
private generalTab: sqlops.window.modelviewdialog.DialogTab;
|
||||||
|
|
||||||
// General tab controls
|
// General tab controls
|
||||||
private proxyNameTextBox: sqlops.InputBoxComponent;
|
private proxyNameTextBox: sqlops.InputBoxComponent;
|
||||||
private credentialNameTextBox: sqlops.InputBoxComponent;
|
private credentialNameDropDown: sqlops.DropDownComponent;
|
||||||
private descriptionTextBox: sqlops.InputBoxComponent;
|
private descriptionTextBox: sqlops.InputBoxComponent;
|
||||||
private subsystemsTable: sqlops.TableComponent;
|
private subsystemCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private operatingSystemCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private replicationSnapshotCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private replicationTransactionLogCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private replicationDistributorCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private replicationMergeCheckbox: sqlops.CheckBoxComponent;
|
||||||
|
private replicationQueueReaderCheckbox: sqlops.CheckBoxComponent;
|
||||||
|
private sqlQueryCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private sqlCommandCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
private sqlIntegrationServicesPackageCheckbox: sqlops.CheckBoxComponent;
|
||||||
|
private powershellCheckBox: sqlops.CheckBoxComponent;
|
||||||
|
|
||||||
constructor(ownerUri: string) {
|
private credentials: sqlops.CredentialInfo[];
|
||||||
super(ownerUri, new ProxyData(ownerUri), ProxyDialog.DialogTitle);
|
|
||||||
|
constructor(ownerUri: string, proxyInfo: sqlops.AgentProxyInfo = undefined, credentials: sqlops.CredentialInfo[]) {
|
||||||
|
super(
|
||||||
|
ownerUri,
|
||||||
|
new ProxyData(ownerUri, proxyInfo),
|
||||||
|
proxyInfo ? ProxyDialog.EditDialogTitle : ProxyDialog.CreateDialogTitle);
|
||||||
|
this.credentials = credentials;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected async initializeDialog(dialog: sqlops.window.modelviewdialog.Dialog) {
|
protected async initializeDialog(dialog: sqlops.window.modelviewdialog.Dialog) {
|
||||||
this.generalTab = sqlops.window.modelviewdialog.createTab(ProxyDialog.GeneralTabText);
|
this.generalTab = sqlops.window.modelviewdialog.createTab(ProxyDialog.GeneralTabText);
|
||||||
|
|
||||||
|
|
||||||
this.initializeGeneralTab();
|
this.initializeGeneralTab();
|
||||||
|
|
||||||
this.dialog.content = [this.generalTab];
|
this.dialog.content = [this.generalTab];
|
||||||
@@ -49,43 +77,143 @@ export class ProxyDialog extends AgentDialog<ProxyData> {
|
|||||||
private initializeGeneralTab() {
|
private initializeGeneralTab() {
|
||||||
this.generalTab.registerContent(async view => {
|
this.generalTab.registerContent(async view => {
|
||||||
|
|
||||||
this.proxyNameTextBox = view.modelBuilder.inputBox().component();
|
this.proxyNameTextBox = view.modelBuilder.inputBox()
|
||||||
|
.withProperties({width: 420})
|
||||||
|
.component();
|
||||||
|
|
||||||
this.credentialNameTextBox = view.modelBuilder.inputBox().component();
|
this.credentialNameDropDown = view.modelBuilder.dropDown()
|
||||||
|
|
||||||
this.descriptionTextBox = view.modelBuilder.inputBox().component();
|
|
||||||
|
|
||||||
this.subsystemsTable = view.modelBuilder.table()
|
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
width: 432,
|
||||||
ProxyDialog.SubsystemNameColumnLabel
|
value: '',
|
||||||
],
|
editable: true,
|
||||||
data: [],
|
values: this.credentials.length > 0 ? this.credentials.map(c => c.name) : ['']
|
||||||
height: 500
|
})
|
||||||
|
.component();
|
||||||
|
|
||||||
|
this.descriptionTextBox = view.modelBuilder.inputBox()
|
||||||
|
.withProperties({
|
||||||
|
width: 420,
|
||||||
|
multiline: true,
|
||||||
|
height: 300
|
||||||
|
})
|
||||||
|
.component();
|
||||||
|
|
||||||
|
this.subsystemCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.SubsystemLabel
|
||||||
}).component();
|
}).component();
|
||||||
|
|
||||||
|
this.subsystemCheckBox.onChanged(() => {
|
||||||
|
if (this.subsystemCheckBox.checked) {
|
||||||
|
this.operatingSystemCheckBox.checked = true;
|
||||||
|
this.replicationSnapshotCheckBox.checked = true;
|
||||||
|
this.replicationTransactionLogCheckBox.checked = true;
|
||||||
|
this.replicationDistributorCheckBox.checked = true;
|
||||||
|
this.replicationMergeCheckbox.checked = true;
|
||||||
|
this.replicationQueueReaderCheckbox.checked = true;
|
||||||
|
this.sqlQueryCheckBox.checked = true;
|
||||||
|
this.sqlCommandCheckBox.checked = true;
|
||||||
|
this.sqlIntegrationServicesPackageCheckbox.checked = true;
|
||||||
|
this.powershellCheckBox.checked = true;
|
||||||
|
} else {
|
||||||
|
this.operatingSystemCheckBox.checked = false;
|
||||||
|
this.replicationSnapshotCheckBox.checked = false;
|
||||||
|
this.replicationTransactionLogCheckBox.checked = false;
|
||||||
|
this.replicationDistributorCheckBox.checked = false;
|
||||||
|
this.replicationMergeCheckbox.checked = false;
|
||||||
|
this.replicationQueueReaderCheckbox.checked = false;
|
||||||
|
this.sqlQueryCheckBox.checked = false;
|
||||||
|
this.sqlCommandCheckBox.checked = false;
|
||||||
|
this.sqlIntegrationServicesPackageCheckbox.checked = false;
|
||||||
|
this.powershellCheckBox.checked = false;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
this.operatingSystemCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.OperatingSystemLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.replicationSnapshotCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.ReplicationSnapshotLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.replicationTransactionLogCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.ReplicationTransactionLogLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.replicationDistributorCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.ReplicationDistributorLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.replicationMergeCheckbox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.ReplicationMergeLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.replicationQueueReaderCheckbox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.ReplicationQueueReaderLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.sqlQueryCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.SSASQueryLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.sqlCommandCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.SSASCommandLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.sqlIntegrationServicesPackageCheckbox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.SSISPackageLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
this.powershellCheckBox = view.modelBuilder.checkBox()
|
||||||
|
.withProperties({
|
||||||
|
label: ProxyDialog.PowerShellLabel
|
||||||
|
}).component();
|
||||||
|
|
||||||
|
let checkBoxContainer = view.modelBuilder.groupContainer()
|
||||||
|
.withItems([this.operatingSystemCheckBox, this.replicationSnapshotCheckBox,
|
||||||
|
this.replicationTransactionLogCheckBox, this.replicationDistributorCheckBox, this.replicationMergeCheckbox,
|
||||||
|
this.replicationQueueReaderCheckbox, this.sqlQueryCheckBox, this.sqlCommandCheckBox, this.sqlIntegrationServicesPackageCheckbox,
|
||||||
|
this.powershellCheckBox])
|
||||||
|
.component();
|
||||||
|
|
||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.proxyNameTextBox,
|
component: this.proxyNameTextBox,
|
||||||
title: ProxyDialog.ProxyNameTextBoxLabel
|
title: ProxyDialog.ProxyNameTextBoxLabel
|
||||||
}, {
|
}, {
|
||||||
component: this.credentialNameTextBox,
|
component: this.credentialNameDropDown,
|
||||||
title: ProxyDialog.CredentialNameTextBoxLabel
|
title: ProxyDialog.CredentialNameTextBoxLabel
|
||||||
}, {
|
}, {
|
||||||
component: this.descriptionTextBox,
|
component: this.descriptionTextBox,
|
||||||
title: ProxyDialog.DescriptionTextBoxLabel
|
title: ProxyDialog.DescriptionTextBoxLabel
|
||||||
}, {
|
}]).withLayout({ width: 420 }).component();
|
||||||
component: this.subsystemsTable,
|
|
||||||
title: ProxyDialog.SubsystemsTableLabel
|
|
||||||
}]).withLayout({ width: '100%' }).component();
|
|
||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
|
|
||||||
|
this.proxyNameTextBox.value = this.model.accountName;
|
||||||
|
this.credentialNameDropDown.value = this.model.credentialName;
|
||||||
|
this.descriptionTextBox.value = this.model.description;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
protected updateModel() {
|
protected updateModel() {
|
||||||
this.model.accountName = this.proxyNameTextBox.value;
|
this.model.accountName = this.proxyNameTextBox.value;
|
||||||
this.model.credentialName = this.credentialNameTextBox.value;
|
this.model.credentialName = this.credentialNameDropDown.value as string;
|
||||||
|
this.model.credentialId = this.credentials.find(
|
||||||
|
c => c.name === this.model.credentialName).id;
|
||||||
|
this.model.credentialIdentity = this.credentials.find(
|
||||||
|
c => c.name === this.model.credentialName).identity;
|
||||||
this.model.description = this.descriptionTextBox.value;
|
this.model.description = this.descriptionTextBox.value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,17 +4,21 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
import * as nls from 'vscode-nls';
|
||||||
import * as sqlops from 'sqlops';
|
import * as sqlops from 'sqlops';
|
||||||
import * as vscode from 'vscode';
|
import * as vscode from 'vscode';
|
||||||
import { ScheduleData } from '../data/scheduleData';
|
import { ScheduleData } from '../data/scheduleData';
|
||||||
|
|
||||||
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
export class ScheduleDialog {
|
export class ScheduleDialog {
|
||||||
|
|
||||||
// Top level
|
// Top level
|
||||||
private readonly DialogTitle: string = 'New Schedule';
|
private readonly DialogTitle: string = localize('scheduleDialog.newSchedule', 'New Schedule');
|
||||||
private readonly OkButtonText: string = 'OK';
|
private readonly OkButtonText: string = localize('scheduleDialog.ok', 'OK');
|
||||||
private readonly CancelButtonText: string = 'Cancel';
|
private readonly CancelButtonText: string = localize('scheduleDialog.cancel', 'Cancel');
|
||||||
|
private readonly ScheduleNameText: string = localize('scheduleDialog.scheduleName', 'Schedule Name');
|
||||||
|
private readonly SchedulesLabelText: string = localize('scheduleDialog.schedules', 'Schedules');
|
||||||
|
|
||||||
// UI Components
|
// UI Components
|
||||||
private dialog: sqlops.window.modelviewdialog.Dialog;
|
private dialog: sqlops.window.modelviewdialog.Dialog;
|
||||||
@@ -46,7 +50,7 @@ export class ScheduleDialog {
|
|||||||
this.schedulesTable = view.modelBuilder.table()
|
this.schedulesTable = view.modelBuilder.table()
|
||||||
.withProperties({
|
.withProperties({
|
||||||
columns: [
|
columns: [
|
||||||
'Schedule Name'
|
this.ScheduleNameText
|
||||||
],
|
],
|
||||||
data: [],
|
data: [],
|
||||||
height: 600,
|
height: 600,
|
||||||
@@ -56,7 +60,7 @@ export class ScheduleDialog {
|
|||||||
let formModel = view.modelBuilder.formContainer()
|
let formModel = view.modelBuilder.formContainer()
|
||||||
.withFormItems([{
|
.withFormItems([{
|
||||||
component: this.schedulesTable,
|
component: this.schedulesTable,
|
||||||
title: 'Schedules'
|
title: this.SchedulesLabelText
|
||||||
}]).withLayout({ width: '100%' }).component();
|
}]).withLayout({ width: '100%' }).component();
|
||||||
|
|
||||||
await view.initializeModel(formModel);
|
await view.initializeModel(formModel);
|
||||||
|
|||||||
@@ -3,6 +3,8 @@
|
|||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
|
import * as nls from 'vscode-nls';
|
||||||
import * as sqlops from 'sqlops';
|
import * as sqlops from 'sqlops';
|
||||||
import * as vscode from 'vscode';
|
import * as vscode from 'vscode';
|
||||||
import { AlertDialog } from './dialogs/alertDialog';
|
import { AlertDialog } from './dialogs/alertDialog';
|
||||||
@@ -12,6 +14,8 @@ import { ProxyDialog } from './dialogs/proxyDialog';
|
|||||||
import { JobStepDialog } from './dialogs/jobStepDialog';
|
import { JobStepDialog } from './dialogs/jobStepDialog';
|
||||||
import { PickScheduleDialog } from './dialogs/pickScheduleDialog';
|
import { PickScheduleDialog } from './dialogs/pickScheduleDialog';
|
||||||
|
|
||||||
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The main controller class that initializes the extension
|
* The main controller class that initializes the extension
|
||||||
*/
|
*/
|
||||||
@@ -23,12 +27,17 @@ export class MainController {
|
|||||||
this._context = context;
|
this._context = context;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static showNotYetImplemented(): void {
|
||||||
|
vscode.window.showInformationMessage(
|
||||||
|
localize('mainController.notImplemented', "This feature is under development. Check-out the latest insiders build if you'd like to try out the most recent changes!"));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Activates the extension
|
* Activates the extension
|
||||||
*/
|
*/
|
||||||
public activate(): void {
|
public activate(): void {
|
||||||
vscode.commands.registerCommand('agent.openCreateJobDialog', (ownerUri: string) => {
|
vscode.commands.registerCommand('agent.openJobDialog', (ownerUri: string, jobInfo: sqlops.AgentJobInfo) => {
|
||||||
let dialog = new JobDialog(ownerUri);
|
let dialog = new JobDialog(ownerUri, jobInfo);
|
||||||
dialog.openDialog();
|
dialog.openDialog();
|
||||||
});
|
});
|
||||||
vscode.commands.registerCommand('agent.openNewStepDialog', (ownerUri: string, jobId: string, server: string, stepId: number) => {
|
vscode.commands.registerCommand('agent.openNewStepDialog', (ownerUri: string, jobId: string, server: string, stepId: number) => {
|
||||||
@@ -39,17 +48,19 @@ export class MainController {
|
|||||||
let dialog = new PickScheduleDialog(ownerUri);
|
let dialog = new PickScheduleDialog(ownerUri);
|
||||||
dialog.showDialog();
|
dialog.showDialog();
|
||||||
});
|
});
|
||||||
vscode.commands.registerCommand('agent.openAlertDialog', (ownerUri: string, alertInfo: sqlops.AgentAlertInfo) => {
|
vscode.commands.registerCommand('agent.openAlertDialog', (ownerUri: string, alertInfo: sqlops.AgentAlertInfo, jobs: string[]) => {
|
||||||
let dialog = new AlertDialog(ownerUri, alertInfo);
|
let dialog = new AlertDialog(ownerUri, alertInfo, jobs);
|
||||||
dialog.openDialog();
|
dialog.openDialog();
|
||||||
});
|
});
|
||||||
vscode.commands.registerCommand('agent.openCreateOperatorDialog', (ownerUri: string) => {
|
vscode.commands.registerCommand('agent.openOperatorDialog', (ownerUri: string, operatorInfo: sqlops.AgentOperatorInfo) => {
|
||||||
let dialog = new OperatorDialog(ownerUri);
|
let dialog = new OperatorDialog(ownerUri, operatorInfo);
|
||||||
dialog.openDialog();
|
dialog.openDialog();
|
||||||
});
|
});
|
||||||
vscode.commands.registerCommand('agent.openCreateProxyDialog', (ownerUri: string) => {
|
vscode.commands.registerCommand('agent.openProxyDialog', (ownerUri: string, proxyInfo: sqlops.AgentProxyInfo, credentials: sqlops.CredentialInfo[]) => {
|
||||||
let dialog = new ProxyDialog(ownerUri);
|
//@TODO: reenable create proxy after snapping July release (7/14/18)
|
||||||
dialog.openDialog();
|
// let dialog = new ProxyDialog(ownerUri, proxyInfo, credentials);
|
||||||
|
// dialog.openDialog();
|
||||||
|
MainController.showNotYetImplemented();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*---------------------------------------------------------------------------------------------
|
/*---------------------------------------------------------------------------------------------
|
||||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import * as assert from 'assert';
|
import * as assert from 'assert';
|
||||||
@@ -15,7 +15,7 @@ const testOwnerUri = 'agent://testuri';
|
|||||||
suite('Agent extension', () => {
|
suite('Agent extension', () => {
|
||||||
test('Create Job Data', async () => {
|
test('Create Job Data', async () => {
|
||||||
let testAgentService = new TestAgentService();
|
let testAgentService = new TestAgentService();
|
||||||
let data = new JobData(testOwnerUri, testAgentService);
|
let data = new JobData(testOwnerUri, undefined, testAgentService);
|
||||||
data.save();
|
data.save();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*---------------------------------------------------------------------------------------------
|
/*---------------------------------------------------------------------------------------------
|
||||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
|
||||||
@@ -86,6 +86,11 @@ export class TestAgentService implements sqlops.AgentServicesProvider {
|
|||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Agent Credential method
|
||||||
|
getCredentials(ownerUri: string): Thenable<sqlops.GetCredentialsResult> {
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
|
||||||
// Job Schedule management methods
|
// Job Schedule management methods
|
||||||
getJobSchedules(ownerUri: string): Thenable<sqlops.AgentJobSchedulesResult> {
|
getJobSchedules(ownerUri: string): Thenable<sqlops.AgentJobSchedulesResult> {
|
||||||
return undefined;
|
return undefined;
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
"If you want to provide a fix or improvement, please create a pull request against the original repository.",
|
"If you want to provide a fix or improvement, please create a pull request against the original repository.",
|
||||||
"Once accepted there, we are happy to receive an update request."
|
"Once accepted there, we are happy to receive an update request."
|
||||||
],
|
],
|
||||||
"version": "https://github.com/mmims/language-batchfile/commit/6235c491be4dff49cd3966b50142874d7f79580a",
|
"version": "https://github.com/mmims/language-batchfile/commit/4b67596631b4ecd2c89c2ec1b2e08a6623438903",
|
||||||
"name": "Batch File",
|
"name": "Batch File",
|
||||||
"scopeName": "source.batchfile",
|
"scopeName": "source.batchfile",
|
||||||
"patterns": [
|
"patterns": [
|
||||||
@@ -163,12 +163,6 @@
|
|||||||
"end": "(?=$\\n|[&|><)])",
|
"end": "(?=$\\n|[&|><)])",
|
||||||
"name": "meta.expression.set.batchfile",
|
"name": "meta.expression.set.batchfile",
|
||||||
"patterns": [
|
"patterns": [
|
||||||
{
|
|
||||||
"include": "#command_set_inside_arithmetic"
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"include": "#command_set_group"
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"begin": "\"",
|
"begin": "\"",
|
||||||
"beginCaptures": {
|
"beginCaptures": {
|
||||||
@@ -194,6 +188,12 @@
|
|||||||
"include": "#variables"
|
"include": "#variables"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"include": "#command_set_inside_arithmetic"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"include": "#command_set_group"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
@@ -266,8 +266,15 @@
|
|||||||
"command_set_operators": {
|
"command_set_operators": {
|
||||||
"patterns": [
|
"patterns": [
|
||||||
{
|
{
|
||||||
"match": "\\+\\=|\\-\\=|\\*\\=|/\\=|%%\\=|&\\=|\\|\\=|\\^\\=|<<\\=|>>\\=",
|
"match": "([^ ]*)(\\+\\=|\\-\\=|\\*\\=|\\/\\=|%%\\=|&\\=|\\|\\=|\\^\\=|<<\\=|>>\\=)",
|
||||||
|
"captures": {
|
||||||
|
"1": {
|
||||||
|
"name": "variable.other.readwrite.batchfile"
|
||||||
|
},
|
||||||
|
"2": {
|
||||||
"name": "keyword.operator.assignment.augmented.batchfile"
|
"name": "keyword.operator.assignment.augmented.batchfile"
|
||||||
|
}
|
||||||
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"match": "\\+|\\-|/|\\*|%%|\\||&|\\^|<<|>>|~",
|
"match": "\\+|\\-|/|\\*|%%|\\||&|\\^|<<|>>|~",
|
||||||
@@ -278,9 +285,16 @@
|
|||||||
"name": "keyword.operator.logical.batchfile"
|
"name": "keyword.operator.logical.batchfile"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"match": "=",
|
"match": "([^ ][^=]*)(=)",
|
||||||
|
"captures": {
|
||||||
|
"1": {
|
||||||
|
"name": "variable.other.readwrite.batchfile"
|
||||||
|
},
|
||||||
|
"2": {
|
||||||
"name": "keyword.operator.assignment.batchfile"
|
"name": "keyword.operator.assignment.batchfile"
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
"command_set_strings": {
|
"command_set_strings": {
|
||||||
|
|||||||
@@ -3,10 +3,10 @@
|
|||||||
"c": "@",
|
"c": "@",
|
||||||
"t": "source.batchfile keyword.operator.at.batchfile",
|
"t": "source.batchfile keyword.operator.at.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.operator: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.operator: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.operator: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.operator: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.operator: #D4D4D4"
|
"hc_black": "keyword.operator: #D4D4D4"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -14,10 +14,10 @@
|
|||||||
"c": "echo",
|
"c": "echo",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -25,10 +25,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -36,10 +36,10 @@
|
|||||||
"c": "off",
|
"c": "off",
|
||||||
"t": "source.batchfile keyword.other.special-method.batchfile",
|
"t": "source.batchfile keyword.other.special-method.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -47,10 +47,10 @@
|
|||||||
"c": "setlocal",
|
"c": "setlocal",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -58,10 +58,10 @@
|
|||||||
"c": "title",
|
"c": "title",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -69,10 +69,10 @@
|
|||||||
"c": " VSCode Dev",
|
"c": " VSCode Dev",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -80,10 +80,10 @@
|
|||||||
"c": "pushd",
|
"c": "pushd",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -91,10 +91,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -102,10 +102,10 @@
|
|||||||
"c": "%",
|
"c": "%",
|
||||||
"t": "source.batchfile punctuation.definition.variable.batchfile",
|
"t": "source.batchfile punctuation.definition.variable.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -113,10 +113,10 @@
|
|||||||
"c": "~dp0",
|
"c": "~dp0",
|
||||||
"t": "source.batchfile variable.parameter.batchfile",
|
"t": "source.batchfile variable.parameter.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "variable: #9CDCFE",
|
"dark_plus": null,
|
||||||
"light_plus": "variable: #001080",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "variable: #9CDCFE"
|
"hc_black": "variable: #9CDCFE"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -124,10 +124,10 @@
|
|||||||
"c": "\\..",
|
"c": "\\..",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -135,10 +135,10 @@
|
|||||||
"c": "::",
|
"c": "::",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -146,10 +146,10 @@
|
|||||||
"c": " Node modules",
|
"c": " Node modules",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -157,10 +157,10 @@
|
|||||||
"c": "if",
|
"c": "if",
|
||||||
"t": "source.batchfile keyword.control.conditional.batchfile",
|
"t": "source.batchfile keyword.control.conditional.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.control: #C586C0",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.control: #AF00DB",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.control: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.control: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.control: #C586C0"
|
"hc_black": "keyword.control: #C586C0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -168,10 +168,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -179,10 +179,10 @@
|
|||||||
"c": "not",
|
"c": "not",
|
||||||
"t": "source.batchfile keyword.operator.logical.batchfile",
|
"t": "source.batchfile keyword.operator.logical.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.operator: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.operator: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.operator: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.operator: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.operator: #D4D4D4"
|
"hc_black": "keyword.operator: #D4D4D4"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -190,10 +190,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -201,10 +201,10 @@
|
|||||||
"c": "exist",
|
"c": "exist",
|
||||||
"t": "source.batchfile keyword.other.special-method.batchfile",
|
"t": "source.batchfile keyword.other.special-method.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -212,10 +212,10 @@
|
|||||||
"c": " node_modules ",
|
"c": " node_modules ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -223,10 +223,10 @@
|
|||||||
"c": "call",
|
"c": "call",
|
||||||
"t": "source.batchfile keyword.control.statement.batchfile",
|
"t": "source.batchfile keyword.control.statement.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.control: #C586C0",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.control: #AF00DB",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.control: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.control: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.control: #C586C0"
|
"hc_black": "keyword.control: #C586C0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -234,10 +234,10 @@
|
|||||||
"c": " .\\scripts\\npm.bat install",
|
"c": " .\\scripts\\npm.bat install",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -245,10 +245,10 @@
|
|||||||
"c": "::",
|
"c": "::",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -256,10 +256,10 @@
|
|||||||
"c": " Get electron",
|
"c": " Get electron",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -267,10 +267,10 @@
|
|||||||
"c": "node .\\node_modules\\gulp\\bin\\gulp.js electron",
|
"c": "node .\\node_modules\\gulp\\bin\\gulp.js electron",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -278,10 +278,10 @@
|
|||||||
"c": "::",
|
"c": "::",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -289,10 +289,10 @@
|
|||||||
"c": " Build",
|
"c": " Build",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -300,10 +300,10 @@
|
|||||||
"c": "if",
|
"c": "if",
|
||||||
"t": "source.batchfile keyword.control.conditional.batchfile",
|
"t": "source.batchfile keyword.control.conditional.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.control: #C586C0",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.control: #AF00DB",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.control: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.control: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.control: #C586C0"
|
"hc_black": "keyword.control: #C586C0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -311,10 +311,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -322,10 +322,10 @@
|
|||||||
"c": "not",
|
"c": "not",
|
||||||
"t": "source.batchfile keyword.operator.logical.batchfile",
|
"t": "source.batchfile keyword.operator.logical.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.operator: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.operator: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.operator: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.operator: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.operator: #D4D4D4"
|
"hc_black": "keyword.operator: #D4D4D4"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -333,10 +333,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -344,10 +344,10 @@
|
|||||||
"c": "exist",
|
"c": "exist",
|
||||||
"t": "source.batchfile keyword.other.special-method.batchfile",
|
"t": "source.batchfile keyword.other.special-method.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -355,10 +355,10 @@
|
|||||||
"c": " out node .\\node_modules\\gulp\\bin\\gulp.js compile",
|
"c": " out node .\\node_modules\\gulp\\bin\\gulp.js compile",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -366,10 +366,10 @@
|
|||||||
"c": "::",
|
"c": "::",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile punctuation.definition.comment.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -377,10 +377,10 @@
|
|||||||
"c": " Configuration",
|
"c": " Configuration",
|
||||||
"t": "source.batchfile comment.line.colon.batchfile",
|
"t": "source.batchfile comment.line.colon.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "comment: #608B4E",
|
"dark_plus": null,
|
||||||
"light_plus": "comment: #008000",
|
"light_plus": null,
|
||||||
"dark_vs": "comment: #608B4E",
|
"dark_vs": null,
|
||||||
"light_vs": "comment: #008000",
|
"light_vs": null,
|
||||||
"hc_black": "comment: #7CA668"
|
"hc_black": "comment: #7CA668"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -388,10 +388,10 @@
|
|||||||
"c": "set",
|
"c": "set",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -399,10 +399,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -410,10 +410,10 @@
|
|||||||
"c": "NODE_ENV",
|
"c": "NODE_ENV",
|
||||||
"t": "source.batchfile variable.other.readwrite.batchfile",
|
"t": "source.batchfile variable.other.readwrite.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "variable: #9CDCFE",
|
"dark_plus": null,
|
||||||
"light_plus": "variable: #001080",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "variable: #9CDCFE"
|
"hc_black": "variable: #9CDCFE"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -421,10 +421,10 @@
|
|||||||
"c": "=",
|
"c": "=",
|
||||||
"t": "source.batchfile keyword.operator.assignment.batchfile",
|
"t": "source.batchfile keyword.operator.assignment.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.operator: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.operator: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.operator: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.operator: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.operator: #D4D4D4"
|
"hc_black": "keyword.operator: #D4D4D4"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -432,10 +432,10 @@
|
|||||||
"c": "development",
|
"c": "development",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -443,10 +443,10 @@
|
|||||||
"c": "call",
|
"c": "call",
|
||||||
"t": "source.batchfile keyword.control.statement.batchfile",
|
"t": "source.batchfile keyword.control.statement.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword.control: #C586C0",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword.control: #AF00DB",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword.control: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword.control: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword.control: #C586C0"
|
"hc_black": "keyword.control: #C586C0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -454,10 +454,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -465,10 +465,10 @@
|
|||||||
"c": "echo",
|
"c": "echo",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -476,10 +476,10 @@
|
|||||||
"c": " ",
|
"c": " ",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -487,10 +487,10 @@
|
|||||||
"c": "%%",
|
"c": "%%",
|
||||||
"t": "source.batchfile constant.character.escape.batchfile",
|
"t": "source.batchfile constant.character.escape.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "constant.character.escape: #D7BA7D",
|
"dark_plus": null,
|
||||||
"light_plus": "constant.character.escape: #A31515",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "constant.character: #569CD6"
|
"hc_black": "constant.character: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -498,10 +498,10 @@
|
|||||||
"c": "LINE:rem +=",
|
"c": "LINE:rem +=",
|
||||||
"t": "source.batchfile",
|
"t": "source.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "default: #D4D4D4",
|
"dark_plus": null,
|
||||||
"light_plus": "default: #000000",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "default: #FFFFFF"
|
"hc_black": "default: #FFFFFF"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -509,10 +509,10 @@
|
|||||||
"c": "%%",
|
"c": "%%",
|
||||||
"t": "source.batchfile constant.character.escape.batchfile",
|
"t": "source.batchfile constant.character.escape.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "constant.character.escape: #D7BA7D",
|
"dark_plus": null,
|
||||||
"light_plus": "constant.character.escape: #A31515",
|
"light_plus": null,
|
||||||
"dark_vs": "default: #D4D4D4",
|
"dark_vs": null,
|
||||||
"light_vs": "default: #000000",
|
"light_vs": null,
|
||||||
"hc_black": "constant.character: #569CD6"
|
"hc_black": "constant.character: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -520,10 +520,10 @@
|
|||||||
"c": "popd",
|
"c": "popd",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@@ -531,10 +531,10 @@
|
|||||||
"c": "endlocal",
|
"c": "endlocal",
|
||||||
"t": "source.batchfile keyword.command.batchfile",
|
"t": "source.batchfile keyword.command.batchfile",
|
||||||
"r": {
|
"r": {
|
||||||
"dark_plus": "keyword: #569CD6",
|
"dark_plus": null,
|
||||||
"light_plus": "keyword: #0000FF",
|
"light_plus": null,
|
||||||
"dark_vs": "keyword: #569CD6",
|
"dark_vs": null,
|
||||||
"light_vs": "keyword: #0000FF",
|
"light_vs": null,
|
||||||
"hc_black": "keyword: #569CD6"
|
"hc_black": "keyword: #569CD6"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user