sphinx-needs icon indicating copy to clipboard operation
sphinx-needs copied to clipboard

✨ Add `list-needs` directive

Open chrisjsewell opened this issue 11 months ago • 5 comments

The list2need directive has a number of notable issues:

  • It uses a bespoke syntax that users have to learn, and contains numerous problematic edge cases (#1323)
  • It uses jinja templating for parsing, which
    • breaks the source mapping for the entire file a list2need is part of
    • it is incompatible with other parsers such a MyST

This directive is intended to replace list2need, using parsing logic similar to the list-table directive, whereby the content is first parsed as a standard field list, then converted to needs. This contains no bespoke syntax, preserves source mapping, and can be used within a MyST document.

See https://sphinx-needs--1427.org.readthedocs.build/en/1427/directives/list-needs.html

TODO: if agreed, look to "soft deprecate" list2need, so that at least new users don't use it, and old users can be guided to start porting


Comparision:

.. list2need::
   :types: req, spec, feat
   :tags: a,b,c

   * Need example on level 1
   * (NEED-002) Another Need example on level 1 with a given ID
     * Sub-Need on level 2 with status option set ((status='open'))
     * Another Sub-Need on level 2. Where this sentence will be used
       as content, the first one as title.
       * Sub-Need on level 3. With some rst-syntax support for
         the **content** by :ref:`list2need`
.. list-needs::
   :defaults:
      :tags: a,b,c

   :req: Need example on level 1
   :req id=NEED-002:
      Another Need example on level 1 with a given ID

      :spec status=open: Sub-Need on level 2 with status option set 
      :spec: Another Sub-Need on level 2.

         Where this sentence will be used as content, the first one as title.

         :feat collapse: Sub-Need on level 3.

            With all rst-syntax support for the **content** by :ref:`list-needs`

Most basic example:

.. list-needs::

    :req: Need example title
    :req: Another need example with nested needs.

       :spec: Sub-Need on level 2
       :spec: Another sub-need

chrisjsewell avatar Mar 24 '25 09:03 chrisjsewell

Codecov Report

Attention: Patch coverage is 80.47809% with 49 lines in your changes missing coverage. Please review.

Project coverage is 88.26%. Comparing base (4e10030) to head (f8c0553). Report is 123 commits behind head on master.

Files with missing lines Patch % Lines
sphinx_needs/directives/listneeds.py 79.14% 49 Missing :warning:
Additional details and impacted files
@@            Coverage Diff             @@
##           master    #1427      +/-   ##
==========================================
+ Coverage   86.87%   88.26%   +1.38%     
==========================================
  Files          56       61       +5     
  Lines        6532     7471     +939     
==========================================
+ Hits         5675     6594     +919     
- Misses        857      877      +20     
Flag Coverage Δ
pytests 88.26% <80.47%> (+1.38%) :arrow_up:

Flags with carried forward coverage won't be shown. Click here to find out more.

:umbrella: View full report in Codecov by Sentry.
:loudspeaker: Have feedback on the report? Share it here.

:rocket: New features to boost your workflow:
  • :snowflake: Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • :package: JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

codecov[bot] avatar Mar 24 '25 09:03 codecov[bot]

The main motivation of list2need was to have a short, simple syntax to create quick & dirty lists during meetings.

The new one is quite overhanging for this use case.

I like the implementation itself, but for the syntax we should try to keep it comprehensive and short. For instance the list-level shall automatically define the need-type.

So the question is, can we save the syntax (mostly) but have a better implementation (without jinja)?

danwos avatar Mar 24 '25 13:03 danwos

In its most basic form, the new directive looks like this:

.. list-needs::

    :req: Need example title
    :req: Another need example with nested needs.

       :spec: Sub-Need on level 2
       :spec: Another sub-need

I think this is also comprehensive and short. (I updated above example, it's messed up due to tabs/spaces mix.) Only diff to list2needs is that the need type is explicitly specified. Cannot let the nesting level decide about that anymore.

We win

  • standardized syntax that is part of the RST language
  • syntactical separation of options (part of the field) and title markup (right of the field); this also means no custom syntax and no escaping mechanisms around brackets.
  • no special symbol . that separate title and content; while I see the point of having the smallest possible syntax, it's hard to build a well-behaving parser around this (how to end a title with a dot?) without thinking about all the corner cases.
  • avoid Jinja templating (which we could also fix in the list2needs directive)

We lose:

  • list2needs users have to migrate their syntax - not sure if that is a heavily used feature; with a deprecation phase I think this is acceptable.

Any other opinions from the community?

ubmarco avatar Mar 24 '25 20:03 ubmarco

Any other opinions from the community?

I would cc @christopheseyler, as this would essentially supersede #1416 (and contains the defaults option)

chrisjsewell avatar Mar 24 '25 21:03 chrisjsewell

I do not see the benefit comparing to the existing : the list2need provides a lightweight and more direct syntax to quickly write a list of requirements

.. list-need
    :req: Need example on level 1

    :req id=NEED-002: Another Need example on level 1 with a given ID

instead of

.. need:: Need example on level 1

.. need:: Another Need example on level 1 with a given ID

    :id: NEED-002

The syntax of the actual list2need is more compact and more readable, IMO

christopheseyler avatar Mar 25 '25 12:03 christopheseyler