1
0
Fork 0
mirror of https://github.com/documize/community.git synced 2025-08-04 21:15:24 +02:00

PostgreSQL prep

Update of vendored SQL libs and refactoring of store provider layer.
This commit is contained in:
HarveyKandola 2018-09-26 17:59:56 +01:00
parent d0e005f638
commit b455e5eaf5
105 changed files with 10949 additions and 2376 deletions

View file

@ -9,31 +9,31 @@
//
// https://documize.com
package mysql
package account
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/account"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to account information.
type Store struct {
store.Context
domain.AccountStorer
}
// Add inserts the given record into the datbase account table.
func (s Scope) Add(ctx domain.RequestContext, account account.Account) (err error) {
func (s Store) Add(ctx domain.RequestContext, account account.Account) (err error) {
account.Created = time.Now().UTC()
account.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_user_account (c_refid, c_orgid, c_userid, c_admin, c_editor, c_users, c_analytics, c_active, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_user_account (c_refid, c_orgid, c_userid, c_admin, c_editor, c_users, c_analytics, c_active, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
account.RefID, account.OrgID, account.UserID, account.Admin, account.Editor, account.Users, account.Analytics, account.Active, account.Created, account.Revised)
if err != nil {
@ -44,14 +44,14 @@ func (s Scope) Add(ctx domain.RequestContext, account account.Account) (err erro
}
// GetUserAccount returns the database account record corresponding to the given userID, using the client's current organizaion.
func (s Scope) GetUserAccount(ctx domain.RequestContext, userID string) (account account.Account, err error) {
err = s.Runtime.Db.Get(&account, `
func (s Store) GetUserAccount(ctx domain.RequestContext, userID string) (account account.Account, err error) {
err = s.Runtime.Db.Get(&account, s.Bind(`
SELECT a.id, a.c_refid AS refid, a.c_orgid AS orgid, a.c_userid AS userid,
a.c_editor AS editor, a.c_admin AS admin, a.c_users AS users, a.c_analytics AS analytics,
a.c_active AS active, a.c_created AS created, a.c_revised AS revised,
b.c_company AS company, b.c_title AS title, b.c_message AS message, b.c_domain as domain
FROM dmz_user_account a, dmz_org b
WHERE b.c_refid=a.c_orgid AND a.c_orgid=? AND a.c_userid=?`,
WHERE b.c_refid=a.c_orgid AND a.c_orgid=? AND a.c_userid=?`),
ctx.OrgID, userID)
if err != sql.ErrNoRows && err != nil {
@ -62,15 +62,15 @@ func (s Scope) GetUserAccount(ctx domain.RequestContext, userID string) (account
}
// GetUserAccounts returns a slice of database account records, for all organizations that the userID is a member of, in organization title order.
func (s Scope) GetUserAccounts(ctx domain.RequestContext, userID string) (t []account.Account, err error) {
err = s.Runtime.Db.Select(&t, `
func (s Store) GetUserAccounts(ctx domain.RequestContext, userID string) (t []account.Account, err error) {
err = s.Runtime.Db.Select(&t, s.Bind(`
SELECT a.id, a.c_refid AS refid, a.c_orgid AS orgid, a.c_userid AS userid,
a.c_editor AS editor, a.c_admin AS admin, a.c_users AS users, a.c_analytics AS analytics,
a.c_active AS active, a.c_created AS created, a.c_revised AS revised,
b.c_company AS company, b.c_title AS title, b.c_message AS message, b.c_domain as domain
FROM dmz_user_account a, dmz_org b
WHERE a.c_userid=? AND a.c_orgid=b.c_refid AND a.c_active=1
ORDER BY b.c_title`,
ORDER BY b.c_title`),
userID)
if err != sql.ErrNoRows && err != nil {
@ -81,14 +81,14 @@ func (s Scope) GetUserAccounts(ctx domain.RequestContext, userID string) (t []ac
}
// GetAccountsByOrg returns a slice of database account records, for all users in the client's organization.
func (s Scope) GetAccountsByOrg(ctx domain.RequestContext) (t []account.Account, err error) {
err = s.Runtime.Db.Select(&t, `
func (s Store) GetAccountsByOrg(ctx domain.RequestContext) (t []account.Account, err error) {
err = s.Runtime.Db.Select(&t, s.Bind(`
SELECT a.id, a.c_refid AS refid, a.c_orgid AS orgid, a.c_userid AS userid,
a.c_editor AS editor, a.c_admin AS admin, a.c_users AS users, a.c_analytics AS analytics,
a.c_active AS active, a.c_created AS created, a.c_revised AS revised,
b.c_company AS company, b.c_title AS title, b.c_message AS message, b.c_domain as domain
FROM dmz_user_account a, dmz_org b
WHERE a.c_orgid=b.c_refid AND a.c_orgid=? AND a.c_active=1`,
WHERE a.c_orgid=b.c_refid AND a.c_orgid=? AND a.c_active=1`),
ctx.OrgID)
if err != sql.ErrNoRows && err != nil {
@ -99,8 +99,8 @@ func (s Scope) GetAccountsByOrg(ctx domain.RequestContext) (t []account.Account,
}
// CountOrgAccounts returns the numnber of active user accounts for specified organization.
func (s Scope) CountOrgAccounts(ctx domain.RequestContext) (c int) {
row := s.Runtime.Db.QueryRow("SELECT count(*) FROM dmz_user_account WHERE c_orgid=? AND c_active=1", ctx.OrgID)
func (s Store) CountOrgAccounts(ctx domain.RequestContext) (c int) {
row := s.Runtime.Db.QueryRow(s.Bind("SELECT count(*) FROM dmz_user_account WHERE c_orgid=? AND c_active=1"), ctx.OrgID)
err := row.Scan(&c)
if err == sql.ErrNoRows {
return 0
@ -114,13 +114,13 @@ func (s Scope) CountOrgAccounts(ctx domain.RequestContext) (c int) {
}
// UpdateAccount updates the database record for the given account to the given values.
func (s Scope) UpdateAccount(ctx domain.RequestContext, account account.Account) (err error) {
func (s Store) UpdateAccount(ctx domain.RequestContext, account account.Account) (err error) {
account.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec(`
_, err = ctx.Transaction.NamedExec(s.Bind(`
UPDATE dmz_user_account SET
c_userid=:userid, c_admin=:admin, c_editor=:editor, c_users=:users, c_analytics=:analytics,
c_active=:active, c_revised=:revised WHERE c_orgid=:orgid AND c_refid=:refid`, &account)
c_active=:active, c_revised=:revised WHERE c_orgid=:orgid AND c_refid=:refid`), &account)
if err != sql.ErrNoRows && err != nil {
err = errors.Wrap(err, fmt.Sprintf("execute update for account %s", account.RefID))
@ -130,8 +130,8 @@ func (s Scope) UpdateAccount(ctx domain.RequestContext, account account.Account)
}
// HasOrgAccount returns if the given orgID has valid userID.
func (s Scope) HasOrgAccount(ctx domain.RequestContext, orgID, userID string) bool {
row := s.Runtime.Db.QueryRow("SELECT count(*) FROM dmz_user_account WHERE c_orgid=? and c_userid=?", orgID, userID)
func (s Store) HasOrgAccount(ctx domain.RequestContext, orgID, userID string) bool {
row := s.Runtime.Db.QueryRow(s.Bind("SELECT count(*) FROM dmz_user_account WHERE c_orgid=? and c_userid=?"), orgID, userID)
var count int
err := row.Scan(&count)
@ -152,7 +152,6 @@ func (s Scope) HasOrgAccount(ctx domain.RequestContext, orgID, userID string) bo
}
// DeleteAccount deletes the database record in the account table for user ID.
func (s Scope) DeleteAccount(ctx domain.RequestContext, ID string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteConstrained(ctx.Transaction, "dmz_user_account", ctx.OrgID, ID)
func (s Store) DeleteAccount(ctx domain.RequestContext, ID string) (rows int64, err error) {
return s.DeleteConstrained(ctx.Transaction, "dmz_user_account", ctx.OrgID, ID)
}

View file

@ -9,32 +9,32 @@
//
// https://documize.com
package mysql
package activity
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/activity"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to user activity information.
type Store struct {
store.Context
domain.ActivityStorer
}
// RecordUserActivity logs user initiated data changes.
func (s Scope) RecordUserActivity(ctx domain.RequestContext, activity activity.UserActivity) (err error) {
func (s Store) RecordUserActivity(ctx domain.RequestContext, activity activity.UserActivity) (err error) {
activity.OrgID = ctx.OrgID
activity.UserID = ctx.UserID
activity.Created = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_user_activity (c_orgid, c_userid, c_spaceid, c_docid, c_sectionid, c_sourcetype, c_activitytype, c_metadata, c_created) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_user_activity (c_orgid, c_userid, c_spaceid, c_docid, c_sectionid, c_sourcetype, c_activitytype, c_metadata, c_created) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)"),
activity.OrgID, activity.UserID, activity.SpaceID, activity.DocumentID, activity.SectionID, activity.SourceType, activity.ActivityType, activity.Metadata, activity.Created)
if err != nil {
@ -45,19 +45,19 @@ func (s Scope) RecordUserActivity(ctx domain.RequestContext, activity activity.U
}
// GetDocumentActivity returns the metadata for a specified document.
func (s Scope) GetDocumentActivity(ctx domain.RequestContext, id string) (a []activity.DocumentActivity, err error) {
qry := `SELECT a.id, DATE(a.c_created) AS created, a.c_orgid AS orgid,
IFNULL(a.c_userid, '') AS userid, a.c_spaceid AS spaceid,
func (s Store) GetDocumentActivity(ctx domain.RequestContext, id string) (a []activity.DocumentActivity, err error) {
qry := s.Bind(`SELECT a.id, DATE(a.c_created) AS created, a.c_orgid AS orgid,
COALESCE(a.c_userid, '') AS userid, a.c_spaceid AS spaceid,
a.c_docid AS documentid, a.c_sectionid AS sectionid, a.c_activitytype AS activitytype,
a.c_metadata AS metadata,
IFNULL(u.c_firstname, 'Anonymous') AS firstname, IFNULL(u.c_lastname, 'Viewer') AS lastname,
IFNULL(p.c_name, '') AS sectionname
COALESCE(u.c_firstname, 'Anonymous') AS firstname, COALESCE(u.c_lastname, 'Viewer') AS lastname,
COALESCE(p.c_name, '') AS sectionname
FROM dmz_user_activity a
LEFT JOIN dmz_user u ON a.c_userid=u.c_refid
LEFT JOIN dmz_section p ON a.c_sectionid=p.c_refid
WHERE a.c_orgid=? AND a.c_docid=?
AND a.c_userid != '0' AND a.c_userid != ''
ORDER BY a.c_created DESC`
ORDER BY a.c_created DESC`)
err = s.Runtime.Db.Select(&a, qry, ctx.OrgID, id)
@ -76,9 +76,8 @@ func (s Scope) GetDocumentActivity(ctx domain.RequestContext, id string) (a []ac
}
// DeleteDocumentChangeActivity removes all entries for document changes (add, remove, update).
func (s Scope) DeleteDocumentChangeActivity(ctx domain.RequestContext, documentID string) (rows int64, err error) {
b := mysql.BaseQuery{}
rows, err = b.DeleteWhere(ctx.Transaction,
func (s Store) DeleteDocumentChangeActivity(ctx domain.RequestContext, documentID string) (rows int64, err error) {
rows, err = s.DeleteWhere(ctx.Transaction,
fmt.Sprintf("DELETE FROM dmz_user_activity WHERE c_orgid='%s' AND c_docid='%s' AND (c_activitytype=1 OR c_activitytype=2 OR c_activitytype=3 OR c_activitytype=4 OR c_activitytype=7)", ctx.OrgID, documentID))
return

View file

@ -15,27 +15,27 @@ import (
"strings"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/attachment"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to document/section attachments information.
type Store struct {
store.Context
domain.AttachmentStorer
}
// Add inserts the given record into the database attachement table.
func (s Scope) Add(ctx domain.RequestContext, a attachment.Attachment) (err error) {
func (s Store) Add(ctx domain.RequestContext, a attachment.Attachment) (err error) {
a.OrgID = ctx.OrgID
a.Created = time.Now().UTC()
a.Revised = time.Now().UTC()
bits := strings.Split(a.Filename, ".")
a.Extension = bits[len(bits)-1]
_, err = ctx.Transaction.Exec("INSERT INTO dmz_doc_attachment (c_refid, c_orgid, c_docid, c_job, c_fileid, c_filename, c_data, c_extension, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_doc_attachment (c_refid, c_orgid, c_docid, c_job, c_fileid, c_filename, c_data, c_extension, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
a.RefID, a.OrgID, a.DocumentID, a.Job, a.FileID, a.Filename, a.Data, a.Extension, a.Created, a.Revised)
if err != nil {
@ -46,14 +46,14 @@ func (s Scope) Add(ctx domain.RequestContext, a attachment.Attachment) (err erro
}
// GetAttachment returns the database attachment record specified by the parameters.
func (s Scope) GetAttachment(ctx domain.RequestContext, orgID, attachmentID string) (a attachment.Attachment, err error) {
err = s.Runtime.Db.Get(&a, `
func (s Store) GetAttachment(ctx domain.RequestContext, orgID, attachmentID string) (a attachment.Attachment, err error) {
err = s.Runtime.Db.Get(&a, s.Bind(`
SELECT id, c_refid AS refid,
c_orgid AS orgid, c_docid AS documentid, c_job AS job, c_fileid AS fileid,
c_filename AS filename, c_data AS data, c_extension AS extension,
c_created AS created, c_revised AS revised
FROM dmz_doc_attachment
WHERE c_orgid=? and c_refid=?`,
WHERE c_orgid=? and c_refid=?`),
orgID, attachmentID)
if err != nil {
@ -64,15 +64,15 @@ func (s Scope) GetAttachment(ctx domain.RequestContext, orgID, attachmentID stri
}
// GetAttachments returns a slice containing the attachement records (excluding their data) for document docID, ordered by filename.
func (s Scope) GetAttachments(ctx domain.RequestContext, docID string) (a []attachment.Attachment, err error) {
err = s.Runtime.Db.Select(&a, `
func (s Store) GetAttachments(ctx domain.RequestContext, docID string) (a []attachment.Attachment, err error) {
err = s.Runtime.Db.Select(&a, s.Bind(`
SELECT id, c_refid AS refid,
c_orgid AS orgid, c_docid AS documentid, c_job AS job, c_fileid AS fileid,
c_filename AS filename, c_extension AS extension,
c_created AS created, c_revised AS revised
FROM dmz_doc_attachment
WHERE c_orgid=? and c_docid=?
ORDER BY c_filename`,
ORDER BY c_filename`),
ctx.OrgID, docID)
if err != nil {
@ -83,15 +83,15 @@ func (s Scope) GetAttachments(ctx domain.RequestContext, docID string) (a []atta
}
// GetAttachmentsWithData returns a slice containing the attachement records (including their data) for document docID, ordered by filename.
func (s Scope) GetAttachmentsWithData(ctx domain.RequestContext, docID string) (a []attachment.Attachment, err error) {
err = s.Runtime.Db.Select(&a, `
func (s Store) GetAttachmentsWithData(ctx domain.RequestContext, docID string) (a []attachment.Attachment, err error) {
err = s.Runtime.Db.Select(&a, s.Bind(`
SELECT id, c_refid AS refid,
c_orgid AS orgid, c_docid AS documentid, c_job AS job, c_fileid AS fileid,
c_filename AS filename, c_data AS data, c_extension AS extension,
c_created AS created, c_revised AS revised
FROM dmz_doc_attachment
WHERE c_orgid=? and c_docid=?
ORDER BY c_filename`,
ORDER BY c_filename`),
ctx.OrgID, docID)
if err != nil {
@ -102,7 +102,6 @@ func (s Scope) GetAttachmentsWithData(ctx domain.RequestContext, docID string) (
}
// Delete deletes the id record from the database attachment table.
func (s Scope) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteConstrained(ctx.Transaction, "dmz_doc_attachment", ctx.OrgID, id)
func (s Store) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
return s.DeleteConstrained(ctx.Transaction, "dmz_doc_attachment", ctx.OrgID, id)
}

View file

@ -15,18 +15,19 @@ package audit
import (
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/audit"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to audit log information.
type Store struct {
store.Context
domain.AuditStorer
}
// Record adds event entry for specified user using own DB TX.
func (s Scope) Record(ctx domain.RequestContext, t audit.EventType) {
func (s Store) Record(ctx domain.RequestContext, t audit.EventType) {
e := audit.AppEvent{}
e.OrgID = ctx.OrgID
e.UserID = ctx.UserID
@ -40,7 +41,7 @@ func (s Scope) Record(ctx domain.RequestContext, t audit.EventType) {
return
}
_, err = tx.Exec("INSERT INTO dmz_audit_log (c_orgid, c_userid, c_eventtype, c_ip, c_created) VALUES (?, ?, ?, ?, ?)",
_, err = tx.Exec(s.Bind("INSERT INTO dmz_audit_log (c_orgid, c_userid, c_eventtype, c_ip, c_created) VALUES (?, ?, ?, ?, ?)"),
e.OrgID, e.UserID, e.Type, e.IP, e.Created)
if err != nil {

View file

@ -9,32 +9,32 @@
//
// https://documize.com
package mysql
package block
import (
"database/sql"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/block"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to section template information.
type Store struct {
store.Context
domain.BlockStorer
}
// Add saves reusable content block.
func (s Scope) Add(ctx domain.RequestContext, b block.Block) (err error) {
func (s Store) Add(ctx domain.RequestContext, b block.Block) (err error) {
b.OrgID = ctx.OrgID
b.UserID = ctx.UserID
b.Created = time.Now().UTC()
b.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_section_template (c_refid, c_orgid, c_spaceid, c_userid, c_contenttype, c_type, c_name, c_body, c_desc, c_rawbody, c_config, c_external, c_used, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_section_template (c_refid, c_orgid, c_spaceid, c_userid, c_contenttype, c_type, c_name, c_body, c_desc, c_rawbody, c_config, c_external, c_used, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
b.RefID, b.OrgID, b.SpaceID, b.UserID, b.ContentType, b.Type, b.Name, b.Body, b.Excerpt, b.RawBody, b.Config, b.ExternalSource, b.Used, b.Created, b.Revised)
if err != nil {
@ -45,8 +45,8 @@ func (s Scope) Add(ctx domain.RequestContext, b block.Block) (err error) {
}
// Get returns requested reusable content block.
func (s Scope) Get(ctx domain.RequestContext, id string) (b block.Block, err error) {
err = s.Runtime.Db.Get(&b, `
func (s Store) Get(ctx domain.RequestContext, id string) (b block.Block, err error) {
err = s.Runtime.Db.Get(&b, s.Bind(`
SELECT a.id, a.c_refid as refid,
a.c_orgid as orgid,
a.c_spaceid AS spaceid, a.c_userid AS userid, a.c_contenttype AS contenttype, a.c_type AS type,
@ -55,7 +55,7 @@ func (s Scope) Get(ctx domain.RequestContext, id string) (b block.Block, err err
a.c_created AS created, a.c_revised AS revised,
b.c_firstname AS firstname, b.c_lastname AS lastname
FROM dmz_section_template a LEFT JOIN dmz_user b ON a.c_userid = b.c_refid
WHERE a.c_orgid=? AND a.c_refid=?`,
WHERE a.c_orgid=? AND a.c_refid=?`),
ctx.OrgID, id)
if err != nil {
@ -66,8 +66,8 @@ func (s Scope) Get(ctx domain.RequestContext, id string) (b block.Block, err err
}
// GetBySpace returns all reusable content scoped to given space.
func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (b []block.Block, err error) {
err = s.Runtime.Db.Select(&b, `
func (s Store) GetBySpace(ctx domain.RequestContext, spaceID string) (b []block.Block, err error) {
err = s.Runtime.Db.Select(&b, s.Bind(`
SELECT a.id, a.c_refid as refid,
a.c_orgid as orgid,
a.c_spaceid AS spaceid, a.c_userid AS userid, a.c_contenttype AS contenttype, a.c_type AS type,
@ -77,7 +77,7 @@ func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (b []block.
b.c_firstname AS firstname, b.c_lastname AS lastname
FROM dmz_section_template a LEFT JOIN dmz_user b ON a.c_userid = b.c_refid
WHERE a.c_orgid=? AND a.c_spaceid=?
ORDER BY a.c_name`,
ORDER BY a.c_name`),
ctx.OrgID, spaceID)
if err != nil {
@ -88,9 +88,9 @@ func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (b []block.
}
// IncrementUsage increments usage counter for content block.
func (s Scope) IncrementUsage(ctx domain.RequestContext, id string) (err error) {
_, err = ctx.Transaction.Exec(`UPDATE dmz_section_template SET
c_used=c_used+1, c_revised=? WHERE c_orgid=? AND c_refid=?`,
func (s Store) IncrementUsage(ctx domain.RequestContext, id string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_section_template SET
c_used=c_used+1, c_revised=? WHERE c_orgid=? AND c_refid=?`),
time.Now().UTC(), ctx.OrgID, id)
if err != nil {
@ -101,9 +101,9 @@ func (s Scope) IncrementUsage(ctx domain.RequestContext, id string) (err error)
}
// DecrementUsage decrements usage counter for content block.
func (s Scope) DecrementUsage(ctx domain.RequestContext, id string) (err error) {
_, err = ctx.Transaction.Exec(`UPDATE dmz_section_template SET
c_used=c_used-1, c_revised=? WHERE c_orgid=? AND c_refid=?`,
func (s Store) DecrementUsage(ctx domain.RequestContext, id string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_section_template SET
c_used=c_used-1, c_revised=? WHERE c_orgid=? AND c_refid=?`),
time.Now().UTC(), ctx.OrgID, id)
if err != nil {
@ -114,10 +114,10 @@ func (s Scope) DecrementUsage(ctx domain.RequestContext, id string) (err error)
}
// RemoveReference clears page.blockid for given blockID.
func (s Scope) RemoveReference(ctx domain.RequestContext, id string) (err error) {
_, err = ctx.Transaction.Exec(`UPDATE dmz_section SET
func (s Store) RemoveReference(ctx domain.RequestContext, id string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_section SET
c_templateid='', c_revised=?
WHERE c_orgid=? AND c_templateid=?`,
WHERE c_orgid=? AND c_templateid=?`),
time.Now().UTC(), ctx.OrgID, id)
if err == sql.ErrNoRows {
@ -131,12 +131,12 @@ func (s Scope) RemoveReference(ctx domain.RequestContext, id string) (err error)
}
// Update updates existing reusable content block item.
func (s Scope) Update(ctx domain.RequestContext, b block.Block) (err error) {
func (s Store) Update(ctx domain.RequestContext, b block.Block) (err error) {
b.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec(`UPDATE dmz_section_template SET
_, err = ctx.Transaction.NamedExec(s.Bind(`UPDATE dmz_section_template SET
c_name=:name, c_body=:body, c_desc=:excerpt, c_rawbody=:rawbody,
c_config=:config, c_revised=:revised
WHERE c_orgid=:orgid AND c_refid=:refid`,
WHERE c_orgid=:orgid AND c_refid=:refid`),
b)
if err != nil {
@ -147,7 +147,6 @@ func (s Scope) Update(ctx domain.RequestContext, b block.Block) (err error) {
}
// Delete removes reusable content block from database.
func (s Scope) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteConstrained(ctx.Transaction, "dmz_section_template", ctx.OrgID, id)
func (s Store) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
return s.DeleteConstrained(ctx.Transaction, "dmz_section_template", ctx.OrgID, id)
}

View file

@ -9,33 +9,31 @@
//
// https://documize.com
// Package mysql handles data persistence for both category definition
// and and document/category association.
package mysql
package category
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/category"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space category information.
type Store struct {
store.Context
domain.CategoryStorer
}
// Add inserts the given record into the category table.
func (s Scope) Add(ctx domain.RequestContext, c category.Category) (err error) {
func (s Store) Add(ctx domain.RequestContext, c category.Category) (err error) {
c.Created = time.Now().UTC()
c.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_category (c_refid, c_orgid, c_spaceid, c_name, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_category (c_refid, c_orgid, c_spaceid, c_name, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?)"),
c.RefID, c.OrgID, c.SpaceID, c.Name, c.Created, c.Revised)
if err != nil {
@ -47,8 +45,8 @@ func (s Scope) Add(ctx domain.RequestContext, c category.Category) (err error) {
// GetBySpace returns space categories accessible by user.
// Context is used to for user ID.
func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (c []category.Category, err error) {
err = s.Runtime.Db.Select(&c, `
func (s Store) GetBySpace(ctx domain.RequestContext, spaceID string) (c []category.Category, err error) {
err = s.Runtime.Db.Select(&c, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_name AS name, c_created AS created, c_revised AS revised
FROM dmz_category
WHERE c_orgid=? AND c_spaceid=? AND c_refid IN
@ -58,7 +56,8 @@ func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (c []catego
SELECT p.c_refid from dmz_permission p LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_who='role' AND p.c_location='category' AND (r.c_userid=? OR r.c_userid='0')
))
ORDER BY name`, ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
ORDER BY name`),
ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
if err == sql.ErrNoRows {
err = nil
@ -71,10 +70,10 @@ func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (c []catego
}
// GetAllBySpace returns all space categories.
func (s Scope) GetAllBySpace(ctx domain.RequestContext, spaceID string) (c []category.Category, err error) {
func (s Store) GetAllBySpace(ctx domain.RequestContext, spaceID string) (c []category.Category, err error) {
c = []category.Category{}
err = s.Runtime.Db.Select(&c, `
err = s.Runtime.Db.Select(&c, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_name AS name, c_created AS created, c_revised AS revised
FROM dmz_category
WHERE c_orgid=? AND c_spaceid=? AND c_spaceid IN
@ -84,7 +83,8 @@ func (s Scope) GetAllBySpace(ctx domain.RequestContext, spaceID string) (c []cat
SELECT p.c_refid FROM dmz_permission p LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_who='role' AND p.c_location='space' AND p.c_action='view' AND (r.c_userid=? OR r.c_userid='0')
))
ORDER BY c_name`, ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
ORDER BY c_name`),
ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
if err == sql.ErrNoRows {
err = nil
@ -97,8 +97,8 @@ func (s Scope) GetAllBySpace(ctx domain.RequestContext, spaceID string) (c []cat
}
// GetByOrg returns all categories accessible by user for their org.
func (s Scope) GetByOrg(ctx domain.RequestContext, userID string) (c []category.Category, err error) {
err = s.Runtime.Db.Select(&c, `
func (s Store) GetByOrg(ctx domain.RequestContext, userID string) (c []category.Category, err error) {
err = s.Runtime.Db.Select(&c, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_name AS name, c_created AS created, c_revised AS revised
FROM dmz_category
WHERE c_orgid=? AND c_refid IN
@ -108,7 +108,8 @@ func (s Scope) GetByOrg(ctx domain.RequestContext, userID string) (c []category.
SELECT p.c_refid FROM dmz_permission p LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_who='role' AND p.c_location='category' AND (r.c_userid=? OR r.c_userid='0')
))
ORDER BY c_name`, ctx.OrgID, ctx.OrgID, ctx.OrgID, userID, ctx.OrgID, userID)
ORDER BY c_name`),
ctx.OrgID, ctx.OrgID, ctx.OrgID, userID, ctx.OrgID, userID)
if err == sql.ErrNoRows {
err = nil
@ -121,11 +122,10 @@ func (s Scope) GetByOrg(ctx domain.RequestContext, userID string) (c []category.
}
// Update saves category name change.
func (s Scope) Update(ctx domain.RequestContext, c category.Category) (err error) {
func (s Store) Update(ctx domain.RequestContext, c category.Category) (err error) {
c.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec("UPDATE dmz_category SET c_name=:name, c_revised=:revised WHERE c_orgid=:orgid AND c_refid=:refid", c)
_, err = ctx.Transaction.NamedExec(s.Bind("UPDATE dmz_category SET c_name=:name, c_revised=:revised WHERE c_orgid=:orgid AND c_refid=:refid"), c)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to execute update for category %s", c.RefID))
}
@ -134,11 +134,11 @@ func (s Scope) Update(ctx domain.RequestContext, c category.Category) (err error
}
// Get returns specified category
func (s Scope) Get(ctx domain.RequestContext, id string) (c category.Category, err error) {
err = s.Runtime.Db.Get(&c, `
func (s Store) Get(ctx domain.RequestContext, id string) (c category.Category, err error) {
err = s.Runtime.Db.Get(&c, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_name AS name, c_created AS created, c_revised AS revised
FROM dmz_category
WHERE c_orgid=? AND c_refid=?`,
WHERE c_orgid=? AND c_refid=?`),
ctx.OrgID, id)
if err != nil {
@ -149,17 +149,16 @@ func (s Scope) Get(ctx domain.RequestContext, id string) (c category.Category, e
}
// Delete removes category from the store.
func (s Scope) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteConstrained(ctx.Transaction, "dmz_category", ctx.OrgID, id)
func (s Store) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
return s.DeleteConstrained(ctx.Transaction, "dmz_category", ctx.OrgID, id)
}
// AssociateDocument inserts category membership record into the category member table.
func (s Scope) AssociateDocument(ctx domain.RequestContext, m category.Member) (err error) {
func (s Store) AssociateDocument(ctx domain.RequestContext, m category.Member) (err error) {
m.Created = time.Now().UTC()
m.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_category_member (c_refid, c_orgid, c_categoryid, c_spaceid, c_docid, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_category_member (c_refid, c_orgid, c_categoryid, c_spaceid, c_docid, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?)"),
m.RefID, m.OrgID, m.CategoryID, m.SpaceID, m.DocumentID, m.Created, m.Revised)
if err != nil {
@ -170,61 +169,51 @@ func (s Scope) AssociateDocument(ctx domain.RequestContext, m category.Member) (
}
// DisassociateDocument removes document associatation from category.
func (s Scope) DisassociateDocument(ctx domain.RequestContext, categoryID, documentID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DisassociateDocument(ctx domain.RequestContext, categoryID, documentID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_category_member WHERE c_orgid='%s' AND c_categoryid='%s' AND c_docid='%s'",
ctx.OrgID, categoryID, documentID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// RemoveCategoryMembership removes all category associations from the store.
func (s Scope) RemoveCategoryMembership(ctx domain.RequestContext, categoryID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) RemoveCategoryMembership(ctx domain.RequestContext, categoryID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_category_member WHERE c_orgid='%s' AND c_categoryid='%s'",
ctx.OrgID, categoryID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// RemoveSpaceCategoryMemberships removes all category associations from the store for the space.
func (s Scope) RemoveSpaceCategoryMemberships(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) RemoveSpaceCategoryMemberships(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_category_member WHERE c_orgid='%s' AND c_spaceid='%s'",
ctx.OrgID, spaceID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// RemoveDocumentCategories removes all document category associations from the store.
func (s Scope) RemoveDocumentCategories(ctx domain.RequestContext, documentID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) RemoveDocumentCategories(ctx domain.RequestContext, documentID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_category_member WHERE c_orgid='%s' AND c_docid='%s'",
ctx.OrgID, documentID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// DeleteBySpace removes all category and category associations for given space.
func (s Scope) DeleteBySpace(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteBySpace(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
s1 := fmt.Sprintf("DELETE FROM categorymember WHERE c_orgid='%s' AND c_groupid='%s'", ctx.OrgID, spaceID)
b.DeleteWhere(ctx.Transaction, s1)
s.DeleteWhere(ctx.Transaction, s1)
s2 := fmt.Sprintf("DELETE FROM dmz_category WHERE c_orgid='%s' AND c_spaceid='%s'", ctx.OrgID, spaceID)
return b.DeleteWhere(ctx.Transaction, s2)
return s.DeleteWhere(ctx.Transaction, s2)
}
// GetSpaceCategorySummary returns number of documents and users for space categories.
func (s Scope) GetSpaceCategorySummary(ctx domain.RequestContext, spaceID string) (c []category.SummaryModel, err error) {
func (s Store) GetSpaceCategorySummary(ctx domain.RequestContext, spaceID string) (c []category.SummaryModel, err error) {
c = []category.SummaryModel{}
err = s.Runtime.Db.Select(&c, `
err = s.Runtime.Db.Select(&c, s.Bind(`
SELECT 'documents' AS type, c_categoryid AS categoryid, COUNT(*) AS count
FROM dmz_category_member
WHERE c_orgid=? AND c_spaceid=?
@ -247,7 +236,7 @@ func (s Scope) GetSpaceCategorySummary(ctx domain.RequestContext, spaceID string
FROM dmz_permission
WHERE c_orgid=? AND c_location='category' AND c_refid IN
(SELECT c_refid FROM dmz_category WHERE c_orgid=? AND c_spaceid=?)
GROUP BY c_refid, type`,
GROUP BY c_refid, type`),
ctx.OrgID, spaceID,
ctx.OrgID, spaceID, ctx.OrgID, spaceID,
ctx.OrgID, ctx.OrgID, spaceID)
@ -263,13 +252,14 @@ func (s Scope) GetSpaceCategorySummary(ctx domain.RequestContext, spaceID string
}
// GetDocumentCategoryMembership returns all space categories associated with given document.
func (s Scope) GetDocumentCategoryMembership(ctx domain.RequestContext, documentID string) (c []category.Category, err error) {
func (s Store) GetDocumentCategoryMembership(ctx domain.RequestContext, documentID string) (c []category.Category, err error) {
c = []category.Category{}
err = s.Runtime.Db.Select(&c, `
err = s.Runtime.Db.Select(&c, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_name AS name, c_created AS created, c_revised AS revised
FROM dmz_category
WHERE c_orgid=? AND c_refid IN (SELECT c_categoryid FROM dmz_category_member WHERE c_orgid=? AND c_docid=?)`, ctx.OrgID, ctx.OrgID, documentID)
WHERE c_orgid=? AND c_refid IN (SELECT c_categoryid FROM dmz_category_member WHERE c_orgid=? AND c_docid=?)`),
ctx.OrgID, ctx.OrgID, documentID)
if err == sql.ErrNoRows {
err = nil
@ -282,8 +272,8 @@ func (s Scope) GetDocumentCategoryMembership(ctx domain.RequestContext, document
}
// GetSpaceCategoryMembership returns category/document associations within space.
func (s Scope) GetSpaceCategoryMembership(ctx domain.RequestContext, spaceID string) (c []category.Member, err error) {
err = s.Runtime.Db.Select(&c, `
func (s Store) GetSpaceCategoryMembership(ctx domain.RequestContext, spaceID string) (c []category.Member, err error) {
err = s.Runtime.Db.Select(&c, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_categoryid AS categoryid, c_docid AS documentid, c_created AS created, c_revised AS revised
FROM dmz_category_member
WHERE c_orgid=? AND c_spaceid=? AND c_spaceid IN
@ -294,7 +284,8 @@ func (s Scope) GetSpaceCategoryMembership(ctx domain.RequestContext, spaceID str
WHERE p.c_orgid=? AND p.c_who='role' AND p.c_location='space'
AND p.c_action='view' AND (r.c_userid=? OR r.c_userid='0')
))
ORDER BY documentid`, ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
ORDER BY documentid`),
ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
if err == sql.ErrNoRows {
err = nil
@ -307,8 +298,8 @@ func (s Scope) GetSpaceCategoryMembership(ctx domain.RequestContext, spaceID str
}
// GetOrgCategoryMembership returns category/document associations within organization.
func (s Scope) GetOrgCategoryMembership(ctx domain.RequestContext, userID string) (c []category.Member, err error) {
err = s.Runtime.Db.Select(&c, `
func (s Store) GetOrgCategoryMembership(ctx domain.RequestContext, userID string) (c []category.Member, err error) {
err = s.Runtime.Db.Select(&c, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_categoryid AS categoryid, c_docid AS documentid, c_created AS created, c_revised AS revised
FROM dmz_category_member
WHERE c_orgid=? AND c_spaceid IN
@ -318,7 +309,8 @@ func (s Scope) GetOrgCategoryMembership(ctx domain.RequestContext, userID string
SELECT p.c_refid from dmz_permission p LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid WHERE p.c_orgid=? AND p.c_who='role' AND p.c_location='space'
AND p.c_action='view' AND (r.c_userid=? OR r.c_userid='0')
))
ORDER BY documentid`, ctx.OrgID, ctx.OrgID, ctx.OrgID, userID, ctx.OrgID, userID)
ORDER BY documentid`),
ctx.OrgID, ctx.OrgID, ctx.OrgID, userID, ctx.OrgID, userID)
if err == sql.ErrNoRows {
err = nil

View file

@ -9,34 +9,34 @@
//
// https://documize.com
package mysql
package document
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/doc"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space category information.
type Store struct {
store.Context
domain.DocumentStorer
}
// Add inserts the given document record into the document table and audits that it has been done.
func (s Scope) Add(ctx domain.RequestContext, d doc.Document) (err error) {
func (s Store) Add(ctx domain.RequestContext, d doc.Document) (err error) {
d.OrgID = ctx.OrgID
d.Created = time.Now().UTC()
d.Revised = d.Created // put same time in both fields
_, err = ctx.Transaction.Exec(`
_, err = ctx.Transaction.Exec(s.Bind(`
INSERT INTO dmz_doc (c_refid, c_orgid, c_spaceid, c_userid, c_job, c_location, 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)
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`,
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)`),
d.RefID, d.OrgID, d.SpaceID, d.UserID, d.Job, d.Location, d.Name, d.Excerpt, d.Slug, d.Tags,
d.Template, d.Protection, d.Approval, d.Lifecycle, d.Versioned, d.VersionID, d.VersionOrder, d.GroupID, d.Created, d.Revised)
@ -48,15 +48,15 @@ func (s Scope) Add(ctx domain.RequestContext, d doc.Document) (err error) {
}
// Get fetches the document record with the given id fromt the document table and audits that it has been got.
func (s Scope) Get(ctx domain.RequestContext, id string) (document doc.Document, err error) {
err = s.Runtime.Db.Get(&document, `
func (s Store) Get(ctx domain.RequestContext, id string) (document doc.Document, err error) {
err = s.Runtime.Db.Get(&document, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_userid AS userid,
c_job AS job, c_location AS location, c_name AS name, c_desc AS excerpt, c_slug AS slug,
c_tags AS tags, c_template AS template, c_protection AS protection, c_approval AS approval,
c_lifecycle AS lifecycle, c_versioned AS versioned, c_versionid AS versionid,
c_versionorder AS versionorder, c_groupid AS groupid, c_created AS created, c_revised AS revised
FROM dmz_doc
WHERE c_orgid=? and c_refid=?`,
WHERE c_orgid=? and c_refid=?`),
ctx.OrgID, id)
if err != nil {
@ -66,42 +66,6 @@ func (s Scope) Get(ctx domain.RequestContext, id string) (document doc.Document,
return
}
// // DocumentMeta returns the metadata for a specified document.
// func (s Scope) DocumentMeta(ctx domain.RequestContext, id string) (meta doc.DocumentMeta, err error) {
// sqlViewers := `
// SELECT MAX(a.c_created) as created,
// IFNULL(a.c_userid, '') AS userid, IFNULL(u.c_firstname, 'Anonymous') AS firstname,
// IFNULL(u.c_lastname, 'Viewer') AS lastname
// FROM dmz_audit_log a LEFT JOIN dmz_user u ON a.c_userid=u.c_refid
// WHERE a.c_orgid=? AND a.documentid=?
// AND a.userid != '0' AND a.userid != ''
// AND action='get-document'
// GROUP BY a.userid ORDER BY MAX(a.created) DESC`
// err = s.Runtime.Db.Select(&meta.Viewers, sqlViewers, ctx.OrgID, id)
// if err != nil {
// err = errors.Wrap(err, fmt.Sprintf("select document viewers %s", id))
// return
// }
// sqlEdits := `SELECT a.created,
// IFNULL(a.action, '') AS action, IFNULL(a.userid, '') AS userid, IFNULL(u.firstname, 'Anonymous') AS firstname, IFNULL(u.lastname, 'Viewer') AS lastname, IFNULL(a.pageid, '') AS pageid
// FROM audit a LEFT JOIN user u ON a.userid=u.refid
// WHERE a.orgid=? AND a.documentid=? AND a.userid != '0' AND a.userid != ''
// AND (a.action='update-page' OR a.action='add-page' OR a.action='remove-page')
// ORDER BY a.created DESC;`
// err = s.Runtime.Db.Select(&meta.Editors, sqlEdits, ctx.OrgID, id)
// if err != nil {
// err = errors.Wrap(err, fmt.Sprintf("select document editors %s", id))
// return
// }
// return
// }
// GetBySpace returns a slice containing the documents for a given space.
//
// No attempt is made to hide documents that are protected by category
@ -109,10 +73,10 @@ func (s Scope) Get(ctx domain.RequestContext, id string) (document doc.Document,
//
// All versions of a document are returned, hence caller must
// decide what to do with them.
func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (documents []doc.Document, err error) {
func (s Store) GetBySpace(ctx domain.RequestContext, spaceID string) (documents []doc.Document, err error) {
documents = []doc.Document{}
err = s.Runtime.Db.Select(&documents, `
err = s.Runtime.Db.Select(&documents, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_userid AS userid,
c_job AS job, c_location AS location, c_name AS name, c_desc AS excerpt, c_slug AS slug,
c_tags AS tags, c_template AS template, c_protection AS protection, c_approval AS approval,
@ -129,7 +93,7 @@ func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (documents
)
)
)
ORDER BY c_name, c_versionorder`,
ORDER BY c_name, c_versionorder`),
ctx.OrgID, ctx.OrgID, ctx.OrgID, spaceID, ctx.OrgID, ctx.UserID, ctx.OrgID, spaceID, ctx.UserID)
if err == sql.ErrNoRows {
@ -143,8 +107,8 @@ func (s Scope) GetBySpace(ctx domain.RequestContext, spaceID string) (documents
}
// TemplatesBySpace returns a slice containing the documents available as templates for given space.
func (s Scope) TemplatesBySpace(ctx domain.RequestContext, spaceID string) (documents []doc.Document, err error) {
err = s.Runtime.Db.Select(&documents, `
func (s Store) TemplatesBySpace(ctx domain.RequestContext, spaceID string) (documents []doc.Document, err error) {
err = s.Runtime.Db.Select(&documents, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_userid AS userid,
c_job AS job, c_location AS location, c_name AS name, c_desc AS excerpt, c_slug AS slug,
c_tags AS tags, c_template AS template, c_protection AS protection, c_approval AS approval,
@ -160,7 +124,8 @@ func (s Scope) TemplatesBySpace(ctx domain.RequestContext, spaceID string) (docu
SELECT p.c_refid FROM dmz_permission p LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid WHERE p.c_orgid=? AND p.c_who='role' AND p.c_location='space' AND p.c_action='view' AND (r.c_userid=? OR r.c_userid='0'))
)
)
ORDER BY c_name`, ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
ORDER BY c_name`),
ctx.OrgID, spaceID, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
if err == sql.ErrNoRows {
err = nil
@ -176,12 +141,13 @@ func (s Scope) TemplatesBySpace(ctx domain.RequestContext, spaceID string) (docu
// PublicDocuments returns a slice of SitemapDocument records
// linking to documents in public spaces.
// These documents can then be seen by search crawlers.
func (s Scope) PublicDocuments(ctx domain.RequestContext, orgID string) (documents []doc.SitemapDocument, err error) {
err = s.Runtime.Db.Select(&documents, `
func (s Store) PublicDocuments(ctx domain.RequestContext, orgID string) (documents []doc.SitemapDocument, err error) {
err = s.Runtime.Db.Select(&documents, s.Bind(`
SELECT d.c_refid AS documentid, d.c_name AS document, d.c_revised as revised, l.c_refid AS spaceid, l.c_name AS space
FROM dmz_doc d
LEFT JOIN dmz_space l ON l.c_refid=d.c_spaceid
WHERE d.c_orgid=? AND l.c_type=1 AND d.c_lifecycle=1 AND d.c_template=0`, orgID)
WHERE d.c_orgid=? AND l.c_type=1 AND d.c_lifecycle=1 AND d.c_template=0`),
orgID)
if err == sql.ErrNoRows {
err = nil
@ -199,17 +165,17 @@ func (s Scope) PublicDocuments(ctx domain.RequestContext, orgID string) (documen
*/
// Update changes the given document record to the new values, updates search information and audits the action.
func (s Scope) Update(ctx domain.RequestContext, document doc.Document) (err error) {
func (s Store) Update(ctx domain.RequestContext, document doc.Document) (err error) {
document.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec(`
_, err = ctx.Transaction.NamedExec(s.Bind(`
UPDATE dmz_doc SET
c_spaceid=:spaceid, c_userid=:userid, c_job=:job, c_location=:location, c_name=:name,
c_desc=:excerpt, c_slug=:slug, c_tags=:tags, c_template=:template,
c_protection=:protection, c_approval=:approval, c_lifecycle=:lifecycle,
c_versioned=:versioned, c_versionid=:versionid, c_versionorder=:versionorder,
c_groupid=:groupid, c_revised=:revised
WHERE c_orgid=:orgid AND c_refid=:refid`,
WHERE c_orgid=:orgid AND c_refid=:refid`),
&document)
if err != nil {
@ -220,8 +186,8 @@ func (s Scope) Update(ctx domain.RequestContext, document doc.Document) (err err
}
// UpdateGroup applies same values to all documents with the same group ID.
func (s Scope) UpdateGroup(ctx domain.RequestContext, d doc.Document) (err error) {
_, err = ctx.Transaction.Exec(`UPDATE dmz_doc SET c_name=?, c_desc=? WHERE c_orgid=? AND c_groupid=?`,
func (s Store) UpdateGroup(ctx domain.RequestContext, d doc.Document) (err error) {
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_doc SET c_name=?, c_desc=? WHERE c_orgid=? AND c_groupid=?`),
d.Name, d.Excerpt, ctx.OrgID, d.GroupID)
if err == sql.ErrNoRows {
@ -235,10 +201,10 @@ func (s Scope) UpdateGroup(ctx domain.RequestContext, d doc.Document) (err error
}
// ChangeDocumentSpace assigns the specified space to the document.
func (s Scope) ChangeDocumentSpace(ctx domain.RequestContext, document, space string) (err error) {
func (s Store) ChangeDocumentSpace(ctx domain.RequestContext, document, space string) (err error) {
revised := time.Now().UTC()
_, err = ctx.Transaction.Exec("UPDATE dmz_doc SET c_spaceid=?, c_revised=? WHERE c_orgid=? AND c_refid=?",
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_doc SET c_spaceid=?, c_revised=? WHERE c_orgid=? AND c_refid=?"),
space, revised, ctx.OrgID, document)
if err != nil {
@ -249,8 +215,8 @@ func (s Scope) ChangeDocumentSpace(ctx domain.RequestContext, document, space st
}
// MoveDocumentSpace changes the space for client's organization's documents which have space "id", to "move".
func (s Scope) MoveDocumentSpace(ctx domain.RequestContext, id, move string) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_doc SET c_spaceid=? WHERE c_orgid=? AND c_spaceid=?",
func (s Store) MoveDocumentSpace(ctx domain.RequestContext, id, move string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_doc SET c_spaceid=? WHERE c_orgid=? AND c_spaceid=?"),
move, ctx.OrgID, id)
if err == sql.ErrNoRows {
@ -264,8 +230,8 @@ func (s Scope) MoveDocumentSpace(ctx domain.RequestContext, id, move string) (er
}
// MoveActivity changes the space for all document activity records.
func (s Scope) MoveActivity(ctx domain.RequestContext, documentID, oldSpaceID, newSpaceID string) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_user_activity SET c_spaceid=? WHERE c_orgid=? AND c_spaceid=? AND c_docid=?",
func (s Store) MoveActivity(ctx domain.RequestContext, documentID, oldSpaceID, newSpaceID string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_user_activity SET c_spaceid=? WHERE c_orgid=? AND c_spaceid=? AND c_docid=?"),
newSpaceID, ctx.OrgID, oldSpaceID, documentID)
if err != nil {
@ -277,63 +243,61 @@ func (s Scope) MoveActivity(ctx domain.RequestContext, documentID, oldSpaceID, n
// Delete removes the specified document.
// Remove document pages, revisions, attachments, updates the search subsystem.
func (s Scope) Delete(ctx domain.RequestContext, documentID string) (rows int64, err error) {
b := mysql.BaseQuery{}
rows, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
func (s Store) Delete(ctx domain.RequestContext, documentID string) (rows int64, err error) {
rows, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
if err != nil {
return
}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_revision WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_revision WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
if err != nil {
return
}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_attachment WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_attachment WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
if err != nil {
return
}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_category_member WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_category_member WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
if err != nil {
return
}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_vote WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_vote WHERE c_docid=\"%s\" AND c_orgid=\"%s\"", documentID, ctx.OrgID))
if err != nil {
return
}
return b.DeleteConstrained(ctx.Transaction, "dmz_doc", ctx.OrgID, documentID)
return s.DeleteConstrained(ctx.Transaction, "dmz_doc", ctx.OrgID, documentID)
}
// DeleteBySpace removes all documents for given space.
// Remove document pages, revisions, attachments, updates the search subsystem.
func (s Scope) DeleteBySpace(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
b := mysql.BaseQuery{}
rows, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
func (s Store) DeleteBySpace(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
rows, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
if err != nil {
return
}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_revision WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_revision WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
if err != nil {
return
}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_attachment WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_attachment WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
if err != nil {
return
}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_vote WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_vote WHERE c_docid IN (SELECT c_refid FROM dmz_doc WHERE c_spaceid=\"%s\" AND c_orgid=\"%s\")", spaceID, ctx.OrgID))
if err != nil {
return
}
return b.DeleteConstrained(ctx.Transaction, "dmz_doc", ctx.OrgID, spaceID)
return s.DeleteConstrained(ctx.Transaction, "dmz_doc", ctx.OrgID, spaceID)
}
// GetVersions returns a slice containing the documents for a given space.
@ -343,14 +307,14 @@ func (s Scope) DeleteBySpace(ctx domain.RequestContext, spaceID string) (rows in
//
// All versions of a document are returned, hence caller must
// decide what to do with them.
func (s Scope) GetVersions(ctx domain.RequestContext, groupID string) (v []doc.Version, err error) {
func (s Store) GetVersions(ctx domain.RequestContext, groupID string) (v []doc.Version, err error) {
v = []doc.Version{}
err = s.Runtime.Db.Select(&v, `
err = s.Runtime.Db.Select(&v, s.Bind(`
SELECT c_versionid AS versionid, c_refid As documentid
FROM dmz_doc
WHERE c_orgid=? AND c_groupid=?
ORDER BY c_versionorder`,
ORDER BY c_versionorder`),
ctx.OrgID, groupID)
if err == sql.ErrNoRows {
@ -365,17 +329,15 @@ func (s Scope) GetVersions(ctx domain.RequestContext, groupID string) (v []doc.V
// Vote records document content vote.
// Any existing vote by the user is replaced.
func (s Scope) Vote(ctx domain.RequestContext, refID, orgID, documentID, userID string, vote int) (err error) {
b := mysql.BaseQuery{}
_, err = b.DeleteWhere(ctx.Transaction,
func (s Store) Vote(ctx domain.RequestContext, refID, orgID, documentID, userID string, vote int) (err error) {
_, err = s.DeleteWhere(ctx.Transaction,
fmt.Sprintf("DELETE FROM dmz_doc_vote WHERE c_orgid=\"%s\" AND c_docid=\"%s\" AND c_voter=\"%s\"",
orgID, documentID, userID))
if err != nil {
s.Runtime.Log.Error("store.Vote", err)
}
_, err = ctx.Transaction.Exec(`INSERT INTO dmz_doc_vote (c_refid, c_orgid, c_docid, c_voter, c_vote) VALUES (?, ?, ?, ?, ?)`,
_, err = ctx.Transaction.Exec(s.Bind(`INSERT INTO dmz_doc_vote (c_refid, c_orgid, c_docid, c_voter, c_vote) VALUES (?, ?, ?, ?, ?)`),
refID, orgID, documentID, userID, vote)
if err != nil {
err = errors.Wrap(err, "execute insert vote")

View file

@ -9,31 +9,31 @@
//
// https://documize.com
package mysql
package group
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/group"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space category information.
type Store struct {
store.Context
domain.DocumentStorer
}
// Add inserts new user group into store.
func (s Scope) Add(ctx domain.RequestContext, g group.Group) (err error) {
func (s Store) Add(ctx domain.RequestContext, g group.Group) (err error) {
g.Created = time.Now().UTC()
g.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_group (c_refid, c_orgid, c_name, c_desc, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_group (c_refid, c_orgid, c_name, c_desc, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?)"),
g.RefID, g.OrgID, g.Name, g.Purpose, g.Created, g.Revised)
if err != nil {
@ -44,11 +44,11 @@ func (s Scope) Add(ctx domain.RequestContext, g group.Group) (err error) {
}
// Get returns requested group.
func (s Scope) Get(ctx domain.RequestContext, refID string) (g group.Group, err error) {
err = s.Runtime.Db.Get(&g, `
SELECT id, c_refid AS refid, c_orgid AS orgid, c_name AS name, c_desc AS purpose, c_created AS created, c_revised AS revised
func (s Store) Get(ctx domain.RequestContext, refID string) (g group.Group, err error) {
err = s.Runtime.Db.Get(&g, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_name AS name, c_desc AS purpose, c_created AS created, c_revised AS revised
FROM dmz_group
WHERE c_orgid=? AND c_refid=?`,
WHERE c_orgid=? AND c_refid=?`),
ctx.OrgID, refID)
if err != nil {
@ -59,17 +59,17 @@ func (s Scope) Get(ctx domain.RequestContext, refID string) (g group.Group, err
}
// GetAll returns all user groups for current orgID.
func (s Scope) GetAll(ctx domain.RequestContext) (groups []group.Group, err error) {
func (s Store) GetAll(ctx domain.RequestContext) (groups []group.Group, err error) {
groups = []group.Group{}
err = s.Runtime.Db.Select(&groups, `
err = s.Runtime.Db.Select(&groups, s.Bind(`
SELECT a.id, a.c_refid AS refid, a.c_orgid AS orgid, a.c_name AS name, a.c_desc AS purpose, a.c_created AS created, a.c_revised AS revised,
COUNT(b.c_groupid) AS members
FROM dmz_group a
LEFT JOIN dmz_group_member b ON a.c_refid=b.c_groupid
WHERE a.c_orgid=?
GROUP BY a.id, a.c_refid, a.c_orgid, a.c_name, a.c_desc, a.c_created, a.c_revised
ORDER BY a.c_name`,
ORDER BY a.c_name`),
ctx.OrgID)
if err == sql.ErrNoRows {
@ -83,12 +83,12 @@ func (s Scope) GetAll(ctx domain.RequestContext) (groups []group.Group, err erro
}
// Update group name and description.
func (s Scope) Update(ctx domain.RequestContext, g group.Group) (err error) {
func (s Store) Update(ctx domain.RequestContext, g group.Group) (err error) {
g.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec(`UPDATE dmz_group SET
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_group SET
c_name=?, c_desc=?, c_revised=?
WHERE c_orgid=? AND c_refid=?`,
WHERE c_orgid=? AND c_refid=?`),
g.Name, g.Purpose, g.Revised, ctx.OrgID, g.RefID)
if err != nil {
@ -99,26 +99,25 @@ func (s Scope) Update(ctx domain.RequestContext, g group.Group) (err error) {
}
// Delete removes group from store.
func (s Scope) Delete(ctx domain.RequestContext, refID string) (rows int64, err error) {
b := mysql.BaseQuery{}
_, err = b.DeleteConstrained(ctx.Transaction, "dmz_group", ctx.OrgID, refID)
func (s Store) Delete(ctx domain.RequestContext, refID string) (rows int64, err error) {
_, err = s.DeleteConstrained(ctx.Transaction, "dmz_group", ctx.OrgID, refID)
if err != nil {
return
}
return b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_group_member WHERE c_orgid=\"%s\" AND c_groupid=\"%s\"", ctx.OrgID, refID))
return s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_group_member WHERE c_orgid=\"%s\" AND c_groupid=\"%s\"", ctx.OrgID, refID))
}
// GetGroupMembers returns all user associated with given group.
func (s Scope) GetGroupMembers(ctx domain.RequestContext, groupID string) (members []group.Member, err error) {
func (s Store) GetGroupMembers(ctx domain.RequestContext, groupID string) (members []group.Member, err error) {
members = []group.Member{}
err = s.Runtime.Db.Select(&members, `
err = s.Runtime.Db.Select(&members, s.Bind(`
SELECT a.id, a.c_orgid AS orgid, a.c_groupid AS groupid, a.c_userid AS userid,
IFNULL(b.c_firstname, '') as firstname, IFNULL(b.c_lastname, '') as lastname
COALESCE(b.c_firstname, '') as firstname, COALESCE(b.c_lastname, '') as lastname
FROM dmz_group_member a
LEFT JOIN dmz_user b ON b.c_refid=a.c_userid
WHERE a.c_orgid=? AND a.c_groupid=?
ORDER BY b.c_firstname, b.c_lastname`,
ORDER BY b.c_firstname, b.c_lastname`),
ctx.OrgID, groupID)
if err == sql.ErrNoRows {
@ -132,8 +131,9 @@ func (s Scope) GetGroupMembers(ctx domain.RequestContext, groupID string) (membe
}
// JoinGroup adds user to group.
func (s Scope) JoinGroup(ctx domain.RequestContext, groupID, userID string) (err error) {
_, err = ctx.Transaction.Exec("INSERT INTO dmz_group_member (c_orgid, c_groupid, c_userid) VALUES (?, ?, ?)", ctx.OrgID, groupID, userID)
func (s Store) JoinGroup(ctx domain.RequestContext, groupID, userID string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_group_member (c_orgid, c_groupid, c_userid) VALUES (?, ?, ?)"),
ctx.OrgID, groupID, userID)
if err != nil {
err = errors.Wrap(err, "insert group member")
}
@ -142,9 +142,9 @@ func (s Scope) JoinGroup(ctx domain.RequestContext, groupID, userID string) (err
}
// LeaveGroup removes user from group.
func (s Scope) LeaveGroup(ctx domain.RequestContext, groupID, userID string) (err error) {
b := mysql.BaseQuery{}
_, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_group_member WHERE c_orgid=\"%s\" AND c_groupid=\"%s\" AND c_userid=\"%s\"", ctx.OrgID, groupID, userID))
func (s Store) LeaveGroup(ctx domain.RequestContext, groupID, userID string) (err error) {
_, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_group_member WHERE c_orgid=\"%s\" AND c_groupid=\"%s\" AND c_userid=\"%s\"",
ctx.OrgID, groupID, userID))
if err != nil {
err = errors.Wrap(err, "clear group member")
}
@ -155,15 +155,15 @@ func (s Scope) LeaveGroup(ctx domain.RequestContext, groupID, userID string) (er
// GetMembers returns members for every group.
// Useful when you need to bulk fetch membership records
// for subsequent processing.
func (s Scope) GetMembers(ctx domain.RequestContext) (r []group.Record, err error) {
func (s Store) GetMembers(ctx domain.RequestContext) (r []group.Record, err error) {
r = []group.Record{}
err = s.Runtime.Db.Select(&r, `
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT a.id, a.c_orgid AS orgid, a.c_groupid AS groupid, a.c_userid AS userid,
b.c_name As name, b.c_desc AS purpose
FROM dmz_group_member a, dmz_group b
WHERE a.c_orgid=? AND a.c_groupid=b.c_refid
ORDER BY a.c_userid`,
ORDER BY a.c_userid`),
ctx.OrgID)
if err == sql.ErrNoRows {

View file

@ -9,7 +9,7 @@
//
// https://documize.com
package mysql
package link
import (
"database/sql"
@ -17,26 +17,26 @@ import (
"strings"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/core/uniqueid"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/link"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space category information.
type Store struct {
store.Context
domain.LinkStorer
}
// Add inserts wiki-link into the store.
// These links exist when content references another document or content.
func (s Scope) Add(ctx domain.RequestContext, l link.Link) (err error) {
func (s Store) Add(ctx domain.RequestContext, l link.Link) (err error) {
l.Created = time.Now().UTC()
l.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_doc_link (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) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_doc_link (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) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
l.RefID, l.OrgID, l.SpaceID, l.UserID, l.SourceDocumentID, l.SourceSectionID, l.TargetDocumentID, l.TargetID, l.ExternalID, l.LinkType, l.Orphan, l.Created, l.Revised)
if err != nil {
@ -47,14 +47,14 @@ func (s Scope) Add(ctx domain.RequestContext, l link.Link) (err error) {
}
// GetDocumentOutboundLinks returns outbound links for specified document.
func (s Scope) GetDocumentOutboundLinks(ctx domain.RequestContext, documentID string) (links []link.Link, err error) {
err = s.Runtime.Db.Select(&links, `
func (s Store) GetDocumentOutboundLinks(ctx domain.RequestContext, documentID string) (links []link.Link, err error) {
err = s.Runtime.Db.Select(&links, s.Bind(`
select c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_userid AS userid,
c_sourcedocid AS sourcedocumentid, c_sourcesectionid AS sourcesectionid,
c_targetdocid AS targetdocumentid, c_targetid AS targetid, c_externalid AS externalid,
c_type as linktype, c_orphan As orphan, c_created AS created, c_revised AS revised
FROM dmz_doc_link
WHERE c_orgid=? AND c_sourcedocid=?`,
WHERE c_orgid=? AND c_sourcedocid=?`),
ctx.OrgID, documentID)
if err != nil && err != sql.ErrNoRows {
@ -69,14 +69,14 @@ func (s Scope) GetDocumentOutboundLinks(ctx domain.RequestContext, documentID st
}
// GetPageLinks returns outbound links for specified page in document.
func (s Scope) GetPageLinks(ctx domain.RequestContext, documentID, pageID string) (links []link.Link, err error) {
err = s.Runtime.Db.Select(&links, `
func (s Store) GetPageLinks(ctx domain.RequestContext, documentID, pageID string) (links []link.Link, err error) {
err = s.Runtime.Db.Select(&links, s.Bind(`
select c_refid AS refid, c_orgid AS orgid, c_spaceid AS spaceid, c_userid AS userid,
c_sourcedocid AS sourcedocumentid, c_sourcesectionid AS sourcesectionid,
c_targetdocid AS targetdocumentid, c_targetid AS targetid, c_externalid AS externalid,
c_type as linktype, c_orphan As orphan, c_created AS created, c_revised AS revised
FROM dmz_doc_link
WHERE c_orgid=? AND c_sourcedocid=? AND c_sourcesectionid=?`,
WHERE c_orgid=? AND c_sourcedocid=? AND c_sourcesectionid=?`),
ctx.OrgID, documentID, pageID)
if err != nil && err != sql.ErrNoRows {
@ -91,11 +91,11 @@ func (s Scope) GetPageLinks(ctx domain.RequestContext, documentID, pageID string
}
// MarkOrphanDocumentLink marks all link records referencing specified document.
func (s Scope) MarkOrphanDocumentLink(ctx domain.RequestContext, documentID string) (err error) {
func (s Store) MarkOrphanDocumentLink(ctx domain.RequestContext, documentID string) (err error) {
revised := time.Now().UTC()
_, err = ctx.Transaction.Exec(`UPDATE dmz_doc_link SET
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_doc_link SET
c_orphan=1, c_revised=?
WHERE c_type='document' AND c_orgid=? AND c_targetdocid=?`,
WHERE c_type='document' AND c_orgid=? AND c_targetdocid=?`),
revised, ctx.OrgID, documentID)
if err != nil {
@ -106,11 +106,11 @@ func (s Scope) MarkOrphanDocumentLink(ctx domain.RequestContext, documentID stri
}
// MarkOrphanPageLink marks all link records referencing specified page.
func (s Scope) MarkOrphanPageLink(ctx domain.RequestContext, pageID string) (err error) {
func (s Store) MarkOrphanPageLink(ctx domain.RequestContext, pageID string) (err error) {
revised := time.Now().UTC()
_, err = ctx.Transaction.Exec(`UPDATE dmz_doc_link SET
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_doc_link SET
c_orphan=1, c_revised=?
WHERE c_type='section' AND c_orgid=? AND c_targetid=?`,
WHERE c_type='section' AND c_orgid=? AND c_targetid=?`),
revised, ctx.OrgID, pageID)
if err != nil {
@ -121,11 +121,11 @@ func (s Scope) MarkOrphanPageLink(ctx domain.RequestContext, pageID string) (err
}
// MarkOrphanAttachmentLink marks all link records referencing specified attachment.
func (s Scope) MarkOrphanAttachmentLink(ctx domain.RequestContext, attachmentID string) (err error) {
func (s Store) MarkOrphanAttachmentLink(ctx domain.RequestContext, attachmentID string) (err error) {
revised := time.Now().UTC()
_, err = ctx.Transaction.Exec(`UPDATE dmz_doc_link SET
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_doc_link SET
c_orphan=1, c_revised=?
WHERE c_type='file' AND c_orgid=? AND c_targetid=?`,
WHERE c_type='file' AND c_orgid=? AND c_targetid=?`),
revised, ctx.OrgID, attachmentID)
if err != nil {
@ -136,25 +136,22 @@ func (s Scope) MarkOrphanAttachmentLink(ctx domain.RequestContext, attachmentID
}
// DeleteSourcePageLinks removes saved links for given source.
func (s Scope) DeleteSourcePageLinks(ctx domain.RequestContext, pageID string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_link WHERE c_orgid=\"%s\" AND c_sourcesectionid=\"%s\"", ctx.OrgID, pageID))
func (s Store) DeleteSourcePageLinks(ctx domain.RequestContext, pageID string) (rows int64, err error) {
return s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_link WHERE c_orgid=\"%s\" AND c_sourcesectionid=\"%s\"", ctx.OrgID, pageID))
}
// DeleteSourceDocumentLinks removes saved links for given document.
func (s Scope) DeleteSourceDocumentLinks(ctx domain.RequestContext, documentID string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_link WHERE c_orgid=\"%s\" AND c_sourcedocid=\"%s\"", ctx.OrgID, documentID))
func (s Store) DeleteSourceDocumentLinks(ctx domain.RequestContext, documentID string) (rows int64, err error) {
return s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_doc_link WHERE c_orgid=\"%s\" AND c_sourcedocid=\"%s\"", ctx.OrgID, documentID))
}
// DeleteLink removes saved link from the store.
func (s Scope) DeleteLink(ctx domain.RequestContext, id string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteConstrained(ctx.Transaction, "dmz_doc_link", ctx.OrgID, id)
func (s Store) DeleteLink(ctx domain.RequestContext, id string) (rows int64, err error) {
return s.DeleteConstrained(ctx.Transaction, "dmz_doc_link", ctx.OrgID, id)
}
// SearchCandidates returns matching documents, sections and attachments using keywords.
func (s Scope) SearchCandidates(ctx domain.RequestContext, keywords string) (docs []link.Candidate,
func (s Store) SearchCandidates(ctx domain.RequestContext, keywords string) (docs []link.Candidate,
pages []link.Candidate, attachments []link.Candidate, err error) {
// find matching documents
@ -162,7 +159,7 @@ func (s Scope) SearchCandidates(ctx domain.RequestContext, keywords string) (doc
keywords = strings.TrimSpace(strings.ToLower(keywords))
likeQuery := "LOWER(d.c_name) LIKE '%" + keywords + "%'"
err = s.Runtime.Db.Select(&temp, `
err = s.Runtime.Db.Select(&temp, s.Bind(`
SELECT d.c_refid AS documentid, d.c_spaceid AS spaceid, d.c_name AS title, l.c_name AS context
FROM dmz_doc d LEFT JOIN dmz_space l ON d.c_spaceid=l.c_refid
WHERE l.c_orgid=? AND `+likeQuery+` AND d.c_spaceid IN
@ -175,7 +172,8 @@ func (s Scope) SearchCandidates(ctx domain.RequestContext, keywords string) (doc
)
)
)
ORDER BY title`, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
ORDER BY title`),
ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
if err != nil {
err = errors.Wrap(err, "execute search links 1")
@ -200,7 +198,7 @@ func (s Scope) SearchCandidates(ctx domain.RequestContext, keywords string) (doc
likeQuery = "LOWER(p.c_name) LIKE '%" + keywords + "%'"
temp = []link.Candidate{}
err = s.Runtime.Db.Select(&temp, `
err = s.Runtime.Db.Select(&temp, s.Bind(`
SELECT p.c_refid AS targetid, p.c_docid AS documentid, p.c_name AS title,
p.c_type AS linktype, d.c_name AS context, d.c_spaceid AS spaceid
FROM dmz_section p LEFT JOIN dmz_doc d ON d.c_refid=p.c_docid
@ -214,7 +212,7 @@ func (s Scope) SearchCandidates(ctx domain.RequestContext, keywords string) (doc
)
)
)
ORDER BY p.c_name`,
ORDER BY p.c_name`),
ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
if err != nil {
@ -240,7 +238,7 @@ func (s Scope) SearchCandidates(ctx domain.RequestContext, keywords string) (doc
likeQuery = "LOWER(a.c_filename) LIKE '%" + keywords + "%'"
temp = []link.Candidate{}
err = s.Runtime.Db.Select(&temp, `
err = s.Runtime.Db.Select(&temp, s.Bind(`
SELECT a.c_refid AS targetid, a.c_docid AS documentid, a.c_filename AS title, a.c_extension AS context, d.c_spaceid AS spaceid
FROM dmz_doc_attachment a LEFT JOIN dmz_doc d ON d.c_refid=a.c_docid
WHERE a.c_orgid=? AND `+likeQuery+` AND d.c_spaceid IN
@ -253,7 +251,8 @@ func (s Scope) SearchCandidates(ctx domain.RequestContext, keywords string) (doc
)
)
)
ORDER BY a.c_filename`, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
ORDER BY a.c_filename`),
ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.OrgID, ctx.UserID, ctx.OrgID, ctx.UserID)
if err != nil {
err = errors.Wrap(err, "execute search links 3")

View file

@ -9,25 +9,26 @@
//
// https://documize.com
package mysql
package meta
import (
"database/sql"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/page"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space category information.
type Store struct {
store.Context
domain.MetaStorer
}
// GetDocumentsID returns every document ID value stored.
// The query runs at the instance level across all tenants.
func (s Scope) GetDocumentsID(ctx domain.RequestContext) (documents []string, err error) {
func (s Store) GetDocumentsID(ctx domain.RequestContext) (documents []string, err error) {
err = s.Runtime.Db.Select(&documents, `SELECT c_refid FROM dmz_doc WHERE c_lifecycle=1`)
if err == sql.ErrNoRows {
@ -42,15 +43,15 @@ func (s Scope) GetDocumentsID(ctx domain.RequestContext) (documents []string, er
}
// GetDocumentPages returns a slice containing all published page records for a given documentID, in presentation sequence.
func (s Scope) GetDocumentPages(ctx domain.RequestContext, documentID string) (p []page.Page, err error) {
err = s.Runtime.Db.Select(&p, `
func (s Store) GetDocumentPages(ctx domain.RequestContext, documentID string) (p []page.Page, err error) {
err = s.Runtime.Db.Select(&p, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_docid AS documentid,
c_userid AS userid, c_contenttype AS contenttype,
c_type AS type, c_level AS level, c_sequence AS sequence, c_name AS name,
c_body AS body, c_revisions AS revisions, c_templateid AS templateid,
c_status AS status, c_relativeid AS relativeid, c_created AS created, c_revised AS revised
FROM dmz_section
WHERE c_docid=? AND (c_status=0 OR ((c_status=4 OR c_status=2) AND c_relativeid=''))`,
WHERE c_docid=? AND (c_status=0 OR ((c_status=4 OR c_status=2) AND c_relativeid=''))`),
documentID)
if err != nil {
@ -61,7 +62,7 @@ func (s Scope) GetDocumentPages(ctx domain.RequestContext, documentID string) (p
}
// SearchIndexCount returns the numnber of index entries.
func (s Scope) SearchIndexCount(ctx domain.RequestContext) (c int, err error) {
func (s Store) SearchIndexCount(ctx domain.RequestContext) (c int, err error) {
row := s.Runtime.Db.QueryRow("SELECT count(*) FROM dmz_search")
err = row.Scan(&c)
if err != nil {

View file

@ -20,23 +20,24 @@ import (
"github.com/documize/community/core/env"
"github.com/documize/community/core/streamutil"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/org"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to organization (tenant) information.
type Store struct {
store.Context
domain.OrganizationStorer
}
// AddOrganization inserts the passed organization record into the organization table.
func (s Scope) AddOrganization(ctx domain.RequestContext, org org.Organization) (err error) {
func (s Store) AddOrganization(ctx domain.RequestContext, org org.Organization) (err error) {
org.Created = time.Now().UTC()
org.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec(
"INSERT INTO dmz_org (c_refid, c_company, c_title, c_message, c_domain, c_email, c_anonaccess, c_serial, c_maxtags, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
s.Bind("INSERT INTO dmz_org (c_refid, c_company, c_title, c_message, c_domain, c_email, c_anonaccess, c_serial, c_maxtags, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
org.RefID, org.Company, org.Title, org.Message, strings.ToLower(org.Domain),
strings.ToLower(org.Email), org.AllowAnonymousAccess, org.Serial, org.MaxTags, org.Created, org.Revised)
@ -48,15 +49,15 @@ func (s Scope) AddOrganization(ctx domain.RequestContext, org org.Organization)
}
// GetOrganization returns the Organization reocrod from the organization database table with the given id.
func (s Scope) GetOrganization(ctx domain.RequestContext, id string) (org org.Organization, err error) {
stmt, err := s.Runtime.Db.Preparex(`SELECT id, c_refid AS refid,
func (s Store) GetOrganization(ctx domain.RequestContext, id string) (org org.Organization, err error) {
stmt, err := s.Runtime.Db.Preparex(s.Bind(`SELECT id, c_refid AS refid,
c_title AS title, c_message AS message, c_domain AS domain,
c_service AS conversionendpoint, c_email AS email, c_serial AS serial, c_active AS active,
c_anonaccess AS allowanonymousaccess, c_authprovider AS authprovider,
coalesce(c_authconfig,JSON_UNQUOTE('{}')) AS authconfig, c_maxtags AS maxtags,
coalesce(c_authconfig,` + s.EmptyJSON() + `) AS authconfig, c_maxtags AS maxtags,
c_created AS created, c_revised AS revised
FROM dmz_org
WHERE c_refid=?`)
WHERE c_refid=?`))
defer streamutil.Close(stmt)
if err != nil {
@ -75,7 +76,7 @@ func (s Scope) GetOrganization(ctx domain.RequestContext, id string) (org org.Or
// GetOrganizationByDomain returns the organization matching a given URL subdomain.
// No context is required because user might not be authenticated yet.
func (s Scope) GetOrganizationByDomain(subdomain string) (o org.Organization, err error) {
func (s Store) GetOrganizationByDomain(subdomain string) (o org.Organization, err error) {
err = nil
subdomain = strings.TrimSpace(strings.ToLower(subdomain))
@ -86,14 +87,15 @@ func (s Scope) GetOrganizationByDomain(subdomain string) (o org.Organization, er
}
// match on given domain name
err = s.Runtime.Db.Get(&o, `SELECT id, c_refid AS refid,
err = s.Runtime.Db.Get(&o, s.Bind(`SELECT id, c_refid AS refid,
c_title AS title, c_message AS message, c_domain AS domain,
c_service AS conversionendpoint, c_email AS email, c_serial AS serial, c_active AS active,
c_anonaccess AS allowanonymousaccess, c_authprovider AS authprovider,
coalesce(c_authconfig,JSON_UNQUOTE('{}')) AS authconfig, c_maxtags AS maxtags,
coalesce(c_authconfig,`+s.EmptyJSON()+`) AS authconfig, c_maxtags AS maxtags,
c_created AS created, c_revised AS revised
FROM dmz_org
WHERE c_domain=? AND c_active=1`, subdomain)
WHERE c_domain=? AND c_active=1`),
subdomain)
if err == nil {
return
}
@ -101,14 +103,15 @@ func (s Scope) GetOrganizationByDomain(subdomain string) (o org.Organization, er
err = nil
// match on empty domain AS last resort
err = s.Runtime.Db.Get(&o, `SELECT id, c_refid AS refid,
err = s.Runtime.Db.Get(&o, s.Bind(`SELECT id, c_refid AS refid,
c_title AS title, c_message AS message, c_domain AS domain,
c_service AS conversionendpoint, c_email AS email, c_serial AS serial, c_active AS active,
c_anonaccess AS allowanonymousaccess, c_authprovider AS authprovider,
coalesce(c_authconfig,JSON_UNQUOTE('{}')) AS authconfig, c_maxtags AS maxtags,
coalesce(c_authconfig,`+s.EmptyJSON()+`) AS authconfig, c_maxtags AS maxtags,
c_created AS created, c_revised AS revised
FROM dmz_org
WHERE c_domain='' AND c_active=1`)
WHERE c_domain='' AND c_active=1`))
if err != nil && err != sql.ErrNoRows {
err = errors.Wrap(err, "unable to execute select for empty subdomain")
}
@ -117,7 +120,7 @@ func (s Scope) GetOrganizationByDomain(subdomain string) (o org.Organization, er
}
// UpdateOrganization updates the given organization record in the database to the values supplied.
func (s Scope) UpdateOrganization(ctx domain.RequestContext, org org.Organization) (err error) {
func (s Store) UpdateOrganization(ctx domain.RequestContext, org org.Organization) (err error) {
org.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec(`UPDATE dmz_org SET
@ -134,14 +137,13 @@ func (s Scope) UpdateOrganization(ctx domain.RequestContext, org org.Organizatio
}
// DeleteOrganization deletes the orgID organization from the organization table.
func (s Scope) DeleteOrganization(ctx domain.RequestContext, orgID string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.Delete(ctx.Transaction, "dmz_org", orgID)
func (s Store) DeleteOrganization(ctx domain.RequestContext, orgID string) (rows int64, err error) {
return s.Delete(ctx.Transaction, "dmz_org", orgID)
}
// RemoveOrganization sets the orgID organization to be inactive, thus executing a "soft delete" operation.
func (s Scope) RemoveOrganization(ctx domain.RequestContext, orgID string) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_org SET c_active=0 WHERE c_refid=?", orgID)
func (s Store) RemoveOrganization(ctx domain.RequestContext, orgID string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_org SET c_active=0 WHERE c_refid=?"), orgID)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to execute soft delete for org %s", orgID))
@ -151,7 +153,7 @@ func (s Scope) RemoveOrganization(ctx domain.RequestContext, orgID string) (err
}
// UpdateAuthConfig updates the given organization record in the database with the auth config details.
func (s Scope) UpdateAuthConfig(ctx domain.RequestContext, org org.Organization) (err error) {
func (s Store) UpdateAuthConfig(ctx domain.RequestContext, org org.Organization) (err error) {
org.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec(`UPDATE dmz_org SET
@ -168,8 +170,8 @@ func (s Scope) UpdateAuthConfig(ctx domain.RequestContext, org org.Organization)
}
// CheckDomain makes sure there is an organisation with the correct domain
func (s Scope) CheckDomain(ctx domain.RequestContext, domain string) string {
row := s.Runtime.Db.QueryRow("SELECT COUNT(*) FROM dmz_org WHERE c_domain=? AND c_active=1", domain)
func (s Store) CheckDomain(ctx domain.RequestContext, domain string) string {
row := s.Runtime.Db.QueryRow(s.Bind("SELECT COUNT(*) FROM dmz_org WHERE c_domain=? AND c_active=1"), domain)
var count int
err := row.Scan(&count)
@ -177,7 +179,6 @@ func (s Scope) CheckDomain(ctx domain.RequestContext, domain string) string {
if err != nil {
return ""
}
if count == 1 {
return domain
}

View file

@ -9,23 +9,23 @@
//
// https://documize.com
package mysql
package page
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/page"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to organization (tenant) information.
type Store struct {
store.Context
domain.OrganizationStorer
}
//**************************************************
@ -33,7 +33,7 @@ type Scope struct {
//**************************************************
// Add inserts the given page into the page table, adds that page to the queue of pages to index and audits that the page has been added.
func (s Scope) Add(ctx domain.RequestContext, model page.NewPage) (err error) {
func (s Store) Add(ctx domain.RequestContext, model page.NewPage) (err error) {
model.Page.OrgID = ctx.OrgID
model.Page.UserID = ctx.UserID
model.Page.Created = time.Now().UTC()
@ -47,7 +47,9 @@ func (s Scope) Add(ctx domain.RequestContext, model page.NewPage) (err error) {
if model.Page.Sequence == 0 {
// Get maximum page sequence number and increment (used to be AND pagetype='section')
row := s.Runtime.Db.QueryRow("SELECT max(c_sequence) FROM dmz_section WHERE c_orgid=? AND c_docid=?", ctx.OrgID, model.Page.DocumentID)
row := s.Runtime.Db.QueryRow(s.Bind("SELECT max(c_sequence) FROM dmz_section WHERE c_orgid=? AND c_docid=?"),
ctx.OrgID, model.Page.DocumentID)
var maxSeq float64
err = row.Scan(&maxSeq)
if err != nil {
@ -57,10 +59,10 @@ func (s Scope) Add(ctx domain.RequestContext, model page.NewPage) (err error) {
model.Page.Sequence = maxSeq * 2
}
_, err = ctx.Transaction.Exec("INSERT INTO dmz_section (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) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_section (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) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
model.Page.RefID, model.Page.OrgID, model.Page.DocumentID, model.Page.UserID, model.Page.ContentType, model.Page.Type, model.Page.Level, model.Page.Name, model.Page.Body, model.Page.Revisions, model.Page.Sequence, model.Page.TemplateID, model.Page.Status, model.Page.RelativeID, model.Page.Created, model.Page.Revised)
_, err = ctx.Transaction.Exec("INSERT INTO dmz_section_meta (c_sectionid, c_orgid, c_userid, c_docid, c_rawbody, c_config, c_external, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_section_meta (c_sectionid, c_orgid, c_userid, c_docid, c_rawbody, c_config, c_external, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)"),
model.Meta.SectionID, model.Meta.OrgID, model.Meta.UserID, model.Meta.DocumentID, model.Meta.RawBody, model.Meta.Config, model.Meta.ExternalSource, model.Meta.Created, model.Meta.Revised)
if err != nil {
@ -71,13 +73,13 @@ func (s Scope) Add(ctx domain.RequestContext, model page.NewPage) (err error) {
}
// Get returns the pageID page record from the page table.
func (s Scope) Get(ctx domain.RequestContext, pageID string) (p page.Page, err error) {
err = s.Runtime.Db.Get(&p, `
func (s Store) Get(ctx domain.RequestContext, pageID string) (p page.Page, err error) {
err = s.Runtime.Db.Get(&p, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_docid AS documentid, c_userid AS userid, c_contenttype AS contenttype, c_type AS type,
c_level AS level, c_sequence AS sequence, c_name AS name, c_body AS body, c_revisions AS revisions, c_templateid AS templateid,
c_status AS status, c_relativeid AS relativeid, c_created AS created, c_revised AS revised
FROM dmz_section
WHERE c_orgid=? AND c_refid=?`,
WHERE c_orgid=? AND c_refid=?`),
ctx.OrgID, pageID)
if err != nil {
@ -88,14 +90,14 @@ func (s Scope) Get(ctx domain.RequestContext, pageID string) (p page.Page, err e
}
// GetPages returns a slice containing all published page records for a given documentID, in presentation sequence.
func (s Scope) GetPages(ctx domain.RequestContext, documentID string) (p []page.Page, err error) {
err = s.Runtime.Db.Select(&p, `
func (s Store) GetPages(ctx domain.RequestContext, documentID string) (p []page.Page, err error) {
err = s.Runtime.Db.Select(&p, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_docid AS documentid, c_userid AS userid, c_contenttype AS contenttype, c_type AS type,
c_level AS level, c_sequence AS sequence, c_name AS name, c_body AS body, c_revisions AS revisions, c_templateid AS templateid,
c_status AS status, c_relativeid AS relativeid, c_created AS created, c_revised AS revised
FROM dmz_section
WHERE c_orgid=? AND c_docid=? AND (c_status=0 OR ((c_status=4 OR c_status=2) AND c_relativeid=''))
ORDER BY c_sequence`,
ORDER BY c_sequence`),
ctx.OrgID, documentID)
if err != nil {
@ -106,14 +108,14 @@ func (s Scope) GetPages(ctx domain.RequestContext, documentID string) (p []page.
}
// GetUnpublishedPages returns a slice containing all published page records for a given documentID, in presentation sequence.
func (s Scope) GetUnpublishedPages(ctx domain.RequestContext, documentID string) (p []page.Page, err error) {
err = s.Runtime.Db.Select(&p, `
func (s Store) GetUnpublishedPages(ctx domain.RequestContext, documentID string) (p []page.Page, err error) {
err = s.Runtime.Db.Select(&p, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_docid AS documentid, c_userid AS userid, c_contenttype AS contenttype, c_type AS type,
c_level AS level, c_sequence AS sequence, c_name AS name, c_body AS body, c_revisions AS revisions, c_templateid AS templateid,
c_status AS status, c_relativeid AS relativeid, c_created AS created, c_revised AS revised
FROM dmz_section
WHERE c_orgid=? AND c_docid=? AND c_status!=0 AND c_relativeid!=''
ORDER BY c_sequence`,
ORDER BY c_sequence`),
ctx.OrgID, documentID)
if err != nil {
@ -125,14 +127,14 @@ func (s Scope) GetUnpublishedPages(ctx domain.RequestContext, documentID string)
// GetPagesWithoutContent returns a slice containing all the page records for a given documentID, in presentation sequence,
// but without the body field (which holds the HTML content).
func (s Scope) GetPagesWithoutContent(ctx domain.RequestContext, documentID string) (pages []page.Page, err error) {
err = s.Runtime.Db.Select(&pages, `
func (s Store) GetPagesWithoutContent(ctx domain.RequestContext, documentID string) (pages []page.Page, err error) {
err = s.Runtime.Db.Select(&pages, s.Bind(`
SELECT id, c_refid AS refid, c_orgid AS orgid, c_docid AS documentid, c_userid AS userid, c_contenttype AS contenttype, c_type AS type,
c_level AS level, c_sequence AS sequence, c_name AS name, c_revisions AS revisions, c_templateid AS templateid,
c_status AS status, c_relativeid AS relativeid, c_created AS created, c_revised AS revised
FROM dmz_section
WHERE c_orgid=? AND c_docid=? AND c_status=0
ORDER BY c_sequence`,
ORDER BY c_sequence`),
ctx.OrgID, documentID)
if err != nil {
@ -144,12 +146,12 @@ func (s Scope) GetPagesWithoutContent(ctx domain.RequestContext, documentID stri
// Update saves changes to the database and handles recording of revisions.
// Not all updates result in a revision being recorded hence the parameter.
func (s Scope) Update(ctx domain.RequestContext, page page.Page, refID, userID string, skipRevision bool) (err error) {
func (s Store) Update(ctx domain.RequestContext, page page.Page, refID, userID string, skipRevision bool) (err error) {
page.Revised = time.Now().UTC()
// Store revision history
if !skipRevision {
_, err = ctx.Transaction.Exec(`
_, err = ctx.Transaction.Exec(s.Bind(`
INSERT INTO dmz_section_revision
(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)
@ -157,7 +159,7 @@ func (s Scope) Update(ctx domain.RequestContext, page page.Page, refID, userID s
? AS userid, a.c_contenttype, a.c_type, a.c_name, a.c_body,
b.c_rawbody, b.c_config, ? AS c_created, ? As c_revised
FROM dmz_section a, dmz_section_meta b
WHERE a.c_refid=? AND a.c_refid=b.c_sectionid`,
WHERE a.c_refid=? AND a.c_refid=b.c_sectionid`),
refID, userID, time.Now().UTC(), time.Now().UTC(), page.RefID)
if err != nil {
@ -181,8 +183,8 @@ func (s Scope) Update(ctx domain.RequestContext, page page.Page, refID, userID s
// Update revisions counter
if !skipRevision {
_, err = ctx.Transaction.Exec(`UPDATE dmz_section SET c_revisions=c_revisions+1
WHERE c_orgid=? AND c_refid=?`,
_, err = ctx.Transaction.Exec(s.Bind(`UPDATE dmz_section SET c_revisions=c_revisions+1
WHERE c_orgid=? AND c_refid=?`),
ctx.OrgID, page.RefID)
if err != nil {
@ -195,16 +197,14 @@ func (s Scope) Update(ctx domain.RequestContext, page page.Page, refID, userID s
// Delete deletes the pageID page in the document.
// It then propagates that change into the search table, adds a delete the page revisions history, and audits that the page has been removed.
func (s Scope) Delete(ctx domain.RequestContext, documentID, pageID string) (rows int64, err error) {
b := mysql.BaseQuery{}
rows, err = b.DeleteConstrained(ctx.Transaction, "dmz_section", ctx.OrgID, pageID)
func (s Store) Delete(ctx domain.RequestContext, documentID, pageID string) (rows int64, err error) {
rows, err = s.DeleteConstrained(ctx.Transaction, "dmz_section", ctx.OrgID, pageID)
if err == nil {
_, _ = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_meta WHERE c_orgid='%s' AND c_sectionid='%s'", ctx.OrgID, pageID))
_, _ = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_meta WHERE c_orgid='%s' AND c_sectionid='%s'", ctx.OrgID, pageID))
}
if err == nil {
_, _ = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_action WHERE c_orgid='%s' AND c_reftypeid='%s' AND c_reftype='P'", ctx.OrgID, pageID))
_, _ = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_action WHERE c_orgid='%s' AND c_reftypeid='%s' AND c_reftype='P'", ctx.OrgID, pageID))
}
return
@ -215,7 +215,7 @@ func (s Scope) Delete(ctx domain.RequestContext, documentID, pageID string) (row
//**************************************************
// UpdateMeta persists meta information associated with a document page.
func (s Scope) UpdateMeta(ctx domain.RequestContext, meta page.Meta, updateUserID bool) (err error) {
func (s Store) UpdateMeta(ctx domain.RequestContext, meta page.Meta, updateUserID bool) (err error) {
meta.Revised = time.Now().UTC()
if updateUserID {
@ -236,13 +236,13 @@ func (s Scope) UpdateMeta(ctx domain.RequestContext, meta page.Meta, updateUserI
}
// GetPageMeta returns the meta information associated with the page.
func (s Scope) GetPageMeta(ctx domain.RequestContext, pageID string) (meta page.Meta, err error) {
err = s.Runtime.Db.Get(&meta, `SELECT id, c_sectionid AS sectionid,
func (s Store) GetPageMeta(ctx domain.RequestContext, pageID string) (meta page.Meta, err error) {
err = s.Runtime.Db.Get(&meta, s.Bind(`SELECT id, c_sectionid AS sectionid,
c_orgid AS orgid, c_userid AS userid, c_docid AS documentid,
c_rawbody AS rawbody, coalesce(c_config,JSON_UNQUOTE('{}')) as config,
c_rawbody AS rawbody, coalesce(c_config,`+s.EmptyJSON()+`) as config,
c_external AS externalsource, c_created AS created, c_revised AS revised
FROM dmz_section_meta
WHERE c_orgid=? AND c_sectionid=?`,
WHERE c_orgid=? AND c_sectionid=?`),
ctx.OrgID, pageID)
if err != nil && err != sql.ErrNoRows {
@ -253,18 +253,18 @@ func (s Scope) GetPageMeta(ctx domain.RequestContext, pageID string) (meta page.
}
// GetDocumentPageMeta returns the meta information associated with a document.
func (s Scope) GetDocumentPageMeta(ctx domain.RequestContext, documentID string, externalSourceOnly bool) (meta []page.Meta, err error) {
func (s Store) GetDocumentPageMeta(ctx domain.RequestContext, documentID string, externalSourceOnly bool) (meta []page.Meta, err error) {
filter := ""
if externalSourceOnly {
filter = " AND c_external=1"
}
err = s.Runtime.Db.Select(&meta, `SELECT id, c_sectionid AS sectionid,
err = s.Runtime.Db.Select(&meta, s.Bind(`SELECT id, c_sectionid AS sectionid,
c_orgid AS orgid, c_userid AS userid, c_docid AS documentid,
c_rawbody AS rawbody, coalesce(c_config,JSON_UNQUOTE('{}')) as config,
c_rawbody AS rawbody, coalesce(c_config,`+s.EmptyJSON()+`) as config,
c_external AS externalsource, c_created AS created, c_revised AS revised
FROM dmz_section_meta
WHERE c_orgid=? AND c_docid=?`+filter,
WHERE c_orgid=? AND c_docid=?`+filter),
ctx.OrgID, documentID)
if err != nil {
@ -280,8 +280,8 @@ func (s Scope) GetDocumentPageMeta(ctx domain.RequestContext, documentID string,
// UpdateSequence changes the presentation sequence of the pageID page in the document.
// It then propagates that change into the search table and audits that it has occurred.
func (s Scope) UpdateSequence(ctx domain.RequestContext, documentID, pageID string, sequence float64) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_section SET c_sequence=? WHERE c_orgid=? AND c_refid=?",
func (s Store) UpdateSequence(ctx domain.RequestContext, documentID, pageID string, sequence float64) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_section SET c_sequence=? WHERE c_orgid=? AND c_refid=?"),
sequence, ctx.OrgID, pageID)
if err != nil {
@ -293,8 +293,8 @@ func (s Scope) UpdateSequence(ctx domain.RequestContext, documentID, pageID stri
// UpdateLevel changes the heading level of the pageID page in the document.
// It then propagates that change into the search table and audits that it has occurred.
func (s Scope) UpdateLevel(ctx domain.RequestContext, documentID, pageID string, level int) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_section SET c_level=? WHERE c_orgid=? AND c_refid=?",
func (s Store) UpdateLevel(ctx domain.RequestContext, documentID, pageID string, level int) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_section SET c_level=? WHERE c_orgid=? AND c_refid=?"),
level, ctx.OrgID, pageID)
if err != nil {
@ -305,8 +305,8 @@ func (s Scope) UpdateLevel(ctx domain.RequestContext, documentID, pageID string,
}
// UpdateLevelSequence changes page level and sequence numbers.
func (s Scope) UpdateLevelSequence(ctx domain.RequestContext, documentID, pageID string, level int, sequence float64) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_section SET c_level=?, c_sequence=? WHERE c_orgid=? AND c_refid=?",
func (s Store) UpdateLevelSequence(ctx domain.RequestContext, documentID, pageID string, level int, sequence float64) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_section SET c_level=?, c_sequence=? WHERE c_orgid=? AND c_refid=?"),
level, sequence, ctx.OrgID, pageID)
if err != nil {
@ -317,8 +317,8 @@ func (s Scope) UpdateLevelSequence(ctx domain.RequestContext, documentID, pageID
}
// GetNextPageSequence returns the next sequence numbner to use for a page in given document.
func (s Scope) GetNextPageSequence(ctx domain.RequestContext, documentID string) (maxSeq float64, err error) {
row := s.Runtime.Db.QueryRow("SELECT max(c_sequence) FROM dmz_section WHERE c_orgid=? AND c_docid=?",
func (s Store) GetNextPageSequence(ctx domain.RequestContext, documentID string) (maxSeq float64, err error) {
row := s.Runtime.Db.QueryRow(s.Bind("SELECT max(c_sequence) FROM dmz_section WHERE c_orgid=? AND c_docid=?"),
ctx.OrgID, documentID)
err = row.Scan(&maxSeq)
@ -335,14 +335,15 @@ func (s Scope) GetNextPageSequence(ctx domain.RequestContext, documentID string)
//**************************************************
// GetPageRevision returns the revisionID page revision record.
func (s Scope) GetPageRevision(ctx domain.RequestContext, revisionID string) (revision page.Revision, err error) {
err = s.Runtime.Db.Get(&revision, `SELECT id, c_refid AS refid,
func (s Store) GetPageRevision(ctx domain.RequestContext, revisionID string) (revision page.Revision, err error) {
err = s.Runtime.Db.Get(&revision, s.Bind(`SELECT id, c_refid AS refid,
c_orgid AS orgid, c_docid AS documentid, c_ownerid AS ownerid, c_sectionid AS sectionid,
c_userid AS userid, c_contenttype AS contenttype, c_type AS type,
c_name AS name, c_body AS body, coalesce(c_rawbody, '') as rawbody, coalesce(c_config,JSON_UNQUOTE('{}')) as config,
c_name AS name, c_body AS body, coalesce(c_rawbody, '') as rawbody,
coalesce(c_config,`+s.EmptyJSON()+`) as config,
c_created AS created, c_revised AS revised
FROM dmz_section_revision
WHERE c_orgid=? and c_refid=?`,
WHERE c_orgid=? and c_refid=?`),
ctx.OrgID, revisionID)
if err != nil {
@ -354,9 +355,10 @@ func (s Scope) GetPageRevision(ctx domain.RequestContext, revisionID string) (re
// GetPageRevisions returns a slice of page revision records for a given pageID, in the order they were created.
// Then audits that the get-page-revisions action has occurred.
func (s Scope) GetPageRevisions(ctx domain.RequestContext, pageID string) (revisions []page.Revision, err error) {
err = s.Runtime.Db.Select(&revisions, `SELECT a.id, a.c_refid AS refid,
a.c_orgid AS orgid, a.c_docid AS documentid, a.c_ownerid AS ownerid, a.c_sectionid AS sectionid, a.c_userid AS userid,
func (s Store) GetPageRevisions(ctx domain.RequestContext, pageID string) (revisions []page.Revision, err error) {
err = s.Runtime.Db.Select(&revisions, s.Bind(`SELECT a.id, a.c_refid AS refid,
a.c_orgid AS orgid, a.c_docid AS documentid, a.c_ownerid AS ownerid, a.c_sectionid AS sectionid,
a.c_userid AS userid,
a.c_contenttype AS contenttype, a.c_type AS type, a.c_name AS name,
a.c_created AS created, a.c_revised AS revised,
coalesce(b.c_email,'') as email, coalesce(b.c_firstname,'') as firstname,
@ -364,7 +366,7 @@ func (s Scope) GetPageRevisions(ctx domain.RequestContext, pageID string) (revis
FROM dmz_section_revision a
LEFT JOIN dmz_user b ON a.c_userid=b.c_refid
WHERE a.c_orgid=? AND a.c_sectionid=? AND a.c_type='section'
ORDER BY a.id DESC`,
ORDER BY a.id DESC`),
ctx.OrgID, pageID)
if err != nil {
@ -376,8 +378,8 @@ func (s Scope) GetPageRevisions(ctx domain.RequestContext, pageID string) (revis
// GetDocumentRevisions returns a slice of page revision records for a given document, in the order they were created.
// Then audits that the get-page-revisions action has occurred.
func (s Scope) GetDocumentRevisions(ctx domain.RequestContext, documentID string) (revisions []page.Revision, err error) {
err = s.Runtime.Db.Select(&revisions, `SELECT a.id, a.c_refid AS refid,
func (s Store) GetDocumentRevisions(ctx domain.RequestContext, documentID string) (revisions []page.Revision, err error) {
err = s.Runtime.Db.Select(&revisions, s.Bind(`SELECT a.id, a.c_refid AS refid,
a.c_orgid AS orgid, a.c_docid AS documentid, a.c_ownerid AS ownerid, a.c_sectionid AS sectionid,
a.c_userid AS userid, a.c_contenttype AS contenttype, a.c_type AS type, a.c_name AS name,
a.c_created AS created, a.c_revised AS revised,
@ -388,7 +390,7 @@ func (s Scope) GetDocumentRevisions(ctx domain.RequestContext, documentID string
LEFT JOIN dmz_user b ON a.c_userid=b.c_refid
LEFT JOIN dmz_section p ON a.c_sectionid=p.c_refid
WHERE a.c_orgid=? AND a.c_docid=? AND a.c_type='section'
ORDER BY a.id DESC`,
ORDER BY a.id DESC`),
ctx.OrgID, documentID)
if len(revisions) == 0 {
@ -403,9 +405,8 @@ func (s Scope) GetDocumentRevisions(ctx domain.RequestContext, documentID string
}
// DeletePageRevisions deletes all of the page revision records for a given pageID.
func (s Scope) DeletePageRevisions(ctx domain.RequestContext, pageID string) (rows int64, err error) {
b := mysql.BaseQuery{}
rows, err = b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_revision WHERE c_orgid='%s' AND c_sectionid='%s'",
func (s Store) DeletePageRevisions(ctx domain.RequestContext, pageID string) (rows int64, err error) {
rows, err = s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_section_revision WHERE c_orgid='%s' AND c_sectionid='%s'",
ctx.OrgID, pageID))
return

View file

@ -9,32 +9,31 @@
//
// https://documize.com
// Package mysql handles data persistence for space and document permissions.
package mysql
package permission
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/permission"
"github.com/documize/community/model/user"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to user permission information.
type Store struct {
store.Context
domain.PermissionStorer
}
// AddPermission inserts the given record into the permisssion table.
func (s Scope) AddPermission(ctx domain.RequestContext, r permission.Permission) (err error) {
func (s Store) AddPermission(ctx domain.RequestContext, r permission.Permission) (err error) {
r.Created = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_permission (c_orgid, c_who, c_whoid, c_action, c_scope, c_location, c_refid, c_created) VALUES (?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_permission (c_orgid, c_who, c_whoid, c_action, c_scope, c_location, c_refid, c_created) VALUES (?, ?, ?, ?, ?, ?, ?, ?)"),
r.OrgID, string(r.Who), r.WhoID, string(r.Action), string(r.Scope), string(r.Location), r.RefID, r.Created)
if err != nil {
@ -45,7 +44,7 @@ func (s Scope) AddPermission(ctx domain.RequestContext, r permission.Permission)
}
// AddPermissions inserts records into permission database table, one per action.
func (s Scope) AddPermissions(ctx domain.RequestContext, r permission.Permission, actions ...permission.Action) (err error) {
func (s Store) AddPermissions(ctx domain.RequestContext, r permission.Permission, actions ...permission.Action) (err error) {
for _, a := range actions {
r.Action = a
@ -61,10 +60,10 @@ func (s Scope) AddPermissions(ctx domain.RequestContext, r permission.Permission
// GetUserSpacePermissions returns space permissions for user.
// Context is used to for userID because must match by userID
// or everyone ID of 0.
func (s Scope) GetUserSpacePermissions(ctx domain.RequestContext, spaceID string) (r []permission.Permission, err error) {
func (s Store) GetUserSpacePermissions(ctx domain.RequestContext, spaceID string) (r []permission.Permission, err error) {
r = []permission.Permission{}
err = s.Runtime.Db.Select(&r, `
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT id, c_orgid AS orgid, c_who AS who, c_whoid AS whoid, c_action AS action,
c_scope AS scope, c_location AS location, c_refid AS refid
FROM dmz_permission
@ -73,7 +72,7 @@ func (s Scope) GetUserSpacePermissions(ctx domain.RequestContext, spaceID string
SELECT p.id, p.c_orgid AS orgid, p.c_who AS who, p.c_whoid AS whoid, p.c_action AS action, p.c_scope AS scope, p.c_location AS location, p.c_refid AS refid
FROM dmz_permission p
LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_location='space' AND c_refid=? AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`,
WHERE p.c_orgid=? AND p.c_location='space' AND c_refid=? AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`),
ctx.OrgID, spaceID, ctx.UserID, ctx.OrgID, spaceID, ctx.UserID)
if err == sql.ErrNoRows {
@ -87,10 +86,10 @@ func (s Scope) GetUserSpacePermissions(ctx domain.RequestContext, spaceID string
}
// GetSpacePermissionsForUser returns space permissions for specified user.
func (s Scope) GetSpacePermissionsForUser(ctx domain.RequestContext, spaceID, userID string) (r []permission.Permission, err error) {
func (s Store) GetSpacePermissionsForUser(ctx domain.RequestContext, spaceID, userID string) (r []permission.Permission, err error) {
r = []permission.Permission{}
err = s.Runtime.Db.Select(&r, `
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT id, c_orgid AS orgid, c_who AS who, c_whoid AS whoid, c_action AS action, c_scope AS scope, c_location AS location, c_refid AS refid
FROM dmz_permission
WHERE c_orgid=? AND c_location='space' AND c_refid=? AND c_who='user' AND (c_whoid=? OR c_whoid='0')
@ -98,7 +97,7 @@ func (s Scope) GetSpacePermissionsForUser(ctx domain.RequestContext, spaceID, us
SELECT p.id, p.c_orgid AS orgid, p.c_who AS who, p.c_whoid AS whoid, p.c_action AS action, p.c_scope AS scope, p.c_location AS location, p.c_refid AS refid
FROM dmz_permission p
LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_location='space' AND c_refid=? AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`,
WHERE p.c_orgid=? AND p.c_location='space' AND c_refid=? AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`),
ctx.OrgID, spaceID, userID, ctx.OrgID, spaceID, userID)
if err == sql.ErrNoRows {
@ -113,13 +112,13 @@ func (s Scope) GetSpacePermissionsForUser(ctx domain.RequestContext, spaceID, us
// GetSpacePermissions returns space permissions for all users.
// We do not filter by userID because we return permissions for all users.
func (s Scope) GetSpacePermissions(ctx domain.RequestContext, spaceID string) (r []permission.Permission, err error) {
func (s Store) GetSpacePermissions(ctx domain.RequestContext, spaceID string) (r []permission.Permission, err error) {
r = []permission.Permission{}
err = s.Runtime.Db.Select(&r, `
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT id, c_orgid AS orgid, c_who AS who, c_whoid AS whoid, c_action AS action, c_scope AS scope, c_location AS location, c_refid AS refid
FROM dmz_permission
WHERE c_orgid=? AND c_location='space' AND c_refid=?`,
WHERE c_orgid=? AND c_location='space' AND c_refid=?`),
ctx.OrgID, spaceID)
if err == sql.ErrNoRows {
@ -133,10 +132,10 @@ func (s Scope) GetSpacePermissions(ctx domain.RequestContext, spaceID string) (r
}
// GetCategoryPermissions returns category permissions for all users.
func (s Scope) GetCategoryPermissions(ctx domain.RequestContext, catID string) (r []permission.Permission, err error) {
func (s Store) GetCategoryPermissions(ctx domain.RequestContext, catID string) (r []permission.Permission, err error) {
r = []permission.Permission{}
err = s.Runtime.Db.Select(&r, `
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT id, c_orgid AS orgid, c_who AS who, c_whoid AS whoid, c_action AS action, c_scope AS scope, c_location AS location, c_refid AS refid
FROM dmz_permission
WHERE c_orgid=? AND c_location='category' AND c_who='user' AND (c_refid=? OR c_refid='0')
@ -144,7 +143,7 @@ func (s Scope) GetCategoryPermissions(ctx domain.RequestContext, catID string) (
SELECT p.id, p.c_orgid AS orgid, p.c_who AS who, p.c_whoid AS whoid, p.c_action AS action, p.c_scope AS scope, p.c_location AS location, p.c_refid AS refid
FROM dmz_permission p
LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_location='category' AND p.c_who='role' AND (p.c_refid=? OR p.c_refid='0')`,
WHERE p.c_orgid=? AND p.c_location='category' AND p.c_who='role' AND (p.c_refid=? OR p.c_refid='0')`),
ctx.OrgID, catID, ctx.OrgID, catID)
if err == sql.ErrNoRows {
@ -158,11 +157,11 @@ func (s Scope) GetCategoryPermissions(ctx domain.RequestContext, catID string) (
}
// GetCategoryUsers returns space permissions for all users.
func (s Scope) GetCategoryUsers(ctx domain.RequestContext, catID string) (u []user.User, err error) {
func (s Store) GetCategoryUsers(ctx domain.RequestContext, catID string) (u []user.User, err error) {
u = []user.User{}
err = s.Runtime.Db.Select(&u, `
SELECT u.id, IFNULL(u.c_refid, '') AS refid, IFNULL(u.c_firstname, '') AS firstname, IFNULL(u.c_lastname, '') as lastname, u.email AS email, u.initials AS initials, u.password AS password, u.salt AS salt, u.c_reset AS reset, u.c_created AS created, u.c_revised AS revised
err = s.Runtime.Db.Select(&u, s.Bind(`
SELECT u.id, COALESCE(u.c_refid, '') AS refid, COALESCE(u.c_firstname, '') AS firstname, COALESCE(u.c_lastname, '') as lastname, u.email AS email, u.initials AS initials, u.password AS password, u.salt AS salt, u.c_reset AS reset, u.c_created AS created, u.c_revised AS revised
FROM dmz_user u
LEFT JOIN dmz_user_account a ON u.c_refid = a.c_userid
WHERE a.c_orgid=? AND a.c_active=1 AND u.c_refid IN (
@ -174,7 +173,7 @@ func (s Scope) GetCategoryUsers(ctx domain.RequestContext, catID string) (u []us
WHERE p.c_orgid=? AND p.c_who='role' AND p.c_location='category' AND p.c_refid=?
)
GROUP by u.id
ORDER BY firstname, lastname`,
ORDER BY firstname, lastname`),
ctx.OrgID, ctx.OrgID, catID, ctx.OrgID, catID)
if err == sql.ErrNoRows {
@ -189,10 +188,10 @@ func (s Scope) GetCategoryUsers(ctx domain.RequestContext, catID string) (u []us
}
// GetUserCategoryPermissions returns category permissions for given user.
func (s Scope) GetUserCategoryPermissions(ctx domain.RequestContext, userID string) (r []permission.Permission, err error) {
func (s Store) GetUserCategoryPermissions(ctx domain.RequestContext, userID string) (r []permission.Permission, err error) {
r = []permission.Permission{}
err = s.Runtime.Db.Select(&r, `
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT id, c_orgid AS orgid, c_who AS who, c_whoid AS whoid, c_action AS action, c_scope AS scope, c_location AS location, c_refid AS refid
FROM dmz_permission
WHERE c_orgid=? AND c_location='category' AND c_who='user' AND (c_whoid=? OR c_whoid='0')
@ -200,7 +199,7 @@ func (s Scope) GetUserCategoryPermissions(ctx domain.RequestContext, userID stri
SELECT p.id, p.c_orgid AS orgid, p.c_who AS who, p.c_whoid AS whoid, p.c_action AS action, p.c_scope AS scope, p.c_location AS location, p.c_refid AS refid
FROM dmz_permission p
LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_location='category' AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`,
WHERE p.c_orgid=? AND p.c_location='category' AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`),
ctx.OrgID, userID, ctx.OrgID, userID)
if err == sql.ErrNoRows {
@ -215,8 +214,8 @@ func (s Scope) GetUserCategoryPermissions(ctx domain.RequestContext, userID stri
// GetUserDocumentPermissions returns document permissions for user.
// Context is used to for user ID.
func (s Scope) GetUserDocumentPermissions(ctx domain.RequestContext, documentID string) (r []permission.Permission, err error) {
err = s.Runtime.Db.Select(&r, `
func (s Store) GetUserDocumentPermissions(ctx domain.RequestContext, documentID string) (r []permission.Permission, err error) {
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT id, c_orgid AS orgid, c_who AS who, c_whoid AS whoid, c_action AS action, c_scope AS scope, c_location AS location, c_refid AS refid
FROM dmz_permission
WHERE c_orgid=? AND c_location='document' AND c_refid=? AND c_who='user' AND (c_whoid=? OR c_whoid='0')
@ -224,7 +223,7 @@ func (s Scope) GetUserDocumentPermissions(ctx domain.RequestContext, documentID
SELECT p.id, p.c_orgid AS orgid, p.c_who AS who, p.c_whoid AS whoid, p.c_action AS action, p.c_scope AS scope, p.c_location AS location, p.c_refid AS refid
FROM dmz_permission p
LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_location='document' AND p.c_refid=? AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`,
WHERE p.c_orgid=? AND p.c_location='document' AND p.c_refid=? AND p.c_who='role' AND (r.c_userid=? OR r.c_userid='0')`),
ctx.OrgID, documentID, ctx.UserID, ctx.OrgID, documentID, ctx.OrgID)
if err == sql.ErrNoRows {
@ -240,8 +239,8 @@ func (s Scope) GetUserDocumentPermissions(ctx domain.RequestContext, documentID
// GetDocumentPermissions returns documents permissions for all users.
// We do not filter by userID because we return permissions for all users.
func (s Scope) GetDocumentPermissions(ctx domain.RequestContext, documentID string) (r []permission.Permission, err error) {
err = s.Runtime.Db.Select(&r, `
func (s Store) GetDocumentPermissions(ctx domain.RequestContext, documentID string) (r []permission.Permission, err error) {
err = s.Runtime.Db.Select(&r, s.Bind(`
SELECT id, c_orgid AS orgid, c_who AS who, c_whoid AS whoid, c_action AS action, c_scope AS scope, c_location AS location, c_refid AS refid
FROM dmz_permission
WHERE c_orgid=? AND c_location='document' AND c_refid=? AND c_who='user'
@ -249,7 +248,7 @@ func (s Scope) GetDocumentPermissions(ctx domain.RequestContext, documentID stri
SELECT p.id, p.c_orgid AS orgid, p.c_who AS who, p.c_whoid AS whoid, p.c_action AS action, p.c_scope AS scope, p.c_location AS location, p.c_refid AS refid
FROM dmz_permission p
LEFT JOIN dmz_group_member r ON p.c_whoid=r.c_groupid
WHERE p.c_orgid=? AND p.c_location='document' AND p.c_refid=? AND p.c_who='role'`,
WHERE p.c_orgid=? AND p.c_location='document' AND p.c_refid=? AND p.c_who='role'`),
ctx.OrgID, documentID, ctx.OrgID, documentID)
if err == sql.ErrNoRows {
@ -264,70 +263,56 @@ func (s Scope) GetDocumentPermissions(ctx domain.RequestContext, documentID stri
}
// DeleteDocumentPermissions removes records from dmz_permissions table for given document.
func (s Scope) DeleteDocumentPermissions(ctx domain.RequestContext, documentID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteDocumentPermissions(ctx domain.RequestContext, documentID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_permission WHERE c_orgid='%s' AND c_location='document' AND c_refid='%s'", ctx.OrgID, documentID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// DeleteSpacePermissions removes records from dmz_permissions table for given space ID.
func (s Scope) DeleteSpacePermissions(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteSpacePermissions(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_permission WHERE c_orgid='%s' AND c_location='space' AND c_refid='%s'", ctx.OrgID, spaceID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// DeleteUserSpacePermissions removes all roles for the specified user, for the specified space.
func (s Scope) DeleteUserSpacePermissions(ctx domain.RequestContext, spaceID, userID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteUserSpacePermissions(ctx domain.RequestContext, spaceID, userID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_permission WHERE c_orgid='%s' AND c_location='space' AND c_refid='%s' c_who='user' AND c_whoid='%s'",
ctx.OrgID, spaceID, userID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// DeleteUserPermissions removes all roles for the specified user, for the specified space.
func (s Scope) DeleteUserPermissions(ctx domain.RequestContext, userID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteUserPermissions(ctx domain.RequestContext, userID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_permission WHERE c_orgid='%s' AND c_who='user' AND c_whoid='%s'",
ctx.OrgID, userID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// DeleteCategoryPermissions removes records from dmz_permissions table for given category ID.
func (s Scope) DeleteCategoryPermissions(ctx domain.RequestContext, categoryID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteCategoryPermissions(ctx domain.RequestContext, categoryID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_permission WHERE c_orgid='%s' AND c_location='category' AND c_refid='%s'", ctx.OrgID, categoryID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// DeleteSpaceCategoryPermissions removes all category permission for for given space.
func (s Scope) DeleteSpaceCategoryPermissions(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteSpaceCategoryPermissions(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
sql := fmt.Sprintf(`
DELETE FROM dmz_permission WHERE c_orgid='%s' AND c_location='category'
AND c_refid IN (SELECT c_refid FROM dmz_category WHERE c_orgid='%s' AND c_spaceid='%s')`,
ctx.OrgID, ctx.OrgID, spaceID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}
// DeleteGroupPermissions removes all roles for the specified group
func (s Scope) DeleteGroupPermissions(ctx domain.RequestContext, groupID string) (rows int64, err error) {
b := mysql.BaseQuery{}
func (s Store) DeleteGroupPermissions(ctx domain.RequestContext, groupID string) (rows int64, err error) {
sql := fmt.Sprintf("DELETE FROM dmz_permission WHERE c_orgid='%s' AND c_who='role' AND c_whoid='%s'",
ctx.OrgID, groupID)
return b.DeleteWhere(ctx.Transaction, sql)
return s.DeleteWhere(ctx.Transaction, sql)
}

View file

@ -15,21 +15,22 @@ import (
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/pin"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to user permission information.
type Store struct {
store.Context
domain.PinStorer
}
// Add saves pinned item.
func (s Scope) Add(ctx domain.RequestContext, pin pin.Pin) (err error) {
row := s.Runtime.Db.QueryRow("SELECT max(c_sequence) FROM dmz_pin WHERE c_orgid=? AND c_userid=?", ctx.OrgID, ctx.UserID)
func (s Store) Add(ctx domain.RequestContext, pin pin.Pin) (err error) {
row := s.Runtime.Db.QueryRow(s.Bind("SELECT max(c_sequence) FROM dmz_pin WHERE c_orgid=? AND c_userid=?"),
ctx.OrgID, ctx.UserID)
var maxSeq int
err = row.Scan(&maxSeq)
@ -41,7 +42,7 @@ func (s Scope) Add(ctx domain.RequestContext, pin pin.Pin) (err error) {
pin.Revised = time.Now().UTC()
pin.Sequence = maxSeq + 1
_, err = ctx.Transaction.Exec("INSERT INTO dmz_pin (c_refid, c_orgid, c_userid, c_spaceid, c_docid, c_name, c_sequence, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_pin (c_refid, c_orgid, c_userid, c_spaceid, c_docid, c_name, c_sequence, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)"),
pin.RefID, pin.OrgID, pin.UserID, pin.SpaceID, pin.DocumentID, pin.Name, pin.Sequence, pin.Created, pin.Revised)
if err != nil {
@ -52,12 +53,12 @@ func (s Scope) Add(ctx domain.RequestContext, pin pin.Pin) (err error) {
}
// GetPin returns requested pinned item.
func (s Scope) GetPin(ctx domain.RequestContext, id string) (pin pin.Pin, err error) {
err = s.Runtime.Db.Get(&pin, `SELECT id, c_refid AS refid,
func (s Store) GetPin(ctx domain.RequestContext, id string) (pin pin.Pin, err error) {
err = s.Runtime.Db.Get(&pin, s.Bind(`SELECT id, c_refid AS refid,
c_orgid AS orgid, c_userid AS userid, c_spaceid AS spaceid, c_docid AS documentid,
c_name AS name, c_sequence AS sequence, c_created AS created, c_revised AS revised
FROM dmz_pin
WHERE c_orgid=? AND c_refid=?`,
WHERE c_orgid=? AND c_refid=?`),
ctx.OrgID, id)
if err != nil {
@ -68,13 +69,13 @@ func (s Scope) GetPin(ctx domain.RequestContext, id string) (pin pin.Pin, err er
}
// GetUserPins returns pinned items for specified user.
func (s Scope) GetUserPins(ctx domain.RequestContext, userID string) (pins []pin.Pin, err error) {
err = s.Runtime.Db.Select(&pins, `SELECT id, c_refid AS refid,
func (s Store) GetUserPins(ctx domain.RequestContext, userID string) (pins []pin.Pin, err error) {
err = s.Runtime.Db.Select(&pins, s.Bind(`SELECT id, c_refid AS refid,
c_orgid AS orgid, c_userid AS userid, c_spaceid AS spaceid, c_docid AS documentid,
c_name AS name, c_sequence AS sequence, c_created AS created, c_revised AS revised
FROM dmz_pin
WHERE c_orgid=? AND c_userid=?
ORDER BY c_sequence`,
ORDER BY c_sequence`),
ctx.OrgID, userID)
if err != nil {
@ -85,7 +86,7 @@ func (s Scope) GetUserPins(ctx domain.RequestContext, userID string) (pins []pin
}
// UpdatePin updates existing pinned item.
func (s Scope) UpdatePin(ctx domain.RequestContext, pin pin.Pin) (err error) {
func (s Store) UpdatePin(ctx domain.RequestContext, pin pin.Pin) (err error) {
pin.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec(`UPDATE dmz_pin SET
@ -101,8 +102,8 @@ func (s Scope) UpdatePin(ctx domain.RequestContext, pin pin.Pin) (err error) {
}
// UpdatePinSequence updates existing pinned item sequence number
func (s Scope) UpdatePinSequence(ctx domain.RequestContext, pinID string, sequence int) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_pin SET c_sequence=?, c_revised=? WHERE c_orgid=? AND c_userid=? AND c_refid=?",
func (s Store) UpdatePinSequence(ctx domain.RequestContext, pinID string, sequence int) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_pin SET c_sequence=?, c_revised=? WHERE c_orgid=? AND c_userid=? AND c_refid=?"),
sequence, time.Now().UTC(), ctx.OrgID, ctx.UserID, pinID)
if err != nil {
@ -113,19 +114,16 @@ func (s Scope) UpdatePinSequence(ctx domain.RequestContext, pinID string, sequen
}
// DeletePin removes folder from the store.
func (s Scope) DeletePin(ctx domain.RequestContext, id string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteConstrained(ctx.Transaction, "dmz_pin", ctx.OrgID, id)
func (s Store) DeletePin(ctx domain.RequestContext, id string) (rows int64, err error) {
return s.DeleteConstrained(ctx.Transaction, "dmz_pin", ctx.OrgID, id)
}
// DeletePinnedSpace removes any pins for specified space.
func (s Scope) DeletePinnedSpace(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_pin WHERE c_orgid=\"%s\" AND c_spaceid=\"%s\"", ctx.OrgID, spaceID))
func (s Store) DeletePinnedSpace(ctx domain.RequestContext, spaceID string) (rows int64, err error) {
return s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_pin WHERE c_orgid=\"%s\" AND c_spaceid=\"%s\"", ctx.OrgID, spaceID))
}
// DeletePinnedDocument removes any pins for specified document.
func (s Scope) DeletePinnedDocument(ctx domain.RequestContext, documentID string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_pin WHERE c_orgid=\"%s\" AND c_docid=\"%s\"", ctx.OrgID, documentID))
func (s Store) DeletePinnedDocument(ctx domain.RequestContext, documentID string) (rows int64, err error) {
return s.DeleteWhere(ctx.Transaction, fmt.Sprintf("DELETE FROM dmz_pin WHERE c_orgid=\"%s\" AND c_docid=\"%s\"", ctx.OrgID, documentID))
}

View file

@ -9,17 +9,17 @@
//
// https://documize.com
package mysql
package search
import (
"database/sql"
"fmt"
"strings"
"github.com/documize/community/core/env"
"github.com/documize/community/core/streamutil"
"github.com/documize/community/core/stringutil"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/attachment"
"github.com/documize/community/model/doc"
"github.com/documize/community/model/page"
@ -29,16 +29,17 @@ import (
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space information.
type Store struct {
store.Context
domain.SearchStorer
}
// IndexDocument adds search index entries for document inserting title, tags and attachments as
// searchable items. Any existing document entries are removed.
func (s Scope) IndexDocument(ctx domain.RequestContext, doc doc.Document, a []attachment.Attachment) (err error) {
func (s Store) IndexDocument(ctx domain.RequestContext, doc doc.Document, a []attachment.Attachment) (err error) {
// remove previous search entries
_, err = ctx.Transaction.Exec("DELETE FROM dmz_search WHERE c_orgid=? AND c_docid=? AND (c_itemtype='doc' OR c_itemtype='file' OR c_itemtype='tag')",
_, err = ctx.Transaction.Exec(s.Bind("DELETE FROM dmz_search WHERE c_orgid=? AND c_docid=? AND (c_itemtype='doc' OR c_itemtype='file' OR c_itemtype='tag')"),
ctx.OrgID, doc.RefID)
if err != nil {
@ -46,7 +47,7 @@ func (s Scope) IndexDocument(ctx domain.RequestContext, doc doc.Document, a []at
}
// insert doc title
_, err = ctx.Transaction.Exec("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)"),
ctx.OrgID, doc.RefID, "", "doc", doc.Name)
if err != nil {
err = errors.Wrap(err, "execute insert document title entry")
@ -59,7 +60,7 @@ func (s Scope) IndexDocument(ctx domain.RequestContext, doc doc.Document, a []at
continue
}
_, err = ctx.Transaction.Exec("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)"),
ctx.OrgID, doc.RefID, "", "tag", t)
if err != nil {
@ -69,7 +70,7 @@ func (s Scope) IndexDocument(ctx domain.RequestContext, doc doc.Document, a []at
}
for _, file := range a {
_, err = ctx.Transaction.Exec("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)"),
ctx.OrgID, doc.RefID, file.RefID, "file", file.Filename)
if err != nil {
@ -81,8 +82,9 @@ func (s Scope) IndexDocument(ctx domain.RequestContext, doc doc.Document, a []at
}
// DeleteDocument removes all search entries for document.
func (s Scope) DeleteDocument(ctx domain.RequestContext, ID string) (err error) {
_, err = ctx.Transaction.Exec("DELETE FROM dmz_search WHERE c_orgid=? AND c_docid=?", ctx.OrgID, ID)
func (s Store) DeleteDocument(ctx domain.RequestContext, ID string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("DELETE FROM dmz_search WHERE c_orgid=? AND c_docid=?"),
ctx.OrgID, ID)
if err != nil {
err = errors.Wrap(err, "execute delete document entries")
@ -93,14 +95,14 @@ func (s Scope) DeleteDocument(ctx domain.RequestContext, ID string) (err error)
// IndexContent adds search index entry for document context.
// Any existing document entries are removed.
func (s Scope) IndexContent(ctx domain.RequestContext, p page.Page) (err error) {
func (s Store) IndexContent(ctx domain.RequestContext, p page.Page) (err error) {
// we do not index pending pages
if p.Status == workflow.ChangePending || p.Status == workflow.ChangePendingNew {
return
}
// remove previous search entries
_, err = ctx.Transaction.Exec("DELETE FROM dmz_search WHERE c_orgid=? AND c_docid=? AND c_itemid=? AND c_itemtype='page'",
_, err = ctx.Transaction.Exec(s.Bind("DELETE FROM dmz_search WHERE c_orgid=? AND c_docid=? AND c_itemid=? AND c_itemtype='page'"),
ctx.OrgID, p.DocumentID, p.RefID)
if err != nil {
@ -115,13 +117,13 @@ func (s Scope) IndexContent(ctx domain.RequestContext, p page.Page) (err error)
}
content = strings.TrimSpace(content)
_, err = ctx.Transaction.Exec("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)"),
ctx.OrgID, p.DocumentID, p.RefID, "page", content)
if err != nil {
err = errors.Wrap(err, "execute insert document content entry")
}
_, err = ctx.Transaction.Exec("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_search (c_orgid, c_docid, c_itemid, c_itemtype, c_content) VALUES (?, ?, ?, ?, ?)"),
ctx.OrgID, p.DocumentID, p.RefID, "page", p.Name)
if err != nil {
err = errors.Wrap(err, "execute insert document page title entry")
@ -131,10 +133,10 @@ func (s Scope) IndexContent(ctx domain.RequestContext, p page.Page) (err error)
}
// DeleteContent removes all search entries for specific document content.
func (s Scope) DeleteContent(ctx domain.RequestContext, pageID string) (err error) {
func (s Store) DeleteContent(ctx domain.RequestContext, pageID string) (err error) {
// remove all search entries
var stmt1 *sqlx.Stmt
stmt1, err = ctx.Transaction.Preparex("DELETE FROM dmz_search WHERE c_orgid=? AND c_itemid=? AND c_itemtype=?")
stmt1, err = ctx.Transaction.Preparex(s.Bind("DELETE FROM dmz_search WHERE c_orgid=? AND c_itemid=? AND c_itemtype=?"))
defer streamutil.Close(stmt1)
if err != nil {
err = errors.Wrap(err, "prepare delete document content entry")
@ -152,7 +154,7 @@ func (s Scope) DeleteContent(ctx domain.RequestContext, pageID string) (err erro
// Documents searches the documents that the client is allowed to see, using the keywords search string, then audits that search.
// Visible documents include both those in the client's own organization and those that are public, or whose visibility includes the client.
func (s Scope) Documents(ctx domain.RequestContext, q search.QueryOptions) (results []search.QueryResult, err error) {
func (s Store) Documents(ctx domain.RequestContext, q search.QueryOptions) (results []search.QueryResult, err error) {
q.Keywords = strings.TrimSpace(q.Keywords)
if len(q.Keywords) == 0 {
return
@ -211,7 +213,7 @@ func (s Scope) Documents(ctx domain.RequestContext, q search.QueryOptions) (resu
return
}
func (s Scope) matchFullText(ctx domain.RequestContext, keywords, itemType string) (r []search.QueryResult, err error) {
func (s Store) matchFullText(ctx domain.RequestContext, keywords, itemType string) (r []search.QueryResult, err error) {
sql1 := `
SELECT
s.id, s.c_orgid AS orgid, s.c_docid AS documentid, s.c_itemid AS itemid, s.c_itemtype AS itemtype,
@ -261,7 +263,7 @@ func (s Scope) matchFullText(ctx domain.RequestContext, keywords, itemType strin
return
}
func (s Scope) matchLike(ctx domain.RequestContext, keywords, itemType string) (r []search.QueryResult, err error) {
func (s Store) matchLike(ctx domain.RequestContext, keywords, itemType string) (r []search.QueryResult, err error) {
// LIKE clause does not like quotes!
keywords = strings.Replace(keywords, "'", "", -1)
keywords = strings.Replace(keywords, "\"", "", -1)

View file

@ -80,16 +80,16 @@ func (h *Handler) SetSMTP(w http.ResponseWriter, r *http.Request) {
var config string
config = string(body)
ctx.Transaction, err = h.Runtime.Db.Beginx()
if err != nil {
response.WriteServerError(w, method, err)
h.Runtime.Log.Error(method, err)
return
}
// ctx.Transaction, err = h.Runtime.Db.Beginx()
// if err != nil {
// response.WriteServerError(w, method, err)
// h.Runtime.Log.Error(method, err)
// return
// }
h.Store.Setting.Set("SMTP", config)
ctx.Transaction.Commit()
// ctx.Transaction.Commit()
h.Store.Audit.Record(ctx, audit.EventTypeSystemSMTP)

View file

@ -9,33 +9,30 @@
//
// https://documize.com
package mysql
package setting
import (
"bytes"
"database/sql"
"fmt"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to user permission information.
type Store struct {
store.Context
domain.SettingStorer
}
// Get fetches a configuration JSON element from the config table.
func (s Scope) Get(area, path string) (value string, err error) {
if path != "" {
path = "." + path
}
sql := "SELECT JSON_EXTRACT(c_config,'$" + path + "') FROM dmz_config WHERE c_key = '" + area + "';"
func (s Store) Get(area, path string) (value string, err error) {
qry := fmt.Sprintf("SELECT %s FROM dmz_config WHERE c_key = '%s';", s.GetJSONValue("c_config", path), area)
var item = make([]uint8, 0)
err = s.Runtime.Db.Get(&item, sql)
err = s.Runtime.Db.Get(&item, qry)
if err != nil {
return "", err
}
@ -49,16 +46,33 @@ func (s Scope) Get(area, path string) (value string, err error) {
}
// Set writes a configuration JSON element to the config table.
func (s Scope) Set(area, json string) (err error) {
func (s Store) Set(area, json string) (err error) {
if area == "" {
return errors.New("no area")
}
sql := "INSERT INTO dmz_config (c_key,c_config) " +
"VALUES ('" + area + "','" + json +
"') ON DUPLICATE KEY UPDATE c_config='" + json + "';"
tx, err := s.Runtime.Db.Beginx()
if err != nil {
s.Runtime.Log.Error(fmt.Sprintf("setting.Set %s", area), err)
return
}
_, err = s.Runtime.Db.Exec(sql)
_, err = tx.Exec(fmt.Sprintf("DELETE FROM dmz_config WHERE c_key = '%s'", area))
if err != nil && err != sql.ErrNoRows {
tx.Rollback()
s.Runtime.Log.Error(fmt.Sprintf("setting.Set %s", area), err)
return err
}
_, err = tx.Exec(fmt.Sprintf("INSERT INTO dmz_config (c_key,c_config) VALUES ('%s','%s')",
area, json))
if err != nil && err != sql.ErrNoRows {
tx.Rollback()
s.Runtime.Log.Error(fmt.Sprintf("setting.Set %s", area), err)
return err
}
tx.Commit()
return err
}
@ -66,15 +80,11 @@ func (s Scope) Set(area, json string) (err error) {
// GetUser fetches a configuration JSON element from the userconfig table for a given orgid/userid combination.
// Errors return the empty string. A blank path returns the whole JSON object, as JSON.
// You can store org level settings by providing an empty user ID.
func (s Scope) GetUser(orgID, userID, key, path string) (value string, err error) {
func (s Store) GetUser(orgID, userID, key, path string) (value string, err error) {
var item = make([]uint8, 0)
if path != "" {
path = "." + path
}
qry := "SELECT JSON_EXTRACT(c_config,'$" + path + "') FROM dmz_user_config WHERE c_key = '" + key +
"' AND c_orgid = '" + orgID + "' AND c_userid = '" + userID + "';"
qry := fmt.Sprintf("SELECT %s FROM dmz_config WHERE c_key = '%s' AND c_orgid='%s' AND c_userid='%s';",
s.GetJSONValue("c_config", path), key, orgID, userID)
err = s.Runtime.Db.Get(&item, qry)
if err != nil && err != sql.ErrNoRows {
@ -91,7 +101,7 @@ func (s Scope) GetUser(orgID, userID, key, path string) (value string, err error
// SetUser writes a configuration JSON element to the userconfig table for the specified user.
// You can store org level settings by providing an empty user ID.
func (s Scope) SetUser(orgID, userID, key, json string) (err error) {
func (s Store) SetUser(orgID, userID, key, json string) (err error) {
if key == "" {
return errors.New("no key")
}
@ -101,16 +111,16 @@ func (s Scope) SetUser(orgID, userID, key, json string) (err error) {
return err
}
_, err = tx.Exec("DELETE FROM dmz_user_config WHERE c_orgid=? AND c_userid=? AND c_key=?", orgID, userID, key)
_, err = tx.Exec(s.Bind("DELETE FROM dmz_user_config WHERE c_orgid=? AND c_userid=? AND c_key=?"),
orgID, userID, key)
if err != nil {
fmt.Println(err)
fmt.Println("ccc")
}
_, err = tx.Exec("INSERT INTO dmz_user_config (c_orgid, c_userid, c_key, c_config) VALUES (?, ?, ?, ?)", orgID, userID, key, json)
_, err = tx.Exec(s.Bind("INSERT INTO dmz_user_config (c_orgid, c_userid, c_key, c_config) VALUES (?, ?, ?, ?)"),
orgID, userID, key, json)
if err != nil {
fmt.Println(err)
fmt.Println("ddd")
}
if err == nil {

View file

@ -9,67 +9,66 @@
//
// https://documize.com
// Package mysql handles data persistence for spaces.
package mysql
package space
import (
"database/sql"
"fmt"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store/mysql"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/space"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space information.
type Store struct {
store.Context
domain.SpaceStorer
}
// Add adds new folder into the store.
func (s Scope) Add(ctx domain.RequestContext, sp space.Space) (err error) {
func (s Store) Add(ctx domain.RequestContext, sp space.Space) (err error) {
sp.UserID = ctx.UserID
sp.Created = time.Now().UTC()
sp.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_space (c_refid, c_name, c_orgid, c_userid, c_type, c_lifecycle, c_likes, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_space (c_refid, c_name, c_orgid, c_userid, c_type, c_lifecycle, c_likes, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)"),
sp.RefID, sp.Name, sp.OrgID, sp.UserID, sp.Type, sp.Lifecycle, sp.Likes, sp.Created, sp.Revised)
if err != nil {
err = errors.Wrap(err, "unable to execute insert for label")
err = errors.Wrap(err, "unable to execute insert for space")
}
return
}
// Get returns a space from the store.
func (s Scope) Get(ctx domain.RequestContext, id string) (sp space.Space, err error) {
err = s.Runtime.Db.Get(&sp, `SELECT id, c_refid AS refid,
func (s Store) Get(ctx domain.RequestContext, id string) (sp space.Space, err error) {
err = s.Runtime.Db.Get(&sp, s.Bind(`SELECT id, c_refid AS refid,
c_name AS name, c_orgid AS orgid, c_userid AS userid,
c_type AS type, c_lifecycle AS lifecycle, c_likes AS likes,
c_created AS created, c_revised AS revised
FROM dmz_space
WHERE c_orgid=? and c_refid=?`,
WHERE c_orgid=? and c_refid=?`),
ctx.OrgID, id)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to execute select for label %s", id))
err = errors.Wrap(err, fmt.Sprintf("unable to execute select for space %s", id))
}
return
}
// PublicSpaces returns spaces that anyone can see.
func (s Scope) PublicSpaces(ctx domain.RequestContext, orgID string) (sp []space.Space, err error) {
qry := `SELECT id, c_refid AS refid,
func (s Store) PublicSpaces(ctx domain.RequestContext, orgID string) (sp []space.Space, err error) {
qry := s.Bind(`SELECT id, c_refid AS refid,
c_name AS name, c_orgid AS orgid, c_userid AS userid,
c_type AS type, c_lifecycle AS lifecycle, c_likes AS likes,
c_created AS created, c_revised AS revised
FROM dmz_space
WHERE c_orgid=? AND c_type=1`
WHERE c_orgid=? AND c_type=1`)
err = s.Runtime.Db.Select(&sp, qry, orgID)
@ -86,9 +85,8 @@ func (s Scope) PublicSpaces(ctx domain.RequestContext, orgID string) (sp []space
// GetViewable returns spaces that the user can see.
// Also handles which spaces can be seen by anonymous users.
func (s Scope) GetViewable(ctx domain.RequestContext) (sp []space.Space, err error) {
q := `
SELECT id, c_refid AS refid,
func (s Store) GetViewable(ctx domain.RequestContext) (sp []space.Space, err error) {
q := s.Bind(`SELECT id, c_refid AS refid,
c_name AS name, c_orgid AS orgid, c_userid AS userid,
c_type AS type, c_lifecycle AS lifecycle, c_likes AS likes,
c_created AS created, c_revised AS revised
@ -101,7 +99,7 @@ func (s Scope) GetViewable(ctx domain.RequestContext) (sp []space.Space, err err
AND p.c_location='space' AND p.c_action='view' AND (r.c_userid=? OR r.c_userid='0')
)
)
ORDER BY c_name`
ORDER BY c_name`)
err = s.Runtime.Db.Select(&sp, q,
ctx.OrgID,
@ -123,15 +121,14 @@ func (s Scope) GetViewable(ctx domain.RequestContext) (sp []space.Space, err err
}
// GetAll for admin users!
func (s Scope) GetAll(ctx domain.RequestContext) (sp []space.Space, err error) {
qry := `
SELECT id, c_refid AS refid,
func (s Store) GetAll(ctx domain.RequestContext) (sp []space.Space, err error) {
qry := s.Bind(`SELECT id, c_refid AS refid,
c_name AS name, c_orgid AS orgid, c_userid AS userid,
c_type AS type, c_lifecycle AS lifecycle, c_likes AS likes,
c_created AS created, c_revised AS revised
FROM dmz_space
WHERE c_orgid=?
ORDER BY c_name`
ORDER BY c_name`)
err = s.Runtime.Db.Select(&sp, qry, ctx.OrgID)
@ -147,19 +144,18 @@ func (s Scope) GetAll(ctx domain.RequestContext) (sp []space.Space, err error) {
}
// Update saves space changes.
func (s Scope) Update(ctx domain.RequestContext, sp space.Space) (err error) {
func (s Store) Update(ctx domain.RequestContext, sp space.Space) (err error) {
sp.Revised = time.Now().UTC()
_, err = ctx.Transaction.NamedExec("UPDATE dmz_space SET c_name=:name, c_type=:type, c_lifecycle=:lifecycle, c_userid=:userid, c_likes=:likes, c_revised=:revised WHERE c_orgid=:orgid AND c_refid=:refid", &sp)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to execute update for label %s", sp.RefID))
err = errors.Wrap(err, fmt.Sprintf("unable to execute update for space %s", sp.RefID))
}
return
}
// Delete removes space from the store.
func (s Scope) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
b := mysql.BaseQuery{}
return b.DeleteConstrained(ctx.Transaction, "dmz_space", ctx.OrgID, id)
func (s Store) Delete(ctx domain.RequestContext, id string) (rows int64, err error) {
return s.DeleteConstrained(ctx.Transaction, "dmz_space", ctx.OrgID, id)
}

107
domain/store/context.go Normal file
View file

@ -0,0 +1,107 @@
// 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 store
import (
"fmt"
"github.com/documize/community/core/env"
"github.com/jmoiron/sqlx"
"github.com/pkg/errors"
)
// Context provides common stuff to store providers.
type Context struct {
Runtime *env.Runtime
}
// Bind selects query parameter placeholder for given database provider.
//
// MySQL uses ?, ?, ? (default for all Documize queries)
// PostgreSQL uses $1, $2, $3
// MS SQL Server uses @p1, @p2, @p3
func (c *Context) Bind(sql string) string {
// Default to MySQL.
bindParam := sqlx.QUESTION
switch c.Runtime.StoreProvider.Type() {
case env.StoreTypePostgreSQL:
bindParam = sqlx.DOLLAR
}
return sqlx.Rebind(bindParam, sql)
}
// Delete record.
func (c *Context) Delete(tx *sqlx.Tx, table string, id string) (rows int64, err error) {
result, err := tx.Exec(c.Bind("DELETE FROM "+table+" WHERE c_refid=?"), id)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to delete row in table %s", table))
return
}
rows, err = result.RowsAffected()
return
}
// DeleteConstrained record constrained to Organization using refid.
func (c *Context) DeleteConstrained(tx *sqlx.Tx, table string, orgID, id string) (rows int64, err error) {
result, err := tx.Exec(c.Bind("DELETE FROM "+table+" WHERE c_orgid=? AND c_refid=?"), orgID, id)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to delete row in table %s", table))
return
}
rows, err = result.RowsAffected()
return
}
// DeleteConstrainedWithID record constrained to Organization using non refid.
func (c *Context) DeleteConstrainedWithID(tx *sqlx.Tx, table string, orgID, id string) (rows int64, err error) {
result, err := tx.Exec(c.Bind("DELETE FROM "+table+" WHERE c_orgid=? AND id=?"), orgID, id)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to delete row in table %s", table))
return
}
rows, err = result.RowsAffected()
return
}
// DeleteWhere free form query.
func (c *Context) DeleteWhere(tx *sqlx.Tx, statement string) (rows int64, err error) {
result, err := tx.Exec(statement)
if err != nil {
err = errors.Wrap(err, fmt.Sprintf("unable to delete rows: %s", statement))
return
}
rows, err = result.RowsAffected()
return
}
// EmptyJSON returns database specific empty JSON object.
func (c *Context) EmptyJSON() string {
return c.Runtime.StoreProvider.JSONEmpty()
}
// GetJSONValue returns database specific empty JSON object.
func (c *Context) GetJSONValue(column, attribute string) string {
return c.Runtime.StoreProvider.JSONGetValue(column, attribute)
}

View file

@ -9,7 +9,7 @@
//
// https://documize.com
package mysql
package user
import (
"database/sql"
@ -18,24 +18,25 @@ import (
"strings"
"time"
"github.com/documize/community/core/env"
"github.com/documize/community/domain"
"github.com/documize/community/domain/store"
"github.com/documize/community/model/user"
"github.com/jmoiron/sqlx"
"github.com/pkg/errors"
)
// Scope provides data access to MySQL.
type Scope struct {
Runtime *env.Runtime
// Store provides data access to space information.
type Store struct {
store.Context
domain.UserStorer
}
// Add adds the given user record to the user table.
func (s Scope) Add(ctx domain.RequestContext, u user.User) (err error) {
func (s Store) Add(ctx domain.RequestContext, u user.User) (err error) {
u.Created = time.Now().UTC()
u.Revised = time.Now().UTC()
_, err = ctx.Transaction.Exec("INSERT INTO dmz_user (c_refid, c_firstname, c_lastname, c_email, c_initials, c_password, c_salt, c_reset, c_lastversion, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)",
_, err = ctx.Transaction.Exec(s.Bind("INSERT INTO dmz_user (c_refid, c_firstname, c_lastname, c_email, c_initials, c_password, c_salt, c_reset, c_lastversion, c_created, c_revised) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"),
u.RefID, u.Firstname, u.Lastname, strings.ToLower(u.Email), u.Initials, u.Password, u.Salt, "", u.LastVersion, u.Created, u.Revised)
if err != nil {
@ -46,13 +47,13 @@ func (s Scope) Add(ctx domain.RequestContext, u user.User) (err error) {
}
// Get returns the user record for the given id.
func (s Scope) Get(ctx domain.RequestContext, id string) (u user.User, err error) {
err = s.Runtime.Db.Get(&u, `
func (s Store) Get(ctx domain.RequestContext, id string) (u user.User, err error) {
err = s.Runtime.Db.Get(&u, s.Bind(`
SELECT id, c_refid AS refid, c_firstname AS firstname, c_lastname AS lastname, c_email AS email,
c_initials AS initials, c_globaladmin AS globaladmin, c_password AS password, c_salt AS salt, c_reset AS reset,
c_lastversion AS lastversion, c_created AS created, c_revised AS revised
FROM dmz_user
WHERE c_refid=?`,
WHERE c_refid=?`),
id)
if err != nil {
@ -63,16 +64,16 @@ func (s Scope) Get(ctx domain.RequestContext, id string) (u user.User, err error
}
// GetByDomain matches user by email and domain.
func (s Scope) GetByDomain(ctx domain.RequestContext, domain, email string) (u user.User, err error) {
func (s Store) GetByDomain(ctx domain.RequestContext, domain, email string) (u user.User, err error) {
email = strings.TrimSpace(strings.ToLower(email))
err = s.Runtime.Db.Get(&u, `SELECT u.id, u.c_refid AS refid,
err = s.Runtime.Db.Get(&u, s.Bind(`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
u.c_password AS password, u.c_salt AS salt, u.c_reset AS reset, u.c_lastversion AS lastversion,
u.c_created AS created, u.c_revised AS revised
FROM dmz_user u, dmz_user_account a, dmz_org o
WHERE TRIM(LOWER(u.c_email))=? AND u.c_refid=a.c_userid AND a.c_orgid=o.c_refid AND TRIM(LOWER(o.c_domain))=?`,
WHERE TRIM(LOWER(u.c_email))=? AND u.c_refid=a.c_userid AND a.c_orgid=o.c_refid AND TRIM(LOWER(o.c_domain))=?`),
email, domain)
if err != nil && err != sql.ErrNoRows {
@ -83,16 +84,16 @@ func (s Scope) GetByDomain(ctx domain.RequestContext, domain, email string) (u u
}
// GetByEmail returns a single row match on email.
func (s Scope) GetByEmail(ctx domain.RequestContext, email string) (u user.User, err error) {
func (s Store) GetByEmail(ctx domain.RequestContext, email string) (u user.User, err error) {
email = strings.TrimSpace(strings.ToLower(email))
err = s.Runtime.Db.Get(&u, `SELECT u.id, u.c_refid AS refid,
err = s.Runtime.Db.Get(&u, s.Bind(`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
u.c_password AS password, u.c_salt AS salt, u.c_reset AS reset, u.c_lastversion AS lastversion,
u.c_created AS created, u.c_revised AS revised
FROM dmz_user u
WHERE TRIM(LOWER(u.c_email))=?`,
WHERE TRIM(LOWER(u.c_email))=?`),
email)
if err != nil && err != sql.ErrNoRows {
@ -103,14 +104,14 @@ func (s Scope) GetByEmail(ctx domain.RequestContext, email string) (u user.User,
}
// GetByToken returns a user record given a reset token value.
func (s Scope) GetByToken(ctx domain.RequestContext, token string) (u user.User, err error) {
err = s.Runtime.Db.Get(&u, `SELECT u.id, u.c_refid AS refid,
func (s Store) GetByToken(ctx domain.RequestContext, token string) (u user.User, err error) {
err = s.Runtime.Db.Get(&u, s.Bind(`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
u.c_password AS password, u.c_salt AS salt, u.c_reset AS reset, u.c_lastversion AS lastversion,
u.c_created AS created, u.c_revised AS revised
FROM dmz_user u
WHERE u.c_reset=?`,
WHERE u.c_reset=?`),
token)
if err != nil {
@ -123,14 +124,14 @@ func (s Scope) GetByToken(ctx domain.RequestContext, token string) (u user.User,
// GetBySerial is used to retrieve a user via their temporary password salt value!
// This occurs when we you share a folder with a new user and they have to complete
// the onboarding process.
func (s Scope) GetBySerial(ctx domain.RequestContext, serial string) (u user.User, err error) {
err = s.Runtime.Db.Get(&u, `SELECT u.id, u.c_refid AS refid,
func (s Store) GetBySerial(ctx domain.RequestContext, serial string) (u user.User, err error) {
err = s.Runtime.Db.Get(&u, s.Bind(`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
u.c_password AS password, u.c_salt AS salt, u.c_reset AS reset, u.c_lastversion AS lastversion,
u.c_created AS created, u.c_revised AS revised
FROM dmz_user u
WHERE u.c_salt=?`,
WHERE u.c_salt=?`),
serial)
if err != nil {
@ -142,10 +143,10 @@ func (s Scope) GetBySerial(ctx domain.RequestContext, serial string) (u user.Use
// GetActiveUsersForOrganization returns a slice containing of active user records for the organization
// identified in the Persister.
func (s Scope) GetActiveUsersForOrganization(ctx domain.RequestContext) (u []user.User, err error) {
func (s Store) GetActiveUsersForOrganization(ctx domain.RequestContext) (u []user.User, err error) {
u = []user.User{}
err = s.Runtime.Db.Select(&u, `SELECT u.id, u.c_refid AS refid,
err = s.Runtime.Db.Select(&u, s.Bind(`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
u.c_password AS password, u.c_salt AS salt, u.c_reset AS reset, u.c_lastversion AS lastversion,
@ -153,7 +154,7 @@ func (s Scope) GetActiveUsersForOrganization(ctx domain.RequestContext) (u []use
a.c_active AS active, a.c_editor AS editor, a.c_admin AS admin, a.c_users AS viewusers, a.c_analytics AS analytics
FROM dmz_user u, dmz_user_account a
WHERE u.c_refid=a.c_userid AND a.c_orgid=? AND a.c_active=1
ORDER BY u.c_firstname, u.c_lastname`,
ORDER BY u.c_firstname, u.c_lastname`),
ctx.OrgID)
if err == sql.ErrNoRows {
@ -168,7 +169,7 @@ func (s Scope) GetActiveUsersForOrganization(ctx domain.RequestContext) (u []use
// GetUsersForOrganization returns a slice containing all of the user records for the organizaiton
// identified in the context.
func (s Scope) GetUsersForOrganization(ctx domain.RequestContext, filter string, limit int) (u []user.User, err error) {
func (s Store) GetUsersForOrganization(ctx domain.RequestContext, filter string, limit int) (u []user.User, err error) {
u = []user.User{}
filter = strings.TrimSpace(strings.ToLower(filter))
@ -177,7 +178,7 @@ func (s Scope) GetUsersForOrganization(ctx domain.RequestContext, filter string,
likeQuery = " AND (LOWER(u.c_firstname) LIKE '%" + filter + "%' OR LOWER(u.c_lastname) LIKE '%" + filter + "%' OR LOWER(u.c_email) LIKE '%" + filter + "%') "
}
err = s.Runtime.Db.Select(&u, `SELECT u.id, u.c_refid AS refid,
err = s.Runtime.Db.Select(&u, s.Bind(`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
u.c_password AS password, u.c_salt AS salt, u.c_reset AS reset, u.c_lastversion AS lastversion,
@ -185,7 +186,7 @@ func (s Scope) GetUsersForOrganization(ctx domain.RequestContext, filter string,
a.c_active AS active, a.c_editor AS editor, a.c_admin AS admin, a.c_users AS viewusers, a.c_analytics AS analytics
FROM dmz_user u, dmz_user_account a
WHERE u.c_refid=a.c_userid AND a.c_orgid=? `+likeQuery+
`ORDER BY u.c_firstname, u.c_lastname LIMIT `+strconv.Itoa(limit), ctx.OrgID)
`ORDER BY u.c_firstname, u.c_lastname LIMIT `+strconv.Itoa(limit)), ctx.OrgID)
if err == sql.ErrNoRows {
err = nil
@ -199,10 +200,10 @@ func (s Scope) GetUsersForOrganization(ctx domain.RequestContext, filter string,
}
// GetSpaceUsers returns a slice containing all user records for given space.
func (s Scope) GetSpaceUsers(ctx domain.RequestContext, spaceID string) (u []user.User, err error) {
func (s Store) GetSpaceUsers(ctx domain.RequestContext, spaceID string) (u []user.User, err error) {
u = []user.User{}
err = s.Runtime.Db.Select(&u, `SELECT u.id, u.c_refid AS refid,
err = s.Runtime.Db.Select(&u, s.Bind(`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
u.c_password AS password, u.c_salt AS salt, u.c_reset AS reset, u.c_lastversion AS lastversion,
@ -214,7 +215,7 @@ func (s Scope) GetSpaceUsers(ctx domain.RequestContext, spaceID string) (u []use
UNION ALL
SELECT r.c_userid from dmz_group_member r LEFT JOIN dmz_permission p ON p.c_whoid=r.c_groupid WHERE p.c_orgid=? AND p.c_who='role' AND p.c_scope='object' AND p.c_location='space' AND p.c_refid=?
)
ORDER BY u.c_firstname, c_u.lastname`,
ORDER BY u.c_firstname, c_u.lastname`),
ctx.OrgID, ctx.OrgID, spaceID, ctx.OrgID, spaceID)
if err == sql.ErrNoRows {
@ -228,14 +229,14 @@ func (s Scope) GetSpaceUsers(ctx domain.RequestContext, spaceID string) (u []use
}
// GetUsersForSpaces returns users with access to specified spaces.
func (s Scope) GetUsersForSpaces(ctx domain.RequestContext, spaces []string) (u []user.User, err error) {
func (s Store) GetUsersForSpaces(ctx domain.RequestContext, spaces []string) (u []user.User, err error) {
u = []user.User{}
if len(spaces) == 0 {
return
}
query, args, err := sqlx.In(`
query, args, err := sqlx.In(s.Bind(`
SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
@ -248,7 +249,7 @@ func (s Scope) GetUsersForSpaces(ctx domain.RequestContext, spaces []string) (u
UNION ALL
SELECT r.c_userid from dmz_group_member r LEFT JOIN dmz_permission p ON p.c_whoid=r.c_groupid WHERE p.c_orgid=? AND p.c_who='role' AND p.c_scope='object' AND p.c_location='space' AND p.c_refid IN(?)
)
ORDER BY u.c_firstname, u.c_lastname`,
ORDER BY u.c_firstname, u.c_lastname`),
ctx.OrgID, ctx.OrgID, spaces, ctx.OrgID, spaces)
query = s.Runtime.Db.Rebind(query)
@ -265,7 +266,7 @@ func (s Scope) GetUsersForSpaces(ctx domain.RequestContext, spaces []string) (u
}
// UpdateUser updates the user table using the given replacement user record.
func (s Scope) UpdateUser(ctx domain.RequestContext, u user.User) (err error) {
func (s Store) UpdateUser(ctx domain.RequestContext, u user.User) (err error) {
u.Revised = time.Now().UTC()
u.Email = strings.ToLower(u.Email)
@ -278,8 +279,9 @@ func (s Scope) UpdateUser(ctx domain.RequestContext, u user.User) (err error) {
}
// UpdateUserPassword updates a user record with new password and salt values.
func (s Scope) UpdateUserPassword(ctx domain.RequestContext, userID, salt, password string) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_user SET c_salt=?, c_password=?, c_reset='' WHERE c_refid=?", salt, password, userID)
func (s Store) UpdateUserPassword(ctx domain.RequestContext, userID, salt, password string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_user SET c_salt=?, c_password=?, c_reset='' WHERE c_refid=?"),
salt, password, userID)
if err != nil {
err = errors.Wrap(err, "execute user update")
}
@ -288,8 +290,9 @@ func (s Scope) UpdateUserPassword(ctx domain.RequestContext, userID, salt, passw
}
// DeactiveUser deletes the account record for the given userID and persister.Context.OrgID.
func (s Scope) DeactiveUser(ctx domain.RequestContext, userID string) (err error) {
_, err = ctx.Transaction.Exec("DELETE FROM dmz_user_account WHERE c_userid=? and c_orgid=?", userID, ctx.OrgID)
func (s Store) DeactiveUser(ctx domain.RequestContext, userID string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("DELETE FROM dmz_user_account WHERE c_userid=? and c_orgid=?"),
userID, ctx.OrgID)
if err != nil {
err = errors.Wrap(err, "execute user deactivation")
}
@ -298,8 +301,9 @@ func (s Scope) DeactiveUser(ctx domain.RequestContext, userID string) (err error
}
// ForgotUserPassword sets the password to '' and the reset field to token, for a user identified by email.
func (s Scope) ForgotUserPassword(ctx domain.RequestContext, email, token string) (err error) {
_, err = ctx.Transaction.Exec("UPDATE dmz_user SET c_reset=?, c_password='' WHERE LOWER(c_email)=?", token, strings.ToLower(email))
func (s Store) ForgotUserPassword(ctx domain.RequestContext, email, token string) (err error) {
_, err = ctx.Transaction.Exec(s.Bind("UPDATE dmz_user SET c_reset=?, c_password='' WHERE LOWER(c_email)=?"),
token, strings.ToLower(email))
if err != nil {
err = errors.Wrap(err, "execute password reset")
}
@ -308,7 +312,7 @@ func (s Scope) ForgotUserPassword(ctx domain.RequestContext, email, token string
}
// CountActiveUsers returns the number of active users in the system.
func (s Scope) CountActiveUsers() (c int) {
func (s Store) CountActiveUsers() (c int) {
row := s.Runtime.Db.QueryRow("SELECT count(*) FROM dmz_user WHERE c_refid IN (SELECT c_userid FROM dmz_user_account WHERE c_active=1)")
err := row.Scan(&c)
@ -325,7 +329,7 @@ func (s Scope) CountActiveUsers() (c int) {
}
// MatchUsers returns users that have match to either firstname, lastname or email.
func (s Scope) MatchUsers(ctx domain.RequestContext, text string, maxMatches int) (u []user.User, err error) {
func (s Store) MatchUsers(ctx domain.RequestContext, text string, maxMatches int) (u []user.User, err error) {
u = []user.User{}
text = strings.TrimSpace(strings.ToLower(text))
@ -334,7 +338,7 @@ func (s Scope) MatchUsers(ctx domain.RequestContext, text string, maxMatches int
likeQuery = " AND (LOWER(c_firstname) LIKE '%" + text + "%' OR LOWER(c_lastname) LIKE '%" + text + "%' OR LOWER(c_email) LIKE '%" + text + "%') "
}
err = s.Runtime.Db.Select(&u,
err = s.Runtime.Db.Select(&u, s.Bind(
`SELECT u.id, u.c_refid AS refid,
u.c_firstname AS firstname, u.c_lastname AS lastname, u.c_email AS email,
u.c_initials AS initials, u.c_globaladmin AS globaladmin,
@ -342,7 +346,7 @@ func (s Scope) MatchUsers(ctx domain.RequestContext, text string, maxMatches int
u.c_created AS created, u.c_revised AS revised,
a.c_active AS active, a.c_editor AS editor, a.c_admin AS admin, a.c_users AS viewusers, a.c_analytics AS analytics
FROM dmz_user u, dmz_user_account a
WHERE a.c_orgid=? AND u.c_refid=a.c_userid AND a.c_active=1 `+likeQuery+` ORDER BY u.c_firstname, u.c_lastname LIMIT `+strconv.Itoa(maxMatches),
WHERE a.c_orgid=? AND u.c_refid=a.c_userid AND a.c_active=1 `+likeQuery+` ORDER BY u.c_firstname, u.c_lastname LIMIT `+strconv.Itoa(maxMatches)),
ctx.OrgID)
if err == sql.ErrNoRows {