0

I'm receiving a null pointer exception when operating on my service because my service is not being Autowired into the class. I've implemented this class's repository and service exactly the same as others in this application and I haven't had this problem before. The class does in fact warn about issues with the Autowire but I'm not sure how to fix them:

Autowired members must be defined in valid spring bean

Again, this is set up the same as other classes and I do not have this issue. Within the service class, it complains that the repository cannot be autowired into the constructor because there are multiple beans of the same type. My other service class shows this warning as well but does not have problems being Autowired into classes and operated upon. Definitions below, please ask for any other context that would be helpful.

//TransactionCategoryRepository.java
@Repository("transactionCategoryRepository")
public interface TransactionCategoryRepository extends 
CrudRepository<TransactionCategory, Integer> {
}

--

//TransactionCategoryService.java
@Service("transactionCategoryService")
public class TransactionCategoryService {

private TransactionCategoryRepository transactionCategoryRepository;

@Autowired
public TransactionCategoryService(TransactionCategoryRepository repository) {
    this.transactionCategoryRepository = repository;
}

public void saveTransactionCategory(TransactionCategory transactionCategory) {
    transactionCategoryRepository.save(transactionCategory);
}
}

--

//Utilities.java
public class PlaidUtilities {

private Logger logger = 
LoggerFactory.getLogger(PlaidUtilities.class.getSimpleName());

private PlaidClient mPlaidClient;

@Autowired
TransactionCategoryService mTransactionCategoryService;
...

The multiple bean warning is thrown on respository in TransactionCategoryService.java and the Autowired definition warning is thrown in Utilities.java. The breaking null pointer exception error occurs later in Utilities.java when operating on mTransactionCategoryService.

justinraczak
  • 776
  • 2
  • 9
  • 24
  • If you have multiple beans which fit the type of an auto-wired component, you need to use `@Qualifier` to specify which one you want. But that wouldn't give you that exception, you need to check if your bean is indeed getting created, if you search for beans in a certain package make sure your repo is in the correct package. – Derrops Jan 14 '18 at 22:51
  • @Snickers3192 I apologize but I'm new to Spring and Spring Boot and am not entirely sure what you're suggesting. What does `search for beans in a certain package` mean? The definition only occurs in one place and it's strange because IntelliJ seems to be aware of that; when it lists the two locations of the bean, it lists the same location (`TransactionCategoryRepository.java`). – justinraczak Jan 15 '18 at 03:38
  • It is probably worth reiterating that I have other repositories and services set up the same exact way and do not have this problem. – justinraczak Jan 15 '18 at 04:01
  • If that is the case you will need to put more info, maybe redo some stuff first and see if that works. – Derrops Jan 15 '18 at 23:55

1 Answers1

0

Unless you need them, take the names out of the @Service and @Repository annotations. I've found it just makes things awkward.

The other thing that might be wrong is that you're not scanning those packages. You can change that in your main class by altering the boot application attribute to @SpringBootApplication(scanBasePackages={"your.package.here"})

Have a look here at this question where they detail it

  • Thank you for your answer. I tried what you've suggested and added the base package to @SpringBootApplication in the main application class but I get the same results. Any ideas what else I might try? – justinraczak Jan 15 '18 at 03:36
  • I've realized that everything I try to autowire into this particular file throws the same warning about it needing to be defined in a spring bean. This file is in a different package than where I've done this autowiring before. Do you know what I might be doing wrong with that being the case? – justinraczak Jan 15 '18 at 17:27
  • Are you trying to inject `PlaidUtilities`? I notice that you don't have it annotated with `Service` or `Component`, so if you're trying to inject it somewhere it won't work. What you can do if you don't want to mark it with the attribute is define a class marked with `@Configuration` and then initialise from a method annotated with `@Bean` [like this](https://stackoverflow.com/questions/28060700/spring-boot-initializing-bean-at-startup-with-constructor-parameters) – HeadBangingSloth Jan 16 '18 at 04:38
  • Ah no, I hadn't annotated it as a service yet, though I did try annotating it as a controller. I'm still ramping up on the proper use of these annotations. I'd temporarily fixed it by moving it to a different related controllers which is good in that it works but bad in that I still didn't understand why it wasn't working. I will try adding a service annotation in the original class file. Thank you for this suggestion. – justinraczak Jan 17 '18 at 17:27
  • I'll try and dig up some links that explain it well. The best way I can explain it is that Spring has a registry of providers (those marked with `@Service`,`@Component`, etc.) and consumers (`@Autowired`). Basically, anywhere you'd pass in a service via a setter or constructor you instead mark the method/field with `@Autowired` and then mark the dependency with `@Component` – HeadBangingSloth Jan 18 '18 at 22:51