mirror of
https://github.com/wavetermdev/waveterm.git
synced 2024-12-22 16:48:23 +01:00
158 lines
3.9 KiB
Go
158 lines
3.9 KiB
Go
// Copyright 2023, Command Line Inc.
|
|
// SPDX-License-Identifier: Apache-2.0
|
|
|
|
package sstore
|
|
|
|
import (
|
|
"context"
|
|
"fmt"
|
|
"log"
|
|
"os"
|
|
"time"
|
|
|
|
"github.com/wavetermdev/waveterm/wavesrv/pkg/scbase"
|
|
)
|
|
|
|
const MigrationChunkSize = 10
|
|
|
|
type cmdMigration13Type struct {
|
|
SessionId string
|
|
ScreenId string
|
|
CmdId string
|
|
}
|
|
|
|
type cmdMigration20Type struct {
|
|
ScreenId string
|
|
LineId string
|
|
CmdId string
|
|
}
|
|
|
|
func getSliceChunk[T any](slice []T, chunkSize int) ([]T, []T) {
|
|
if chunkSize >= len(slice) {
|
|
return slice, nil
|
|
}
|
|
return slice[0:chunkSize], slice[chunkSize:]
|
|
}
|
|
|
|
func RunMigration20() error {
|
|
ctx := context.Background()
|
|
startTime := time.Now()
|
|
var migrations []cmdMigration20Type
|
|
txErr := WithTx(ctx, func(tx *TxWrap) error {
|
|
tx.Select(&migrations, `SELECT * FROM cmd_migrate20`)
|
|
return nil
|
|
})
|
|
if txErr != nil {
|
|
return fmt.Errorf("trying to get cmd20 migrations: %w", txErr)
|
|
}
|
|
log.Printf("[db] got %d cmd-line migrations\n", len(migrations))
|
|
for len(migrations) > 0 {
|
|
var mchunk []cmdMigration20Type
|
|
mchunk, migrations = getSliceChunk(migrations, MigrationChunkSize)
|
|
err := processMigration20Chunk(ctx, mchunk)
|
|
if err != nil {
|
|
return fmt.Errorf("cmd migration failed on chunk: %w", err)
|
|
}
|
|
}
|
|
log.Printf("[db] cmd line migration done: %v\n", time.Since(startTime))
|
|
return nil
|
|
}
|
|
|
|
func processMigration20Chunk(ctx context.Context, mchunk []cmdMigration20Type) error {
|
|
for _, mig := range mchunk {
|
|
newFile, err := scbase.PtyOutFile(mig.ScreenId, mig.LineId)
|
|
if err != nil {
|
|
log.Printf("ptyoutfile(lineid) error: %v\n", err)
|
|
continue
|
|
}
|
|
oldFile, err := scbase.PtyOutFile(mig.ScreenId, mig.CmdId)
|
|
if err != nil {
|
|
log.Printf("ptyoutfile(cmdid) error: %v\n", err)
|
|
continue
|
|
}
|
|
err = os.Rename(oldFile, newFile)
|
|
if err != nil {
|
|
log.Printf("error renaming %s => %s: %v\n", oldFile, newFile, err)
|
|
continue
|
|
}
|
|
}
|
|
txErr := WithTx(ctx, func(tx *TxWrap) error {
|
|
for _, mig := range mchunk {
|
|
query := `DELETE FROM cmd_migrate20 WHERE cmdid = ?`
|
|
tx.Exec(query, mig.CmdId)
|
|
}
|
|
return nil
|
|
})
|
|
if txErr != nil {
|
|
return txErr
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func RunMigration13() error {
|
|
ctx := context.Background()
|
|
startTime := time.Now()
|
|
var migrations []cmdMigration13Type
|
|
txErr := WithTx(ctx, func(tx *TxWrap) error {
|
|
tx.Select(&migrations, `SELECT * FROM cmd_migrate`)
|
|
return nil
|
|
})
|
|
if txErr != nil {
|
|
return fmt.Errorf("trying to get cmd13 migrations: %w", txErr)
|
|
}
|
|
log.Printf("[db] got %d cmd-screen migrations\n", len(migrations))
|
|
for len(migrations) > 0 {
|
|
var mchunk []cmdMigration13Type
|
|
mchunk, migrations = getSliceChunk(migrations, MigrationChunkSize)
|
|
err := processMigration13Chunk(ctx, mchunk)
|
|
if err != nil {
|
|
return fmt.Errorf("cmd migration failed on chunk: %w", err)
|
|
}
|
|
}
|
|
err := os.RemoveAll(scbase.GetSessionsDir())
|
|
if err != nil {
|
|
return fmt.Errorf("cannot remove old sessions dir %s: %w\n", scbase.GetSessionsDir(), err)
|
|
}
|
|
txErr = WithTx(ctx, func(tx *TxWrap) error {
|
|
query := `UPDATE client SET cmdstoretype = 'screen'`
|
|
tx.Exec(query)
|
|
return nil
|
|
})
|
|
if txErr != nil {
|
|
return fmt.Errorf("cannot change client cmdstoretype: %w", err)
|
|
}
|
|
log.Printf("[db] cmd screen migration done: %v\n", time.Since(startTime))
|
|
return nil
|
|
}
|
|
|
|
func processMigration13Chunk(ctx context.Context, mchunk []cmdMigration13Type) error {
|
|
for _, mig := range mchunk {
|
|
newFile, err := scbase.PtyOutFile(mig.ScreenId, mig.CmdId)
|
|
if err != nil {
|
|
log.Printf("ptyoutfile error: %v\n", err)
|
|
continue
|
|
}
|
|
oldFile, err := scbase.PtyOutFile_Sessions(mig.SessionId, mig.CmdId)
|
|
if err != nil {
|
|
log.Printf("ptyoutfile_sessions error: %v\n", err)
|
|
continue
|
|
}
|
|
err = os.Rename(oldFile, newFile)
|
|
if err != nil {
|
|
log.Printf("error renaming %s => %s: %v\n", oldFile, newFile, err)
|
|
continue
|
|
}
|
|
}
|
|
txErr := WithTx(ctx, func(tx *TxWrap) error {
|
|
for _, mig := range mchunk {
|
|
query := `DELETE FROM cmd_migrate WHERE cmdid = ?`
|
|
tx.Exec(query, mig.CmdId)
|
|
}
|
|
return nil
|
|
})
|
|
if txErr != nil {
|
|
return txErr
|
|
}
|
|
return nil
|
|
}
|