Skip to content
This repository was archived by the owner on Sep 6, 2018. It is now read-only.

Fix catalog entry sort#57

Merged
AliSoftware merged 4 commits intoSwiftGen:masterfrom
fdiaz:fix/catalog-entry-sort
Oct 8, 2017
Merged

Fix catalog entry sort#57
AliSoftware merged 4 commits intoSwiftGen:masterfrom
fdiaz:fix/catalog-entry-sort

Conversation

@fdiaz
Copy link
Copy Markdown
Contributor

@fdiaz fdiaz commented Oct 5, 2017

Closes #56

@fdiaz fdiaz force-pushed the fix/catalog-entry-sort branch 2 times, most recently from 60adef8 to 42f14e5 Compare October 5, 2017 18:23
@AliSoftware
Copy link
Copy Markdown
Contributor

Note that this is a duplicate of #55 so whichever of those two will be validated and finished first will invalidate the other one.

PS: If you wish, it could be a nice courtesy to also credit the original author of #55 in your CHANGELOG entry too if you used #55 as inspiration and this #56 is just a continuation of their work to finish the work 😉

@fdiaz fdiaz force-pushed the fix/catalog-entry-sort branch from 42f14e5 to aafe853 Compare October 5, 2017 18:27
@fdiaz
Copy link
Copy Markdown
Contributor Author

fdiaz commented Oct 5, 2017

You're totally right @AliSoftware ! Updated the CHANGELOG. I didn't wanna build on top of #55 since this is a slightly different approach.

#55 modifies AssetsCatalogContext.swift and this PR modifies AssetsCatalogParser.swift.

I took this road since the underlying problem is with the children() function. So this sorts the ouput of anyone using process(folder: Path, withPrefix prefix: String = "")

final class CatalogEntryTests: XCTestCase {
func testGroupEntry_IsComparableAlphabetically() {
let entryA = Catalog.Entry.group(name: "A", items: [])
let entryB = Catalog.Entry.group(name: "B", items: [])
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could be nice to also add some tests using different letter case to check if that comparability is case-sensitive or not (but whether it is or not, that it always sorts ["A","a"].map { Catalog.Entry.group(name: $0, items: []) } in the same order

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Now that I think about it, I should also test that two groups with the same name order its items correctly.

I'll work on that 👍

let entryA = Catalog.Entry.group(name: "A", items: [])
let entryB = Catalog.Entry.group(name: "B", items: [])

XCTAssertEqual(entryA < entryB, true)
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The expected usage of XCTAssertEqual is to take 2 parameters to equate, like XCTAssertEqual(entryA, entryB).

If you want to check if an expression, like entryA < entryB, is true, prefer XCTAssert or XCTAssertTrue.
(Some even prefer using XCTAssertLessThan(entryA, entryB) but this last one being less commonly known, XCTAssert or XCTAssertTrue are generally more fitting)

return .orderedDescending
}

return compare(Array(lhs.dropFirst()), Array(rhs.dropFirst()))
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not a fan of using this recursive approach as it can make the stack grow quite quickly for a group containing 100s of images…

What about:

private static func compare(_ lhs: [Catalog.Entry], _ rhs: [Catalog.Entry]) -> ComparisonResult {
  for pair in zip(lhs, rhs) {
    if pair.0 < pair.1 { return .orderedAscending }
    if pair.0 > pair.1 { return .orderedDescending }
  }
  // If we arrive a this point, this means all pairs have been considered equal
  // but one of the list might be longer than the other
  if lhs.count < rhs.count { return .orderedAscending }
  if lhs.count > rhs.count { return .orderedDescending }
  return .orderedSame
}

Copy link
Copy Markdown
Contributor Author

@fdiaz fdiaz Oct 6, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's a good point and a much cleaner implementation. Updating 👍

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I even wonder if the last part (last 3 lines) couldn't be reduced to return compare(lhs.count, rhs.count)?
(Don't we have a compare(Int,Int) -> ComparisonResult in the stdlib?)

@fdiaz fdiaz force-pushed the fix/catalog-entry-sort branch 2 times, most recently from f4463e2 to bc03531 Compare October 6, 2017 11:38
@AliSoftware AliSoftware requested a review from djbe October 6, 2017 11:51
@@ -82,7 +133,7 @@ extension AssetsCatalogParser {
func process(folder: Path, withPrefix prefix: String = "") -> [Catalog.Entry] {
return (try? folder.children().flatMap {
Copy link
Copy Markdown
Contributor

@AliSoftware AliSoftware Oct 6, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@fdiaz I just realised: wouldn't it be simpler instead of all the Equatable + Comparable implementations you added… to just sort the output of children() directly? i.e. apply folder.children().sorted(by: <).flatMap { … } to children, instead of using folder.children().flatMap { … }.sorted(by: <) and sort the the final, recursively-constructed structure?

Which would mean in practice removing all the code that you added above and a simpler and mode performant solution (because you don't have to traverse the recursive structure twice) in the end, right?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh wow, you're right. I didn't notice that Path was already Comparable. I'll just go back with all these changes and add that little change instead. Nice catch!

fdiaz added 2 commits October 6, 2017 12:18
The children() function uses under the hood
contentsOfDirectory(atPath:) https://developer.apple.com/documentation/foundation/filemanager/1414584-contentsofdirectory

This array returned by that function has an undefined order.
@fdiaz fdiaz force-pushed the fix/catalog-entry-sort branch from bc03531 to 5d1401f Compare October 6, 2017 20:28
Copy link
Copy Markdown
Member

@djbe djbe left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should probably also change our tests to run on the latest Xcode, and the latest macOS (if possible), to ensure that this is actually fixed (and remains so).

Comment thread CHANGELOG.md Outdated
### Bug Fixes

_None_
* Fixes an issue in High Sierra where the output of the processed Catalog Entries was not ordered alphabetically.
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems to be missing the 2 spaces at the end?

@AliSoftware
Copy link
Copy Markdown
Contributor

Good point @djbe our scripts would probably need updating, or more precisely the .circle.yml configuration should target 10.13 at some point.

@fdiaz any news on the rebase we spoke about on slack simplifying this whole PR?

@djbe
Copy link
Copy Markdown
Member

djbe commented Oct 8, 2017

What simplification? This PR boils down to 1 line of code 😄

@AliSoftware
Copy link
Copy Markdown
Contributor

Oh I missed the notification telling me that @fdiaz did in fact already commit the simplification we talked about about sorting children() directly (idk if you saw the PR before that @djbe but it was sorting the output of process() instead, having to do a recursive sort and having to implement Equatable+Comparable on Catalog.Entry and all.

Seems like the Circle tests are still failing though.

@djbe
Copy link
Copy Markdown
Member

djbe commented Oct 8, 2017

Yeah, I partially followed it, will fix the contexts.

@djbe djbe force-pushed the fix/catalog-entry-sort branch from cddee57 to 7128771 Compare October 8, 2017 21:51
@AliSoftware AliSoftware merged commit 1621d9d into SwiftGen:master Oct 8, 2017
@nafu
Copy link
Copy Markdown

nafu commented Oct 9, 2017

Cool 💚

@fdiaz fdiaz deleted the fix/catalog-entry-sort branch October 9, 2017 09:32
@fdiaz
Copy link
Copy Markdown
Contributor Author

fdiaz commented Oct 9, 2017

Thanks for finishing this up @djbe 👍

I'm not sure why the tests were still failing though? Any context on that? I was about to take a look on High Sierra to see what was going on with that.

@djbe
Copy link
Copy Markdown
Member

djbe commented Oct 9, 2017

There is a slight difference between the (built in) sort-order in Sierra, and the sorting we now apply. Nothing much to worry about.

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants