Description

Describe the bug...

Steps to reproduce

Create a C file (for example) with standard 8-character tab width. Add it to a page with inline:file.c. Observe odd formatting of resulting page.

Example

   1 #include <stdio.h>
   2 
   3 int main (int argc, const char *argv) {
   4 
   5   printf("Hello world!\n");
   6   printf("Using default indent of C Abrev mode in Emacs\n");
   7 
   8   return 0;
   9 }
main.c

   1 #include <stdio.h>
   2 
   3 int main (int argc, const char *argv) {
   4 
   5 	printf("Hello world!\n");
   6 	printf("Using tabs\n");
   7 
   8 	return 0;
   9 }
main-tabs.c

   1 #include <stdio.h>
   2 
   3 int main (int argc, const char *argv) {
   4 
   5         printf("Hello world!\n");
   6         printf("Using (stupid) 8 spaces indent\n");
   7 
   8         return 0;
   9 }
main-8.c

Details

MoinMoin 1.3.3

RedHat 9.0

Python 2.2.2

Workaround

Edit utils/ParserBase.py to replace 4 by 8 in two calls to expandtabs

Discussion

The better solution is to make the value of the tab width an option in wikiconfig.

Python uses 4 spaces per level indentation standard. So I don't think this is a bug.

I'm sorry, I don't see any bug here, see examples. -- NirSoffer 2005-02-15 22:39:39

---

The above discussion mixes up "indentation" with "tabs" a bit too freely. It is common practice to use four spaces for indenting, but a tab character (ASCII 9) is always 8 spaces wide in Python when used at the start of the line. Check the language reference on indentation, second paragraph, for this. The reference also rightfully indicates that this is a standard for Unix. However, Python behaves like this on all platforms, not just on Unix. For example, consider this Python program:

   1 if True:
   2     if False:
   3         pass
   4 	print "Hello"
example.py.

Now consider the same program, but not marked as a Python program by its file extension:

   1 if True:
   2     if False:
   3         pass
   4 	print "Hello"
example.c.

Note that this is physically the same file. I've uploaded it twice, choosing different remote names. It looks different because one line uses eight spaces, while the other uses one tab, and the C and Python formatters of MoinMoin treat this differently. The C formatter uses four spaces, while the Python formatter uses 8 spaces. If you download the second program from the attachments section and execute it with python example.c, then it will not print anything, because the print statement is at the same logical indentation level as the line above it. The interesting thing here is that the Python formatter for MoinMoin is smart enough to replace one tab with eight characters, rather than four as the earlier comment would suggest. Having the C formatter use four spaces instead seems somewhat inconsistent to me, and also diverges from Unix. In any case, one should not argue for it by mentioning Python as a four-space example, since Python clearly and unambiguously defines the tab width to be 8. (C does not need to make such a definition because whitespace is not used for structuring.)

So any reasonable Python formatter must interpret a tab as eight spaces or it will mess up the logical program structure. MoinMoin respects this standard and works correctly for Python files. However, given that it uses a tab as eight spaces in Python, a language where the typical indentation width is four, it seems inconsistent to have a tab be four spaces in other cases. It would be much easier for users to understand a simple rule: "tab width = 8" rather than "tab width = 8 for Python, tab width = something else in other cases". So I'd say it's best to always have a tab be eight spaces. As Nir says, this is very wide indentation, so the reasonable thing is to do as he says: If you want an indentation width of k, type k spaces and don't use tabs at all.

To recap: Keep the concepts indentation and tab apart. One tab is eight spaces. If you want one indentation level to represent four spaces, which is indeed the recommended style for Python, use four space characters per level of indentation. Actually, you could also legally use four spaces for one level of indentation, one tab for two levels, and one tab plus four spaces for three levels of indentation. Of course you shouldn't do this; that way lies madness. It just shows that Python indeed interprets one tab as eight spaces in these contexts.

Addition: If you go to the AttachFile page and click "view" for any of the two attachments, you also see that it is displayed with a tab width of 8. That's an additional inconsistency if a tab width of 4 is used in pretty-printed displays of C code.

--

About language reference on indentation - this is only an implementation detail of the python parser, used to parse text into python code, and has nothing to do with the way code should be rendered, which is a graphic design issue. If the file contain tabs, you will get those tabs when you download the file, and it will be displayed by your text editor according to your preferences.

The test example.c/py test files are examples of bad usage of tabs and spaces. You should not mix them - because each editor might use different value for tab, as its a user preferences, not a standard.

From a design point of view, we should not use 8 spaces for expanding because it leads to too wide texts. We should not waste our time on stuff like this, we have real bugs to fix.

-- NirSoffer 2005-02-16 00:44:39

I said I would not write more on this, but I had a new idea: Don't expand tabs at all, just send tab characters as tab characters. For OSes that have standard widths for tabs, browsers on those OSes should follow those standards and display it correctly. For OSes where tabs are seen as configurable-width, browsers should include a setting to configure tab width. (If they don't do it yet, manufacturers can be pestered. ;-) ) Of course this means that if you want to rely on a particular indentation width, you must use spaces, but in environments with configurable tab widths, this is the case anyway, so no harm done. I have suggested this to Nir in e-mail first to check if this fits "both worlds" and he considers it a reasonable solution, so maybe everyone can agree on this.

Attached is a test file from Nir to see if this works well with all browsers: tabs-test.html. It should, because tab characters are perfectly ordinary ASCII, but a test won't hurt. Everything looks as expected under Firefox and Safari (tested by Nir), and under Mozilla and Internet Explorer (tested by Malte).

-- MalteHelmert 2005-02-17 01:55:05

Plan

Check if its possible to don't expand tabs for display, tabs will display as tabs.


CategoryMoinMoinBug

MoinMoin: MoinMoinBugs/TabWidthInParserBase (last edited 2008-03-18 19:08:09 by JohannesBerg)