Example #1
0
// BeforeSave invokes required actions before persisting.
func (u *User) BeforeSave(db *gorm.DB) (err error) {
	if u.Slug == "" {
		for i := 0; true; i++ {
			if i == 0 {
				u.Slug = slugify.Slugify(u.Username)
			} else {
				u.Slug = slugify.Slugify(
					fmt.Sprintf("%s-%d", u.Username, i),
				)
			}

			notFound := db.Where(
				"slug = ?",
				u.Slug,
			).Not(
				"id",
				u.ID,
			).First(
				&User{},
			).RecordNotFound()

			if notFound {
				break
			}
		}
	}

	if u.Email != "" {
		email, err := govalidator.NormalizeEmail(
			u.Email,
		)

		if err != nil {
			return fmt.Errorf("Failed to normalize email")
		}

		u.Email = email
	}

	if u.Password != "" {
		encrypt, err := bcrypt.GenerateFromPassword(
			[]byte(u.Password),
			bcrypt.DefaultCost,
		)

		if err != nil {
			return fmt.Errorf("Failed to encrypt password")
		}

		u.Hashword = string(encrypt)
	}

	if u.Hash == "" {
		u.Hash = base32.StdEncoding.EncodeToString(
			securecookie.GenerateRandomKey(32),
		)
	}

	return nil
}
Example #2
0
func NewAccountEmail(addr string) (AccountEmail, error) {
	norm, err := govalidator.NormalizeEmail(addr)
	if err != nil {
		return AccountEmail{}, err
	}
	return AccountEmail{
		Address:     addr,
		AddressNorm: norm,
	}, nil
}
Example #3
0
func GetAccountEmail(addr string) (*Account, error) {
	addr, err := govalidator.NormalizeEmail(addr)
	if err != nil {
		return nil, nil
	}
	acc := Account{}
	err = sess.DB("").C(accountC).Find(bson.M{"emails.address_norm": addr}).One(&acc)
	if err == mgo.ErrNotFound {
		return nil, nil
	}
	if err != nil {
		return nil, err
	}
	return &acc, nil
}
Example #4
0
// CreateUser create a new user. Checks for duplicate users and password-length requirement
func CreateUser(handle tools.Handle, db *mgo.DbQueue) (interface{}, error) {
	var user models.User

	user.Enable = true
	user.Domains = nil
	user.Variables = nil
	err := rest.Parse(handle.R, &user)
	if err != nil {
		return nil, tools.NewError(err, 400, "bad request: couldn't parse body")
	}

	if user.Username == "" {
		return nil, tools.NewError(nil, 400, "bad request: username is missing")
	}
	if user.Password == "" {
		return nil, tools.NewError(nil, 400, "bad request: password is missing")
	}
	if len(user.Password) < handle.C.PasswordMinLength {
		return nil, tools.NewError(nil, 400, "bad request: password is too short")
	}
	if user.Domains == nil || len(user.Domains) == 0 {
		return nil, tools.NewError(nil, 400, "bad request: domains is missing")
	}
	if user.Variables == nil {
		user.Variables = make(map[string]interface{})
	}
	if govalidator.IsEmail(user.Username) == false {
		return nil, tools.NewError(nil, 400, "bad request: username must be a valid email")
	}

	user.Username, err = govalidator.NormalizeEmail(user.Username)
	if err != nil {
		return nil, tools.NewError(nil, 400, "bad request: username must be a valid email")
	}
	uid, err := user.Create(db)
	return CreateResponse{
		Status: "ok",
		UserID: uid.Hex(),
	}, err
}
Example #5
0
func (u User) Login(username, password, domain string, lifespan int64, db *mgo.DbQueue) (Session, error) {
	var s Session
	var err error

	u.Username, err = govalidator.NormalizeEmail(username)
	if err != nil {
		return s, tools.NewError(nil, 400, "bad request: username must be a valid email")
	}
	u.Password = password
	if password == "" {
		return s, tools.NewError(nil, 400, "bad request: password is missing")
	}

	ok, err := u.Check(db)
	if err != nil {
		return s, err
	}
	if ok == false {
		return s, tools.NewError(nil, 403, "forbidden: invalid user or password")
	}
	if u.Enable == false {
		return s, tools.NewError(nil, 403, "forbidden: user is diabled")
	}
	ok = u.CheckDomain(domain)
	if ok == false {
		return s, tools.NewError(nil, 403, "forbidden: restricted domain")
	}

	s.UserID = u.ID
	s.Domain = domain
	_, err = s.Create(db, lifespan)
	if err != nil {
		return s, err
	}

	return s, nil
}
Example #6
0
// Validate does some validation to be able to store the record.
func (u *User) Validate(db *gorm.DB) {
	if !govalidator.StringLength(u.Username, "2", "255") {
		db.AddError(fmt.Errorf("Username should be longer than 2 and shorter than 255"))
	}

	if u.Username != "" {
		notFound := db.Where(
			"username = ?",
			u.Username,
		).Not(
			"id",
			u.ID,
		).First(
			&User{},
		).RecordNotFound()

		if !notFound {
			db.AddError(fmt.Errorf("Username is already present"))
		}
	}

	if u.Hash != "" {
		notFound := db.Where(
			"hash = ?",
			u.Hash,
		).Not(
			"id",
			u.ID,
		).First(
			&User{},
		).RecordNotFound()

		if !notFound {
			db.AddError(fmt.Errorf("Hash is already present"))
		}
	}

	if !govalidator.IsEmail(u.Email) {
		db.AddError(fmt.Errorf(
			"Email must be a valid email address",
		))
	}

	if u.Email != "" {
		normalized, _ := govalidator.NormalizeEmail(
			u.Email,
		)

		notFound := db.Where(
			"email = ?",
			normalized,
		).Not(
			"id",
			u.ID,
		).First(
			&User{},
		).RecordNotFound()

		if !notFound {
			db.AddError(fmt.Errorf("Email is already present"))
		}
	}

	if db.NewRecord(u) {
		if !govalidator.StringLength(u.Password, "5", "255") {
			db.AddError(fmt.Errorf("Password should be longer than 5 and shorter than 255"))
		}
	}
}
Example #7
0
// Login a user, creating a new session.
func Login(handle tools.Handle, db *mgo.DbQueue) (interface{}, error) {
	var q LoginRequest
	var user models.User
	var session models.Session
	var resp LoginResponse

	err := rest.Parse(handle.R, &q)
	if err != nil {
		return nil, tools.NewError(err, 400, "bad request: couldn't parse body")
	}

	if q.Domain == "" {
		return nil, tools.NewError(nil, 400, "bad request: domain is missing")
	}
	if q.Domain == "/" {
		return nil, tools.NewError(nil, 400, "bad request: illegal domain")
	}

	if q.Username == "" {
		return nil, tools.NewError(nil, 400, "bad request: username is missing")
	}
	if q.Password == "" {
		return nil, tools.NewError(nil, 400, "bad request: password is missing")
	}

	user.Username = q.Username
	user.Password = q.Password

	if govalidator.IsEmail(user.Username) == false {
		return nil, tools.NewError(nil, 400, "bad request: username must be a valid email")
	}

	user.Username, err = govalidator.NormalizeEmail(user.Username)
	if err != nil {
		return nil, tools.NewError(nil, 400, "bad request: username must be a valid email")
	}

	ok, err := user.Check(db)
	if err != nil {
		return nil, err
	}
	if ok == false {
		return nil, tools.NewError(nil, 403, "forbidden: invalid user or password")
	}
	if user.Enable == false {
		return nil, tools.NewError(nil, 403, "forbidden: user is diabled")
	}
	ok = user.CheckDomain(q.Domain)
	if ok == false {
		return nil, tools.NewError(nil, 403, "forbidden: restricted domain")
	}

	session.UserID = user.ID
	session.Domain = q.Domain
	remaining, err := session.Create(db, handle.C.SessionLifespan)
	if err != nil {
		return nil, err
	}
	resp.Status = "ok"
	resp.Session.Token = session.ID.Hex()
	resp.Session.UserID = session.UserID.Hex()
	resp.Session.Expire = session.Expire
	resp.Session.Remaining = remaining
	return resp, nil
}