Accessing other classes defined in a Model Class file in Zend Framework - zend-framework

I have a model class "Application_Model_Person" located in application/models/Person.php that also defines other classes, like Gender and Age:
class Age
{
...
};
class Gender
{
...
};
class Application_Model_Person
{
...
}
My problem is that I want to access Age and Gender in a controller, but I don't know how. Calling new Application_Model_Age doesn't work because Age.php doesn't exist. I want these classes to stay in Application_Model_Person because they are strongly related.
Any ideas?

Well, either create Application_Model_Age and Application_Model_Gender include the File via
require(APPLICATION_PATH . '/models/Person.php');
$age = new Age();
$gender = new Gender();
I would suggest the first way though. Several Classes in one named File ... might be a personal opinion, but i think that's not the most straightforward thing to do. Even though i understand the relation between the three Classes ;)

Related

Zend Model access in singleton class - best approach

I'm looking for best pattern/approach to access one table data in singleton class (in ZF 1.x). In details:
I have one singleton class (just like Zend_Date for example) that make for me some basic abstract stuff very detached from application reality.
In this class, in two points, I need to access to one db table and I need to make some basic operation on it.
It's not a problem to use my regular ZF models class inside functions of this singleton. It works fine. Now it look like:
class My_ZF_Singleton
{
...
public function someFunctionInMySingleton()
{
...
$oModel = new Model_My_Model_Form_ZF_Application();
$oModel->letsDoSomeStuffWithDb();
...
}
...
}
But I feel in my bones that it's not a very good solution, not so glamour as I would like to be. It make my singleton class more attached to application then it should be. I would like to use some other pattern to access this db data then application model class. I would be very thankfull for any clue or better solution - it's not a "hey I'm stuck probem" or "hey I've got an error" - I'm just looking for better solution.
Not sure I quite understand your question or want the point might be, but I'll try.
In ZF1 the database adapter is typically a singleton already. Multiple databases maybe connected to but each will require a unique identification. Typical access to the default adapter setup in the application.ini or Bootstrap.php:
$adapter = Zend_Db_Table::getDefaultAdapter();
a common way to provide access to a single database table and give access to the Zend_Db_Table api is to build a DbTable model:
class Application_Model_DbTable_TableName extends Zend_DbTable_Abstract
{
protected $_name = 'Table_Name' //required if classname does not match table name
protected $_primary = 'primary_key_column_name'//optional, use if primary key is not 'id'
}
You can treat this class as an instance of the default database adapter for a single table (works really well in a mapper). You can also add functions to this class to override or add to the default Zend_Db_Table api.
I hope this at least comes close.

EF Codefirst, One class, multiple tables with discriminator

I doing a little investigation and I am wondering if the following is possible.
I am looking to create a BaseEntityWithDetails class that I can reuse for any type that I would like to have extendable. For example
public abstract class EntityDetail
{
}
This class is used to persist a key and value for the entity.
"Products" would be extended by doing the following...
public class ProductDetail : EntityDetail
{
}
public class Product : BaseEntityWithDetails<ProductDetail>
{
}
The base class "BaseEntityWithDetails" will provide some helper methods for setting and getting. What do you think?
What is the most effective way of mapping this with EF CodeFirst while being super easy to allow another type implement an DetailsEntityTypeConfiguration like the following
public class ProductMap : DetailsEntityTypeConfiguration<Product, ProductDetail>
{
}
Thanks in advance!
I would like to quote someone really smart on this: Reuse is a fallacy. Don't bother doing stuff like this because it will only make your design more obfuscated and complex. Save your inheritance to the entities in your domain which really share the same behavior, don't do this type of assumptions up front.
As a side note: You can map this as a table per type if you put your "EntityDetail" into your database, but as I said before, this is just not a good idea.

MVC2 Action to handle multiple models

I've been looking around for an answer to this, which I can't believe hasn't been asked before, but with no luck I'm attempting here.
I have a signup form which differs slightly based upon what type of participant the requester is. While writing tests for the solution, I realized that all actions did the same things, so I'm attempting to combine the actions into one using a strategy pattern.
public abstract class BaseForm { common properties and methods }
public class Form1 : BaseForm { unique properties and overrides }
....
public class FormX : BaseForm { unique properties and overrides... in all about 5 forms }
Here is the combined action:
[ModelStateToTempData, HttpPost]
public ActionResult Signup(int id, FormCollection collection)
{
uiWrapper= this.uiWrapperCollection.SingleOrDefault(w => w.CanHandle(collection));
// nullcheck on uiWrapper, redirect if null
var /*BaseForm*/ form = uiWrapper.GetForm(); // Returns FormX corresponding to collection.
this.TryUpdateModel(form, collection.ToValueProvider()); // Here is the problem
form.Validate(this.ModelState); // Multi-Property validation unique to some forms.
if (!this.ModelState.IsValid)
return this.RedirectToAction(c => c.Signup(id));
this.Logic.Save(form.ToDomainClass());
return this.RedirectToAction(c => c.SignupComplete());
}
The problem I'm having is that TryUpdateModel binds only the common properties found in BaseForm. My previous code used public ActionResult FormName(int id, FormX form) which bound properly. However, I did some testing and discovered that if I replace var form with FormX form the form binds and everything works, but I'm back to one action per form type.
I'm hoping to find a way to get this to bind properly. form.GetType() returns the proper non-base class of the form, but I'm not sure of how to grab the constructor, instantiate a class, and then throw that into TryUpdateModel. I know that the other possibility is a custom ModelBinder, but I don't see a way of creating one without running into the same FormBase problem.
Any ideas or suggestions of where to look?
I was trying to do something similar to Linq, I was trying to create a class that would inherit some standard fields (ID, etc). I found that the default Linq engine would only use fields from the instantiated class, not from any inherited classes or interfaces.
To construct a Type simply use code like:
var form = Activator.CreateInstance(uiWrapper.GetForm());
I figured it out!
Erik's answer wasn't the solution, but for some reason it made me think of the solution.
What I really want form to be is a dynamic type. If I change this line:
dynamic form = uiWrapper.GetForm();
Everything works :)
On top of that, logic.Save(form.ToDomainClass()) also goes directly to Save(DomainTypeOfForm) rather than Save(BaseDomainForm) so I can avoid the headache there as well. I knew that once I figured out the problem here I could apply the answer in my logic class as well.

Extend model class in ASP.MVC (inheritance?)

i'd like to create something like wrapper or mayby better word would be "Extension" for generated in EntityFramework model class...
I've got model USER, with password, username etc... and user is in relation many-to-many with some other objects... whatever...
I'd like to create something like this:
class ExtendedUser : USER {
public void AddObject(Object o) {}
}
But i don't know, is it good idea...
I don't know how to create constructor. I'd like do something like this.
User u = ...;
ExtendedUser eu = u as ExtendedUser;
Conceptual i'd like to fetch data from DB and put it into ExtendedUser instance, because this object will have methods to manipulate on this data...
How to do this?
I believe that the classes generated by the entity framework are partial classes, so you could create another partial class with the same name, within the same namespace, and you should see any extra methods that you add on the user class, e.g.:
partial class User
{
//Generated code
}
partial class User
{
public void MyMethod();
}
User u = new User();
u.MyMethod();
If you just want to extend methods, that's enough. However if you also want to add metadata to your model (like data annotations, etc.) this approach doesn't works.
In fact, you can only add methods to the auto generated class.
I answered a question about adding and preserving data annotations to auto generated entity classes, here.

How Do You Create Multiple Instances of a Library Class in CodeIgniter?

I'd like to create several instances of a class in CodeIgniter. I have created my class as a library, but cannot figure out the syntax to use to create more than one instance.
From the CodeIgniter users guide:
CI Users Guide: Loader Class
Assigning a Library to a different object name
If the third (optional) parameter is
blank, the library will usually be
assigned to an object with the same
name as the library. For example, if
the library is named Session, it will
be assigned to a variable named
$this->session.
If you prefer to set your own class
names you can pass its value to the
third parameter:
$this->load->library('session', '',
'my_session');
Session class is now accessed.
using:
$this->my_session
I think that's what you're looking for.
I know this thread is long passed, but it was one of the questions I came across while looking for my answer. So here's my solution...
It's PHP. Create your class as a library, load it using the standard CI Loader Class, but use it like you would in a regular PHP script.
Build your class:
class My_class {
var $number;
public function __construct($given_number){
$number = $given_number;
}
public function set_new_num($given_number){
$number = $given_number;
}
}
Load it:
// This will load the code so PHP can create an instance of the class
$this->load->library('My_class');
Then instantiate and use the object where needed:
$num = new My_class(24);
echo $num->number;
// OUTPUT: 24
$num->set_new_num(12);
echo $num->number;
// OUTPUT: 12
The only time I use $this->my_class is to make calls to static functions that I code.
Sorry for reviving this topic but I think I might have something reasonable to add.
You can do this to add multiple instances of a class. I don't know if it violates Codeigniter standard usage anyhow but seems more Codeigniterish than loading a library (which creates $this->library_name which isn't used) and then making 2 MORE instances with the "new" keyword.
$this->load->library( 'my_library', '', 'instance1' );
$this->load->library( 'my_library', '', 'instance2' );
$this->instance1->my_class_variable = 1;
$this->instance2->my_class_variable = 2;
echo $this->instance1->my_class_variable; // outputs 1
echo $this->instance2->my_class_variable; // outputs 2
I use this in my code to generate different menus. I have a "menu" class and different instances for each menu, with different menu items in each.