func watchAndParseTemplates() { templatesDir := utils.FindDir("web/templates") l4g.Debug("Parsing templates at %v", templatesDir) var err error if Templates, err = template.ParseGlob(templatesDir + "*.html"); err != nil { l4g.Error("Failed to parse templates %v", err) } watcher, err := fsnotify.NewWatcher() if err != nil { l4g.Error("Failed to create directory watcher %v", err) } go func() { for { select { case event := <-watcher.Events: if event.Op&fsnotify.Write == fsnotify.Write { l4g.Info("Re-parsing templates because of modified file %v", event.Name) if Templates, err = template.ParseGlob(templatesDir + "*.html"); err != nil { l4g.Error("Failed to parse templates %v", err) } } case err := <-watcher.Errors: l4g.Error("Failed in directory watcher %v", err) } } }() err = watcher.Add(templatesDir) if err != nil { l4g.Error("Failed to add directory to watcher %v", err) } }
func InitWeb() { l4g.Debug("Initializing web routes") mainrouter := api.Srv.Router staticDir := utils.FindDir("web/static") l4g.Debug("Using static directory at %v", staticDir) mainrouter.PathPrefix("/static/").Handler(http.StripPrefix("/static/", http.FileServer(http.Dir(staticDir)))) mainrouter.Handle("/", api.AppHandlerIndependent(root)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/login", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/logout", api.AppHandler(logout)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/reset_password", api.AppHandler(resetPassword)).Methods("GET") // Bug in gorilla.mux pervents us from using regex here. mainrouter.Handle("/{team}/channels/{channelname}", api.UserRequired(getChannel)).Methods("GET") // Anything added here must have an _ in it so it does not conflict with team names mainrouter.Handle("/signup_team_complete/", api.AppHandlerIndependent(signupTeamComplete)).Methods("GET") mainrouter.Handle("/signup_user_complete/", api.AppHandlerIndependent(signupUserComplete)).Methods("GET") mainrouter.Handle("/signup_team_confirm/", api.AppHandlerIndependent(signupTeamConfirm)).Methods("GET") mainrouter.Handle("/verify_email", api.AppHandlerIndependent(verifyEmail)).Methods("GET") mainrouter.Handle("/find_team", api.AppHandlerIndependent(findTeam)).Methods("GET") mainrouter.Handle("/signup_team", api.AppHandlerIndependent(signup)).Methods("GET") watchAndParseTemplates() }
func InitWeb() { l4g.Debug("Initializing web routes") staticDir := utils.FindDir("web/static") l4g.Debug("Using static directory at %v", staticDir) api.Srv.Router.PathPrefix("/static/").Handler(http.StripPrefix("/static/", http.FileServer(http.Dir(staticDir)))) api.Srv.Router.Handle("/", api.AppHandler(root)).Methods("GET") api.Srv.Router.Handle("/login", api.AppHandler(login)).Methods("GET") api.Srv.Router.Handle("/signup_team_confirm/", api.AppHandler(signupTeamConfirm)).Methods("GET") api.Srv.Router.Handle("/signup_team_complete/", api.AppHandler(signupTeamComplete)).Methods("GET") api.Srv.Router.Handle("/signup_user_complete/", api.AppHandler(signupUserComplete)).Methods("GET") api.Srv.Router.Handle("/logout", api.AppHandler(logout)).Methods("GET") api.Srv.Router.Handle("/verify", api.AppHandler(verifyEmail)).Methods("GET") api.Srv.Router.Handle("/find_team", api.AppHandler(findTeam)).Methods("GET") api.Srv.Router.Handle("/reset_password", api.AppHandler(resetPassword)).Methods("GET") csr := api.Srv.Router.PathPrefix("/channels").Subrouter() csr.Handle("/{name:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}", api.UserRequired(getChannel)).Methods("GET") watchAndParseTemplates() }
func watchAndParseTemplates() { templatesDir := utils.FindDir("web/templates") l4g.Debug(utils.T("web.parsing_templates.debug"), templatesDir) var err error if Templates, err = template.ParseGlob(templatesDir + "*.html"); err != nil { l4g.Error(utils.T("web.parsing_templates.error"), err) } watcher, err := fsnotify.NewWatcher() if err != nil { l4g.Error(utils.T("web.create_dir.error"), err) } go func() { for { select { case event := <-watcher.Events: if event.Op&fsnotify.Write == fsnotify.Write { l4g.Info(utils.T("web.reparse_templates.info"), event.Name) if Templates, err = template.ParseGlob(templatesDir + "*.html"); err != nil { l4g.Error(utils.T("web.parsing_templates.error"), err) } } case err := <-watcher.Errors: l4g.Error(utils.T("web.dir_fail.error"), err) } } }() err = watcher.Add(templatesDir) if err != nil { l4g.Error(utils.T("web.watcher_fail.error"), err) } }
func root(c *api.Context, w http.ResponseWriter, r *http.Request) { if !CheckBrowserCompatability(c, r) { return } if api.IsApiCall(r) { api.Handle404(w, r) return } http.ServeFile(w, r, utils.FindDir(CLIENT_DIR)+"root.html") }
func root(c *api.Context, w http.ResponseWriter, r *http.Request) { if !CheckBrowserCompatability(c, r) { return } if api.IsApiCall(r) { api.Handle404(w, r) return } w.Header().Set("Cache-Control", "no-cache, max-age=31556926, public") http.ServeFile(w, r, utils.FindDir(CLIENT_DIR)+"root.html") }
func InitWeb() { l4g.Debug("Initializing web routes") mainrouter := api.Srv.Router staticDir := utils.FindDir("web/static") l4g.Debug("Using static directory at %v", staticDir) mainrouter.PathPrefix("/static/").Handler(http.StripPrefix("/static/", http.FileServer(http.Dir(staticDir)))) mainrouter.Handle("/", api.AppHandlerIndependent(root)).Methods("GET") mainrouter.Handle("/oauth/authorize", api.UserRequired(authorizeOAuth)).Methods("GET") mainrouter.Handle("/oauth/access_token", api.ApiAppHandler(getAccessToken)).Methods("POST") mainrouter.Handle("/signup_team_complete/", api.AppHandlerIndependent(signupTeamComplete)).Methods("GET") mainrouter.Handle("/signup_user_complete/", api.AppHandlerIndependent(signupUserComplete)).Methods("GET") mainrouter.Handle("/signup_team_confirm/", api.AppHandlerIndependent(signupTeamConfirm)).Methods("GET") mainrouter.Handle("/verify_email", api.AppHandlerIndependent(verifyEmail)).Methods("GET") mainrouter.Handle("/find_team", api.AppHandlerIndependent(findTeam)).Methods("GET") mainrouter.Handle("/signup_team", api.AppHandlerIndependent(signup)).Methods("GET") mainrouter.Handle("/login/{service:[A-Za-z]+}/complete", api.AppHandlerIndependent(completeOAuth)).Methods("GET") // Remove after a few releases (~1.8) mainrouter.Handle("/signup/{service:[A-Za-z]+}/complete", api.AppHandlerIndependent(completeOAuth)).Methods("GET") // Remove after a few releases (~1.8) mainrouter.Handle("/{service:[A-Za-z]+}/complete", api.AppHandlerIndependent(completeOAuth)).Methods("GET") mainrouter.Handle("/admin_console", api.UserRequired(adminConsole)).Methods("GET") mainrouter.Handle("/admin_console/", api.UserRequired(adminConsole)).Methods("GET") mainrouter.Handle("/admin_console/{tab:[A-Za-z0-9-_]+}", api.UserRequired(adminConsole)).Methods("GET") mainrouter.Handle("/admin_console/{tab:[A-Za-z0-9-_]+}/{team:[A-Za-z0-9-]*}", api.UserRequired(adminConsole)).Methods("GET") mainrouter.Handle("/hooks/{id:[A-Za-z0-9]+}", api.ApiAppHandler(incomingWebhook)).Methods("POST") mainrouter.Handle("/docs/{doc:[A-Za-z0-9]+}", api.AppHandlerIndependent(docs)).Methods("GET") // ---------------------------------------------------------------------------------------------- // *ANYTHING* team specific should go below this line // ---------------------------------------------------------------------------------------------- mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/login", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/logout", api.AppHandler(logout)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/reset_password", api.AppHandler(resetPassword)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/claim", api.AppHandler(claimAccount)).Methods("GET") mainrouter.Handle("/{team}/pl/{postid}", api.AppHandler(postPermalink)).Methods("GET") // Bug in gorilla.mux prevents us from using regex here. mainrouter.Handle("/{team}/login/{service}", api.AppHandler(loginWithOAuth)).Methods("GET") // Bug in gorilla.mux prevents us from using regex here. mainrouter.Handle("/{team}/channels/{channelname}", api.AppHandler(getChannel)).Methods("GET") // Bug in gorilla.mux prevents us from using regex here. mainrouter.Handle("/{team}/signup/{service}", api.AppHandler(signupWithOAuth)).Methods("GET") // Bug in gorilla.mux prevents us from using regex here. watchAndParseTemplates() }
func readTestFile(name string) ([]byte, error) { path := utils.FindDir("tests") file, err := os.Open(path + "/" + name) if err != nil { return nil, err } defer file.Close() data := &bytes.Buffer{} if _, err := io.Copy(data, file); err != nil { return nil, err } else { return data.Bytes(), nil } }
func root(c *api.Context, w http.ResponseWriter, r *http.Request) { if !CheckBrowserCompatability(c, r) { w.Header().Set("Cache-Control", "no-store") w.WriteHeader(http.StatusBadRequest) w.Write([]byte(c.T("web.check_browser_compatibility.app_error"))) return } if api.IsApiCall(r) { api.Handle404(w, r) return } w.Header().Set("Cache-Control", "no-cache, max-age=31556926, public") http.ServeFile(w, r, utils.FindDir(model.CLIENT_DIR)+"root.html") }
func InitWeb() { l4g.Debug(utils.T("web.init.debug")) mainrouter := api.Srv.Router if *utils.Cfg.ServiceSettings.WebserverMode != "disabled" { staticDir := utils.FindDir(CLIENT_DIR) l4g.Debug("Using client directory at %v", staticDir) if *utils.Cfg.ServiceSettings.WebserverMode == "gzip" { mainrouter.PathPrefix("/static/").Handler(gziphandler.GzipHandler(staticHandler(http.StripPrefix("/static/", http.FileServer(http.Dir(staticDir)))))) } else { mainrouter.PathPrefix("/static/").Handler(staticHandler(http.StripPrefix("/static/", http.FileServer(http.Dir(staticDir))))) } mainrouter.Handle("/{anything:.*}", api.AppHandlerIndependent(root)).Methods("GET") } }
func InitApi() { r := Srv.Router.PathPrefix("/api/v1").Subrouter() InitUser(r) InitTeam(r) InitChannel(r) InitPost(r) InitWebSocket(r) InitFile(r) InitCommand(r) templatesDir := utils.FindDir("api/templates") l4g.Debug("Parsing server templates at %v", templatesDir) var err error if ServerTemplates, err = template.ParseGlob(templatesDir + "*.html"); err != nil { l4g.Error("Failed to parse server templates %v", err) } }
func (cfg *AutoPostCreator) UploadTestFile() ([]string, bool) { body := &bytes.Buffer{} writer := multipart.NewWriter(body) filename := cfg.ImageFilenames[utils.RandIntFromRange(utils.Range{0, len(cfg.ImageFilenames) - 1})] part, err := writer.CreateFormFile("files", filename) if err != nil { return nil, false } path := utils.FindDir("web/static/images") file, err := os.Open(path + "/" + filename) defer file.Close() _, err = io.Copy(part, file) if err != nil { return nil, false } field, err := writer.CreateFormField("channel_id") if err != nil { return nil, false } _, err = field.Write([]byte(cfg.channelid)) if err != nil { return nil, false } err = writer.Close() if err != nil { return nil, false } resp, appErr := cfg.client.UploadPostAttachment(body.Bytes(), writer.FormDataContentType()) if appErr != nil { return nil, false } return resp.Data.(*model.FileUploadResponse).Filenames, true }
func (cfg *AutoPostCreator) UploadTestFile() ([]string, bool) { filename := cfg.ImageFilenames[utils.RandIntFromRange(utils.Range{0, len(cfg.ImageFilenames) - 1})] path := utils.FindDir("web/static/images") file, err := os.Open(path + "/" + filename) defer file.Close() data := &bytes.Buffer{} _, err = io.Copy(data, file) if err != nil { return nil, false } resp, appErr := cfg.client.UploadPostAttachment(data.Bytes(), cfg.channelid, filename) if appErr != nil { return nil, false } return []string{resp.FileInfos[0].Id}, true }
func addCertificate(c *Context, w http.ResponseWriter, r *http.Request) { err := r.ParseMultipartForm(*utils.Cfg.FileSettings.MaxFileSize) if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) return } m := r.MultipartForm fileArray, ok := m.File["certificate"] if !ok { c.Err = model.NewLocAppError("addCertificate", "api.admin.add_certificate.no_file.app_error", nil, "") c.Err.StatusCode = http.StatusBadRequest return } if len(fileArray) <= 0 { c.Err = model.NewLocAppError("addCertificate", "api.admin.add_certificate.array.app_error", nil, "") c.Err.StatusCode = http.StatusBadRequest return } fileData := fileArray[0] file, err := fileData.Open() defer file.Close() if err != nil { c.Err = model.NewLocAppError("addCertificate", "api.admin.add_certificate.open.app_error", nil, err.Error()) return } out, err := os.Create(utils.FindDir("config") + fileData.Filename) if err != nil { c.Err = model.NewLocAppError("addCertificate", "api.admin.add_certificate.saving.app_error", nil, err.Error()) return } defer out.Close() io.Copy(out, file) ReturnStatusOK(w) }
func InitApi() { r := Srv.Router.PathPrefix("/api/v1").Subrouter() InitUser(r) InitTeam(r) InitChannel(r) InitPost(r) InitWebSocket(r) InitFile(r) InitCommand(r) InitAdmin(r) InitOAuth(r) InitWebhook(r) InitPreference(r) InitLicense(r) templatesDir := utils.FindDir("api/templates") l4g.Debug(utils.T("api.api.init.parsing_templates.debug"), templatesDir) var err error if ServerTemplates, err = template.ParseGlob(templatesDir + "*.html"); err != nil { l4g.Error(utils.T("api.api.init.parsing_templates.error"), err) } }
func InitWeb() { l4g.Debug("Initializing web routes") mainrouter := api.Srv.Router staticDir := utils.FindDir("web/static") l4g.Debug("Using static directory at %v", staticDir) mainrouter.PathPrefix("/static/").Handler(http.StripPrefix("/static/", http.FileServer(http.Dir(staticDir)))) mainrouter.Handle("/", api.AppHandlerIndependent(root)).Methods("GET") mainrouter.Handle("/signup_team_complete/", api.AppHandlerIndependent(signupTeamComplete)).Methods("GET") mainrouter.Handle("/signup_user_complete/", api.AppHandlerIndependent(signupUserComplete)).Methods("GET") mainrouter.Handle("/signup_team_confirm/", api.AppHandlerIndependent(signupTeamConfirm)).Methods("GET") mainrouter.Handle("/verify_email", api.AppHandlerIndependent(verifyEmail)).Methods("GET") mainrouter.Handle("/find_team", api.AppHandlerIndependent(findTeam)).Methods("GET") mainrouter.Handle("/signup_team", api.AppHandlerIndependent(signup)).Methods("GET") mainrouter.Handle("/login/{service:[A-Za-z]+}/complete", api.AppHandlerIndependent(loginCompleteOAuth)).Methods("GET") mainrouter.Handle("/signup/{service:[A-Za-z]+}/complete", api.AppHandlerIndependent(signupCompleteOAuth)).Methods("GET") mainrouter.Handle("/admin_console", api.UserRequired(adminConsole)).Methods("GET") // ---------------------------------------------------------------------------------------------- // *ANYTHING* team spefic should go below this line // ---------------------------------------------------------------------------------------------- mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/login", api.AppHandler(login)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/logout", api.AppHandler(logout)).Methods("GET") mainrouter.Handle("/{team:[A-Za-z0-9-]+(__)?[A-Za-z0-9-]+}/reset_password", api.AppHandler(resetPassword)).Methods("GET") mainrouter.Handle("/{team}/login/{service}", api.AppHandler(loginWithOAuth)).Methods("GET") // Bug in gorilla.mux prevents us from using regex here. mainrouter.Handle("/{team}/channels/{channelname}", api.UserRequired(getChannel)).Methods("GET") // Bug in gorilla.mux prevents us from using regex here. mainrouter.Handle("/{team}/signup/{service}", api.AppHandler(signupWithOAuth)).Methods("GET") // Bug in gorilla.mux prevents us from using regex here. watchAndParseTemplates() }
func TestGetFile(t *testing.T) { th := Setup().InitBasic() Client := th.BasicClient team := th.BasicTeam user := th.BasicUser channel := th.BasicChannel if utils.Cfg.FileSettings.DriverName != "" { body := &bytes.Buffer{} writer := multipart.NewWriter(body) part, err := writer.CreateFormFile("files", "test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("tests") file, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } field, err := writer.CreateFormField("channel_id") if err != nil { t.Fatal(err) } _, err = field.Write([]byte(channel.Id)) if err != nil { t.Fatal(err) } err = writer.Close() if err != nil { t.Fatal(err) } resp, upErr := Client.UploadPostAttachment(body.Bytes(), writer.FormDataContentType()) if upErr != nil { t.Fatal(upErr) } filenames := resp.Data.(*model.FileUploadResponse).Filenames // wait a bit for files to ready time.Sleep(5 * time.Second) if _, downErr := Client.GetFile(filenames[0], false); downErr != nil { t.Fatal(downErr) } if resp, downErr := Client.GetFileInfo(filenames[0]); downErr != nil { t.Fatal(downErr) } else { info := resp.Data.(*model.FileInfo) if info.Size == 0 { t.Fatal("No file size returned") } } if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_S3 { var auth aws.Auth auth.AccessKey = utils.Cfg.FileSettings.AmazonS3AccessKeyId auth.SecretKey = utils.Cfg.FileSettings.AmazonS3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.FileSettings.AmazonS3Region]) bucket := s.Bucket(utils.Cfg.FileSettings.AmazonS3Bucket) filenames := strings.Split(resp.Data.(*model.FileUploadResponse).Filenames[0], "/") filename := filenames[len(filenames)-2] + "/" + filenames[len(filenames)-1] fileId := strings.Split(filename, ".")[0] err = bucket.Del("teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + filename) if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_thumb.jpg") if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_preview.jpg") if err != nil { t.Fatal(err) } } else { filenames := strings.Split(resp.Data.(*model.FileUploadResponse).Filenames[0], "/") filename := filenames[len(filenames)-2] + "/" + filenames[len(filenames)-1] fileId := strings.Split(filename, ".")[0] path := utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + filename if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } path = utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_thumb.jpg" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } path = utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_preview.jpg" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } } } else { if _, downErr := Client.GetFile("/files/get/yxebdmbz5pgupx7q6ez88rw11a/n3btzxu9hbnapqk36iwaxkjxhc/junk.jpg", false); downErr.StatusCode != http.StatusNotImplemented { t.Fatal("Status code should have been 501 - Not Implemented") } } }
func TestGetPublicLink(t *testing.T) { Setup() team := &model.Team{Name: "Name", Domain: "z-z-" + model.NewId() + "a", Email: "*****@*****.**", Type: model.TEAM_OPEN} team = Client.Must(Client.CreateTeam(team)).Data.(*model.Team) user1 := &model.User{TeamId: team.Id, Email: model.NewId() + "*****@*****.**", FullName: "Corey Hulen", Password: "******"} user1 = Client.Must(Client.CreateUser(user1, "")).Data.(*model.User) Srv.Store.User().VerifyEmail(user1.Id) user2 := &model.User{TeamId: team.Id, Email: model.NewId() + "*****@*****.**", FullName: "Corey Hulen", Password: "******"} user2 = Client.Must(Client.CreateUser(user2, "")).Data.(*model.User) Srv.Store.User().VerifyEmail(user2.Id) Client.LoginByEmail(team.Domain, user1.Email, "pwd") channel1 := &model.Channel{DisplayName: "Test API Name", Name: "a" + model.NewId() + "a", Type: model.CHANNEL_OPEN, TeamId: team.Id} channel1 = Client.Must(Client.CreateChannel(channel1)).Data.(*model.Channel) if utils.IsS3Configured() { body := &bytes.Buffer{} writer := multipart.NewWriter(body) part, err := writer.CreateFormFile("files", "test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("web/static/images") file, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } field, err := writer.CreateFormField("channel_id") if err != nil { t.Fatal(err) } _, err = field.Write([]byte(channel1.Id)) if err != nil { t.Fatal(err) } err = writer.Close() if err != nil { t.Fatal(err) } resp, upErr := Client.UploadFile("/files/upload", body.Bytes(), writer.FormDataContentType()) if upErr != nil { t.Fatal(upErr) } filenames := resp.Data.(*model.FileUploadResponse).Filenames post1 := &model.Post{ChannelId: channel1.Id, Message: "a" + model.NewId() + "a", Filenames: filenames} rpost1, postErr := Client.CreatePost(post1) if postErr != nil { t.Fatal(postErr) } if rpost1.Data.(*model.Post).Filenames[0] != filenames[0] { t.Fatal("filenames don't match") } // wait a bit for files to ready time.Sleep(5 * time.Second) data := make(map[string]string) data["filename"] = filenames[0] if _, err := Client.GetPublicLink(data); err != nil { t.Fatal(err) } data["filename"] = "junk" if _, err := Client.GetPublicLink(data); err == nil { t.Fatal("Should have errored - bad file path") } Client.LoginByEmail(team.Domain, user2.Email, "pwd") data["filename"] = filenames[0] if _, err := Client.GetPublicLink(data); err == nil { t.Fatal("should have errored, user not member of channel") } // perform clean-up on s3 var auth aws.Auth auth.AccessKey = utils.Cfg.AWSSettings.S3AccessKeyId auth.SecretKey = utils.Cfg.AWSSettings.S3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.AWSSettings.S3Region]) bucket := s.Bucket(utils.Cfg.AWSSettings.S3Bucket) fileId := strings.Split(filenames[0], ".")[0] if err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + rpost1.Data.(*model.Post).UserId + "/" + filenames[0]); err != nil { t.Fatal(err) } if err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + rpost1.Data.(*model.Post).UserId + "/" + fileId + "_thumb.jpg"); err != nil { t.Fatal(err) } if err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + rpost1.Data.(*model.Post).UserId + "/" + fileId + "_preview.png"); err != nil { t.Fatal(err) } } else { data := make(map[string]string) if _, err := Client.GetPublicLink(data); err.StatusCode != http.StatusNotImplemented { t.Fatal("Status code should have been 501 - Not Implemented") } } }
func TestUploadFile(t *testing.T) { Setup() team := &model.Team{Name: "Name", Domain: "z-z-" + model.NewId() + "a", Email: "*****@*****.**", Type: model.TEAM_OPEN} team = Client.Must(Client.CreateTeam(team)).Data.(*model.Team) user1 := &model.User{TeamId: team.Id, Email: model.NewId() + "*****@*****.**", FullName: "Corey Hulen", Password: "******"} user1 = Client.Must(Client.CreateUser(user1, "")).Data.(*model.User) Srv.Store.User().VerifyEmail(user1.Id) Client.LoginByEmail(team.Domain, user1.Email, "pwd") channel1 := &model.Channel{DisplayName: "Test API Name", Name: "a" + model.NewId() + "a", Type: model.CHANNEL_OPEN, TeamId: team.Id} channel1 = Client.Must(Client.CreateChannel(channel1)).Data.(*model.Channel) body := &bytes.Buffer{} writer := multipart.NewWriter(body) part, err := writer.CreateFormFile("files", "test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("web/static/images") file, err := os.Open(path + "/test.png") defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } field, err := writer.CreateFormField("channel_id") if err != nil { t.Fatal(err) } _, err = field.Write([]byte(channel1.Id)) if err != nil { t.Fatal(err) } err = writer.Close() if err != nil { t.Fatal(err) } resp, appErr := Client.UploadFile("/files/upload", body.Bytes(), writer.FormDataContentType()) if utils.IsS3Configured() { if appErr != nil { t.Fatal(appErr) } filenames := resp.Data.(*model.FileUploadResponse).Filenames var auth aws.Auth auth.AccessKey = utils.Cfg.AWSSettings.S3AccessKeyId auth.SecretKey = utils.Cfg.AWSSettings.S3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.AWSSettings.S3Region]) bucket := s.Bucket(utils.Cfg.AWSSettings.S3Bucket) fileId := strings.Split(filenames[0], ".")[0] // wait a bit for files to ready time.Sleep(5 * time.Second) err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + filenames[0]) if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_thumb.jpg") if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_preview.png") if err != nil { t.Fatal(err) } } else { if appErr == nil { t.Fatal("S3 not configured, should have failed") } } }
func TestGetFile(t *testing.T) { Setup() team := &model.Team{Name: "Name", Domain: "z-z-" + model.NewId() + "a", Email: "*****@*****.**", Type: model.TEAM_OPEN} team = Client.Must(Client.CreateTeam(team)).Data.(*model.Team) user1 := &model.User{TeamId: team.Id, Email: model.NewId() + "*****@*****.**", FullName: "Corey Hulen", Password: "******"} user1 = Client.Must(Client.CreateUser(user1, "")).Data.(*model.User) Srv.Store.User().VerifyEmail(user1.Id) Client.LoginByEmail(team.Domain, user1.Email, "pwd") channel1 := &model.Channel{DisplayName: "Test API Name", Name: "a" + model.NewId() + "a", Type: model.CHANNEL_OPEN, TeamId: team.Id} channel1 = Client.Must(Client.CreateChannel(channel1)).Data.(*model.Channel) if utils.IsS3Configured() { body := &bytes.Buffer{} writer := multipart.NewWriter(body) part, err := writer.CreateFormFile("files", "test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("web/static/images") file, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } field, err := writer.CreateFormField("channel_id") if err != nil { t.Fatal(err) } _, err = field.Write([]byte(channel1.Id)) if err != nil { t.Fatal(err) } err = writer.Close() if err != nil { t.Fatal(err) } resp, upErr := Client.UploadFile("/files/upload", body.Bytes(), writer.FormDataContentType()) if upErr != nil { t.Fatal(upErr) } filenames := resp.Data.(*model.FileUploadResponse).Filenames // wait a bit for files to ready time.Sleep(5 * time.Second) if _, downErr := Client.GetFile(filenames[0], true); downErr != nil { t.Fatal("file get failed") } team2 := &model.Team{Name: "Name", Domain: "z-z-" + model.NewId() + "a", Email: "*****@*****.**", Type: model.TEAM_OPEN} team2 = Client.Must(Client.CreateTeam(team2)).Data.(*model.Team) user2 := &model.User{TeamId: team2.Id, Email: model.NewId() + "*****@*****.**", FullName: "Corey Hulen", Password: "******"} user2 = Client.Must(Client.CreateUser(user2, "")).Data.(*model.User) Srv.Store.User().VerifyEmail(user2.Id) newProps := make(map[string]string) newProps["filename"] = filenames[0] newProps["time"] = fmt.Sprintf("%v", model.GetMillis()) data := model.MapToJson(newProps) hash := model.HashPassword(fmt.Sprintf("%v:%v", data, utils.Cfg.ServiceSettings.PublicLinkSalt)) Client.LoginByEmail(team2.Domain, user2.Email, "pwd") if _, downErr := Client.GetFile(filenames[0]+"?d="+url.QueryEscape(data)+"&h="+url.QueryEscape(hash)+"&t="+team.Id, true); downErr != nil { t.Fatal(downErr) } if _, downErr := Client.GetFile(filenames[0]+"?d="+url.QueryEscape(data)+"&h="+url.QueryEscape(hash), true); downErr == nil { t.Fatal("Should have errored - missing team id") } if _, downErr := Client.GetFile(filenames[0]+"?d="+url.QueryEscape(data)+"&h="+url.QueryEscape(hash)+"&t=junk", true); downErr == nil { t.Fatal("Should have errored - bad team id") } if _, downErr := Client.GetFile(filenames[0]+"?d="+url.QueryEscape(data)+"&h="+url.QueryEscape(hash)+"&t=12345678901234567890123456", true); downErr == nil { t.Fatal("Should have errored - bad team id") } if _, downErr := Client.GetFile(filenames[0]+"?d="+url.QueryEscape(data)+"&t="+team.Id, true); downErr == nil { t.Fatal("Should have errored - missing hash") } if _, downErr := Client.GetFile(filenames[0]+"?d="+url.QueryEscape(data)+"&h=junk&t="+team.Id, true); downErr == nil { t.Fatal("Should have errored - bad hash") } if _, downErr := Client.GetFile(filenames[0]+"?h="+url.QueryEscape(hash)+"&t="+team.Id, true); downErr == nil { t.Fatal("Should have errored - missing data") } if _, downErr := Client.GetFile(filenames[0]+"?d=junk&h="+url.QueryEscape(hash)+"&t="+team.Id, true); downErr == nil { t.Fatal("Should have errored - bad data") } if _, downErr := Client.GetFile(filenames[0], true); downErr == nil { t.Fatal("Should have errored - user not logged in and link not public") } var auth aws.Auth auth.AccessKey = utils.Cfg.AWSSettings.S3AccessKeyId auth.SecretKey = utils.Cfg.AWSSettings.S3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.AWSSettings.S3Region]) bucket := s.Bucket(utils.Cfg.AWSSettings.S3Bucket) fileId := strings.Split(filenames[0], ".")[0] err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + filenames[0]) if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_thumb.jpg") if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_preview.png") if err != nil { t.Fatal(err) } } else { if _, downErr := Client.GetFile("/files/get/yxebdmbz5pgupx7q6ez88rw11a/n3btzxu9hbnapqk36iwaxkjxhc/junk.jpg", false); downErr.StatusCode != http.StatusNotImplemented { t.Fatal("Status code should have been 501 - Not Implemented") } } }
func authorizeOAuth(c *Context, w http.ResponseWriter, r *http.Request) { if !utils.Cfg.ServiceSettings.EnableOAuthServiceProvider { c.Err = model.NewLocAppError("authorizeOAuth", "api.oauth.authorize_oauth.disabled.app_error", nil, "") c.Err.StatusCode = http.StatusNotImplemented return } responseType := r.URL.Query().Get("response_type") clientId := r.URL.Query().Get("client_id") redirect := r.URL.Query().Get("redirect_uri") scope := r.URL.Query().Get("scope") state := r.URL.Query().Get("state") if len(scope) == 0 { scope = model.DEFAULT_SCOPE } if len(responseType) == 0 || len(clientId) == 0 || len(redirect) == 0 { c.Err = model.NewLocAppError("authorizeOAuth", "api.oauth.authorize_oauth.missing.app_error", nil, "") return } var app *model.OAuthApp if result := <-Srv.Store.OAuth().GetApp(clientId); result.Err != nil { c.Err = result.Err return } else { app = result.Data.(*model.OAuthApp) } // here we should check if the user is logged in if len(c.Session.UserId) == 0 { http.Redirect(w, r, c.GetSiteURL()+"/login?redirect_to="+url.QueryEscape(r.RequestURI), http.StatusFound) return } isAuthorized := false if result := <-Srv.Store.Preference().Get(c.Session.UserId, model.PREFERENCE_CATEGORY_AUTHORIZED_OAUTH_APP, clientId); result.Err == nil { // when we support scopes we should check if the scopes match isAuthorized = true } // Automatically allow if the app is trusted if app.IsTrusted || isAuthorized { closeBody := func(r *http.Response) { if r.Body != nil { ioutil.ReadAll(r.Body) r.Body.Close() } } doAllow := func() (*http.Response, *model.AppError) { HttpClient := &http.Client{} url := c.GetSiteURL() + "/api/v3/oauth/allow?response_type=" + model.AUTHCODE_RESPONSE_TYPE + "&client_id=" + clientId + "&redirect_uri=" + url.QueryEscape(redirect) + "&scope=" + scope + "&state=" + url.QueryEscape(state) rq, _ := http.NewRequest("GET", url, strings.NewReader("")) rq.Header.Set(model.HEADER_AUTH, model.HEADER_BEARER+" "+c.Session.Token) if rp, err := HttpClient.Do(rq); err != nil { return nil, model.NewLocAppError(url, "model.client.connecting.app_error", nil, err.Error()) } else if rp.StatusCode == 304 { return rp, nil } else if rp.StatusCode >= 300 { defer closeBody(rp) return rp, model.AppErrorFromJson(rp.Body) } else { return rp, nil } } if result, err := doAllow(); err != nil { c.Err = err return } else { //defer closeBody(result) data := model.MapFromJson(result.Body) redirectTo := data["redirect"] http.Redirect(w, r, redirectTo, http.StatusFound) return } } w.Header().Set("Content-Type", "text/html") w.Header().Set("Cache-Control", "no-cache, max-age=31556926, public") http.ServeFile(w, r, utils.FindDir(model.CLIENT_DIR)+"root.html") }
func createProfileImage(username string, userId string) ([]byte, *model.AppError) { colors := []color.NRGBA{ {197, 8, 126, 255}, {227, 207, 18, 255}, {28, 181, 105, 255}, {35, 188, 224, 255}, {116, 49, 196, 255}, {197, 8, 126, 255}, {197, 19, 19, 255}, {250, 134, 6, 255}, {227, 207, 18, 255}, {123, 201, 71, 255}, {28, 181, 105, 255}, {35, 188, 224, 255}, {116, 49, 196, 255}, {197, 8, 126, 255}, {197, 19, 19, 255}, {250, 134, 6, 255}, {227, 207, 18, 255}, {123, 201, 71, 255}, {28, 181, 105, 255}, {35, 188, 224, 255}, {116, 49, 196, 255}, {197, 8, 126, 255}, {197, 19, 19, 255}, {250, 134, 6, 255}, {227, 207, 18, 255}, {123, 201, 71, 255}, } h := fnv.New32a() h.Write([]byte(userId)) seed := h.Sum32() initial := string(strings.ToUpper(username)[0]) fontBytes, err := ioutil.ReadFile(utils.FindDir("web/static/fonts") + utils.Cfg.FileSettings.InitialFont) if err != nil { return nil, model.NewAppError("createProfileImage", "Could not create default profile image font", err.Error()) } font, err := freetype.ParseFont(fontBytes) if err != nil { return nil, model.NewAppError("createProfileImage", "Could not create default profile image font", err.Error()) } width := int(utils.Cfg.FileSettings.ProfileWidth) height := int(utils.Cfg.FileSettings.ProfileHeight) color := colors[int64(seed)%int64(len(colors))] dstImg := image.NewRGBA(image.Rect(0, 0, width, height)) srcImg := image.White draw.Draw(dstImg, dstImg.Bounds(), &image.Uniform{color}, image.ZP, draw.Src) size := float64((width + height) / 4) c := freetype.NewContext() c.SetFont(font) c.SetFontSize(size) c.SetClip(dstImg.Bounds()) c.SetDst(dstImg) c.SetSrc(srcImg) pt := freetype.Pt(width/6, height*2/3) _, err = c.DrawString(initial, pt) if err != nil { return nil, model.NewAppError("createProfileImage", "Could not add user initial to default profile picture", err.Error()) } buf := new(bytes.Buffer) if imgErr := png.Encode(buf, dstImg); imgErr != nil { return nil, model.NewAppError("createProfileImage", "Could not encode default profile image", imgErr.Error()) } else { return buf.Bytes(), nil } }
func TestUploadFile(t *testing.T) { Setup() team := &model.Team{DisplayName: "Name", Name: "z-z-" + model.NewId() + "a", Email: "*****@*****.**", Type: model.TEAM_OPEN} team = Client.Must(Client.CreateTeam(team)).Data.(*model.Team) user1 := &model.User{TeamId: team.Id, Email: model.NewId() + "*****@*****.**", Nickname: "Corey Hulen", Password: "******"} user1 = Client.Must(Client.CreateUser(user1, "")).Data.(*model.User) store.Must(Srv.Store.User().VerifyEmail(user1.Id)) Client.LoginByEmail(team.Name, user1.Email, "pwd") channel1 := &model.Channel{DisplayName: "Test API Name", Name: "a" + model.NewId() + "a", Type: model.CHANNEL_OPEN, TeamId: team.Id} channel1 = Client.Must(Client.CreateChannel(channel1)).Data.(*model.Channel) body := &bytes.Buffer{} writer := multipart.NewWriter(body) part, err := writer.CreateFormFile("files", "../test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("web/static/images") file, err := os.Open(path + "/test.png") defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } field, err := writer.CreateFormField("channel_id") if err != nil { t.Fatal(err) } _, err = field.Write([]byte(channel1.Id)) if err != nil { t.Fatal(err) } err = writer.Close() if err != nil { t.Fatal(err) } resp, appErr := Client.UploadFile("/files/upload", body.Bytes(), writer.FormDataContentType()) if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_S3 { if appErr != nil { t.Fatal(appErr) } filenames := strings.Split(resp.Data.(*model.FileUploadResponse).Filenames[0], "/") filename := filenames[len(filenames)-2] + "/" + filenames[len(filenames)-1] if strings.Contains(filename, "../") { t.Fatal("relative path should have been sanitized out") } fileId := strings.Split(filename, ".")[0] var auth aws.Auth auth.AccessKey = utils.Cfg.FileSettings.AmazonS3AccessKeyId auth.SecretKey = utils.Cfg.FileSettings.AmazonS3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.FileSettings.AmazonS3Region]) bucket := s.Bucket(utils.Cfg.FileSettings.AmazonS3Bucket) // wait a bit for files to ready time.Sleep(5 * time.Second) err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + filename) if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_thumb.jpg") if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_preview.jpg") if err != nil { t.Fatal(err) } } else if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_LOCAL { filenames := strings.Split(resp.Data.(*model.FileUploadResponse).Filenames[0], "/") filename := filenames[len(filenames)-2] + "/" + filenames[len(filenames)-1] if strings.Contains(filename, "../") { t.Fatal("relative path should have been sanitized out") } fileId := strings.Split(filename, ".")[0] // wait a bit for files to ready time.Sleep(5 * time.Second) path := utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + filename if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } path = utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_thumb.jpg" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } path = utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel1.Id + "/users/" + user1.Id + "/" + fileId + "_preview.jpg" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } } else { if appErr == nil { t.Fatal("S3 and local storage not configured, should have failed") } } }
func TestUserUploadProfileImage(t *testing.T) { Setup() team := &model.Team{DisplayName: "Name", Name: "z-z-" + model.NewId() + "a", Email: "*****@*****.**", Type: model.TEAM_OPEN} team = Client.Must(Client.CreateTeam(team)).Data.(*model.Team) user := &model.User{TeamId: team.Id, Email: strings.ToLower(model.NewId()) + "*****@*****.**", Nickname: "Corey Hulen", Password: "******"} user = Client.Must(Client.CreateUser(user, "")).Data.(*model.User) store.Must(Srv.Store.User().VerifyEmail(user.Id)) if utils.IsS3Configured() || utils.Cfg.ServiceSettings.UseLocalStorage { body := &bytes.Buffer{} writer := multipart.NewWriter(body) if _, upErr := Client.UploadFile("/users/newimage", body.Bytes(), writer.FormDataContentType()); upErr == nil { t.Fatal("Should have errored") } Client.LoginByEmail(team.Name, user.Email, "pwd") if _, upErr := Client.UploadFile("/users/newimage", body.Bytes(), writer.FormDataContentType()); upErr == nil { t.Fatal("Should have errored") } part, err := writer.CreateFormFile("blargh", "test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("web/static/images") file, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } if err := writer.Close(); err != nil { t.Fatal(err) } if _, upErr := Client.UploadFile("/users/newimage", body.Bytes(), writer.FormDataContentType()); upErr == nil { t.Fatal("Should have errored") } file2, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file2.Close() body = &bytes.Buffer{} writer = multipart.NewWriter(body) part, err = writer.CreateFormFile("image", "test.png") if err != nil { t.Fatal(err) } if _, err := io.Copy(part, file2); err != nil { t.Fatal(err) } if err := writer.Close(); err != nil { t.Fatal(err) } if _, upErr := Client.UploadFile("/users/newimage", body.Bytes(), writer.FormDataContentType()); upErr != nil { t.Fatal(upErr) } Client.DoGet("/users/"+user.Id+"/image", "", "") if utils.IsS3Configured() && !utils.Cfg.ServiceSettings.UseLocalStorage { var auth aws.Auth auth.AccessKey = utils.Cfg.AWSSettings.S3AccessKeyId auth.SecretKey = utils.Cfg.AWSSettings.S3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.AWSSettings.S3Region]) bucket := s.Bucket(utils.Cfg.AWSSettings.S3Bucket) if err := bucket.Del("teams/" + user.TeamId + "/users/" + user.Id + "/profile.png"); err != nil { t.Fatal(err) } } else { path := utils.Cfg.ServiceSettings.StorageDirectory + "teams/" + user.TeamId + "/users/" + user.Id + "/profile.png" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } } } else { body := &bytes.Buffer{} writer := multipart.NewWriter(body) if _, upErr := Client.UploadFile("/users/newimage", body.Bytes(), writer.FormDataContentType()); upErr.StatusCode != http.StatusNotImplemented { t.Fatal("Should have failed with 501 - Not Implemented") } } }
func TestUserUploadProfileImage(t *testing.T) { th := Setup() Client := th.CreateClient() team := &model.Team{DisplayName: "Name", Name: "z-z-" + model.NewId() + "a", Email: "*****@*****.**", Type: model.TEAM_OPEN} team = Client.Must(Client.CreateTeam(team)).Data.(*model.Team) user := &model.User{Email: strings.ToLower(model.NewId()) + "*****@*****.**", Nickname: "Corey Hulen", Password: "******"} user = Client.Must(Client.CreateUser(user, "")).Data.(*model.User) LinkUserToTeam(user, team) store.Must(Srv.Store.User().VerifyEmail(user.Id)) if utils.Cfg.FileSettings.DriverName != "" { body := &bytes.Buffer{} writer := multipart.NewWriter(body) if _, upErr := Client.UploadProfileFile(body.Bytes(), writer.FormDataContentType()); upErr == nil { t.Fatal("Should have errored") } Client.Login(user.Email, "pwd") Client.SetTeamId(team.Id) if _, upErr := Client.UploadProfileFile(body.Bytes(), writer.FormDataContentType()); upErr == nil { t.Fatal("Should have errored") } part, err := writer.CreateFormFile("blargh", "test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("tests") file, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } if err := writer.Close(); err != nil { t.Fatal(err) } if _, upErr := Client.UploadProfileFile(body.Bytes(), writer.FormDataContentType()); upErr == nil { t.Fatal("Should have errored") } file2, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file2.Close() body = &bytes.Buffer{} writer = multipart.NewWriter(body) part, err = writer.CreateFormFile("image", "test.png") if err != nil { t.Fatal(err) } if _, err := io.Copy(part, file2); err != nil { t.Fatal(err) } if err := writer.Close(); err != nil { t.Fatal(err) } if _, upErr := Client.UploadProfileFile(body.Bytes(), writer.FormDataContentType()); upErr != nil { t.Fatal(upErr) } Client.DoApiGet("/users/"+user.Id+"/image", "", "") if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_S3 { var auth aws.Auth auth.AccessKey = utils.Cfg.FileSettings.AmazonS3AccessKeyId auth.SecretKey = utils.Cfg.FileSettings.AmazonS3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.FileSettings.AmazonS3Region]) bucket := s.Bucket(utils.Cfg.FileSettings.AmazonS3Bucket) if err := bucket.Del("users/" + user.Id + "/profile.png"); err != nil { t.Fatal(err) } } else { path := utils.Cfg.FileSettings.Directory + "users/" + user.Id + "/profile.png" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } } } else { body := &bytes.Buffer{} writer := multipart.NewWriter(body) if _, upErr := Client.UploadProfileFile(body.Bytes(), writer.FormDataContentType()); upErr.StatusCode != http.StatusNotImplemented { t.Fatal("Should have failed with 501 - Not Implemented") } } }
func TestUploadFile(t *testing.T) { th := Setup().InitBasic() Client := th.BasicClient team := th.BasicTeam user := th.BasicUser channel := th.BasicChannel body := &bytes.Buffer{} writer := multipart.NewWriter(body) part, err := writer.CreateFormFile("files", "../test.png") if err != nil { t.Fatal(err) } path := utils.FindDir("tests") file, err := os.Open(path + "/test.png") if err != nil { t.Fatal(err) } defer file.Close() _, err = io.Copy(part, file) if err != nil { t.Fatal(err) } field, err := writer.CreateFormField("channel_id") if err != nil { t.Fatal(err) } _, err = field.Write([]byte(channel.Id)) if err != nil { t.Fatal(err) } err = writer.Close() if err != nil { t.Fatal(err) } resp, appErr := Client.UploadPostAttachment(body.Bytes(), writer.FormDataContentType()) if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_S3 { if appErr != nil { t.Fatal(appErr) } filenames := strings.Split(resp.Data.(*model.FileUploadResponse).Filenames[0], "/") filename := filenames[len(filenames)-2] + "/" + filenames[len(filenames)-1] if strings.Contains(filename, "../") { t.Fatal("relative path should have been sanitized out") } fileId := strings.Split(filename, ".")[0] var auth aws.Auth auth.AccessKey = utils.Cfg.FileSettings.AmazonS3AccessKeyId auth.SecretKey = utils.Cfg.FileSettings.AmazonS3SecretAccessKey s := s3.New(auth, aws.Regions[utils.Cfg.FileSettings.AmazonS3Region]) bucket := s.Bucket(utils.Cfg.FileSettings.AmazonS3Bucket) // wait a bit for files to ready time.Sleep(5 * time.Second) err = bucket.Del("teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + filename) if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_thumb.jpg") if err != nil { t.Fatal(err) } err = bucket.Del("teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_preview.jpg") if err != nil { t.Fatal(err) } } else if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_LOCAL { filenames := strings.Split(resp.Data.(*model.FileUploadResponse).Filenames[0], "/") filename := filenames[len(filenames)-2] + "/" + filenames[len(filenames)-1] if strings.Contains(filename, "../") { t.Fatal("relative path should have been sanitized out") } fileId := strings.Split(filename, ".")[0] // wait a bit for files to ready time.Sleep(5 * time.Second) path := utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + filename if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } path = utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_thumb.jpg" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } path = utils.Cfg.FileSettings.Directory + "teams/" + team.Id + "/channels/" + channel.Id + "/users/" + user.Id + "/" + fileId + "_preview.jpg" if err := os.Remove(path); err != nil { t.Fatal("Couldn't remove file at " + path) } } else { if appErr == nil { t.Fatal("S3 and local storage not configured, should have failed") } } }