Compare commits
22 Commits
v1.682.0
...
dieri/chan
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
58d9052a8b | ||
|
|
e912042c08 | ||
|
|
039ecf0f53 | ||
|
|
5097b4c97f | ||
|
|
7139e414d5 | ||
|
|
61628ff2d9 | ||
|
|
5ae489ee4b | ||
|
|
03252d82bf | ||
|
|
3e81551c99 | ||
|
|
04afbf4624 | ||
|
|
3c1449b39f | ||
|
|
c0a4c48ec1 | ||
|
|
7b2aa2c7d8 | ||
|
|
3aee427068 | ||
|
|
b1b4ac9821 | ||
|
|
48af67d2a5 | ||
|
|
fca9b19542 | ||
|
|
64325bc9b1 | ||
|
|
00e28d4749 | ||
|
|
4934d113d4 | ||
|
|
b6ae5d4f57 | ||
|
|
e38dd2f1a5 |
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE resource SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "00f68ea1ad2d5ab045b4a20ce3f4dd7850041e396e14890e37e1d0db276d3694"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE asset SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "029b81eb00250eacded407b12bcfbab2b3f35354bdb9ef6e30281a4ff6235060"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE usr SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "0659bab15d4cccdb04c7a57e0e3bbb6bfebb8896601a27ddf5618d4eae678bc1"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE audit SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "0ba594244a366a31d9bed97a2d7b031d42c23463599d267d1712d1af1d26b321"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE kafka_trigger SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "0ca4365e7144584ef5723db7e133bb42525ff91a734caa87be8b802c6607e6be"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE workspace_key SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "0d0c379b1cd2eec15869dd0b1a31886a95d53096fdcb1cdb1e0eb282b54105dc"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE v2_job_queue SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "0ea5ba568ec0f62b808fe938a41174646b6bdd658b8461db1bb90a871d076718"
|
||||
}
|
||||
22
backend/.sqlx/query-14cb27031d383462b35e6b71c35242af1ac0276d3143e3af00e9a99f058fe5bb.json
generated
Normal file
22
backend/.sqlx/query-14cb27031d383462b35e6b71c35242af1ac0276d3143e3af00e9a99f058fe5bb.json
generated
Normal file
@@ -0,0 +1,22 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "SELECT \n COUNT(*) \n FROM (\n SELECT id FROM v2_job WHERE workspace_id = $1\n UNION ALL\n SELECT id FROM v2_job_completed WHERE workspace_id = $1\n ) as total_jobs",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "count",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
null
|
||||
]
|
||||
},
|
||||
"hash": "14cb27031d383462b35e6b71c35242af1ac0276d3143e3af00e9a99f058fe5bb"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE variable SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "15c29ab03fdeda346adc4db3fd0b9d9aee1a99f0c795afe203efe42b967569a5"
|
||||
}
|
||||
15
backend/.sqlx/query-16577af504ba1bade4c92f023dac246591354e28e4c0a61095a2d16a2753fa3a.json
generated
Normal file
15
backend/.sqlx/query-16577af504ba1bade4c92f023dac246591354e28e4c0a61095a2d16a2753fa3a.json
generated
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "INSERT INTO flow\n (workspace_id, path, summary, description, archived, extra_perms, dependency_job, draft_only, tag, ws_error_handler_muted, dedicated_worker, timeout, visible_to_runner_only, on_behalf_of_email, concurrency_key, versions, value, schema, edited_by, edited_at)\n SELECT $1, path, summary, description, archived, extra_perms, dependency_job, draft_only, tag, ws_error_handler_muted, dedicated_worker, timeout, visible_to_runner_only, on_behalf_of_email, concurrency_key, versions, value, schema, edited_by, edited_at\n FROM flow WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "16577af504ba1bade4c92f023dac246591354e28e4c0a61095a2d16a2753fa3a"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE http_trigger SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "1c94d4f3b90a47b40263c254f85d14cc8b551e9ab0208e3a10ca717a4e85888b"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE resource_type SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "2133e06ac9f7de884dbd36d51bca9a427bde64a9e278658bc0777e23abde4cd5"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE v2_job SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "4244640e62fffb0f6978f8f7d78291b3294a6a7d1549d752f14acf5972552ba5"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE app SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "5395887680e4ff458a962d99614085e45a723964b7937cfe9943019e5c49df90"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE draft SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "5422a53e642c491b02be5d17fe9d7389a42a84c21fea9876c84a5ba719b6ede5"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE token SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "543b8f6e4850c15439e9bed8432db071c361867f9603d962b6edec6c18160491"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE folder SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "5876d8271adcb75752d518fc52ac192e162469a504338b4a0a37e8bcec114385"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE job_stats SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "65121a4bfba70c2d7055a2b58c8520fddaef1bd9a3f041e851f9c136c73d34e7"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE v2_job_completed SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "6bdb3fcfe16fc40222dc7010a11026d4d4e0d381b31fe02da7d2667c0cdc1a85"
|
||||
}
|
||||
24
backend/.sqlx/query-706a45bebb2321d6bb2330d225ecdb0573b5dc8221b33b93a7fd5244980d99b7.json
generated
Normal file
24
backend/.sqlx/query-706a45bebb2321d6bb2330d225ecdb0573b5dc8221b33b93a7fd5244980d99b7.json
generated
Normal file
@@ -0,0 +1,24 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "WITH \n batch_completed_jobs AS (\n SELECT id FROM v2_job_completed\n WHERE workspace_id = $1\n LIMIT $2\n ),\n batch_jobs AS (\n SELECT id FROM v2_job\n WHERE workspace_id = $1\n LIMIT $2\n ),\n updated_completed AS (\n UPDATE v2_job_completed\n SET workspace_id = $3\n WHERE id IN (SELECT id FROM batch_completed_jobs)\n RETURNING 1\n ),\n updated_jobs AS (\n UPDATE v2_job\n SET workspace_id = $3\n WHERE id IN (SELECT id FROM batch_jobs)\n RETURNING 1\n )\n SELECT \n (SELECT COUNT(*) FROM updated_completed) + \n (SELECT COUNT(*) FROM updated_jobs) as total_count",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "total_count",
|
||||
"type_info": "Int8"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text",
|
||||
"Int8",
|
||||
"Varchar"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
null
|
||||
]
|
||||
},
|
||||
"hash": "706a45bebb2321d6bb2330d225ecdb0573b5dc8221b33b93a7fd5244980d99b7"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE workspace_env SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "73706be0610149682fa6131494212095e9494ade5e01b138c7fbbd16f42be791"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE account SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "73a2dbe03a7debbcb236765a9f9d73f3aeb11469f773797ece590f9327878085"
|
||||
}
|
||||
22
backend/.sqlx/query-7a88553e784004530f829085d7bd61a5493d9e292396f14c149eeb016376574c.json
generated
Normal file
22
backend/.sqlx/query-7a88553e784004530f829085d7bd61a5493d9e292396f14c149eeb016376574c.json
generated
Normal file
@@ -0,0 +1,22 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT \n w.id \n FROM \n workspace w \n LEFT JOIN usr u ON u.workspace_id = w.id\n WHERE \n w.parent_workspace_id = $1 \n AND u.workspace_id IS NULL\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "id",
|
||||
"type_info": "Varchar"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
false
|
||||
]
|
||||
},
|
||||
"hash": "7a88553e784004530f829085d7bd61a5493d9e292396f14c149eeb016376574c"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE job_logs SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "7e90578bb37b2923cd94c201f1818c8c5b0bd62c9555949dda2e6aba3e09a4f0"
|
||||
}
|
||||
17
backend/.sqlx/query-7f9da38a52ecee61e6ecfe272207b1572b7974b3f77400aa9d4a80cf1a225500.json
generated
Normal file
17
backend/.sqlx/query-7f9da38a52ecee61e6ecfe272207b1572b7974b3f77400aa9d4a80cf1a225500.json
generated
Normal file
@@ -0,0 +1,17 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n INSERT INTO\n workspace (id, name, owner, deleted, premium, parent_workspace_id)\n SELECT $1, $2, owner, deleted, premium, $3\n FROM \n workspace \n WHERE \n id = $4\n ",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Varchar",
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "7f9da38a52ecee61e6ecfe272207b1572b7974b3f77400aa9d4a80cf1a225500"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE schedule SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "7fff1cc19a4b2a7ee99b1e4bd74986f4c9253052272145f37c4da1dfe5be0754"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "INSERT INTO flow \n (workspace_id, path, summary, description, archived, extra_perms, dependency_job, draft_only, tag, ws_error_handler_muted, dedicated_worker, timeout, visible_to_runner_only, on_behalf_of_email, concurrency_key, versions, value, schema, edited_by, edited_at) \n SELECT $1, path, summary, description, archived, extra_perms, dependency_job, draft_only, tag, ws_error_handler_muted, dedicated_worker, timeout, visible_to_runner_only, on_behalf_of_email, concurrency_key, versions, value, schema, edited_by, edited_at\n FROM flow WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "81a9d976ac5c1a78c83b95a1164995e78878a4a4ff6894a04e6626cdd98c24e4"
|
||||
}
|
||||
@@ -1,16 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "INSERT INTO workspace SELECT $1, $2, owner, deleted, premium FROM workspace WHERE id = $3",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "8f0031533f1bf407bd5d8af4d364eaf00d4c38ee7ba75141b40fc9fcd2ffc0b8"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE workspace_settings SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "93e6cdf58803f63d7d465f9d778c052c40dcdacade0f9b9921860160604f3763"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE dependency_map SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "940b6f4869e545cbeb796ef379dd718cf03e3752607b6bf7c85a176f8a44cbc2"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE script SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "96bc4b0f9909bd555fa58547fa87e4b311c4b515b9e3d14d922d7aec53a9505e"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE websocket_trigger SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "98880172e7d163e0db06eea2b9008c5082a3e34d8d294b341f01f549be6c7333"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE raw_app SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "a0d7dbff9ef98c3cc25281cb5dc9e29023766ba04c57d07c3f89f07640833619"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE capture_config SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "a17b1b8d4f58c58c253e63ec4c2fbb1df4bef54003b01fa901bfa782b5f83342"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE deployment_metadata SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "b101ce2acb77e2f3861d9e50ea241f55bb3ffc8afd26f377c8f0c9f894321806"
|
||||
}
|
||||
22
backend/.sqlx/query-b686da843d5df74e4a58b528b42e726f76c1da907d590589d9b1e8fed930d9b5.json
generated
Normal file
22
backend/.sqlx/query-b686da843d5df74e4a58b528b42e726f76c1da907d590589d9b1e8fed930d9b5.json
generated
Normal file
@@ -0,0 +1,22 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "\n SELECT \n parent_workspace_id \n FROM \n workspace \n WHERE \n id = $1\n ",
|
||||
"describe": {
|
||||
"columns": [
|
||||
{
|
||||
"ordinal": 0,
|
||||
"name": "parent_workspace_id",
|
||||
"type_info": "Varchar"
|
||||
}
|
||||
],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": [
|
||||
true
|
||||
]
|
||||
},
|
||||
"hash": "b686da843d5df74e4a58b528b42e726f76c1da907d590589d9b1e8fed930d9b5"
|
||||
}
|
||||
14
backend/.sqlx/query-bb0259204a4d05cbe52d781de9116f273ae1e72d178aaab1ba1ed6af3eff83de.json
generated
Normal file
14
backend/.sqlx/query-bb0259204a4d05cbe52d781de9116f273ae1e72d178aaab1ba1ed6af3eff83de.json
generated
Normal file
@@ -0,0 +1,14 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE workspace SET parent_workspace_id = NULL WHERE id = $1",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "bb0259204a4d05cbe52d781de9116f273ae1e72d178aaab1ba1ed6af3eff83de"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE capture SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "bf0ae8e884556a87f8a495aa2c8245e69b8f68b7c2748b2b1c29a3f013123a09"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE favorite SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "c721347a78ada56730f92038820e4b7e9e1f541f76bb37a0906a3c96dfe8169e"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE input SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "cfa0daf8f342aedd2d9b0bbb00965187e3838bbfe6a14be5b7a308e246123f71"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE nats_trigger SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "e2b17a69501978f2617ff4d20198111e3dab821c25d3164db7983b3192d149a0"
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
{
|
||||
"db_name": "PostgreSQL",
|
||||
"query": "UPDATE workspace_invite SET workspace_id = $1 WHERE workspace_id = $2",
|
||||
"describe": {
|
||||
"columns": [],
|
||||
"parameters": {
|
||||
"Left": [
|
||||
"Varchar",
|
||||
"Text"
|
||||
]
|
||||
},
|
||||
"nullable": []
|
||||
},
|
||||
"hash": "fc384ad2e85f3b21887d65ae68e8c408acbe4ad5c5c63a9ca9dac35dbb2eec2e"
|
||||
}
|
||||
@@ -847,6 +847,130 @@ paths:
|
||||
schema:
|
||||
type: boolean
|
||||
|
||||
/workspaces/migrate/tables:
|
||||
post:
|
||||
summary: migrate workspace data from source to target
|
||||
operationId: migrateWorkspaceTables
|
||||
tags:
|
||||
- workspace
|
||||
requestBody:
|
||||
description: migration request
|
||||
required: true
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: "#/components/schemas/MigrateWorkspaceRequest"
|
||||
responses:
|
||||
"200":
|
||||
description: migration completed
|
||||
content:
|
||||
text/plain:
|
||||
schema:
|
||||
type: string
|
||||
|
||||
/workspaces/migrate/jobs:
|
||||
post:
|
||||
summary: migrate workspace jobs from source to target
|
||||
operationId: migrateWorkspaceJobs
|
||||
tags:
|
||||
- workspace
|
||||
requestBody:
|
||||
description: migration jobs
|
||||
required: true
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: "#/components/schemas/MigrateJobsRequest"
|
||||
responses:
|
||||
"200":
|
||||
description: migration completed
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: "#/components/schemas/MigrateJobsStatus"
|
||||
|
||||
|
||||
/workspaces/migrate/status:
|
||||
get:
|
||||
summary: get migration status
|
||||
operationId: getMigrationStatus
|
||||
tags:
|
||||
- workspace
|
||||
parameters:
|
||||
- name: source_workspace
|
||||
in: query
|
||||
required: true
|
||||
description: source workspace id to check migration status
|
||||
schema:
|
||||
type: string
|
||||
responses:
|
||||
"200":
|
||||
description: migration status
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: "#/components/schemas/MigrationStatus"
|
||||
|
||||
/workspaces/migrate/complete:
|
||||
post:
|
||||
operationId: completeWorkspaceMigration
|
||||
tags:
|
||||
- workspace
|
||||
requestBody:
|
||||
description: complete migration request
|
||||
required: true
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: "#/components/schemas/CompleteWorkspaceMigrationRequest"
|
||||
responses:
|
||||
"200":
|
||||
description: migration completed
|
||||
content:
|
||||
text/plain:
|
||||
schema:
|
||||
type: string
|
||||
|
||||
/workspaces/migrate/{workspace}/revert:
|
||||
post:
|
||||
summary: revert incomplete workspace migration
|
||||
operationId: revertWorkspaceMigration
|
||||
tags:
|
||||
- workspace
|
||||
parameters:
|
||||
- $ref: "#/components/parameters/WorkspaceId"
|
||||
requestBody:
|
||||
description: revert migration request
|
||||
required: true
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: "#/components/schemas/RevertWorkspaceMigrationRequest"
|
||||
responses:
|
||||
"200":
|
||||
description: migration reverted
|
||||
content:
|
||||
text/plain:
|
||||
schema:
|
||||
type: string
|
||||
|
||||
/workspaces/migrate/{workspace}/incomplete:
|
||||
get:
|
||||
summary: get incomplete migration for source workspace
|
||||
operationId: getIncompleteMigration
|
||||
tags:
|
||||
- workspace
|
||||
parameters:
|
||||
- $ref: "#/components/parameters/WorkspaceId"
|
||||
responses:
|
||||
"200":
|
||||
description: target workspace id if incomplete migration exists
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
type: string
|
||||
nullable: true
|
||||
|
||||
/settings/get_ducklake_instance_catalog_db_status:
|
||||
post:
|
||||
summary: Returns the set-up statuses of ducklake instance catalog dbs
|
||||
@@ -18152,6 +18276,83 @@ components:
|
||||
- SKIP
|
||||
- FAIL
|
||||
|
||||
MigrateWorkspaceRequest:
|
||||
type: object
|
||||
properties:
|
||||
source_workspace_id:
|
||||
type: string
|
||||
description: source workspace id
|
||||
target_workspace_id:
|
||||
type: string
|
||||
description: target workspace id
|
||||
target_workspace_name:
|
||||
type: string
|
||||
description: target workspace name
|
||||
required:
|
||||
- source_workspace_id
|
||||
- target_workspace_name
|
||||
- target_workspace_id
|
||||
|
||||
CompleteWorkspaceMigrationRequest:
|
||||
type: object
|
||||
properties:
|
||||
source_workspace_id:
|
||||
type: string
|
||||
description: source workspace id
|
||||
target_workspace_id:
|
||||
type: string
|
||||
description: target workspace id
|
||||
required:
|
||||
- source_workspace_id
|
||||
- target_workspace_id
|
||||
|
||||
RevertWorkspaceMigrationRequest:
|
||||
type: object
|
||||
properties:
|
||||
target_workspace_id:
|
||||
type: string
|
||||
description: target workspace id to revert
|
||||
required:
|
||||
- target_workspace_id
|
||||
|
||||
MigrateJobsRequest:
|
||||
type: object
|
||||
properties:
|
||||
source_workspace_id:
|
||||
type: string
|
||||
description: source workspace id
|
||||
target_workspace_id:
|
||||
type: string
|
||||
description: target workspace id
|
||||
batch_size:
|
||||
type: integer
|
||||
format: int64
|
||||
default: 10000
|
||||
description: number of jobs to migrate per batch
|
||||
required:
|
||||
- source_workspace_id
|
||||
- target_workspace_id
|
||||
|
||||
MigrateJobsStatus:
|
||||
type: object
|
||||
properties:
|
||||
migrated_count:
|
||||
type: integer
|
||||
format: int64
|
||||
description: number of jobs migrated in this batch
|
||||
required:
|
||||
- migrated_count
|
||||
|
||||
MigrationStatus:
|
||||
type: object
|
||||
properties:
|
||||
processed_jobs:
|
||||
type: integer
|
||||
format: int64
|
||||
description: number of jobs processed in source workspace
|
||||
required:
|
||||
- processed_jobs
|
||||
|
||||
DucklakeInstanceCatalogDbStatusLogs:
|
||||
type: object
|
||||
properties:
|
||||
|
||||
@@ -67,6 +67,11 @@ use crate::teams_oss::{
|
||||
workspaces_list_available_teams_channels, workspaces_list_available_teams_ids,
|
||||
};
|
||||
|
||||
use crate::workspaces_extra::{
|
||||
complete_workspace_migration, get_incomplete_migration, get_migration_status, migrate_jobs,
|
||||
migrate_workspace, revert_workspace_migration,
|
||||
};
|
||||
|
||||
lazy_static::lazy_static! {
|
||||
static ref WORKSPACE_KEY_REGEXP: Regex = Regex::new("^[a-zA-Z0-9]{64}$").unwrap();
|
||||
}
|
||||
@@ -148,10 +153,6 @@ pub fn workspaced_service() -> Router {
|
||||
.route("/create_fork", post(create_workspace_fork))
|
||||
.route("/change_workspace_name", post(change_workspace_name))
|
||||
.route("/change_workspace_color", post(change_workspace_color))
|
||||
.route(
|
||||
"/change_workspace_id",
|
||||
post(crate::workspaces_extra::change_workspace_id),
|
||||
)
|
||||
.route("/usage", get(get_usage))
|
||||
.route("/used_triggers", get(get_used_triggers))
|
||||
.route("/critical_alerts", get(get_critical_alerts))
|
||||
@@ -178,6 +179,19 @@ pub fn workspaced_service() -> Router {
|
||||
#[cfg(not(feature = "stripe"))]
|
||||
router
|
||||
}
|
||||
|
||||
pub fn migrate_service() -> Router {
|
||||
Router::new().nest(
|
||||
"/migrate",
|
||||
Router::new()
|
||||
.route("/tables", post(migrate_workspace))
|
||||
.route("/jobs", post(migrate_jobs))
|
||||
.route("/status", get(get_migration_status))
|
||||
.route("/complete", post(complete_workspace_migration))
|
||||
.route("/:workspace/revert", post(revert_workspace_migration))
|
||||
.route("/:workspace/incomplete", get(get_incomplete_migration)),
|
||||
)
|
||||
}
|
||||
pub fn global_service() -> Router {
|
||||
Router::new()
|
||||
.route("/list_as_superadmin", get(list_workspaces_as_super_admin))
|
||||
@@ -197,6 +211,7 @@ pub fn global_service() -> Router {
|
||||
"/create_workspace_require_superadmin",
|
||||
get(create_workspace_require_superadmin),
|
||||
)
|
||||
.merge(migrate_service())
|
||||
}
|
||||
|
||||
#[derive(FromRow, Serialize)]
|
||||
@@ -2352,6 +2367,13 @@ lazy_static::lazy_static! {
|
||||
}
|
||||
};
|
||||
|
||||
pub static ref MIGRATE_JOBS_WORKSPACE_REQUIRE_SUPERADMIN: bool = {
|
||||
match std::env::var("MIGRATE_JOBS_WORKSPACE_REQUIRE_SUPERADMIN") {
|
||||
Ok(val) => val == "true",
|
||||
Err(_) => true,
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
async fn create_workspace_require_superadmin() -> String {
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
128
cli/src/commands/workspace/migrate.ts
Normal file
128
cli/src/commands/workspace/migrate.ts
Normal file
@@ -0,0 +1,128 @@
|
||||
// deno-lint-ignore-file no-explicit-any
|
||||
import { Command, colors, log } from "../../../deps.ts";
|
||||
import { GlobalOptions } from "../../types.ts";
|
||||
import { requireLogin } from "../../core/auth.ts";
|
||||
import { setClient } from "../../../deps.ts";
|
||||
import * as wmill from "../../../gen/services.gen.ts";
|
||||
import { getActiveWorkspace } from "./workspace.ts";
|
||||
|
||||
async function migrate(
|
||||
opts: GlobalOptions & {
|
||||
token?: string;
|
||||
remote?: string;
|
||||
sourceWorkspace?: string;
|
||||
},
|
||||
targetWorkspaceId: string
|
||||
) {
|
||||
let token: string;
|
||||
let remote: string;
|
||||
let sourceWorkspaceId: string;
|
||||
|
||||
if (opts.token && opts.remote && opts.sourceWorkspace) {
|
||||
token = opts.token;
|
||||
remote = opts.remote.endsWith("/")
|
||||
? opts.remote.substring(0, opts.remote.length - 1)
|
||||
: opts.remote;
|
||||
sourceWorkspaceId = opts.sourceWorkspace;
|
||||
log.info(
|
||||
colors.blue("Running in worker job mode with provided credentials")
|
||||
);
|
||||
} else {
|
||||
await requireLogin(opts);
|
||||
|
||||
const workspace = await getActiveWorkspace(opts);
|
||||
if (!workspace) {
|
||||
throw new Error(
|
||||
"No active workspace. Please run 'wmill workspace add' first."
|
||||
);
|
||||
}
|
||||
|
||||
token = workspace.token;
|
||||
remote = workspace.remote.endsWith("/")
|
||||
? workspace.remote.substring(0, workspace.remote.length - 1)
|
||||
: workspace.remote;
|
||||
sourceWorkspaceId = workspace.workspaceId;
|
||||
|
||||
log.info(colors.blue("Running in CLI mode with active workspace"));
|
||||
}
|
||||
|
||||
setClient(token, remote);
|
||||
|
||||
log.info(colors.blue("Starting workspace migration:"));
|
||||
log.info(` Source: ${colors.bold(sourceWorkspaceId)}`);
|
||||
log.info("");
|
||||
|
||||
try {
|
||||
log.info(colors.blue("=".repeat(60)));
|
||||
log.info(colors.blue("Migrating jobs"));
|
||||
log.info(colors.blue("=".repeat(60)));
|
||||
log.info("");
|
||||
|
||||
const initialStatus = await wmill.getMigrationStatus({
|
||||
sourceWorkspace: sourceWorkspaceId,
|
||||
});
|
||||
|
||||
const totalJobs = initialStatus.processed_jobs || 0;
|
||||
log.info(`Total jobs to migrate: ${colors.bold(totalJobs.toString())}`);
|
||||
|
||||
if (totalJobs === 0) {
|
||||
log.info(colors.yellow("No jobs to migrate"));
|
||||
return;
|
||||
}
|
||||
|
||||
let totalMigrated = 0;
|
||||
const batchSize = 10000;
|
||||
|
||||
while (true) {
|
||||
log.info(`Processing batch (size: ${batchSize})...`);
|
||||
|
||||
const batchResult = await wmill.migrateWorkspaceJobs({
|
||||
requestBody: {
|
||||
source_workspace_id: sourceWorkspaceId,
|
||||
target_workspace_id: targetWorkspaceId,
|
||||
batch_size: batchSize,
|
||||
},
|
||||
});
|
||||
|
||||
const migratedInBatch = batchResult.migrated_count || 0;
|
||||
totalMigrated += migratedInBatch;
|
||||
|
||||
const progress = Math.round((totalMigrated / totalJobs) * 100);
|
||||
log.info(`${colors.green(migratedInBatch.toString())} jobs migrated`);
|
||||
log.info(
|
||||
`Progress: ${colors.cyan(
|
||||
`${totalMigrated}/${totalJobs}`
|
||||
)} (${colors.yellow(`${progress}%`)})`
|
||||
);
|
||||
|
||||
if (migratedInBatch < batchSize) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
const jobsResult = `Successfully migrated ${totalMigrated} jobs`;
|
||||
|
||||
log.info(colors.green(`✅ ${jobsResult}`));
|
||||
log.info("");
|
||||
log.info(colors.green("=".repeat(60)));
|
||||
log.info(colors.green("✅ Complete migration finished successfully!"));
|
||||
log.info(colors.green("=".repeat(60)));
|
||||
} catch (error) {
|
||||
log.error(colors.red(`❌ Migration failed: ${error}`));
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
const command = new Command()
|
||||
.name("migrate")
|
||||
.description("Migrate workspace data from source to target workspace")
|
||||
.arguments("<target_workspace_id:string>")
|
||||
.option("-t --token <token:string>", "API token for worker job mode")
|
||||
.option("-r --remote <url:string>", "Remote URL for worker job mode")
|
||||
.option(
|
||||
"-s --source-workspace <workspace:string>",
|
||||
"Source workspace ID (defaults to active workspace in CLI mode, required in worker job mode)"
|
||||
)
|
||||
.action(migrate as any);
|
||||
|
||||
export default command;
|
||||
@@ -5,6 +5,7 @@ import { loginInteractive, tryGetLoginInfo } from "../../core/login.ts";
|
||||
import { colors, Command, Confirm, Input, log, setClient, Table } from "../../../deps.ts";
|
||||
import { requireLogin } from "../../core/auth.ts";
|
||||
import { createWorkspaceFork, deleteWorkspaceFork } from "./fork.ts";
|
||||
import migrate from "./migrate.ts";
|
||||
|
||||
import * as wmill from "../../../gen/services.gen.ts";
|
||||
|
||||
|
||||
@@ -3,19 +3,29 @@
|
||||
import Alert from '../common/alert/Alert.svelte'
|
||||
import Button from '../common/button/Button.svelte'
|
||||
import { sendUserToast } from '$lib/toast'
|
||||
import { WorkspaceService } from '$lib/gen'
|
||||
import { WorkspaceService, JobService } from '$lib/gen'
|
||||
import Modal from '../common/modal/Modal.svelte'
|
||||
import { Pen } from 'lucide-svelte'
|
||||
import { Pen, Loader2 } from 'lucide-svelte'
|
||||
import { isCloudHosted } from '$lib/cloud'
|
||||
import { onDestroy } from 'svelte'
|
||||
import { hubPaths } from '$lib/hub'
|
||||
|
||||
let newName = ''
|
||||
let newId = ''
|
||||
let checking = false
|
||||
let errorId = ''
|
||||
let { open = $bindable(false) } = $props()
|
||||
|
||||
$: newId = newName.toLowerCase().replace(/\s/gi, '-')
|
||||
let newName = $state('')
|
||||
let newId = $state('')
|
||||
|
||||
$: validateName(newId)
|
||||
$effect(() => {
|
||||
if (!incompleteMigration && newName) {
|
||||
newId = newName.toLowerCase().replace(/\s/gi, '-')
|
||||
}
|
||||
})
|
||||
let checking = $state(false)
|
||||
let errorId = $state('')
|
||||
|
||||
$effect(() => {
|
||||
validateName(newId)
|
||||
})
|
||||
|
||||
async function validateName(id: string): Promise<void> {
|
||||
checking = true
|
||||
@@ -30,30 +40,216 @@
|
||||
checking = false
|
||||
}
|
||||
|
||||
let loading = false
|
||||
async function renameWorkspace() {
|
||||
let loading = $state(false)
|
||||
let workspaceDataMigrated = $state(false)
|
||||
let oldWorkspaceId = $state('')
|
||||
|
||||
let jobMigrationJobId = $state<string | undefined>(undefined)
|
||||
let migratingJobs = $state(false)
|
||||
let jobMigrationComplete = $state(false)
|
||||
let pollInterval: number | null = null
|
||||
|
||||
let migrationInProgress = $state(false)
|
||||
let migrationError = $state<string | null>(null)
|
||||
|
||||
const isWorkspaceDataStep = $derived(migrationInProgress && !workspaceDataMigrated)
|
||||
const isJobsStep = $derived(migratingJobs)
|
||||
const isComplete = $derived(jobMigrationComplete)
|
||||
const isError = $derived(!!migrationError)
|
||||
|
||||
let incompleteMigration = $state<{
|
||||
targetWorkspaceId: string
|
||||
sourceWorkspaceId: string
|
||||
} | null>(null)
|
||||
let checkingIncomplete = $state(false)
|
||||
|
||||
async function checkForIncompleteMigration() {
|
||||
if (!$workspaceStore) return
|
||||
|
||||
console.log('Checking for incomplete migration for workspace:', $workspaceStore)
|
||||
try {
|
||||
loading = true
|
||||
await WorkspaceService.changeWorkspaceId({
|
||||
checkingIncomplete = true
|
||||
const targetWorkspaceId = await WorkspaceService.getIncompleteMigration({
|
||||
workspace: $workspaceStore
|
||||
})
|
||||
|
||||
console.log('Incomplete migration check result:', targetWorkspaceId)
|
||||
if (targetWorkspaceId) {
|
||||
incompleteMigration = {
|
||||
targetWorkspaceId,
|
||||
sourceWorkspaceId: $workspaceStore
|
||||
}
|
||||
oldWorkspaceId = $workspaceStore
|
||||
newId = targetWorkspaceId
|
||||
newName = targetWorkspaceId.replace(/-/g, ' ')
|
||||
workspaceDataMigrated = true
|
||||
}
|
||||
} catch (err: any) {
|
||||
console.error('Error checking for incomplete migration:', err)
|
||||
} finally {
|
||||
checkingIncomplete = false
|
||||
}
|
||||
}
|
||||
|
||||
async function checkJobStatus() {
|
||||
if (!jobMigrationJobId) return
|
||||
|
||||
try {
|
||||
const jobResult = await JobService.getCompletedJobResultMaybe({
|
||||
workspace: $workspaceStore!,
|
||||
id: jobMigrationJobId
|
||||
})
|
||||
if (jobResult.completed) {
|
||||
migratingJobs = false
|
||||
stopPolling()
|
||||
if (jobResult.success) {
|
||||
jobMigrationComplete = true
|
||||
sendUserToast('Job migration completed!')
|
||||
try {
|
||||
await WorkspaceService.completeWorkspaceMigration({
|
||||
requestBody: {
|
||||
source_workspace_id: $workspaceStore!,
|
||||
target_workspace_id: newId
|
||||
}
|
||||
})
|
||||
sendUserToast(`Migration completed and old workspace deleted`)
|
||||
window.location.href = `/workspace_settings?tab=general&workspace=${newId}`
|
||||
} catch (error) {
|
||||
throw error
|
||||
}
|
||||
} else {
|
||||
throw Error(JSON.stringify(jobResult.result))
|
||||
}
|
||||
}
|
||||
} catch (err: any) {
|
||||
stopPolling()
|
||||
migratingJobs = false
|
||||
migrationInProgress = false
|
||||
migrationError = err.body || err.message
|
||||
sendUserToast(`Migration error: ${err.body || err.message}`, true)
|
||||
}
|
||||
}
|
||||
|
||||
async function cancelJobMigration() {
|
||||
if (!jobMigrationJobId) return
|
||||
|
||||
try {
|
||||
await JobService.cancelQueuedJob({
|
||||
workspace: $workspaceStore!,
|
||||
id: jobMigrationJobId,
|
||||
requestBody: {
|
||||
new_name: newName,
|
||||
new_id: newId
|
||||
reason: 'User cancelled migration'
|
||||
}
|
||||
})
|
||||
open = false
|
||||
|
||||
sendUserToast(`Renamed workspace to ${newName}. Reloading...`)
|
||||
await new Promise((resolve) => setTimeout(resolve, 1000))
|
||||
window.location.href = '/workspace_settings?tab=general&workspace=' + newId
|
||||
} catch (err) {
|
||||
sendUserToast(`Error renaming workspace: ${err}`, true)
|
||||
sendUserToast('Migration cancelled')
|
||||
stopPolling()
|
||||
migratingJobs = false
|
||||
migrationInProgress = false
|
||||
incompleteMigration = {
|
||||
sourceWorkspaceId: $workspaceStore!,
|
||||
targetWorkspaceId: newId
|
||||
}
|
||||
} catch (err: any) {
|
||||
sendUserToast(`Failed to cancel: ${err.body || err.message}`, true)
|
||||
}
|
||||
}
|
||||
|
||||
function startPolling() {
|
||||
if (!pollInterval) {
|
||||
pollInterval = setInterval(checkJobStatus, 1000) as any
|
||||
}
|
||||
}
|
||||
|
||||
function stopPolling() {
|
||||
if (pollInterval) {
|
||||
clearInterval(pollInterval)
|
||||
pollInterval = null
|
||||
}
|
||||
}
|
||||
|
||||
async function performFullMigration(ignore_workspace_data?: boolean) {
|
||||
try {
|
||||
migrationInProgress = true
|
||||
migrationError = null
|
||||
loading = true
|
||||
oldWorkspaceId = $workspaceStore!
|
||||
|
||||
if (!ignore_workspace_data) {
|
||||
await WorkspaceService.migrateWorkspaceTables({
|
||||
requestBody: {
|
||||
source_workspace_id: oldWorkspaceId,
|
||||
target_workspace_id: newId,
|
||||
target_workspace_name: newName
|
||||
}
|
||||
})
|
||||
workspaceDataMigrated = true
|
||||
sendUserToast(`Workspace data migrated to ${newId}`)
|
||||
}
|
||||
|
||||
migratingJobs = true
|
||||
|
||||
jobMigrationJobId = await JobService.runScriptByPath({
|
||||
workspace: $workspaceStore!,
|
||||
path: hubPaths.workspaceMigrator,
|
||||
requestBody: {
|
||||
source_workspace_id: oldWorkspaceId,
|
||||
target_workspace_id: newId
|
||||
},
|
||||
skipPreprocessor: true
|
||||
})
|
||||
|
||||
startPolling()
|
||||
loading = false
|
||||
} catch (err: any) {
|
||||
migrationError = err.body || err.message
|
||||
sendUserToast(`Migration failed: ${migrationError}`, true)
|
||||
} finally {
|
||||
if (!migratingJobs) {
|
||||
loading = false
|
||||
migrationInProgress = false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
async function revertMigration() {
|
||||
const sourceWorkspaceId = incompleteMigration?.sourceWorkspaceId || oldWorkspaceId
|
||||
const targetWorkspaceId = incompleteMigration?.targetWorkspaceId || newId
|
||||
|
||||
if (!sourceWorkspaceId || !targetWorkspaceId) return
|
||||
|
||||
try {
|
||||
loading = true
|
||||
|
||||
await WorkspaceService.revertWorkspaceMigration({
|
||||
workspace: sourceWorkspaceId,
|
||||
requestBody: {
|
||||
target_workspace_id: targetWorkspaceId
|
||||
}
|
||||
})
|
||||
|
||||
sendUserToast('Migration reverted successfully!')
|
||||
|
||||
incompleteMigration = null
|
||||
workspaceDataMigrated = false
|
||||
migratingJobs = false
|
||||
jobMigrationComplete = false
|
||||
migrationInProgress = false
|
||||
migrationError = null
|
||||
newName = ''
|
||||
newId = ''
|
||||
oldWorkspaceId = ''
|
||||
errorId = ''
|
||||
} catch (err: any) {
|
||||
sendUserToast(`Failed to revert migration: ${err.body || err.message}`, true)
|
||||
} finally {
|
||||
loading = false
|
||||
}
|
||||
}
|
||||
|
||||
export let open = false
|
||||
onDestroy(() => {
|
||||
stopPolling()
|
||||
})
|
||||
</script>
|
||||
|
||||
<div class="flex flex-col gap-1">
|
||||
@@ -63,6 +259,7 @@
|
||||
{#if !isCloudHosted() || $superadmin}
|
||||
<Button
|
||||
on:click={() => {
|
||||
checkForIncompleteMigration()
|
||||
open = true
|
||||
}}
|
||||
size="xs"
|
||||
@@ -78,38 +275,255 @@
|
||||
<p class="text-xs text-secondary font-normal">Slug to uniquely identify your workspace</p>
|
||||
</div>
|
||||
|
||||
<Modal bind:open title="Change workspace ID">
|
||||
<div class="flex flex-col gap-4">
|
||||
<Alert type="warning" title="Warning">
|
||||
Renaming the workspace may take a few minutes to complete. Once finished, please update your
|
||||
webhook calls and adjust your CLI sync configuration accordingly.
|
||||
</Alert>
|
||||
<p class="text-secondary text-sm"
|
||||
>Current ID <br /> <span class="font-bold">{$workspaceStore ?? ''}</span></p
|
||||
>
|
||||
<label class="block">
|
||||
<span class="text-secondary text-sm">New name</span>
|
||||
<input type="text" bind:value={newName} />
|
||||
</label>
|
||||
<label class="block">
|
||||
<span class="text-secondary text-sm">New ID</span>
|
||||
<input type="text" bind:value={newId} />
|
||||
{#if errorId}
|
||||
<div class="text-red-500 text-xs mt-1">{errorId}</div>
|
||||
<Modal
|
||||
bind:open
|
||||
title={isComplete
|
||||
? 'Migration Complete'
|
||||
: migrationInProgress
|
||||
? isWorkspaceDataStep
|
||||
? 'Step 1: Migrating workspace data'
|
||||
: 'Step 2: Migrating Jobs'
|
||||
: 'Change Workspace ID'}
|
||||
>
|
||||
<div class="flex flex-col gap-6">
|
||||
{#if checkingIncomplete}
|
||||
<Alert type="info" title="Checking for incomplete migrations...">
|
||||
<p class="text-sm">Please wait while we check for any incomplete workspace migrations.</p>
|
||||
</Alert>
|
||||
{:else if migrationInProgress || migratingJobs}
|
||||
<div
|
||||
class="bg-blue-50 dark:bg-blue-900/20 border border-blue-200 dark:border-blue-800 p-6 rounded-lg"
|
||||
>
|
||||
<div class="flex items-center gap-4 mb-4">
|
||||
<Loader2 class="w-12 h-12 animate-spin text-blue-500" />
|
||||
<div>
|
||||
<h3 class="font-semibold text-blue-900 dark:text-blue-100">Migration in Progress</h3>
|
||||
<p class="text-sm text-blue-700 dark:text-blue-300">
|
||||
{#if isWorkspaceDataStep}
|
||||
Migrating workspace data (scripts, flows, apps, settings)...
|
||||
{:else if isJobsStep}
|
||||
Migrating job history - this may take several minutes
|
||||
{:else}
|
||||
This process may take several minutes depending on job history size
|
||||
{/if}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div class="w-full bg-gray-200 dark:bg-gray-700 rounded-full h-2">
|
||||
<div
|
||||
class="bg-blue-500 h-2 rounded-full transition-all duration-500"
|
||||
style="width: {isWorkspaceDataStep ? '30%' : isJobsStep ? '70%' : '100%'}"
|
||||
></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="bg-surface-secondary p-4 rounded-lg border">
|
||||
<p class="text-sm font-medium mb-3">Migration Progress</p>
|
||||
<div class="space-y-2">
|
||||
<div class="flex items-center gap-3">
|
||||
<div
|
||||
class="w-4 h-4 rounded-full {!isWorkspaceDataStep && workspaceDataMigrated
|
||||
? 'bg-green-500'
|
||||
: 'bg-blue-500 animate-pulse'} flex items-center justify-center"
|
||||
>
|
||||
{#if !isWorkspaceDataStep && workspaceDataMigrated}
|
||||
<span class="text-white text-xs">✓</span>
|
||||
{/if}
|
||||
</div>
|
||||
<span class="text-sm">Step 1: Migrate workspace data</span>
|
||||
</div>
|
||||
<div class="flex items-center gap-3">
|
||||
<div
|
||||
class="w-4 h-4 rounded-full {isComplete
|
||||
? 'bg-green-500'
|
||||
: isJobsStep
|
||||
? 'bg-blue-500 animate-pulse'
|
||||
: 'bg-gray-300 dark:bg-gray-600'} flex items-center justify-center"
|
||||
>
|
||||
{#if isComplete}
|
||||
<span class="text-white text-xs">✓</span>
|
||||
{/if}
|
||||
</div>
|
||||
<span class="text-sm {isJobsStep || isComplete ? '' : 'text-gray-500'}"
|
||||
>Step 2: Migrate job</span
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="space-y-1 text-sm text-secondary mt-3 pt-3 border-t border-gray-200 dark:border-gray-700"
|
||||
>
|
||||
<p><span class="font-medium">From:</span> {oldWorkspaceId}</p>
|
||||
<p><span class="font-medium">To:</span> {newId}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<Alert type="warning" title="Important">
|
||||
<p class="text-sm">
|
||||
Please do not close this window or navigate away during the migration process. This
|
||||
ensures data integrity and allows proper completion tracking.
|
||||
</p>
|
||||
</Alert>
|
||||
{:else if isError && migrationError}
|
||||
<Alert type="error" title="Migration Failed">
|
||||
<div class="space-y-3">
|
||||
<p class="text-sm"> The change workspace ID process failed. </p>
|
||||
<details class="text-sm">
|
||||
<summary class="cursor-pointer font-medium">Error Details</summary>
|
||||
<pre class="mt-2 text-xs bg-gray-100 dark:bg-gray-800 p-2 rounded overflow-auto"
|
||||
>{migrationError}</pre
|
||||
>
|
||||
</details>
|
||||
</div>
|
||||
</Alert>
|
||||
{:else}
|
||||
{#if incompleteMigration}
|
||||
<Alert type="warning" title="Incomplete Migration Detected">
|
||||
<div class="space-y-3">
|
||||
<p class="text-sm">
|
||||
We found an incomplete migration from workspace <strong
|
||||
>{incompleteMigration.sourceWorkspaceId}</strong
|
||||
>
|
||||
to <strong>{incompleteMigration.targetWorkspaceId}</strong>.
|
||||
</p>
|
||||
<p class="text-sm"> You can either complete the migration or revert to start over. </p>
|
||||
</div>
|
||||
</Alert>
|
||||
{/if}
|
||||
</label>
|
||||
|
||||
<div
|
||||
class="bg-blue-50 dark:bg-blue-900/20 border border-blue-200 dark:border-blue-800 p-4 rounded-lg"
|
||||
>
|
||||
<div class="flex items-center gap-2 mb-2">
|
||||
<div class="w-2 h-2 bg-blue-500 rounded-full"></div>
|
||||
<span class="text-blue-700 dark:text-blue-300 text-sm font-medium">Current Workspace</span
|
||||
>
|
||||
</div>
|
||||
<p class="font-mono text-lg font-bold text-blue-900 dark:text-blue-100">
|
||||
{$workspaceStore ?? ''}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div class="space-y-4">
|
||||
<label class="block">
|
||||
<span class="text-secondary text-sm font-medium">New Workspace Name</span>
|
||||
<input
|
||||
type="text"
|
||||
bind:value={newName}
|
||||
placeholder="Enter new workspace name"
|
||||
class="mt-1 w-full px-3 py-2 border border-gray-300 dark:border-gray-600 rounded-md focus:ring-2 focus:ring-blue-500 focus:border-blue-500 disabled:bg-gray-100 dark:disabled:bg-gray-800 disabled:cursor-not-allowed"
|
||||
disabled={incompleteMigration !== null || migrationInProgress || workspaceDataMigrated}
|
||||
/>
|
||||
</label>
|
||||
<label class="block">
|
||||
<span class="text-secondary text-sm font-medium">New Workspace ID</span>
|
||||
<input
|
||||
type="text"
|
||||
bind:value={newId}
|
||||
placeholder="auto-generated from name"
|
||||
class="mt-1 w-full px-3 py-2 border border-gray-300 dark:border-gray-600 rounded-md focus:ring-2 focus:ring-blue-500 focus:border-blue-500 disabled:bg-gray-100 dark:disabled:bg-gray-800 disabled:cursor-not-allowed"
|
||||
disabled={incompleteMigration !== null || migrationInProgress || workspaceDataMigrated}
|
||||
/>
|
||||
{#if errorId && incompleteMigration == null}
|
||||
<div class="text-red-500 text-xs mt-1 flex items-center gap-1">
|
||||
<span class="w-3 h-3 text-red-500">⚠</span>
|
||||
{errorId}
|
||||
</div>
|
||||
{/if}
|
||||
</label>
|
||||
</div>
|
||||
|
||||
<Alert type="warning" title="Important Notice">
|
||||
<p class="text-sm">
|
||||
Once finished, please update your webhook calls and adjust your CLI sync configuration
|
||||
accordingly.
|
||||
</p>
|
||||
</Alert>
|
||||
{/if}
|
||||
</div>
|
||||
|
||||
<svelte:fragment slot="actions">
|
||||
<Button
|
||||
size="sm"
|
||||
disabled={checking || errorId.length > 0 || !newName || !newId}
|
||||
{loading}
|
||||
on:click={() => {
|
||||
renameWorkspace()
|
||||
}}
|
||||
>
|
||||
Save
|
||||
</Button>
|
||||
{#if migrationInProgress && migratingJobs}
|
||||
<Button
|
||||
onclick={(e) => {
|
||||
e.preventDefault()
|
||||
cancelJobMigration()
|
||||
}}
|
||||
color="red"
|
||||
size="sm"
|
||||
>
|
||||
Cancel Migration
|
||||
</Button>
|
||||
{:else if incompleteMigration}
|
||||
<div class="flex gap-3 w-full">
|
||||
<Button
|
||||
size="sm"
|
||||
color="red"
|
||||
onclick={(e) => {
|
||||
e.preventDefault()
|
||||
revertMigration()
|
||||
}}
|
||||
{loading}
|
||||
>
|
||||
Revert Migration
|
||||
</Button>
|
||||
<Button
|
||||
size="sm"
|
||||
disabled={loading}
|
||||
onclick={async (e) => {
|
||||
e.preventDefault()
|
||||
incompleteMigration = null
|
||||
workspaceDataMigrated = true
|
||||
await performFullMigration(true)
|
||||
}}
|
||||
color="blue"
|
||||
>
|
||||
Complete Migration
|
||||
</Button>
|
||||
</div>
|
||||
{:else if isError}
|
||||
<div class="flex gap-3">
|
||||
<Button
|
||||
size="sm"
|
||||
color="red"
|
||||
onclick={(e) => {
|
||||
e.preventDefault()
|
||||
revertMigration()
|
||||
}}
|
||||
{loading}
|
||||
>
|
||||
Revert Migration
|
||||
</Button>
|
||||
<Button
|
||||
size="sm"
|
||||
color="blue"
|
||||
onclick={async (e) => {
|
||||
e.preventDefault()
|
||||
migrationError = null
|
||||
migrationInProgress = false
|
||||
await performFullMigration(!isWorkspaceDataStep)
|
||||
}}
|
||||
>
|
||||
Try Again
|
||||
</Button>
|
||||
</div>
|
||||
{:else}
|
||||
<Button
|
||||
size="sm"
|
||||
disabled={checking ||
|
||||
errorId.length > 0 ||
|
||||
!newName ||
|
||||
!newId ||
|
||||
loading ||
|
||||
migrationInProgress}
|
||||
{loading}
|
||||
onclick={async (e) => {
|
||||
e.preventDefault()
|
||||
await performFullMigration()
|
||||
}}
|
||||
color="blue"
|
||||
>
|
||||
Change Workspace
|
||||
</Button>
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
</Modal>
|
||||
|
||||
@@ -99,6 +99,7 @@ type HubPaths = {
|
||||
emailErrorHandler: string
|
||||
cloneRepoToS3forGitRepoViewer: string
|
||||
appReport: string
|
||||
workspaceMigrator: string
|
||||
}
|
||||
|
||||
export const hubPaths = JSON.parse(rawHubPaths) as HubPaths
|
||||
|
||||
@@ -43,5 +43,6 @@
|
||||
"smtpReport": "hub/9086/smtp",
|
||||
"appReport": "hub/28076/app-report",
|
||||
"cloneRepoToS3forGitRepoViewer_0": "hub/19825/clone_repo_and_upload_to_instance_storage",
|
||||
"cloneRepoToS3forGitRepoViewer": "hub/19827/clone_repo_and_upload_to_instance_storage"
|
||||
"cloneRepoToS3forGitRepoViewer": "hub/19827/clone_repo_and_upload_to_instance_storage",
|
||||
"workspaceMigrator": "hub/28067/workspace_job_migrator"
|
||||
}
|
||||
|
||||
Submodule intra-uuid-e4eed185-2f29-415f-947e-b2bdc697c8a9-4888488-dtoure added at 6668698e0b
Reference in New Issue
Block a user