add tag
samcarter
I'm looking for a way to include (only) the comments from a .sty file as actual text in another document.

At first I thought about using the `catchfilebetweentags` package, but this shallows line endings and can't deal with verbatim content.

Are there any other ways to include commented lines from another file? 

MWE (I'm not set on any specific syntax, feel free to add tags/characters/whatever as long as the lines stay commented in the .sty file)

```
\documentclass{article}

\begin{filecontents*}[overwrite]{duck.sty}

\newcommand{\quack}{Quack!}

% line to be included in the other document
% \begin{verbatim}
% something verbatim to be included in other document
% \end{verbatim}

%% line not to be included 

\end{filecontents*}

\begin{document}

some text

some magic is needed here to include the line "line to be included in the other document" and the verbatim material here

\end{document}
```

*Background: I like the concept of keeping the documentation close to the source, like it is done in `.dtx` files, however I would prefer to directly have the `.sty` file available (this makes it easier to switch between different versions/branches with git and is also easier for users to install if they don't have deep latex knowledge).*
Top Answer
Phelype Oleinik
Here's one possibility.  The command `\CommentInput{⟨file⟩}` reads the `⟨file⟩`, parsing it line by line, and rewriting the lines that start with a single `%` to a file `\jobname.cif` (cif stands for Comment Input File) without the leading `%`, then proceeds to read the `\jobname.cif` file back in.

I don't see how it would be possible to do this without the intermediate file while keeping the possibility of verbatim environments and commands with arguments spanning more than one line.  But I think the extra file shouldn't be that big of an issue.

The code takes care to make a file substitution so that file hooks still work by name on the original file you want to read in, rather than on the temporary file.

This behaves different from `\DocInput` regarding the `%` sign:  `\DocInput` makes a `%` catcode-9, so it's completely ignored (anywhere in the line) while here only the first `%` is removed and the other ones are still comment characters (also `^^A` is not a comment char then).  This is harder to change because then unless the `doc` package is loaded, the `verbatim` environment will see the should-be-ignored start-of-line `%` character and will typeset it.  It is easy to change though, if you intend to use this with `doc` and prefer the all-`%`-are-ignored behaviour.

And without further ado, here's the code:
```
\documentclass{article}

\begin{filecontents*}[overwrite]{duck.sty}

\newcommand{\quack}{Quack!}

% line to be included in the other document
% \begin{verbatim}
% something verbatim to be included in other document
% \end{verbatim}

%% line not to be included 

\end{filecontents*}

\ExplSyntaxOn
\makeatletter
\iow_new:N \l__samcarter_iow
\tl_new:N \l__samcarter_file_name_tl
\NewDocumentCommand \CommentInput { m }
  { \samcarter_comment_input:n {#1} }
\cs_new_protected:Npn \samcarter_comment_input:n #1
  {
    \file_get_full_name:nNTF {#1} \l__samcarter_file_name_tl
      { \__samcarter_comment_input: }
      { \msg_error:nnn { samcarter } { file-not-found } {#1} }
  }
\msg_new:nnn { samcarter } { file-not-found } { File~'#1'~not~found. }
\cs_new_protected:Npn \__samcarter_comment_input:
  {
    \group_begin:
      \cctab_select:N \c_other_cctab
      \int_set:Nn \tex_endlinechar:D { `\^^M }
      \use:x { \tex_everyeof:D { \exp_not:N \q_nil \char_generate:nn { 13 } { 13 } } }
      \char_set_active_eq:NN \^^M \__samcarter_process_line:w
      \char_set_catcode_active:N \^^M
      \iow_open:Nn \l__samcarter_iow { \c_sys_jobname_str . cif } % cif => comment input file
      \exp_after:wN \__samcarter_process_line:w
        \tex_input:D { \l__samcarter_file_name_tl }
      \iow_close:N \l__samcarter_iow
    \group_end:
    \declare@file@substitution { \l__samcarter_file_name_tl } { \c_sys_jobname_str . cif }
    \input { \l__samcarter_file_name_tl }
    \undeclare@file@substitution { \l__samcarter_file_name_tl }
  }
\group_begin:
\char_set_catcode_active:N \^^M
\char_set_active_eq:NN \^^M \scan_stop:
\cs_new_protected:Npx \__samcarter_process_line:w #1 ^^M
  { \exp_not:N \__samcarter_parse_line:w ^^M #1 ^^M \c_percent_str \s_stop }
\cs_set_protected:Npn \__samcarter_tmp:w #1
  {
    \cs_new_protected:Npn \__samcarter_parse_line:w ##1 ^^M #1 ##2 \s_stop
      {
        \tl_if_empty:nTF {##1}
          {
            \peek_charcode_remove:NTF #1
              { \__samcarter_ignore_line:w }
              { \__samcarter_output_line:w }
            ##2 \s_stop ^^M
          }
          {
            \tl_set:Nx \l_tmpa_tl { \tl_tail:n {##1} }
            \tl_if_eq:NNF \l_tmpa_tl \q_nil { ^^M }
          }
      }
    \cs_new_protected:Npn \__samcarter_output_line:w ##1 ^^M #1 \s_stop
      { \iow_now:Nn \l__samcarter_iow {##1} }
    \cs_new_protected:Npn \__samcarter_ignore_line:w ##1 \s_stop { }
  }
\exp_args:No \__samcarter_tmp:w { \c_percent_str }
\group_end:
\makeatother
\ExplSyntaxOff

\begin{document}

some text

\AddToHook{file/before/duck.sty}{A line added with a hook\par}

\CommentInput{duck.sty}

\end{document}
```

Enter question or answer id or url (and optionally further answer ids/urls from the same question) from

Separate each id/url with a space. No need to list your own answers; they will be imported automatically.