Thread overview
How to evaluate a JSON file at compile time and create a struct out of it?
Oct 04
Dennis
Oct 04
monkyyy
October 04

Hello hello everyone ^_^,

I am new in D, and started this morning. I found a way to read a file at compile time with -J. and static string content = import("my_json_file.json")

But then tried to statically evaluate with static JSONValue j = parseJson(content) but it fails.

main.d(12): Error: variable `content` cannot be read at compile time
main.d(12):        called from here: `readJSON(content)`

Is there a way to achieve this?

My goal is to have a JSONValue at runtime that would be already present in the binary. Cause the JSONValue is huge. Like megabytes of data... And no I don't want to deal with a database for now.

Thank you !

October 04

On Friday, 4 October 2024 at 08:45:49 UTC, holyzantaclara wrote:

>

Hello hello everyone ^_^,

I am new in D, and started this morning. I found a way to read a file at compile time with -J. and static string content = import("my_json_file.json")

But then tried to statically evaluate with static JSONValue j = parseJson(content) but it fails.

main.d(12): Error: variable `content` cannot be read at compile time
main.d(12):        called from here: `readJSON(content)`

Is there a way to achieve this?

My goal is to have a JSONValue at runtime that would be already present in the binary. Cause the JSONValue is huge. Like megabytes of data... And no I don't want to deal with a database for now.

Thank you !

If you use dub, have a "stringImportPaths" field in dub.json which works for me.

dub.json:
```
    {
    	"name": "foo",
    	"stringImportPaths": [
    		"./"
    	]
    }
```

my_json_file.json:
```
    {
    	"name": "foo"
    }

import std;

void main(){

    	immutable content = import("my_json_file.json");

    	pragma(msg, content);
    	
    	immutable mjson = parseJSON(content);
    	
    	writeln(mjson);
    }
```
```
yields:
```
    {
            "name": "foo"
    }
         Linking foo
         Running foo.exe
    {"name":"foo"}
```
October 04

On Friday, 4 October 2024 at 08:45:49 UTC, holyzantaclara wrote:

>

Hello hello everyone ^_^,

I am new in D, and started this morning. I found a way to read a file at compile time with -J. and static string content = import("my_json_file.json")

But then tried to statically evaluate with static JSONValue j = parseJson(content) but it fails.

main.d(12): Error: variable `content` cannot be read at compile time
main.d(12):        called from here: `readJSON(content)`

Is there a way to achieve this?

My goal is to have a JSONValue at runtime that would be already present in the binary. Cause the JSONValue is huge. Like megabytes of data... And no I don't want to deal with a database for now.

Thank you !

Your issue is related to static that seems it does not trigger a compile time evaluation.

October 04

On Friday, 4 October 2024 at 10:33:37 UTC, Ferhat Kurtulmuş wrote:

>

On Friday, 4 October 2024 at 08:45:49 UTC, holyzantaclara wrote:

>

[...]

Your issue is related to static that seems it does not trigger a compile time evaluation.

According to the docs, static does not imply immutability at al. For your case, you can also use enum.

https://dlang.org/spec/attribute.html#static

October 04

On Friday, 4 October 2024 at 08:45:49 UTC, holyzantaclara wrote:

>

I am new in D, and started this morning. I found a way to read a file at compile time with -J. and static string content = import("my_json_file.json")

static usually means "give this declaration the same semantics as if it were at global scope". So:

void main()
{
    static struct S
    {
        int x, y;
    }

    static string v;

    static void fun()
    {

    }
}

// Same meaning as these declarations:
struct S
{
    int x, y;
}

string v;

void fun()
{

}

This turns local variables into global variables, and nested functions which usually can access local variables into functions without access to locals.

When you add static to a variable that is already at global scope, it does nothing.
The confusion is understandable, because static has a million other meanings across programming languages. For example, in C and C++, static global variables/functions do have a meaning, which is similar to D's private. Also, static if and static foreach do imply compile time execution in D, but to enforce compile time execution on a variable, you need the enum or immutable keyword.

immutable string content = import("my_json_file.json")

// Or inside a function:
void main()
{
    static immutable string content = import("my_json_file.json")
}
>

My goal is to have a JSONValue at runtime that would be already present in the binary. Cause the JSONValue is huge. Like megabytes of data...

Be careful that Compile Time Function Execution (CTFE) is not very performant, so parsing a large JSON string at compile time can be very slow and RAM hungry. If you're using dub to build your program, you might want to put the JSON object into its own package so it will be cached, and you won't have to wait so long for your build to finish every time.

October 04

Thank you everyone, true the compilation speed with the static immutable string s is unbearable for my workflow right now. Will try to generate a .d file that would contain a static D object instead and then compile this .d file.

October 04

On Friday, 4 October 2024 at 08:45:49 UTC, holyzantaclara wrote:

>

Hello hello everyone ^_^,

I am new in D, and started this morning. I found a way to read a file at compile time with -J. and static string content = import("my_json_file.json")

https://dlang.org/spec/expression.html#import_expressions

October 04

On Friday, 4 October 2024 at 08:45:49 UTC, holyzantaclara wrote:

>

Is there a way to achieve this?

> >

dub concerns
ctfe risky

whats this fud about?

>

Will try to generate a .d file that would contain a static D object instead and then compile this .d file.

While ctfe json is bad, you should still try to ctfe; without clarification of what the data is idk, but if you could get something like csv that would be trivial.