Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dependency injection in serializer #627

Closed
celian-garcia opened this issue Jun 20, 2017 · 4 comments
Closed

Dependency injection in serializer #627

celian-garcia opened this issue Jun 20, 2017 · 4 comments

Comments

@celian-garcia
Copy link

celian-garcia commented Jun 20, 2017

Hello,
I'm currently using your library with great pleasure but I was wondering if I could inject a service as a dependency to the adl_serializer and how to do that.

I saw that a lot of things are done at compile time so maybe that I'll have to use it as a static service ?
This option would work but if you have a better one, I'm listening :)

To illustrate, here is an example with both solutions.

namespace nlohmann {
    template<>
    struct adl_serializer<firefly::Task> {
        static firefly::Task from_json(const json &j) {
            return firefly::Task(
                    j["name"].get<std::string>(),
                    j["description"].get<std::string>(),
                    ////////////////////////////////////////
                    // Solution 1 (wanted one) : Injected instantiated service ? How to inject it ? 
                    service.getProcessingTypeById(j["type"].get<int>()),
                    service.getModuleById(j["module"].get<int>()),
                    // Solution 2 (working) : Use the service statically
                    firefly::DataService::getProcessingTypeById(j["type"].get<int>()),
                    firefly::DataService::getModuleById(j["module"].get<int>()),
                    ////////////////////////////////////////
                    j["user_name"].get<std::string>(),
                    j["date"].get<std::string>(),
                    j["state"].get<int>()
            );
        }
    };
}

Thank you :)

Célian Garcia

Edit : NB : I'll use "at" instead of "[]" as mentionned in your doc ;)

@theodelrieu
Copy link
Contributor

Hi, you could add a third argument (DataService&) to your method, which would be defaulted to the object you want to use.

I didn't test it, but I'm confident this will work.

@celian-garcia
Copy link
Author

celian-garcia commented Jun 20, 2017 via email

@celian-garcia
Copy link
Author

Your solution did'nt solve my problem since from_json method call the default constructor of the object, and I don't want to make any encapsulated initialization in the default constructor of my object.

Ok after some digging, I found a solution. My solution consist in injecting my DataService after the parse.

Example :

CommonDataStore dataStore("a/file"); // Create the dependency
TaskBuilder taskBuilder = raw_json_data; // Parse the json in a builder (adl_serializer is called with TaskBuilder)
taskBuilder.injectDataStore(dataStore); // Inject the dependency to the builder
Task task = taskBuilder.build(); // The builder use the data from data store to build the Task object

@celian-garcia
Copy link
Author

I close it because it works well for me. Thank you again.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants