diff --git a/app/src/main/java/com/example/tampopo_client/models/Activity.java b/app/src/main/java/com/example/tampopo_client/models/Activity.java index fd54d94..f5432f2 100644 --- a/app/src/main/java/com/example/tampopo_client/models/Activity.java +++ b/app/src/main/java/com/example/tampopo_client/models/Activity.java @@ -1,13 +1,18 @@ package com.example.tampopo_client.models; +import com.fasterxml.jackson.annotation.JsonIgnoreProperties; import com.fasterxml.jackson.annotation.JsonProperty; +import java.util.Objects; + +@JsonIgnoreProperties(ignoreUnknown = true) public class Activity { private String userId; @JsonProperty("activity-id") private String activityId; + @JsonProperty("text") private String text; @JsonProperty("updated-time") @@ -54,4 +59,19 @@ public void setUpdateTime(String updateTime) { this.updateTime = updateTime; } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + Activity activity = (Activity) o; + return Objects.equals(activityId, activity.activityId) && + Objects.equals(text, activity.text) && + Objects.equals(updateTime, activity.updateTime); + } + + @Override + public int hashCode() { + return Objects.hash(activityId, text, updateTime); + } } diff --git a/app/src/main/java/com/example/tampopo_client/viewmodels/ActivityViewModel.java b/app/src/main/java/com/example/tampopo_client/viewmodels/ActivityViewModel.java index da81a65..32b6c19 100644 --- a/app/src/main/java/com/example/tampopo_client/viewmodels/ActivityViewModel.java +++ b/app/src/main/java/com/example/tampopo_client/viewmodels/ActivityViewModel.java @@ -64,7 +64,7 @@ userResource = retrofit.create(UserResource.class); friendToActivitiesLiveData = new HashMap<>(); - friendUserIdsLiveData = new MutableLiveData<>(List.of()); + friendUserIdsLiveData = new MutableLiveData<>(new ArrayList<>()); myLatestActivityLiveData = new MutableLiveData<>(null); userActivityStatusChangeListeners = new ArrayList<>(); @@ -109,8 +109,9 @@ }); // 自分のフレンドの最新のアクティビティを取得して更新する - if (friendUserIdsLiveData.isInitialized() && friendUserIdsLiveData.getValue() != null) { - for (String userId : friendUserIdsLiveData.getValue()) { + List currentFriends = friendUserIdsLiveData.getValue(); + if (currentFriends != null) { + for (String userId : currentFriends) { pullLatestActivity(userId, activitiesResource, new ActivityFetchCallback() { @Override public void onSuccess(Activity activity) { @@ -125,11 +126,8 @@ } } - if (friendUserIdsLiveData.isInitialized()) { - // 最新のフレンドのユーザーIDを取得して更新する - // TODO: 適切なコールバックを使う必要あり - pullLatestFriendUserIds(myUserId, myToken); - } + // 最新のフレンドのユーザーIDを取得して更新する + pullLatestFriendUserIds(myUserId, myToken); }; } @@ -147,17 +145,20 @@ assert userActivitiesLiveData != null; List userActivities = userActivitiesLiveData.getValue(); - - if (userActivities == null || userActivities.isEmpty()) { - userActivitiesLiveData.postValue(List.of(latestActivity)); - } else { + + if (userActivities != null && !userActivities.isEmpty()) { Activity currentLatest = userActivities.get(userActivities.size() - 1); - // IDか更新時間が異なる場合に更新する - if (!currentLatest.getActivityId().equals(latestActivity.getActivityId()) || - !currentLatest.getUpdateTime().equals(latestActivity.getUpdateTime())) { - userActivitiesLiveData.postValue(List.of(latestActivity)); + // 内容もIDも時間も同じならスキップ + if (currentLatest.equals(latestActivity)) { + return; } } + + // 確実に変更を通知するために新しいリストをセット + List newList = new ArrayList<>(); + newList.add(latestActivity); + userActivitiesLiveData.postValue(newList); + Log.d("ActivityViewModel", "Friend activity updated for user: " + userId + " content: " + latestActivity.getText()); } /** @@ -168,10 +169,6 @@ * @param newActivity 新しいアクティビティのテキスト */ public void createActivity(String userId, String token, String newActivity) { - if (!myLatestActivityLiveData.isInitialized()) { - return; - } - Call createActivityCall = activitiesResource.addActivity(userId, token, newActivity); createActivityCall.enqueue(new Callback() { @Override @@ -187,6 +184,7 @@ if (createdActivity == null) { return; } + createdActivity.setUserId(userId); myLatestActivityLiveData.postValue(createdActivity); } @@ -220,20 +218,33 @@ @Override public void onResponse(@NonNull Call> call, @NonNull Response> response) { if (response.isSuccessful() && response.body() != null) { - Collection activities = response.body().values(); // アクティビティが存在しない場合は空のリスト + Collection activities = response.body().values(); if (activities == null || activities.isEmpty()) { return; } - Activity latestActivity = activities.iterator().next(); - callback.onSuccess(latestActivity); + // 取得したアクティビティの中で最新のものを探す(複数返ってきた場合への対策) + Activity latest = null; + LocalDateTime latestTime = LocalDateTime.MIN; + + for (Activity a : activities) { + LocalDateTime t = getDateTimeFromString(a.getUpdateTime()); + if (t.isAfter(latestTime)) { + latestTime = t; + latest = a; + } + } + + if (latest != null) { + latest.setUserId(userId); + callback.onSuccess(latest); + } } } @Override public void onFailure(@NonNull Call> call, @NonNull Throwable t) { Log.e(ActivityViewModel.class.getSimpleName(), "An error has occurred while fetching the latest activity.", t); - callback.onFailure(t); } }); @@ -246,8 +257,13 @@ * @return 変換後の日時(LocalDateTime) */ private static LocalDateTime getDateTimeFromString(String dateTime) { - DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm"); - return LocalDateTime.parse(dateTime, formatter); + if (dateTime == null || dateTime.isEmpty()) return LocalDateTime.MIN; + try { + DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy/MM/dd HH:mm"); + return LocalDateTime.parse(dateTime, formatter); + } catch (Exception e) { + return LocalDateTime.MIN; + } } /** @@ -262,26 +278,27 @@ @Override public void onResponse(@NonNull Call> call, @NonNull Response> response) { if (response.isSuccessful() && response.body() != null) { + List newFriendIds = response.body(); + List currentFriendIds = friendUserIdsLiveData.getValue(); + + if (currentFriendIds == null || !currentFriendIds.equals(newFriendIds)) { + friendUserIdsLiveData.postValue(newFriendIds); + } - // MEMO: 入れ込んだだけ - // フレンドのIDをアクティビティ更新順に並べ替える - List friendUserIds = friendUserIdsLiveData.getValue(); - if (friendUserIds == null || !friendUserIds.equals(response.body())) { - friendUserIdsLiveData.postValue(response.body()); - SortedSet friends = new TreeSet<>(new Friend.UpdateTimeComparator()); - - for (String fid : response.body()) { - MutableLiveData> liveData = getActivitiesLiveDataFromUserId(fid); - List activities = liveData.getValue(); - if (activities == null || activities.isEmpty()) { - continue; - } - + // 並び替え + SortedSet friends = new TreeSet<>(new Friend.UpdateTimeComparator()); + for (String fid : newFriendIds) { + MutableLiveData> liveData = getActivitiesLiveDataFromUserId(fid); + List activities = liveData.getValue(); + if (activities != null && !activities.isEmpty()) { Activity latestActivity = activities.get(activities.size() - 1); friends.add(new Friend(fid, latestActivity.getUpdateTime())); + } else { + friends.add(new Friend(fid, "1970/01/01 00:00")); } + } - // 並び替えたフレンドのユーザーIDを順番に格納して更新する + synchronized (sortedFriendUserIds) { sortedFriendUserIds.clear(); friends.forEach(friend -> sortedFriendUserIds.add(friend.getUserId())); } @@ -299,12 +316,6 @@ return myLatestActivityLiveData; } - /** - * ユーザIDからそのユーザーのアクティビティのリストのライブデータを取得する - * - * @param userId 取得対象のユーザーID - * @return 取得対象のユーザーのアクティビティのリストのライブデータ - */ public MutableLiveData> getActivitiesLiveDataFromUserId(String userId) { if (!friendToActivitiesLiveData.containsKey(userId)) { friendToActivitiesLiveData.put(userId, new MutableLiveData<>(new ArrayList<>())); @@ -325,7 +336,9 @@ } public List getSortedFriendUserIds() { - return sortedFriendUserIds; + synchronized (sortedFriendUserIds) { + return new ArrayList<>(sortedFriendUserIds); + } } public void addActivityStatusChangeObserver(UserActivityStatusChangeListener observer) { @@ -356,9 +369,9 @@ public static class UpdateTimeComparator implements Comparator { @Override public int compare(Friend o1, Friend o2) { - int timeCompare = o2.getLatestUpdateTime().compareTo(o1.getLatestUpdateTime()); // 降順 + int timeCompare = o2.getLatestUpdateTime().compareTo(o1.getLatestUpdateTime()); if (timeCompare == 0) { - return o1.getUserId().compareTo(o2.getUserId()); // 時間が同じならIDで比較(TreeSet用) + return o1.getUserId().compareTo(o2.getUserId()); } return timeCompare; } @@ -367,7 +380,6 @@ private interface ActivityFetchCallback { void onSuccess(Activity activity); - void onFailure(Throwable throwable); } }