From 507fbeb068ac168868ef00bd1f40d3ba4d17c884 Mon Sep 17 00:00:00 2001 From: Elias Nahum Date: Thu, 21 Jan 2016 10:07:29 -0300 Subject: Refactoring api to use translations (chunk 1) - Add spanish translations - Files in order by name from admin to export - Does not include api templates and tests - Fix web_test to load translations - Fix i18n to fallback to DEFAULT_LOCALE if no system locale found --- api/admin.go | 4 +- api/api.go | 6 +- api/channel.go | 89 ++++++------ api/command.go | 72 +++++----- api/context.go | 32 ++--- api/export.go | 40 +++--- config/config.json | 25 +++- i18n/en.json | 386 ++++++++++++++++++++++++++++++++++++++++++++++++- i18n/es.json | 416 ++++++++++++++++++++++++++++++++++++++++++++++++++--- utils/i18n.go | 14 +- web/web_test.go | 1 + 11 files changed, 945 insertions(+), 140 deletions(-) diff --git a/api/admin.go b/api/admin.go index 72a95ba6a..bdacb3afb 100644 --- a/api/admin.go +++ b/api/admin.go @@ -17,7 +17,7 @@ import ( ) func InitAdmin(r *mux.Router) { - l4g.Debug("Initializing admin api routes") + l4g.Debug(utils.T("api.admin.init.debug")) sr := r.PathPrefix("/admin").Subrouter() sr.Handle("/logs", ApiUserRequired(getLogs)).Methods("GET") @@ -132,7 +132,7 @@ func testEmail(c *Context, w http.ResponseWriter, r *http.Request) { c.Err = result.Err return } else { - if err := utils.SendMailUsingConfig(result.Data.(*model.User).Email, "Mattermost - Testing Email Settings", "


It appears your Mattermost email is setup correctly!", cfg); err != nil { + if err := utils.SendMailUsingConfig(result.Data.(*model.User).Email, c.T("api.admin.test_email.subject"), c.T("api.admin.test_email.body"), cfg); err != nil { c.Err = err return } diff --git a/api/api.go b/api/api.go index 3b35a08fa..d0f41bcab 100644 --- a/api/api.go +++ b/api/api.go @@ -30,7 +30,7 @@ func NewServerTemplatePage(templateName string) *ServerTemplatePage { func (me *ServerTemplatePage) Render() string { var text bytes.Buffer if err := ServerTemplates.ExecuteTemplate(&text, me.TemplateName, me); err != nil { - l4g.Error("Error rendering template %v err=%v", me.TemplateName, err) + l4g.Error(utils.T("api.api.render.error"), me.TemplateName, err) } return text.String() @@ -52,10 +52,10 @@ func InitApi() { InitLicense(r) templatesDir := utils.FindDir("api/templates") - l4g.Debug("Parsing server templates at %v", templatesDir) + 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("Failed to parse server templates %v", err) + l4g.Error(utils.T("api.api.init.parsing_templates.error"), err) } } diff --git a/api/channel.go b/api/channel.go index 706baa004..de39ad1a8 100644 --- a/api/channel.go +++ b/api/channel.go @@ -8,6 +8,7 @@ import ( l4g "github.com/alecthomas/log4go" "github.com/gorilla/mux" "github.com/mattermost/platform/model" + "github.com/mattermost/platform/utils" "net/http" "strconv" "strings" @@ -18,7 +19,7 @@ const ( ) func InitChannel(r *mux.Router) { - l4g.Debug("Initializing channel api routes") + l4g.Debug(utils.T("api.channel.init.debug")) sr := r.PathPrefix("/channels").Subrouter() sr.Handle("/", ApiUserRequiredActivity(getChannels, false)).Methods("GET") @@ -56,12 +57,12 @@ func createChannel(c *Context, w http.ResponseWriter, r *http.Request) { } if channel.Type == model.CHANNEL_DIRECT { - c.Err = model.NewAppError("createDirectChannel", "Must use createDirectChannel api service for direct message channel creation", "") + c.Err = model.NewLocAppError("createDirectChannel", "api.channel.create_channel.direct_channel.app_error", nil, "") return } if strings.Index(channel.Name, "__") > 0 { - c.Err = model.NewAppError("createDirectChannel", "Invalid character '__' in channel name for non-direct channel", "") + c.Err = model.NewLocAppError("createDirectChannel", "api.channel.create_channel.invalid_character.app_error", nil, "") return } @@ -120,7 +121,7 @@ func createDirectChannel(c *Context, w http.ResponseWriter, r *http.Request) { func CreateDirectChannel(c *Context, otherUserId string) (*model.Channel, *model.AppError) { if len(otherUserId) != 26 { - return nil, model.NewAppError("CreateDirectChannel", "Invalid other user id ", otherUserId) + return nil, model.NewLocAppError("CreateDirectChannel", "api.channel.create_direct_channel.invalid_user.app_error", nil, otherUserId) } uc := Srv.Store.User().Get(otherUserId) @@ -135,7 +136,7 @@ func CreateDirectChannel(c *Context, otherUserId string) (*model.Channel, *model channel.Type = model.CHANNEL_DIRECT if uresult := <-uc; uresult.Err != nil { - return nil, model.NewAppError("CreateDirectChannel", "Invalid other user id ", otherUserId) + return nil, model.NewLocAppError("CreateDirectChannel", "api.channel.create_direct_channel.invalid_user.app_error", nil, otherUserId) } cm1 := &model.ChannelMember{ @@ -157,13 +158,13 @@ func CreateDirectChannel(c *Context, otherUserId string) (*model.Channel, *model } func CreateDefaultChannels(c *Context, teamId string) ([]*model.Channel, *model.AppError) { - townSquare := &model.Channel{DisplayName: "Town Square", Name: "town-square", Type: model.CHANNEL_OPEN, TeamId: teamId} + townSquare := &model.Channel{DisplayName: c.T("api.channel.create_default_channels.town_square"), Name: "town-square", Type: model.CHANNEL_OPEN, TeamId: teamId} if _, err := CreateChannel(c, townSquare, false); err != nil { return nil, err } - offTopic := &model.Channel{DisplayName: "Off-Topic", Name: "off-topic", Type: model.CHANNEL_OPEN, TeamId: teamId} + offTopic := &model.Channel{DisplayName: c.T("api.channel.create_default_channels.off_topic"), Name: "off-topic", Type: model.CHANNEL_OPEN, TeamId: teamId} if _, err := CreateChannel(c, offTopic, false); err != nil { return nil, err @@ -199,20 +200,20 @@ func updateChannel(c *Context, w http.ResponseWriter, r *http.Request) { } if !strings.Contains(channelMember.Roles, model.CHANNEL_ROLE_ADMIN) && !strings.Contains(c.Session.Roles, model.ROLE_TEAM_ADMIN) { - c.Err = model.NewAppError("updateChannel", "You do not have the appropriate permissions", "") + c.Err = model.NewLocAppError("updateChannel", "api.channel.update_channel.permission.app_error", nil, "") c.Err.StatusCode = http.StatusForbidden return } if oldChannel.DeleteAt > 0 { - c.Err = model.NewAppError("updateChannel", "The channel has been archived or deleted", "") + c.Err = model.NewLocAppError("updateChannel", "api.channel.update_channel.deleted.app_error", nil, "") c.Err.StatusCode = http.StatusBadRequest return } if oldChannel.Name == model.DEFAULT_CHANNEL { if (len(channel.Name) > 0 && channel.Name != oldChannel.Name) || (len(channel.Type) > 0 && channel.Type != oldChannel.Type) { - c.Err = model.NewAppError("updateChannel", "Tried to perform an invalid update of the default channel "+model.DEFAULT_CHANNEL, "") + c.Err = model.NewLocAppError("updateChannel", "api.channel.update_channel.tried.app_error", map[string]interface{}{"Channel": model.DEFAULT_CHANNEL}, "") c.Err.StatusCode = http.StatusForbidden return } @@ -293,18 +294,18 @@ func PostUpdateChannelHeaderMessageAndForget(c *Context, channelId string, oldCh uc := Srv.Store.User().Get(c.Session.UserId) if uresult := <-uc; uresult.Err != nil { - l4g.Error("Failed to retrieve user while trying to save update channel header message %v", uresult.Err) + l4g.Error(utils.T("api.channel.post_update_channel_header_message_and_forget.retrieve_user.error"), uresult.Err) return } else { user := uresult.Data.(*model.User) var message string if oldChannelHeader == "" { - message = fmt.Sprintf("%s updated the channel header to: %s", user.Username, newChannelHeader) + message = fmt.Sprintf(c.T("api.channel.post_update_channel_header_message_and_forget.updated_to"), user.Username, newChannelHeader) } else if newChannelHeader == "" { - message = fmt.Sprintf("%s removed the channel header (was: %s)", user.Username, oldChannelHeader) + message = fmt.Sprintf(c.T("api.channel.post_update_channel_header_message_and_forget.removed"), user.Username, oldChannelHeader) } else { - message = fmt.Sprintf("%s updated the channel header from: %s to: %s", user.Username, oldChannelHeader, newChannelHeader) + message = fmt.Sprintf(c.T("api.channel.post_update_channel_header_message_and_forget.updated_from"), user.Username, oldChannelHeader, newChannelHeader) } post := &model.Post{ @@ -313,7 +314,7 @@ func PostUpdateChannelHeaderMessageAndForget(c *Context, channelId string, oldCh Type: model.POST_HEADER_CHANGE, } if _, err := CreatePost(c, post, false); err != nil { - l4g.Error("Failed to post join/leave message %v", err) + l4g.Error(utils.T("api.channel.post_update_channel_header_message_and_forget.join_leave.error"), err) } } }() @@ -367,12 +368,12 @@ func getChannels(c *Context, w http.ResponseWriter, r *http.Request) { // user is already in the team if result := <-Srv.Store.Channel().GetChannels(c.Session.TeamId, c.Session.UserId); result.Err != nil { - if result.Err.Message == "No channels were found" { + if result.Err.Message == "No channels were found" { // store translation dependant // lets make sure the user is valid if result := <-Srv.Store.User().Get(c.Session.UserId); result.Err != nil { c.Err = result.Err c.RemoveSessionCookie(w, r) - l4g.Error("Error in getting users profile for id=%v forcing logout", c.Session.UserId) + l4g.Error(utils.T("api.channel.get_channels.error"), c.Session.UserId) return } } @@ -408,7 +409,7 @@ func getChannelCounts(c *Context, w http.ResponseWriter, r *http.Request) { // user is already in the team if result := <-Srv.Store.Channel().GetChannelCounts(c.Session.TeamId, c.Session.UserId); result.Err != nil { - c.Err = model.NewAppError("getChannelCounts", "Unable to get channel counts from the database", result.Err.Message) + c.Err = model.NewLocAppError("getChannelCounts", "api.channel.get_channel_counts.app_error", nil, result.Err.Message) return } else if HandleEtag(result.Data.(*model.ChannelCounts).Etag(), w, r) { return @@ -459,9 +460,9 @@ func JoinChannel(c *Context, channelId string, role string) { c.Err = err return } - PostUserAddRemoveMessageAndForget(c, channel.Id, fmt.Sprintf(`%v has joined the channel.`, user.Username)) + PostUserAddRemoveMessageAndForget(c, channel.Id, fmt.Sprintf(c.T("api.channel.join_channel.post_and_forget"), user.Username)) } else { - c.Err = model.NewAppError("join", "You do not have the appropriate permissions", "") + c.Err = model.NewLocAppError("join", "api.channel.join_channel.permissions.app_error", nil, "") c.Err.StatusCode = http.StatusForbidden return } @@ -476,24 +477,24 @@ func PostUserAddRemoveMessageAndForget(c *Context, channelId string, message str Type: model.POST_JOIN_LEAVE, } if _, err := CreatePost(c, post, false); err != nil { - l4g.Error("Failed to post join/leave message %v", err) + l4g.Error(utils.T("api.channel.post_user_add_remove_message_and_forget.error"), err) } }() } func AddUserToChannel(user *model.User, channel *model.Channel) (*model.ChannelMember, *model.AppError) { if channel.DeleteAt > 0 { - return nil, model.NewAppError("AddUserToChannel", "The channel has been archived or deleted", "") + return nil, model.NewLocAppError("AddUserToChannel", "api.channel.add_user_to_channel.deleted.app_error", nil, "") } if channel.Type != model.CHANNEL_OPEN && channel.Type != model.CHANNEL_PRIVATE { - return nil, model.NewAppError("AddUserToChannel", "Can not add user to this channel type", "") + return nil, model.NewLocAppError("AddUserToChannel", "api.channel.add_user_to_channel.type.app_error", nil, "") } newMember := &model.ChannelMember{ChannelId: channel.Id, UserId: user.Id, NotifyProps: model.GetDefaultChannelNotifyProps()} if cmresult := <-Srv.Store.Channel().SaveMember(newMember); cmresult.Err != nil { l4g.Error("Failed to add member user_id=%v channel_id=%v err=%v", user.Id, channel.Id, cmresult.Err) - return nil, model.NewAppError("AddUserToChannel", "Failed to add user to channel", "") + return nil, model.NewLocAppError("AddUserToChannel", "api.channel.add_user.to.channel.failed.app_error", nil, "") } go func() { @@ -559,13 +560,13 @@ func leave(c *Context, w http.ResponseWriter, r *http.Request) { } if channel.Type == model.CHANNEL_DIRECT { - c.Err = model.NewAppError("leave", "Cannot leave a direct message channel", "") + c.Err = model.NewLocAppError("leave", "api.channel.leave.direct.app_error", nil, "") c.Err.StatusCode = http.StatusForbidden return } if channel.Name == model.DEFAULT_CHANNEL { - c.Err = model.NewAppError("leave", "Cannot leave the default channel "+model.DEFAULT_CHANNEL, "") + c.Err = model.NewLocAppError("leave", "api.channel.leave.default.app_error", map[string]interface{}{"Channel": model.DEFAULT_CHANNEL}, "") c.Err.StatusCode = http.StatusForbidden return } @@ -577,7 +578,7 @@ func leave(c *Context, w http.ResponseWriter, r *http.Request) { RemoveUserFromChannel(c.Session.UserId, c.Session.UserId, channel) - PostUserAddRemoveMessageAndForget(c, channel.Id, fmt.Sprintf(`%v has left the channel.`, user.Username)) + PostUserAddRemoveMessageAndForget(c, channel.Id, fmt.Sprintf(c.T("api.channel.leave.left"), user.Username)) result := make(map[string]string) result["id"] = channel.Id @@ -623,19 +624,19 @@ func deleteChannel(c *Context, w http.ResponseWriter, r *http.Request) { } if !strings.Contains(channelMember.Roles, model.CHANNEL_ROLE_ADMIN) && !strings.Contains(c.Session.Roles, model.ROLE_TEAM_ADMIN) { - c.Err = model.NewAppError("deleteChannel", "You do not have the appropriate permissions", "") + c.Err = model.NewLocAppError("deleteChannel", "api.channel.delete_channel.permissions.app_error", nil, "") c.Err.StatusCode = http.StatusForbidden return } if channel.DeleteAt > 0 { - c.Err = model.NewAppError("deleteChannel", "The channel has been archived or deleted", "") + c.Err = model.NewLocAppError("deleteChannel", "api.channel.delete_channel.deleted.app_error", nil, "") c.Err.StatusCode = http.StatusBadRequest return } if channel.Name == model.DEFAULT_CHANNEL { - c.Err = model.NewAppError("deleteChannel", "Cannot delete the default channel "+model.DEFAULT_CHANNEL, "") + c.Err = model.NewLocAppError("deleteChannel", "api.channel.delete_channel.cannot.app_error", map[string]interface{}{"Channel": model.DEFAULT_CHANNEL}, "") c.Err.StatusCode = http.StatusForbidden return } @@ -644,7 +645,7 @@ func deleteChannel(c *Context, w http.ResponseWriter, r *http.Request) { for _, hook := range incomingHooks { go func() { if result := <-Srv.Store.Webhook().DeleteIncoming(hook.Id, now); result.Err != nil { - l4g.Error("Encountered error deleting incoming webhook, id=" + hook.Id) + l4g.Error(utils.T("api.channel.delete_channel.incoming_webhook.error"), hook.Id) } }() } @@ -652,7 +653,7 @@ func deleteChannel(c *Context, w http.ResponseWriter, r *http.Request) { for _, hook := range outgoingHooks { go func() { if result := <-Srv.Store.Webhook().DeleteOutgoing(hook.Id, now); result.Err != nil { - l4g.Error("Encountered error deleting outgoing webhook, id=" + hook.Id) + l4g.Error(utils.T("api.channel.delete_channel.outgoing_webhook.error"), hook.Id) } }() } @@ -665,11 +666,11 @@ func deleteChannel(c *Context, w http.ResponseWriter, r *http.Request) { c.LogAudit("name=" + channel.Name) post := &model.Post{ChannelId: channel.Id, Message: fmt.Sprintf( - `%v has archived the channel.`, + c.T("api.channel.delete_channel.archived"), user.Username)} if _, err := CreatePost(c, post, false); err != nil { - l4g.Error("Failed to post archive message %v", err) - c.Err = model.NewAppError("deleteChannel", "Failed to send archive message", "") + l4g.Error(utils.T("api.channel.delete_channel.failed_post.error"), err) + c.Err = model.NewLocAppError("deleteChannel", "api.channel.delete_channel.failed_send.app_error", nil, "") return } @@ -743,7 +744,7 @@ func getChannelExtraInfo(c *Context, w http.ResponseWriter, r *http.Request) { if memberLimitString, ok := params["member_limit"]; !ok { memberLimit = defaultExtraMemberLimit } else if memberLimitInt64, err := strconv.ParseInt(memberLimitString, 10, 0); err != nil { - c.Err = model.NewAppError("getChannelExtraInfo", "Failed to parse member limit", err.Error()) + c.Err = model.NewLocAppError("getChannelExtraInfo", "api.channel.get_channel_extra_info.member_limit.app_error", nil, err.Error()) return } else { memberLimit = int(memberLimitInt64) @@ -790,7 +791,7 @@ func getChannelExtraInfo(c *Context, w http.ResponseWriter, r *http.Request) { } if channel.DeleteAt > 0 { - c.Err = model.NewAppError("getChannelExtraInfo", "The channel has been archived or deleted", "") + c.Err = model.NewLocAppError("getChannelExtraInfo", "api.channel.get_channel_extra_info.deleted.app_error", nil, "") c.Err.StatusCode = http.StatusBadRequest return } @@ -825,17 +826,17 @@ func addMember(c *Context, w http.ResponseWriter, r *http.Request) { } if nresult := <-nuc; nresult.Err != nil { - c.Err = model.NewAppError("addMember", "Failed to find user to be added", "") + c.Err = model.NewLocAppError("addMember", "api.channel.add_member.find_user.app_error", nil, "") return } else if cresult := <-sc; cresult.Err != nil { - c.Err = model.NewAppError("addMember", "Failed to find channel", "") + c.Err = model.NewLocAppError("addMember", "api.channel.add_member.find_channel.app_error", nil, "") return } else { channel := cresult.Data.(*model.Channel) nUser := nresult.Data.(*model.User) if oresult := <-ouc; oresult.Err != nil { - c.Err = model.NewAppError("addMember", "Failed to find user doing the adding", "") + c.Err = model.NewLocAppError("addMember", "api.channel.add_member.user_adding.app_error", nil, "") return } else { oUser := oresult.Data.(*model.User) @@ -848,7 +849,7 @@ func addMember(c *Context, w http.ResponseWriter, r *http.Request) { c.LogAudit("name=" + channel.Name + " user_id=" + userId) - PostUserAddRemoveMessageAndForget(c, channel.Id, fmt.Sprintf(`%v added to the channel by %v`, nUser.Username, oUser.Username)) + PostUserAddRemoveMessageAndForget(c, channel.Id, fmt.Sprintf(c.T("api.channel.add_member.added"), nUser.Username, oUser.Username)) <-Srv.Store.Channel().UpdateLastViewedAt(id, oUser.Id) w.Write([]byte(cm.ToJson())) @@ -886,13 +887,13 @@ func removeMember(c *Context, w http.ResponseWriter, r *http.Request) { } if !strings.Contains(removerChannelMember.Roles, model.CHANNEL_ROLE_ADMIN) && !c.IsTeamAdmin() { - c.Err = model.NewAppError("updateChannel", "You do not have the appropriate permissions ", "") + c.Err = model.NewLocAppError("updateChannel", "api.channel.remove_member.permissions.app_error", nil, "") c.Err.StatusCode = http.StatusForbidden return } if err := RemoveUserFromChannel(userIdToRemove, c.Session.UserId, channel); err != nil { - c.Err = model.NewAppError("updateChannel", "Unable to remove user.", err.Message) + c.Err = model.NewLocAppError("updateChannel", "api.channel.remove_member.unable.app_error", nil, err.Message) return } @@ -908,7 +909,7 @@ func removeMember(c *Context, w http.ResponseWriter, r *http.Request) { func RemoveUserFromChannel(userIdToRemove string, removerUserId string, channel *model.Channel) *model.AppError { if channel.DeleteAt > 0 { - return model.NewAppError("updateChannel", "The channel has been archived or deleted", "") + return model.NewLocAppError("updateChannel", "api.channel.remove_user_from_channel.deleted.app_error", nil, "") } if cmresult := <-Srv.Store.Channel().RemoveMember(channel.Id, userIdToRemove); cmresult.Err != nil { diff --git a/api/command.go b/api/command.go index 00293cf16..ab63a15a7 100644 --- a/api/command.go +++ b/api/command.go @@ -36,12 +36,12 @@ var ( shrugCommand, meCommand, } - commandNotImplementedErr = model.NewAppError("checkCommand", "Command not implemented", "") + commandNotImplementedErr = model.NewLocAppError("checkCommand", "api.command.no_implemented.app_error", nil, "") ) var echoSem chan bool func InitCommand(r *mux.Router) { - l4g.Debug("Initializing command api routes") + l4g.Debug(utils.T("api.command.init.debug")) r.Handle("/command", ApiUserRequired(command)).Methods("POST") } @@ -74,7 +74,7 @@ func command(c *Context, w http.ResponseWriter, r *http.Request) { func checkCommand(c *Context, command *model.Command) bool { if len(command.Command) == 0 || strings.Index(command.Command, "/") != 0 { - c.Err = model.NewAppError("checkCommand", "Command must start with /", "") + c.Err = model.NewLocAppError("checkCommand", "api.command.check_command.start.app_error", nil, "") return false } @@ -118,7 +118,7 @@ func logoutCommand(c *Context, command *model.Command) bool { cmd := cmds["logoutCommand"] if strings.Index(command.Command, cmd) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Logout"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.command.logout_command.description")}) if !command.Suggest { command.GotoLocation = "/logout" @@ -127,7 +127,7 @@ func logoutCommand(c *Context, command *model.Command) bool { } } else if strings.Index(cmd, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Logout"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.command.logout_command.description")}) } return false @@ -160,7 +160,7 @@ func echoCommand(c *Context, command *model.Command) bool { } if delay > 10000 { - c.Err = model.NewAppError("echoCommand", "Delays must be under 10000 seconds", "") + c.Err = model.NewLocAppError("echoCommand", "api.command.echo_command.under.app_error", nil, "") return false } @@ -170,7 +170,7 @@ func echoCommand(c *Context, command *model.Command) bool { } if len(echoSem) >= maxThreads { - c.Err = model.NewAppError("echoCommand", "High volume of echo request, cannot process request", "") + c.Err = model.NewLocAppError("echoCommand", "api.command.echo_command.high_volume.app_error", nil, "") return false } @@ -184,7 +184,7 @@ func echoCommand(c *Context, command *model.Command) bool { time.Sleep(time.Duration(delay) * time.Second) if _, err := CreatePost(c, post, true); err != nil { - l4g.Error("Unable to create /echo post, err=%v", err) + l4g.Error(utils.T("api.command.echo_command.create.error"), err) } }() @@ -192,7 +192,7 @@ func echoCommand(c *Context, command *model.Command) bool { return true } else if strings.Index(cmd, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Echo back text from your account, /echo \"message\" [delay in seconds]"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.command.echo_command.description")}) } return false @@ -213,14 +213,14 @@ func meCommand(c *Context, command *model.Command) bool { post.Message = message post.ChannelId = command.ChannelId if _, err := CreatePost(c, post, false); err != nil { - l4g.Error("Unable to create /me post post, err=%v", err) + l4g.Error(utils.T("api.command.me_command.create.error"), err) return false } command.Response = model.RESP_EXECUTED return true } else if strings.Index(cmd, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Do an action, /me [message]"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.command.me_command.description")}) } return false @@ -241,14 +241,14 @@ func shrugCommand(c *Context, command *model.Command) bool { post.Message = message post.ChannelId = command.ChannelId if _, err := CreatePost(c, post, false); err != nil { - l4g.Error("Unable to create /shrug post post, err=%v", err) + l4g.Error(utils.T("api.command.shrug_command.create.error"), err) return false } command.Response = model.RESP_EXECUTED return true } else if strings.Index(cmd, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Adds ¯\\_(ツ)_/¯ to your message, /shrug [message]"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.command.shrug_command.description")}) } return false @@ -295,12 +295,12 @@ func joinCommand(c *Context, command *model.Command) bool { } if len(startsWith) == 0 || strings.Index(v.Name, startsWith) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd + " " + v.Name, Description: "Join the open channel"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd + " " + v.Name, Description: c.T("api.commmand.join_command.description")}) } } } } else if strings.Index(cmd, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Join an open channel"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.commmand.join_command.description")}) } return false @@ -331,7 +331,7 @@ func loadTestCommand(c *Context, command *model.Command) bool { return true } } else if strings.Index(cmd, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Debug Load Testing"}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.command.load_test_command.description")}) } return false @@ -416,7 +416,7 @@ func loadTestSetupCommand(c *Context, command *model.Command) bool { if doTeams { if err := CreateBasicUser(client); err != nil { - l4g.Error("Failed to create testing environment") + l4g.Error(utils.T("api.command.load_test_setup_command.create.error")) return true } client.LoginByEmail(BTEST_TEAM_NAME, BTEST_USER_EMAIL, BTEST_USER_PASSWORD) @@ -428,13 +428,13 @@ func loadTestSetupCommand(c *Context, command *model.Command) bool { utils.Range{numPosts, numPosts}, doFuzz) if err != true { - l4g.Error("Failed to create testing environment") + l4g.Error(utils.T("api.command.load_test_setup_command.create.error")) return true } else { l4g.Info("Testing environment created") for i := 0; i < len(environment.Teams); i++ { - l4g.Info("Team Created: " + environment.Teams[i].Name) - l4g.Info("\t User to login: " + environment.Environments[i].Users[0].Email + ", " + USER_PASSWORD) + l4g.Info(utils.T("api.command.load_test_setup_command.created.info"), environment.Teams[i].Name) + l4g.Info(utils.T("api.command.load_test_setup_command.login.info"), environment.Environments[i].Users[0].Email, USER_PASSWORD) } } } else { @@ -451,7 +451,7 @@ func loadTestSetupCommand(c *Context, command *model.Command) bool { } else if strings.Index(cmd, command.Command) == 0 { command.AddSuggestion(&model.SuggestCommand{ Suggestion: cmd, - Description: "Creates a testing environment in current team. [teams] [fuzz] "}) + Description: c.T("api.command.load_test_setup_command.description")}) } return false @@ -478,10 +478,10 @@ func loadTestUsersCommand(c *Context, command *model.Command) bool { userCreator.CreateTestUsers(usersr) return true } else if strings.Index(cmd1, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd1, Description: "Add a specified number of random users to current team "}) - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: "Add a specified number of random users with fuzz text to current team "}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd1, Description: c.T("api.command.load_test_users_command.users.description")}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: c.T("api.command.load_test_users_command.fuzz.description")}) } else if strings.Index(cmd2, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: "Add a specified number of random users with fuzz text to current team "}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: c.T("api.command.load_test_users_command.fuzz.description")}) } return false @@ -509,10 +509,10 @@ func loadTestChannelsCommand(c *Context, command *model.Command) bool { channelCreator.CreateTestChannels(channelsr) return true } else if strings.Index(cmd1, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd1, Description: "Add a specified number of random channels to current team "}) - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: "Add a specified number of random channels with fuzz text to current team "}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd1, Description: c.T("api.command.load_test_channels_command.channel.description")}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: c.T("api.command.load_test_channels_command.fuzz.description")}) } else if strings.Index(cmd2, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: "Add a specified number of random channels with fuzz text to current team "}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: c.T("api.command.load_test_channels_command.fuzz.description")}) } return false @@ -568,10 +568,10 @@ func loadTestPostsCommand(c *Context, command *model.Command) bool { } return true } else if strings.Index(cmd1, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd1, Description: "Add some random posts to current channel "}) - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: "Add some random posts with fuzz text to current channel "}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd1, Description: c.T("api.command.load_test_posts_command.posts.description")}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: c.T("api.command.load_test_posts_command.fuzz.description")}) } else if strings.Index(cmd2, command.Command) == 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: "Add some random posts with fuzz text to current channel "}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd2, Description: c.T("api.command.load_test_posts_command.fuzz.description")}) } return false @@ -585,7 +585,7 @@ func loadTestUrlCommand(c *Context, command *model.Command) bool { parameters := strings.SplitN(command.Command, " ", 3) if len(parameters) != 3 { - c.Err = model.NewAppError("loadTestUrlCommand", "Command must contain a url", "") + c.Err = model.NewLocAppError("loadTestUrlCommand", "api.command.load_test_url_command.url.app_error", nil, "") return true } else { url = parameters[2] @@ -602,10 +602,10 @@ func loadTestUrlCommand(c *Context, command *model.Command) bool { var contents io.ReadCloser if r, err := http.Get(url); err != nil { - c.Err = model.NewAppError("loadTestUrlCommand", "Unable to get file", err.Error()) + c.Err = model.NewLocAppError("loadTestUrlCommand", "api.command.load_test_url_command.file.app_error", nil, err.Error()) return false } else if r.StatusCode > 400 { - c.Err = model.NewAppError("loadTestUrlCommand", "Unable to get file", r.Status) + c.Err = model.NewLocAppError("loadTestUrlCommand", "api.command.load_test_url_command.file.app_error", nil, r.Status) return false } else { contents = r.Body @@ -617,7 +617,7 @@ func loadTestUrlCommand(c *Context, command *model.Command) bool { for { length, err := contents.Read(bytes) if err != nil && err != io.EOF { - c.Err = model.NewAppError("loadTestUrlCommand", "Encountered error reading file", err.Error()) + c.Err = model.NewLocAppError("loadTestUrlCommand", "api.command.load_test_url_command.reading.app_error", nil, err.Error()) return false } @@ -630,7 +630,7 @@ func loadTestUrlCommand(c *Context, command *model.Command) bool { post.ChannelId = command.ChannelId if _, err := CreatePost(c, post, false); err != nil { - l4g.Error("Unable to create post, err=%v", err) + l4g.Error(utils.T("api.command.load_test_url_command.create.error"), err) return false } } @@ -639,7 +639,7 @@ func loadTestUrlCommand(c *Context, command *model.Command) bool { return true } else if strings.Index(cmd, command.Command) == 0 && strings.Index(command.Command, "/loadtest posts") != 0 { - command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: "Add a post containing the text from a given url to current channel "}) + command.AddSuggestion(&model.SuggestCommand{Suggestion: cmd, Description: c.T("api.command.load_test_url_command.description")}) } return false diff --git a/api/context.go b/api/context.go index a3311a971..b152d6da8 100644 --- a/api/context.go +++ b/api/context.go @@ -166,10 +166,10 @@ func (h handler) ServeHTTP(w http.ResponseWriter, r *http.Request) { if session == nil || session.IsExpired() { c.RemoveSessionCookie(w, r) - c.Err = model.NewAppError("ServeHTTP", "Invalid or expired session, please login again.", "token="+token) + c.Err = model.NewLocAppError("ServeHTTP", "api.context.session_expired.app_error", nil, "token="+token) c.Err.StatusCode = http.StatusUnauthorized } else if !session.IsOAuth && isTokenFromQueryString { - c.Err = model.NewAppError("ServeHTTP", "Session is not OAuth but token was provided in the query string", "token="+token) + c.Err = model.NewLocAppError("ServeHTTP", "api.context.token_provided.app_error", nil, "token="+token) c.Err.StatusCode = http.StatusUnauthorized } else { c.Session = *session @@ -196,7 +196,7 @@ func (h handler) ServeHTTP(w http.ResponseWriter, r *http.Request) { if c.Err == nil && h.isUserActivity && token != "" && len(c.Session.UserId) > 0 { go func() { if err := (<-Srv.Store.User().UpdateUserAndSessionActivity(c.Session.UserId, c.Session.Id, model.GetMillis())).Err; err != nil { - l4g.Error("Failed to update LastActivityAt for user_id=%v and session_id=%v, err=%v", c.Session.UserId, c.Session.Id, err) + l4g.Error(utils.T("api.context.last_activity_at.error"), c.Session.UserId, c.Session.Id, err) } }() } @@ -252,13 +252,13 @@ func (c *Context) LogAuditWithUserId(userId, extraInfo string) { } func (c *Context) LogError(err *model.AppError) { - l4g.Error("%v:%v code=%v rid=%v uid=%v ip=%v %v [details: %v]", c.Path, err.Where, err.StatusCode, + l4g.Error(utils.T("api.context.log.error"), c.Path, err.Where, err.StatusCode, c.RequestId, c.Session.UserId, c.IpAddress, err.Message, err.DetailedError) } func (c *Context) UserRequired() { if len(c.Session.UserId) == 0 { - c.Err = model.NewAppError("", "Invalid or expired session, please login again.", "UserRequired") + c.Err = model.NewLocAppError("", "api.context.session_expired.app_error", nil, "UserRequired") c.Err.StatusCode = http.StatusUnauthorized return } @@ -266,11 +266,11 @@ func (c *Context) UserRequired() { func (c *Context) SystemAdminRequired() { if len(c.Session.UserId) == 0 { - c.Err = model.NewAppError("", "Invalid or expired session, please login again.", "SystemAdminRequired") + c.Err = model.NewLocAppError("", "api.context.session_expired.app_error", nil, "SystemAdminRequired") c.Err.StatusCode = http.StatusUnauthorized return } else if !c.IsSystemAdmin() { - c.Err = model.NewAppError("", "You do not have the appropriate permissions", "AdminRequired") + c.Err = model.NewLocAppError("", "api.context.permissions.app_error", nil, "AdminRequired") c.Err.StatusCode = http.StatusForbidden return } @@ -288,7 +288,7 @@ func (c *Context) HasPermissionsToUser(userId string, where string) bool { return true } - c.Err = model.NewAppError(where, "You do not have the appropriate permissions", "userId="+userId) + c.Err = model.NewLocAppError(where, "api.context.permissions.app_error", nil, "userId="+userId) c.Err.StatusCode = http.StatusForbidden return false } @@ -303,7 +303,7 @@ func (c *Context) HasPermissionsToTeam(teamId string, where string) bool { return true } - c.Err = model.NewAppError(where, "You do not have the appropriate permissions", "userId="+c.Session.UserId+", teamId="+teamId) + c.Err = model.NewLocAppError(where, "api.context.permissions.app_error", nil, "userId="+c.Session.UserId+", teamId="+teamId) c.Err.StatusCode = http.StatusForbidden return false } @@ -313,7 +313,7 @@ func (c *Context) HasPermissionsToChannel(sc store.StoreChannel, where string) b c.Err = cresult.Err return false } else if cresult.Data.(int64) != 1 { - c.Err = model.NewAppError(where, "You do not have the appropriate permissions", "userId="+c.Session.UserId) + c.Err = model.NewLocAppError(where, "api.context.permissions.app_error", nil, "userId="+c.Session.UserId) c.Err.StatusCode = http.StatusForbidden return false } @@ -326,7 +326,7 @@ func (c *Context) HasSystemAdminPermissions(where string) bool { return true } - c.Err = model.NewAppError(where, "You do not have the appropriate permissions (system)", "userId="+c.Session.UserId) + c.Err = model.NewLocAppError(where, "api.context.system_permissions.app_error", nil, "userId="+c.Session.UserId) c.Err.StatusCode = http.StatusForbidden return false } @@ -374,12 +374,12 @@ func (c *Context) RemoveSessionCookie(w http.ResponseWriter, r *http.Request) { } func (c *Context) SetInvalidParam(where string, name string) { - c.Err = model.NewLocAppError(where, "api.context.invalid_param", map[string]interface{}{"Name": name}, "") + c.Err = model.NewLocAppError(where, "api.context.invalid_param.app_error", map[string]interface{}{"Name": name}, "") c.Err.StatusCode = http.StatusBadRequest } func (c *Context) SetUnknownError(where string, details string) { - c.Err = model.NewAppError(where, "An unknown error has occured. Please contact support.", details) + c.Err = model.NewLocAppError(where, "api.context.unknown.app_error", nil, details) } func (c *Context) setTeamURL(url string, valid bool) { @@ -405,7 +405,7 @@ func (c *Context) GetTeamURL() string { if !c.teamURLValid { c.SetTeamURLFromSession() if !c.teamURLValid { - l4g.Debug("TeamURL accessed when not valid. Team URL should not be used in api functions or those that are team independent") + l4g.Debug(utils.T("api.context.invalid_team_url.debug")) } } return c.teamURL @@ -510,7 +510,7 @@ func RenderWebError(err *model.AppError, w http.ResponseWriter, r *http.Request) } func Handle404(w http.ResponseWriter, r *http.Request) { - err := model.NewAppError("Handle404", "Sorry, we could not find the page.", "") + err := model.NewLocAppError("Handle404", "api.context.404.app_error", nil, "") err.StatusCode = http.StatusNotFound l4g.Error("%v: code=404 ip=%v", r.URL.Path, GetIpAddress(r)) RenderWebError(err, w, r) @@ -524,7 +524,7 @@ func GetSession(token string) *model.Session { if session == nil { if sessionResult := <-Srv.Store.Session().Get(token); sessionResult.Err != nil { - l4g.Error("Invalid session token=" + token + ", err=" + sessionResult.Err.DetailedError) + l4g.Error(utils.T("api.context.invalid_token.error"), token, sessionResult.Err.DetailedError) } else { session = sessionResult.Data.(*model.Session) diff --git a/api/export.go b/api/export.go index fa9686005..77b821147 100644 --- a/api/export.go +++ b/api/export.go @@ -70,10 +70,10 @@ func ExportToWriter(w io.Writer, options *ExportOptions) *model.AppError { // Write our options to file if optionsFile, err := zipWriter.Create(EXPORT_OPTIONS_FILE); err != nil { - return model.NewAppError("ExportToWriter", "Unable to create options file", err.Error()) + return model.NewLocAppError("ExportToWriter", "api.export.options.create.app_error", nil, err.Error()) } else { if _, err := optionsFile.Write([]byte(options.ToJson())); err != nil { - return model.NewAppError("ExportToWriter", "Unable to write to options file", err.Error()) + return model.NewLocAppError("ExportToWriter", "api.export.options.write.app_error", nil, err.Error()) } } @@ -109,10 +109,10 @@ func ExportTeams(writer ExportWriter, options *ExportOptions) *model.AppError { teams[i].PreExport() if teamFile, err := writer.Create(EXPORT_TEAMS_FOLDER + "/" + teams[i].Name + ".json"); err != nil { - return model.NewAppError("ExportTeams", "Unable to open file for export", err.Error()) + return model.NewLocAppError("ExportTeams", "api.export.open_file.app_error", nil, err.Error()) } else { if _, err := teamFile.Write([]byte(teams[i].ToJson())); err != nil { - return model.NewAppError("ExportTeams", "Unable to write to team export file", err.Error()) + return model.NewLocAppError("ExportTeams", "api.export.write_file.app_error", nil, err.Error()) } } @@ -162,10 +162,10 @@ func ExportChannels(writer ExportWriter, options *ExportOptions, teamId string) channels[i].PreExport() if channelFile, err := writer.Create(EXPORT_CHANNELS_FOLDER + "/" + channels[i].Id + ".json"); err != nil { - return model.NewAppError("ExportChannels", "Unable to open file for export", err.Error()) + return model.NewLocAppError("ExportChannels", "api.export.open_file.app_error", nil, err.Error()) } else { if _, err := channelFile.Write([]byte(channels[i].ToJson())); err != nil { - return model.NewAppError("ExportChannels", "Unable to write to export file", err.Error()) + return model.NewLocAppError("ExportChannels", "api.export.write_file.app_error", nil, err.Error()) } } @@ -177,14 +177,14 @@ func ExportChannels(writer ExportWriter, options *ExportOptions, teamId string) } if membersFile, err := writer.Create(EXPORT_CHANNELS_FOLDER + "/" + channels[i].Id + "_members.json"); err != nil { - return model.NewAppError("ExportChannels", "Unable to open file for export", err.Error()) + return model.NewLocAppError("ExportChannels", "api.export.open_file.app_error", nil, err.Error()) } else { result, err2 := json.Marshal(members) if err2 != nil { - return model.NewAppError("ExportChannels", "Unable to convert to json", err.Error()) + return model.NewLocAppError("ExportChannels", "api.export.json.app_error", nil, err.Error()) } if _, err3 := membersFile.Write([]byte(result)); err3 != nil { - return model.NewAppError("ExportChannels", "Unable to write to export file", err.Error()) + return model.NewLocAppError("ExportChannels", "api.export.write_file.app_error", nil, err.Error()) } } } @@ -209,14 +209,14 @@ func ExportPosts(writer ExportWriter, options *ExportOptions, channelId string) // Export the posts if postsFile, err := writer.Create(EXPORT_POSTS_FOLDER + "/" + channelId + "_posts.json"); err != nil { - return model.NewAppError("ExportPosts", "Unable to open file for export", err.Error()) + return model.NewLocAppError("ExportPosts", "api.export.open_file.app_error", nil, err.Error()) } else { result, err2 := json.Marshal(posts) if err2 != nil { - return model.NewAppError("ExportPosts", "Unable to convert to json", err.Error()) + return model.NewLocAppError("ExportPosts", "api.export.json.app_error", nil, err.Error()) } if _, err3 := postsFile.Write([]byte(result)); err3 != nil { - return model.NewAppError("ExportPosts", "Unable to write to export file", err.Error()) + return model.NewLocAppError("ExportPosts", "api.export.write_file.app_error", nil, err.Error()) } } @@ -234,14 +234,14 @@ func ExportUsers(writer ExportWriter, options *ExportOptions, teamId string) *mo // Write the users if usersFile, err := writer.Create(EXPORT_USERS_FOLDER + "/" + teamId + "_users.json"); err != nil { - return model.NewAppError("ExportUsers", "Unable to open file for export", err.Error()) + return model.NewLocAppError("ExportUsers", "api.export.open_file.app_error", nil, err.Error()) } else { result, err2 := json.Marshal(users) if err2 != nil { - return model.NewAppError("ExportUsers", "Unable to convert to json", err.Error()) + return model.NewLocAppError("ExportUsers", "api.export.json.app_error", nil, err.Error()) } if _, err3 := usersFile.Write([]byte(result)); err3 != nil { - return model.NewAppError("ExportUsers", "Unable to write to export file", err.Error()) + return model.NewLocAppError("ExportUsers", "api.export.write_file.app_error", nil, err.Error()) } } return nil @@ -250,12 +250,12 @@ func ExportUsers(writer ExportWriter, options *ExportOptions, teamId string) *mo func copyDirToExportWriter(writer ExportWriter, inPath string, outPath string) *model.AppError { dir, err := os.Open(inPath) if err != nil { - return model.NewAppError("copyDirToExportWriter", "Unable to open directory", err.Error()) + return model.NewLocAppError("copyDirToExportWriter", "api.export.open_dir.app_error", nil, err.Error()) } fileInfoList, err := dir.Readdir(0) if err != nil { - return model.NewAppError("copyDirToExportWriter", "Unable to read directory", err.Error()) + return model.NewLocAppError("copyDirToExportWriter", "api.export.read_dir.app_error", nil, err.Error()) } for _, fileInfo := range fileInfoList { @@ -263,11 +263,11 @@ func copyDirToExportWriter(writer ExportWriter, inPath string, outPath string) * copyDirToExportWriter(writer, inPath+"/"+fileInfo.Name(), outPath+"/"+fileInfo.Name()) } else { if toFile, err := writer.Create(outPath + "/" + fileInfo.Name()); err != nil { - return model.NewAppError("copyDirToExportWriter", "Unable to open file for export", err.Error()) + return model.NewLocAppError("copyDirToExportWriter", "api.export.open_file.app_error", nil, err.Error()) } else { fromFile, err := os.Open(inPath + "/" + fileInfo.Name()) if err != nil { - return model.NewAppError("copyDirToExportWriter", "Unable to open file", err.Error()) + return model.NewAppError("copyDirToExportWriter", "api.export.open.app_error", err.Error()) } io.Copy(toFile, fromFile) } @@ -281,7 +281,7 @@ func ExportLocalStorage(writer ExportWriter, options *ExportOptions, teamId stri teamDir := utils.Cfg.FileSettings.Directory + "teams/" + teamId if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_S3 { - return model.NewAppError("ExportLocalStorage", "S3 is not supported for local storage export.", "") + return model.NewLocAppError("ExportLocalStorage", "api.export.s3.app_error", nil, "") } else if utils.Cfg.FileSettings.DriverName == model.IMAGE_DRIVER_LOCAL { if err := copyDirToExportWriter(writer, teamDir, EXPORT_LOCAL_STORAGE_FOLDER); err != nil { return err diff --git a/config/config.json b/config/config.json index b00dbc201..907b66828 100644 --- a/config/config.json +++ b/config/config.json @@ -107,5 +107,28 @@ "AuthEndpoint": "", "TokenEndpoint": "", "UserApiEndpoint": "" + }, + "GoogleSettings": { + "Enable": false, + "Secret": "", + "Id": "", + "Scope": "", + "AuthEndpoint": "", + "TokenEndpoint": "", + "UserApiEndpoint": "" + }, + "LdapSettings": { + "Enable": false, + "LdapServer": null, + "LdapPort": 389, + "BaseDN": null, + "BindUsername": null, + "BindPassword": null, + "FirstNameAttribute": null, + "LastNameAttribute": null, + "EmailAttribute": null, + "UsernameAttribute": null, + "IdAttribute": null, + "QueryTimeout": 60 } -} +} \ No newline at end of file diff --git a/i18n/en.json b/i18n/en.json index d1035e89a..ca514f71d 100644 --- a/i18n/en.json +++ b/i18n/en.json @@ -12,7 +12,391 @@ "translation": "Error reading log file" }, { - "id": "api.context.invalid_param", + "id": "api.admin.init.debug", + "translation": "Initializing admin api routes" + }, + { + "id": "api.admin.test_email.subject", + "translation": "Mattermost - Testing Email Settings" + }, + { + "id": "api.admin.test_email.body", + "translation": "


It appears your Mattermost email is setup correctly!" + }, + { + "id": "api.api.render.error", + "translation": "Error rendering template %v err=%v" + }, + { + "id": "api.api.init.parsing_templates.debug", + "translation": "Parsing server templates at %v" + }, + { + "id": "api.api.init.parsing_templates.error", + "translation": "Failed to parse server templates %v" + }, + { + "id": "api.channel.init.debug", + "translation": "Initializing channel api routes" + }, + { + "id": "api.channel.create_channel.direct_channel.app_error", + "translation": "Must use createDirectChannel api service for direct message channel creation" + }, + { + "id": "api.channel.create_channel.invalid_character.app_error", + "translation": "Invalid character '__' in channel name for non-direct channel" + }, + { + "id": "api.channel.create_direct_channel.invalid_user.app_error", + "translation": "Invalid other user id " + }, + { + "id": "api.channel.create_default_channels.town_square", + "translation": "Town Square" + }, + { + "id": "api.channel.create_default_channels.off_topic", + "translation": "Off-Topic" + }, + { + "id": "api.channel.update_channel.permission.app_error", + "translation": "You do not have the appropriate permissions" + }, + { + "id": "api.channel.update_channel.deleted.app_error", + "translation": "The channel has been archived or deleted" + }, + { + "id": "api.channel.update_channel.tried.app_error", + "translation": "Tried to perform an invalid update of the default channel {{.Channel}}" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.retrieve_user.error", + "translation": "Failed to retrieve user while trying to save update channel header message %v" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.updated_to", + "translation": "%s updated the channel header to: %s" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.removed", + "translation": "%s removed the channel header (was: %s)" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.updated_from", + "translation": "%s updated the channel header from: %s to: %s" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.join_leave.error", + "translation": "Failed to post join/leave message %v" + }, + { + "id": "api.channel.get_channels.error", + "translation": "Error in getting users profile for id=%v forcing logout" + }, + { + "id": "api.channel.get_channel_counts.app_error", + "translation": "Unable to get channel counts from the database" + }, + { + "id": "api.channel.join_channel.post_and_forget", + "translation": "%v has joined the channel." + }, + { + "id": "api.channel.join_channel.permissions.app_error", + "translation": "You do not have the appropriate permissions" + }, + { + "id": "api.channel.post_user_add_remove_message_and_forget.error", + "translation": "Failed to post join/leave message %v" + }, + { + "id": "api.channel.add_user_to_channel.deleted.app_error", + "translation": "The channel has been archived or deleted" + }, + { + "id": "api.channel.add_user_to_channel.type.app_error", + "translation": "Can not add user to this channel type" + }, + { + "id": "api.channel.add_user.to.channel.failed.app_error", + "translation": "Failed to add user to channel" + }, + { + "id": "api.channel.leave.direct.app_error", + "translation": "Cannot leave a direct message channel" + }, + { + "id": "api.channel.leave.default.app_error", + "translation": "Cannot leave the default channel {{.Channel}}" + }, + { + "id": "api.channel.leave.left", + "translation": "%v has left the channel." + }, + { + "id": "api.channel.delete_channel.permissions.app_error", + "translation": "You do not have the appropriate permissions" + }, + { + "id": "api.channel.delete_channel.deleted.app_error", + "translation": "The channel has been archived or deleted" + }, + { + "id": "api.channel.delete_channel.cannot.app_error", + "translation": "Cannot delete the default channel {{.Channel}}" + }, + { + "id": "api.channel.delete_channel.incoming_webhook.error", + "translation": "Encountered error deleting incoming webhook, id=%v" + }, + { + "id": "api.channel.delete_channel.outgoing_webhook.error", + "translation": "Encountered error deleting outgoing webhook, id=%v" + }, + { + "id": "api.channel.delete_channel.archived", + "translation": "%v has archived the channel." + }, + { + "id": "api.channel.delete_channel.failed_post.error", + "translation": "Failed to post archive message %v" + }, + { + "id": "api.channel.delete_channel.failed_send.app_error", + "translation": "Failed to send archive message" + }, + { + "id": "api.channel.get_channel_extra_info.member_limit.app_error", + "translation": "Failed to parse member limit" + }, + { + "id": "api.channel.get_channel_extra_info.deleted.app_error", + "translation": "The channel has been archived or deleted" + }, + { + "id": "api.channel.add_member.find_user.app_error", + "translation": "Failed to find user to be added" + }, + { + "id": "api.channel.add_member.find_channel.app_error", + "translation": "Failed to find channel" + }, + { + "id": "api.channel.add_member.user_adding.app_error", + "translation": "Failed to find user doing the adding" + }, + { + "id": "api.channel.add_member.added", + "translation": "%v added to the channel by %v" + }, + { + "id": "api.channel.remove_member.permissions.app_error", + "translation": "You do not have the appropriate permissions " + }, + { + "id": "api.channel.remove_member.unable.app_error", + "translation": "Unable to remove user." + }, + { + "id": "api.channel.remove_user_from_channel.deleted.app_error", + "translation": "The channel has been archived or deleted" + }, + { + "id": "api.command.no_implemented.app_error", + "translation": "Command not implemented" + }, + { + "id": "api.command.init.debug", + "translation": "Initializing command api routes" + }, + { + "id": "api.command.check_command.start.app_error", + "translation": "Command must start with /" + }, + { + "id": "api.command.logout_command.description", + "translation": "Logout" + }, + { + "id": "api.command.echo_command.under.app_error", + "translation": "Delays must be under 10000 seconds" + }, + { + "id": "api.command.echo_command.high_volume.app_error", + "translation": "High volume of echo request, cannot process request" + }, + { + "id": "api.command.echo_command.create.error", + "translation": "Unable to create /echo post, err=%v" + }, + { + "id": "api.command.echo_command.description", + "translation": "Echo back text from your account, /echo \"message\" [delay in seconds]" + }, + { + "id": "api.command.me_command.create.error", + "translation": "Unable to create /me post post, err=%v" + }, + { + "id": "api.command.me_command.description", + "translation": "Do an action, /me [message]" + }, + { + "id": "api.command.shrug_command.create.error", + "translation": "Unable to create /shrug post post, err=%v" + }, + { + "id": "api.command.shrug_command.description", + "translation": "Adds ¯\\_(ツ)_/¯ to your message, /shrug [message]" + }, + { + "id": "api.commmand.join_command.description", + "translation": "Join the open channel" + }, + { + "id": "api.command.load_test_command.description", + "translation": "Debug Load Testing" + }, + { + "id": "api.command.load_test_setup_command.create.error", + "translation": "Failed to create testing environment" + }, + { + "id": "api.command.load_test_setup_command.created.info", + "translation": "Team Created: %v" + }, + { + "id": "api.command.load_test_setup_command.login.info", + "translation": "\t User to login: %v, %v" + }, + { + "id": "api.command.load_test_setup_command.description", + "translation": "Creates a testing environment in current team. [teams] [fuzz] " + }, + { + "id": "api.command.load_test_users_command.users.description", + "translation": "Add a specified number of random users to current team " + }, + { + "id": "api.command.load_test_users_command.fuzz.description", + "translation": "Add a specified number of random users with fuzz text to current team " + }, + { + "id": "api.command.load_test_channels_command.channel.description", + "translation": "Add a specified number of random channels to current team " + }, + { + "id": "api.command.load_test_channels_command.fuzz.description", + "translation": "Add a specified number of random channels with fuzz text to current team " + }, + { + "id": "api.command.load_test_posts_command.posts.description", + "translation": "Add some random posts to current channel " + }, + { + "id": "api.command.load_test_posts_command.fuzz.description", + "translation": "Add some random posts with fuzz text to current channel " + }, + { + "id": "api.command.load_test_url_command.url.app_error", + "translation": "Command must contain a url" + }, + { + "id": "api.command.load_test_url_command.file.app_error", + "translation": "Unable to get file" + }, + { + "id": "api.command.load_test_url_command.reading.app_error", + "translation": "Encountered error reading file" + }, + { + "id": "api.command.load_test_url_command.create.error", + "translation": "Unable to create post, err=%v" + }, + { + "id": "api.command.load_test_url_command.description", + "translation": "Add a post containing the text from a given url to current channel " + }, + { + "id": "api.context.invalid_param.app_error", "translation": "Invalid {{.Name}} parameter" + }, + { + "id": "api.context.session_expired.app_error", + "translation": "Invalid or expired session, please login again." + }, + { + "id": "api.context.token_provided.app_error", + "translation": "Session is not OAuth but token was provided in the query string" + }, + { + "id": "api.context.last_activity_at.error", + "translation": "Failed to update LastActivityAt for user_id=%v and session_id=%v, err=%v" + }, + { + "id": "api.context.log.error", + "translation": "%v:%v code=%v rid=%v uid=%v ip=%v %v [details: %v]" + }, + { + "id": "api.context.permissions.app_error", + "translation": "You do not have the appropriate permissions" + }, + { + "id": "api.context.system_permissions.app_error", + "translation": "You do not have the appropriate permissions (system)" + }, + { + "id": "api.context.unknown.app_error", + "translation": "An unknown error has occured. Please contact support." + }, + { + "id": "api.context.invalid_team_url.debug", + "translation": "TeamURL accessed when not valid. Team URL should not be used in api functions or those that are team independent" + }, + { + "id": "api.context.404.app_error", + "translation": "Sorry, we could not find the page." + }, + { + "id": "api.context.invalid_token.error", + "translation": "Invalid session token=%v, err=%v" + }, + { + "id": "api.export.options.create.app_error", + "translation": "Unable to create options file" + }, + { + "id": "api.export.options.write.app_error", + "translation": "Unable to write to options file" + }, + { + "id": "api.export.open_file.app_error", + "translation": "Unable to open file for export" + }, + { + "id": "api.export.write_file.app_error", + "translation": "Unable to write to export file" + }, + { + "id": "api.export.json.app_error", + "translation": "Unable to convert to json" + }, + { + "id": "api.export.open.app_error", + "translation": "Unable to open file" + }, + { + "id": "api.export.open_dir.app_error", + "translation": "Unable to open directory" + }, + { + "id": "api.export.read_dir.app_error", + "translation": "Unable to read directory" + }, + { + "id": "api.export.s3.app_error", + "translation": "S3 is not supported for local storage export." } ] \ No newline at end of file diff --git a/i18n/es.json b/i18n/es.json index efa5b857b..ca26da673 100644 --- a/i18n/es.json +++ b/i18n/es.json @@ -1,18 +1,402 @@ [ - { - "id": "utils.i18n.loaded", - "translation": "Loaded system translations for '%v' from '%v' spanish test!" - }, - { - "id": "mattermost.current_version", - "translation": "Current version is %v (%v/%v/%v) spanish test!" - }, - { - "id": "api.admin.file_read_error", - "translation": "Error reading log file spanish test!" - }, - { - "id": "api.context.invalid_param", - "translation": "Invalid {{.Name}} parameter spanish test!" - } + { + "id": "api.admin.file_read_error", + "translation": "Error leyendo el archivo de registro" + }, + { + "id": "api.admin.init.debug", + "translation": "Inicializando rutas del API para la administración" + }, + { + "id": "api.admin.test_email.body", + "translation": "


Parece que tu correo electrónico para Mattermost fue configurado correctamente!" + }, + { + "id": "api.admin.test_email.subject", + "translation": "Mattermost - Configuración de pruebas de correo" + }, + { + "id": "api.api.init.parsing_templates.debug", + "translation": "Analizando el contenido plantillas del servidor en %v" + }, + { + "id": "api.api.init.parsing_templates.error", + "translation": "Falla al analizar el contenido de las plantillas de servidor %v" + }, + { + "id": "api.api.render.error", + "translation": "Error renderinzando la plantilla %v err=%v" + }, + { + "id": "api.channel.add_member.added", + "translation": "%v agregado al canal por %v" + }, + { + "id": "api.channel.add_member.find_channel.app_error", + "translation": "Falla al encontrar el canal" + }, + { + "id": "api.channel.add_member.find_user.app_error", + "translation": "Falla al encontrar el usuario a ser agregado" + }, + { + "id": "api.channel.add_member.user_adding.app_error", + "translation": "Falla al encontrar el usuario mientras se agregaba" + }, + { + "id": "api.channel.add_user.to.channel.failed.app_error", + "translation": "Falla al agregar el usuario al canal" + }, + { + "id": "api.channel.add_user_to_channel.deleted.app_error", + "translation": "El canal ha sido archivado o eliminado" + }, + { + "id": "api.channel.add_user_to_channel.type.app_error", + "translation": "No se puede agregar al usuario a este tipo de canal" + }, + { + "id": "api.channel.create_channel.direct_channel.app_error", + "translation": "Debe usar el servicio del api createDirectChannel para crear un mensaje directo al canal" + }, + { + "id": "api.channel.create_channel.invalid_character.app_error", + "translation": "carácter '__' inválido en el nombre del canal para un canal no-directo" + }, + { + "id": "api.channel.create_default_channels.off_topic", + "translation": "Fuera de Tópico" + }, + { + "id": "api.channel.create_default_channels.town_square", + "translation": "General" + }, + { + "id": "api.channel.create_direct_channel.invalid_user.app_error", + "translation": "Id de otro usuario inválido " + }, + { + "id": "api.channel.delete_channel.archived", + "translation": "%v ha archivado el canal." + }, + { + "id": "api.channel.delete_channel.cannot.app_error", + "translation": "No se puede eliminar el canal predeterminado {{.Channel}}" + }, + { + "id": "api.channel.delete_channel.deleted.app_error", + "translation": "El canal ha sido archivado o eliminado" + }, + { + "id": "api.channel.delete_channel.failed_post.error", + "translation": "Falla al publicar archivar el mensaje %v" + }, + { + "id": "api.channel.delete_channel.failed_send.app_error", + "translation": "Falla al enviar el archivo del mensaje" + }, + { + "id": "api.channel.delete_channel.incoming_webhook.error", + "translation": "Encontrado un error borrando el webhook de entrada, id=%v" + }, + { + "id": "api.channel.delete_channel.outgoing_webhook.error", + "translation": "Encontrado un error borrando el webhook de salida, id=%v" + }, + { + "id": "api.channel.delete_channel.permissions.app_error", + "translation": "No tienes los permisos apropiados" + }, + { + "id": "api.channel.get_channel_counts.app_error", + "translation": "No se puede obtener el contador del canal desde la base de datos" + }, + { + "id": "api.channel.get_channel_extra_info.deleted.app_error", + "translation": "El canal ha sido archivado o eliminado" + }, + { + "id": "api.channel.get_channel_extra_info.member_limit.app_error", + "translation": "Error al analizar el límite de miembros" + }, + { + "id": "api.channel.get_channels.error", + "translation": "Error obteniendo el pérfil de usuario para id=%v forzando el cierre de sesión" + }, + { + "id": "api.channel.init.debug", + "translation": "Inicializando rutas del API para los canales" + }, + { + "id": "api.channel.join_channel.permissions.app_error", + "translation": "No tienes los permisos apropiados" + }, + { + "id": "api.channel.join_channel.post_and_forget", + "translation": "%v se ha unido al canal." + }, + { + "id": "api.channel.leave.default.app_error", + "translation": "No puedes abandonar el canal predeterminado {{.Channel}}" + }, + { + "id": "api.channel.leave.direct.app_error", + "translation": "No puedes dejar un mensaje directo a un canal" + }, + { + "id": "api.channel.leave.left", + "translation": "%v ha abandonado el canal." + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.join_leave.error", + "translation": "Fallo al publicar el mensaje de unir/abandonar %v" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.removed", + "translation": "%s removió el encabezado del canal (era: %s)" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.retrieve_user.error", + "translation": "No se pudo recuperar de usuario al intentar guardar la actualización del encabezado del canal %v" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.updated_from", + "translation": "%s actualizó el encabezado del canal de: %s a: %s" + }, + { + "id": "api.channel.post_update_channel_header_message_and_forget.updated_to", + "translation": "%s actualizó el encabezado del canal a: %s" + }, + { + "id": "api.channel.post_user_add_remove_message_and_forget.error", + "translation": "Fallo al publicar el mensaje de unir/abandonar %v" + }, + { + "id": "api.channel.remove_member.permissions.app_error", + "translation": "No tienes los permisos apropiados " + }, + { + "id": "api.channel.remove_member.unable.app_error", + "translation": "No se puede remover el usuario." + }, + { + "id": "api.channel.remove_user_from_channel.deleted.app_error", + "translation": "El canal ha sido archivado o eliminado" + }, + { + "id": "api.channel.update_channel.deleted.app_error", + "translation": "El canal ha sido archivado o eliminado" + }, + { + "id": "api.channel.update_channel.permission.app_error", + "translation": "No tienes los permisos apropiados" + }, + { + "id": "api.channel.update_channel.tried.app_error", + "translation": "Intento de realizar una actualización inválida al canal predeterminado {{.Channel}}" + }, + { + "id": "api.command.check_command.start.app_error", + "translation": "El comando debe comenzar con /" + }, + { + "id": "api.command.echo_command.create.error", + "translation": "No se puede crear /echo mensaje, err=%v" + }, + { + "id": "api.command.echo_command.description", + "translation": "Echo del texto desde tu cuenta, /echo \"mensaje\" [retraso en segundos]" + }, + { + "id": "api.command.echo_command.high_volume.app_error", + "translation": "Volumen alto de solicitudes echo, no se puede procesar la solicitud" + }, + { + "id": "api.command.echo_command.under.app_error", + "translation": "El retraso debe ser menor a 10000 segundos" + }, + { + "id": "api.command.init.debug", + "translation": "Inicializando rutas del API para los comandos" + }, + { + "id": "api.command.load_test_channels_command.channel.description", + "translation": "Agrega un número específico de canales aleatorios al equipo actual " + }, + { + "id": "api.command.load_test_channels_command.fuzz.description", + "translation": "Agrega un número específico de canales aleatorios con el texto fuzz al equipo actual " + }, + { + "id": "api.command.load_test_command.description", + "translation": "Depurar pruebas de carga" + }, + { + "id": "api.command.load_test_posts_command.fuzz.description", + "translation": "Agrega algunos mensajes aleatorios con el texto fuzz al canal actual " + }, + { + "id": "api.command.load_test_posts_command.posts.description", + "translation": "Agrega algunos mensajes aleatorios al canal actual " + }, + { + "id": "api.command.load_test_setup_command.create.error", + "translation": "Falla al crear el entorno de pruebas" + }, + { + "id": "api.command.load_test_setup_command.created.info", + "translation": "Equipo Creado: %v" + }, + { + "id": "api.command.load_test_setup_command.description", + "translation": "Crea un entorno de prueba para el equipo actual. [equipos] [fuzz] " + }, + { + "id": "api.command.load_test_setup_command.login.info", + "translation": "\t Usuario que inicia sesión: %v, %v" + }, + { + "id": "api.command.load_test_url_command.create.error", + "translation": "No se pudo crear el mensaje, err=%v" + }, + { + "id": "api.command.load_test_url_command.description", + "translation": "Agraga un mensaje que contiene el texto de un url dado al canal actual " + }, + { + "id": "api.command.load_test_url_command.file.app_error", + "translation": "No se puede obtener el archivo" + }, + { + "id": "api.command.load_test_url_command.reading.app_error", + "translation": "Se encontró un error leyendo el archivo" + }, + { + "id": "api.command.load_test_url_command.url.app_error", + "translation": "El comando debe contener un url" + }, + { + "id": "api.command.load_test_users_command.fuzz.description", + "translation": "Agraga un número específico de usuarios aleatorios con el texto fuzz al equipo actual " + }, + { + "id": "api.command.load_test_users_command.users.description", + "translation": "Agrega un número específico de usuarios aleatorios al equipo actual " + }, + { + "id": "api.command.logout_command.description", + "translation": "Cerrar sesión" + }, + { + "id": "api.command.me_command.create.error", + "translation": "No se pudo crear el mensaje /me mensaje, err=%v" + }, + { + "id": "api.command.me_command.description", + "translation": "Realiza una acción, /me [mensaje]" + }, + { + "id": "api.command.no_implemented.app_error", + "translation": "Comando no implementado" + }, + { + "id": "api.command.shrug_command.create.error", + "translation": "No se pudo crear el mensaje /shrug mensaje, err=%v" + }, + { + "id": "api.command.shrug_command.description", + "translation": "Agrega ¯\\_(ツ)_/¯ a tu mensaje, /shrug [mensaje]" + }, + { + "id": "api.commmand.join_command.description", + "translation": "Unirme al canal abierto" + }, + { + "id": "api.context.404.app_error", + "translation": "Lo sentimos, pero no pudimos encontrar la página." + }, + { + "id": "api.context.invalid_param.app_error", + "translation": "Parámetro {{.Name}} inválido" + }, + { + "id": "api.context.invalid_team_url.debug", + "translation": "El URL de Equipo fue accesado de forma inválida. El URL del Equipo no debe ser utilizado en funciones del API o aquellas funciones que son independientes del equipo" + }, + { + "id": "api.context.invalid_token.error", + "translation": "Token=%v de sesión inválido, err=%v" + }, + { + "id": "api.context.last_activity_at.error", + "translation": "Falla al actualizar LastActivityAt para user_id=%v and session_id=%v, err=%v" + }, + { + "id": "api.context.log.error", + "translation": "%v:%v code=%v rid=%v uid=%v ip=%v %v [detalles: %v]" + }, + { + "id": "api.context.permissions.app_error", + "translation": "No tienes los permisos apropiados" + }, + { + "id": "api.context.session_expired.app_error", + "translation": "Sesión inválida o expirada, por favor inicia sesión otra vez." + }, + { + "id": "api.context.system_permissions.app_error", + "translation": "No tienes los permisos apropiados (admin de sistema)" + }, + { + "id": "api.context.token_provided.app_error", + "translation": "La sesión no es de tipo OAuth pero existe un token en el query string" + }, + { + "id": "api.context.unknown.app_error", + "translation": "Ocurrió un error inesperado. Por favor contacta a soporte." + }, + { + "id": "api.export.json.app_error", + "translation": "No se puede convertir a JSON" + }, + { + "id": "api.export.open.app_error", + "translation": "No se puede abrir el archivo" + }, + { + "id": "api.export.open_dir.app_error", + "translation": "No se puede abrir el directorio" + }, + { + "id": "api.export.open_file.app_error", + "translation": "No se puede abrir el archivo a exportar" + }, + { + "id": "api.export.options.create.app_error", + "translation": "No se puede crear el archivo de opciones" + }, + { + "id": "api.export.options.write.app_error", + "translation": "No se puede escribir al archivo de opciones" + }, + { + "id": "api.export.read_dir.app_error", + "translation": "No se puede leer el directorio" + }, + { + "id": "api.export.s3.app_error", + "translation": "S3 no está soportado para exportar al almacenamiento local." + }, + { + "id": "api.export.write_file.app_error", + "translation": "No se puede escribir al archivo a exportar" + }, + { + "id": "mattermost.current_version", + "translation": "La versión actual es %v (%v/%v/%v)" + }, + { + "id": "utils.i18n.loaded", + "translation": "Cargada traducciones del sistema para '%v' desde '%v'" + } ] \ No newline at end of file diff --git a/utils/i18n.go b/utils/i18n.go index 4fc8c725a..0f9b65617 100644 --- a/utils/i18n.go +++ b/utils/i18n.go @@ -36,7 +36,10 @@ func InitTranslations() { func GetTranslationsBySystemLocale() i18n.TranslateFunc { locale := model.DEFAULT_LOCALE if userLanguage, err := jibber_jabber.DetectLanguage(); err == nil { - locale = userLanguage + // only set the system locale if is supported, fallback to DEFAULT_LOCALE + if contains(userLanguage) { + locale = userLanguage + } } if locales[locale] == "" { @@ -138,3 +141,12 @@ func getTranslationsAndLocale(w http.ResponseWriter, r *http.Request) (i18n.Tran SetLocaleCookie(w, model.DEFAULT_LOCALE, 10) return translations, model.DEFAULT_LOCALE } + +func contains(l string) bool { + for _, a := range locales { + if a == l { + return true + } + } + return false +} diff --git a/web/web_test.go b/web/web_test.go index 8d40810b5..237fdceaf 100644 --- a/web/web_test.go +++ b/web/web_test.go @@ -22,6 +22,7 @@ var URL string func Setup() { if api.Srv == nil { utils.LoadConfig("config.json") + utils.InitTranslations() api.NewServer() api.StartServer() api.InitApi() -- cgit v1.2.3-1-g7c22 From aa68caa8f043008728ddd0cb34c9bcd29fd9638a Mon Sep 17 00:00:00 2001 From: Elias Nahum Date: Thu, 21 Jan 2016 12:09:56 -0300 Subject: Remove settings from config.json --- config/config.json | 23 ----------------------- 1 file changed, 23 deletions(-) diff --git a/config/config.json b/config/config.json index 907b66828..076f795cc 100644 --- a/config/config.json +++ b/config/config.json @@ -107,28 +107,5 @@ "AuthEndpoint": "", "TokenEndpoint": "", "UserApiEndpoint": "" - }, - "GoogleSettings": { - "Enable": false, - "Secret": "", - "Id": "", - "Scope": "", - "AuthEndpoint": "", - "TokenEndpoint": "", - "UserApiEndpoint": "" - }, - "LdapSettings": { - "Enable": false, - "LdapServer": null, - "LdapPort": 389, - "BaseDN": null, - "BindUsername": null, - "BindPassword": null, - "FirstNameAttribute": null, - "LastNameAttribute": null, - "EmailAttribute": null, - "UsernameAttribute": null, - "IdAttribute": null, - "QueryTimeout": 60 } } \ No newline at end of file -- cgit v1.2.3-1-g7c22 From c8d22ed1fba591e7a6b18afc5e6a6d541c11645c Mon Sep 17 00:00:00 2001 From: Elias Nahum Date: Thu, 21 Jan 2016 12:30:14 -0300 Subject: Fix bug to load the default locale if no system locale is found --- utils/i18n.go | 23 ++++++----------------- 1 file changed, 6 insertions(+), 17 deletions(-) diff --git a/utils/i18n.go b/utils/i18n.go index 0f9b65617..4b7b187a8 100644 --- a/utils/i18n.go +++ b/utils/i18n.go @@ -36,18 +36,16 @@ func InitTranslations() { func GetTranslationsBySystemLocale() i18n.TranslateFunc { locale := model.DEFAULT_LOCALE if userLanguage, err := jibber_jabber.DetectLanguage(); err == nil { - // only set the system locale if is supported, fallback to DEFAULT_LOCALE - if contains(userLanguage) { + if _, ok := locales[userLanguage]; ok { locale = userLanguage + } else { + l4g.Error("Failed to load system translations for '%v' attempting to fall back to '%v'", locale, model.DEFAULT_LOCALE) + locale = model.DEFAULT_LOCALE } } - if locales[locale] == "" { - l4g.Error("Failed to load system translations for '%v' attempting to fall back to '%v'", locale, model.DEFAULT_LOCALE) - - if locales[model.DEFAULT_LOCALE] == "" { - panic("Failed to load system translations for '" + model.DEFAULT_LOCALE + "'") - } + if locales[model.DEFAULT_LOCALE] == "" { + panic("Failed to load system translations for '" + model.DEFAULT_LOCALE + "'") } translations, _ := i18n.Tfunc(locale) @@ -141,12 +139,3 @@ func getTranslationsAndLocale(w http.ResponseWriter, r *http.Request) (i18n.Tran SetLocaleCookie(w, model.DEFAULT_LOCALE, 10) return translations, model.DEFAULT_LOCALE } - -func contains(l string) bool { - for _, a := range locales { - if a == l { - return true - } - } - return false -} -- cgit v1.2.3-1-g7c22