Browse Source

fix(home): resolve nearby filter not refreshing feed view

- Fix FeedFilters component missing activeDid context for settings updates
- Update reloadFeedOnChange to retrieve actual settings without defaults
- Add comprehensive logging throughout feed refresh process for debugging
- Ensure filter state changes immediately trigger feed refresh without page reload

The issue was caused by FeedFilters component calling $updateSettings() without
the activeDid parameter, causing settings to be saved to wrong location. Now
properly passes activeDid from HomeView and uses $accountSettings() for
accurate user-specific settings retrieval.

Closes filter refresh issue where turning ON nearby filter required page reload
pull/162/head
Matthew Raymer 5 days ago
parent
commit
9196081f34
  1. 7
      src/components/DataExportSection.vue
  2. 87
      src/components/FeedFilters.vue
  3. 6
      src/components/OfferDialog.vue
  4. 108
      src/views/HomeView.vue

7
src/components/DataExportSection.vue

@ -187,9 +187,10 @@ export default class DataExportSection extends Vue {
const exContact: Contact = R.omit(["contactMethods"], contact);
// now add contactMethods as a true array of ContactMethod objects
exContact.contactMethods = contact.contactMethods
? (typeof contact.contactMethods === 'string' && contact.contactMethods.trim() !== ''
? JSON.parse(contact.contactMethods)
: [])
? typeof contact.contactMethods === "string" &&
contact.contactMethods.trim() !== ""
? JSON.parse(contact.contactMethods)
: []
: [];
return exContact;
});

87
src/components/FeedFilters.vue

@ -119,11 +119,13 @@ export default class FeedFilters extends Vue {
isNearby = false;
settingChanged = false;
visible = false;
activeDid = "";
async open(onCloseIfChanged: () => void) {
async open(onCloseIfChanged: () => void, activeDid: string) {
this.onCloseIfChanged = onCloseIfChanged;
this.activeDid = activeDid;
const settings = await this.$settings();
const settings = await this.$accountSettings(activeDid);
this.hasVisibleDid = !!settings.filterFeedByVisible;
this.isNearby = !!settings.filterFeedByNearby;
if (settings.searchBoxes && settings.searchBoxes.length > 0) {
@ -137,17 +139,45 @@ export default class FeedFilters extends Vue {
async toggleHasVisibleDid() {
this.settingChanged = true;
this.hasVisibleDid = !this.hasVisibleDid;
await this.$updateSettings({
filterFeedByVisible: this.hasVisibleDid,
});
if (this.activeDid) {
await this.$updateSettings(
{
filterFeedByVisible: this.hasVisibleDid,
},
this.activeDid,
);
} else {
await this.$updateSettings({
filterFeedByVisible: this.hasVisibleDid,
});
}
}
async toggleNearby() {
this.settingChanged = true;
this.isNearby = !this.isNearby;
await this.$updateSettings({
filterFeedByNearby: this.isNearby,
console.log("[FeedFilters] 🔄 Toggling nearby filter:", {
newValue: this.isNearby,
settingChanged: this.settingChanged,
activeDid: this.activeDid,
});
if (this.activeDid) {
await this.$updateSettings(
{
filterFeedByNearby: this.isNearby,
},
this.activeDid,
);
} else {
await this.$updateSettings({
filterFeedByNearby: this.isNearby,
});
}
console.log("[FeedFilters] ✅ Nearby filter updated in settings");
}
async clearAll() {
@ -155,10 +185,20 @@ export default class FeedFilters extends Vue {
this.settingChanged = true;
}
await this.$updateSettings({
filterFeedByNearby: false,
filterFeedByVisible: false,
});
if (this.activeDid) {
await this.$updateSettings(
{
filterFeedByNearby: false,
filterFeedByVisible: false,
},
this.activeDid,
);
} else {
await this.$updateSettings({
filterFeedByNearby: false,
filterFeedByVisible: false,
});
}
this.hasVisibleDid = false;
this.isNearby = false;
@ -169,23 +209,40 @@ export default class FeedFilters extends Vue {
this.settingChanged = true;
}
await this.$updateSettings({
filterFeedByNearby: true,
filterFeedByVisible: true,
});
if (this.activeDid) {
await this.$updateSettings(
{
filterFeedByNearby: true,
filterFeedByVisible: true,
},
this.activeDid,
);
} else {
await this.$updateSettings({
filterFeedByNearby: true,
filterFeedByVisible: true,
});
}
this.hasVisibleDid = true;
this.isNearby = true;
}
close() {
console.log("[FeedFilters] 🚪 Closing dialog:", {
settingChanged: this.settingChanged,
hasCallback: !!this.onCloseIfChanged,
});
if (this.settingChanged) {
console.log("[FeedFilters] 🔄 Settings changed, calling callback");
this.onCloseIfChanged();
}
this.visible = false;
}
done() {
console.log("[FeedFilters] ✅ Done button clicked");
this.close();
}
}

6
src/components/OfferDialog.vue

@ -18,7 +18,7 @@ Raymer */
<div class="flex mb-4">
<AmountInput
:value="parseFloat(amountInput) || 0"
:onUpdateValue="handleAmountUpdate"
:on-update-value="handleAmountUpdate"
data-testId="inputOfferAmount"
/>
@ -152,8 +152,6 @@ export default class OfferDialog extends Vue {
};
}
// =================================================
// COMPONENT METHODS
// =================================================
@ -199,8 +197,6 @@ export default class OfferDialog extends Vue {
this.visible = false;
}
/**
* Handle amount updates from AmountInput component
* @param value - New amount value

108
src/views/HomeView.vue

@ -763,17 +763,34 @@ export default class HomeView extends Vue {
* Called by FeedFilters component when filters change
*/
async reloadFeedOnChange() {
const settings = await this.$accountSettings(this.activeDid, {
filterFeedByVisible: false,
filterFeedByNearby: false,
logger.info("[HomeView] 🔄 reloadFeedOnChange() called - refreshing feed");
// Get current settings without overriding with defaults
const settings = await this.$accountSettings(this.activeDid);
logger.info("[HomeView] 📊 Current filter settings:", {
filterFeedByVisible: settings.filterFeedByVisible,
filterFeedByNearby: settings.filterFeedByNearby,
searchBoxes: settings.searchBoxes?.length || 0,
});
this.isFeedFilteredByVisible = !!settings.filterFeedByVisible;
this.isFeedFilteredByNearby = !!settings.filterFeedByNearby;
this.isAnyFeedFilterOn = checkIsAnyFeedFilterOn(settings);
logger.info("[HomeView] 🎯 Updated filter states:", {
isFeedFilteredByVisible: this.isFeedFilteredByVisible,
isFeedFilteredByNearby: this.isFeedFilteredByNearby,
isAnyFeedFilterOn: this.isAnyFeedFilterOn,
});
this.feedData = [];
this.feedPreviousOldestId = undefined;
logger.info("[HomeView] 🧹 Cleared feed data, calling updateAllFeed()");
await this.updateAllFeed();
logger.info("[HomeView] ✅ Feed refresh completed");
}
/**
@ -852,6 +869,14 @@ export default class HomeView extends Vue {
* - this.feedLastViewedClaimId (via updateFeedLastViewedId)
*/
async updateAllFeed() {
logger.info("[HomeView] 🚀 updateAllFeed() called", {
isFeedLoading: this.isFeedLoading,
currentFeedDataLength: this.feedData.length,
isAnyFeedFilterOn: this.isAnyFeedFilterOn,
isFeedFilteredByVisible: this.isFeedFilteredByVisible,
isFeedFilteredByNearby: this.isFeedFilteredByNearby,
});
this.isFeedLoading = true;
let endOfResults = true;
@ -860,21 +885,37 @@ export default class HomeView extends Vue {
this.apiServer,
this.feedPreviousOldestId,
);
logger.info("[HomeView] 📡 Retrieved gives from API", {
resultsCount: results.data.length,
endOfResults,
});
if (results.data.length > 0) {
endOfResults = false;
// gather any contacts that user has blocked from view
await this.processFeedResults(results.data);
await this.updateFeedLastViewedId(results.data);
logger.info("[HomeView] 📝 Processed feed results", {
processedCount: this.feedData.length,
});
}
} catch (e) {
logger.error("[HomeView] ❌ Error in updateAllFeed:", e);
this.handleFeedError(e);
}
if (this.feedData.length === 0 && !endOfResults) {
logger.info("[HomeView] 🔄 No results after filtering, retrying...");
await this.updateAllFeed();
}
this.isFeedLoading = false;
logger.info("[HomeView] ✅ updateAllFeed() completed", {
finalFeedDataLength: this.feedData.length,
isFeedLoading: this.isFeedLoading,
});
}
/**
@ -899,12 +940,35 @@ export default class HomeView extends Vue {
* @param records Array of feed records to process
*/
private async processFeedResults(records: GiveSummaryRecord[]) {
logger.info("[HomeView] 📝 Processing feed results:", {
inputRecords: records.length,
currentFilters: {
isAnyFeedFilterOn: this.isAnyFeedFilterOn,
isFeedFilteredByVisible: this.isFeedFilteredByVisible,
isFeedFilteredByNearby: this.isFeedFilteredByNearby,
},
});
let processedCount = 0;
let filteredCount = 0;
for (const record of records) {
const processedRecord = await this.processRecord(record);
if (processedRecord) {
this.feedData.push(processedRecord);
processedCount++;
} else {
filteredCount++;
}
}
logger.info("[HomeView] 📊 Feed processing results:", {
processed: processedCount,
filtered: filteredCount,
total: records.length,
finalFeedLength: this.feedData.length,
});
this.feedPreviousOldestId = records[records.length - 1].jwtId;
}
@ -938,7 +1002,7 @@ export default class HomeView extends Vue {
* - this.feedData (via createFeedRecord)
*
* @param record The record to process
* @returns Processed record with contact info if it passes filters, null otherwise
* @returns Processed record if it passes filters, null otherwise
*/
private async processRecord(
record: GiveSummaryRecord,
@ -948,13 +1012,28 @@ export default class HomeView extends Vue {
const recipientDid = this.extractRecipientDid(claim);
const fulfillsPlan = await this.getFulfillsPlan(record);
// Log record details for debugging
logger.debug("[HomeView] 🔍 Processing record:", {
recordId: record.jwtId,
hasFulfillsPlan: !!fulfillsPlan,
fulfillsPlanHandleId: record.fulfillsPlanHandleId,
filters: {
isAnyFeedFilterOn: this.isAnyFeedFilterOn,
isFeedFilteredByVisible: this.isFeedFilteredByNearby,
isFeedFilteredByNearby: this.isFeedFilteredByNearby,
},
});
if (!this.shouldIncludeRecord(record, fulfillsPlan)) {
logger.debug("[HomeView] ❌ Record filtered out:", record.jwtId);
return null;
}
const provider = this.extractProvider(claim);
const providedByPlan = await this.getProvidedByPlan(provider);
logger.debug("[HomeView] ✅ Record included:", record.jwtId);
return this.createFeedRecord(
record,
claim,
@ -1103,6 +1182,22 @@ export default class HomeView extends Vue {
}
}
// Add debug logging for nearby filter
if (this.isFeedFilteredByNearby && record.fulfillsPlanHandleId) {
logger.debug("[HomeView] 🔍 Nearby filter check:", {
recordId: record.jwtId,
hasFulfillsPlan: !!fulfillsPlan,
hasLocation: !!(fulfillsPlan?.locLat && fulfillsPlan?.locLon),
location: fulfillsPlan
? { lat: fulfillsPlan.locLat, lon: fulfillsPlan.locLon }
: null,
inSearchBox: fulfillsPlan
? this.latLongInAnySearchBox(fulfillsPlan.locLat, fulfillsPlan.locLon)
: null,
finalResult: anyMatch,
});
}
return anyMatch;
}
@ -1538,7 +1633,10 @@ export default class HomeView extends Vue {
* Called by template click handler
*/
openFeedFilters() {
(this.$refs.feedFilters as FeedFilters).open(this.reloadFeedOnChange);
(this.$refs.feedFilters as FeedFilters).open(
this.reloadFeedOnChange,
this.activeDid,
);
}
/**

Loading…
Cancel
Save