Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- server.go
- ______________________________________________________________________________________
- // Reset routes
- goji.Get("/reset", application.Route(controller, "Reset"))
- goji.Post("/reset", application.Route(controller, "ResetPost"))
- views/auth/reset.html
- ______________________________________________________________________________________
- {{define "auth/reset"}}
- <div class="panel panel-default">
- <div class="panel-heading">
- <h4 class="panel-title">Reset password</h4>
- </div>
- <div class="panel-body">
- <form class="form-horizontal" method="post" data-parsley-validate>
- <fieldset>
- {{range .Flash}}
- <div class="alert alert-danger">{{.}}</div><p>
- {{end}}
- {{range .Success}}
- <div class="alert alert-success">{{.}}</div><p>
- {{end}}
- <div class="form-group">
- <label class="col-md-4 control-label" for="email">Email</label>
- <div class="col-md-6">
- <input id="email" name="email" type="email" placeholder="Email address" class="form-control input-md" required="" data-parsley-required-message="Please enter your email">
- </div>
- </div>
- <div class="form-group">
- <label class="col-md-4 control-label" for=""></label>
- <div class="col-md-6">
- <div class="g-recaptcha" data-sitekey=""></div>
- </div>
- </div>
- <div class="form-group">
- <label class="col-md-4 control-label" for="reset"></label>
- <div class="col-md-4">
- <button id="reset" name="reset" class="btn btn-primary">Reset password</button>
- </div>
- </div>
- </fieldset>
- <input type="hidden" name="{{.CsrfKey}}" value={{.CsrfToken}}>
- </form>
- </div>
- </div>
- {{end}}
- models / user.go
- ______________________________________________________________________
- func ResetPassword(dbMap *gorp.DbMap, id int64, password []byte) (user *User) {
- err := dbMap.SelectOne(&user, "SELECT * FROM Users WHERE UserId = ?", id)
- if err != nil {
- glog.Warningf("Can't get user by id: %v", err)
- }
- user.Password = password
- _, err = dbMap.Update(user)
- if err != nil {
- glog.Warningf("Couldn't update user: %v", err)
- }
- return
- }
- controllers / main.go
- ___________________________________________________________________________
- import (
- "net/smtp"
- "net/mail"
- "encoding/base64"
- )
- // Reset route
- func (controller *MainController) Reset(c web.C, r *http.Request) (string, int) {
- t := controller.GetTemplate(c)
- session := controller.GetSession(c)
- c.Env["IsReset"] = true
- c.Env["Flash"] = session.Flashes("reset")
- c.Env["Success"] = session.Flashes("reset-success")
- c.Env["RecaptchaSiteKey"] = controller.recaptchaSiteKey
- var widgets = controller.Parse(t, "auth/reset", c.Env)
- c.Env["Content"] = template.HTML(widgets)
- return controller.Parse(t, "main", c.Env), http.StatusOK
- }
- func (controller *MainController) ResetPost(c web.C, r *http.Request) (string, int) {
- re := recaptcha.R{
- Secret: controller.recaptchaSecret,
- }
- email := r.FormValue("email")
- session := controller.GetSession(c)
- isValid := re.Verify(*r)
- if !isValid {
- session.AddFlash("Recaptcha error", "reset")
- glog.Errorf("Error whilst resetting password for user: %v", re.LastError())
- return controller.Reset(c, r)
- }
- dbMap := controller.GetDbMap(c)
- user := models.GetUserByEmail(dbMap, email)
- if user == nil {
- session.AddFlash("User not found", "reset")
- return controller.Reset(c, r)
- }
- password := helpers.NewPass(10)
- user.HashPassword(password)
- models.ResetPassword(dbMap, user.Id, user.Password)
- auth := smtp.PlainAuth(
- "",
- "FROM_EMAIL",
- "PASSWORD",
- "smtp.gmail.com",
- )
- from := mail.Address{"Stakepool Dcrstats", "info@dcrstats.com"}
- to := mail.Address{email, email}
- title := "Stakepool Dcrstats: New Password"
- body := "Hi! Here is your new password at stakepool.dcrstats.com: " + password
- header := make(map[string]string)
- header["From"] = from.String()
- header["To"] = to.String()
- header["Subject"] = title
- header["MIME-Version"] = "1.0"
- header["Content-Type"] = "text/plain; charset=\"utf-8\""
- header["Content-Transfer-Encoding"] = "base64"
- message := ""
- for k, v := range header {
- message += fmt.Sprintf("%s: %s\r\n", k, v)
- }
- message += "\r\n" + base64.StdEncoding.EncodeToString([]byte(body))
- // Connect to the server, authenticate, set the sender and recipient,
- // and send the email all in one step.
- err := smtp.SendMail(
- "smtp.gmail.com:25",
- auth,
- "info@dcrstats.com",
- []string{email},
- []byte(message),
- )
- if err != nil {
- session.AddFlash("Failed to send email with new password", "reset")
- glog.Errorf("Error while resetting password: %v", err)
- return controller.Reset(c, r)
- }
- session.AddFlash("Success! We've sent you email with new password", "reset-success")
- return controller.Reset(c, r)
- }
- helpers / auth.go
- ________________________________________________________________________________________
- import (
- "github.com/decred/dcrstakepool/models"
- "golang.org/x/crypto/bcrypt"
- "gopkg.in/gorp.v1"
- "crypto/rand"
- )
- const (
- // StdLen is a standard length of the string to achive ~95 bits of entropy.
- StdLen = 16
- // UUIDLen is a length of uniuri string to achive ~119 bits of entropy, closest
- // to what can be losslessly converted to UUIDv4 (122 bits).
- UUIDLen = 20
- )
- // StdChars is a set of standard characters allowed in the string.
- var StdChars = []byte("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789")
- // NewLen returns a new random string of the provided length, consisting of
- // standard characters.
- func NewPass(length int) string {
- return NewLenChars(length, StdChars)
- }
- // NewLenChars returns a new random string of the provided length, consisting
- // of the provided byte slice of allowed characters (maximum 256).
- func NewLenChars(length int, chars []byte) string {
- if length == 0 {
- return ""
- }
- clen := len(chars)
- if clen < 2 || clen > 256 {
- panic("uniuri: wrong charset length for NewLenChars")
- }
- maxrb := 255 - (256 % clen)
- b := make([]byte, length)
- r := make([]byte, length+(length/4)) // storage for random bytes.
- i := 0
- for {
- if _, err := rand.Read(r); err != nil {
- panic("uniuri: error reading random bytes: " + err.Error())
- }
- for _, rb := range r {
- c := int(rb)
- if c > maxrb {
- // Skip this number to avoid modulo bias.
- continue
- }
- b[i] = chars[c%clen]
- i++
- if i == length {
- return string(b)
- }
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement