I have a singleton model and an associated AJAX proxy.
If I make a call to MyModel.load(), I get the error:
MyModel.load is not a function
However, you do have load in Model:
http://docs.sencha.com/touch/2.4/2.4.1-apidocs/#!/api/Ext.data.Model-static-method-load
On the contrary, MyModel.save() exists and I can access it.
Is this a bug or am I missing something?
The load method listed on Ext.data.Model is a static method on the class definition, not an instance. The documentation even denotes this is a static method. When you want to load a record, you don't load an already instantiated record, you load the model definition and that loading creates an instance.
The save method listed on Ext.data.Model is an instance method, the docs do not denote this as a static method. You don't save a class definition, you save an instance.
Example usage: https://fiddle.sencha.com/#fiddle/lvj
Related
A similar question has been answered here:
How can I pass a runtime parameter as part of the dependency resolution?
However, I was wondering how this can be done when registering a generic class?
Normally, I would register it as following:
services.AddScoped(typeof(ITest<>), typeof(Test<>));
But what if I want to pass a runtime parameter to constructor? Without using DI, it would be something like:
new Test<MyClass>(string mystring, int myInt)
In the linked answer it's suggests using a factory method but this is giving me an error if I don't pass it the exact type.
The alternative would be to get an instance without passing a runtime parameter in the constructor and instead using a setter method after getting exact instance. I would like to avoid this however because every time after getting instance you must remember to call setter method.
Is there some way around it? I guess I could use some factory class instead of registering it in startup class...
EDIT:
After reading Steven's answer which was very useful, I updated question with more concrete example:
Following example is inside some method:
//instance of repository are passed inside constructor of class
//calling some to update/insert
//IMPORTANT - calling external service I want save parameters to db no matter what
using(var ctx=new DbContext())
{
//create log object
ctx.logs.add(Obj)
ctx.save()
}
//some code after
Let's say I want to be consistent and call method of my loggingrepository and there add logging object and save everything to database
However, every repository in constructor accepts DbContext, which is registered as scoped (durig one request).
If it's inside transaction, saving depends about code after calling external service and it can throw exception and save nothing.
So yeah, I could create new dbContext and pass it in logging method or call some private logging function and save inside it,
but point is that if I would ask for instance of loggingRepository I would want DI to pass this localy created dbContext variable to constructor
and not one registered as scoped inside startup method, so that addind and saving log happens no matter what external service or code after calling it does.
My situation in something similar, but it's going for some data in db based on current user and I don't wanna pass same parameter to numerous method, but only inside class constructor.
The general solution in injecting primitive configuration values into your application components, is to extract them into a Parameter Object. This gives those values a new, unambiguous type, which can be registered into your container:
// Parameter Object
public TestConfiguration
{
public string Mystring;
public int MyInt;
}
// (Generic) class using the Parameter Object
public class Test<T>
{
public Test(TestConfiguration config) { ... }
}
// Registering both
services.AddScoped(typeof(ITest<>), typeof(Test<>));
services.AddSingleton(new TestConfiguration { Mystring = ..., Myint = ... });
Configuration values are not considered to be runtime data as their values are known at startup and constant for the duration of the application. That's why you can supply them to the constructors of your application components.
Real runtime data, however, should not be passed on to a component during construction. Runtime data are values that are not known at startup and typically passed along by the user through a web request, are retrieved from the database, session, or anything that can change during the lifetime of the application.
Instead of passing runtime data in through the constructor, you should either:
Pass runtime data through method calls of the API or
Retrieve runtime data from specific abstractions that allow resolving runtime data.
You can find more information about passing runtime data here.
SO I am trying to redefine a class. I have a class named folder. In OSGi (using Felix) I have a new Folder class with the same methods but some additional logging.
I am trying to take the Folder Class from Felix and redefine the main Folder class on the main classloader
I do have the agent set on startup.
new ByteBuddy()
.redefine(Class.forName(classToOverride.trim()), ClassFileLocator.ForClassLoader.of(felixClassLoader))
.name(classToOverride.trim())
.make() .load(contextClassLoader);
I have tried different strategies in the load method.
Without any strategies I get the following error
Caused by: java.lang.IllegalStateException: Cannot inject already loaded type: class com.dotmarketing.portlets.folders.model.Folder
at net.bytebuddy.dynamic.loading.ClassInjector$UsingReflection.inject(ClassInjector.java:187) ~[byte-buddy-1.6.12.jar:?]
at net.bytebuddy.dynamic.loading.ClassLoadingStrategy$Default$InjectionDispatcher.load(ClassLoadingStrategy.java:187) ~[byte-buddy-1.6.12.jar:?]
at net.bytebuddy.dynamic.loading.ClassLoadingStrategy$Default.load(ClassLoadingStrategy.java:120) ~[byte-buddy-1.6.12.jar:?]
at net.bytebuddy.dynamic.TypeResolutionStrategy$Passive.initialize(TypeResolutionStrategy.java:79) ~[byte-buddy-1.6.12.jar:?]
at net.bytebuddy.dynamic.DynamicType$Default$Unloaded.load(DynamicType.java:4376) ~[byte-buddy-1.6.12.jar:?]
at com.dotmarketing.osgi.GenericBundleActivator.publishBundleServices(GenericBundleActivator.java:177) ~[dotcms_4.1.0_563a5c3.jar:?]
With ClassReloadingStrategy.fromInstalledAgent I get no error but doesn't work.
On a JVM, you cannot simply redefine an already loaded class. You can only redefine a class using a Java agent where Byte Buddy supplies the AgentBuilder API which you can use. Note that it is only possible to change the content of methods but not a class's layout. You probably want to have a look at the Advice API to do so.
In my Restler index.php let's say I've done this:
$r->addAPIClass('Person');
$r->addAPIClass('Team');
And now I'm inside one of the methods defined in Person, and I have a need to call one of the methods defined in Team. What's the right way to get a handle to the Team API so that I can call one of its methods?
There is nothing special, doing it with Restler.
If it is a static method directly call Team::method(parameter)
Otherwise create an instance either
at constructor if you need it in many methods and store it in a private variable
at the method level
If you are using a database model, it may already provide you with an instance of team as a relationship
I am trying to run some code on objects that are loaded from RavenDB, and I need to do it just after the object has been loaded with its property values.
I've tried intercepting the deserialization process using a CustomCreationConverter and overriding ReadJson, but the object I can access at that point has all the properties set, except the one I need : the Id. Is there somewhere else I can slot into the pipeline in order to do this?
The reason you don't see the Id is because it's not part of the document, it's in the metadata as #id.
If you want to intercept client side, you can register a custom Conversion Listener. Create a class that implements IDocumentConversionListener and register it with documentStore.RegisterListener(). In the DocumentToEntity method, you can run your custom logic. The documentation is lacking on Listeners in general, but there is another topic that also uses them:
http://ravendb.net/kb/16/using-optimistic-concurrency-in-real-world-scenarios
The other option would be to add a bundle that intercepts on the server side. For that, you would use a Read Trigger.
The Problem
I have a class which calculates the path a user took using CoreLocation and and array of arrays containing the coordinates of each point (taken when the users location changes). This class method is being called by my View Controller, but I want to set it's delegate to another class which will store the result in Core Data or upload it to a database. I can return the array to the View Controller by using:
PathFinder.delegate = self
Then make my View Controller implement my delegate protocol, but this isn't what I want.
What I've Considered
I've thought about making the class which uploads the data to the database/stores it in Core Data a singleton class so that I can easily access it from my View Controller. E.g.
PathFinder.delegate = <MY SINGLETON CLASS>
Conclusion
What would be the best way to do this? Would it be bad practice to put the code to upload the array to my server in the PathFinder class? Any help would be appreciated.
I have something like this - a singleton class that manages a Core Data repository for images (some in the repository, some on the file system but a URL in the entity).
Why not have a singleton class that all objects that need the services import? That way, you tell some object to do something, when that works is done they tell the repository to save it. You can use a delegate protocol to know if it succeeded or not, but just decouple the saving of it from driving the process and knowing the outcome.