iphone Core data and entity inheritance - iphone

This is a two part question, here is the situation:
I have an app that lists a set of product models. The user should be able to select from this list the product models that they specifically own. They can own more than 1 of the same type of product and should also be able to set a custom name for the products they own. So I set up my data model with two entities. Product, and OwnedProduct. OwnedProduct inherits from the Product entity and adds a customName property.
Question 1: Is this the best way to implement the model or should I be doing something with relationships? Right now I don't have any relationships in place.
The next question involves actually creating an OwnedProduct record from one of the Products that has been selected by the user.
Question 2: Is there a way to take the selected Product object, duplicate it , and then cast it as an OwnedProduct? Or would I have to create a brand new instance of OwnedProduct and then manually assign all of it's properties from the properties of the Product instance?

Question 1: Is this the best way to implement the model or should I be doing something with relationships? Right now I don't have any relationships in place.
Do you plan to have multiple owners within the same context?
Can a single product be owned by different owners with different custom names?
If yes I would take a look at relationships. I would not duplicate a product because of an ownership. If the product changes, it probably should change for all owners.
A possible datamodel for your requirements:
Question 2: Is there a way to take the selected Product object, duplicate it , and then cast it as an OwnedProduct? Or would I have to create a brand new instance of OwnedProduct and then manually assign all of it's properties from the properties of the Product instance?
As the clone will be a separate instance within your context you have to create a new one and copy all necessary properties. You can speed things up by iterating over NSEntityDescription properties and relationships. There is already a solution to cloning NSManagedObjects on SO

Related

Google Could Datastore - parent entity or array property

I'm trying to get my head around NoSQL and Google Cloud Datastore, and I don't know how to chose between two different options for storing data.
I have a list of orders, and every order is for an unspecified number of products. What are the pros/cons of storing the product list as an array property for the order entity vs having product child entities for each order parent?
Firstly, be well aware of the distinction between the 2 possible approaches of implementing a relationship between entities:
one entity can contain a Key type property pointing to another entity (which might or might not exist!) - this is a functional relationship only, not one at the datastore level
having the 2 datastore entities in a parent-child (ancestry) relationship, inside the same datastore entity group.
Using the 2nd one has scalability implications, see also:
Ancestor relation in datastore
E-commerce Product Categories in Google App Engine (Python)
As for storing a list as an array property vs as separate entities, see Creating your own activity logging in GAE/P (where repeated properties is just how array properties are called in the ndb client library context).

How to set the relationship between the core data entities?

So, I have a core data database with multiple relationship already populated with data. My problem is that I created the relationships between the tables but i don't know how to set them in code. I only need to set one and then I can figure it out for the rest of them.
For example: Colleges has the "has Groups" relationship because one college has many groups. The Groupe table has the "bellongsToColegiu" relationship becouse one or more groups are in one college.
I know that, i have to set the ".bellongsToCollegiu = Colegiu?" or ".hasGrupe = Grupe?" but i don't know how to fetch the college in proper way.
For now I have only one college in database.
Can someone help me with this please? I've been knocking my head for a few days and got nothing.
Thank you and have a nice day!
When you create entities and relationship between them Xcode also generates code for handling those relationships. The name pattern for code that handles relationships are
The same as the name of the relation for to-one relationships
addToX and removeFromX (x is the relationship) for to-many relationship.
So you should have for instance addToHasGrupe(_ value: Grupe) on College and that you can add a group instance to and Grupe should have a belongsToColegiu property that you can set to a college instance. Autocompletion should help you.
You can fetch a existing 'Colegiu' from the data base or create a new one. for both fetching and creating new one you would need a managed object context. Managed object context is the last part of the data stack which has 3 components comprising of 1. Persistence store, 2. persistence store coordinator, and 3. managed object context.
Here is how to create a stack:
https://developer.apple.com/library/content/documentation/Cocoa/Conceptual/CoreData/InitializingtheCoreDataStack.html
Then you can create a new object:
let newItem = NSEntityDescription.insertNewObject(forEntityName: 'Colegiu',
into: 'reference to managed object context here')
or you can search the existing one by calling fetch on managed object context,
Keep in mind CoreData is a complicated topic and it takes time to put the head around. All the best.

Core Data object graph design decision

I am designing an app which tracks data on Game objects. Each Game has a name, a date and other attributes. The problem I am having arises because I want the user to be able to add more names (for example) to pick from in the application. (in this case from a UITableView). So the user is presented with a list of names to choose from, and if the one they want is not in the list, they can add one to the list.
My solution is that I currently have a second entity called GameName so that I can show the user a list of those game names to pick from when they are adding a new Game. I just call an NSFetchRequest on all the GameName objects and display them in the UITableView. There doesn't have to be a Game object created yet to do this.
My dilemma is that I want to know if this is a good practice. It seems that if I do it this way, I will end up having a lot of entities with just one attribute, for the sake of allowing the user to pick from and add to a customizable list.
I hope this makes sense. I can clarify anything upon request.
Your approach is fine, and is commonly used in database design. The entity you want to add is called a "domain table" in databases. See this page, in particular this paragraph:
In a normalized data model, the reference domain is typically specified in a reference table. Following the previous example, a Gender reference table would have exactly two records, one per allowed value—excluding NULL. Reference tables are formally related to other tables in a database by the use of foreign keys.
Of course, you probably want to have an optional relationship between the GameName and Game entities.

How to create Entity dynamically in Objective-C?

I'm building an iPad application where I need user to create entity dynamically. I'm already having 3 entities which program uses.
Could you help me with code how to do it?
I want to understand the whole structure according to my understanding I have to create new managedObjectModel, add new entities and than merge it with existing one, is it correct?
While it is possible to create a new entity and a new model on the fly in practice this is massively complex. If nothing else you would have to migrate any existing persisted data to the new model and a new persistent store file. I strongly recommend against attempting this especially if you are just starting out with Core Data.
You do have options:
Firstly, are you sure you actually need a new entity? People just starting out with Core Data often mistake entities for managed objects. Entities are to managed objects as classes are to instances. Entities are abstractions used to create the object graph. They don't actually contain data. The times when you need new entities are very,very rare.
Secondly, if you do need some kind of dynamic entity, it would usually be best to decompose the dynamic entity into numerous fixed subentities and then use relationships to create a virtual entity. E.g. you need a dynamic Person "entity" so you create several entities in the model each of which holds one attribute of the person. You could have a Field entity which would have a fieldName attribute and then a fieldValue attribute. Then have a an actual Person entity that has no attributes but just relationships to the necessary Field objects. You could add any fields needed to any person and then reconstitute an virtual person object by walking the relationships to its fields.
I rather doubt however that you need that kind of flexibility. Such a need is very rare. I would step back and see exactly what dynamic data you think the user might need to enter.
That's correct -- you'd create an array of NSEntityDescription objects, then call setEntities: on the new managed object model. Then, finally, you'd merge that model with your built-in model.
But note that you can't change a model once it has been used to create a managed object context (or used for storage). You'll need to create new storage and context after the model is changed.

restrict delete of a referenced managedobject

I have a simple Core Data model:
Entity Team (name, logo)
Entity Sport (name, teams to->many Teams)
So, a Sport can have many Teams
I create the Team first, then add or edit a Sport and add the Teams.
If I delete a Team, my app starts crashing.
I believe because it is looking for the deleted reference.
So, how can I restrict via Core Data, not to delete an Entity which is being used as reference from another Entity's relation.
I don't want to set the relationship to nil. And I don't want to go and delete the Team from the Sport first, and then delete it alone. I just want it to notify that I can't delete it. i.e. I'm looking for a built-in checker.
You might want to read up on Core Data's "Relationship Delete Rules", if you haven't already. And you want to make sure that your Team <<---> Sport relationship is bidirectional.
Alternatively, instead of calling the generated removeXxxObject and removeXxxs methods directly, you may want to implement wrapper methods that do necessary checking before calling 'remove' methods.