@yadsh/dsh-qa-surface 0.15.1 → 0.15.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/access/model.js +15 -0
- package/lib/access/model.js.map +1 -1
- package/lib/access/service.js +56 -16
- package/lib/access/service.js.map +1 -1
- package/lib/attestation.js.map +1 -1
- package/lib/client/QaAccountsController.js +3 -1
- package/lib/client/QaAccountsController.js.map +1 -1
- package/lib/client/QaSessionController.js +66 -18
- package/lib/client/QaSessionController.js.map +1 -1
- package/lib/client/QaSurface.js +64 -2
- package/lib/client/QaSurface.js.map +1 -1
- package/lib/client/QaTranscriptAdapter.js +46 -8
- package/lib/client/QaTranscriptAdapter.js.map +1 -1
- package/lib/client/admin/pages/Users.js +2 -2
- package/lib/client/admin/pages/Users.js.map +1 -1
- package/lib/client/attestation.js +13 -5
- package/lib/client/attestation.js.map +1 -1
- package/lib/client/chat-artifacts.js +94 -0
- package/lib/client/chat-artifacts.js.map +1 -0
- package/lib/client/chat-files.js +24 -14
- package/lib/client/chat-files.js.map +1 -1
- package/lib/client/clipboard.js +86 -0
- package/lib/client/clipboard.js.map +1 -0
- package/lib/client/components/QaAuthGate.js +41 -5
- package/lib/client/components/QaAuthGate.js.map +1 -1
- package/lib/client/components/QaChangelog.js +46 -0
- package/lib/client/components/QaChangelog.js.map +1 -1
- package/lib/client/components/QaFileAttachment.js +7 -5
- package/lib/client/components/QaFileAttachment.js.map +1 -1
- package/lib/client/components/QaFilesPanel.js +7 -3
- package/lib/client/components/QaFilesPanel.js.map +1 -1
- package/lib/client/components/QaMessage.js +27 -24
- package/lib/client/components/QaMessage.js.map +1 -1
- package/lib/client/components/QaWorkspaceBrowser.js +18 -25
- package/lib/client/components/QaWorkspaceBrowser.js.map +1 -1
- package/lib/client/components/copy-hint.js +10 -0
- package/lib/client/components/copy-hint.js.map +1 -0
- package/lib/client/markdown/CodeBlock.js +6 -13
- package/lib/client/markdown/CodeBlock.js.map +1 -1
- package/lib/client/project-session-state.js +1 -0
- package/lib/client/project-session-state.js.map +1 -1
- package/lib/client/settings/styles.js +1 -1
- package/lib/client/styles.js +11 -4
- package/lib/client/styles.js.map +1 -1
- package/lib/client/user-settings/IntegrationTokensPage.js +4 -12
- package/lib/client/user-settings/IntegrationTokensPage.js.map +1 -1
- package/lib/client/user-settings/PasswordSettingsPage.js +6 -1
- package/lib/client/user-settings/PasswordSettingsPage.js.map +1 -1
- package/lib/client/workspace-download.js +32 -0
- package/lib/client/workspace-download.js.map +1 -0
- package/lib/client/workspace-paths.js +55 -0
- package/lib/client/workspace-paths.js.map +1 -0
- package/lib/client.js +727 -253
- package/lib/client.js.map +1 -1
- package/lib/enforcement/skill-policy.js +2 -1
- package/lib/enforcement/skill-policy.js.map +1 -1
- package/lib/index.js +26 -10
- package/lib/index.js.map +1 -1
- package/lib/secure-session.js +36 -11
- package/lib/secure-session.js.map +1 -1
- package/lib/slash/catalog.js.map +1 -1
- package/lib/typert.host.js +75 -75
- package/lib/typert.remote-client.js +75 -75
- package/lib/types/access/model.d.ts +13 -0
- package/lib/types/access/service.d.ts +26 -0
- package/lib/types/attestation.d.ts +1 -1
- package/lib/types/client/QaAccountsController.d.ts +2 -0
- package/lib/types/client/QaSessionController.d.ts +13 -0
- package/lib/types/client/QaTranscriptAdapter.d.ts +6 -0
- package/lib/types/client/attestation.d.ts +7 -3
- package/lib/types/client/chat-artifacts.d.ts +10 -0
- package/lib/types/client/chat-files.d.ts +13 -8
- package/lib/types/client/clipboard.d.ts +37 -0
- package/lib/types/client/components/QaAuthGate.d.ts +4 -2
- package/lib/types/client/components/QaFileAttachment.d.ts +13 -4
- package/lib/types/client/components/QaFilesPanel.d.ts +15 -2
- package/lib/types/client/components/QaMessage.d.ts +10 -2
- package/lib/types/client/components/QaWorkspaceBrowser.d.ts +7 -1
- package/lib/types/client/components/copy-hint.d.ts +8 -0
- package/lib/types/client/project-session-state.d.ts +5 -0
- package/lib/types/client/workspace-download.d.ts +16 -0
- package/lib/types/client/workspace-paths.d.ts +25 -0
- package/lib/types/index.d.ts +6 -4
- package/lib/types/secure-session.d.ts +4 -0
- package/lib/types/slash/catalog.d.ts +5 -0
- package/lib/types/types.d.ts +26 -0
- package/locale/en.json +6 -0
- package/package.json +5 -3
package/lib/client.js
CHANGED
|
@@ -8721,7 +8721,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8721
8721
|
},
|
|
8722
8722
|
sourceLocation: {
|
|
8723
8723
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8724
|
-
"line":
|
|
8724
|
+
"line": 1034,
|
|
8725
8725
|
"column": 9
|
|
8726
8726
|
}
|
|
8727
8727
|
},
|
|
@@ -8757,7 +8757,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8757
8757
|
},
|
|
8758
8758
|
sourceLocation: {
|
|
8759
8759
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8760
|
-
"line":
|
|
8760
|
+
"line": 1045,
|
|
8761
8761
|
"column": 3
|
|
8762
8762
|
}
|
|
8763
8763
|
},
|
|
@@ -8784,7 +8784,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8784
8784
|
},
|
|
8785
8785
|
sourceLocation: {
|
|
8786
8786
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8787
|
-
"line":
|
|
8787
|
+
"line": 1019,
|
|
8788
8788
|
"column": 3
|
|
8789
8789
|
}
|
|
8790
8790
|
},
|
|
@@ -8833,7 +8833,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8833
8833
|
},
|
|
8834
8834
|
sourceLocation: {
|
|
8835
8835
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8836
|
-
"line":
|
|
8836
|
+
"line": 1059,
|
|
8837
8837
|
"column": 3
|
|
8838
8838
|
}
|
|
8839
8839
|
},
|
|
@@ -8869,7 +8869,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8869
8869
|
},
|
|
8870
8870
|
sourceLocation: {
|
|
8871
8871
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8872
|
-
"line":
|
|
8872
|
+
"line": 1025,
|
|
8873
8873
|
"column": 3
|
|
8874
8874
|
}
|
|
8875
8875
|
},
|
|
@@ -8905,7 +8905,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8905
8905
|
},
|
|
8906
8906
|
sourceLocation: {
|
|
8907
8907
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8908
|
-
"line":
|
|
8908
|
+
"line": 1104,
|
|
8909
8909
|
"column": 3
|
|
8910
8910
|
}
|
|
8911
8911
|
},
|
|
@@ -8954,7 +8954,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8954
8954
|
},
|
|
8955
8955
|
sourceLocation: {
|
|
8956
8956
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8957
|
-
"line":
|
|
8957
|
+
"line": 1081,
|
|
8958
8958
|
"column": 3
|
|
8959
8959
|
}
|
|
8960
8960
|
},
|
|
@@ -8990,7 +8990,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8990
8990
|
},
|
|
8991
8991
|
sourceLocation: {
|
|
8992
8992
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
8993
|
-
"line":
|
|
8993
|
+
"line": 1071,
|
|
8994
8994
|
"column": 3
|
|
8995
8995
|
}
|
|
8996
8996
|
},
|
|
@@ -9026,7 +9026,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9026
9026
|
},
|
|
9027
9027
|
sourceLocation: {
|
|
9028
9028
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9029
|
-
"line":
|
|
9029
|
+
"line": 1093,
|
|
9030
9030
|
"column": 3
|
|
9031
9031
|
}
|
|
9032
9032
|
},
|
|
@@ -9075,7 +9075,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9075
9075
|
},
|
|
9076
9076
|
sourceLocation: {
|
|
9077
9077
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9078
|
-
"line":
|
|
9078
|
+
"line": 1052,
|
|
9079
9079
|
"column": 3
|
|
9080
9080
|
}
|
|
9081
9081
|
},
|
|
@@ -9124,7 +9124,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9124
9124
|
},
|
|
9125
9125
|
sourceLocation: {
|
|
9126
9126
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9127
|
-
"line":
|
|
9127
|
+
"line": 740,
|
|
9128
9128
|
"column": 3
|
|
9129
9129
|
}
|
|
9130
9130
|
},
|
|
@@ -9160,7 +9160,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9160
9160
|
},
|
|
9161
9161
|
sourceLocation: {
|
|
9162
9162
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9163
|
-
"line":
|
|
9163
|
+
"line": 774,
|
|
9164
9164
|
"column": 3
|
|
9165
9165
|
}
|
|
9166
9166
|
},
|
|
@@ -9196,7 +9196,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9196
9196
|
},
|
|
9197
9197
|
sourceLocation: {
|
|
9198
9198
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9199
|
-
"line":
|
|
9199
|
+
"line": 861,
|
|
9200
9200
|
"column": 3
|
|
9201
9201
|
}
|
|
9202
9202
|
},
|
|
@@ -9223,7 +9223,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9223
9223
|
},
|
|
9224
9224
|
sourceLocation: {
|
|
9225
9225
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9226
|
-
"line":
|
|
9226
|
+
"line": 795,
|
|
9227
9227
|
"column": 3
|
|
9228
9228
|
}
|
|
9229
9229
|
},
|
|
@@ -9250,7 +9250,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9250
9250
|
},
|
|
9251
9251
|
sourceLocation: {
|
|
9252
9252
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9253
|
-
"line":
|
|
9253
|
+
"line": 848,
|
|
9254
9254
|
"column": 3
|
|
9255
9255
|
}
|
|
9256
9256
|
},
|
|
@@ -9286,7 +9286,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9286
9286
|
},
|
|
9287
9287
|
sourceLocation: {
|
|
9288
9288
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9289
|
-
"line":
|
|
9289
|
+
"line": 734,
|
|
9290
9290
|
"column": 3
|
|
9291
9291
|
}
|
|
9292
9292
|
},
|
|
@@ -9313,7 +9313,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9313
9313
|
},
|
|
9314
9314
|
sourceLocation: {
|
|
9315
9315
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9316
|
-
"line":
|
|
9316
|
+
"line": 785,
|
|
9317
9317
|
"column": 3
|
|
9318
9318
|
}
|
|
9319
9319
|
},
|
|
@@ -9349,7 +9349,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9349
9349
|
},
|
|
9350
9350
|
sourceLocation: {
|
|
9351
9351
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9352
|
-
"line":
|
|
9352
|
+
"line": 729,
|
|
9353
9353
|
"column": 3
|
|
9354
9354
|
}
|
|
9355
9355
|
},
|
|
@@ -9376,7 +9376,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9376
9376
|
},
|
|
9377
9377
|
sourceLocation: {
|
|
9378
9378
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9379
|
-
"line":
|
|
9379
|
+
"line": 758,
|
|
9380
9380
|
"column": 3
|
|
9381
9381
|
}
|
|
9382
9382
|
},
|
|
@@ -9412,7 +9412,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9412
9412
|
},
|
|
9413
9413
|
sourceLocation: {
|
|
9414
9414
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9415
|
-
"line":
|
|
9415
|
+
"line": 874,
|
|
9416
9416
|
"column": 3
|
|
9417
9417
|
}
|
|
9418
9418
|
},
|
|
@@ -9448,7 +9448,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9448
9448
|
},
|
|
9449
9449
|
sourceLocation: {
|
|
9450
9450
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9451
|
-
"line":
|
|
9451
|
+
"line": 835,
|
|
9452
9452
|
"column": 3
|
|
9453
9453
|
}
|
|
9454
9454
|
},
|
|
@@ -9484,7 +9484,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9484
9484
|
},
|
|
9485
9485
|
sourceLocation: {
|
|
9486
9486
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9487
|
-
"line":
|
|
9487
|
+
"line": 808,
|
|
9488
9488
|
"column": 3
|
|
9489
9489
|
}
|
|
9490
9490
|
},
|
|
@@ -9520,7 +9520,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9520
9520
|
},
|
|
9521
9521
|
sourceLocation: {
|
|
9522
9522
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9523
|
-
"line":
|
|
9523
|
+
"line": 821,
|
|
9524
9524
|
"column": 3
|
|
9525
9525
|
}
|
|
9526
9526
|
},
|
|
@@ -9547,7 +9547,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9547
9547
|
},
|
|
9548
9548
|
sourceLocation: {
|
|
9549
9549
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9550
|
-
"line":
|
|
9550
|
+
"line": 764,
|
|
9551
9551
|
"column": 3
|
|
9552
9552
|
}
|
|
9553
9553
|
},
|
|
@@ -9606,7 +9606,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9606
9606
|
},
|
|
9607
9607
|
sourceLocation: {
|
|
9608
9608
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9609
|
-
"line":
|
|
9609
|
+
"line": 1476,
|
|
9610
9610
|
"column": 3
|
|
9611
9611
|
}
|
|
9612
9612
|
},
|
|
@@ -9642,7 +9642,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9642
9642
|
},
|
|
9643
9643
|
sourceLocation: {
|
|
9644
9644
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9645
|
-
"line":
|
|
9645
|
+
"line": 1356,
|
|
9646
9646
|
"column": 3
|
|
9647
9647
|
}
|
|
9648
9648
|
},
|
|
@@ -9702,7 +9702,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9702
9702
|
},
|
|
9703
9703
|
sourceLocation: {
|
|
9704
9704
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9705
|
-
"line":
|
|
9705
|
+
"line": 1336,
|
|
9706
9706
|
"column": 3
|
|
9707
9707
|
}
|
|
9708
9708
|
},
|
|
@@ -9738,7 +9738,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9738
9738
|
},
|
|
9739
9739
|
sourceLocation: {
|
|
9740
9740
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9741
|
-
"line":
|
|
9741
|
+
"line": 1371,
|
|
9742
9742
|
"column": 3
|
|
9743
9743
|
}
|
|
9744
9744
|
},
|
|
@@ -9797,7 +9797,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9797
9797
|
},
|
|
9798
9798
|
sourceLocation: {
|
|
9799
9799
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9800
|
-
"line":
|
|
9800
|
+
"line": 1381,
|
|
9801
9801
|
"column": 3
|
|
9802
9802
|
}
|
|
9803
9803
|
},
|
|
@@ -9833,7 +9833,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9833
9833
|
},
|
|
9834
9834
|
sourceLocation: {
|
|
9835
9835
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9836
|
-
"line":
|
|
9836
|
+
"line": 1418,
|
|
9837
9837
|
"column": 3
|
|
9838
9838
|
}
|
|
9839
9839
|
},
|
|
@@ -9892,7 +9892,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9892
9892
|
},
|
|
9893
9893
|
sourceLocation: {
|
|
9894
9894
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9895
|
-
"line":
|
|
9895
|
+
"line": 1230,
|
|
9896
9896
|
"column": 3
|
|
9897
9897
|
}
|
|
9898
9898
|
},
|
|
@@ -9941,7 +9941,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9941
9941
|
},
|
|
9942
9942
|
sourceLocation: {
|
|
9943
9943
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
9944
|
-
"line":
|
|
9944
|
+
"line": 1243,
|
|
9945
9945
|
"column": 3
|
|
9946
9946
|
}
|
|
9947
9947
|
},
|
|
@@ -10010,7 +10010,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10010
10010
|
},
|
|
10011
10011
|
sourceLocation: {
|
|
10012
10012
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10013
|
-
"line":
|
|
10013
|
+
"line": 1216,
|
|
10014
10014
|
"column": 3
|
|
10015
10015
|
}
|
|
10016
10016
|
},
|
|
@@ -10037,7 +10037,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10037
10037
|
},
|
|
10038
10038
|
sourceLocation: {
|
|
10039
10039
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10040
|
-
"line":
|
|
10040
|
+
"line": 1210,
|
|
10041
10041
|
"column": 3
|
|
10042
10042
|
}
|
|
10043
10043
|
},
|
|
@@ -10086,7 +10086,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10086
10086
|
},
|
|
10087
10087
|
sourceLocation: {
|
|
10088
10088
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10089
|
-
"line":
|
|
10089
|
+
"line": 1261,
|
|
10090
10090
|
"column": 3
|
|
10091
10091
|
}
|
|
10092
10092
|
},
|
|
@@ -10114,7 +10114,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10114
10114
|
},
|
|
10115
10115
|
sourceLocation: {
|
|
10116
10116
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10117
|
-
"line":
|
|
10117
|
+
"line": 1469,
|
|
10118
10118
|
"column": 3
|
|
10119
10119
|
}
|
|
10120
10120
|
},
|
|
@@ -10142,7 +10142,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10142
10142
|
},
|
|
10143
10143
|
sourceLocation: {
|
|
10144
10144
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10145
|
-
"line":
|
|
10145
|
+
"line": 1280,
|
|
10146
10146
|
"column": 3
|
|
10147
10147
|
}
|
|
10148
10148
|
},
|
|
@@ -10169,7 +10169,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10169
10169
|
},
|
|
10170
10170
|
sourceLocation: {
|
|
10171
10171
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10172
|
-
"line":
|
|
10172
|
+
"line": 1316,
|
|
10173
10173
|
"column": 3
|
|
10174
10174
|
}
|
|
10175
10175
|
},
|
|
@@ -10218,7 +10218,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10218
10218
|
},
|
|
10219
10219
|
sourceLocation: {
|
|
10220
10220
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10221
|
-
"line":
|
|
10221
|
+
"line": 1446,
|
|
10222
10222
|
"column": 3
|
|
10223
10223
|
}
|
|
10224
10224
|
},
|
|
@@ -10277,7 +10277,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10277
10277
|
},
|
|
10278
10278
|
sourceLocation: {
|
|
10279
10279
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10280
|
-
"line":
|
|
10280
|
+
"line": 1402,
|
|
10281
10281
|
"column": 3
|
|
10282
10282
|
}
|
|
10283
10283
|
},
|
|
@@ -10326,7 +10326,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10326
10326
|
},
|
|
10327
10327
|
sourceLocation: {
|
|
10328
10328
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10329
|
-
"line":
|
|
10329
|
+
"line": 1325,
|
|
10330
10330
|
"column": 3
|
|
10331
10331
|
}
|
|
10332
10332
|
},
|
|
@@ -10376,7 +10376,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10376
10376
|
},
|
|
10377
10377
|
sourceLocation: {
|
|
10378
10378
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10379
|
-
"line":
|
|
10379
|
+
"line": 1428,
|
|
10380
10380
|
"column": 3
|
|
10381
10381
|
}
|
|
10382
10382
|
},
|
|
@@ -10412,7 +10412,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10412
10412
|
},
|
|
10413
10413
|
sourceLocation: {
|
|
10414
10414
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10415
|
-
"line":
|
|
10415
|
+
"line": 1461,
|
|
10416
10416
|
"column": 3
|
|
10417
10417
|
}
|
|
10418
10418
|
},
|
|
@@ -10461,7 +10461,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10461
10461
|
},
|
|
10462
10462
|
sourceLocation: {
|
|
10463
10463
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10464
|
-
"line":
|
|
10464
|
+
"line": 1134,
|
|
10465
10465
|
"column": 3
|
|
10466
10466
|
}
|
|
10467
10467
|
},
|
|
@@ -10520,7 +10520,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10520
10520
|
},
|
|
10521
10521
|
sourceLocation: {
|
|
10522
10522
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10523
|
-
"line":
|
|
10523
|
+
"line": 1162,
|
|
10524
10524
|
"column": 3
|
|
10525
10525
|
}
|
|
10526
10526
|
},
|
|
@@ -10556,7 +10556,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10556
10556
|
},
|
|
10557
10557
|
sourceLocation: {
|
|
10558
10558
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10559
|
-
"line":
|
|
10559
|
+
"line": 1125,
|
|
10560
10560
|
"column": 3
|
|
10561
10561
|
}
|
|
10562
10562
|
},
|
|
@@ -10615,7 +10615,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10615
10615
|
},
|
|
10616
10616
|
sourceLocation: {
|
|
10617
10617
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10618
|
-
"line":
|
|
10618
|
+
"line": 1149,
|
|
10619
10619
|
"column": 3
|
|
10620
10620
|
}
|
|
10621
10621
|
},
|
|
@@ -10651,7 +10651,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10651
10651
|
},
|
|
10652
10652
|
sourceLocation: {
|
|
10653
10653
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10654
|
-
"line":
|
|
10654
|
+
"line": 1188,
|
|
10655
10655
|
"column": 9
|
|
10656
10656
|
}
|
|
10657
10657
|
},
|
|
@@ -10710,7 +10710,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10710
10710
|
},
|
|
10711
10711
|
sourceLocation: {
|
|
10712
10712
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10713
|
-
"line":
|
|
10713
|
+
"line": 1175,
|
|
10714
10714
|
"column": 3
|
|
10715
10715
|
}
|
|
10716
10716
|
},
|
|
@@ -10759,7 +10759,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10759
10759
|
},
|
|
10760
10760
|
sourceLocation: {
|
|
10761
10761
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10762
|
-
"line":
|
|
10762
|
+
"line": 1305,
|
|
10763
10763
|
"column": 3
|
|
10764
10764
|
}
|
|
10765
10765
|
},
|
|
@@ -10795,7 +10795,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10795
10795
|
},
|
|
10796
10796
|
sourceLocation: {
|
|
10797
10797
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10798
|
-
"line":
|
|
10798
|
+
"line": 1299,
|
|
10799
10799
|
"column": 3
|
|
10800
10800
|
}
|
|
10801
10801
|
},
|
|
@@ -10854,7 +10854,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10854
10854
|
},
|
|
10855
10855
|
sourceLocation: {
|
|
10856
10856
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10857
|
-
"line":
|
|
10857
|
+
"line": 1287,
|
|
10858
10858
|
"column": 3
|
|
10859
10859
|
}
|
|
10860
10860
|
},
|
|
@@ -10913,7 +10913,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10913
10913
|
},
|
|
10914
10914
|
sourceLocation: {
|
|
10915
10915
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10916
|
-
"line":
|
|
10916
|
+
"line": 1555,
|
|
10917
10917
|
"column": 9
|
|
10918
10918
|
}
|
|
10919
10919
|
},
|
|
@@ -10972,7 +10972,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
10972
10972
|
},
|
|
10973
10973
|
sourceLocation: {
|
|
10974
10974
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
10975
|
-
"line":
|
|
10975
|
+
"line": 1584,
|
|
10976
10976
|
"column": 9
|
|
10977
10977
|
}
|
|
10978
10978
|
},
|
|
@@ -11021,7 +11021,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11021
11021
|
},
|
|
11022
11022
|
sourceLocation: {
|
|
11023
11023
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11024
|
-
"line":
|
|
11024
|
+
"line": 1596,
|
|
11025
11025
|
"column": 9
|
|
11026
11026
|
}
|
|
11027
11027
|
},
|
|
@@ -11070,7 +11070,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11070
11070
|
},
|
|
11071
11071
|
sourceLocation: {
|
|
11072
11072
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11073
|
-
"line":
|
|
11073
|
+
"line": 920,
|
|
11074
11074
|
"column": 9
|
|
11075
11075
|
}
|
|
11076
11076
|
},
|
|
@@ -11088,7 +11088,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11088
11088
|
},
|
|
11089
11089
|
sourceLocation: {
|
|
11090
11090
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11091
|
-
"line":
|
|
11091
|
+
"line": 889,
|
|
11092
11092
|
"column": 3
|
|
11093
11093
|
}
|
|
11094
11094
|
},
|
|
@@ -11137,7 +11137,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11137
11137
|
},
|
|
11138
11138
|
sourceLocation: {
|
|
11139
11139
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11140
|
-
"line":
|
|
11140
|
+
"line": 1664,
|
|
11141
11141
|
"column": 9
|
|
11142
11142
|
}
|
|
11143
11143
|
},
|
|
@@ -11173,7 +11173,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11173
11173
|
},
|
|
11174
11174
|
sourceLocation: {
|
|
11175
11175
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11176
|
-
"line":
|
|
11176
|
+
"line": 1541,
|
|
11177
11177
|
"column": 9
|
|
11178
11178
|
}
|
|
11179
11179
|
},
|
|
@@ -11209,7 +11209,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11209
11209
|
},
|
|
11210
11210
|
sourceLocation: {
|
|
11211
11211
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11212
|
-
"line":
|
|
11212
|
+
"line": 1570,
|
|
11213
11213
|
"column": 9
|
|
11214
11214
|
}
|
|
11215
11215
|
},
|
|
@@ -11258,7 +11258,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11258
11258
|
},
|
|
11259
11259
|
sourceLocation: {
|
|
11260
11260
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11261
|
-
"line":
|
|
11261
|
+
"line": 1725,
|
|
11262
11262
|
"column": 9
|
|
11263
11263
|
}
|
|
11264
11264
|
},
|
|
@@ -11276,7 +11276,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11276
11276
|
},
|
|
11277
11277
|
sourceLocation: {
|
|
11278
11278
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11279
|
-
"line":
|
|
11279
|
+
"line": 907,
|
|
11280
11280
|
"column": 3
|
|
11281
11281
|
}
|
|
11282
11282
|
},
|
|
@@ -11325,7 +11325,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11325
11325
|
},
|
|
11326
11326
|
sourceLocation: {
|
|
11327
11327
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11328
|
-
"line":
|
|
11328
|
+
"line": 1615,
|
|
11329
11329
|
"column": 9
|
|
11330
11330
|
}
|
|
11331
11331
|
},
|
|
@@ -11374,7 +11374,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11374
11374
|
},
|
|
11375
11375
|
sourceLocation: {
|
|
11376
11376
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11377
|
-
"line":
|
|
11377
|
+
"line": 1691,
|
|
11378
11378
|
"column": 9
|
|
11379
11379
|
}
|
|
11380
11380
|
},
|
|
@@ -11410,7 +11410,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11410
11410
|
},
|
|
11411
11411
|
sourceLocation: {
|
|
11412
11412
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11413
|
-
"line":
|
|
11413
|
+
"line": 1489,
|
|
11414
11414
|
"column": 9
|
|
11415
11415
|
}
|
|
11416
11416
|
},
|
|
@@ -11446,7 +11446,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11446
11446
|
},
|
|
11447
11447
|
sourceLocation: {
|
|
11448
11448
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11449
|
-
"line":
|
|
11449
|
+
"line": 1795,
|
|
11450
11450
|
"column": 3
|
|
11451
11451
|
}
|
|
11452
11452
|
},
|
|
@@ -11482,7 +11482,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11482
11482
|
},
|
|
11483
11483
|
sourceLocation: {
|
|
11484
11484
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11485
|
-
"line":
|
|
11485
|
+
"line": 1789,
|
|
11486
11486
|
"column": 3
|
|
11487
11487
|
}
|
|
11488
11488
|
},
|
|
@@ -11509,7 +11509,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11509
11509
|
},
|
|
11510
11510
|
sourceLocation: {
|
|
11511
11511
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11512
|
-
"line":
|
|
11512
|
+
"line": 1783,
|
|
11513
11513
|
"column": 3
|
|
11514
11514
|
}
|
|
11515
11515
|
},
|
|
@@ -11558,7 +11558,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11558
11558
|
},
|
|
11559
11559
|
sourceLocation: {
|
|
11560
11560
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11561
|
-
"line":
|
|
11561
|
+
"line": 1814,
|
|
11562
11562
|
"column": 3
|
|
11563
11563
|
}
|
|
11564
11564
|
},
|
|
@@ -11585,7 +11585,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11585
11585
|
},
|
|
11586
11586
|
sourceLocation: {
|
|
11587
11587
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11588
|
-
"line":
|
|
11588
|
+
"line": 1840,
|
|
11589
11589
|
"column": 3
|
|
11590
11590
|
}
|
|
11591
11591
|
},
|
|
@@ -11634,7 +11634,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11634
11634
|
},
|
|
11635
11635
|
sourceLocation: {
|
|
11636
11636
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11637
|
-
"line":
|
|
11637
|
+
"line": 1804,
|
|
11638
11638
|
"column": 3
|
|
11639
11639
|
}
|
|
11640
11640
|
},
|
|
@@ -11683,7 +11683,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11683
11683
|
},
|
|
11684
11684
|
sourceLocation: {
|
|
11685
11685
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11686
|
-
"line":
|
|
11686
|
+
"line": 1827,
|
|
11687
11687
|
"column": 3
|
|
11688
11688
|
}
|
|
11689
11689
|
},
|
|
@@ -11719,7 +11719,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11719
11719
|
},
|
|
11720
11720
|
sourceLocation: {
|
|
11721
11721
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11722
|
-
"line":
|
|
11722
|
+
"line": 1857,
|
|
11723
11723
|
"column": 3
|
|
11724
11724
|
}
|
|
11725
11725
|
},
|
|
@@ -11778,7 +11778,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11778
11778
|
},
|
|
11779
11779
|
sourceLocation: {
|
|
11780
11780
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11781
|
-
"line":
|
|
11781
|
+
"line": 1872,
|
|
11782
11782
|
"column": 3
|
|
11783
11783
|
}
|
|
11784
11784
|
},
|
|
@@ -11814,7 +11814,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
11814
11814
|
},
|
|
11815
11815
|
sourceLocation: {
|
|
11816
11816
|
"file": "packages/dsh-qa-surface/src/index.ts",
|
|
11817
|
-
"line":
|
|
11817
|
+
"line": 1528,
|
|
11818
11818
|
"column": 9
|
|
11819
11819
|
}
|
|
11820
11820
|
}
|
|
@@ -13428,7 +13428,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
13428
13428
|
case "account-disabled": return "Аккаунт отключён администратором.";
|
|
13429
13429
|
case "email-taken": return "Этот email уже зарегистрирован.";
|
|
13430
13430
|
case "invalid-email": return "Введите корректный email.";
|
|
13431
|
-
case "weak-password": return
|
|
13431
|
+
case "weak-password": return `Пароль должен быть не короче 8 символов.`;
|
|
13432
13432
|
case "invalid-display-name": return "Слишком длинное имя.";
|
|
13433
13433
|
case "invalid-profile": return "Проверьте поля профиля: значение слишком длинное или недопустимое.";
|
|
13434
13434
|
case "profile-disabled": return "Профиль отключён на этом сервере.";
|
|
@@ -14517,12 +14517,16 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
14517
14517
|
}
|
|
14518
14518
|
};
|
|
14519
14519
|
/**
|
|
14520
|
-
* Refusals that classify
|
|
14521
|
-
*
|
|
14522
|
-
*
|
|
14520
|
+
* Refusals that classify what the browser has on screen rather than faulting
|
|
14521
|
+
* the deployment: an existing chat of an older composition, one adopted from
|
|
14522
|
+
* outside the QA policy, or an identity that is another conversation's
|
|
14523
|
+
* delegated child.
|
|
14524
|
+
*
|
|
14525
|
+
* Keeping only its transcript is safe: policyReady stays false, so no prompt,
|
|
14526
|
+
* cancel, approval or question reaches the Host.
|
|
14523
14527
|
*/
|
|
14524
14528
|
function canOpenAsCompatibilityReadOnly(reason) {
|
|
14525
|
-
return reason === "composition-mismatch" || reason === "agent-unavailable" || reason === "adoption-refused";
|
|
14529
|
+
return reason === "composition-mismatch" || reason === "agent-unavailable" || reason === "adoption-refused" || reason === "subagent-session";
|
|
14526
14530
|
}
|
|
14527
14531
|
/**
|
|
14528
14532
|
* Extract the coarse attestation reason code from a Host wire failure, if the
|
|
@@ -14533,7 +14537,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
14533
14537
|
return reason === void 0 ? null : reason;
|
|
14534
14538
|
}
|
|
14535
14539
|
function attestationHint(reason) {
|
|
14536
|
-
if (reason === "agent-unavailable") return "
|
|
14540
|
+
if (reason === "agent-unavailable") return "This chat's transcript is on the Host, but no agent stands behind it: resuming the composition its session recorded failed — a preset that no longer mounts, or a log the Host refuses to read. That is not what a restarted stand looks like; after a restart the next open simply resumes the chat. The failing session is named in the Host log under `session.agent-resolve-rejected` — re-mount the preset that session recorded and re-open the chat, while New chat gives the visitor a working one meanwhile.";
|
|
14541
|
+
if (reason === "subagent-session") return "The id this page asked about is a delegated subagent run, not a chat: subagent routing owns that identity, so the Host puts no sendable agent behind it and nothing can be attested here. Read the run from its parent chat's work group — its sources already reach that chat. If a chat row of this browser leads here, it points at a child: start a new chat and leave that id behind.";
|
|
14537
14542
|
if (reason === "unknown-tools") return "A lockdown.toolPolicy name is not mounted in this session's tool catalog — check the deployment agent preset and the tool's server availability.";
|
|
14538
14543
|
if (reason === "workspace-unavailable") return "The configured session.workspaceId does not match a registered workspace - create the workspace or fix the id (session.cwd is the no-registry alternative).";
|
|
14539
14544
|
if (reason === "composition-mismatch") return "The session's agent preset, workspace or model no longer matches the deployment QA config.";
|
|
@@ -15157,6 +15162,97 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
15157
15162
|
});
|
|
15158
15163
|
}
|
|
15159
15164
|
//#endregion
|
|
15165
|
+
//#region src/client/chat-artifacts.ts
|
|
15166
|
+
/**
|
|
15167
|
+
* The files one turn produced, read out of the tool results that produced them.
|
|
15168
|
+
*
|
|
15169
|
+
* A document the agent made is the result of the conversation, but nothing
|
|
15170
|
+
* carries it into the transcript: it is a file in the chat's own workspace, and
|
|
15171
|
+
* the only trace it leaves is the line the producing tool rendered. Reading
|
|
15172
|
+
* those lines is what turns a paragraph that mentions a file into a card a
|
|
15173
|
+
* person can open and download, so the reader does not have to know the files
|
|
15174
|
+
* tab exists to receive what they asked for.
|
|
15175
|
+
*
|
|
15176
|
+
* The line shape belongs to the tools of `@yadsh/dsh-documents`, which report
|
|
15177
|
+
* every produced file as `<format>: <path> (<size>, sha256 …)`. The path is the
|
|
15178
|
+
* workspace-relative name the tool was asked to report: an absolute path would
|
|
15179
|
+
* both refuse at the workspace fence and print the account's own directory into
|
|
15180
|
+
* the answer, so a line carrying one is ignored rather than rendered.
|
|
15181
|
+
*/
|
|
15182
|
+
/** The tools that hand a file to the user, and the formats each reports. */
|
|
15183
|
+
const PRODUCED_FORMATS = Object.freeze({
|
|
15184
|
+
document_create: ["docx", "pdf"],
|
|
15185
|
+
document_convert: [
|
|
15186
|
+
"docx",
|
|
15187
|
+
"pdf",
|
|
15188
|
+
"md"
|
|
15189
|
+
],
|
|
15190
|
+
document_to_markdown: ["markdown"],
|
|
15191
|
+
document_from_url: ["markdown"]
|
|
15192
|
+
});
|
|
15193
|
+
/** One reported file: `<format>: <path>` with an optional `(<size>, …)`. */
|
|
15194
|
+
const FILE_LINE = /^([a-z][a-z0-9]*):\s+(\S+)(?:\s+\(([^)]*)\))?$/u;
|
|
15195
|
+
/** A path spelled from the filesystem root, which the fence would refuse. */
|
|
15196
|
+
function isAbsolutePath(value) {
|
|
15197
|
+
return value.startsWith("/") || value.startsWith("\\") || /^[A-Za-z]:[\\/]/u.test(value);
|
|
15198
|
+
}
|
|
15199
|
+
/** `12.3 KiB` back to bytes; an unparseable size reads as unknown. */
|
|
15200
|
+
const UNIT_SCALES = Object.freeze({
|
|
15201
|
+
b: 1,
|
|
15202
|
+
kib: 1024,
|
|
15203
|
+
mib: 1048576,
|
|
15204
|
+
gib: 1073741824
|
|
15205
|
+
});
|
|
15206
|
+
function reportedBytes(details) {
|
|
15207
|
+
const size = /^([\d.]+)\s*([A-Za-z]+)$/u.exec(details?.split(",")[0]?.trim() ?? "");
|
|
15208
|
+
if (size === null) return 0;
|
|
15209
|
+
const value = Number.parseFloat(size[1] ?? "");
|
|
15210
|
+
const scale = UNIT_SCALES[(size[2] ?? "").toLowerCase()];
|
|
15211
|
+
if (!Number.isFinite(value) || scale === void 0) return 0;
|
|
15212
|
+
return Math.round(value * scale);
|
|
15213
|
+
}
|
|
15214
|
+
/** Last segment of a reported path, spelled with forward slashes. */
|
|
15215
|
+
function baseName(path) {
|
|
15216
|
+
const segments = path.split(/[/\\]/u).filter((segment) => segment !== "");
|
|
15217
|
+
return segments[segments.length - 1] ?? path;
|
|
15218
|
+
}
|
|
15219
|
+
/**
|
|
15220
|
+
* Whether a reported name is a file. A produced document always carries its
|
|
15221
|
+
* extension, while a prose line that happens to start with a format word — a
|
|
15222
|
+
* summary the tool wrote, a translation of the status — does not. Reading the
|
|
15223
|
+
* one as the other would card a sentence.
|
|
15224
|
+
*/
|
|
15225
|
+
function isFileName(value) {
|
|
15226
|
+
return /^[^./\\][^/\\]*\.[A-Za-z][A-Za-z0-9]{0,9}$/u.test(baseName(value));
|
|
15227
|
+
}
|
|
15228
|
+
/**
|
|
15229
|
+
* The files one tool result reports, in the order it reported them.
|
|
15230
|
+
*
|
|
15231
|
+
* `output` is the rendered text of the result, the same string the work group
|
|
15232
|
+
* shows. A tool that produced nothing — a read, an inspection, a refusal — is
|
|
15233
|
+
* not in the table and contributes no artifact.
|
|
15234
|
+
*/
|
|
15235
|
+
function artifactsOfToolResult(toolName, output) {
|
|
15236
|
+
const formats = PRODUCED_FORMATS[toolName];
|
|
15237
|
+
if (formats === void 0 || output === null) return [];
|
|
15238
|
+
const artifacts = [];
|
|
15239
|
+
for (const line of output.split(/\r?\n/u)) {
|
|
15240
|
+
const reported = FILE_LINE.exec(line.trim());
|
|
15241
|
+
if (reported === null) continue;
|
|
15242
|
+
const format = reported[1] ?? "";
|
|
15243
|
+
const path = reported[2] ?? "";
|
|
15244
|
+
if (!formats.includes(format)) continue;
|
|
15245
|
+
if (path === "failed" || !isFileName(path) || isAbsolutePath(path)) continue;
|
|
15246
|
+
artifacts.push({
|
|
15247
|
+
path,
|
|
15248
|
+
name: baseName(path),
|
|
15249
|
+
format,
|
|
15250
|
+
bytes: reportedBytes(reported[3])
|
|
15251
|
+
});
|
|
15252
|
+
}
|
|
15253
|
+
return artifacts;
|
|
15254
|
+
}
|
|
15255
|
+
//#endregion
|
|
15160
15256
|
//#region src/provenance/normalize.ts
|
|
15161
15257
|
const TRACKING_PARAMETERS = /* @__PURE__ */ new Set([
|
|
15162
15258
|
"fbclid",
|
|
@@ -15864,6 +15960,55 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
15864
15960
|
return configured === void 0 || configured === "" ? void 0 : configured;
|
|
15865
15961
|
}
|
|
15866
15962
|
//#endregion
|
|
15963
|
+
//#region src/client/workspace-paths.ts
|
|
15964
|
+
/**
|
|
15965
|
+
* The answer a person reads names a file; it does not say where the deployment
|
|
15966
|
+
* keeps the account that owns it.
|
|
15967
|
+
*
|
|
15968
|
+
* A model quoting a path it was handed prints it verbatim, and a QA deployment
|
|
15969
|
+
* gives every account its own directory under one parent, so a path printed
|
|
15970
|
+
* with an account identifier is a sentence about the server's layout — and
|
|
15971
|
+
* stand dialogs below the signature line can be read by other accounts of the
|
|
15972
|
+
* same server. The document tools report workspace-relative names, which is
|
|
15973
|
+
* the fix at the source; this is the repair for what still arrives, because a
|
|
15974
|
+
* model can rebuild a path from the working directory it is told, and because
|
|
15975
|
+
* an answer written before this change is durable history that replays.
|
|
15976
|
+
*/
|
|
15977
|
+
/** Characters a literal path may carry into a regular expression. */
|
|
15978
|
+
function escapeForRegex(value) {
|
|
15979
|
+
return value.replace(/[.*+?^${}()|[\]\\]/gu, String.raw`\$&`);
|
|
15980
|
+
}
|
|
15981
|
+
/** One or two separators, either convention, as a regular-expression source. */
|
|
15982
|
+
const SEPARATOR = String.raw`[\\\/]+`;
|
|
15983
|
+
const TRAILING_SEPARATOR = String.raw`[\\\/]?`;
|
|
15984
|
+
/**
|
|
15985
|
+
* The workspace root spelled so either separator convention matches it: a
|
|
15986
|
+
* container records forward slashes, a browser on Windows may print backslashes
|
|
15987
|
+
* at the same position, and a mask that only reads one of them leaks on the
|
|
15988
|
+
* other. A leading separator is kept, so what replaces the root reads as a name
|
|
15989
|
+
* inside the workspace rather than as a path leading out of nowhere.
|
|
15990
|
+
*/
|
|
15991
|
+
function rootPattern(workspaceRoot) {
|
|
15992
|
+
const segments = workspaceRoot.split(/[/\\]/u).filter((segment) => segment !== "").map((segment) => escapeForRegex(segment));
|
|
15993
|
+
const leading = /^[/\\]/u.test(workspaceRoot) ? SEPARATOR : "";
|
|
15994
|
+
return new RegExp(`${leading}${segments.join(SEPARATOR)}${TRAILING_SEPARATOR}`, "gu");
|
|
15995
|
+
}
|
|
15996
|
+
/**
|
|
15997
|
+
* Rewrite an answer so a file is named, not located.
|
|
15998
|
+
*
|
|
15999
|
+
* The chat's own workspace directory is removed, leaving the spelling the
|
|
16000
|
+
* producing tool reports and the workspace reads take. The per-account
|
|
16001
|
+
* partition is removed the same way even when the root is unknown or the answer
|
|
16002
|
+
* quotes a different chat's file, because the identifier inside it is the part
|
|
16003
|
+
* that must not be printed. A path that is neither of those is left alone: a
|
|
16004
|
+
* reader told about `/etc/hosts` is not being shown this deployment's layout.
|
|
16005
|
+
*/
|
|
16006
|
+
function toWorkspaceRelativeText(text, workspaceRoot) {
|
|
16007
|
+
if (!text.includes("/") && !text.includes("\\")) return text;
|
|
16008
|
+
const root = workspaceRoot?.trim();
|
|
16009
|
+
return (root === void 0 || root === "" ? text : text.replace(rootPattern(root), "")).replace(/[/\\](?:[^/\\\s]+[/\\])*?\.qa-users[/\\][^/\\\s]+[/\\]/gu, "");
|
|
16010
|
+
}
|
|
16011
|
+
//#endregion
|
|
15867
16012
|
//#region src/client/subagent-codenames.ts
|
|
15868
16013
|
/**
|
|
15869
16014
|
* Deterministic display codenames for subagent sessions.
|
|
@@ -16246,8 +16391,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16246
16391
|
return Reflect.get(block, "type") === "text" && typeof Reflect.get(block, "text") === "string" ? [Reflect.get(block, "text")] : [];
|
|
16247
16392
|
}).join("");
|
|
16248
16393
|
}
|
|
16249
|
-
function visibleAssistantText(blocks) {
|
|
16250
|
-
return blocks.filter((block) => block.kind === "text" && typeof block.text === "string").map((block) => block.text).join("");
|
|
16394
|
+
function visibleAssistantText(blocks, workspaceRoot) {
|
|
16395
|
+
return toWorkspaceRelativeText(blocks.filter((block) => block.kind === "text" && typeof block.text === "string").map((block) => block.text).join(""), workspaceRoot);
|
|
16251
16396
|
}
|
|
16252
16397
|
/**
|
|
16253
16398
|
* Response timing for the message row, straight from the host-recorded step
|
|
@@ -16277,15 +16422,16 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16277
16422
|
buffer = {
|
|
16278
16423
|
turn,
|
|
16279
16424
|
text: [],
|
|
16280
|
-
work: []
|
|
16425
|
+
work: [],
|
|
16426
|
+
artifacts: []
|
|
16281
16427
|
};
|
|
16282
16428
|
turns.set(turn, buffer);
|
|
16283
16429
|
}
|
|
16284
16430
|
return buffer;
|
|
16285
16431
|
}
|
|
16286
|
-
function collectAssistant(node, turns, toolHeads, showReasoning) {
|
|
16432
|
+
function collectAssistant(node, turns, toolHeads, showReasoning, workspaceRoot) {
|
|
16287
16433
|
const turn = getTurn(turns, node.turn);
|
|
16288
|
-
const text = visibleAssistantText(node.blocks);
|
|
16434
|
+
const text = visibleAssistantText(node.blocks, workspaceRoot);
|
|
16289
16435
|
if (text !== "") turn.text.push({
|
|
16290
16436
|
id: `assistant:${node.messageId ?? node.seq}`,
|
|
16291
16437
|
seq: node.seq,
|
|
@@ -16335,6 +16481,31 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16335
16481
|
}
|
|
16336
16482
|
return settled;
|
|
16337
16483
|
}
|
|
16484
|
+
/**
|
|
16485
|
+
* The files each turn's tools handed over, keyed onto the turn that made them.
|
|
16486
|
+
*
|
|
16487
|
+
* This reads the settled tool results whatever the work-view switch says: a
|
|
16488
|
+
* produced document is part of the answer, not tool noise, so a stand that
|
|
16489
|
+
* hides the tool rows must still hand the file to the reader. The turn is
|
|
16490
|
+
* resolved exactly as the work rows resolve it, because the card belongs to the
|
|
16491
|
+
* answer the same turn wrote.
|
|
16492
|
+
*/
|
|
16493
|
+
function collectTurnArtifacts(nodes, turns, toolHeads) {
|
|
16494
|
+
let nearestTurn;
|
|
16495
|
+
for (const node of nodes) {
|
|
16496
|
+
if (node.kind === "assistant") nearestTurn = node.turn;
|
|
16497
|
+
if (node.kind !== "tool-result") continue;
|
|
16498
|
+
const head = toolHeads.get(node.callId);
|
|
16499
|
+
const name = head?.name ?? node.call?.name;
|
|
16500
|
+
const turnNumber = head?.turn ?? nearestTurn;
|
|
16501
|
+
if (name === void 0 || turnNumber === void 0) continue;
|
|
16502
|
+
const buffer = getTurn(turns, turnNumber);
|
|
16503
|
+
for (const artifact of artifactsOfToolResult(name, flattenToolOutput(node))) {
|
|
16504
|
+
if (buffer.artifacts.some((seen) => seen.path === artifact.path)) continue;
|
|
16505
|
+
buffer.artifacts.push(artifact);
|
|
16506
|
+
}
|
|
16507
|
+
}
|
|
16508
|
+
}
|
|
16338
16509
|
function collectRunningTool(call, turns, toolHeads) {
|
|
16339
16510
|
const head = toolHeads.get(call.callId);
|
|
16340
16511
|
getTurn(turns, call.turn).work.push({
|
|
@@ -16420,7 +16591,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16420
16591
|
turn: turn.turn,
|
|
16421
16592
|
...finalText.seq === void 0 ? {} : { seq: finalText.seq },
|
|
16422
16593
|
...finalText.timestamp === void 0 ? {} : { timestamp: finalText.timestamp },
|
|
16423
|
-
...finalText.stats === void 0 ? {} : { stats: finalText.stats }
|
|
16594
|
+
...finalText.stats === void 0 ? {} : { stats: finalText.stats },
|
|
16595
|
+
...turn.artifacts.length === 0 ? {} : { artifacts: turn.artifacts }
|
|
16424
16596
|
}
|
|
16425
16597
|
});
|
|
16426
16598
|
}
|
|
@@ -16428,6 +16600,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16428
16600
|
function projectTranscript(snapshot, options = {}) {
|
|
16429
16601
|
const legacy = chatLegacyOf(snapshot);
|
|
16430
16602
|
const running = options.running === true;
|
|
16603
|
+
const workspaceRoot = options.workspaceRoot;
|
|
16431
16604
|
const output = [];
|
|
16432
16605
|
const turns = /* @__PURE__ */ new Map();
|
|
16433
16606
|
const toolHeads = /* @__PURE__ */ new Map();
|
|
@@ -16450,7 +16623,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16450
16623
|
...files.length === 0 ? {} : { files }
|
|
16451
16624
|
}
|
|
16452
16625
|
});
|
|
16453
|
-
} else if (node.kind === "assistant") collectAssistant(node, turns, toolHeads, options.showReasoning === true);
|
|
16626
|
+
} else if (node.kind === "assistant") collectAssistant(node, turns, toolHeads, options.showReasoning === true, workspaceRoot);
|
|
16454
16627
|
else if (node.kind === "context") {
|
|
16455
16628
|
if (!(node.producer.label ?? "").toLowerCase().startsWith("subagent")) continue;
|
|
16456
16629
|
const text = visibleContentText(node.content);
|
|
@@ -16517,13 +16690,14 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16517
16690
|
timestamp: node.time
|
|
16518
16691
|
}
|
|
16519
16692
|
});
|
|
16693
|
+
collectTurnArtifacts(legacy.nodes, turns, toolHeads);
|
|
16520
16694
|
if (options.showToolActivity === true) {
|
|
16521
16695
|
const settled = collectSettledTools(legacy.nodes, turns, toolHeads);
|
|
16522
16696
|
for (const call of legacy.runningCalls) if (!settled.has(call.callId)) collectRunningTool(call, turns, toolHeads);
|
|
16523
16697
|
}
|
|
16524
16698
|
if (legacy.partial !== null) {
|
|
16525
16699
|
const partialTurn = getTurn(turns, legacy.partial.turn);
|
|
16526
|
-
const text = visibleAssistantText(legacy.partial.blocks);
|
|
16700
|
+
const text = visibleAssistantText(legacy.partial.blocks, workspaceRoot);
|
|
16527
16701
|
if (text !== "") partialTurn.text.push({
|
|
16528
16702
|
id: `assistant:partial:${legacy.partial.turn}:${legacy.partial.step}`,
|
|
16529
16703
|
order: Number.MAX_SAFE_INTEGER - 1,
|
|
@@ -16687,7 +16861,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16687
16861
|
showToolActivity: config.ui.showToolActivity,
|
|
16688
16862
|
showReasoning: config.ui.showReasoning,
|
|
16689
16863
|
subagentNames: input.subagentNames,
|
|
16690
|
-
subagentCodenames: config.ui.subagentCodenames
|
|
16864
|
+
subagentCodenames: config.ui.subagentCodenames,
|
|
16865
|
+
workspaceRoot: input.workspaceRoot
|
|
16691
16866
|
}).map((message) => {
|
|
16692
16867
|
if (message.role === "user" && input.author !== void 0) return {
|
|
16693
16868
|
...message,
|
|
@@ -17425,10 +17600,29 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17425
17600
|
}
|
|
17426
17601
|
if (this.disposed || this.generation !== owned) return;
|
|
17427
17602
|
}
|
|
17603
|
+
this.enterDraft();
|
|
17604
|
+
}
|
|
17605
|
+
/**
|
|
17606
|
+
* Put a draft on the screen: no session, so no row in the chat history and no
|
|
17607
|
+
* record on the Host until the first prompt is sent into it
|
|
17608
|
+
* ({@link materializeDraft}). Taking the screen moves the generation the way
|
|
17609
|
+
* every other path that retires a binding does, so an adoption still looking
|
|
17610
|
+
* for its session measures itself against the new one rather than taking the
|
|
17611
|
+
* draft back.
|
|
17612
|
+
*
|
|
17613
|
+
* A draft that is already on screen — including one whose first send fell
|
|
17614
|
+
* short of a claimed session — keeps its chat identity: a new one rebuilds the
|
|
17615
|
+
* composer over the question the visitor is still looking at.
|
|
17616
|
+
*/
|
|
17617
|
+
enterDraft() {
|
|
17428
17618
|
this.generation += 1;
|
|
17429
17619
|
this.materializing = void 0;
|
|
17430
17620
|
this.drafting = true;
|
|
17431
|
-
this.openChat();
|
|
17621
|
+
if (this.namedSession !== null) this.openChat();
|
|
17622
|
+
else {
|
|
17623
|
+
this.pendingSubmission = void 0;
|
|
17624
|
+
this.admissionPending = false;
|
|
17625
|
+
}
|
|
17432
17626
|
this.unbind();
|
|
17433
17627
|
this.operationError = null;
|
|
17434
17628
|
this.policyReady = false;
|
|
@@ -17638,6 +17832,11 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17638
17832
|
this.listeners.clear();
|
|
17639
17833
|
}
|
|
17640
17834
|
async ensureSessionNow() {
|
|
17835
|
+
const resumable = this.config.session.policy === "browser-persistent" && this.chats.activeId() !== null;
|
|
17836
|
+
if (this.config.session.policy !== "fixed" && !resumable) {
|
|
17837
|
+
this.enterDraft();
|
|
17838
|
+
return;
|
|
17839
|
+
}
|
|
17641
17840
|
const operation = ++this.generation;
|
|
17642
17841
|
this.drafting = false;
|
|
17643
17842
|
this.state = {
|
|
@@ -17666,12 +17865,10 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17666
17865
|
existing = true;
|
|
17667
17866
|
} else if (stored !== null) this.chats.clearActive();
|
|
17668
17867
|
}
|
|
17669
|
-
if (id === null)
|
|
17670
|
-
|
|
17671
|
-
|
|
17672
|
-
|
|
17673
|
-
adminPreview: this.adminPreview
|
|
17674
|
-
});
|
|
17868
|
+
if (id === null) {
|
|
17869
|
+
this.enterDraft();
|
|
17870
|
+
return;
|
|
17871
|
+
}
|
|
17675
17872
|
if (this.disposed || operation !== this.generation) return;
|
|
17676
17873
|
try {
|
|
17677
17874
|
if (!await this.bind(id, {
|
|
@@ -17942,7 +18139,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17942
18139
|
publish() {
|
|
17943
18140
|
if (this.disposed) return;
|
|
17944
18141
|
const connected = this.connection.getSnapshot() !== void 0;
|
|
17945
|
-
|
|
18142
|
+
const refusedDraft = this.drafting && this.namedSession === null && this.materializing === void 0;
|
|
18143
|
+
if (this.drafting && (this.session === void 0 || refusedDraft)) {
|
|
17946
18144
|
const materializing = this.materializing !== void 0 || this.pendingSubmission !== void 0;
|
|
17947
18145
|
this.state = {
|
|
17948
18146
|
...QA_SESSION_IDLE_STATE,
|
|
@@ -17972,7 +18170,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17972
18170
|
const conversationSnapshot = this.conversationBinding?.snapshot.getSnapshot();
|
|
17973
18171
|
const projectedSourceBundles = projectTurnSources(conversationSnapshot, sessionId, this.sourceAnchor(sessionId));
|
|
17974
18172
|
const sourceBundles = this.hostSources.merge(projectedSourceBundles);
|
|
17975
|
-
if (!snapshot.running) this.hostSources.refresh(sessionId, () => this.publish());
|
|
18173
|
+
if (!snapshot.running && this.viewingSubagent === null) this.hostSources.refresh(sessionId, () => this.publish());
|
|
17976
18174
|
this.probePending(sessionId, connected);
|
|
17977
18175
|
this.syncPendingPolling(snapshot.running === true && !this.compatibilityReadOnly);
|
|
17978
18176
|
const queuedMessages = this.queuedMessages();
|
|
@@ -17983,6 +18181,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17983
18181
|
sessionSnapshot: snapshot,
|
|
17984
18182
|
conversationSnapshot,
|
|
17985
18183
|
sourceBundles,
|
|
18184
|
+
workspaceRoot: this.sourceAnchor(sessionId),
|
|
17986
18185
|
approvals: this.hostApprovals.list(),
|
|
17987
18186
|
questions: this.hostQuestions.list(),
|
|
17988
18187
|
author: this.accounts?.messageAuthorOf(sessionId),
|
|
@@ -18617,6 +18816,14 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18617
18816
|
}
|
|
18618
18817
|
//#endregion
|
|
18619
18818
|
//#region src/client/components/QaAuthGate.tsx
|
|
18819
|
+
/** The Host's address shape, mirrored so the card refuses before the round trip. */
|
|
18820
|
+
const EMAIL_PATTERN = /^[^\s@]+@[^\s@]+\.[^\s@]+$/u;
|
|
18821
|
+
/** Own copy for input the browser would otherwise answer with its own English bubble. */
|
|
18822
|
+
function refusalOf(email, password) {
|
|
18823
|
+
if (!EMAIL_PATTERN.test(email.trim().toLowerCase())) return accountsErrorMessage("invalid-email");
|
|
18824
|
+
if (password !== null && password.length < 8) return accountsErrorMessage("weak-password");
|
|
18825
|
+
return null;
|
|
18826
|
+
}
|
|
18620
18827
|
function Logo({ logoUrl }) {
|
|
18621
18828
|
if (logoUrl !== null) return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("img", {
|
|
18622
18829
|
className: "dsh-qa-auth__logo",
|
|
@@ -18635,7 +18842,9 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18635
18842
|
/**
|
|
18636
18843
|
* The full-frame login/registration card shown instead of the chat while the
|
|
18637
18844
|
* deployment has accounts enabled and the browser holds no valid identity.
|
|
18638
|
-
*
|
|
18845
|
+
* Both halves of the error line are the surface's own copy: the card refuses
|
|
18846
|
+
* mistyped input itself, and renders the Host's coarse codes in audience-safe
|
|
18847
|
+
* words.
|
|
18639
18848
|
*/
|
|
18640
18849
|
function QaAuthGate(props) {
|
|
18641
18850
|
const { snapshot, accounts } = props;
|
|
@@ -18645,11 +18854,16 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18645
18854
|
const notice = gate?.notice ?? null;
|
|
18646
18855
|
const [email, setEmail] = (0, react.useState)("");
|
|
18647
18856
|
const [password, setPassword] = (0, react.useState)("");
|
|
18857
|
+
const [refusal, setRefusal] = (0, react.useState)(null);
|
|
18648
18858
|
const showRegister = props.allowRegistration;
|
|
18649
18859
|
const reset = mode === "reset";
|
|
18860
|
+
const error = refusal ?? gate?.error ?? null;
|
|
18650
18861
|
const submit = (event) => {
|
|
18651
18862
|
event.preventDefault();
|
|
18652
18863
|
if (busy) return;
|
|
18864
|
+
const next = refusalOf(email, reset ? null : password);
|
|
18865
|
+
setRefusal(next);
|
|
18866
|
+
if (next !== null) return;
|
|
18653
18867
|
reset ? accounts.requestPasswordReset(email) : mode === "register" ? accounts.register(email, password) : accounts.login(email, password);
|
|
18654
18868
|
};
|
|
18655
18869
|
return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("main", {
|
|
@@ -18659,6 +18873,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18659
18873
|
children: /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("form", {
|
|
18660
18874
|
className: "dsh-qa-auth__card",
|
|
18661
18875
|
"data-testid": "qa-surface-auth-card",
|
|
18876
|
+
noValidate: true,
|
|
18662
18877
|
onSubmit: submit,
|
|
18663
18878
|
children: [
|
|
18664
18879
|
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
@@ -18685,7 +18900,10 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18685
18900
|
"data-testid": "qa-surface-auth-tab-login",
|
|
18686
18901
|
"aria-selected": mode === "login",
|
|
18687
18902
|
className: mode === "login" ? "dsh-qa-auth__tab dsh-qa-auth__tab--active" : "dsh-qa-auth__tab",
|
|
18688
|
-
onClick: () =>
|
|
18903
|
+
onClick: () => {
|
|
18904
|
+
setRefusal(null);
|
|
18905
|
+
accounts.setMode("login");
|
|
18906
|
+
},
|
|
18689
18907
|
children: "Вход"
|
|
18690
18908
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
18691
18909
|
type: "button",
|
|
@@ -18693,7 +18911,10 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18693
18911
|
"data-testid": "qa-surface-auth-tab-register",
|
|
18694
18912
|
"aria-selected": mode === "register",
|
|
18695
18913
|
className: mode === "register" ? "dsh-qa-auth__tab dsh-qa-auth__tab--active" : "dsh-qa-auth__tab",
|
|
18696
|
-
onClick: () =>
|
|
18914
|
+
onClick: () => {
|
|
18915
|
+
setRefusal(null);
|
|
18916
|
+
accounts.setMode("register");
|
|
18917
|
+
},
|
|
18697
18918
|
children: "Регистрация"
|
|
18698
18919
|
})]
|
|
18699
18920
|
}) : null,
|
|
@@ -18708,7 +18929,10 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18708
18929
|
required: true,
|
|
18709
18930
|
disabled: busy,
|
|
18710
18931
|
value: email,
|
|
18711
|
-
onChange: (event) =>
|
|
18932
|
+
onChange: (event) => {
|
|
18933
|
+
setRefusal(null);
|
|
18934
|
+
setEmail(event.currentTarget.value);
|
|
18935
|
+
}
|
|
18712
18936
|
})]
|
|
18713
18937
|
}),
|
|
18714
18938
|
reset ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("label", {
|
|
@@ -18723,15 +18947,18 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18723
18947
|
minLength: 8,
|
|
18724
18948
|
disabled: busy,
|
|
18725
18949
|
value: password,
|
|
18726
|
-
onChange: (event) =>
|
|
18950
|
+
onChange: (event) => {
|
|
18951
|
+
setRefusal(null);
|
|
18952
|
+
setPassword(event.currentTarget.value);
|
|
18953
|
+
}
|
|
18727
18954
|
})]
|
|
18728
18955
|
}),
|
|
18729
|
-
|
|
18956
|
+
error === null ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
18730
18957
|
className: "dsh-qa-auth__error",
|
|
18731
18958
|
"data-testid": "qa-surface-auth-error",
|
|
18732
18959
|
role: "alert",
|
|
18733
|
-
children:
|
|
18734
|
-
})
|
|
18960
|
+
children: error
|
|
18961
|
+
}),
|
|
18735
18962
|
notice === null ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
18736
18963
|
className: "dsh-qa-auth__notice",
|
|
18737
18964
|
"data-testid": "qa-surface-auth-notice",
|
|
@@ -18750,7 +18977,10 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18750
18977
|
className: "dsh-qa-auth__link",
|
|
18751
18978
|
"data-testid": "qa-surface-auth-forgot",
|
|
18752
18979
|
disabled: busy,
|
|
18753
|
-
onClick: () =>
|
|
18980
|
+
onClick: () => {
|
|
18981
|
+
setRefusal(null);
|
|
18982
|
+
accounts.setMode(reset ? "login" : "reset");
|
|
18983
|
+
},
|
|
18754
18984
|
children: reset ? "Вернуться ко входу" : "Забыли пароль?"
|
|
18755
18985
|
})
|
|
18756
18986
|
]
|
|
@@ -19560,11 +19790,24 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
19560
19790
|
return extension.length > 0 && extension.length <= 4 ? extension.toUpperCase() : "FILE";
|
|
19561
19791
|
}
|
|
19562
19792
|
/**
|
|
19563
|
-
* One attached file: the extension badge, the name and the size.
|
|
19564
|
-
*
|
|
19565
|
-
*
|
|
19793
|
+
* One attached file: the extension badge, the name and the size. A sent
|
|
19794
|
+
* attachment shows the handle the model resolved and the browser never
|
|
19795
|
+
* re-reads its bytes; a file the turn produced is the same chip with the two
|
|
19796
|
+
* controls that make it usable — open it, or take it away.
|
|
19566
19797
|
*/
|
|
19567
|
-
function QaFileAttachment({ name, bytes, tone, onRemove }) {
|
|
19798
|
+
function QaFileAttachment({ name, bytes, tone, onRemove, onOpen, onDownload }) {
|
|
19799
|
+
const text = /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("span", {
|
|
19800
|
+
className: "dsh-qa-file__text",
|
|
19801
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
19802
|
+
className: "dsh-qa-file__name",
|
|
19803
|
+
"data-testid": "qa-file-name",
|
|
19804
|
+
children: name
|
|
19805
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
19806
|
+
className: "dsh-qa-file__meta",
|
|
19807
|
+
"data-testid": "qa-file-size",
|
|
19808
|
+
children: formatFileSize(bytes)
|
|
19809
|
+
})]
|
|
19810
|
+
});
|
|
19568
19811
|
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("span", {
|
|
19569
19812
|
className: "dsh-qa-file",
|
|
19570
19813
|
"data-testid": "qa-file",
|
|
@@ -19577,17 +19820,23 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
19577
19820
|
"aria-hidden": "true",
|
|
19578
19821
|
children: badgeText(name)
|
|
19579
19822
|
}),
|
|
19580
|
-
/* @__PURE__ */ (0, react_jsx_runtime.
|
|
19581
|
-
|
|
19582
|
-
|
|
19583
|
-
|
|
19584
|
-
|
|
19585
|
-
|
|
19586
|
-
|
|
19587
|
-
|
|
19588
|
-
|
|
19589
|
-
|
|
19590
|
-
|
|
19823
|
+
onOpen === void 0 ? text : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
19824
|
+
type: "button",
|
|
19825
|
+
className: "dsh-qa-file__open",
|
|
19826
|
+
"data-testid": "qa-file-open",
|
|
19827
|
+
"aria-label": `Открыть ${name}`,
|
|
19828
|
+
title: `Открыть ${name}`,
|
|
19829
|
+
onClick: onOpen,
|
|
19830
|
+
children: text
|
|
19831
|
+
}),
|
|
19832
|
+
onDownload === void 0 ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
19833
|
+
type: "button",
|
|
19834
|
+
className: "dsh-qa-file__download",
|
|
19835
|
+
"data-testid": "qa-file-download",
|
|
19836
|
+
"aria-label": `Скачать ${name}`,
|
|
19837
|
+
title: "Скачать",
|
|
19838
|
+
onClick: onDownload,
|
|
19839
|
+
children: "Скачать"
|
|
19591
19840
|
}),
|
|
19592
19841
|
onRemove === void 0 ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
19593
19842
|
type: "button",
|
|
@@ -21574,6 +21823,124 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
21574
21823
|
};
|
|
21575
21824
|
}
|
|
21576
21825
|
//#endregion
|
|
21826
|
+
//#region src/client/markdown/use-transient-flag.ts
|
|
21827
|
+
/**
|
|
21828
|
+
* A boolean that turns on for a fixed window and drops back off — the
|
|
21829
|
+
* "Скопировано" flash and its siblings. The pending timer lives in a ref and
|
|
21830
|
+
* is cleared by the unmount cleanup, so a pulse fired right before the block
|
|
21831
|
+
* leaves the DOM never schedules a state update on it, and re-pulsing restarts
|
|
21832
|
+
* the window instead of stacking timers.
|
|
21833
|
+
*/
|
|
21834
|
+
function useTransientFlag(windowMs) {
|
|
21835
|
+
const [on, setOn] = (0, react.useState)(false);
|
|
21836
|
+
const timer = (0, react.useRef)(void 0);
|
|
21837
|
+
(0, react.useEffect)(() => () => {
|
|
21838
|
+
if (timer.current !== void 0) clearTimeout(timer.current);
|
|
21839
|
+
}, []);
|
|
21840
|
+
return {
|
|
21841
|
+
on,
|
|
21842
|
+
pulse: (0, react.useCallback)(() => {
|
|
21843
|
+
setOn(true);
|
|
21844
|
+
if (timer.current !== void 0) clearTimeout(timer.current);
|
|
21845
|
+
timer.current = setTimeout(() => {
|
|
21846
|
+
timer.current = void 0;
|
|
21847
|
+
setOn(false);
|
|
21848
|
+
}, windowMs);
|
|
21849
|
+
}, [windowMs])
|
|
21850
|
+
};
|
|
21851
|
+
}
|
|
21852
|
+
//#endregion
|
|
21853
|
+
//#region src/client/clipboard.ts
|
|
21854
|
+
/** How long the confirmation that a copy landed stays on screen. */
|
|
21855
|
+
const COPIED_WINDOW_MS = 1200;
|
|
21856
|
+
/**
|
|
21857
|
+
* The sentence a copy affordance falls back to. Three surfaces show it, so it
|
|
21858
|
+
* is written once.
|
|
21859
|
+
*/
|
|
21860
|
+
const COPY_MANUAL_HINT = "Скопируйте вручную";
|
|
21861
|
+
/** The reason behind that sentence, for the tooltip that carries it. */
|
|
21862
|
+
const COPY_MANUAL_REASON = "Браузер не отдаёт буфер обмена — выделите текст и скопируйте его сами";
|
|
21863
|
+
function hasClipboardApi() {
|
|
21864
|
+
return navigator.clipboard?.writeText !== void 0;
|
|
21865
|
+
}
|
|
21866
|
+
/**
|
|
21867
|
+
* Whether this browser can be asked to move text at all.
|
|
21868
|
+
*
|
|
21869
|
+
* The stand is served over plain HTTP on a LAN address, and there
|
|
21870
|
+
* `window.isSecureContext` is false, so the browser never exposes
|
|
21871
|
+
* `navigator.clipboard`. The older copy command still works in an insecure
|
|
21872
|
+
* context, which is why the absence of the API alone does not mean copying is
|
|
21873
|
+
* impossible — and why asking for it anyway only ends in silence.
|
|
21874
|
+
*/
|
|
21875
|
+
function canCopyToClipboard() {
|
|
21876
|
+
return hasClipboardApi() || typeof document.execCommand === "function";
|
|
21877
|
+
}
|
|
21878
|
+
/**
|
|
21879
|
+
* Write `text` to the clipboard, resolving false when nothing took it — the
|
|
21880
|
+
* caller then says so instead of leaving the click unanswered.
|
|
21881
|
+
*/
|
|
21882
|
+
async function copyTextToClipboard(text) {
|
|
21883
|
+
const clipboard = navigator.clipboard;
|
|
21884
|
+
if (clipboard?.writeText !== void 0) try {
|
|
21885
|
+
await clipboard.writeText(text);
|
|
21886
|
+
return true;
|
|
21887
|
+
} catch {}
|
|
21888
|
+
return copyThroughField(text);
|
|
21889
|
+
}
|
|
21890
|
+
/** The pre-API path: select a throwaway field and ask the browser to copy it. */
|
|
21891
|
+
function copyThroughField(text) {
|
|
21892
|
+
const field = document.createElement("textarea");
|
|
21893
|
+
field.value = text;
|
|
21894
|
+
field.readOnly = true;
|
|
21895
|
+
field.setAttribute("aria-hidden", "true");
|
|
21896
|
+
field.style.position = "fixed";
|
|
21897
|
+
field.style.top = "0";
|
|
21898
|
+
field.style.left = "-100vw";
|
|
21899
|
+
document.body.appendChild(field);
|
|
21900
|
+
field.select();
|
|
21901
|
+
try {
|
|
21902
|
+
return document.execCommand("copy");
|
|
21903
|
+
} catch {
|
|
21904
|
+
return false;
|
|
21905
|
+
} finally {
|
|
21906
|
+
field.remove();
|
|
21907
|
+
}
|
|
21908
|
+
}
|
|
21909
|
+
/**
|
|
21910
|
+
* The copy state one affordance needs: the confirmation window, the refusal
|
|
21911
|
+
* that replaces it with the manual hint, and whether either was ever possible.
|
|
21912
|
+
*/
|
|
21913
|
+
function useCopyAction(text) {
|
|
21914
|
+
const [impossible] = (0, react.useState)(() => !canCopyToClipboard());
|
|
21915
|
+
const { on: copied, pulse } = useTransientFlag(COPIED_WINDOW_MS);
|
|
21916
|
+
const [refused, setRefused] = (0, react.useState)(false);
|
|
21917
|
+
return {
|
|
21918
|
+
copied,
|
|
21919
|
+
impossible,
|
|
21920
|
+
refused,
|
|
21921
|
+
copy: (0, react.useCallback)(() => {
|
|
21922
|
+
copyTextToClipboard(text).then((ok) => {
|
|
21923
|
+
setRefused(!ok);
|
|
21924
|
+
if (ok) pulse();
|
|
21925
|
+
});
|
|
21926
|
+
}, [text, pulse])
|
|
21927
|
+
};
|
|
21928
|
+
}
|
|
21929
|
+
//#endregion
|
|
21930
|
+
//#region src/client/components/copy-hint.tsx
|
|
21931
|
+
/**
|
|
21932
|
+
* What a copy affordance shows where copying cannot happen: a sentence naming
|
|
21933
|
+
* the dead end, in place of a button that would only look like it worked.
|
|
21934
|
+
*/
|
|
21935
|
+
function CopyHint({ testId }) {
|
|
21936
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
21937
|
+
className: "dsh-qa-copy-hint",
|
|
21938
|
+
"data-testid": testId,
|
|
21939
|
+
title: COPY_MANUAL_REASON,
|
|
21940
|
+
children: COPY_MANUAL_HINT
|
|
21941
|
+
});
|
|
21942
|
+
}
|
|
21943
|
+
//#endregion
|
|
21577
21944
|
//#region src/client/markdown/highlight.ts
|
|
21578
21945
|
/** Double and single quotes that end at the line they start on. */
|
|
21579
21946
|
const QUOTES = [{
|
|
@@ -22698,36 +23065,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
22698
23065
|
return cursor;
|
|
22699
23066
|
}
|
|
22700
23067
|
//#endregion
|
|
22701
|
-
//#region src/client/markdown/use-transient-flag.ts
|
|
22702
|
-
/**
|
|
22703
|
-
* A boolean that turns on for a fixed window and drops back off — the
|
|
22704
|
-
* "Скопировано" flash and its siblings. The pending timer lives in a ref and
|
|
22705
|
-
* is cleared by the unmount cleanup, so a pulse fired right before the block
|
|
22706
|
-
* leaves the DOM never schedules a state update on it, and re-pulsing restarts
|
|
22707
|
-
* the window instead of stacking timers.
|
|
22708
|
-
*/
|
|
22709
|
-
function useTransientFlag(windowMs) {
|
|
22710
|
-
const [on, setOn] = (0, react.useState)(false);
|
|
22711
|
-
const timer = (0, react.useRef)(void 0);
|
|
22712
|
-
(0, react.useEffect)(() => () => {
|
|
22713
|
-
if (timer.current !== void 0) clearTimeout(timer.current);
|
|
22714
|
-
}, []);
|
|
22715
|
-
return {
|
|
22716
|
-
on,
|
|
22717
|
-
pulse: (0, react.useCallback)(() => {
|
|
22718
|
-
setOn(true);
|
|
22719
|
-
if (timer.current !== void 0) clearTimeout(timer.current);
|
|
22720
|
-
timer.current = setTimeout(() => {
|
|
22721
|
-
timer.current = void 0;
|
|
22722
|
-
setOn(false);
|
|
22723
|
-
}, windowMs);
|
|
22724
|
-
}, [windowMs])
|
|
22725
|
-
};
|
|
22726
|
-
}
|
|
22727
|
-
//#endregion
|
|
22728
23068
|
//#region src/client/markdown/CodeBlock.tsx
|
|
22729
|
-
/** Copied-label window: long enough to read, short enough to not stick. */
|
|
22730
|
-
const COPIED_MS = 1200;
|
|
22731
23069
|
/**
|
|
22732
23070
|
* One fenced code block: the language banner, a copy button, and the code
|
|
22733
23071
|
* itself. Highlighting is our own scanner (see `highlight.ts`) — the fence is
|
|
@@ -22736,12 +23074,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
22736
23074
|
*/
|
|
22737
23075
|
const CodeBlock = (0, react.memo)(function CodeBlock({ code, lang }) {
|
|
22738
23076
|
const lines = (0, react.useMemo)(() => highlightLines(code, lang), [code, lang]);
|
|
22739
|
-
const
|
|
22740
|
-
const onCopy = (0, react.useCallback)(() => {
|
|
22741
|
-
const clipboard = navigator.clipboard;
|
|
22742
|
-
if (clipboard === void 0) return;
|
|
22743
|
-
clipboard.writeText(code).then(pulseCopied, () => void 0);
|
|
22744
|
-
}, [code, pulseCopied]);
|
|
23077
|
+
const copy = useCopyAction(code);
|
|
22745
23078
|
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
22746
23079
|
className: "dsh-qa-md-code",
|
|
22747
23080
|
"data-testid": "qa-md-code",
|
|
@@ -22752,14 +23085,14 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
22752
23085
|
className: "dsh-qa-md-code__lang",
|
|
22753
23086
|
"data-testid": "qa-md-code-lang",
|
|
22754
23087
|
children: lang ?? ""
|
|
22755
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
23088
|
+
}), copy.impossible ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)(CopyHint, { testId: "qa-md-code-copy-hint" }) : /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
22756
23089
|
type: "button",
|
|
22757
23090
|
className: "dsh-qa-md-code__copy",
|
|
22758
23091
|
"data-testid": "qa-md-code-copy",
|
|
22759
|
-
onClick:
|
|
22760
|
-
"aria-label": copied ? "Скопировано" : "Копировать код",
|
|
22761
|
-
children: copied ? "Скопировано" : "Копировать"
|
|
22762
|
-
})]
|
|
23092
|
+
onClick: copy.copy,
|
|
23093
|
+
"aria-label": copy.copied ? "Скопировано" : "Копировать код",
|
|
23094
|
+
children: copy.copied ? "Скопировано" : "Копировать"
|
|
23095
|
+
}), copy.refused ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)(CopyHint, { testId: "qa-md-code-copy-hint" }) : null] })]
|
|
22763
23096
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("pre", {
|
|
22764
23097
|
tabIndex: 0,
|
|
22765
23098
|
"data-testid": "qa-md-code-pre",
|
|
@@ -50301,7 +50634,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50301
50634
|
if (a.role === "work" && b.role === "work") return a.turn === b.turn && a.startedAt === b.startedAt && a.endedAt === b.endedAt && sameWorkItems(a.items, b.items);
|
|
50302
50635
|
if (a.role === "work" || b.role === "work") return false;
|
|
50303
50636
|
if (a.text !== b.text || a.timestamp !== b.timestamp) return false;
|
|
50304
|
-
if (a.role === "assistant" && b.role === "assistant") return sameSources(a.sources, b.sources) && a.stats === void 0 === (b.stats === void 0) && (a.stats === void 0 || b.stats === void 0 || a.stats.durationMs === b.stats.durationMs && a.stats.ttftMs === b.stats.ttftMs && a.stats.tokensPerSecond === b.stats.tokensPerSecond);
|
|
50637
|
+
if (a.role === "assistant" && b.role === "assistant") return sameSources(a.sources, b.sources) && sameArtifacts(a.artifacts, b.artifacts) && a.stats === void 0 === (b.stats === void 0) && (a.stats === void 0 || b.stats === void 0 || a.stats.durationMs === b.stats.durationMs && a.stats.ttftMs === b.stats.ttftMs && a.stats.tokensPerSecond === b.stats.tokensPerSecond);
|
|
50305
50638
|
if (a.role === "user" && b.role === "user") return a.author === b.author && sameImages(a.images, b.images) && sameFiles(a.files, b.files);
|
|
50306
50639
|
if (a.role === "system" && b.role === "system") return a.notice === void 0 === (b.notice === void 0) && (a.notice === void 0 || b.notice === void 0 || a.notice.title === b.notice.title && a.notice.body === b.notice.body && a.notice.meta === b.notice.meta);
|
|
50307
50640
|
return false;
|
|
@@ -50321,6 +50654,11 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50321
50654
|
if (a === void 0 || b === void 0 || a.length !== b.length) return false;
|
|
50322
50655
|
return a.every((file, index) => file.attachmentId === b[index].attachmentId && file.name === b[index].name && file.bytes === b[index].bytes);
|
|
50323
50656
|
}
|
|
50657
|
+
function sameArtifacts(a, b) {
|
|
50658
|
+
if (a === b) return true;
|
|
50659
|
+
if (a === void 0 || b === void 0 || a.length !== b.length) return false;
|
|
50660
|
+
return a.every((artifact, index) => artifact.path === b[index].path && artifact.name === b[index].name && artifact.format === b[index].format && artifact.bytes === b[index].bytes);
|
|
50661
|
+
}
|
|
50324
50662
|
const REASONS = [
|
|
50325
50663
|
"incorrect",
|
|
50326
50664
|
"instruction_not_followed",
|
|
@@ -50411,9 +50749,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50411
50749
|
}
|
|
50412
50750
|
return parts;
|
|
50413
50751
|
}
|
|
50414
|
-
const QaMessage = (0, react.memo)(function QaMessage({ message, renderMarkdown, showTimestamp, stateKey, onRegenerate, resolveImage, onOpenSources, onSourceDetail, thinkingPhrases, onRateFeedback }) {
|
|
50415
|
-
const
|
|
50416
|
-
const copiedTimer = (0, react.useRef)(void 0);
|
|
50752
|
+
const QaMessage = (0, react.memo)(function QaMessage({ message, renderMarkdown, showTimestamp, stateKey, onRegenerate, resolveImage, onOpenSources, onSourceDetail, onArtifactOpen, onArtifactDownload, thinkingPhrases, onRateFeedback }) {
|
|
50753
|
+
const { copied, impossible: copyImpossible, refused: copyRefused, copy } = useCopyAction(message.role === "work" ? "" : message.text);
|
|
50417
50754
|
const [rating, setRating] = (0, react.useState)(null);
|
|
50418
50755
|
const [askingWhy, setAskingWhy] = (0, react.useState)(false);
|
|
50419
50756
|
const refsCache = (0, react.useRef)({
|
|
@@ -50431,9 +50768,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50431
50768
|
(0, react.useEffect)(() => {
|
|
50432
50769
|
setRating(readRatings(stateKey)[message.id] ?? null);
|
|
50433
50770
|
}, [stateKey, message.id]);
|
|
50434
|
-
(0, react.useEffect)(() => () => {
|
|
50435
|
-
if (copiedTimer.current !== void 0) clearTimeout(copiedTimer.current);
|
|
50436
|
-
}, []);
|
|
50437
50771
|
if (message.role === "system" && message.command !== void 0) {
|
|
50438
50772
|
const activity = message.command;
|
|
50439
50773
|
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("article", {
|
|
@@ -50515,15 +50849,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50515
50849
|
})
|
|
50516
50850
|
});
|
|
50517
50851
|
const label = message.role === "assistant" ? "Помощник" : message.role === "user" ? message.author ?? "Вы" : "Статус";
|
|
50518
|
-
const copy = async () => {
|
|
50519
|
-
if (copied || navigator.clipboard?.writeText === void 0) return;
|
|
50520
|
-
try {
|
|
50521
|
-
await navigator.clipboard.writeText(message.text);
|
|
50522
|
-
setCopied(true);
|
|
50523
|
-
if (copiedTimer.current !== void 0) clearTimeout(copiedTimer.current);
|
|
50524
|
-
copiedTimer.current = setTimeout(() => setCopied(false), 1200);
|
|
50525
|
-
} catch {}
|
|
50526
|
-
};
|
|
50527
50852
|
const persist = (next, detail) => {
|
|
50528
50853
|
if (next === null || onRateFeedback === void 0) return;
|
|
50529
50854
|
if (message.role !== "assistant" || message.seq === void 0) {
|
|
@@ -50600,6 +50925,18 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50600
50925
|
sourceRefs,
|
|
50601
50926
|
onSourceOpen: onSourceDetail
|
|
50602
50927
|
}) : message.text,
|
|
50928
|
+
message.role === "assistant" && message.artifacts !== void 0 && message.artifacts.length > 0 ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
50929
|
+
className: "dsh-qa-message__artifacts",
|
|
50930
|
+
"data-testid": "qa-message-artifacts",
|
|
50931
|
+
"aria-label": "Созданные файлы",
|
|
50932
|
+
children: message.artifacts.map((artifact) => /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaFileAttachment, {
|
|
50933
|
+
name: artifact.name,
|
|
50934
|
+
bytes: artifact.bytes,
|
|
50935
|
+
tone: "sent",
|
|
50936
|
+
onOpen: onArtifactOpen === void 0 ? void 0 : () => onArtifactOpen(artifact),
|
|
50937
|
+
onDownload: onArtifactDownload === void 0 ? void 0 : () => onArtifactDownload(artifact)
|
|
50938
|
+
}, artifact.path))
|
|
50939
|
+
}) : null,
|
|
50603
50940
|
message.status === "streaming" ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
50604
50941
|
className: "dsh-qa-message__cursor",
|
|
50605
50942
|
"aria-hidden": "true"
|
|
@@ -50632,12 +50969,12 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50632
50969
|
"data-persistent": persistentMeta || void 0,
|
|
50633
50970
|
children: [
|
|
50634
50971
|
message.role === "user" ? meta : null,
|
|
50635
|
-
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
50972
|
+
copyImpossible ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)(CopyHint, { testId: "qa-message-copy-hint" }) : /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
50636
50973
|
type: "button",
|
|
50637
50974
|
"data-testid": "qa-message-copy",
|
|
50638
50975
|
"aria-label": copied ? "Скопировано" : "Скопировать сообщение",
|
|
50639
50976
|
title: copied ? "Скопировано" : "Копировать",
|
|
50640
|
-
onClick:
|
|
50977
|
+
onClick: copy,
|
|
50641
50978
|
children: copied ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)("svg", {
|
|
50642
50979
|
viewBox: "0 0 18 18",
|
|
50643
50980
|
"aria-hidden": "true",
|
|
@@ -50653,7 +50990,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50653
50990
|
rx: "2"
|
|
50654
50991
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("path", { d: "M11.75 11.75v.5a2.5 2.5 0 0 1-2.5 2.5h-3.5a2.5 2.5 0 0 1-2.5-2.5v-3.5a2.5 2.5 0 0 1 2.5-2.5h.5" })]
|
|
50655
50992
|
})
|
|
50656
|
-
}),
|
|
50993
|
+
}), copyRefused ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)(CopyHint, { testId: "qa-message-copy-hint" }) : null] }),
|
|
50657
50994
|
message.role === "user" ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [
|
|
50658
50995
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
50659
50996
|
type: "button",
|
|
@@ -50714,7 +51051,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
50714
51051
|
}) : null
|
|
50715
51052
|
]
|
|
50716
51053
|
});
|
|
50717
|
-
}, (prev, next) => prev.renderMarkdown === next.renderMarkdown && prev.showTimestamp === next.showTimestamp && prev.stateKey === next.stateKey && prev.onRegenerate === next.onRegenerate && prev.resolveImage === next.resolveImage && prev.onOpenSources === next.onOpenSources && prev.onSourceDetail === next.onSourceDetail && prev.thinkingPhrases === next.thinkingPhrases && sameMessage(prev.message, next.message));
|
|
51054
|
+
}, (prev, next) => prev.renderMarkdown === next.renderMarkdown && prev.showTimestamp === next.showTimestamp && prev.stateKey === next.stateKey && prev.onRegenerate === next.onRegenerate && prev.resolveImage === next.resolveImage && prev.onOpenSources === next.onOpenSources && prev.onSourceDetail === next.onSourceDetail && prev.onArtifactOpen === next.onArtifactOpen && prev.onArtifactDownload === next.onArtifactDownload && prev.thinkingPhrases === next.thinkingPhrases && sameMessage(prev.message, next.message));
|
|
50718
51055
|
//#endregion
|
|
50719
51056
|
//#region ../../packages/audit-core/lib/types.js
|
|
50720
51057
|
/**
|
|
@@ -52624,8 +52961,42 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
52624
52961
|
}
|
|
52625
52962
|
//#endregion
|
|
52626
52963
|
//#region src/client/components/QaChangelog.tsx
|
|
52627
|
-
const QA_VERSION = "0.15.
|
|
52964
|
+
const QA_VERSION = "0.15.3";
|
|
52628
52965
|
const QA_CHANGELOG = [
|
|
52966
|
+
{
|
|
52967
|
+
version: "0.15.3",
|
|
52968
|
+
date: "2026-10-08",
|
|
52969
|
+
sections: [{
|
|
52970
|
+
title: "Исправления",
|
|
52971
|
+
items: ["Палитра слэш-команд в чате, который ещё не начался, называет те же навыки, что и в чате, где уже шёл ответ. Пока за разговором не стоял живой агент, список строился по одному общему allow-list'у развёртывания и не сужался ролью: в него попадал навык, который в этом чате вызвать нельзя — имя подсвечивалось, Enter подставлял его в строку, а в ответ приходил отказ, — и наоборот, доступный навык мог не показаться. Теперь роль учитывается при обоих чтениях, а список, который палитра показывает, и список, которым проверяется введённая строка, выводятся из одного правила, поэтому предложение в палитре и возможность его вызвать больше не могут разойтись."]
|
|
52972
|
+
}]
|
|
52973
|
+
},
|
|
52974
|
+
{
|
|
52975
|
+
version: "0.15.2",
|
|
52976
|
+
date: "2026-10-07",
|
|
52977
|
+
sections: [
|
|
52978
|
+
{
|
|
52979
|
+
title: "Исправления",
|
|
52980
|
+
items: ["Кнопка «Копировать» работает на стенде, открытом по http по адресу в локальной сети. Браузер доверяет буфер обмена только защищённым страницам, поэтому на таком стенде современного интерфейса буфера нет вовсе — и нажатие молчало: ни ошибки, ни отметки «Скопировано», ни текста в буфере, а проверка вставлялась пустой. Теперь поверхность сначала пробует буфер, а когда его нет, копирует через временное поле — этот путь доступен и на незащищённой странице. Так копируются код-блок в ответе, ответ целиком и значение интеграционного токена. Если браузер не отдал буфер ни одним путём, на месте кнопки появляется строка «Скопируйте вручную», а там, где кнопка осталась рабочей, та же строка встаёт рядом с ней после отказа: молчание больше не выглядит удачным копированием.", "Палитра слэш-команд в чате, который ещё не начался, называет те же навыки, что и в чате, где уже шёл ответ. Пока за разговором не стоял живой агент, список строился по одному общему allow-list'у развёртывания и не сужался ролью: в него попадал навык, который в этом чате вызвать нельзя — имя подсвечивалось, Enter подставлял его в строку, а в ответ приходил отказ, — и наоборот, доступный навык мог не показаться. Теперь роль учитывается при обоих чтениях, а список, который палитра показывает, и список, которым проверяется введённая строка, выводятся из одного правила, поэтому предложение в палитре и возможность его вызвать больше не могут разойтись."]
|
|
52981
|
+
},
|
|
52982
|
+
{
|
|
52983
|
+
title: "Изменения",
|
|
52984
|
+
items: [
|
|
52985
|
+
"Ряд плагина на странице Plugins называется словами, а не спецификатором пакета. Хост берёт имя и описание ряда из `locale/en.json` — этот файл читается без активации плагина, — и без него подписывает ряд полным именем пакета: вместо «QA Surface» оператор читал `@yadsh/dsh-qa-surface`. То же предложение, что описывает ряд, карточка отвечает и как однострочник на случай, когда описания у ряда нет, — проверка сверяет пару с самим файлом, а не с копией строки в тесте, поэтому ряд не сможет описать одну страницу, открыв другую. Так названы ряды всех плагинов набора.",
|
|
52986
|
+
"Страница настроек Prompt Firewall переехала на панель Plugins: её ряд открывает секцию конфигурации, и карточка больше не рисует свою рамку, заголовок и стрелку — их рисует страница. Раздел, который недоступен этому браузеру, отвечает предложением, а не пустой секцией. Страница Domain Experts села на ряд самого пакета и сняла собственный заголовок: панель уже подписывает пакет его именем и описанием.",
|
|
52987
|
+
"Блоки отказа и опасные действия снова окрашены. Стили ссылались на имена токенов, которых у темы хоста нет (`--dsw-alias-bg-error`, `--dsw-alias-label-error`), а неизвестный `var(--dsw-…)` отбрасывает всю декларацию молча: фон становился прозрачным, цвет — унаследованным, и отказ на вкладке выглядел обычным мелким текстом. Теперь цвет берётся из `--dsw-alias-state-error-primary` с фолбэком, а каждая подстановка `--dsw-*` сверяется с самой темой (`pnpm verify:tokens`), поэтому список несуществующих имён не вырастет."
|
|
52988
|
+
]
|
|
52989
|
+
},
|
|
52990
|
+
{
|
|
52991
|
+
title: "Исправления",
|
|
52992
|
+
items: ["Отказ открыть чат называет причину. Дочерняя сессия субагента — кусок работы, делегированный из другого разговора, — раньше отвергалась теми же тремя словами, что и чат, за которым стенд не смог собрать агента: в консоли читалась подсказка про пресет, который никто не менял, а в журнале стенда на каждое обращение к чату падали две строки уровня ERROR, из-за чего день одного стенда выглядел как двенадцать одинаковых аварий. У этих двух случаев теперь разные лица: дочерняя сессия называется дочерней, и её строка идёт предупреждением — стенд ответил правильно про чужой разговор, и чинить нечего; чат же без агента остаётся ошибкой и в подсказке называет, куда смотреть и что делать (перемонтировать записанный пресет и открыть чат заново), а читателю тем временем остаётся переписка только для чтения и «Новый чат». Панель субагента перестала спрашивать у стенда источники дочерней сессии, которые тот по правилам не выдаёт: доказательства делегированного хода и так приходят в родительский чат, а экран читает их из самого транскрипта."]
|
|
52993
|
+
},
|
|
52994
|
+
{
|
|
52995
|
+
title: "Исправления",
|
|
52996
|
+
items: ["История чатов больше не наполняется пустыми. Вход на поверхность создавал разговор раньше, чем в него что-нибудь написали, и тот оставался в сайдбаре строкой «Новый чат»: шесть заходов одним и тем же аккаунтом — шесть одинаковых строк, а поиск по истории выдавал их вместо разговоров. Теперь разговор появляется вместе с первым отправленным сообщением: зашли, посмотрели, ушли — в истории ничего, и на стенде не осталось сессии, в которую никто не написал. Кнопка «Новый чат» пустой разговор не создавала и раньше; теперь так же ведёт себя и загрузка страницы.", "Созданный по просьбе документ приходит файлом, а не строкой пути. Ответ на «сделай docx» был текстом: карточки под ответом не было, вкладка «Файлы» стояла с «нет вложений», а в тексте печатался путь контейнера вместе с идентификатором аккаунта — раскладка сервера в сообщении, которое на этом стенде может быть видно другим аккаунтом. Теперь под ответом лежит карточка созданного файла с предпросмотром и скачиванием, она же появляется в списке вложений чата, и карточка видна независимо от того, скрыта ли в настройках активность инструментов: файл, который попросили, — это не шум инструментов. Плагины документов сообщают путь файла внутри рабочего каталога чата (тем же написанием, которым этот файл потом снова открывается), а если абсолютный путь всё же попадает в текст ответа — из старого, уже сохранённого хода или собранный моделью из известного ей рабочего каталога, — интерфейс вычитает из него каталог аккаунта, и остаётся имя файла."]
|
|
52997
|
+
}
|
|
52998
|
+
]
|
|
52999
|
+
},
|
|
52629
53000
|
{
|
|
52630
53001
|
version: "0.15.1",
|
|
52631
53002
|
date: "2026-10-05",
|
|
@@ -53150,7 +53521,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
53150
53521
|
className: "dsh-qa-changelog__date",
|
|
53151
53522
|
children: entry.date
|
|
53152
53523
|
}),
|
|
53153
|
-
entry.version === "0.15.
|
|
53524
|
+
entry.version === "0.15.3" ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
53154
53525
|
className: "dsh-qa-changelog__current",
|
|
53155
53526
|
children: "текущая"
|
|
53156
53527
|
}) : null
|
|
@@ -53985,14 +54356,15 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
53985
54356
|
/** Total attachment count across groups; the header badge's value. */
|
|
53986
54357
|
function countChatAttachments(groups) {
|
|
53987
54358
|
let total = 0;
|
|
53988
|
-
for (const group of groups) total += group.files.length + group.images.length;
|
|
54359
|
+
for (const group of groups) total += group.files.length + group.images.length + (group.artifacts?.length ?? 0);
|
|
53989
54360
|
return total;
|
|
53990
54361
|
}
|
|
53991
54362
|
/**
|
|
53992
|
-
* Group the attachments of a chat by their
|
|
53993
|
-
*
|
|
53994
|
-
*
|
|
53995
|
-
*
|
|
54363
|
+
* Group the attachments of a chat by their message. A user message carries what
|
|
54364
|
+
* was sent; an assistant message carries what its turn produced, so a document
|
|
54365
|
+
* the stand made is listed beside the answer that made it instead of only on
|
|
54366
|
+
* disk. Messages with neither are dropped. The groups come out newest first,
|
|
54367
|
+
* matching a roster that grows at the bottom of the transcript.
|
|
53996
54368
|
* @param messages - the chat's projected transcript.
|
|
53997
54369
|
* @returns attachment groups, newest message first.
|
|
53998
54370
|
*/
|
|
@@ -54000,20 +54372,53 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54000
54372
|
const groups = [];
|
|
54001
54373
|
for (let index = messages.length - 1; index >= 0; index -= 1) {
|
|
54002
54374
|
const message = messages[index];
|
|
54003
|
-
if (message === void 0
|
|
54004
|
-
const files = message.files ?? [];
|
|
54005
|
-
const images = message.images ?? [];
|
|
54006
|
-
|
|
54375
|
+
if (message === void 0) continue;
|
|
54376
|
+
const files = message.role === "user" ? message.files ?? [] : [];
|
|
54377
|
+
const images = message.role === "user" ? message.images ?? [] : [];
|
|
54378
|
+
const artifacts = message.role === "assistant" ? message.artifacts ?? [] : [];
|
|
54379
|
+
if (files.length === 0 && images.length === 0 && artifacts.length === 0) continue;
|
|
54380
|
+
const timestamp = message.role === "work" ? void 0 : message.timestamp;
|
|
54007
54381
|
groups.push({
|
|
54008
54382
|
messageId: message.id,
|
|
54009
|
-
...
|
|
54383
|
+
...timestamp === void 0 ? {} : { timestamp },
|
|
54010
54384
|
files,
|
|
54011
|
-
images
|
|
54385
|
+
images,
|
|
54386
|
+
...artifacts.length === 0 ? {} : { artifacts }
|
|
54012
54387
|
});
|
|
54013
54388
|
}
|
|
54014
54389
|
return groups;
|
|
54015
54390
|
}
|
|
54016
54391
|
//#endregion
|
|
54392
|
+
//#region src/client/workspace-download.ts
|
|
54393
|
+
/**
|
|
54394
|
+
* Handing one file of the chat's workspace to the person the turn produced it
|
|
54395
|
+
* for.
|
|
54396
|
+
*
|
|
54397
|
+
* A produced document has no attachment-store handle, so the download is the
|
|
54398
|
+
* same read the files panel does: the Host returns the bytes under the chat's
|
|
54399
|
+
* own fence and the browser's download machinery takes it from there. Shared by
|
|
54400
|
+
* the panel's own viewer and the card under an answer, so the two can never
|
|
54401
|
+
* disagree on what "download this file" means.
|
|
54402
|
+
*/
|
|
54403
|
+
/** Last segment of a workspace path, spelled with either separator. */
|
|
54404
|
+
function fileNameOf(path) {
|
|
54405
|
+
const segments = path.split(/[/\\]/u).filter((segment) => segment !== "");
|
|
54406
|
+
return segments[segments.length - 1] ?? path;
|
|
54407
|
+
}
|
|
54408
|
+
/** Save one workspace file under its own name. */
|
|
54409
|
+
function downloadWorkspaceFile(file) {
|
|
54410
|
+
const bytes = file.base64 === void 0 ? new TextEncoder().encode(file.text ?? "") : base64ToBytes(file.base64);
|
|
54411
|
+
const url = URL.createObjectURL(new Blob([bytes], { type: file.mime }));
|
|
54412
|
+
const anchor = document.createElement("a");
|
|
54413
|
+
anchor.href = url;
|
|
54414
|
+
anchor.download = fileNameOf(file.path);
|
|
54415
|
+
anchor.rel = "noreferrer";
|
|
54416
|
+
document.body.append(anchor);
|
|
54417
|
+
anchor.click();
|
|
54418
|
+
anchor.remove();
|
|
54419
|
+
URL.revokeObjectURL(url);
|
|
54420
|
+
}
|
|
54421
|
+
//#endregion
|
|
54017
54422
|
//#region src/shared/documents.ts
|
|
54018
54423
|
/**
|
|
54019
54424
|
* Formats the files panel previews by conversion instead of by bytes.
|
|
@@ -54057,11 +54462,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54057
54462
|
}
|
|
54058
54463
|
//#endregion
|
|
54059
54464
|
//#region src/client/components/QaWorkspaceBrowser.tsx
|
|
54060
|
-
/** Name of one entry: the last path segment, root spelled as the directory. */
|
|
54061
|
-
function entryName(path) {
|
|
54062
|
-
const parts = path.split("/");
|
|
54063
|
-
return parts[parts.length - 1] ?? path;
|
|
54064
|
-
}
|
|
54065
54465
|
/** Path join for the panel's own navigation, never leaving the chat root. */
|
|
54066
54466
|
function joinPath(directory, name) {
|
|
54067
54467
|
return directory === "" ? name : `${directory}/${name}`;
|
|
@@ -54083,19 +54483,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54083
54483
|
}
|
|
54084
54484
|
return crumbs;
|
|
54085
54485
|
}
|
|
54086
|
-
/** Hand one file to the browser's download machinery. */
|
|
54087
|
-
function downloadFile(file) {
|
|
54088
|
-
const bytes = file.base64 === void 0 ? new TextEncoder().encode(file.text ?? "") : base64ToBytes(file.base64);
|
|
54089
|
-
const url = URL.createObjectURL(new Blob([bytes], { type: file.mime }));
|
|
54090
|
-
const anchor = document.createElement("a");
|
|
54091
|
-
anchor.href = url;
|
|
54092
|
-
anchor.download = entryName(file.path);
|
|
54093
|
-
anchor.rel = "noreferrer";
|
|
54094
|
-
document.body.append(anchor);
|
|
54095
|
-
anchor.click();
|
|
54096
|
-
anchor.remove();
|
|
54097
|
-
URL.revokeObjectURL(url);
|
|
54098
|
-
}
|
|
54099
54486
|
/** One row of the listing: a directory to descend into or a file to open. */
|
|
54100
54487
|
function EntryRow({ entry, directory, onOpenFile, onOpenDirectory }) {
|
|
54101
54488
|
const path = joinPath(directory, entry.name);
|
|
@@ -54160,13 +54547,13 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54160
54547
|
if (file.mime.startsWith("image/") && file.base64 !== void 0) return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("img", {
|
|
54161
54548
|
className: "dsh-qa-ws__image",
|
|
54162
54549
|
"data-testid": "qa-surface-workspace-image",
|
|
54163
|
-
alt:
|
|
54550
|
+
alt: fileNameOf(file.path),
|
|
54164
54551
|
src: `data:${file.mime};base64,${file.base64}`
|
|
54165
54552
|
});
|
|
54166
54553
|
if (pdf !== null) return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("iframe", {
|
|
54167
54554
|
className: "dsh-qa-ws__pdf",
|
|
54168
54555
|
"data-testid": "qa-surface-workspace-pdf",
|
|
54169
|
-
title:
|
|
54556
|
+
title: fileNameOf(file.path),
|
|
54170
54557
|
src: pdf
|
|
54171
54558
|
});
|
|
54172
54559
|
if (converting) return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
@@ -54222,7 +54609,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54222
54609
|
className: "dsh-qa-ws__preview-name",
|
|
54223
54610
|
"data-testid": "qa-surface-workspace-preview-name",
|
|
54224
54611
|
title: file.path,
|
|
54225
|
-
children:
|
|
54612
|
+
children: fileNameOf(file.path)
|
|
54226
54613
|
}),
|
|
54227
54614
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("button", {
|
|
54228
54615
|
type: "button",
|
|
@@ -54241,7 +54628,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54241
54628
|
type: "button",
|
|
54242
54629
|
className: "dsh-qa-ws__download",
|
|
54243
54630
|
"data-testid": "qa-surface-workspace-download",
|
|
54244
|
-
onClick: () =>
|
|
54631
|
+
onClick: () => downloadWorkspaceFile(file),
|
|
54245
54632
|
children: "Скачать"
|
|
54246
54633
|
})
|
|
54247
54634
|
]
|
|
@@ -54277,7 +54664,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54277
54664
|
* the visitor out of the chat's tree. Opening a file reads exactly that file —
|
|
54278
54665
|
* text inline, anything else as a downloadable handle.
|
|
54279
54666
|
*/
|
|
54280
|
-
function QaWorkspaceBrowser({ sessionId, api }) {
|
|
54667
|
+
function QaWorkspaceBrowser({ sessionId, api, initialFile }) {
|
|
54281
54668
|
const [directory, setDirectory] = (0, react.useState)("");
|
|
54282
54669
|
const [entries, setEntries] = (0, react.useState)([]);
|
|
54283
54670
|
const [truncated, setTruncated] = (0, react.useState)(false);
|
|
@@ -54373,6 +54760,13 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54373
54760
|
convert,
|
|
54374
54761
|
sessionId
|
|
54375
54762
|
]);
|
|
54763
|
+
const arrivalOpened = (0, react.useRef)(false);
|
|
54764
|
+
(0, react.useEffect)(() => {
|
|
54765
|
+
if (arrivalOpened.current) return;
|
|
54766
|
+
if (initialFile === void 0 || initialFile === "") return;
|
|
54767
|
+
arrivalOpened.current = true;
|
|
54768
|
+
openFile(initialFile);
|
|
54769
|
+
}, [initialFile, openFile]);
|
|
54376
54770
|
if (opened !== null) {
|
|
54377
54771
|
const closeFile = () => {
|
|
54378
54772
|
setOpened(null);
|
|
@@ -54395,7 +54789,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54395
54789
|
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaModal, {
|
|
54396
54790
|
open: expanded && file !== void 0,
|
|
54397
54791
|
size: "document",
|
|
54398
|
-
title: file === void 0 ? "" :
|
|
54792
|
+
title: file === void 0 ? "" : fileNameOf(file.path),
|
|
54399
54793
|
closeLabel: "Закрыть файл",
|
|
54400
54794
|
onClose: () => setExpanded(false),
|
|
54401
54795
|
children: /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
@@ -54515,14 +54909,15 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54515
54909
|
* back, and the images are the same object URLs the message showed — while the
|
|
54516
54910
|
* workspace section reads through the Host's fenced listing and file reads.
|
|
54517
54911
|
*/
|
|
54518
|
-
function QaFilesPanel({ groups, resolveImage, onJumpToMessage, sessionId, api }) {
|
|
54912
|
+
function QaFilesPanel({ groups, resolveImage, onJumpToMessage, onArtifactOpen, onArtifactDownload, openArtifact, sessionId, api }) {
|
|
54519
54913
|
const workspace = sessionId === void 0 || api === void 0 ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("section", {
|
|
54520
54914
|
className: "dsh-qa-files__workspace",
|
|
54521
54915
|
"data-testid": "qa-files-workspace",
|
|
54522
54916
|
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("h3", { children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", { children: "Рабочий каталог" }) }), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaWorkspaceBrowser, {
|
|
54523
54917
|
sessionId,
|
|
54524
|
-
api
|
|
54525
|
-
|
|
54918
|
+
api,
|
|
54919
|
+
initialFile: openArtifact?.path
|
|
54920
|
+
}, openArtifact?.stamp ?? "browse")]
|
|
54526
54921
|
});
|
|
54527
54922
|
if (groups.length === 0) return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
54528
54923
|
className: "dsh-qa-files",
|
|
@@ -54559,14 +54954,24 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
54559
54954
|
})] }), /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
54560
54955
|
className: "dsh-qa-files__items",
|
|
54561
54956
|
"data-testid": "qa-files-group-items",
|
|
54562
|
-
children: [
|
|
54563
|
-
|
|
54564
|
-
|
|
54565
|
-
|
|
54566
|
-
|
|
54567
|
-
|
|
54568
|
-
|
|
54569
|
-
|
|
54957
|
+
children: [
|
|
54958
|
+
group.files.map((file) => /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaFileAttachment, {
|
|
54959
|
+
name: file.name,
|
|
54960
|
+
bytes: file.bytes,
|
|
54961
|
+
tone: "sent"
|
|
54962
|
+
}, file.attachmentId)),
|
|
54963
|
+
group.images.map((image) => resolveImage === void 0 ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaFileImage, {
|
|
54964
|
+
image,
|
|
54965
|
+
resolve: resolveImage
|
|
54966
|
+
}, image.attachmentId)),
|
|
54967
|
+
(group.artifacts ?? []).map((artifact) => /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaFileAttachment, {
|
|
54968
|
+
name: artifact.name,
|
|
54969
|
+
bytes: artifact.bytes,
|
|
54970
|
+
tone: "sent",
|
|
54971
|
+
onOpen: onArtifactOpen === void 0 ? void 0 : () => onArtifactOpen(artifact),
|
|
54972
|
+
onDownload: onArtifactDownload === void 0 ? void 0 : () => onArtifactDownload(artifact)
|
|
54973
|
+
}, artifact.path))
|
|
54974
|
+
]
|
|
54570
54975
|
})]
|
|
54571
54976
|
}, group.messageId);
|
|
54572
54977
|
})]
|
|
@@ -56172,7 +56577,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
56172
56577
|
const [scopes, setScopes] = (0, react.useState)(QA_SERVICE_TOKEN_DEFAULT_SCOPES);
|
|
56173
56578
|
const [busy, setBusy] = (0, react.useState)(false);
|
|
56174
56579
|
const [issued, setIssued] = (0, react.useState)(null);
|
|
56175
|
-
const
|
|
56580
|
+
const { copied, impossible: copyImpossible, refused: copyRefused, copy: copySecret } = useCopyAction(issued?.token ?? "");
|
|
56176
56581
|
const [pendingRevoke, setPendingRevoke] = (0, react.useState)(null);
|
|
56177
56582
|
const [revoking, setRevoking] = (0, react.useState)(null);
|
|
56178
56583
|
(0, react.useEffect)(() => {
|
|
@@ -56204,7 +56609,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
56204
56609
|
if (busy) return;
|
|
56205
56610
|
setBusy(true);
|
|
56206
56611
|
setError(null);
|
|
56207
|
-
setCopied(false);
|
|
56208
56612
|
props.api.create({
|
|
56209
56613
|
label: label.trim(),
|
|
56210
56614
|
scopes: [...scopes],
|
|
@@ -56237,11 +56641,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
56237
56641
|
await reload();
|
|
56238
56642
|
});
|
|
56239
56643
|
};
|
|
56240
|
-
const copySecret = (secret) => {
|
|
56241
|
-
const clipboard = navigator.clipboard;
|
|
56242
|
-
if (clipboard === void 0) return;
|
|
56243
|
-
clipboard.writeText(secret).then(() => setCopied(true), () => void 0);
|
|
56244
|
-
};
|
|
56245
56644
|
const now = Date.now();
|
|
56246
56645
|
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
56247
56646
|
className: "dsh-qa-settings__page",
|
|
@@ -56277,18 +56676,15 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
56277
56676
|
onFocus: (event) => event.currentTarget.select()
|
|
56278
56677
|
})
|
|
56279
56678
|
}),
|
|
56280
|
-
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)(QaSettingsActions, { children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaSettingsButton, {
|
|
56679
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsxs)(QaSettingsActions, { children: [copyImpossible ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)(CopyHint, { testId: "qa-settings-tokens-copy-hint" }) : /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(react_jsx_runtime.Fragment, { children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaSettingsButton, {
|
|
56281
56680
|
testId: "qa-settings-tokens-copy",
|
|
56282
56681
|
label: copied ? "Скопировано" : "Скопировать",
|
|
56283
|
-
onClick:
|
|
56284
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaSettingsButton, {
|
|
56682
|
+
onClick: copySecret
|
|
56683
|
+
}), copyRefused ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)(CopyHint, { testId: "qa-settings-tokens-copy-hint" }) : null] }), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(QaSettingsButton, {
|
|
56285
56684
|
testId: "qa-settings-tokens-ack",
|
|
56286
56685
|
tone: "primary",
|
|
56287
56686
|
label: "Я сохранил токен",
|
|
56288
|
-
onClick: () =>
|
|
56289
|
-
setIssued(null);
|
|
56290
|
-
setCopied(false);
|
|
56291
|
-
}
|
|
56687
|
+
onClick: () => setIssued(null)
|
|
56292
56688
|
})] })
|
|
56293
56689
|
]
|
|
56294
56690
|
}),
|
|
@@ -56617,11 +57013,13 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
56617
57013
|
const [busy, setBusy] = (0, react.useState)(false);
|
|
56618
57014
|
const [error, setError] = (0, react.useState)(null);
|
|
56619
57015
|
const [saved, setSaved] = (0, react.useState)(false);
|
|
57016
|
+
const [attempted, setAttempted] = (0, react.useState)(false);
|
|
56620
57017
|
const tooShort = next !== "" && next.length < MIN_PASSWORD_LENGTH$1;
|
|
56621
57018
|
const mismatch = repeat !== "" && repeat !== next;
|
|
56622
57019
|
const incomplete = current === "" || next === "" || repeat === "";
|
|
56623
57020
|
const submit = (event) => {
|
|
56624
57021
|
event.preventDefault();
|
|
57022
|
+
setAttempted(true);
|
|
56625
57023
|
if (busy || incomplete || mismatch || tooShort) return;
|
|
56626
57024
|
setBusy(true);
|
|
56627
57025
|
setError(null);
|
|
@@ -56635,12 +57033,14 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
56635
57033
|
setCurrent("");
|
|
56636
57034
|
setNext("");
|
|
56637
57035
|
setRepeat("");
|
|
57036
|
+
setAttempted(false);
|
|
56638
57037
|
setSaved(true);
|
|
56639
57038
|
});
|
|
56640
57039
|
};
|
|
56641
57040
|
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("form", {
|
|
56642
57041
|
className: "dsh-qa-settings__page",
|
|
56643
57042
|
"data-testid": "qa-settings-password",
|
|
57043
|
+
noValidate: true,
|
|
56644
57044
|
onSubmit: submit,
|
|
56645
57045
|
children: [
|
|
56646
57046
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)("h3", {
|
|
@@ -56694,6 +57094,11 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
56694
57094
|
onChange: (event) => setRepeat(event.currentTarget.value)
|
|
56695
57095
|
})
|
|
56696
57096
|
}),
|
|
57097
|
+
attempted && incomplete ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
57098
|
+
className: "dsh-qa-settings__field-hint",
|
|
57099
|
+
"data-testid": "qa-settings-password-incomplete",
|
|
57100
|
+
children: "Заполните все поля."
|
|
57101
|
+
}) : null,
|
|
56697
57102
|
tooShort ? /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("p", {
|
|
56698
57103
|
className: "dsh-qa-settings__field-hint",
|
|
56699
57104
|
"data-testid": "qa-settings-password-too-short",
|
|
@@ -61315,7 +61720,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
61315
61720
|
//#endregion
|
|
61316
61721
|
//#region src/client/admin/pages/Users.tsx
|
|
61317
61722
|
const PAGE_SIZE = 25;
|
|
61318
|
-
/** The Host's floor; the
|
|
61723
|
+
/** The Host's floor; the queue answers a shorter password before the round trip. */
|
|
61319
61724
|
const MIN_PASSWORD_LENGTH = 8;
|
|
61320
61725
|
/**
|
|
61321
61726
|
* The forgotten-password queue: an account asked for a reset from the sign-in
|
|
@@ -61429,7 +61834,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
61429
61834
|
type: "password",
|
|
61430
61835
|
"data-testid": "qa-admin-password-reset-input",
|
|
61431
61836
|
autoComplete: "new-password",
|
|
61432
|
-
minLength: MIN_PASSWORD_LENGTH,
|
|
61433
61837
|
placeholder: "не короче 8 символов",
|
|
61434
61838
|
disabled: busy === request.userId,
|
|
61435
61839
|
value: drafts[request.userId] ?? "",
|
|
@@ -63771,7 +64175,17 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
63771
64175
|
const listState = (0, react.useSyncExternalStore)(props.sessions.list.subscribe, props.sessions.list.getSnapshot, props.sessions.list.getSnapshot);
|
|
63772
64176
|
const ui = useSessionUiState(state.chatKey);
|
|
63773
64177
|
const rail = useRightRail(ui);
|
|
63774
|
-
const { activeTurn, setActiveTurn, variantOffsets, setVariantOffsets, agentsOpen, setAgentsOpen, pendingAttachments, setPendingAttachments } = ui;
|
|
64178
|
+
const { activeTurn, setActiveTurn, variantOffsets, setVariantOffsets, agentsOpen, setAgentsOpen, setRailOpen, setRailTab, pendingAttachments, setPendingAttachments } = ui;
|
|
64179
|
+
/**
|
|
64180
|
+
* The file a card asked to open, with the chat it was asked in and the stamp
|
|
64181
|
+
* of the request. The chat is part of the arrival because the rail survives
|
|
64182
|
+
* switching chats: an arrival from the previous chat must not open its file
|
|
64183
|
+
* in this one. The stamp makes a second click on the same card a fresh
|
|
64184
|
+
* arrival rather than a path that never changed.
|
|
64185
|
+
*/
|
|
64186
|
+
const [artifactArrival, setArtifactArrival] = (0, react.useState)(null);
|
|
64187
|
+
/** Counts the open requests, so the same file twice is two arrivals. */
|
|
64188
|
+
const artifactStamp = (0, react.useRef)(0);
|
|
63775
64189
|
(0, react.useEffect)(() => {
|
|
63776
64190
|
if (!route.active) return;
|
|
63777
64191
|
const frame = requestAnimationFrame(() => {
|
|
@@ -63853,6 +64267,50 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
63853
64267
|
if (element === null || !scrollToTranscriptAnchor(element, messageId)) return;
|
|
63854
64268
|
nearBottom.current = isNearBottom(element);
|
|
63855
64269
|
}, []);
|
|
64270
|
+
/**
|
|
64271
|
+
* A produced file the reader wants to see: open the rail on its workspace
|
|
64272
|
+
* viewer at exactly that file. The viewer is the panel's own — it reads under
|
|
64273
|
+
* the chat's fence and converts a Word document into a preview — so a card
|
|
64274
|
+
* under an answer points at that work instead of carrying a second viewer
|
|
64275
|
+
* that could disagree with it.
|
|
64276
|
+
*/
|
|
64277
|
+
const handleArtifactOpen = (0, react.useCallback)((artifact) => {
|
|
64278
|
+
artifactStamp.current += 1;
|
|
64279
|
+
setArtifactArrival({
|
|
64280
|
+
path: artifact.path,
|
|
64281
|
+
chatKey: state.chatKey,
|
|
64282
|
+
stamp: artifactStamp.current
|
|
64283
|
+
});
|
|
64284
|
+
setAgentsOpen(false);
|
|
64285
|
+
setRailOpen(true);
|
|
64286
|
+
setRailTab("files");
|
|
64287
|
+
}, [
|
|
64288
|
+
setAgentsOpen,
|
|
64289
|
+
setRailOpen,
|
|
64290
|
+
setRailTab,
|
|
64291
|
+
state.chatKey
|
|
64292
|
+
]);
|
|
64293
|
+
/**
|
|
64294
|
+
* A produced file the reader wants to keep: the same fenced read the panel
|
|
64295
|
+
* uses, handed to the browser's download machinery. A read that fails opens
|
|
64296
|
+
* the viewer instead, which reports the refusal rather than swallowing the
|
|
64297
|
+
* click.
|
|
64298
|
+
*/
|
|
64299
|
+
const handleArtifactDownload = (0, react.useCallback)((artifact) => {
|
|
64300
|
+
const sessionId = state.sessionId;
|
|
64301
|
+
if (sessionId === null) return;
|
|
64302
|
+
boundSourceApi.readWorkspaceFile(sessionId, artifact.path).then((result) => {
|
|
64303
|
+
if (result.ok) {
|
|
64304
|
+
downloadWorkspaceFile(result.value);
|
|
64305
|
+
return;
|
|
64306
|
+
}
|
|
64307
|
+
handleArtifactOpen(artifact);
|
|
64308
|
+
}, () => handleArtifactOpen(artifact));
|
|
64309
|
+
}, [
|
|
64310
|
+
boundSourceApi,
|
|
64311
|
+
handleArtifactOpen,
|
|
64312
|
+
state.sessionId
|
|
64313
|
+
]);
|
|
63856
64314
|
const view = useTranscriptView(state.messages, variantOffsets);
|
|
63857
64315
|
const railItems = view.railItems;
|
|
63858
64316
|
(0, react.useLayoutEffect)(() => {
|
|
@@ -63885,6 +64343,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
63885
64343
|
const fileGroups = (0, react.useMemo)(() => collectChatFiles(state.messages), [state.messages]);
|
|
63886
64344
|
const attachmentCount = (0, react.useMemo)(() => countChatAttachments(fileGroups), [fileGroups]);
|
|
63887
64345
|
const filesEnabled = attachmentCount > 0 || state.sessionId !== null && config.sources.filePreview.enabled;
|
|
64346
|
+
const workspaceReadable = state.sessionId !== null && config.sources.filePreview.enabled;
|
|
63888
64347
|
const quickQuestions = (0, react.useMemo)(() => effectiveQuickQuestions(config.accounts.starters.enabled && accountsSnapshot.stage === "authed" ? accountsSnapshot.user.starters : void 0, config.suggestedQuestions), [config, accountsSnapshot]);
|
|
63889
64348
|
const ownerNames = (0, react.useMemo)(() => config.accounts.enabled && config.accounts.showOtherUsersChats && accounts !== void 0 && accountsSnapshot.stage === "authed" && accountsSnapshot.user.role === "admin" ? accounts.ownerNames() : void 0, [
|
|
63890
64349
|
config,
|
|
@@ -64042,6 +64501,12 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
64042
64501
|
groups: fileGroups,
|
|
64043
64502
|
resolveImage,
|
|
64044
64503
|
onJumpToMessage: handleJumpToMessage,
|
|
64504
|
+
onArtifactOpen: workspaceReadable ? handleArtifactOpen : void 0,
|
|
64505
|
+
onArtifactDownload: workspaceReadable ? handleArtifactDownload : void 0,
|
|
64506
|
+
openArtifact: artifactArrival !== null && artifactArrival.chatKey === state.chatKey ? {
|
|
64507
|
+
path: artifactArrival.path,
|
|
64508
|
+
stamp: artifactArrival.stamp
|
|
64509
|
+
} : void 0,
|
|
64045
64510
|
sessionId: state.sessionId ?? void 0,
|
|
64046
64511
|
api: boundSourceApi
|
|
64047
64512
|
})
|
|
@@ -64287,6 +64752,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
64287
64752
|
onRegenerate: isLast && message.role === "assistant" && message.status === "committed" && controller !== void 0 ? handleRegenerate : void 0,
|
|
64288
64753
|
onOpenSources: config.sources.enabled && config.sources.display.footer ? rail.openSources : void 0,
|
|
64289
64754
|
onSourceDetail: config.sources.enabled ? rail.openSourceDetail : void 0,
|
|
64755
|
+
onArtifactOpen: workspaceReadable ? handleArtifactOpen : void 0,
|
|
64756
|
+
onArtifactDownload: workspaceReadable ? handleArtifactDownload : void 0,
|
|
64290
64757
|
onRateFeedback: rateFeedback
|
|
64291
64758
|
}), group !== void 0 && group.turns.length > 1 ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)(VariantSwitcher, {
|
|
64292
64759
|
count: group.turns.length,
|
|
@@ -64946,8 +65413,8 @@ body[data-dsh-qa-surface="active"] div:has(>[data-shell-overlay])>:not([data-she
|
|
|
64946
65413
|
.dsh-qa-settings__button:disabled{opacity:.6;cursor:default}
|
|
64947
65414
|
.dsh-qa-settings__button--primary{border-color:transparent;background:var(--dsh-qa-brand);color:var(--dsh-qa-accent-contrast);font-weight:600}
|
|
64948
65415
|
.dsh-qa-settings__button--primary:hover:not(:disabled){background:var(--dsh-qa-accent-hover);color:var(--dsh-qa-accent-contrast)}
|
|
64949
|
-
.dsh-qa-settings__button--danger{border-color:var(--dsw-alias-
|
|
64950
|
-
.dsh-qa-settings__button--danger:hover:not(:disabled){background:var(--dsw-alias-
|
|
65416
|
+
.dsh-qa-settings__button--danger{border-color:var(--dsw-alias-state-error-primary);color:var(--dsw-alias-state-error-primary)}
|
|
65417
|
+
.dsh-qa-settings__button--danger:hover:not(:disabled){background:color-mix(in srgb, var(--dsw-alias-state-error-primary) 8%, transparent);color:var(--dsw-alias-state-error-primary)}
|
|
64951
65418
|
.dsh-qa-settings__empty{display:flex;flex-direction:column;align-items:flex-start;gap:10px;padding:22px 18px;border:1px dashed var(--dsw-alias-border-l2);border-radius:12px;background:var(--dsw-alias-bg-layer-3)}
|
|
64952
65419
|
.dsh-qa-settings__empty-title{margin:0;color:var(--dsw-alias-label-primary);font-size:14px;font-weight:600;line-height:20px}
|
|
64953
65420
|
.dsh-qa-settings__search{appearance:none;width:100%;padding:8px 11px;border:1px solid var(--dsw-alias-border-l2);border-radius:9px;background:var(--dsw-alias-bg-base);color:var(--dsw-alias-label-primary);font:inherit;font-size:13px;line-height:19px}
|
|
@@ -65389,11 +65856,12 @@ a.dsh-qa-srcref:hover,button.dsh-qa-srcref:hover{border-color:var(--dsw-alias-la
|
|
|
65389
65856
|
.dsh-qa-md-image{display:block;max-width:100%;height:auto;margin:0;border-radius:8px}
|
|
65390
65857
|
.dsh-qa-md-image-alt{color:var(--dsw-alias-label-tertiary);font-style:italic}
|
|
65391
65858
|
.dsh-qa-md-code{margin:16px 0;border-radius:12px;background:var(--dsw-alias-markdown-code-block,var(--dsw-alias-bg-layer-2));color:var(--dsw-alias-label-primary)}
|
|
65392
|
-
.dsh-qa-md-code__banner{display:flex;align-items:center;justify-content:
|
|
65393
|
-
.dsh-qa-md-code__lang{min-width:0;overflow:hidden;color:var(--dsw-alias-label-primary);font-family:var(--ds-font-family-code,ui-monospace,SFMono-Regular,Consolas,monospace);font-size:11px;line-height:18px;text-overflow:ellipsis;white-space:nowrap}
|
|
65859
|
+
.dsh-qa-md-code__banner{display:flex;align-items:center;justify-content:flex-end;gap:12px;padding:9px 14px;border-radius:12px 12px 0 0;background:var(--dsw-alias-markdown-code-block-banner,var(--dsw-alias-bg-layer-3))}
|
|
65860
|
+
.dsh-qa-md-code__lang{flex:none;min-width:0;margin-right:auto;overflow:hidden;color:var(--dsw-alias-label-primary);font-family:var(--ds-font-family-code,ui-monospace,SFMono-Regular,Consolas,monospace);font-size:11px;line-height:18px;text-overflow:ellipsis;white-space:nowrap}
|
|
65394
65861
|
.dsh-qa-md-code__copy{appearance:none;flex:none;padding:0;border:0;background:transparent;color:var(--dsw-alias-label-secondary);font:inherit;font-size:11px;line-height:18px;cursor:pointer}
|
|
65395
65862
|
.dsh-qa-md-code__copy:hover{color:var(--dsw-alias-label-primary)}
|
|
65396
65863
|
.dsh-qa-md-code__copy:focus-visible{outline:var(--dsw-focus-ring-width, 2px) solid var(--dsw-focus-ring-color, var(--dsh-qa-accent));outline-offset:2px}
|
|
65864
|
+
.dsh-qa-copy-hint{flex:none;color:var(--dsw-alias-label-tertiary);font-size:11px;line-height:18px;white-space:nowrap}
|
|
65397
65865
|
.dsh-qa-md-code pre{overflow-x:auto;margin:0;padding:16px;border:0;border-radius:0 0 12px 12px;background:transparent;font-family:var(--ds-font-family-code,ui-monospace,SFMono-Regular,Consolas,monospace);font-size:var(--dsw-font-markdown-code-block-font-size,11px);line-height:var(--dsw-font-markdown-code-block-line-height,19px);white-space:pre-wrap;word-break:break-word}
|
|
65398
65866
|
.dsh-qa-md-code pre code{display:block;padding:0;border:0;background:transparent;font:inherit}
|
|
65399
65867
|
.dsh-qa-md-tok[data-tok="comment"]{color:var(--shiki-token-comment)}
|
|
@@ -65573,6 +66041,12 @@ a.dsh-qa-srcref:hover,button.dsh-qa-srcref:hover{border-color:var(--dsw-alias-la
|
|
|
65573
66041
|
.dsh-qa-file button:hover{color:var(--dsh-qa-error)}
|
|
65574
66042
|
.dsh-qa-file button:focus-visible{outline:var(--dsw-focus-ring-width, 2px) solid var(--dsw-focus-ring-color, var(--dsh-qa-accent));outline-offset:1px}
|
|
65575
66043
|
.dsh-qa-file button svg{width:11px;height:11px;fill:none;stroke:currentColor;stroke-width:1.6;stroke-linecap:round}
|
|
66044
|
+
.dsh-qa-file .dsh-qa-file__open{display:flex;align-items:center;gap:10px;flex:1;min-width:0;width:auto;height:auto;padding:0;border-radius:6px;background:0 0;color:inherit;text-align:left;place-items:stretch;cursor:pointer}
|
|
66045
|
+
.dsh-qa-file .dsh-qa-file__open:hover{background:0 0;color:inherit}
|
|
66046
|
+
.dsh-qa-file .dsh-qa-file__open:hover .dsh-qa-file__name{color:var(--dsw-alias-brand-primary)}
|
|
66047
|
+
.dsh-qa-file .dsh-qa-file__download{width:auto;height:auto;padding:2px 8px;border:1px solid var(--dsw-alias-border-l2);border-radius:999px;background:var(--dsw-alias-bg-layer-3);color:var(--dsw-alias-label-secondary);font-size:11px}
|
|
66048
|
+
.dsh-qa-file .dsh-qa-file__download:hover{background:var(--dsw-alias-bg-layer-3);color:var(--dsw-alias-label-primary);border-color:var(--dsw-alias-label-dimmed)}
|
|
66049
|
+
.dsh-qa-message__artifacts{display:flex;flex-wrap:wrap;gap:8px;margin:10px 0 0}
|
|
65576
66050
|
.dsh-qa-composer__image{position:relative;display:block;width:64px;height:64px;flex:none}
|
|
65577
66051
|
.dsh-qa-composer__image img{display:block;width:100%;height:100%;object-fit:cover;border-radius:10px;border:1px solid var(--dsw-alias-border-l2)}
|
|
65578
66052
|
.dsh-qa-composer__image button{position:absolute;top:-6px;right:-6px;display:grid;place-items:center;width:18px;height:18px;padding:0;border:0;border-radius:999px;background:var(--dsw-alias-bg-layer-2);color:var(--dsw-alias-label-secondary);cursor:pointer;box-shadow:var(--dsw-shadow-lv2)}
|
|
@@ -68459,7 +68933,7 @@ textarea.qa-card-control{height:auto;padding:8px 12px;line-height:1.5;resize:ver
|
|
|
68459
68933
|
.qa-card-chip.off{color:var(--dsw-alias-label-tertiary)}
|
|
68460
68934
|
.qa-card-notice{padding:9px 11px;border-radius:8px;background:var(--dsw-alias-bg-module-platform);border:1px solid var(--dsw-alias-border-l2);font-size:11px;line-height:1.5;color:var(--dsw-alias-label-secondary)}
|
|
68461
68935
|
.qa-card-notice.warn{border-color:var(--dsw-alias-label-dimmed);color:var(--dsw-alias-label-primary)}
|
|
68462
|
-
.qa-card-error{padding:9px 11px;border-radius:8px;background:var(--dsw-alias-
|
|
68936
|
+
.qa-card-error{padding:9px 11px;border-radius:8px;background:color-mix(in srgb, var(--dsw-alias-state-error-primary, #b3261e) 8%, transparent);color:var(--dsw-alias-state-error-primary, #b3261e);font-size:11px;line-height:1.5}
|
|
68463
68937
|
.qa-card-advanced{border:1px solid var(--dsw-alias-border-l2);border-radius:10px;padding:0 12px}
|
|
68464
68938
|
.qa-card-advanced summary{cursor:pointer;padding:11px 0;font-size:12px;font-weight:600}
|
|
68465
68939
|
.qa-card-advanced summary:focus-visible{outline:var(--dsw-focus-ring-width, 2px) solid var(--dsw-focus-ring-color, var(--dsw-alias-state-business-primary));outline-offset:-1px}
|