-
Notifications
You must be signed in to change notification settings - Fork 119
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
Support for associations #11
Comments
You can serialize a vector in Hiberlite, so
would create another table and store employers there. Other C++ way of doing it is:
If those a stored and referenced from elsewhere. I'm not saying that associations is a bad idea, and more than happy to discuss this feature. However, I have some concerns on the philosophical level: The term "association" comes from the database design world, it's not something present in STL, or in I'm sure you don't ask to support association for the sake of it, you want achieve certain behaviour of your code. There may be an easier and "more object-orientier" :) way of achieving that behaviour. |
I agree wholeheartedly that there's a nice object oriented way of dealing with my issue, rather than simply copying database terms. Let me demonstrate what happens. class Person:
Class Employer:
main.cpp:
This creates the following underlying table structures:
Employer table:
Person__Employers_person table:
This is not the table structure that I expect. I expect the following:
Employer table:
Now, what I'd also like to do, is map persons to an employer, with exactly the same table structure as I expect above. This is going to be especially tricky due to circular dependency, and since it's rather late, I have no idea how to best solve this. To show my intent, here's an example of magic thinking:
|
hm, maybe using the SRP and creating another object for that should be a cleaner way to solve the problem? Do you need the back-reference persistent? If not, you might just create a map once at application start and keep it up to date. Correct me, please, if I haven't understood the problem :) |
Well, there are two problems here:
As for the back-reference, I don't know what you mean with persistence? On 4 November 2014 07:11, Dmitry Ledentsov [email protected] wrote:
|
SRP sounds like an overkill to me. We do not support foreign keys, and that may be part of the problem here. How would you write it in C++? I would come up with something like:
Then [what seems to me as] a natural translation to hiberlite API is:
Another good question to ask is what would Boost Serialization? I think quite similar to the above. But there are a few problems with the C++ way:
SQL would be more convenient & powerful here. It also seems to me that SQL association is closer to the "natural language" of what @Oipo wants to implement. I am now leaning towards supporting associations - it may actually be a good idea. |
P.S. with SRP I meant the Single Responsibility Principle, sorry for the ambiguity :) |
What I mean by persistence is the presence of that back-reference in the database. If you can fit it in memory and it doesn't cost you much, one can do the simplest thing first. There's always a possibility of adding features, the question is, why C++ and not C#+EF then?
If you just want to solve it in your case, go for the examples, @paulftw has sketched. Build the C++-side back-reference, i.e. after initializing your data structures.
I can't say much on the subject, since I only occasionally need SQL. If I see a convincing example, I might be able to give a judgement. If the value is learning, then that feature might be fun to implement.
While EF6 is striving to take SQL hell out of C# coders routine, the coders themselves run into troubles in grey zones. i.e. while not exactly the same problem, but ... SO:EF6 code-first inheritance back-reference I am sorry for the meta-talk, but I like hiberlite for its cleanliness. Circular references create chaos in software design, whatever the software is. Thus, I'd recommend two rants from Uncle Bob. As for the software outside the library, I'd suggest to abstract the persistence (DB) layer further at the application level, and write a simple implementation of back-references in pure C++, test it, and then try to implement that in hiberlite, if the use-case is convincing. @Oipo: |
Thanks for your clarification, the SRP idea could probably work in my case of back-reference. However, I do wish to clarify that my Person <-> Employer example is just an example to show a situation where I find odd things. Combined with the lack of internal documentation and also the lack of explanation of why certain design decisions were made, I find myself encountering things I would like to see but aren't yet present in Hiberlite. The use case I have is to do efficient SQL queries, using SQLite's already diminished capabilities. SQLite's capabilities are chosen exactly because they are often used. One of those often used capabilities is to fetch a collection based on a foreign key. As such, I think paul correctly identified one of the problems, namely the missing support for foreign keys in hiberlite. Of course, fetching collections based on any columns is another, separate, functionality that I would like to have, especially in conjunction with joins. An example (in pure SQL) to select all Persons working at an Employer whose name contains 'Eric':
Ideally, doing this in hiberlite would cause each Person to have an initialized Employer and each Employer to have a filled list of Persons. All in one query, such as in nHibernate(which I believe is more or less similar to EF, but as I lack experience in EF, I can't say for sure). However, what I currently have to do, regardless of using SRP or not, in hiberlite is the following:
Of course, I may be missing crucial functionality that is already in hiberlite here. But if I understand correctly, this is needlessly complex, creates two queries with disastrous performance by pulling in ALL instances of both Person and Employer and destroys the one thing SQL was made for: joining arbitrary collections. |
Thank you for your answer too, @Oipo. If I understand you correctly now, you'd like to see an abstraction for queries, such as joins in hiberlite. |
Sorry for the confusion, yes, such an abstraction is what I'd like. I thought, however, that associations were necessary to implement those. Do you have other ideas on how to achieve query abstractions? And should I make a new issue with a better title? |
I haven't looked at that one: quince, but it may suit your needs. The scope is somewhat different, however. |
Ah thanks, that library looks promising. |
@paulftw. I'm now also convinced of associations. Having seen quince, one can define a clear difference of scope of the two libraries. I can imagine a fully hidden queries behind an API that would be understandable without SQL jargon, would however be useful for hiberlite users. I can't think of a good replacement name for a join at the moment, but the first step could be abstracting that query |
@d-led quince is nice, though some of its tricks are a mystery for me:
Maybe down the road we could look into making quince an underlying SQL engine - would let us remove some code and support other RDBMS. With associations - how should it be expressed in code? I'm not concerned about using SQL jargon - it'd be familiar to most developers, unlike for example "transclusion" in AngularJS. But I agree that "join" is far from perfect. Let's decide what we want the code to look like, and then find right words to fill in the gaps. |
@paulftw I'll think about it ... might take time and reading |
It would be really nice to be able to do
The text was updated successfully, but these errors were encountered: