git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: [PATCH v10 13/14] convert: add filter.<driver>.process option

From
Jakub Narębski <jnareb@gmail.com>
Date
Oct 15, 2016, 19:42 UTC
Message-ID
<06ff0781-edb8-d3fb-d588-094b1299cb54@gmail.com>
In-Reply-To
<3732E902-2FE9-4C99-B27D-69B9A3FF8639@gmail.com>
W dniu 15.10.2016 o 16:45, Lars Schneider pisze:
Show 51 quoted lines
>> On 12 Oct 2016, at 03:54, Jakub Narębski <jnareb@gmail.com> wrote:
>> W dniu 12.10.2016 o 00:26, Lars Schneider pisze: 
>>>> On 09 Oct 2016, at 01:06, Jakub Narębski <jnareb@gmail.com> wrote:
>>>>>
>>>
>>>>> After the filter started
>>>>> Git sends a welcome message ("git-filter-client"), a list of
>>>>> supported protocol version numbers, and a flush packet. Git expects
>>>>> +to read a welcome response message ("git-filter-server") and exactly
>>>>> +one protocol version number from the previously sent list. All further
>>>>> +communication will be based on the selected version. The remaining
>>>>> +protocol description below documents "version=2". Please note that
>>>>> +"version=42" in the example below does not exist and is only there
>>>>> +to illustrate how the protocol would look like with more than one
>>>>> +version.
>>>>> +
>>>>> +After the version negotiation Git sends a list of all capabilities that
>>>>> +it supports and a flush packet. Git expects to read a list of desired
>>>>> +capabilities, which must be a subset of the supported capabilities list,
>>>>> +and a flush packet as response:
>>>>> +------------------------
>>>>> +packet:          git> git-filter-client
>>>>> +packet:          git> version=2
>>>>> +packet:          git> version=42
>>>>> +packet:          git> 0000
>>>>> +packet:          git< git-filter-server
>>>>> +packet:          git< version=2
>>>>> +packet:          git> clean=true
>>>>> +packet:          git> smudge=true
>>>>> +packet:          git> not-yet-invented=true
>>>>> +packet:          git> 0000
>>>>> +packet:          git< clean=true
>>>>> +packet:          git< smudge=true
>>>>> +packet:          git< 0000
>>>>
>>>> WARNING: This example is different from description!!!
>>>
>>> Can you try to explain the difference more clearly? I read it multiple
>>> times and I think this is sound.
>>
>> I'm sorry it was *my mistake*.  I have read the example exchange wrong.
>>
>> On the other hand that means that I have other comment, which I though
>> was addressed already in v10, namely that not all exchanges ends with
>> flush packet (inconsistency, and I think a bit of lack of extendability).
> 
> Well, this part of the protocol is not supposed to be extensible because
> it is supposed to deal *only* with the version number. It needs to keep 
> the same structure to ensure forward and backward compatibility.
> 
> However, for consistency sake I will add a flush packet.
Thanks.  That is one thing I feel quite strongly about.

I can agree that extendability does not matter much here: we can always change the version number. But there might be some additional information that filter process wants to send to Git in first exchange, and using flush-terminated list here means that we don't need to change version number, assuming that this additional information is advisory.

The consistency means in my opinion that it should be easier to implement filter scripts.

Show 25 quoted lines
>>>> In description above the example you have 4-part handshake, not 3-part;
>>>> the filter is described to send list of supported capabilities last
>>>> (a subset of what Git command supports).
>>>
>>> Part 1: Git sends a welcome message...
>>> Part 2: Git expects to read a welcome response message...
>>> Part 3: After the version negotiation Git sends a list of all capabilities...
>>> Part 4: Git expects to read a list of desired capabilities...
>>>
>>> I think example and text match, no?
>>
>> Yes, it does; as I have said already, I have misread the example. 
>>
>> Anyway, in some cases 4-way handshake, where Git sends list of
>> supported capabilities first, is better.  If the protocol has
>> to prepare something for each of capabilities, and perhaps check
>> those preparation status, it can do it after Git sends what it
>> could need, and before it sends what it does support.
>>
>> Though it looks a bit strange that client (as Git is client here)
>> sends its capabilities first...
> 
> Git tells the filter what it can do. Then the filter decides what
> features it supports. I would prefer to keep it that way as I don't
> see a strong advantage for the other way around.
I think the current order is good, no need to change it.
As I said it is better for Git to send capabilities first.
 
Show 58 quoted lines
>>>> By the way, now I look at it, the argument for using the
>>>> "<capability>=true" format instead of "capability=<capability>"
>>>> (or "supported-command=<capability>") is weak.  The argument for
>>>> using "<variable>=<value>" to make it easier to implement parsing
>>>> is sound, but the argument for "<capability>=true" is weak.
>>>>
>>>> The argument was that with "<capability>=true" one can simply
>>>> parse metadata into hash / dictionary / hashmap, and choose
>>>> response based on that.  Hash / hashmap / associative array
>>>> needs different keys, so the reasoning went for "<capability>=true"
>>>> over "capability=<capability>"... but the filter process still
>>>> needs to handle lines with repeating keys, namely "version=<N>"
>>>> lines!
>>>>
>>>> So the argument doesn't hold water IMVHO, and we can choose
>>>> version which reads better / is more natural.
>>>
>>> I have to agree that "capability=<capability>" might read a
>>> little bit nicer. However, Peff suggested "<capability>=true" 
>>> as his preference and this is absolutely OK with me.
>>
>> From what I remember it was Peff stating that he thinks "<foo>=true"
>> is easier for parsing (it is, but we still need to support the harder
>> way parsing anyway), and offered that "<foo>" is good enough (if less
>> consistent).
>>
>>> I am happy to change that if a second reviewer shares your
>>> opinion.
>>
>> Also, with "capability=<foo>" we can be more self descriptive,
>> for example "supported-command=<foo>"; though "capability" is good
>> enough for me.
>>
>> For example
>>
>> packet:          git> wants=clean
>> packet:          git> wants=smudge
>> packet:          git> wants=size
>> packet:          git> 0000
>> packet:          git< supports=clean
>> packet:          git< supports=smudge
>> packet:          git< 0000
>>
>> Though coming up with good names is hard; and as I said "capability"
>> is good enough; OTOH with "smudge=true" etc. we don't need to come
>> up with good name at all... though I wonder if it is a good thing `\_o,_/
> 
> How about this (I borrowed these terms from contract negotiation)?
> 
> packet:          git> offers=clean
> packet:          git> offers=smudge
> packet:          git> offers=size
> packet:          git> 0000
> packet:          git< accepts=clean
> packet:          git< accepts=smudge
> packet:          git< 0000
> 
> @Peff: Would that be OK for you?

I don't feel strongly about it. It could be "<capability>=true", it could be "<capability>", it could be "capability=<capability>", it could be something more descriptive.

I guess "<capability>=true" looks a bit strange (would it ever be there "<capability>=false"?), but it is good enough for me.

One think we can all agree on is that each capability is to be send as separate packets, and not as space or comma separated list in a single packet (like for fetch / push).

Show 27 quoted lines
>>>>> +------------------------
>>>>> +packet:          git< status=abort
>>>>> +packet:          git< 0000
>>>>> +------------------------
>>>>> +
>>>>> +After the filter has processed a blob it is expected to wait for
>>>>> +the next "key=value" list containing a command. Git will close
>>>>> +the command pipe on exit. The filter is expected to detect EOF
>>>>> +and exit gracefully on its own.
>>>>
>>>> Any "kill filter" solutions should probably be put here.
>>>
>>> Agreed. 
>>>
>>>> I guess
>>>> that filter exiting means EOF on its standard output when read
>>>> by Git command, isn't it?
>>>
>>> Yes, but at this point Git is not listening anymore.
>>
>> I think it might be good idea to have here the information about
>> what filter process should do if it needs maybe lengthy closing
>> process, to not hold/stop Git command or to not be killed.
> 
> I've added:
> 
> "Git will wait until the filter process has stopped."
Thanks.  Looks good for me.

I think any advices (like how to handle shutdown in filter without blocking Git) could be added later, when we have some experience making and using long-running multi-file filter drivers.

Thank you for your work on this series.
-- 
Jakub Narębski
Previous: Jeff KingNext: Junio C Hamano
Message 25 of 34 in “Git filter protocol”
  1. 00/14 Git filter protocollarsxschneider@gmail.com, Oct 8, 2016
  2. 01/14 convert: quote filter names in error messageslarsxschneider@gmail.com, Oct 8, 2016
  3. 02/14 convert: modernize testslarsxschneider@gmail.com, Oct 8, 2016
  4. 03/14 run-command: move check_pipe() from write_or_die to run_commandlarsxschneider@gmail.com, Oct 8, 2016
  5. 04/14 run-command: add clean_on_exit_handlerlarsxschneider@gmail.com, Oct 8, 2016
  6. Johannes SchindelinOct 11, 2016
  7. Lars SchneiderOct 15, 2016
  8. Johannes SchindelinOct 16, 2016
  9. Lars SchneiderOct 16, 2016
  10. 05/14 pkt-line: rename packet_write() to packet_write_fmt()larsxschneider@gmail.com, Oct 8, 2016
  11. 07/14 pkt-line: add packet_write_fmt_gently()larsxschneider@gmail.com, Oct 8, 2016
  12. 08/14 pkt-line: add packet_flush_gently()larsxschneider@gmail.com, Oct 8, 2016
  13. 09/14 pkt-line: add packet_write_gently()larsxschneider@gmail.com, Oct 8, 2016
  14. 11/14 convert: make apply_filter() adhere to standard Git error handlinglarsxschneider@gmail.com, Oct 8, 2016
  15. 06/14 pkt-line: extract set_packet_header()larsxschneider@gmail.com, Oct 8, 2016
  16. 12/14 convert: prepare filter.<driver>.process optionlarsxschneider@gmail.com, Oct 8, 2016
  17. 13/14 convert: add filter.<driver>.process optionlarsxschneider@gmail.com, Oct 8, 2016
  18. Jakub NarębskiOct 8, 2016
  19. Torsten BögershausenOct 9, 2016
  20. Lars SchneiderOct 11, 2016
  21. Lars SchneiderOct 11, 2016
  22. Jakub NarębskiOct 12, 2016
  23. Lars SchneiderOct 15, 2016
  24. Jeff KingOct 15, 2016
  25. Jakub NarębskiOct 15, 2016
  26. Junio C HamanoOct 10, 2016
  27. Lars SchneiderOct 11, 2016
  28. Torsten BögershausenOct 11, 2016
  29. Lars SchneiderOct 16, 2016
  30. Junio C HamanoOct 17, 2016
  31. 10/14 pkt-line: add functions to read/write flush terminated packet streamslarsxschneider@gmail.com, Oct 8, 2016
  32. 14/14 contrib/long-running-filter: add long running filter examplelarsxschneider@gmail.com, Oct 8, 2016
  33. Torsten BögershausenOct 9, 2016
  34. Lars SchneiderOct 15, 2016

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.