mirror of
https://github.com/documize/community.git
synced 2025-07-19 21:29:42 +02:00
Enable in-app backup/restore for global/tenants
Re-mapping of ORG and USER ID values ensures conflict-free merging. Version numbers bumped. Co-Authored-By: Harvey Kandola <harvey@documize.com>
This commit is contained in:
parent
ec1939c01d
commit
db04057d9e
10 changed files with 913 additions and 788 deletions
|
@ -58,9 +58,9 @@ Space view.
|
||||||
|
|
||||||
## Latest version
|
## Latest version
|
||||||
|
|
||||||
[Community edition: v1.71.0](https://github.com/documize/community/releases)
|
[Community edition: v1.72.0](https://github.com/documize/community/releases)
|
||||||
|
|
||||||
[Enterprise edition: v1.73.0](https://documize.com/downloads)
|
[Enterprise edition: v1.74.0](https://documize.com/downloads)
|
||||||
|
|
||||||
## OS support
|
## OS support
|
||||||
|
|
||||||
|
|
1
core/env/logger.go
vendored
1
core/env/logger.go
vendored
|
@ -15,6 +15,7 @@ package env
|
||||||
// Logger provides the interface for Documize compatible loggers.
|
// Logger provides the interface for Documize compatible loggers.
|
||||||
type Logger interface {
|
type Logger interface {
|
||||||
Info(message string)
|
Info(message string)
|
||||||
|
Infof(message string, a ...interface{})
|
||||||
Trace(message string)
|
Trace(message string)
|
||||||
Error(message string, err error)
|
Error(message string, err error)
|
||||||
// SetDB(l Logger, db *sqlx.DB) Logger
|
// SetDB(l Logger, db *sqlx.DB) Logger
|
||||||
|
|
|
@ -194,6 +194,7 @@ func (h *Handler) Restore(w http.ResponseWriter, r *http.Request) {
|
||||||
spec := m.ImportSpec{OverwriteOrg: overwriteOrg, CreateUsers: createUsers, Org: org}
|
spec := m.ImportSpec{OverwriteOrg: overwriteOrg, CreateUsers: createUsers, Org: org}
|
||||||
rh := restoreHandler{Runtime: h.Runtime, Store: h.Store, Context: ctx, Spec: spec}
|
rh := restoreHandler{Runtime: h.Runtime, Store: h.Store, Context: ctx, Spec: spec}
|
||||||
|
|
||||||
|
// Run the restore process.
|
||||||
err = rh.PerformRestore(b.Bytes(), r.ContentLength)
|
err = rh.PerformRestore(b.Bytes(), r.ContentLength)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
response.WriteServerError(w, method, err)
|
response.WriteServerError(w, method, err)
|
||||||
|
@ -201,6 +202,8 @@ func (h *Handler) Restore(w http.ResponseWriter, r *http.Request) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
h.Runtime.Log.Infof("Restore remapped %d OrgID values", len(rh.MapOrgID))
|
||||||
|
h.Runtime.Log.Infof("Restore remapped %d UserID values", len(rh.MapUserID))
|
||||||
h.Runtime.Log.Info("Restore completed")
|
h.Runtime.Log.Info("Restore completed")
|
||||||
|
|
||||||
response.WriteEmpty(w)
|
response.WriteEmpty(w)
|
||||||
|
|
|
@ -18,6 +18,7 @@ package backup
|
||||||
import (
|
import (
|
||||||
"archive/zip"
|
"archive/zip"
|
||||||
"bytes"
|
"bytes"
|
||||||
|
"database/sql"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/documize/community/model/account"
|
"github.com/documize/community/model/account"
|
||||||
|
@ -53,6 +54,27 @@ type restoreHandler struct {
|
||||||
Spec m.ImportSpec
|
Spec m.ImportSpec
|
||||||
Context domain.RequestContext
|
Context domain.RequestContext
|
||||||
Zip *zip.Reader
|
Zip *zip.Reader
|
||||||
|
MapOrgID map[string]string
|
||||||
|
MapUserID map[string]string
|
||||||
|
}
|
||||||
|
|
||||||
|
// During the restore process, it may be necessary to change
|
||||||
|
// ID values found in backup file with a value that exists in the
|
||||||
|
// target database.
|
||||||
|
//
|
||||||
|
// NOTE: this only applies to tenant backups as we have to restore data
|
||||||
|
// into the active tenant.
|
||||||
|
func (r *restoreHandler) remapOrg(id string) string {
|
||||||
|
if n, ok := r.MapOrgID[id]; ok {
|
||||||
|
return n
|
||||||
|
}
|
||||||
|
return id
|
||||||
|
}
|
||||||
|
func (r *restoreHandler) remapUser(id string) string {
|
||||||
|
if n, ok := r.MapUserID[id]; ok {
|
||||||
|
return n
|
||||||
|
}
|
||||||
|
return id
|
||||||
}
|
}
|
||||||
|
|
||||||
// PerformRestore will unzip backup file and verify contents
|
// PerformRestore will unzip backup file and verify contents
|
||||||
|
@ -79,12 +101,40 @@ func (r *restoreHandler) PerformRestore(b []byte, l int64) (err error) {
|
||||||
r.Spec.GlobalBackup = false
|
r.Spec.GlobalBackup = false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Process might require reassignment of ID's so prepare map.
|
||||||
|
r.MapOrgID = make(map[string]string)
|
||||||
|
r.MapUserID = make(map[string]string)
|
||||||
|
|
||||||
// Organization.
|
// Organization.
|
||||||
err = r.dmzOrg()
|
err = r.dmzOrg()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// User.
|
||||||
|
err = r.dmzUser()
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// User Account.
|
||||||
|
err = r.dmzUserAccount()
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// User Activity.
|
||||||
|
err = r.dmzUserActivity()
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// User Config.
|
||||||
|
err = r.dmzUserConfig()
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
// Config.
|
// Config.
|
||||||
err = r.dmzConfig()
|
err = r.dmzConfig()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -205,30 +255,6 @@ func (r *restoreHandler) PerformRestore(b []byte, l int64) (err error) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// User.
|
|
||||||
err = r.dmzUser()
|
|
||||||
if err != nil {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
// User Account.
|
|
||||||
err = r.dmzUserAccount()
|
|
||||||
if err != nil {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
// User Activity.
|
|
||||||
err = r.dmzUserActivity()
|
|
||||||
if err != nil {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
// User Config.
|
|
||||||
err = r.dmzUserConfig()
|
|
||||||
if err != nil {
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -319,18 +345,17 @@ func (r *restoreHandler) dmzOrg() (err error) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// Nuke all existing data.
|
|
||||||
_, err = r.Context.Transaction.Exec("TRUNCATE TABLE dmz_org")
|
|
||||||
if err != nil {
|
|
||||||
r.Context.Transaction.Rollback()
|
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
// For global backup we recreate everything.
|
// For global backup we recreate everything.
|
||||||
// For tenant backup we just update the current OrgID to match
|
// For tenant backup we just update the current OrgID to match
|
||||||
// the one in the backup file, ensuring correct data linkage.
|
// the one in the backup file, ensuring correct data linkage.
|
||||||
if r.Spec.GlobalBackup {
|
if r.Spec.GlobalBackup {
|
||||||
|
// Nuke all existing data.
|
||||||
|
_, err = r.Context.Transaction.Exec("TRUNCATE TABLE dmz_org")
|
||||||
|
if err != nil {
|
||||||
|
r.Context.Transaction.Rollback()
|
||||||
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
for i := range org {
|
for i := range org {
|
||||||
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
||||||
|
@ -356,7 +381,10 @@ func (r *restoreHandler) dmzOrg() (err error) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
org[1].RefID = r.Spec.Org.RefID
|
// Existing orgID from database overrides all incoming orgID values
|
||||||
|
// by using remapOrg().
|
||||||
|
r.MapOrgID[org[0].RefID] = r.Spec.Org.RefID
|
||||||
|
org[0].RefID = r.remapOrg(org[0].RefID) // e.g. remap orgID
|
||||||
|
|
||||||
// Update org settings if allowed to do so.
|
// Update org settings if allowed to do so.
|
||||||
if !r.Spec.OverwriteOrg {
|
if !r.Spec.OverwriteOrg {
|
||||||
|
@ -460,13 +488,13 @@ func (r *restoreHandler) dmzAudit() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
for i := range log {
|
for i := range log {
|
||||||
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind("INSERT INTO dmz_audit_log (c_orgid, c_userid, c_eventtype, c_ip, c_created) VALUES (?, ?, ?, ?, ?)"),
|
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind("INSERT INTO dmz_audit_log (c_orgid, c_userid, c_eventtype, c_ip, c_created) VALUES (?, ?, ?, ?, ?)"),
|
||||||
log[i].OrgID, log[i].UserID, log[i].Type, log[i].IP, log[i].Created)
|
r.remapOrg(log[i].OrgID), r.remapUser(log[i].UserID), log[i].Type, log[i].IP, log[i].Created)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to insert %s %d", filename, log[i].ID))
|
err = errors.Wrap(err, fmt.Sprintf("unable to insert %s %d", filename, log[i].ID))
|
||||||
|
@ -516,13 +544,13 @@ func (r *restoreHandler) dmzAction() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
for i := range ac {
|
for i := range ac {
|
||||||
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind("INSERT INTO dmz_action (c_refid, c_orgid, c_userid, c_docid, c_actiontype, c_note, c_requestorid, c_requested, c_due, c_reftype, c_reftypeid) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
|
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind("INSERT INTO dmz_action (c_refid, c_orgid, c_userid, c_docid, c_actiontype, c_note, c_requestorid, c_requested, c_due, c_reftype, c_reftypeid) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
|
||||||
ac[i].RefID, ac[i].OrgID, ac[i].UserID, ac[i].DocumentID, ac[i].ActionType, ac[i].Note, ac[i].RequestorID, ac[i].Requested, ac[i].Due, ac[i].RefType, ac[i].RefTypeID)
|
ac[i].RefID, r.remapOrg(ac[i].OrgID), r.remapUser(ac[i].UserID), ac[i].DocumentID, ac[i].ActionType, ac[i].Note, ac[i].RequestorID, ac[i].Requested, ac[i].Due, ac[i].RefType, ac[i].RefTypeID)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to insert %s %s", filename, ac[i].RefID))
|
err = errors.Wrap(err, fmt.Sprintf("unable to insert %s %s", filename, ac[i].RefID))
|
||||||
|
@ -569,13 +597,13 @@ func (r *restoreHandler) dmzSpace() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
for i := range sp {
|
for i := range sp {
|
||||||
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind("INSERT INTO dmz_space (c_refid, c_name, c_orgid, c_userid, c_type, c_lifecycle, c_likes, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)"),
|
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind("INSERT INTO dmz_space (c_refid, c_name, c_orgid, c_userid, c_type, c_lifecycle, c_likes, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)"),
|
||||||
sp[i].RefID, sp[i].Name, sp[i].OrgID, sp[i].UserID, sp[i].Type, sp[i].Lifecycle, sp[i].Likes, sp[i].Created, sp[i].Revised)
|
sp[i].RefID, sp[i].Name, r.remapOrg(sp[i].OrgID), r.remapUser(sp[i].UserID), sp[i].Type, sp[i].Lifecycle, sp[i].Likes, sp[i].Created, sp[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -623,7 +651,7 @@ func (r *restoreHandler) dmzCategory() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -631,7 +659,7 @@ func (r *restoreHandler) dmzCategory() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
||||||
INSERT INTO dmz_category (c_refid, c_orgid, c_spaceid, c_name, c_created, c_revised)
|
INSERT INTO dmz_category (c_refid, c_orgid, c_spaceid, c_name, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?)`),
|
||||||
ct[i].RefID, ct[i].OrgID, ct[i].SpaceID, ct[i].Name, ct[i].Created, ct[i].Revised)
|
ct[i].RefID, r.remapOrg(ct[i].OrgID), ct[i].SpaceID, ct[i].Name, ct[i].Created, ct[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -679,7 +707,7 @@ func (r *restoreHandler) dmzCategoryMember() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -688,7 +716,7 @@ func (r *restoreHandler) dmzCategoryMember() (err error) {
|
||||||
INSERT INTO dmz_category_member
|
INSERT INTO dmz_category_member
|
||||||
(c_refid, c_orgid, c_categoryid, c_spaceid, c_docid, c_created, c_revised)
|
(c_refid, c_orgid, c_categoryid, c_spaceid, c_docid, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?)`),
|
||||||
cm[i].RefID, cm[i].OrgID, cm[i].CategoryID, cm[i].SpaceID, cm[i].DocumentID, cm[i].Created, cm[i].Revised)
|
cm[i].RefID, r.remapOrg(cm[i].OrgID), cm[i].CategoryID, cm[i].SpaceID, cm[i].DocumentID, cm[i].Created, cm[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -736,7 +764,7 @@ func (r *restoreHandler) dmzGroup() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -745,7 +773,7 @@ func (r *restoreHandler) dmzGroup() (err error) {
|
||||||
INSERT INTO dmz_group
|
INSERT INTO dmz_group
|
||||||
(c_refid, c_orgid, c_name, c_desc, c_created, c_revised)
|
(c_refid, c_orgid, c_name, c_desc, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?)`),
|
||||||
gr[i].RefID, gr[i].OrgID, gr[i].Name, gr[i].Purpose, gr[i].Created, gr[i].Revised)
|
gr[i].RefID, r.remapOrg(gr[i].OrgID), gr[i].Name, gr[i].Purpose, gr[i].Created, gr[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -793,7 +821,7 @@ func (r *restoreHandler) dmzGroupMember() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -802,7 +830,7 @@ func (r *restoreHandler) dmzGroupMember() (err error) {
|
||||||
INSERT INTO dmz_group_member
|
INSERT INTO dmz_group_member
|
||||||
(c_orgid, c_groupid, c_userid)
|
(c_orgid, c_groupid, c_userid)
|
||||||
VALUES (?, ?, ?)`),
|
VALUES (?, ?, ?)`),
|
||||||
gm[i].OrgID, gm[i].GroupID, gm[i].UserID)
|
r.remapOrg(gm[i].OrgID), gm[i].GroupID, r.remapUser(gm[i].UserID))
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -850,7 +878,7 @@ func (r *restoreHandler) dmzPermission() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -859,7 +887,9 @@ func (r *restoreHandler) dmzPermission() (err error) {
|
||||||
INSERT INTO dmz_permission
|
INSERT INTO dmz_permission
|
||||||
(c_orgid, c_who, c_whoid, c_action, c_scope, c_location, c_refid, c_created)
|
(c_orgid, c_who, c_whoid, c_action, c_scope, c_location, c_refid, c_created)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
pm[i].OrgID, string(pm[i].Who), pm[i].WhoID, string(pm[i].Action), string(pm[i].Scope), string(pm[i].Location), pm[i].RefID, pm[i].Created)
|
r.remapOrg(pm[i].OrgID), string(pm[i].Who), r.remapUser(pm[i].WhoID),
|
||||||
|
string(pm[i].Action), string(pm[i].Scope),
|
||||||
|
string(pm[i].Location), pm[i].RefID, pm[i].Created)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -907,7 +937,7 @@ func (r *restoreHandler) dmzPin() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -916,7 +946,8 @@ func (r *restoreHandler) dmzPin() (err error) {
|
||||||
INSERT INTO dmz_pin
|
INSERT INTO dmz_pin
|
||||||
(c_refid, c_orgid, c_userid, c_spaceid, c_docid, c_name, c_sequence, c_created, c_revised)
|
(c_refid, c_orgid, c_userid, c_spaceid, c_docid, c_name, c_sequence, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
pin[i].RefID, pin[i].OrgID, pin[i].UserID, pin[i].SpaceID, pin[i].DocumentID, pin[i].Name, pin[i].Sequence, pin[i].Created, pin[i].Revised)
|
pin[i].RefID, r.remapOrg(pin[i].OrgID), r.remapUser(pin[i].UserID), pin[i].SpaceID,
|
||||||
|
pin[i].DocumentID, pin[i].Name, pin[i].Sequence, pin[i].Created, pin[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -964,7 +995,7 @@ func (r *restoreHandler) dmzSection() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -974,7 +1005,7 @@ func (r *restoreHandler) dmzSection() (err error) {
|
||||||
(c_refid, c_orgid, c_docid, c_userid, c_contenttype, c_type, c_level, c_name, c_body,
|
(c_refid, c_orgid, c_docid, c_userid, c_contenttype, c_type, c_level, c_name, c_body,
|
||||||
c_revisions, c_sequence, c_templateid, c_status, c_relativeid, c_created, c_revised)
|
c_revisions, c_sequence, c_templateid, c_status, c_relativeid, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
sc[i].RefID, sc[i].OrgID, sc[i].DocumentID, sc[i].UserID,
|
sc[i].RefID, r.remapOrg(sc[i].OrgID), sc[i].DocumentID, r.remapUser(sc[i].UserID),
|
||||||
sc[i].ContentType, sc[i].Type, sc[i].Level, sc[i].Name,
|
sc[i].ContentType, sc[i].Type, sc[i].Level, sc[i].Name,
|
||||||
sc[i].Body, sc[i].Revisions, sc[i].Sequence, sc[i].TemplateID,
|
sc[i].Body, sc[i].Revisions, sc[i].Sequence, sc[i].TemplateID,
|
||||||
sc[i].Status, sc[i].RelativeID, sc[i].Created, sc[i].Revised)
|
sc[i].Status, sc[i].RelativeID, sc[i].Created, sc[i].Revised)
|
||||||
|
@ -1026,7 +1057,7 @@ func (r *restoreHandler) dmzSectionMeta() (err error) {
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1036,7 +1067,7 @@ func (r *restoreHandler) dmzSectionMeta() (err error) {
|
||||||
(c_sectionid, c_orgid, c_userid, c_docid, c_rawbody,
|
(c_sectionid, c_orgid, c_userid, c_docid, c_rawbody,
|
||||||
c_config, c_external, c_created, c_revised)
|
c_config, c_external, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
sm[i].SectionID, sm[i].OrgID, sm[i].UserID, sm[i].DocumentID,
|
sm[i].SectionID, r.remapOrg(sm[i].OrgID), r.remapUser(sm[i].UserID), sm[i].DocumentID,
|
||||||
sm[i].RawBody, sm[i].Config, sm[i].ExternalSource,
|
sm[i].RawBody, sm[i].Config, sm[i].ExternalSource,
|
||||||
sm[i].Created, sm[i].Revised)
|
sm[i].Created, sm[i].Revised)
|
||||||
|
|
||||||
|
@ -1086,7 +1117,7 @@ func (r *restoreHandler) dmzSectionRevision() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1096,8 +1127,8 @@ func (r *restoreHandler) dmzSectionRevision() (err error) {
|
||||||
(c_refid, c_orgid, c_docid, c_ownerid, c_sectionid, c_userid, c_contenttype,
|
(c_refid, c_orgid, c_docid, c_ownerid, c_sectionid, c_userid, c_contenttype,
|
||||||
c_type, c_name, c_body, c_rawbody, c_config, c_created, c_revised)
|
c_type, c_name, c_body, c_rawbody, c_config, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
sr[i].RefID, sr[i].OrgID, sr[i].DocumentID, sr[i].OwnerID,
|
sr[i].RefID, r.remapOrg(sr[i].OrgID), sr[i].DocumentID, sr[i].OwnerID,
|
||||||
sr[i].SectionID, sr[i].UserID, sr[i].ContentType, sr[i].Type, sr[i].Name,
|
sr[i].SectionID, r.remapUser(sr[i].UserID), sr[i].ContentType, sr[i].Type, sr[i].Name,
|
||||||
sr[i].Body, sr[i].RawBody, sr[i].Config, sr[i].Created, sr[i].Revised)
|
sr[i].Body, sr[i].RawBody, sr[i].Config, sr[i].Created, sr[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1146,7 +1177,7 @@ func (r *restoreHandler) dmzSectionTemplate() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1157,7 +1188,8 @@ func (r *restoreHandler) dmzSectionTemplate() (err error) {
|
||||||
c_type, c_name, c_body, c_desc, c_rawbody, c_used,
|
c_type, c_name, c_body, c_desc, c_rawbody, c_used,
|
||||||
c_config, c_external, c_created, c_revised)
|
c_config, c_external, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
st[i].RefID, st[i].OrgID, st[i].SpaceID, st[i].UserID, st[i].ContentType, st[i].Type,
|
st[i].RefID, r.remapOrg(st[i].OrgID), st[i].SpaceID, r.remapUser(st[i].UserID),
|
||||||
|
st[i].ContentType, st[i].Type,
|
||||||
st[i].Name, st[i].Body, st[i].Excerpt, st[i].RawBody, st[i].Used,
|
st[i].Name, st[i].Body, st[i].Excerpt, st[i].RawBody, st[i].Used,
|
||||||
st[i].Config, st[i].ExternalSource, st[i].Created, st[i].Revised)
|
st[i].Config, st[i].ExternalSource, st[i].Created, st[i].Revised)
|
||||||
|
|
||||||
|
@ -1207,7 +1239,7 @@ func (r *restoreHandler) dmzDoc() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1218,7 +1250,7 @@ func (r *restoreHandler) dmzDoc() (err error) {
|
||||||
c_name, c_desc, c_slug, c_tags, c_template, c_protection, c_approval,
|
c_name, c_desc, c_slug, c_tags, c_template, c_protection, c_approval,
|
||||||
c_lifecycle, c_versioned, c_versionid, c_versionorder, c_groupid, c_created, c_revised)
|
c_lifecycle, c_versioned, c_versionid, c_versionorder, c_groupid, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
doc[i].RefID, doc[i].OrgID, doc[i].SpaceID, doc[i].UserID, doc[i].Job,
|
doc[i].RefID, r.remapOrg(doc[i].OrgID), doc[i].SpaceID, r.remapUser(doc[i].UserID), doc[i].Job,
|
||||||
doc[i].Location, doc[i].Name, doc[i].Excerpt, doc[i].Slug, doc[i].Tags,
|
doc[i].Location, doc[i].Name, doc[i].Excerpt, doc[i].Slug, doc[i].Tags,
|
||||||
doc[i].Template, doc[i].Protection, doc[i].Approval, doc[i].Lifecycle,
|
doc[i].Template, doc[i].Protection, doc[i].Approval, doc[i].Lifecycle,
|
||||||
doc[i].Versioned, doc[i].VersionID, doc[i].VersionOrder, doc[i].GroupID,
|
doc[i].Versioned, doc[i].VersionID, doc[i].VersionOrder, doc[i].GroupID,
|
||||||
|
@ -1279,7 +1311,7 @@ func (r *restoreHandler) dmzDocVote() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1287,7 +1319,7 @@ func (r *restoreHandler) dmzDocVote() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
||||||
INSERT INTO dmz_doc_vote (c_refid, c_orgid, c_docid, c_voter, c_vote, c_created, c_revised)
|
INSERT INTO dmz_doc_vote (c_refid, c_orgid, c_docid, c_voter, c_vote, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?)`),
|
||||||
v[i].RefID, v[i].OrgID, v[i].DocumentID, v[i].VoterID, v[i].Vote, v[i].Created, v[i].Revised)
|
v[i].RefID, r.remapOrg(v[i].OrgID), v[i].DocumentID, v[i].VoterID, v[i].Vote, v[i].Created, v[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
@ -1335,7 +1367,7 @@ func (r *restoreHandler) dmzDocLink() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1345,7 +1377,8 @@ func (r *restoreHandler) dmzDocLink() (err error) {
|
||||||
(c_refid, c_orgid, c_spaceid, c_userid, c_sourcedocid, c_sourcesectionid,
|
(c_refid, c_orgid, c_spaceid, c_userid, c_sourcedocid, c_sourcesectionid,
|
||||||
c_targetdocid, c_targetid, c_externalid, c_type, c_orphan, c_created, c_revised)
|
c_targetdocid, c_targetid, c_externalid, c_type, c_orphan, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
lk[i].RefID, lk[i].OrgID, lk[i].SpaceID, lk[i].UserID, lk[i].SourceDocumentID, lk[i].SourceSectionID,
|
lk[i].RefID, r.remapOrg(lk[i].OrgID), lk[i].SpaceID, r.remapUser(lk[i].UserID),
|
||||||
|
lk[i].SourceDocumentID, lk[i].SourceSectionID,
|
||||||
lk[i].TargetDocumentID, lk[i].TargetID, lk[i].ExternalID, lk[i].LinkType, lk[i].Orphan,
|
lk[i].TargetDocumentID, lk[i].TargetID, lk[i].ExternalID, lk[i].LinkType, lk[i].Orphan,
|
||||||
lk[i].Created, lk[i].Revised)
|
lk[i].Created, lk[i].Revised)
|
||||||
|
|
||||||
|
@ -1395,7 +1428,7 @@ func (r *restoreHandler) dmzDocAttachment() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1405,7 +1438,8 @@ func (r *restoreHandler) dmzDocAttachment() (err error) {
|
||||||
(c_refid, c_orgid, c_docid, c_job, c_fileid,
|
(c_refid, c_orgid, c_docid, c_job, c_fileid,
|
||||||
c_filename, c_data, c_extension, c_created, c_revised)
|
c_filename, c_data, c_extension, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
at[i].RefID, at[i].OrgID, at[i].DocumentID, at[i].Job, at[i].FileID, at[i].Filename,
|
at[i].RefID, r.remapOrg(at[i].OrgID), at[i].DocumentID, at[i].Job,
|
||||||
|
at[i].FileID, at[i].Filename,
|
||||||
at[i].Data, at[i].Extension, at[i].Created, at[i].Revised)
|
at[i].Data, at[i].Extension, at[i].Created, at[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1440,7 +1474,6 @@ func (r *restoreHandler) dmzDocComment() (err error) {
|
||||||
Feedback string `json:"feedback"`
|
Feedback string `json:"feedback"`
|
||||||
Created string `json:"created"`
|
Created string `json:"created"`
|
||||||
}
|
}
|
||||||
|
|
||||||
cm := []comment{}
|
cm := []comment{}
|
||||||
err = r.fileJSON(filename, &cm)
|
err = r.fileJSON(filename, &cm)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1464,7 +1497,7 @@ func (r *restoreHandler) dmzDocComment() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1473,7 +1506,7 @@ func (r *restoreHandler) dmzDocComment() (err error) {
|
||||||
INSERT INTO dmz_doc_comment
|
INSERT INTO dmz_doc_comment
|
||||||
(c_refid, c_orgid, c_userid, c_docid, c_email, c_feedback, c_created)
|
(c_refid, c_orgid, c_userid, c_docid, c_email, c_feedback, c_created)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?)`),
|
||||||
cm[i].RefID, cm[i].OrgID, cm[i].UserID, cm[i].DocumentID,
|
cm[i].RefID, r.remapOrg(cm[i].OrgID), r.remapUser(cm[i].UserID), cm[i].DocumentID,
|
||||||
cm[i].Email, cm[i].Feedback, cm[i].Created)
|
cm[i].Email, cm[i].Feedback, cm[i].Created)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1512,7 +1545,6 @@ func (r *restoreHandler) dmzDocShare() (err error) {
|
||||||
Active bool `json:"active"`
|
Active bool `json:"active"`
|
||||||
Created time.Time `json:"created"`
|
Created time.Time `json:"created"`
|
||||||
}
|
}
|
||||||
|
|
||||||
sh := []share{}
|
sh := []share{}
|
||||||
err = r.fileJSON(filename, &sh)
|
err = r.fileJSON(filename, &sh)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1536,7 +1568,7 @@ func (r *restoreHandler) dmzDocShare() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1546,7 +1578,7 @@ func (r *restoreHandler) dmzDocShare() (err error) {
|
||||||
(c_orgid, c_userid, c_docid, c_email, c_message,
|
(c_orgid, c_userid, c_docid, c_email, c_message,
|
||||||
c_secret, c_expires, c_active, c_created)
|
c_secret, c_expires, c_active, c_created)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
sh[i].OrgID, sh[i].UserID, sh[i].DocumentID, sh[i].Email, sh[i].Message,
|
r.remapOrg(sh[i].OrgID), r.remapUser(sh[i].UserID), sh[i].DocumentID, sh[i].Email, sh[i].Message,
|
||||||
sh[i].Secret, sh[i].Expires, sh[i].Active, sh[i].Created)
|
sh[i].Secret, sh[i].Expires, sh[i].Active, sh[i].Created)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1592,18 +1624,41 @@ func (r *restoreHandler) dmzUser() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec("TRUNCATE TABLE dmz_user")
|
_, err = r.Context.Transaction.Exec("TRUNCATE TABLE dmz_user")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for i := range u {
|
for i := range u {
|
||||||
|
// For tenant backups we first check to see if user exists.
|
||||||
|
insert := true
|
||||||
|
if !r.Spec.GlobalBackup {
|
||||||
|
row := r.Runtime.Db.QueryRow(r.Runtime.Db.Rebind("SELECT COALESCE(c_refid, '') AS userid FROM dmz_user WHERE c_email=?"), u[i].Email)
|
||||||
|
userID := ""
|
||||||
|
err = row.Scan(&userID)
|
||||||
|
if err == sql.ErrNoRows {
|
||||||
|
err = nil
|
||||||
|
insert = true
|
||||||
|
}
|
||||||
|
if err != nil {
|
||||||
|
err = errors.Wrap(err, fmt.Sprintf("unable to check email %s", u[i].Email))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
// Existing userID from database overrides all incoming userID values
|
||||||
|
// by using remapUser().
|
||||||
|
if len(userID) > 0 {
|
||||||
|
r.MapUserID[u[i].RefID] = userID
|
||||||
|
insert = false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if insert {
|
||||||
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
_, err = r.Context.Transaction.Exec(r.Runtime.Db.Rebind(`
|
||||||
INSERT INTO dmz_user
|
INSERT INTO dmz_user
|
||||||
(c_refid, c_firstname, c_lastname, c_email, c_initials, c_globaladmin,
|
(c_refid, c_firstname, c_lastname, c_email, c_initials, c_globaladmin,
|
||||||
c_password, c_salt, c_reset, c_active, c_lastversion, c_created, c_revised)
|
c_password, c_salt, c_reset, c_active, c_lastversion, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
u[i].RefID, u[i].Firstname, u[i].Lastname, strings.ToLower(u[i].Email), u[i].Initials,
|
r.remapUser(u[i].RefID), u[i].Firstname, u[i].Lastname, strings.ToLower(u[i].Email), u[i].Initials,
|
||||||
u[i].GlobalAdmin, u[i].Password, u[i].Salt, u[i].Reset, u[i].Active,
|
u[i].GlobalAdmin, u[i].Password, u[i].Salt, u[i].Reset, u[i].Active,
|
||||||
u[i].LastVersion, u[i].Created, u[i].Revised)
|
u[i].LastVersion, u[i].Created, u[i].Revised)
|
||||||
|
|
||||||
|
@ -1613,6 +1668,7 @@ func (r *restoreHandler) dmzUser() (err error) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
err = r.Context.Transaction.Commit()
|
err = r.Context.Transaction.Commit()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1653,7 +1709,7 @@ func (r *restoreHandler) dmzUserAccount() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1663,7 +1719,7 @@ func (r *restoreHandler) dmzUserAccount() (err error) {
|
||||||
(c_refid, c_orgid, c_userid, c_admin, c_editor, c_users,
|
(c_refid, c_orgid, c_userid, c_admin, c_editor, c_users,
|
||||||
c_analytics, c_active, c_created, c_revised)
|
c_analytics, c_active, c_created, c_revised)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
ac[i].RefID, ac[i].OrgID, ac[i].UserID, ac[i].Admin, ac[i].Editor,
|
ac[i].RefID, r.remapOrg(ac[i].OrgID), r.remapUser(ac[i].UserID), ac[i].Admin, ac[i].Editor,
|
||||||
ac[i].Users, ac[i].Analytics, ac[i].Active, ac[i].Created, ac[i].Revised)
|
ac[i].Users, ac[i].Analytics, ac[i].Active, ac[i].Created, ac[i].Revised)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -1712,7 +1768,7 @@ func (r *restoreHandler) dmzUserActivity() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1722,7 +1778,7 @@ func (r *restoreHandler) dmzUserActivity() (err error) {
|
||||||
(c_orgid, c_userid, c_spaceid, c_docid, c_sectionid, c_sourcetype,
|
(c_orgid, c_userid, c_spaceid, c_docid, c_sectionid, c_sourcetype,
|
||||||
c_activitytype, c_metadata, c_created)
|
c_activitytype, c_metadata, c_created)
|
||||||
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`),
|
||||||
ac[i].OrgID, ac[i].UserID, ac[i].SpaceID, ac[i].DocumentID,
|
r.remapOrg(ac[i].OrgID), r.remapUser(ac[i].UserID), ac[i].SpaceID, ac[i].DocumentID,
|
||||||
ac[i].SectionID, ac[i].SourceType, ac[i].ActivityType,
|
ac[i].SectionID, ac[i].SourceType, ac[i].ActivityType,
|
||||||
ac[i].Metadata, ac[i].Created)
|
ac[i].Metadata, ac[i].Created)
|
||||||
|
|
||||||
|
@ -1778,7 +1834,7 @@ func (r *restoreHandler) dmzUserConfig() (err error) {
|
||||||
_, err = r.Context.Transaction.Exec(nuke)
|
_, err = r.Context.Transaction.Exec(nuke)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table", filename))
|
err = errors.Wrap(err, fmt.Sprintf("unable to truncate table %s", filename))
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1787,7 +1843,7 @@ func (r *restoreHandler) dmzUserConfig() (err error) {
|
||||||
INSERT INTO dmz_user_config
|
INSERT INTO dmz_user_config
|
||||||
(c_orgid, c_userid, c_key, c_config)
|
(c_orgid, c_userid, c_key, c_config)
|
||||||
VALUES (?, ?, ?, ?)`),
|
VALUES (?, ?, ?, ?)`),
|
||||||
uc[i].OrgID, uc[i].UserID, uc[i].ConfigKey, uc[i].ConfigValue)
|
r.remapOrg(uc[i].OrgID), r.remapUser(uc[i].UserID), uc[i].ConfigKey, uc[i].ConfigValue)
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
r.Context.Transaction.Rollback()
|
r.Context.Transaction.Rollback()
|
||||||
|
|
59
domain/backup/restore_test.go
Normal file
59
domain/backup/restore_test.go
Normal file
|
@ -0,0 +1,59 @@
|
||||||
|
// Copyright 2016 Documize Inc. <legal@documize.com>. All rights reserved.
|
||||||
|
//
|
||||||
|
// This software (Documize Community Edition) is licensed under
|
||||||
|
// GNU AGPL v3 http://www.gnu.org/licenses/agpl-3.0.en.html
|
||||||
|
//
|
||||||
|
// You can operate outside the AGPL restrictions by purchasing
|
||||||
|
// Documize Enterprise Edition and obtaining a commercial license
|
||||||
|
// by contacting <sales@documize.com>.
|
||||||
|
//
|
||||||
|
// https://documize.com
|
||||||
|
|
||||||
|
package backup
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
// go test github.com/documize/community/domain/backup -run TestRemapORg
|
||||||
|
func TestRemapOrg(t *testing.T) {
|
||||||
|
r := restoreHandler{MapOrgID: make(map[string]string)}
|
||||||
|
r.MapOrgID["abc"] = "def"
|
||||||
|
r.MapOrgID["xyz"] = "123"
|
||||||
|
|
||||||
|
n := r.remapOrg("abc")
|
||||||
|
if n != "def" {
|
||||||
|
t.Errorf("expected def got %s", n)
|
||||||
|
}
|
||||||
|
|
||||||
|
n = r.remapOrg("xyz")
|
||||||
|
if n != "123" {
|
||||||
|
t.Errorf("expected 123 got %s", n)
|
||||||
|
}
|
||||||
|
|
||||||
|
n = r.remapOrg("jkl")
|
||||||
|
if n != "jkl" {
|
||||||
|
t.Errorf("expected jkl got %s", n)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestRemapUser(t *testing.T) {
|
||||||
|
r := restoreHandler{MapUserID: make(map[string]string)}
|
||||||
|
r.MapUserID["abc"] = "def"
|
||||||
|
r.MapUserID["xyz"] = "123"
|
||||||
|
|
||||||
|
n := r.remapUser("abc")
|
||||||
|
if n != "def" {
|
||||||
|
t.Errorf("expected def got %s", n)
|
||||||
|
}
|
||||||
|
|
||||||
|
n = r.remapUser("xyz")
|
||||||
|
if n != "123" {
|
||||||
|
t.Errorf("expected 123 got %s", n)
|
||||||
|
}
|
||||||
|
|
||||||
|
n = r.remapUser("jkl")
|
||||||
|
if n != "jkl" {
|
||||||
|
t.Errorf("expected jkl got %s", n)
|
||||||
|
}
|
||||||
|
}
|
|
@ -38,7 +38,7 @@ func main() {
|
||||||
// product details
|
// product details
|
||||||
rt.Product = env.ProdInfo{}
|
rt.Product = env.ProdInfo{}
|
||||||
rt.Product.Major = "1"
|
rt.Product.Major = "1"
|
||||||
rt.Product.Minor = "71"
|
rt.Product.Minor = "72"
|
||||||
rt.Product.Patch = "0"
|
rt.Product.Patch = "0"
|
||||||
rt.Product.Revision = 181007125514
|
rt.Product.Revision = 181007125514
|
||||||
rt.Product.Version = fmt.Sprintf("%s.%s.%s", rt.Product.Major, rt.Product.Minor, rt.Product.Patch)
|
rt.Product.Version = fmt.Sprintf("%s.%s.%s", rt.Product.Major, rt.Product.Minor, rt.Product.Patch)
|
||||||
|
|
|
@ -35,6 +35,11 @@ func (l Logger) Info(message string) {
|
||||||
l.log.Println(message)
|
l.log.Println(message)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Infof logs message via Sprintf.
|
||||||
|
func (l Logger) Infof(message string, a ...interface{}) {
|
||||||
|
l.log.Println(fmt.Sprintf(message, a))
|
||||||
|
}
|
||||||
|
|
||||||
// Trace logs message if tracing enabled.
|
// Trace logs message if tracing enabled.
|
||||||
func (l Logger) Trace(message string) {
|
func (l Logger) Trace(message string) {
|
||||||
if l.trace {
|
if l.trace {
|
||||||
|
|
1346
embed/bindata.go
1346
embed/bindata.go
File diff suppressed because one or more lines are too long
|
@ -24,6 +24,7 @@
|
||||||
As a Documize <b>Tenant Administrator</b> you can perform a tenant-level backup (e.g. marketing.mycompany.com).
|
As a Documize <b>Tenant Administrator</b> you can perform a tenant-level backup (e.g. marketing.mycompany.com).
|
||||||
</p>
|
</p>
|
||||||
{{/if}}
|
{{/if}}
|
||||||
|
<p>Please use a Tenant Backup when migrating between self-host and Documize Cloud hosting.</p>
|
||||||
<p>It can take <b>several minutes</b> to complete the backup process — please be patient while the backup operation is in progress.</p>
|
<p>It can take <b>several minutes</b> to complete the backup process — please be patient while the backup operation is in progress.</p>
|
||||||
|
|
||||||
<div class="margin-top-30 margin-bottom-20">
|
<div class="margin-top-30 margin-bottom-20">
|
||||||
|
@ -35,10 +36,10 @@
|
||||||
{{#if backupRunning}}
|
{{#if backupRunning}}
|
||||||
<h3 class="text-success">Backup running, please wait...</h3>
|
<h3 class="text-success">Backup running, please wait...</h3>
|
||||||
{{else}}
|
{{else}}
|
||||||
<button class="btn btn-success mb-3" {{action 'onBackup'}}>BACKUP TENANT</button>
|
<button class="btn btn-success mb-3" {{action 'onBackup'}}>TENANT BACKUP ({{appMeta.appHost}})</button>
|
||||||
{{#if session.isGlobalAdmin}}
|
{{#if session.isGlobalAdmin}}
|
||||||
<div class="button-gap" />
|
<div class="button-gap" />
|
||||||
<button class="btn btn-success mb-3" {{action 'onSystemBackup'}}>BACKUP SYSTEM</button>
|
<button class="btn btn-success mb-3" {{action 'onSystemBackup'}}>SYSTEM BACKUP</button>
|
||||||
{{/if}}
|
{{/if}}
|
||||||
{{/if}}
|
{{/if}}
|
||||||
{{#if backupFailed}}
|
{{#if backupFailed}}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
{
|
{
|
||||||
"name": "documize",
|
"name": "documize",
|
||||||
"version": "1.71.0",
|
"version": "1.72.0",
|
||||||
"description": "The Document IDE",
|
"description": "The Document IDE",
|
||||||
"private": true,
|
"private": true,
|
||||||
"repository": "",
|
"repository": "",
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue