Sangcheol Hwang 2013-01-14
apply avatar at board, issue
@a380563eecb642f2703f7a96e9c271e9f2d2e44e
app/controllers/IssueApp.java
--- app/controllers/IssueApp.java
+++ app/controllers/IssueApp.java
@@ -135,6 +135,7 @@
             Issue newIssue = issueForm.get();
             newIssue.date = JodaDateUtil.now();
             newIssue.authorId = UserApp.currentUser().id;
+            newIssue.authorLoginId = UserApp.currentUser().loginId;
             newIssue.authorName = UserApp.currentUser().name;
             newIssue.project = project;
             newIssue.state = State.OPEN;
@@ -184,6 +185,7 @@
         issue.id = id;
         issue.date = originalIssue.date;
         issue.authorId = originalIssue.authorId;
+        issue.authorLoginId = originalIssue.authorLoginId;
         issue.authorName = originalIssue.authorName;
         issue.project = originalIssue.project;
         if (issue.assignee.user.id != null) {
@@ -227,6 +229,7 @@
             IssueComment comment = commentForm.get();
             comment.issue = Issue.findById(issueId);
             comment.authorId = UserApp.currentUser().id;
+            comment.authorLoginId = UserApp.currentUser().loginId;
             comment.authorName = UserApp.currentUser().name;
             Long commentId = IssueComment.create(comment);
             Issue.updateNumOfComments(issueId);
app/controllers/UserApp.java
--- app/controllers/UserApp.java
+++ app/controllers/UserApp.java
@@ -100,7 +100,7 @@
 		}
 
 		flash(Constants.WARNING, "user.login.failed");
-		return redirect(routes.UserApp.login());
+		return redirect(routes.UserApp.loginForm());
 	}
 
 	public static User authenticateWithHashedPassword(String loginId, String password) {
app/models/Issue.java
--- app/models/Issue.java
+++ app/models/Issue.java
@@ -93,16 +93,16 @@
         return JodaDateUtil.ago(this.date);
     }
 
-    public String getAuthorName() {
-        if (authorName == null) {
-            if (authorId == null)
-                return null;
-            else
-                return User.find.byId(this.authorId).name;
-        } else {
-            return authorName;
-        }
-    }
+//    public String getAuthorName() {
+//        if (authorName == null) {
+//            if (authorId == null)
+//                return null;
+//            else
+//                return User.find.byId(this.authorId).name;
+//        } else {
+//            return authorName;
+//        }
+//    }
 
     /**
      * issueList, issue view에서 assignee의 이름을 출력해준다. 아래의 getAssigneeName과 합쳐질 수
app/models/IssueComment.java
--- app/models/IssueComment.java
+++ app/models/IssueComment.java
@@ -26,6 +26,7 @@
 
     public Date date;
     public Long authorId;
+    public String authorLoginId;
     public String authorName;
     public String filePath;
 
app/views/board/post.scala.html
--- app/views/board/post.scala.html
+++ app/views/board/post.scala.html
@@ -14,7 +14,8 @@
   </div>
   <div class="board-body">
     <div class="author-info">
-      <a href="@routes.UserApp.userInfo(post.authorLoginId)" class="pull-left img-rounded"><img src="/assets/images/default-avatar-34.png" class="media-object" width="32" height="32" alt="avatar"></a>
+      <a href="@routes.UserApp.userInfo(post.authorLoginId)" class="pull-left img-rounded">
+      <img class="user-picture" src="@User.findByLoginId(post.authorLoginId).avatarUrl" width="34" height="34" alt="@post.authorName"></a>
       <div class="media-body">
         <p>
           <a href="@routes.UserApp.userInfo(post.authorLoginId)"><strong>@post.authorName</strong></a> <!--<span class="name">(Loren Brichter)</span>-->
@@ -37,7 +38,8 @@
     <ul class="comments">
       @for(comment <-post.comments){
       <li class="comment">
-        <a href="@routes.UserApp.userInfo(comment.authorLoginId)" class="pull-left img-rounded"><img src="/assets/images/default-avatar-34.png" width="32" height="32" class="media-object" alt="avatar"></a>
+        <a href="@routes.UserApp.userInfo(comment.authorLoginId)" class="pull-left img-rounded">
+        <img class="user-picture" src="@User.findByLoginId(comment.authorLoginId).avatarUrl" width="34" height="34" alt="@comment.authorName">
         <div class="media-body">
           @roleCheck(session.get("userId"), project.id, Resource.BOARD_COMMENT, Operation.DELETE, comment.id){
           <a class="pull-right close" href="@routes.BoardApp.deleteComment(project.owner, project.name, post.id, comment.id)">&times;</a>
app/views/board/postList.scala.html
--- app/views/board/postList.scala.html
+++ app/views/board/postList.scala.html
@@ -59,14 +59,14 @@
       <div class="attach-wrap"></div>
       <div class="contents">
         <p class="title"><a href="@routes.BoardApp.post(project.owner, project.name, post.id)">@post.title</a></p>
-        <p class="infos nm">by <a href="@routes.UserApp.userInfo(post.authorLoginId)" class="author">@post.authorName</a> <span class="date">@utils.TemplateHelper.agoString(post.ago())</span></p>
+        <p class="infos nm">by <a href="@routes.UserApp.userInfo(post.authorLoginId)" class="author">@post.authorLoginId</a> <span class="date">@utils.TemplateHelper.agoString(post.ago())</span></p>
       </div>
       <div class="right-panel">
         <div class="comment-wrap">
             <i class="ico ico-comment-bubble"></i><span class="num">@post.commentCount</span>
         </div>
         <a href="@routes.UserApp.userInfo(post.authorLoginId)" class="author-avatar img-rounded pull-right">
-        <img class="user-picture" src="@User.findByLoginId(session.get("loginId")).avatarUrl" width="34" height="34" alt="@post.authorName">
+        <img class="user-picture" src="@User.findByLoginId(post.authorLoginId).avatarUrl" width="34" height="34" alt="@post.authorName">
       </div>
     </li>
     }
app/views/issue/issue.scala.html
--- app/views/issue/issue.scala.html
+++ app/views/issue/issue.scala.html
@@ -32,7 +32,7 @@
 
   <hgroup class="row-fluid">
     <div class="span1">
-      <img class="user-picture" src="@urlToPicture(User.find.byId(issue.authorId).email, 34)" />
+      <img class="user-picture" src="@User.findByLoginId(issue.authorLoginId).avatarUrl" />
     </div>
     <div class="info">
       <p>
@@ -42,7 +42,8 @@
           <span class="badge badge-info">@Messages(issue.state.state)</span>
         </span>
       </p>
-      <p class="author">by <a href="@routes.IssueApp.newIssueForm(project.owner, project.name)">@Option(issue.getAuthorName).orElse(Option(Messages("issue.noAuthor"))).get</a> @agoString(issue.ago)</p>
+      <p class="author">by <a href="@routes.IssueApp.newIssueForm(project.owner, project.name)">
+      @Option(issue.authorLoginId).orElse(Option(Messages("issue.noAuthor"))).get</a> @agoString(issue.ago)</p>
     </div>
   </hgroup>
 
@@ -78,7 +79,8 @@
 <div class="comments">
   @for(comment <- issue.comments){
   <div class="comment row-fluid">
-    <div class="span1"><img class="user-picture" src="@urlToPicture(User.find.byId(comment.authorId).email, 34)" /></div>
+    <div class="span1">
+    <img class="user-picture" src="@User.findByLoginId(comment.authorLoginId).avatarUrl" width="34" height="34" alt="@comment.authorName"/></div>
     <div class="span11">
       <div>
         <span class="author">@comment.authorName</span>
app/views/issue/issueList.scala.html
--- app/views/issue/issueList.scala.html
+++ app/views/issue/issueList.scala.html
@@ -113,7 +113,7 @@
           <td class="attachmend attached">@if(Attachment.findByContainer(Resource.ISSUE_POST, issue.id).size > 0){<span class="icon-file"/>}</td>
           <td class="info">
             <p><a href="@routes.IssueApp.issue(project.owner, project.name, issue.id)">@issue.title</a></p>
-            <p class="author">by <a href="@routes.UserApp.userInfo(issue.authorLoginId)">@Option(issue.getAuthorName).orElse(Option(Messages("issue.noAuthor"))).get</a> @agoString(issue.ago)</p>
+            <p class="author">by <a href="@routes.UserApp.userInfo(issue.authorLoginId)">@Option(issue.authorLoginId).orElse(Option(Messages("issue.noAuthor"))).get</a> @agoString(issue.ago)</p>
           </td>
           <td class="state @issue.state.toString.toLowerCase">@Messages(issue.state.state)</td>
           <td class="comments">
@@ -121,7 +121,8 @@
             <span class="num">@issue.numOfComments</span>
           </td>
           <td class="assignee">
-            <a href="#"><img class="user-picture" src="@urlToPicture(User.find.byId(issue.authorId).email, 34)"></a>
+            <a href="#">
+            <img class="user-picture" src="@User.findByLoginId(issue.authorLoginId).avatarUrl" width="34" height="34" alt="@issue.authorName"></a>
           </td>
 
         </tr>
app/views/navbar.scala.html
--- app/views/navbar.scala.html
+++ app/views/navbar.scala.html
@@ -29,8 +29,10 @@
                 <!-- for Testing end here-->
             </ul>
             <ul class="gnb-menus right unstyled">
-                @if(session.contains("userId")){
-                <li><a href="@routes.UserApp.userInfo(session.get("loginId"))" class="d-link signin"><img class="user-thumb img-rounded" src="@urlToPicture(User.find.byId(session.get("userId").toLong).email, 22)" alt="avatar" width="22" height="22">@session.get("userName")</a></li>
+                @if(session.contains("loginId")){
+                <li><a href="@routes.UserApp.userInfo(session.get("loginId"))" class="d-link signin">
+                    <img class="user-thumb img-rounded" 
+                    src="@User.findByLoginId(session.get("loginId")).avatarUrl" alt="avatar" width="22" height="22">@session.get("loginId")</a></li>
                 <li class="sp-line">|</li>
                 <li><a href="@routes.UserApp.logout()" class="d-link signup">@Messages("title.logout")</a></li>
                 } else {
app/views/project/projectHome.scala.html
--- app/views/project/projectHome.scala.html
+++ app/views/project/projectHome.scala.html
@@ -46,7 +46,8 @@
                 <ul class="project-members">
                     @for(member <- User.findUsersByProject(project.id)){
                     <li class="member">
-                        <a href="/uname" class="user-thumb"><img src="/assets/images/default-avatar-34.png" alt="uname"></a>
+                        <a href="/uname" class="user-thumb">
+                        <img src="@member.avatarUrl" alt="uname"></a>
                         <a href="@routes.UserApp.userInfo(member.loginId)"><strong>@member.loginId</strong></a>
                     </li>
                     }
app/views/topmenu.scala.html
--- app/views/topmenu.scala.html
+++ app/views/topmenu.scala.html
@@ -45,7 +45,8 @@
             </ul>
             <ul class="gnb-menus right unstyled">
                 @if(session.contains("userId")){
-                <li><a href="@routes.UserApp.userInfo(session.get("loginId"))"><img class="user-thumb img-rounded" src="@urlToPicture(User.find.byId(session.get("userId").toLong).email, 22)" alt="avatar" width="22" height="22"></a>
+                <li><a href="@routes.UserApp.userInfo(session.get("loginId"))">
+                <img class="user-thumb img-rounded" src="@User.findByLoginId(session.get("loginId")).avatarUrl" alt="avatar" width="22" height="22"></a>
                     <a href="@routes.UserApp.userInfo(session.get("loginId"))">@session.get("userName")</a>
                 </li>
                 <li class="sp-line">|</li>
conf/initial-data.yml
--- conf/initial-data.yml
+++ conf/initial-data.yml
@@ -94,169 +94,188 @@
     - !!models.Comment
         contents:       게시판이 너무 기대됩니다. 많은 글이 필요합니다. 
         authorId:       2
-        authorName:     hobi
+        authorLoginId:  hobi
+        authorName:     hobi        
         post:           !!models.Post
                             id: 1
 # Issues
 issues:
     - !!models.Issue
-        authorId:     2       
+        authorId:       2
+        authorLoginId:  hobi       
         title:          불필요한 로그 출력 코드 제거
         body:           내용 불필요한~
-        state:      OPEN
+        state:          OPEN
         milestoneId:    1
         date: 2012-11-01 08:00:00
         project:        !!models.Project
                             id: 1
     - !!models.Issue
-        authorId:     3
+        authorId:       3
+        authorLoginId:  k16wire
         title:          다운로드는 익명 댓글에도 사용자명에 링크가 걸림
         body:           내용 다운로드는 익명 댓글에도 사용자명에 링크가 걸림
-        state:      OPEN
+        state:          OPEN
         milestoneId:    2
-        date: 2012-11-02 08:00:00
+        date:           2012-11-02 08:00:00
         project:        !!models.Project
                             id: 1
     - !!models.Issue
-        authorId:     4
+        authorId:       4
+        authorLoginId:  doortts
         title:          gittracker.php의 메모리 제한 에러
         body:           내용 gittracker.php의 메모리 제한 에러
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    2
-        date: 2012-11-03 08:00:00
+        date:           2012-11-03 08:00:00
         project:        !!models.Project
                             id: 1
         numOfComments:  1
     - !!models.Issue
-        authorId:     4
+        authorId:       4
+        authorLoginId:  doortts
         title:          git/hg 코드 브라우저에 i18n이 적용되지 않음
         body:           내용 git/hg 코드 브라우저에 i18n이 적용되지 않음
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    2
-        date: 2012-11-04 08:00:00
+        date:           2012-11-04 08:00:00
         project:        !!models.Project
                             id: 1
     - !!models.Issue
-        authorId:     4
+        authorId:       4
+        authorLoginId:  doortts
         title:          CUBRID 설치 문제
         body:           IOS는 설치 못하나요?
-        state:      OPEN
+        state:          OPEN
         milestoneId:    0
-        date: 2012-11-05 08:00:00
+        date:           2012-11-05 08:00:00
         project:        !!models.Project
                             id: 3
     - !!models.Issue
-        authorId:     4
+        authorId:       4
+        authorLoginId:  doortts
         title:          메모리 누수 현상
         body:           메모리가 너무 누수가 되는듯.
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    6
-        date: 2012-11-06 08:00:00
+        date:           2012-11-06 08:00:00
         project:        !!models.Project
                             id: 3
     - !!models.Issue
-        authorId:     4
+        authorId:       4
+        authorLoginId:  doortts
         title:          Client application for Mac.
         body:           Please make it.
-        state:      OPEN
+        state:          OPEN
         milestoneId:    5
-        date: 2012-11-07 08:00:00
+        date:           2012-11-07 08:00:00
         project:        !!models.Project
                             id: 3
     - !!models.Issue
-        authorId:     4
+        authorId:       4
+        authorLoginId:  doortts
         title:          CPU 무한 점유울 문제.
         body:           CPU를 무한사용 중이에요.
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    5
         date: 2012-11-08 08:00:00
         project:        !!models.Project
                             id: 3
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          Less chained imports causes compile error
         body:           When using Play, when I chain less files such as a.less imports b.less which in turn imports c.less
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    1
         date: 2012-11-09 08:00:00
         project:        !!models.Project
                             id: 1
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          Weird TypeDoesNotMatch exception in RC-3 and final
         body:           The following code works as expected in RC1-Snapshot, but breaks with an TypeDoesNotMatch exception in RC-3 and 2.0 final.
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    1
-        date: 2012-11-10 08:00:00
+        date:           2012-11-10 08:00:00
         project:        !!models.Project
                             id: 1
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          Anorm and PostgreSQL - return value not accessible
         body:           PostgreSQL allows you to insert a row and obtain the id of the new row in one query
-        state:      OPEN
+        state:          OPEN
         milestoneId:    1
-        date: 2012-11-11 08:00:00
+        date:           2012-11-11 08:00:00
         project:        !!models.Project
                             id: 1
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          Update sbt-idea to 1.1.0
         body:           Create sbt project definition module, if exists, for each subproject (pull 128)
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    3
-        date: 2012-11-12 08:00:00
+        date:           2012-11-12 08:00:00
         project:        !!models.Project
                             id: 2
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          Support Tuple 22, not just Tuple 18 in api/data/Forms.scala
         body:           While creating some complex forms, Eclipse started hanging for some unknown reason.
-        state:      CLOSED
+        state:          CLOSED
         milestoneId:    3
-        date: 2012-11-13 08:00:00
+        date:           2012-11-13 08:00:00
         project:        !!models.Project
                             id: 2
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          Support Tuple 22, not just Tuple 18 in api/data/Forms.scala
         body:           While creating some complex forms, Eclipse started hanging for some unknown reason.
-        state:      OPEN
+        state:          OPEN
         milestoneId:    4
-        date: 2012-11-14 08:00:00
+        date:           2012-11-14 08:00:00
         project:        !!models.Project
                             id: 2
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          Cookie Expires date
         body:           With Play 2.0.2, when creating a cookie with response().setCookie, HTTP output is like
-        state:      OPEN
+        state:          OPEN
         milestoneId:    4
-        date: 2012-11-15 08:00:00
+        date:           2012-11-15 08:00:00
         project:        !!models.Project
                             id: 2
     - !!models.Issue
-        authorId:     1
+        authorId:       1
+        authorLoginId:  admin
         title:          require is not work in windows (Closure Compiler)
         body:           Test on Play2.1-Snapshot
-        state:      OPEN
+        state:          OPEN
         milestoneId:    4
-        date: 2012-11-15 08:00:00
+        date:           2012-11-15 08:00:00
         project:        !!models.Project
                             id: 2
     - !!models.Issue
-        authorId:     2
+        authorId:       2
+        authorLoginId:  hobi
         title:          Remember me is not working
         body:           Test on Play2.1-Snapshot
-        state:      OPEN
+        state:          OPEN
         milestoneId:    4
-        date: 2012-11-16 08:00:00
+        date:           2012-11-16 08:00:00
         project:        !!models.Project
                             id: 3
 issueComments:
     - !!models.IssueComment
         contents:       코드를 수정했습니다
         authorId:       2
+        authorLoginId:  hobi
         issue:          !!models.Issue
                             id: 3
 # Milestone
test/controllers/UserAppTest.java
--- test/controllers/UserAppTest.java
+++ test/controllers/UserAppTest.java
@@ -27,7 +27,7 @@
         running(fakeApplication(), new Runnable() {
             public void run() {
                 //Given
-                Map<String,String> data = new HashMap<>();
+                Map<String,String> data = new HashMap<String,String>();
                 data.put("loginId", "nekure");
 
                 //When
@@ -48,7 +48,7 @@
         running(fakeApplication(), new Runnable() {
             public void run() {
                 //Given
-                Map<String,String> data = new HashMap<>();
+                Map<String,String> data = new HashMap<String,String>();
                 data.put("loginId", "hobi");
 
                 //When
Add a comment
List