question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Multiline string indent control does not work

See original GitHub issue

Hi there,

First: Nice project, it reduced the code for my CodeGenerator from about 1200 very confusing lines to about 700 clearly readable lines. 😃

But I need to write some multiline strings, but they cause problems. A few examples:

using var stringWriter = new StringWriter();
var codeWriter = new CodegenTextWriter(stringWriter);

var s = @"a
empty:

c
empty:

e";

codeWriter.WriteLine($$"""
    namespace N
    {
        public class A
        {
            {{TestMethod(s, "Test1", StringToCode1)}}
            {{TestMethod(s, "Test2", StringToCode2)}}
            {{TestMethod(s, "Test3", StringToCode3)}}
            {{TestMethod(s, "Test4", StringToCode4)}}
            {{TestMethod(s, "Test5", StringToCode5)}}
            {{TestMethod(s, "Test_Workaround", StringToCode_Workaround)}}
            // All tests end
        }
    }
    """);

codeWriter.Flush();

Console.WriteLine(stringWriter.ToString());

static FormattableString TestMethod(string s, string name, Func<string, object> getStringCode)
{
    return $$"""
        public static string {{name}}()
        {
            return {{getStringCode(s)}};
        }
        // {{name}} end
        """;
}
static object StringToCode1(string s)
    => $"\"{s}\"";
static FormattableString StringToCode2(string s)
    => $$"""
        @"{{s}}"
        """;
static FormattableString StringToCode3(string s)
    => $$"""
        @"{{s.Split(new[] { "\r\n", "\r", "\n" }, StringSplitOptions.None)}}"
        """;
static FormattableString StringToCode4(string s)
{
    var lines = s
        .Split(new[] { "\r\n", "\r", "\n" }, StringSplitOptions.None)
        .Select<string, FormattableString>(l => $$"""{{l}}""");

    return $$"""
        @"{{lines}}"
        """;
}
static FormattableString StringToCode5(string s)
{
    var lines = s
        .Split(new[] { "\r\n", "\r", "\n" }, StringSplitOptions.None)
        .Select<string, FormattableString>(l => $$"""{{TTW}}{{l}}""");

    return $$"""
        @"{{lines}}"
        """;
}
static Action<ICodegenTextWriter> StringToCode_Workaround(string s)
    => (ICodegenTextWriter writer) =>
    {
        var lines = s
            .Split(new[] { "\r\n", "\r", "\n" }, StringSplitOptions.None);

        var indentLevel = writer.IndentLevel;

        for (int i = 0; i < indentLevel; i++)
            writer.DecreaseIndent();

        writer.Write($"@\"{lines[0]}");

        foreach (var line in lines.Skip(1))
        {
            writer.WriteLine();
            writer.Write(line);
        }

        writer.Write("\"");

        for (int i = 0; i < indentLevel; i++)
            writer.IncreaseIndent();
    };

Das Ergebnis:

namespace N
{
    public class A
    {
        public static string Test1()
        {
            return "a
            return empty:

            return c
            return empty:

            return e";
        }
        // Test1 end
        public static string Test2()
        {
            return @"a
            return @"empty:

            return @"c
            return @"empty:

            return @"e";
        }
        // Test2 end
        public static string Test3()
        {
            return @"a
            return @"empty:
            return @"c
            return @"empty:
            return @"e
            return ";
        }
        // Test3 end
        public static string Test4()
        {
            return @"a
            return @"empty:
            return @"c
            return @"empty:
            return @"e
            return ";
        }
        // Test4 end
        public static string Test5()
        {
            return @"a
return @"empty:
return @"c
return @"empty:
return @"e
            return ";
        }
        // Test5 end
        public static string Test_Workaround()
        {
            return @"a
empty:

c
empty:

e";
    }
    // Test_Workaround end
        // All tests end
    }
}

The last method is my workaround, for my purposes it works, but it messes up the indentation of the following lines, as you can see from the comments. I also had another problem where the string was written without a duplicated return, but the indentation of the new lines was messed up. However, I could not reproduce the problem in the small sample code.

For me this TODO would solve the problem, then I can split the string and put all following lines at the beginning of the line, but this would then no longer be automatic indent control?

Best greetings

Issue Analytics

  • State:closed
  • Created 5 months ago
  • Comments:13 (6 by maintainers)

github_iconTop GitHub Comments

2reactions
loop8ackcommented, May 5, 2023

There it is 😃

However, I think it’s still a bug that it duplicates the text of the same line for multi-line strings.

1reaction
loop8ackcommented, May 10, 2023

Everything works for me - thank you 😃

Read more comments on GitHub >

github_iconTop Results From Across the Web

Proper indentation for multiline strings? - python
If a text file does not work well for your application and you don't want to postprocess, I'd probably go with def foo():...
Read more >
Changing the Indentation of a Multiline String - Python ...
Problem. You have a string made up of multiple lines, and you need to build another string from it, adding or removing leading...
Read more >
Proper Indentation for Python Multiline Strings - YouTube
... #finxter #python Do you want to thrive as a self-employed Python freelancer controlling your own time, income, and work schedule?
Read more >
Multiline template strings that don't break indentation
Solution 1: Ignore all space and tab characters following a newline until the first non-space or tab character. The problem with this is...
Read more >
Pretty print just fixes indentation and doesn't convert/ ...
Limit pretty-print functionality to just fix indentation, i.e. don't convert any quoting style and don't collapse multiline strings.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found