import posts at least partially tested, we should do some more work on it - also, a few other bugs have been stomped
This commit is contained in:
Vendored
+8
@@ -19,5 +19,13 @@
|
||||
"program": "${workspaceFolder}",
|
||||
"args": ["-C", "${workspaceFolder}/test.yaml"]
|
||||
},
|
||||
{
|
||||
"name": "Import Test",
|
||||
"type": "go",
|
||||
"request": "launch",
|
||||
"mode": "auto",
|
||||
"program": "${workspaceFolder}",
|
||||
"args": ["-C", "${workspaceFolder}/test2.yaml"]
|
||||
},
|
||||
]
|
||||
}
|
||||
|
||||
+3
-4
@@ -782,11 +782,10 @@ func CreateCommunity(ctxt ui.AmContext) (string, any) {
|
||||
}
|
||||
var testcomm *database.Community
|
||||
testcomm, err = database.AmGetCommunityByAlias(ctxt.Ctx(), dlg.Field("alias").Value)
|
||||
if err != nil {
|
||||
return dlg.RenderError(ctxt, err.Error())
|
||||
}
|
||||
if testcomm != nil {
|
||||
if err == nil {
|
||||
return dlg.RenderError(ctxt, fmt.Sprintf("A community with the alias \"%s\" already exists; please try again.", testcomm.Alias))
|
||||
} else if err != database.ErrNoCommunity {
|
||||
return dlg.RenderError(ctxt, err.Error())
|
||||
}
|
||||
var hideDir, hideSearch bool
|
||||
switch dlg.Field("hidemode").Value {
|
||||
|
||||
+6
-1
@@ -765,6 +765,7 @@ func ConferenceImport(ctxt ui.AmContext) (string, any) {
|
||||
|
||||
if ctxt.Verb() == "GET" {
|
||||
ctxt.VarMap().Set("confName", conf.Name)
|
||||
ctxt.VarMap().Set("selfLink", fmt.Sprintf("/comm/%s/conf/%s/import", comm.Alias, ctxt.GetScratch("currentAlias")))
|
||||
ctxt.SetFrameTitle("Import Messages: " + conf.Name)
|
||||
return "framed", "conf_import.jet"
|
||||
}
|
||||
@@ -784,6 +785,7 @@ func ConferenceImport(ctxt ui.AmContext) (string, any) {
|
||||
default:
|
||||
ctxt.VarMap().Set("errorMessage", "Invalid matching parameter.")
|
||||
ctxt.VarMap().Set("confName", conf.Name)
|
||||
ctxt.VarMap().Set("selfLink", fmt.Sprintf("/comm/%s/conf/%s/import", comm.Alias, ctxt.GetScratch("currentAlias")))
|
||||
ctxt.SetFrameTitle("Import Messages: " + conf.Name)
|
||||
return "framed", "conf_import.jet"
|
||||
}
|
||||
@@ -792,6 +794,7 @@ func ConferenceImport(ctxt ui.AmContext) (string, any) {
|
||||
if err != nil {
|
||||
ctxt.VarMap().Set("errorMessage", err.Error())
|
||||
ctxt.VarMap().Set("confName", conf.Name)
|
||||
ctxt.VarMap().Set("selfLink", fmt.Sprintf("/comm/%s/conf/%s/import", comm.Alias, ctxt.GetScratch("currentAlias")))
|
||||
ctxt.SetFrameTitle("Import Messages: " + conf.Name)
|
||||
return "framed", "conf_import.jet"
|
||||
}
|
||||
@@ -799,6 +802,7 @@ func ConferenceImport(ctxt ui.AmContext) (string, any) {
|
||||
if err != nil {
|
||||
ctxt.VarMap().Set("errorMessage", err.Error())
|
||||
ctxt.VarMap().Set("confName", conf.Name)
|
||||
ctxt.VarMap().Set("selfLink", fmt.Sprintf("/comm/%s/conf/%s/import", comm.Alias, ctxt.GetScratch("currentAlias")))
|
||||
ctxt.SetFrameTitle("Import Messages: " + conf.Name)
|
||||
return "framed", "conf_import.jet"
|
||||
}
|
||||
@@ -807,11 +811,12 @@ func ConferenceImport(ctxt ui.AmContext) (string, any) {
|
||||
if err != nil {
|
||||
ctxt.VarMap().Set("errorMessage", err.Error())
|
||||
ctxt.VarMap().Set("confName", conf.Name)
|
||||
ctxt.VarMap().Set("selfLink", fmt.Sprintf("/comm/%s/conf/%s/import", comm.Alias, ctxt.GetScratch("currentAlias")))
|
||||
ctxt.SetFrameTitle("Import Messages: " + conf.Name)
|
||||
return "framed", "conf_import.jet"
|
||||
}
|
||||
|
||||
ctxt.VarMap().Set("backLink", "/sysadmin")
|
||||
ctxt.VarMap().Set("backLink", fmt.Sprintf("/comm/%s/conf/%s/manage", comm.Alias, ctxt.GetScratch("currentAlias")))
|
||||
ctxt.VarMap().Set("headline", fmt.Sprintf("Processed %d topic(s) and added %d new post(s).", topics, posts))
|
||||
ctxt.VarMap().Set("scroll", scroll)
|
||||
ctxt.SetFrameTitle("Import Results")
|
||||
|
||||
+19
-3
@@ -568,8 +568,17 @@ func (c *Conference) TouchPost(ctx context.Context, tx *sqlx.Tx, u *User, lastPo
|
||||
|
||||
// UnreadMessages returns the total number of unread messages in a conference for a user.
|
||||
func (c *Conference) UnreadMessages(ctx context.Context, u *User) (int32, error) {
|
||||
var count int32
|
||||
err := amdb.GetContext(ctx, &count, `SELECT COUNT(*) FROM topics t LEFT JOIN topicsettings s
|
||||
ON t.topicid = s.topicid AND s.uid = ? WHERE t.confid = ? AND t.archived = 0 AND (s.hidden IS NULL OR s.hidden = 0)`, u.Uid, c.ConfId)
|
||||
if err != nil {
|
||||
return -1, err
|
||||
}
|
||||
if count == 0 {
|
||||
return 0, nil
|
||||
}
|
||||
var rc int32
|
||||
err := amdb.GetContext(ctx, &rc, `SELECT SUM(t.top_message - IFNULL(s.last_message,-1))
|
||||
err = amdb.GetContext(ctx, &rc, `SELECT SUM(t.top_message - IFNULL(s.last_message,-1))
|
||||
FROM topics t LEFT JOIN topicsettings s ON t.topicid = s.topicid AND s.uid = ?
|
||||
WHERE t.confid = ? AND t.archived = 0 AND (s.hidden IS NULL OR s.hidden = 0)`, u.Uid, c.ConfId)
|
||||
return rc, err
|
||||
@@ -1284,10 +1293,17 @@ func AmCreateConference(ctx context.Context, comm *Community, name, alias, descr
|
||||
}
|
||||
|
||||
// Get the current "last" sequence number.
|
||||
var seq int
|
||||
if err = tx.GetContext(ctx, &seq, "SELECT MAX(sequence) FROM commtoconf WHERE commid = ?", comm.Id); err != nil {
|
||||
seq := 0
|
||||
count := 0
|
||||
if err = tx.GetContext(ctx, &count, "SELECT COUNT(*) FROM commtoconf WHERE commid = ?", comm.Id); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if count > 0 {
|
||||
if err = tx.GetContext(ctx, &seq, "SELECT MAX(sequence) FROM commtoconf WHERE commid = ?", comm.Id); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
// else assume we start with a 0 sequence
|
||||
|
||||
// Link the conference into the community, and set the hide flag.
|
||||
if _, err = tx.ExecContext(ctx, "INSERT INTO commtoconf (commid, confid, sequence, hide_list) VALUES (?, ?, ?, ?)", comm.Id, rc.ConfId,
|
||||
|
||||
+3
-1
@@ -757,9 +757,11 @@ func AmCreateNewUser(ctx context.Context, username string, password string, remi
|
||||
}
|
||||
|
||||
// Insert the user record.
|
||||
ecn := util.GenerateRandomConfirmationNumber()
|
||||
log.Debugf("generated E-mail confirmation number %d", ecn)
|
||||
_, err = tx.ExecContext(ctx, `INSERT INTO users (username, passhash, verify_email, lockout, email_confnum,
|
||||
base_lvl, created, lastaccess, passreminder, description, dob) VALUES (?, ?, 0, 0, ?, ?, NOW(), NOW(), ?, '', ?)`,
|
||||
username, hashPassword(password), util.GenerateRandomConfirmationNumber(), AmDefaultRole("Global.NewUser").Level(),
|
||||
username, hashPassword(password), ecn, AmDefaultRole("Global.NewUser").Level(),
|
||||
reminder, dob)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
||||
@@ -61,7 +61,7 @@ CREATE TABLE users (
|
||||
verify_email TINYINT DEFAULT 0,
|
||||
lockout TINYINT DEFAULT 0,
|
||||
access_tries SMALLINT DEFAULT 0,
|
||||
email_confnum MEDIUMINT DEFAULT 0,
|
||||
email_confnum INT DEFAULT 0,
|
||||
base_lvl SMALLINT UNSIGNED NOT NULL,
|
||||
created DATETIME NOT NULL,
|
||||
lastaccess DATETIME,
|
||||
|
||||
+1
-1
@@ -69,7 +69,7 @@ CREATE TABLE users (
|
||||
verify_email TINYINT DEFAULT 0,
|
||||
lockout TINYINT DEFAULT 0,
|
||||
access_tries SMALLINT DEFAULT 0,
|
||||
email_confnum MEDIUMINT DEFAULT 0,
|
||||
email_confnum INT DEFAULT 0,
|
||||
base_lvl SMALLINT UNSIGNED NOT NULL,
|
||||
created DATETIME NOT NULL,
|
||||
lastaccess DATETIME,
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
{{ end }}
|
||||
|
||||
<!-- Upload Form -->
|
||||
<form method="POST" enctype="multipart/form-data" action="/sysadmin/import" class="max-w-3xl">
|
||||
<form method="POST" enctype="multipart/form-data" action="{{ selfLink }}" class="max-w-3xl">
|
||||
<div class="bg-gray-50 p-6 rounded-lg">
|
||||
<div class="mb-6 flex gap-2">
|
||||
<label for="idata" class="block text-black text-sm font-medium mb-2">
|
||||
|
||||
+31
-27
@@ -18,36 +18,40 @@
|
||||
<div class="max-w-4xl">
|
||||
<div class="bg-gray-50 p-6 rounded-lg mb-6">
|
||||
<div class="space-y-6">
|
||||
{{ range i, c := conferences }}
|
||||
<div class="flex items-start gap-3">
|
||||
<span class="text-lg pt-0.5 flex-shrink-0">🟣</span>
|
||||
<div class="flex-1">
|
||||
<div class="mb-2">
|
||||
<a href="/comm/{{ commAlias }}/conf/{{ c.Alias }}"
|
||||
class="text-blue-700 hover:text-blue-900 font-bold text-lg">{{ c.Name }}</a>
|
||||
<span class="text-gray-600 text-sm ml-2">- Latest activity: {{ DisplayActivity(c.LastUpdate, .) }}</span>
|
||||
{{ if newflag[i] }}
|
||||
<span class="ml-2" title="There are new messages in this conference">🔔</span>
|
||||
{{ end }}
|
||||
</div>
|
||||
<div class="text-sm text-gray-700 mb-1">
|
||||
{{ if len(c.Hosts) == 1 }}
|
||||
<span class="font-medium">Host:</span>
|
||||
{{ else }}
|
||||
<span class="font-medium">Hosts:</span>
|
||||
{{ end }}
|
||||
{{ if len(c.Hosts) > 0 }}
|
||||
{{ range j, u := c.Hosts }}
|
||||
{{ if j > 0 }}, {{ end }}
|
||||
<a href="/users/{{ u }}" class="text-blue-700 hover:text-blue-900">{{ u }}</a>
|
||||
{{ if len(conferences) > 0 }}
|
||||
{{ range i, c := conferences }}
|
||||
<div class="flex items-start gap-3">
|
||||
<span class="text-lg pt-0.5 flex-shrink-0">🟣</span>
|
||||
<div class="flex-1">
|
||||
<div class="mb-2">
|
||||
<a href="/comm/{{ commAlias }}/conf/{{ c.Alias }}"
|
||||
class="text-blue-700 hover:text-blue-900 font-bold text-lg">{{ c.Name }}</a>
|
||||
<span class="text-gray-600 text-sm ml-2">- Latest activity: {{ DisplayActivity(c.LastUpdate, .) }}</span>
|
||||
{{ if newflag[i] }}
|
||||
<span class="ml-2" title="There are new messages in this conference">🔔</span>
|
||||
{{ end }}
|
||||
{{ else }}
|
||||
None
|
||||
{{ end }}
|
||||
</div>
|
||||
<div class="text-sm text-gray-700 mb-1">
|
||||
{{ if len(c.Hosts) == 1 }}
|
||||
<span class="font-medium">Host:</span>
|
||||
{{ else }}
|
||||
<span class="font-medium">Hosts:</span>
|
||||
{{ end }}
|
||||
{{ if len(c.Hosts) > 0 }}
|
||||
{{ range j, u := c.Hosts }}
|
||||
{{ if j > 0 }}, {{ end }}
|
||||
<a href="/users/{{ u }}" class="text-blue-700 hover:text-blue-900">{{ u }}</a>
|
||||
{{ end }}
|
||||
{{ else }}
|
||||
None
|
||||
{{ end }}
|
||||
</div>
|
||||
<div class="italic text-gray-600 text-sm">{{ c.Description }}</div>
|
||||
</div>
|
||||
<div class="italic text-gray-600 text-sm">{{ c.Description }}</div>
|
||||
</div>
|
||||
</div>
|
||||
{{ end }}
|
||||
{{ else }}
|
||||
<div class="italic text-gray-600 text-lg">No conferences in this community.</div>
|
||||
{{ end }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+23
-5
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Amsterdam Web Communities System
|
||||
* Copyright (c) 2025 Erbosoft Metaverse Design Solutions, All Rights Reserved
|
||||
* Copyright (c) 2025-2026 Erbosoft Metaverse Design Solutions, All Rights Reserved
|
||||
*
|
||||
* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
@@ -12,8 +12,9 @@ package util
|
||||
|
||||
import (
|
||||
crand "crypto/rand"
|
||||
"fmt"
|
||||
"io"
|
||||
mrand "math/rand"
|
||||
"math/big"
|
||||
"strings"
|
||||
|
||||
log "github.com/sirupsen/logrus"
|
||||
@@ -49,6 +50,15 @@ var syllabary = [...]string{
|
||||
"za", "ze", "zi", "zo", "zu",
|
||||
}
|
||||
|
||||
// RCN_BASE is the base for generating random confirmation numbers.
|
||||
var RCN_BASE *big.Int = big.NewInt(900000)
|
||||
|
||||
// RCN_OFFSET is what we add to a generated random number to get a proper confirmation number.
|
||||
const RCN_OFFSET = 1000000
|
||||
|
||||
// RCN_MAX is the maximum value of a confirmation number.
|
||||
const RCN_MAX = 9999999
|
||||
|
||||
// GenerateRandomAuthString generates a random authentication string.
|
||||
func GenerateRandomAuthString() string {
|
||||
b := make([]byte, authStringLen)
|
||||
@@ -64,10 +74,18 @@ func GenerateRandomAuthString() string {
|
||||
|
||||
// GenerateRandomConfirmationNumber generates a random 7-digit confirmation number.
|
||||
func GenerateRandomConfirmationNumber() int32 {
|
||||
rc := mrand.Int31n(9000000) + 1000000
|
||||
for rc < 1000000 || rc > 9999999 {
|
||||
v1, err := crand.Int(crand.Reader, RCN_BASE)
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("GRCN ERR %v", err))
|
||||
}
|
||||
rc := int32(v1.Int64()) + RCN_OFFSET
|
||||
for rc < RCN_OFFSET || rc > RCN_MAX {
|
||||
log.Errorf("*** GRCN out of range error! %d", rc)
|
||||
rc = mrand.Int31n(9000000) + 1000000
|
||||
v1, err = crand.Int(crand.Reader, RCN_BASE)
|
||||
if err != nil {
|
||||
panic(fmt.Sprintf("GRCN ERR %v", err))
|
||||
}
|
||||
rc = int32(v1.Int64()) + RCN_OFFSET
|
||||
}
|
||||
return rc
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user