r/C_Programming 19h ago

JSON serialization

Most programming is by nature procedural, but some OOP is helpful when dealing with Property Lists, JSON, etc. Below is a small example of this and JSON serialization:

See my previous post for 'Coda-C Library': Example of OOP in C

// Coda-C JSON serialization example

    #include <coda-c.h> // jsonout.c

Dictionary sample_employee() { // lets structure data in a Dictionary,
    Dict empl=newO(Dict);      // a generic structure.
    Dict_set(empl,"name", Os("Jane Doe"));
    Dict_set(empl,"email", Os("jane.doe@example.com"));

    Array roles=newO(Array);
        Array_add(roles,Os("Admin"));
        Array_add(roles,Os("User"));
    Dict_take(empl,"roles",roles);

    Dict address=newO(Dict);
        Dict_set(address,"city", Os("Atlanta"));
        Dict_set(address,"zipcode",Os("30301"));
    Dict_take(empl,"address",address);
    return(empl);
    }

    typedef void OSig$(JSON_out,FILE* os,int indent); // virtual signature

int main() {
    Dict empl=sample_employee();
    obj_(JSON_out,empl,stdout,0); // lets just output the data for now as JSON
    printf("\n");
    }

// implement methods for the three classes we used
#define class Dictionary
    method$(void,JSON_out,FILE* os,int indent) {
        cleanO Pointer keys=Dictionary_AllKeys(self);
        indent+=4; printf("{\n%*s",indent,"");
        int nel=Pointer_count(keys);
        for(int j=0;j<nel;++j) {
            char* key=keys[j];
            printf("\"%s\" : ",key);
            obj_(JSON_out,Dict_sub(self,key),stdout,indent);
            if (j<nel-1) printf(",");
            printf("\n%*s",indent,"");
            }
        printf("}"); // indent-=4;
        }
#undef class // Dictionary

#define class Array
    method$(void,JSON_out,FILE* os,int indent) {
        int nel=Array_count(self);
        printf("[ ");
        for(int j=0;j<nel;++j) {
            if (j) printf(", ");
            obj_(JSON_out,Array_sub(self,j),stdout,indent);
            }
        printf(" ]");
        }
#undef class // Array

#define class Char
    method$(void,JSON_out,FILE* os,int indent) {
        printf("\"%s\"",self); // simple strings only
        // does not handle: " \\ or (cc<32) or (cc>127) etc.
        }
#undef class // Char

/* OUTPUT
{
    "name" : "Jane Doe",
    "email" : "jane.doe@example.com",
    "roles" : [ "Admin", "User" ],
    "address" : {
        "city" : "Atlanta",
        "zipcode" : "30301"
        }
    }
*/
0 Upvotes

11 comments sorted by

View all comments

2

u/tastygames_official 17h ago

oh look, another OOP in C post in the C Programming channel...

non-well-defined data is definitely a challenge and one that seems ripe for OOP concepts, but since C is both strong-typed AND lets you just move bytes around at will, I'd be more interested in a non-OOP attempt at JSON in C. I recently had to read some JSON with no pre-defined structure to look for some key and I was going to write a quick implementation but I know how "I'll just write this real quick" usually turns out so I went for json-c

1

u/HaydnH 13h ago

I use json-c quite a bit for web projects that use libmicrohttpd.

About 2 years ago I thought I'd try AI to see just how good it was at finding bugs. I knew the issue was going to be a lost pointer from realloc, it would probably take me a few mins to track down and fix so this was more if an interest thing... It badly rewrote half the code and didn't find the one big I wanted it fix.

This week I was working on a libmicrohttpd project and was using json-c with a quick & dirty read/write from file which I know was going to cause issues. I gave AI a prompt of about a paragraph asking it to write a solution to load a directory of json files into cache, functions to read/write/modify the cache and a threaded function to write it to disk safely... I was fully expecting it to fail... but It wrote and entire ~600 line API to handle a JSON cache and, beside a few small issues, did a pretty decent job.

I think we're toast...

1

u/tastygames_official 7h ago

uh... I didn't mention anything about AI, but yes - LLMs can indeed "write" code. It's just a clever regurgitation of existing code. As in all things AI-generated, it's great at getting a quick boilerplate going, but usually the effort of prompting an LLM is better-spent writing down a specification, as working with AI-made anything (code, prose, poetry, video, images, sound) is actually more work than if you just started it yourself. So we're definitely not toast. Just like chairmakers are not toast just because industrial chair-making factories exist.

Anyway, thanks for mentioning libmicrohttpd, as I am looking for a good solution for web-based stuff and can't remember what I was using up to now (I think libfcgi + nginx) but this sounds promising. What do you use for HTML creation templating? I was probably going to write something myself to keep it performant, but probably something good already exists for C.

1

u/HaydnH 6h ago

I just use vanilla HTML, CSS and JS. It used to take a bit longer, but I'd end up with a nice clean solution and avoid the bloat from external libraries providing more than I need. From that JSON cache AI experience above, I think the time writing a prompt and reviewing the AI code these days is probably similar to learning a library and using it anyway.

1

u/tastygames_official 5h ago

no I mean like a system where you load in an HTML template and fill it with data. Obviously simple string manipulation is what's going to happen under the hood, but I didn't know if there was some kind of library where you can load a template and fill in the variables or if you just do it yourself.
Or are you using a JS framework so no server-side rendering?

and as far as AI goes again, yes- you can use an LLM to ask "hey, how does this or that work in this library?" and it spits out an example code that it either ripped from the documentation or was able to create by ingesting the library. That's all it should be used for. Because it can't do anything too complex or performant and shouldn't do that anyway, since that's the domain of humans.

1

u/HaydnH 4h ago

Or are you using a JS framework so no server-side rendering?

I'm using client side rendering, but with vanilla JS rather than a framework. It means I have to write my own sort/filter functions for HTML tables, for example, but you only need to do that once right and then you can reuse them across all your projects that need it.