I am trying to develop Prism 6 UWP Application .
My current problem is I want to register all objects used in Application with Unity Dependency injection container .
But so many UI objects are created by infrastructure(Activator.CreateInstance(type)) and no way to trigger their creation through dependency injection conatiner.I would be fine even if I register created objects with DI conatiner.
I refered Github sample application AdventureWorks.Shopper in Prism samples.
Here I saw views are created by infrastructure ,but some other objects are created by Dependency injection conatiner .
Is there any way to get all objects in applications and register them with DI conatiner ?
Is there any way to get all objects in applications and register them with DI container or trigger all creation through DI conatiner?
Generally you shouldn't try to have your UI objects created by the container, because as you mention, the XAML parsing process (infrastructure as you call it) is responsible for doing that and there is no easy way to get in the loop to take over that construction process.
This is one of the reasons we added the ViewModelLocator to Prism - so that from the ViewModel down through all of its dependencies, you can wire up the SetDefaultViewModelFactory method to use the container to do the construction of all your ViewModels and their dependencies (and their dependency's dependencies, etc.) as long as you use ViewModelLocator to wire the View to the ViewModel.
If you are following the MVVM pattern well, then there should almost never be a need to construct the UI objects themselves through the container because they should not be doing any logic in the code behind that would depend on things injected by the container. But that is not to say you will never need to do that. So for those situations where you need to do that You can either get to the container through the Application.Current as suggested by S Vasudev with some casting. Or if you need to do that a few places and don't want all that casting "noise" in the code, then write a simple helper object with a static property that you can set in the OnInitializeAsync method of the App class and then easily access anywhere.
If you are doing that in more than a few places you should start to question your design. And yes statics (globals) are evil and should be avoided whenever possible. But if it is just a few places in the code behind of a few views, sometimes you need to be a pragmatic programmer who gets things done and not an MVVM purist who overcomplicates things just to avoid a few minor violations of the MVVM guidance.
One way we found :-
You can access unity container like this :-
unityContainer = (UnityContainer)((Prism.Unity.Windows.PrismUnityApplication)Application.Current).Container;
In constructor of objects which are created by Activator.CreateInstance,we can use unity container and register that instance to unity container.
In that way , all objects gets registered with unity conatiner
example:-
unityContainer.RegisterInstance(this);
Related
I've found myself in an interesting position. I currently use the latest Unity container, I'm on asp.net core 2.2, and I use application insights. As such, I have configured DI in my web app to use unity instead of the out of the box DI provider in core. I also use Application Insights and use the IWebHostBuilder.UseApplicationInsights extension to spin up AI for my app.
With all this in mind, I have a piece of code whose constructor takes in IHttpContextAccessor so I can access the HttpContext. It was working great. Then, I had another small app that I was trying to reuse the functionality, and the HttpContext was null coming from IHttpContextAccessor. With a bunch of guess, test, revise, I found that IWebHostBuilder.UseApplicationInsights seems to initialize that Request property (HttpContext) on IHttpContextAccessor. If I commented out that AI extension, I would get null; uncomment it, it worked.
I've started to look through the AI code to figure out what exactly they're doing, but honestly, with all the dependencies and pipelines and all that, it's a pretty daunting task. I was hoping someone could point out where/how AI is doing this so my code doesn't NEED AI in order to work. All help would be incredibly awesome.
Use AddHttpContextAccessor extension to add it to DI. HttpContextAccessor is not added by default due to performance impact.
services.AddHttpContextAccessor();
After some struggle, and hoping this post would enlighten me on the AI ask, I found that I didn't need to replicate the AI mechanism, if there's even one at all.
Originally, I was accessing the IHttpContextAccessor via code in the view (Razor). I have an abstract factory pattern I was using to instantiate IHttpContextAccessor via Unity (this pattern came over from my .Net Frame work days). Once I moved that code back to the controller and used proper .net core DI to get the dependency via the constructor, everything started working.
There must be something there I'm missing, but I have the code working so I'm happy. If someone could shed light on why one way works vs the other, I'd be happy to hear it.
When you enable application insights by calling .UseApplicationInsights(), it adds HttpContextAccessor. There are many components in ApplicationInsights which require HttpContextAccessor injected to it. eg: ClientIpHeaderTelemetryInitializer.
This is the exact line where this is occuring:
https://github.com/Microsoft/ApplicationInsights-aspnetcore/blob/develop/src/Microsoft.ApplicationInsights.AspNetCore/Extensions/ApplicationInsightsExtensions.cs#L137
I have made three different applications in j JHipster with monolithic. I need to merge these applications. I know that by using micro-services my quest can be easy but the current requirement is to do the merging with the monolithic pattern only.
I need to merge two applications with another or main application. I am using MySQL as database. I don't know where I need to change and how. Please help me out, I am a newbie in this scenario.
i tried to create a java file for setter getter methods and and a dao file for three databases and now in the main class file and am trying to take every dao file as an array of object and integrate it and put it into the third db.is it possible.i wanted to show the code bt,since i am new not able to maintain the coding standards to show.
by this i way i tried to involve three databases in a single scenario and want to complete my query through CRUD model.
as you already pointed out, the proper way of merging here would be using the microservice option, which you cannot take, as you are forced to use monolithic architecture...
almost automatic merge
if you did not changed anything to your code, after generating the entities, you just can put the contents of your applications .jhipster directory into one, and run yo jhipster --with-entities to regenerate the entities in one application. You should keep in mind, you will have to take a look at your main/resource/config/liquibase folder, to set the migration ids properly.
manual merge
For this you should be more experienced in the underlying technologies, as you will have to:
recreate your entity classes
recreate zour DAO/Repositories
(maybe) recreate your services, or service implementations
recreate your REST controllers
do a proper liquibase migration
provide some tests
migrate the frontend code, by adding states, components, templates etc..
the most of these things you just can copy paste already generated code.
For more information, you should ask more precise, what is not working, if you already tried something...
Is it possible using EF6 Code First and MVC5 to put all the models, views, and controllers that involve ASP.Identity into its own class library project. So that over multiple web applications you could use that same DLL and already have all the views / controllers / models and be using the same security database for multiple applications?
We have several web applications with separate databases and one security database that handles all of them, and we weren't sure how to keep this model now that we're moving to EF6 Code First and MVC5.
If it is possible could someone point me to a tutorial of something similar or give me a basic outline of steps to go through?
Or if there is a better way to achieve my goal, of having one set of code to handle ASP.NET-Identity security that I can plug that dll into multiple web applications and get the same logic and databases?
Or is this not a good idea in general?
Very open to suggestion and advice. I appreciate it.
Yes it is. We do this with every project that we have. The structure is very simple. Just create a class library project to your solution, add EF to the project, then reference the class library from your main project.
If using Code First Migrations be sure to select the class library project as the default project in the Package Manager console when running migrations or adding migrations.
Here is a pseudo solution structure for your solution
MySolution
- MyWebApp
reference: MyDAL
-MyDAL
reference: EF6
The advantage that I find to this is that you can then reference the "DAL" class library from say a companion console application or windows form application, or a companion website, even in a different solution, and they will use the same code base.
For example:
MySolution
- MyWebApp
reference: MyDAL
- MyDAL
reference: EF6
- MyOtherWebApp
reference: MyDAL
NOTE: Your data context will look for its connection string in the Web.config or App.config in the startup project. NOT the class library. This can be confusing at first... But once you think about how .NET compiles the application together into the final package, it makes sense.
If you're talking about creating one class library for an entire data layer shared between multiple projects, then that's easy enough. You can move all your models, your context, etc. into a class library and run migrations using the class library project. The other projects will just reference that class library and not have migrations of their own.
However, if you're talking about multiple databases and associated data layers, where project Foo has its own models, context and migrations and project Bar has its own models, context and migrations, while the class library has just the IdentityUser and IdentityDbContext, things get a little more complicated. You won't be able to combine any of these contexts. So in your Foo project you'd have to instantiate your context for Foo and your Identity context if you need to work with both. It's not a problem, per se, but it's something to be aware of.
I know that there are already some questions related to this topic but I couldn't find a real solution yet.
Currently I am developing applications with EE6, using JPA, CDI, JSF. I would like to take a more modular approach than packaging everything into a WAR or EAR and deploy the whole thing on an Application Server.
I am trying to design my applications as modular as possible by separating a module into 3 maven projects:
API - Contains the interfaces for (stateless) services
Model - Contains the JPA Entities for the specific module
Impl - Contains the implementation of the API, mostly CDI beans
The view logic of every module is currently bundeled within a big web project, which is ugly. I already thought of web fragmets, but if I spread my bean classes and xhtml files in jar files, I would have to implement a hook so that the resources could be looked up by a parent web application. This kind of solution would at least enable me to have a fourth project per module that would contain all the view logic related to the module, which is a good start.
What I want is not only that I can have those 4 kinds of projects, but also that every project is hot swappable. This led me to OSGi, which was at first really cool until I realized that the EE6 technologies are not very well supported within an OSGi Container.
JPA
Let's look at JPA first. There are some tutorials[1] around that explain how to make a JPA enabled OSGi Bundle, but none of these tutorials shows how to spread entities into different bundles(the model project of a module). I would want to have for example three different modules
Core
User
Blog
The model project of the blog module has a (compile-time)dependency on the model project of user.
The model project of the user module has a (compile-time)dependency on the model project of core.
How can I make JPA work in such a scenario without having to create a Persistence Unit for each model project of a module? I want one persistence unit that is aware of all entities available at runtime. The model projects in which the entities are should of course be hot swappable. Maybe I will need to make a separate project for every client that imports all the needed entities of the projects and contains a persistence.xml that includes all necessary configuration things. Are there any available maven plugins for building such a projects or even other approaches to solve that issue?
CDI
CDI is very nice. I really love it and I don't want to miss it any more! I use CDI extensions like MyFaces CODI and DeltaSpike which are awesome!
I inject my (stateless) services into other services or into the view layer which is just great. Since my services are stateless it should not be a problem to use them as OSGi Services, but what about CDI integration in OSGi? I found a glassfish CDI Extension[2] that would the injection of OSGi Services into CDI beans, but I also want may OSGi Services to be CDI beans. I am not totally sure how to achive that, probably I would have to use the BeanManager to instantiate the implementations and then register every implementation for its interface in the ServiceRegistry within a BundleActivator. Is there any standard way for doing that? I would like to avoid any (compile-time)dependencies to the OSGi framework.
I would also like to use my services just like I use them right now, without changing anything(implementations not annotated and injection points not qualified).
There is a JBoss Weld extension/sub project[3] that seems to target that issue but it seems to be inactive, i can't find any best practices or how-tos.
How can I leave my implementation as it is but still be able to use OSGi? I mean it would not be a big deal to add an annotation to the implementations since every implementation is already annotated with a stereotype annotation, anyway I would like to prevent that.
JSF
As mentioned before I would like to be able to spread my view logic module wise. As far as I know this is not really possible out of the box. Pax Web[4] should solve that somehow, but I am not familiar with it.
I would like to have a project "CoreWeb" in the module "core" that contains a Facelet template, let's call it "template.xhtml". A JSF page in a project called "BlogWeb" in the module "blog" should then be able to reference that template and apply a composition.
To be able to extend the view I would introduce a java interface "Extension" that can be implemented by a specific class of a module. A controller for a view would then inject all implementations of the extension. An extension would for example provide a list of subviews that will be included into a main view.
The described extension mechanism can be implemented easily, but the following requirements must be fulfilled:
When adding new OSGi Bundles to the application server, the set of available extensions might change, the extensions must be available for the controller of the view.
The subviews(from a separate bundle) which should be included into a main view should be accessible.
The concept of a single host but multiple slice applications of Spring Slices[5] is very interesting, but seems limited to Spring DM Server and the project also seems to be inactive.
Summary
After all the examples and behaviors I described I hope that you know what I would like to achive. It's simply an EE6 App that is very dynamic and modularized.
What I look for at the end is at least documentation on how to get everything running as I would expect it or even better an already working solution!
[1] http://jaxenter.com/tutorial-using-jpa-in-an-osgi-environment-36661.html
[2] https://blogs.oracle.com/sivakumart/entry/typesafe_injection_of_dynamic_osgi
[3] http://www.slideshare.net/TrevorReznik/weldosgi-injecting-easiness-in-osgi
[4] http://team.ops4j.org/wiki//display/paxweb/Pax+Web
[5] https://jira.springsource.org/browse/SLICE
To answer some of your questions, using a single persistence unit but spreading your entities across multiple bundles is not recommended, but may occasionally work. However, if your entities are so closely related that they need to share a persistence unit, splitting them across modules may not make sense. Also, don't forget you can handle compile-time dependencies by separating the implementation and interface for each entity - interface and implementation need not be in the same bundle.
For dependency injection, you may like Blueprint.
Several implementations are available and most application servers with enterprise OSGi support support Blueprint out of the box. It uses XML to add metadata, so classes themselves won't need any modification.
I'm new to Haskell and Snap and I want to write a simple bug-tracking application. I set up a Snap project using $ snap init and it works. The problem is that I don't know how to go any further.
I want to create a snaplet Tickets that uses a database to store bug reports, and use that snaplet in my main web application.
I read the documentation about snaplets but I couldn't figure out where to put their source code (in the /snaplets directory, I suppose? If so, how do I load them?). Could anybody point me in the right direction?
Are you sure you need to create a separate snaplet for Tickets? The snaplet infrasructure is meant for reusable components such as session management, authentication, database access, admin panels, user management, etc.
Are you going to be using your Tickets self-contained module across multiple web applications? If so, then by all means go ahead and create a snaplet.
In any case, it sounds to me like you are at least in part asking how to organize a project with multiple "modules" or "parts" while using snap. I'll try to address this below. Please let me know if you feel I have missed the mark.
Assuming you don't need to create a separate snaplet for Tickets:
For functionality specific to a single site, I think you would be better off creating a few modules and developing the code for the functionality right inside your current application's package and module hierarchy. Here are a few points on how I have been organizing my snap projects of late:
I put my database-related code under modules in MyApp.DB.
namespace. You could have a MyApp.DB.Tickets that contains all
database calls needed for operation on your Tickets module.
I put all UI-related functionality under MyApp.UI. namespace. You
could put a MyApp.UI.Tickets module that contains your Handlers,
your Splices, your Forms and so on.
To handle forms, I use the excellent digestive-functors library. You may find this blog post helpful if you don't know them already.
I usually have a shared UI helper library under MyApp.UI.Helpers where I place common code used across all/most UI modules.
I usually have a shared Form helper library under MyApp.UI.Forms
Any code tangential to the fact that my application exposes a Web UI goes outside the MyApp.UI. namespace. So if my application needs to perform some offline analyses, I may put them under the MyApp.Analysis. namespace.
Once you define and export your Handlers under MyApp.UI.Tickets, you can go to your Site.hs file and wire them into your application at specific routes.
For inspiration on how to handle database connections, you can check out the postgresql-simple snaplet.
However, if you do need to create a snaplet:
A snaplet is simply a stand-alone application that uses the Snap.Snaplet infrastructure, (typically) has its own .cabal file and (typically) is its own Haskell package. Snap then gives you a way to embed or nest this re-usable, self-contained application in yet another snap application. Think a hierarchy of Russian dolls.
Assuming you performed something similar to what I described in the section above, you are now 95% ready to convert to a snaplet. Just name your application snaplet-tickets, expose a SnapletInit using makeSnaplet and use nestSnaplet in another snap application to include this reusable piece of functionality right there.