Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Introduce RemoteCollection.Rename. #741

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

Merged
merged 1 commit into from
Jun 6, 2014
Merged

Conversation

Therzok
Copy link
Member

@Therzok Therzok commented Jun 2, 2014

Ready to merge on sight!

@Therzok
Copy link
Member Author

Therzok commented Jun 2, 2014

/cc @nulltoken @carlosmn

@Therzok
Copy link
Member Author

Therzok commented Jun 3, 2014

In fact, should I just use the internal delegate for interop and make the RemoteCollection.Rename take a Func<string, bool> ?

@carlosmn
Copy link
Member

carlosmn commented Jun 3, 2014

I like the idea of making it a Func<string, bool>, but @nulltoken knows better. I'm not sure about the compatibility stuff (or even if it's relevant here).

The way you bring in the user's callback is typically by always passing in our own, and passing the user's callback as the pyaload and performing the marshalling of the string in the callback. You can check out e.g. RemoteCallbacks.cs for this pattern.

@dahlbyk
Copy link
Member

dahlbyk commented Jun 4, 2014

A callback for this doesn't seem particularly idiomatic. Maybe return a RemoteRenameResult (or just IEnumerable<string>?) with the problem refs?

@Therzok
Copy link
Member Author

Therzok commented Jun 4, 2014

I could do that. So I just resolve the refspec and tell the user it failed?

@Therzok
Copy link
Member Author

Therzok commented Jun 4, 2014

Also, this requires at least libgit2/libgit2@dfcba09

@dahlbyk
Copy link
Member

dahlbyk commented Jun 4, 2014

I could do that. So I just resolve the refspec and tell the user it failed?

I don't think there's anything to resolve, just marshal the string parameter and add it to the problem spec list.

@Therzok Therzok changed the title Unfinished remote rename implementation. Introduce RemoteCollection.Rename. Jun 5, 2014
@Therzok
Copy link
Member Author

Therzok commented Jun 5, 2014

I still have a nitpick, I don't know how to trigger the problematic refspecs issue. Any pointers on how to trigger it to have some unit tests around it?

int res = NativeMethods.git_remote_rename(
remote,
new_name,
(problem, payload) => { failingRemotes.Add(problem); return 0; },
Copy link
Member Author

Choose a reason for hiding this comment

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

Would this work? Or should I create a specific delegate on top of the delegate type?

Copy link
Member Author

Choose a reason for hiding this comment

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

I mean, I'm unsure if the custom marshaler applies here. I could create a delegate based on rename_problem_cb which wouldn't be collected in this scope.

Copy link
Member

Choose a reason for hiding this comment

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

This works for me. What does the return value mean?

Copy link
Member Author

Choose a reason for hiding this comment

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

0 to ignore error, 1 if you want an error message and stop.

See this.

@dahlbyk
Copy link
Member

dahlbyk commented Jun 5, 2014

I still have a nitpick, I don't know how to trigger the problematic refspecs issue. Any pointers on how to trigger it to have some unit tests around it?

Try manually creating refs/remote/renamed/master and then rename origin to renamed. That should create a conflict in renaming origin/master to renamed/master.

@Therzok
Copy link
Member Author

Therzok commented Jun 5, 2014

That's another test!

@Therzok
Copy link
Member Author

Therzok commented Jun 5, 2014

And by that I mean, I already have more running. :D

@Therzok
Copy link
Member Author

Therzok commented Jun 5, 2014

@dahlbyk Whoa, thanks for that test. It uncovered a bug in libgit2.


var failing = repo.Network.Remotes.Rename("origin", "renamed");
// This fails in libgit2. It changes the manually added ref to /remotes/renamedd/master.
//Assert.NotEmpty(failing);
Copy link
Member Author

Choose a reason for hiding this comment

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

This is most likely a bug in libgit2. The ref I added above is renamed to refs/remotes/renamedd/master.

Copy link
Member

Choose a reason for hiding this comment

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

There's a PR in libgit2. I however don't think failing should contain anything. That reference gets overwritten, as it doesn't belong to a repository.

Copy link
Member Author

Choose a reason for hiding this comment

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

Guess I'll remove that and this is ready to merge.

Copy link
Member

Choose a reason for hiding this comment

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

So @carlosmn in what case would we expect the "problem refspec" callback to fire on a rename?

Copy link
Member Author

Choose a reason for hiding this comment

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

@dahlbyk from what I understood, only when the default fetch refspec doesn't contain the remote name under /refs/remotes/<namehere>/.

/// <param name="name">The current remote name.</param>
/// <param name="newName">The new name the existing remote should bear.</param>
/// <returns>An <see cref="IEnumerable{T}"/> containing the refspecs which failed to be renamed and need manual modifications.</returns>
public virtual IEnumerable<string> Rename(string name, string newName)
Copy link
Member

Choose a reason for hiding this comment

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

Actually, from an API perspective, I think this method should rather return a Remote. This would mimic what other collections do.

So the list of failed refspecs may rather end up being returned in a call back (maybe bearing a similar signature than UnmatchedPathHandler)

Copy link
Member Author

Choose a reason for hiding this comment

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

That was the first approach, but @dahlbyk told me this would be a better approach. Please decide. :D

Copy link
Member Author

Choose a reason for hiding this comment

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

The thing is, the user cant' do anything with that without triggering another interop command and that would blow up on mono. Better just collect them and tell the user to modify them himself.

Copy link
Member Author

Choose a reason for hiding this comment

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

Actually, it won't blow up, since we're in managed land when we get on the callback. But the user still can't do much with that data at that time.

Copy link
Member

Choose a reason for hiding this comment

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

I agree, this is why the callback isn't "stoppable" (it returns void). It would optionally notify the user of refspecs that haven't been properly dealt with.

Copy link
Member Author

Choose a reason for hiding this comment

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

So, should I change this?

Copy link
Member

Choose a reason for hiding this comment

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

That was the first approach, but @dahlbyk told me this would be a better approach. Please decide. 💃

This is my fault. I overlooked this and got a bit late in the game. Let's make this return a Remote and if/when I'll have the chance to meet both of you in person, I'll treat you with 🍻.

Deal? 😉

Copy link
Member Author

Choose a reason for hiding this comment

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

Sure.

@nulltoken
Copy link
Member

@Therzok Pretty neat!

@Therzok
Copy link
Member Author

Therzok commented Jun 6, 2014

/cc @nulltoken how's it now?

int res = NativeMethods.git_remote_rename(
remote,
new_name,
(problem, payload) => { callback(problem); return 0; },
Copy link
Member Author

Choose a reason for hiding this comment

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

I could send the callback as payload, but this works too and it's shorter and more concise.

Copy link
Member

Choose a reason for hiding this comment

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

Couldn't we rather pass IntPtr.Zero (rather than an empty callback) when the user doesn't want to be notified?

Grmpf... The callback doesn't seem to be as optional as it should be (cf https://github.com/libgit2/libgit2/blob/development/src/remote.c#L1450)

/cc @carlosmn

Copy link
Member Author

Choose a reason for hiding this comment

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

Yesh,

Copy link
Member

Choose a reason for hiding this comment

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

I think we should go with returning a list of strings instead of using a callback, but making it optional would be a good first step.

Copy link
Member Author

Choose a reason for hiding this comment

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

How would you handle normal rename issues then?

Copy link
Member

Choose a reason for hiding this comment

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

What would these "normal" issues be? AFAICT we only call this for non-default refspecs.

Copy link
Member Author

Choose a reason for hiding this comment

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

Oh, I see, you meant a ref param with a list of strings.

Copy link
Member

Choose a reason for hiding this comment

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

Yeah, what in C# would be an out param where we tell the caller what went wrong, since this has nothing to do with events and thus doesn't need a callback.

Copy link
Member

Choose a reason for hiding this comment

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

Actually, I'd rather avoid relying on ref/out params on public API as none of the user facing methods behave this way.

Copy link
Member

Choose a reason for hiding this comment

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

Right, I'm talking about the C interface. Hence the "would" :p You still get to keep your fancy return values.

@carlosmn
Copy link
Member

carlosmn commented Jun 6, 2014

I've gone ahead and removed the callback in libgit2/libgit2#2407 and replaced it with a git_strarray.

@Therzok
Copy link
Member Author

Therzok commented Jun 6, 2014

Shall I bump native binaries?

@carlosmn
Copy link
Member

carlosmn commented Jun 6, 2014

Hold off until it's actually merged.

@@ -79,6 +79,15 @@
public delegate void UnmatchedPathHandler(string unmatchedPath);

/// <summary>
/// Delegate definition for rename failure callback.
/// <para>
/// This callback will be called to notify the caller of remotes which need manual modifications.
Copy link
Member

Choose a reason for hiding this comment

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

Shamelessly inspired from libgit2 remote.h

This callback will be called to notify the caller of fetch refspecs
that haven't been automatically updated and need potential manual tweaking.

@Therzok
Copy link
Member Author

Therzok commented Jun 6, 2014

@nulltoken All of the current issues fixed. Shall we wait for the libgit2 PR and bump and update or merge as is?

@nulltoken nulltoken merged commit e1b6166 into libgit2:vNext Jun 6, 2014
@nulltoken
Copy link
Member

All of the current issues fixed

@Therzok Awesome work! 👍 ‼️

Shall we wait for the libgit2 PR and bump and update or merge as is?

Don't worry, we'll update the binaries later. I'm pretty sure @carlosmn is hard at work trying to find so many interesting ways the break the libgit2 API. Again. 😉

@nulltoken nulltoken added this to the v0.19.0 milestone Jun 6, 2014
@Therzok
Copy link
Member Author

Therzok commented Jun 6, 2014

Coool. :D I can now get to working on stuff on XS side. I'll be back with contributions after the weekend.

@nulltoken
Copy link
Member

🚀

@Therzok Therzok deleted the remoteRename branch June 7, 2014 00:50
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 this pull request may close these issues.

4 participants