In Intellij 15.0.3. and using Java8 I have a problem in using ::new.
In particular, I have a class with a default constructor
public class Container{
public Container(){}
}
I want to create a map from a list, as follows:
public class Test{
private final Map<Key, Container> map;
#Before
public void setUp(){
List<Key> keys=...//Init the list
map = keys.stream().collect(Collectors.toMap(Function.identity(), Container::new));
}
}
In Intellij, new is red and the tooltip says cannot resolve constructor Container
If I do () -> {new Container()} I also have cannot infer functional interface type Container
Any idea why?
Each mapping function is supposed to accept a Key argument. Function.identity() does, but Container::new takes no parameters. Same thing with () -> new Container(). You need a one-argument lambda. An argument that you'll ignore, as it happens.
map = keys.stream().collect(Collectors.toMap(Function.identity(), key -> new Container()));
it should be something like :
Collectors.toMap(Container::getMyUniqueField, Function.identity())
This will use getter for keys, and the object itself as the value, in the created hashmap.
Related
Suppose I have below Person class with one getAccountNumber() method having #ShouldNotBeLogged custom annotation.
public class Person {
private String name;
private String accountNumber;
#ShouldNotBeLogged
public String getAccountNumber() {
return accountNumber;
}
}
Considering the above Person class I want to find the all occurrences where getAccountNumber() method is logged using the Logger class - error|warn|debug|info methods like in the below HelloWorld class logMessage method. Please note that there are many methods having ShouldNotBeLogged annotation in the actual code, so we cannot create search with name of the method in it.
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
public class HelloWorld {
private static final Logger logger = LogManager.getLogger(HelloWorld.class);
public void logMessage(Person person) {
logger.debug("logging Acc No. - {}", person.getAccountNumber()); // Occurence Type 1
LogManager.getLogger(HelloWorld.class).info("Account Number - {}", person.getAccountNumber()); // Occurence Type 2
}
}
I have tried using the Method call existing template and given the Text filter for $MethodCall$ with - error|warn|debug|info and it finds the Logger method with the error,warn,debug or, info names. Not able to create the filter for $Instance$ & $Parameter$ where Instance will be of Logger type (can be instantiated as a constant of a class or, directly with the Logger class method) and Parameter will be the call to #ShouldNotBeLogged annotated method.
$Instance$.$MethodCall$($Parameter$)
I'm using the IntelliJ IDEA 2022.2 (Ultimate Edition)
This is a difficult case. Hopefully this will help you.
First, create a search that will find #ShouldNotBeLogged annotated methods:
#ShouldNotBeLogged
$ReturnType$ $Method$($ParameterType$ $Parameter$);
With a count modifier [0,∞] on $Parameter$ (this template is based on the existing template "Deprecated methods"). Save this template under a name, for example "Methods that should not be logged".
$logger$.$call$($arg1$, $method$())
Modifiers:
$logger$: type=Logger
$method$: reference=Methods that should not be logged
This will find all logger calls with a call to a #ShouldNotBeLogged annotated method as the second argument.
Unfortunately, if you want to find logger calls with calls to a #ShouldNotBeLogged annotated method on a different position, you will have to construct a separate query template. For example:
$logger$.$call$($arg1$, $arg2$, $method$())
Just when I thought I understood it, I got the following issue.
I have a base class in another module (called base here)
It looks like that:
open class BaseTest {
companion object {
lateinit var baseTest: BaseTest
}
protected open var someProperty: String? = "base"
}
I want to set that property and made it protected so my extended class in another module could access it.
class Extended: BaseTest() {
fun extendedCall() {
BaseTest().someProperty = "extended"
baseTest.someProperty = "extended"
}
}
However, neither the static one, not the direct property is accessable stating the following error:
Cannot access 'someProperty': it is protected in 'BaseTest'
But shouldn't that be accessable since Extended inherents from BaseTest()? I mean the definition of protected is "Declarations are only visible in its class and in its subclassess" so what have I missed? It even doesn't work in the same module so that's not the cause.
What am I missing?
BaseTest().someProperty = "extended"
Here you make a new BaseTest object by calling the constructor BaseTest() and you are not allowed to access protected properties of other BaseTest objects.
baseTest.someProperty = "extended"
the static BaseTest object is also another object and not the Extended object itself.
Being protected merely makes it possible to do
someProperty = "extended"
or the equivalent
this.someProperty = "extended"
That is, access the property of this object.
I believe the protected modifier doesn't work like that in Kotlin.
The documentation says:
The protected modifier is not available for top-level declarations.
But I agree it's quite confusing as written. It appears the documentation focuses more on the Outter/Inner class relationship via the this keyword.
for some reason I don't wanna let user to create an instance of the object, without sending a property to the constructor
but as I know the object should have default constructor and so it would be possible to create an instance with out sending requierd property.
is there any way to prevent this problem? and if yes does it have any side effect?
Just use a protected default constructor:
public class Product
{
protected Product() { }
public Product(Category category)
{
this.Category = category;
}
}
"NHibernate allows a private default constructor for Value Objects, but for Entities you will need a default public or protected constructor as private is not sufficient."
Here you can find something:
https://github.com/davybrion/companysite-dotnet/blob/master/content/blog/2009-10-why-nhibernate-entities-need-a-public-or-protected-parameterless-constructor.md
Here there's an experiment to work without constructor:
http://kozmic.net/2011/03/20/working-with-nhibernate-without-default-constructors/
This is an example working with Dependency Injection:
http://nhibernate.info/blog/2008/12/12/entities-behavior-injection.html
I'm trying to find a method of passing a constructor argument to the constructors of child classes.
These objects are immutable so I'd prefer to use constructor arguments.
The issue I have encountered is that ConstructorArgument does not inherit to child instantiations and the following statements are not interchangeable:
_parsingProcessor = _kernel.Get<IParsingProcessor>(new ConstructorArgument("dataFilePath", dataFilePath);
and
_parsingProcessor = _kernel.Get<IParsingProcessor>(new Parameter("dataFilePath", dataFilePath, true);
So, how can get an inheritable ConstructorArgument and when does it makes sense, if ever, to new the Parameter class?
Yes, you can do this, but it's probably not what you really want. If the container is not actually responsible for instantiating its own dependencies, then its dependencies probably shouldn't be sharing its constructor arguments - it just doesn't make sense.
I'm pretty sure I know what you're trying to do, and the recommended approach is to create a unique binding specifically for your one container, and use the WhenInjectedInto conditional binding syntax, as in the example below:
public class Hello : IHello
{
private readonly string name;
public Hello(string name)
{
this.name = name;
}
public void SayHello()
{
Console.WriteLine("Hello, {0}!", name);
}
}
This is the class that takes a constructor argument which we want to modify, depending on who is asking for an IHello. Let's say it's this boring container class:
public class MyApp : IApp
{
private readonly IHello hello;
public MyApp(IHello hello)
{
this.hello = hello;
}
public virtual void Run()
{
hello.SayHello();
Console.ReadLine();
}
}
Now, here's how you do up the bindings:
public class MainModule : NinjectModule
{
public override void Load()
{
Bind<IApp>().To<MyApp>();
Bind<IHello>().To<Hello>()
.WithConstructorArgument("name", "Jim");
Bind<IHello>().To<Hello>()
.WhenInjectedInto<MyApp>()
.WithConstructorArgument("name", "Bob");
}
}
Basically all this binding is doing is saying the name should be "Jim" unless it's being requested by Hello, which in this case it is, so instead it will get the name "Bob".
If you are absolutely certain that you truly want cascading behaviour and understand that this is very dangerous and brittle, you can cheat using a method binding. Assuming that we've now added a name argument to the MyApp class for some unspecified purpose, the binding would be:
Bind<IHello>().ToMethod(ctx =>
ctx.Kernel.Get<Hello>(ctx.Request.ParentContext.Parameters
.OfType<ConstructorArgument>()
.Where(c => c.Name == "name")
.First()));
Please, please, make sure you are positive that this is what you want before doing it. It looks easy but it is also very likely to break during a simple refactoring, and 95% of the "customized dependency" scenarios I've seen can be addressed using the WhenInjectedInto binding instead.
I have looked at the Dozer's FAQs and docs, including the SourceForge forum, but I didn't see any good tutorial or even a simple example on how to implement a custom BeanFactory.
Everyone says, "Just implement a BeanFactory". How exactly do you implement it?
I've Googled and all I see are just jars and sources of jars.
Here is one of my BeanFactories, I hope it helps to explain the common pattern:
public class LineBeanFactory implements BeanFactory {
#Override
public Object createBean(final Object source, final Class<?> sourceClass, final String targetBeanId) {
final LineDto dto = (LineDto) source;
return new Line(dto.getCode(), dto.getElectrified(), dto.getName());
}
}
And the corresponding XML mapping:
<mapping>
<class-a bean-factory="com.floyd.nav.web.ws.mapping.dozer.LineBeanFactory">com.floyd.nav.core.model.Line</class-a>
<class-b>com.floyd.nav.web.contract.dto.LineDto</class-b>
</mapping>
This way I declare that when a new instance of Line is needed then it should create it with my BeanFactory. Here is a unit test, that can explain it:
#Test
public void Line_is_created_with_three_arg_constructor_from_LineDto() {
final LineDto dto = createTransientLineDto();
final Line line = (Line) this.lineBeanFactory.createBean(dto, LineDto.class, null);
assertEquals(dto.getCode(), line.getCode());
assertEquals(dto.getElectrified(), line.isElectrified());
assertEquals(dto.getName(), line.getName());
}
So Object source is the source bean that is mapped, Class sourceClass is the class of the source bean (I'm ignoring it, 'cause it will always be a LineDto instance). String targetBeanId is the ID of the destination bean (too ignored).
A custom bean factory is a class that has a method that creates a bean. There are two "flavours"
a) static create method
SomeBean x = SomeBeanFactory.createSomeBean();
b) instance create method
SomeBeanFactory sbf = new SomeBeanFactory();
SomeBean x = sbf.createSomeBean();
You would create a bean factory if creating and setting up your bean requires some tricky logic, like for example initial value of certain properties depend on external configuration file. A bean factory class allows you to centralize "knowledge" about how to create such a tricky bean. Other classes just call create method without worying how to correctly create such bean.
Here is an actual implementation. Obviously it does not make a lot of sense, since Dozer would do the same without the BeanFactory, but instead of just returning an object, you could initialized it somehow differently.
public class ComponentBeanFactory implements BeanFactory {
#Override
public Object createBean(Object source, Class<?> sourceClass,
String targetBeanId) {
return new ComponentDto();
}
}
Why do you need a BeanFactory anyways? Maybe that would help understanding your question.