github.com/psyb0t/mattermost-server@v4.6.1-0.20180125161845-5503a1351abf+incompatible/app/post_test.go (about) 1 // Copyright (c) 2017-present Mattermost, Inc. All Rights Reserved. 2 // See License.txt for license information. 3 4 package app 5 6 import ( 7 "encoding/json" 8 "fmt" 9 "net/http" 10 "net/http/httptest" 11 "testing" 12 "time" 13 14 "github.com/stretchr/testify/assert" 15 "github.com/stretchr/testify/require" 16 17 "github.com/mattermost/mattermost-server/model" 18 ) 19 20 func TestUpdatePostEditAt(t *testing.T) { 21 th := Setup().InitBasic() 22 defer th.TearDown() 23 24 post := &model.Post{} 25 *post = *th.BasicPost 26 27 post.IsPinned = true 28 if saved, err := th.App.UpdatePost(post, true); err != nil { 29 t.Fatal(err) 30 } else if saved.EditAt != post.EditAt { 31 t.Fatal("shouldn't have updated post.EditAt when pinning post") 32 33 *post = *saved 34 } 35 36 time.Sleep(time.Millisecond * 100) 37 38 post.Message = model.NewId() 39 if saved, err := th.App.UpdatePost(post, true); err != nil { 40 t.Fatal(err) 41 } else if saved.EditAt == post.EditAt { 42 t.Fatal("should have updated post.EditAt when updating post message") 43 } 44 } 45 46 func TestPostReplyToPostWhereRootPosterLeftChannel(t *testing.T) { 47 // This test ensures that when replying to a root post made by a user who has since left the channel, the reply 48 // post completes successfully. This is a regression test for PLT-6523. 49 th := Setup().InitBasic() 50 defer th.TearDown() 51 52 channel := th.BasicChannel 53 userInChannel := th.BasicUser2 54 userNotInChannel := th.BasicUser 55 rootPost := th.BasicPost 56 57 if _, err := th.App.AddUserToChannel(userInChannel, channel); err != nil { 58 t.Fatal(err) 59 } 60 61 if err := th.App.RemoveUserFromChannel(userNotInChannel.Id, "", channel); err != nil { 62 t.Fatal(err) 63 } 64 65 replyPost := model.Post{ 66 Message: "asd", 67 ChannelId: channel.Id, 68 RootId: rootPost.Id, 69 ParentId: rootPost.Id, 70 PendingPostId: model.NewId() + ":" + fmt.Sprint(model.GetMillis()), 71 UserId: userInChannel.Id, 72 CreateAt: 0, 73 } 74 75 if _, err := th.App.CreatePostAsUser(&replyPost); err != nil { 76 t.Fatal(err) 77 } 78 } 79 80 func TestPostAction(t *testing.T) { 81 th := Setup().InitBasic() 82 defer th.TearDown() 83 84 th.App.UpdateConfig(func(cfg *model.Config) { 85 *cfg.ServiceSettings.AllowedUntrustedInternalConnections = "localhost 127.0.0.1" 86 }) 87 88 ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { 89 var request model.PostActionIntegrationRequest 90 err := json.NewDecoder(r.Body).Decode(&request) 91 assert.NoError(t, err) 92 assert.Equal(t, request.UserId, th.BasicUser.Id) 93 assert.Equal(t, "foo", request.Context["s"]) 94 assert.EqualValues(t, 3, request.Context["n"]) 95 fmt.Fprintf(w, `{"update": {"message": "updated"}, "ephemeral_text": "foo"}`) 96 })) 97 defer ts.Close() 98 99 interactivePost := model.Post{ 100 Message: "Interactive post", 101 ChannelId: th.BasicChannel.Id, 102 PendingPostId: model.NewId() + ":" + fmt.Sprint(model.GetMillis()), 103 UserId: th.BasicUser.Id, 104 Props: model.StringInterface{ 105 "attachments": []*model.SlackAttachment{ 106 { 107 Text: "hello", 108 Actions: []*model.PostAction{ 109 { 110 Integration: &model.PostActionIntegration{ 111 Context: model.StringInterface{ 112 "s": "foo", 113 "n": 3, 114 }, 115 URL: ts.URL, 116 }, 117 Name: "action", 118 }, 119 }, 120 }, 121 }, 122 }, 123 } 124 125 post, err := th.App.CreatePostAsUser(&interactivePost) 126 require.Nil(t, err) 127 128 attachments, ok := post.Props["attachments"].([]*model.SlackAttachment) 129 require.True(t, ok) 130 131 require.NotEmpty(t, attachments[0].Actions) 132 require.NotEmpty(t, attachments[0].Actions[0].Id) 133 134 err = th.App.DoPostAction(post.Id, "notavalidid", th.BasicUser.Id) 135 require.NotNil(t, err) 136 assert.Equal(t, http.StatusNotFound, err.StatusCode) 137 138 err = th.App.DoPostAction(post.Id, attachments[0].Actions[0].Id, th.BasicUser.Id) 139 require.Nil(t, err) 140 } 141 142 func TestPostChannelMentions(t *testing.T) { 143 th := Setup().InitBasic() 144 defer th.TearDown() 145 146 channel := th.BasicChannel 147 user := th.BasicUser 148 149 channelToMention, err := th.App.CreateChannel(&model.Channel{ 150 DisplayName: "Mention Test", 151 Name: "mention-test", 152 Type: model.CHANNEL_OPEN, 153 TeamId: th.BasicTeam.Id, 154 }, false) 155 if err != nil { 156 t.Fatal(err.Error()) 157 } 158 defer th.App.PermanentDeleteChannel(channelToMention) 159 160 _, err = th.App.AddUserToChannel(user, channel) 161 require.Nil(t, err) 162 163 post := &model.Post{ 164 Message: fmt.Sprintf("hello, ~%v!", channelToMention.Name), 165 ChannelId: channel.Id, 166 PendingPostId: model.NewId() + ":" + fmt.Sprint(model.GetMillis()), 167 UserId: user.Id, 168 CreateAt: 0, 169 } 170 171 result, err := th.App.CreatePostAsUser(post) 172 require.Nil(t, err) 173 assert.Equal(t, map[string]interface{}{ 174 "mention-test": map[string]interface{}{ 175 "display_name": "Mention Test", 176 }, 177 }, result.Props["channel_mentions"]) 178 179 post.Message = fmt.Sprintf("goodbye, ~%v!", channelToMention.Name) 180 result, err = th.App.UpdatePost(post, false) 181 require.Nil(t, err) 182 assert.Equal(t, map[string]interface{}{ 183 "mention-test": map[string]interface{}{ 184 "display_name": "Mention Test", 185 }, 186 }, result.Props["channel_mentions"]) 187 } 188 189 func TestImageProxy(t *testing.T) { 190 th := Setup().InitBasic() 191 defer th.TearDown() 192 193 for name, tc := range map[string]struct { 194 ProxyType string 195 ProxyURL string 196 ProxyOptions string 197 ImageURL string 198 ProxiedImageURL string 199 }{ 200 "atmos/camo": { 201 ProxyType: "atmos/camo", 202 ProxyURL: "https://127.0.0.1", 203 ProxyOptions: "foo", 204 ImageURL: "http://mydomain.com/myimage", 205 ProxiedImageURL: "https://127.0.0.1/f8dace906d23689e8d5b12c3cefbedbf7b9b72f5/687474703a2f2f6d79646f6d61696e2e636f6d2f6d79696d616765", 206 }, 207 "willnorris/imageproxy": { 208 ProxyType: "willnorris/imageproxy", 209 ProxyURL: "https://127.0.0.1", 210 ProxyOptions: "x1000", 211 ImageURL: "http://mydomain.com/myimage", 212 ProxiedImageURL: "https://127.0.0.1/x1000/http://mydomain.com/myimage", 213 }, 214 "willnorris/imageproxy_WithSigning": { 215 ProxyType: "willnorris/imageproxy", 216 ProxyURL: "https://127.0.0.1", 217 ProxyOptions: "x1000|foo", 218 ImageURL: "http://mydomain.com/myimage", 219 ProxiedImageURL: "https://127.0.0.1/x1000,sbhHVoG5d60UvnNtGh6Iy6x4PaMmnsh8JfZ7JfErKjGU=/http://mydomain.com/myimage", 220 }, 221 } { 222 t.Run(name, func(t *testing.T) { 223 th.App.UpdateConfig(func(cfg *model.Config) { 224 cfg.ServiceSettings.ImageProxyType = model.NewString(tc.ProxyType) 225 cfg.ServiceSettings.ImageProxyOptions = model.NewString(tc.ProxyOptions) 226 cfg.ServiceSettings.ImageProxyURL = model.NewString(tc.ProxyURL) 227 }) 228 229 post := &model.Post{ 230 Id: model.NewId(), 231 Message: "", 232 } 233 234 list := model.NewPostList() 235 list.Posts[post.Id] = post 236 237 assert.Equal(t, "", th.App.PostListWithProxyAddedToImageURLs(list).Posts[post.Id].Message) 238 assert.Equal(t, "", th.App.PostWithProxyAddedToImageURLs(post).Message) 239 240 assert.Equal(t, "", th.App.PostWithProxyRemovedFromImageURLs(post).Message) 241 post.Message = "" 242 assert.Equal(t, "", th.App.PostWithProxyRemovedFromImageURLs(post).Message) 243 }) 244 } 245 } 246 247 var imageProxyBenchmarkSink *model.Post 248 249 func BenchmarkPostWithProxyRemovedFromImageURLs(b *testing.B) { 250 th := Setup().InitBasic() 251 defer th.TearDown() 252 253 th.App.UpdateConfig(func(cfg *model.Config) { 254 cfg.ServiceSettings.ImageProxyType = model.NewString("willnorris/imageproxy") 255 cfg.ServiceSettings.ImageProxyOptions = model.NewString("x1000|foo") 256 cfg.ServiceSettings.ImageProxyURL = model.NewString("https://127.0.0.1") 257 }) 258 259 post := &model.Post{ 260 Message: "", 261 } 262 263 b.ResetTimer() 264 265 for i := 0; i < b.N; i++ { 266 imageProxyBenchmarkSink = th.App.PostWithProxyAddedToImageURLs(post) 267 } 268 }