Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[BUG] Two Calendar objects with different events should not == each other #526

Closed
Lx opened this issue Jun 27, 2023 · 5 comments · Fixed by #550
Closed

[BUG] Two Calendar objects with different events should not == each other #526

Lx opened this issue Jun 27, 2023 · 5 comments · Fixed by #550

Comments

@Lx
Copy link

Lx commented Jun 27, 2023

Describe the bug

Given two Calendar objects being loaded from a .ics file (one fresh, one cached):

calendar_a: icalendar.cal.Calendar
calendar_b: icalendar.cal.Calendar

I would expect (and attempted to rely upon) the == operator to reliably test whether they're the same or not (so I can avoid emitting "changes" when no changes have occurred).

calendar_a == calendar_b in all cases, regardless of whether their contents differ.

Expected behavior

The == operator correctly returns True or False depending on content.

@niccokunzmann
Copy link
Member

niccokunzmann commented Jun 27, 2023 via email

@Lx
Copy link
Author

Lx commented Jun 27, 2023

Thanks for looking into this.

  • In my use case, an ICS file is periodically downloaded and parsed via Calendar.from_ical(ics_file_as_bytes).
  • On subsequent loads, the calendar needs to be compared with the previous one and act only if any event changes have occurred.
    • For avoidance of doubt, two different Calendar object instances are being compared—that is, id(calendar_a) != id(calendar_b).
  • Most of the time, there is no change, and calendar_a == calendar_b has evaluated to True (as expected if Calendar equality checking has overridden the default mechanism of comparing ids).
  • When the calendars do differ, calendar_a == calendar_b still evaluates to True (which is very unexpected).

I did not fully understand how equality is determined.

My expectation would be that calendar_a == calendar_b if and only if both calendars convey exactly the same information. If calendar_b had an additional event, or if one of its events' descriptions had been changed, I would expect that calendar_a != calendar_b. I may be misunderstanding your request for clarification—does this help?

How is this equality universal for all the sub-components?

Sorry, but I don't immediately understand what is being asked. Could you please rephrase?

Looking broadly at the codebase, it seems that the equality checking is done in CaselessDict:

def __eq__(self, other):
return self is other or dict(self.items()) == dict(other.items())

which to me is doubly surprising, because at first glance, this should return False whenever two objects' items aren't in the exact same order, let alone if the two objects have a different number of keys. Could this be a hashing issue maybe?

@niccokunzmann
Copy link
Member

niccokunzmann commented Jun 27, 2023 via email

@yassirasad
Copy link

@niccokunzmann
This issue occurred to me as well, you can verify it with any two ICS files which are different.

jacadzaca added a commit to jacadzaca/icalendar that referenced this issue Sep 1, 2023
@jacadzaca jacadzaca mentioned this issue Sep 1, 2023
jacadzaca added a commit to jacadzaca/icalendar that referenced this issue Sep 1, 2023
jacadzaca added a commit to jacadzaca/icalendar that referenced this issue Sep 1, 2023
@niccokunzmann
Copy link
Member

See also #570.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants