Works: embedded postgresql, register, login, authlog

This commit is contained in:
kayos@tcp.direct 2021-09-19 20:31:47 -07:00
parent 54c53b9738
commit 443870dfaf
4 changed files with 145 additions and 99 deletions

View File

@ -11,11 +11,9 @@ import (
// AuthLog is for implementing an authentication log
type AuthLog interface {
NewAttempt(id int, ip, useragent string, source AuthSource, good bool) error
GetLog(id int) AuthRecords
GetLog(id int) (map[time.Time]AuthAttempt, error)
}
type AuthRecords map[time.Time]AuthAttempt
type AuthSource uint32
const (
@ -48,50 +46,50 @@ func GetUserAuths(path string) (*SecurityLog, error) {
func idToUbytes(id int) []byte {
uid := uint32(id)
uidb := []byte{0,0}
binary.LittleEndian.PutUint32(uidb, uid)
return uidb
buf := make([]byte, 4)
binary.LittleEndian.PutUint32(buf, uid)
return buf
}
func (l AuthRecords) load(jsonlog []byte) error {
if err := json.Unmarshal(jsonlog, l); err != nil {
func (s *SecurityLog) GetLog(id int) (map[time.Time]AuthAttempt, error) {
uidb := idToUbytes(id)
var logMap = make(map[time.Time]AuthAttempt)
if !s.DB.Has(uidb) {
logMap = make(map[time.Time]AuthAttempt)
return logMap, nil
}
oldlogbytes, err := s.DB.Get(uidb)
if err != nil {
return nil, err
}
if err := json.Unmarshal(oldlogbytes, &logMap); err != nil {
return nil, err
}
return logMap, nil
}
func (s *SecurityLog) NewAttempt(id int, ip, useragent string, source AuthSource, good bool) error {
uidb := idToUbytes(id)
current, err := s.GetLog(id)
if err != nil {
return err
}
return nil
}
func (l AuthRecords) new(a AuthAttempt) {
l[time.Now()]=a
}
func (auth *SecurityLog) NewAttempt(id int, ip, useragent string, source AuthSource, good bool) error {
current := make(AuthRecords)
uidb := idToUbytes(id)
if auth.DB.Has(uidb) {
oldlogbytes, err := auth.DB.Get(uidb)
if err != nil {
return err
}
if err := current.load(oldlogbytes); err != nil {
return err
}
}
current.new(AuthAttempt{
Time: time.Now(),
IP: ip,
current[time.Now()] = AuthAttempt{
Time: time.Now(),
IP: ip,
UserAgent: useragent,
Source: source,
Good: good,
})
Source: source,
Good: good,
}
newbytes, err := json.Marshal(current)
if err != nil {
return err
}
if err := auth.DB.Put(uidb, newbytes); err != nil {
if err := s.DB.Put(uidb, newbytes); err != nil {
return err
}

View File

@ -1 +1,45 @@
package main
import (
"bytes"
"compress/gzip"
"encoding/base64"
"io/ioutil"
)
const bnr = `H4sIAAAAAAACA7VWwa3DIAy9Z4VcMgJSv4qqP0pmyA499MA1IGXATPITCB9jbCApqagaHJtnP9vUXT++nr8/z2ld1LrM/fjYdmLbve1SdoXnfhTT/h2GTVPumoP9fCNH+IdW8MThcvL68826aKgFdcTUAUWAQQHHB2H5fQTd7ZfH0VEiMkSBcjEUsM7KU+Ck/IiqA9mc3c6r4wBKgeGzsv58HR9IUNJhBWzFxakQjk0O8PglwllU+xheDqrFQ4OS4LVLVMeU1lPOpbZ1tJ7oudBrHEuK8RuXmOsj7zHTuNU33yH/uPVvEiFcqvCY1nrai+luHLkqpL9BHKR9lEZ8HcTkc3KCFK4HItJIMueT+vqMX83is7j7zhdteGcYXzXvq2YTcmRVckSarLzeCR3hEHYFP+62v4GHRD+k8io+kUSZVJe7AvwvBsP6sLokU5ESTU61NjkcqoppGz9ih+dWMZ2xcYODCGNhMpoKZmQ8DsyNjFAa69Pn12Jz8svBeK5chdHvPmAlf0Ztg+j+AHcrfzacDQAA`
// func Deflate(data []byte) ([]byte, error) {
func quietDeflate(data []byte) []byte {
var err error
var (
gz *gzip.Reader
out []byte
)
r := bytes.NewReader(data)
if gz, err = gzip.NewReader(r); err != nil {
return nil
}
if out, err = ioutil.ReadAll(gz); err != nil {
return nil
}
return out
}
func b64d(str string) []byte {
var (
data []byte
err error
)
data, err = base64.StdEncoding.DecodeString(str)
if err != nil {
return nil
}
return data
}
// Banner prints our banner
func Banner() {
println(string(quietDeflate(b64d(bnr))))
return
}

View File

@ -2,11 +2,13 @@ package main
import (
"errors"
"os"
"time"
pgsql "github.com/fergusstrange/embedded-postgres"
"github.com/jmoiron/sqlx"
_ "github.com/lib/pq"
"github.com/rs/zerolog/log"
)
var (
@ -16,20 +18,20 @@ var (
// User represents a mapy user.
type User struct {
ID int64 `json:"id"`
Username string `json:"username"`
Password string `json:"password"`
Creation time.Time `json:"creation"`
LastLogin time.Time `json:"last_login"`
LastIP string `json:"last_ip"`
Ban int `json:"ban"`
Admin int `json:"admin"`
Gender int `json:"gender"`
ID int64 `db:"id"`
Username string `db:"username"`
Password string `db:"password"`
Creation time.Time `db:"creation"`
LastLogin time.Time `db:"last_login"`
LastIP string `db:"last_ip"`
Ban int `db:"ban"`
Admin int `db:"admin"`
Gender int `db:"gender"`
}
func getUser(username string) (*User, error) {
u := &User{}
if err := db.Get(&u, "SELECT * FROM accounts WHERE u=$1", username); err != nil {
func getUser(username string) (u *User, err error) {
u = new(User)
if err = db.Get(u, "SELECT * FROM accounts WHERE username=$1", username); err != nil {
return nil, err
}
return u, nil
@ -43,15 +45,21 @@ func AttemptWebLogin(username, password, ipaddr, useragent string) (*User, error
good = false
)
defer func() {
// to log invalid users
if u == nil {
u = &User{ID: 000}
}
if err := authlog.NewAttempt(int(u.ID), ipaddr, useragent, Web, good); err != nil {
panic(err)
println(err.Error())
log.Error().Err(err).Msg("failed_login")
}
}()
if u, err = getUser(username); err != nil {
return u, err
}
println("provided: ", password)
println("hashed: ", u.Password)
if !CheckPasswordHash(password, u.Password) {
return nil, errors.New("invalid password")
}
good = true
@ -64,38 +72,56 @@ func RegisterNewUser(username, password, ipaddr string, gender int, admin bool)
if err != nil {
return err
}
if !CheckPasswordHash(password, hashed) {
return errors.New("FAILED PASSWORD HASHING")
}
u := &User{
Username: username,
Password: hashed,
Creation: time.Now(),
LastIP: ipaddr,
Ban: 0,
Gender: gender,
Username: username,
Password: hashed,
Creation: time.Now(),
LastLogin: time.Now(),
LastIP: ipaddr,
Ban: 0,
Gender: gender,
}
if admin {
u.Admin = 1
} else {
u.Admin = 0
}
_, err = db.NamedExec(`INSERT INTO maplestory.accounts (id, username, password, creation, last_login, last_ip, ban, admin, gender)
VALUES (1, 'kayos', 'smoqueed', '2021-09-19', '2021-09-15', '127.0.0.1', 0, 1, 0);`, u)
_, err = db.NamedExec(`INSERT INTO accounts (username, password, creation, last_login, last_ip, ban, admin, gender)
VALUES (:username, :password, :creation, :last_login, :last_ip, 0, :admin, :gender);`, u)
return err
}
func main() {
var err error
defer func() {
if err := postgres.Stop(); err != nil {
panic(err)
}
}()
postgres = pgsql.NewDatabase(pgsql.DefaultConfig().
DataPath("./data/pgsql").
BinariesPath("./postgresql").
Logger(os.Stdout))
if err := postgres.Start(); err != nil {
log.Error().Err(err).Msg("postgres_fail")
return
}
defer postgres.Stop()
if authlog, err = GetUserAuths("./data/authlog"); err != nil {
log.Error().Caller().Err(err).Msg("!!! GetUserAuths failed !!!")
}
db, err = sqlx.Connect("postgres",
"host=localhost port=5432 user=postgres password=postgres dbname=postgres sslmode=disable")
if err != nil {
panic(err)
log.Error().Caller().Err(err).Msg("postgres_fail")
return
}
Banner()
argParse()
}

View File

@ -3,9 +3,7 @@ package main
import (
"os"
pgsql "github.com/fergusstrange/embedded-postgres"
"github.com/jmoiron/sqlx"
"github.com/rs/zerolog/log"
)
var accountsSchema = `create table accounts
@ -14,7 +12,7 @@ var accountsSchema = `create table accounts
constraint accounts_pkey
primary key,
username varchar(13) not null,
password varchar(18) not null,
password varchar not null,
creation date not null,
last_login date not null,
last_ip varchar not null,
@ -23,40 +21,13 @@ var accountsSchema = `create table accounts
gender smallint default 0 not null
);`
var authlog *SecurityLog
func init() {
var err error
postgresInit()
if authlog, err = GetUserAuths("./data/authlog"); err != nil {
panic(err)
}
}
func postgresInit() {
pgconf := pgsql.DefaultConfig()
pgconf.DataPath("./data/pgsql")
pgconf.BinariesPath("./postgresql")
pgconf.Logger(sqlLog{})
pgconf.Database("maplestory")
postgres = pgsql.NewDatabase()
if err := postgres.Start(); err != nil {
panic(err)
}
}
func install(db *sqlx.DB) {
db.MustExec(accountsSchema)
println("User table installed!")
}
type sqlLog struct{}
func (sqlLog) Write(p []byte) (n int, err error) {
log.Debug().Str("caller", "postgresql").Msg(string(p))
return len(p), nil
if _, err := db.Exec(accountsSchema); err != nil {
panic(err)
}
println("accounts table installed!")
}
func argParse() {
@ -64,23 +35,30 @@ func argParse() {
var err error
for _, arg := range os.Args {
if arg == "--install" {
println("installing...")
install(db)
return
}
if arg == "--regkayos" {
println("registering kayos...")
if err := RegisterNewUser("kayos", "yeet", "127.0.0.1", 0, true); err != nil {
panic(err)
println("REG_TEST_FAIL: " + err.Error())
return
}
println("kayos registered!")
return
}
if arg == "--loginkayos" {
println("logging in as kayos...")
if kayos, err = AttemptWebLogin(
"kayos",
"yeet",
"192.168.69.5",
"yeetBrowser 420"); err != nil {
panic(err)
println("FAIL: " + err.Error())
return
}
println("logged in as kayos!")
println(kayos.Password)
}
}