aboutsummaryrefslogtreecommitdiff
path: root/models/models.go
diff options
context:
space:
mode:
Diffstat (limited to 'models/models.go')
-rw-r--r--models/models.go40
1 files changed, 28 insertions, 12 deletions
diff --git a/models/models.go b/models/models.go
index f33c32d0..4392bb76 100644
--- a/models/models.go
+++ b/models/models.go
@@ -7,7 +7,6 @@ package models
import (
"bufio"
"database/sql"
- "encoding/json"
"errors"
"fmt"
"net/url"
@@ -20,6 +19,7 @@ import (
_ "github.com/go-sql-driver/mysql"
"github.com/go-xorm/core"
"github.com/go-xorm/xorm"
+ "github.com/json-iterator/go"
_ "github.com/lib/pq"
log "gopkg.in/clog.v1"
@@ -285,8 +285,7 @@ func DumpDatabase(dirPath string) (err error) {
}
if err = x.Asc("id").Iterate(table, func(idx int, bean interface{}) (err error) {
- enc := json.NewEncoder(f)
- return enc.Encode(bean)
+ return jsoniter.NewEncoder(f).Encode(bean)
}); err != nil {
f.Close()
return fmt.Errorf("fail to dump table '%s': %v", tableName, err)
@@ -300,6 +299,10 @@ func DumpDatabase(dirPath string) (err error) {
func ImportDatabase(dirPath string, verbose bool) (err error) {
snakeMapper := core.SnakeMapper{}
+ skipInsertProcessors := map[string]bool{
+ "mirror": true,
+ }
+
// Purposely create a local variable to not modify global variable
tables := append(tables, new(Version))
for _, table := range tables {
@@ -314,22 +317,24 @@ func ImportDatabase(dirPath string, verbose bool) (err error) {
}
if err = x.DropTables(table); err != nil {
- return fmt.Errorf("fail to drop table '%s': %v", tableName, err)
+ return fmt.Errorf("drop table '%s': %v", tableName, err)
} else if err = x.Sync2(table); err != nil {
- return fmt.Errorf("fail to sync table '%s': %v", tableName, err)
+ return fmt.Errorf("sync table '%s': %v", tableName, err)
}
f, err := os.Open(tableFile)
if err != nil {
- return fmt.Errorf("fail to open JSON file: %v", err)
+ return fmt.Errorf("open JSON file: %v", err)
}
+ rawTableName := x.TableName(table)
+ _, isInsertProcessor := table.(xorm.BeforeInsertProcessor)
scanner := bufio.NewScanner(f)
for scanner.Scan() {
switch bean := table.(type) {
case *LoginSource:
meta := make(map[string]interface{})
- if err = json.Unmarshal(scanner.Bytes(), &meta); err != nil {
- return fmt.Errorf("fail to unmarshal to map: %v", err)
+ if err = jsoniter.Unmarshal(scanner.Bytes(), &meta); err != nil {
+ return fmt.Errorf("unmarshal to map: %v", err)
}
tp := LoginType(com.StrTo(com.ToStr(meta["Type"])).MustInt64())
@@ -346,12 +351,23 @@ func ImportDatabase(dirPath string, verbose bool) (err error) {
table = bean
}
- if err = json.Unmarshal(scanner.Bytes(), table); err != nil {
- return fmt.Errorf("fail to unmarshal to struct: %v", err)
+ if err = jsoniter.Unmarshal(scanner.Bytes(), table); err != nil {
+ return fmt.Errorf("unmarshal to struct: %v", err)
}
if _, err = x.Insert(table); err != nil {
- return fmt.Errorf("fail to insert strcut: %v", err)
+ return fmt.Errorf("insert strcut: %v", err)
+ }
+
+ // Reset created_unix back to the date save in archive because Insert method updates its value
+ if isInsertProcessor && !skipInsertProcessors[rawTableName] {
+ meta := make(map[string]interface{})
+ if err = jsoniter.Unmarshal(scanner.Bytes(), &meta); err != nil {
+ log.Error(2, "Failed to unmarshal to map: %v", err)
+ }
+ if _, err = x.Exec("UPDATE "+rawTableName+" SET created_unix=? WHERE id=?", meta["CreatedUnix"], meta["ID"]); err != nil {
+ log.Error(2, "Failed to reset 'created_unix': %v", err)
+ }
}
}
@@ -360,7 +376,7 @@ func ImportDatabase(dirPath string, verbose bool) (err error) {
rawTableName := snakeMapper.Obj2Table(tableName)
seqName := rawTableName + "_id_seq"
if _, err = x.Exec(fmt.Sprintf(`SELECT setval('%s', COALESCE((SELECT MAX(id)+1 FROM "%s"), 1), false);`, seqName, rawTableName)); err != nil {
- return fmt.Errorf("fail to reset table '%s' sequence: %v", rawTableName, err)
+ return fmt.Errorf("reset table '%s' sequence: %v", rawTableName, err)
}
}
}