春季的@Autowired服务奇怪地为null,尽管在各个地方都使用了required字段。

huangapple go评论77阅读模式
英文:

Spring @Autowired service is strangely null inspite of using required fields all over

问题

I am using a pojo for handling form request and I am trying to access service using Autowired. But it keeps returning null inspite of whatever I try changing. I will publish all my code, please take a look into it.

CategoryAddForm:

In this page, I am trying to use categoryService but it seems be empty(null) and when I try using any function inside the service, I get nullpointerexception. I have not tried to initialize the autowired class anywhere.

@Getter
@Setter
@AllArgsConstructor
@NoArgsConstructor
@Component
public class CategoryAddForm {
    private Long id;
    private String title;
    private String description;
    private String language;
    private String image_url;

    @Autowired
    CategoryService categoryService;

    public Category save() {
        Category category;
        if(this.id==null) {
            if(this.language==null || this.language.trim().equals("en")) {
                category = Category.builder()
                        .title_en(this.title)
                        .description_en(this.description)
                        .image_url(this.image_url)
                        .en_available(true)
                        .count(0l).build();
                System.out.println("New for English: \n id: "+this.id+" \n title:"+this.title+"\n description: "+this.description+"\n language: "+this.language);
                System.out.println(categoryService);
//                categoryService.save(category);
            }
            else {
                category = Category.builder()
                        .title_np(this.title)
                        .description_np(this.description)
                        .np_available(true)
                        .en_available(false)
                        .count(0l).build();
                System.out.println("New for Nepali: \n id: "+this.id+" \n title:"+this.title+"\n description: "+this.description+"\n language: "+this.language);
                System.out.println(categoryService);
//                categoryService.save(category);
            }
        }
        else {
            if(this.language==null || this.language.trim().equals("en")) {
                category = Category.builder()
                        .id(this.id)
                        .title_en(this.title)
                        .description_en(this.description)
                        .en_available(true)
                        .image_url(this.image_url).build();
            }
            else {
                category = Category.builder()
                        .id(this.id)
                        .title_np(this.title)
                        .description_np(this.description)
                        .np_available(true)
                        .image_url(this.image_url).build();
            }
        }
        System.out.println(category);
    return categoryService.save(category);

    }
}

Form page:

This page sends categoryForm object to /save in controller which invokes the save function that is inside CategoryAddForm

            <form th:action="@{'/admin/category/save'}" method="post" th:object="${categoryForm}">
                <div class="form-group my-1 p-2 row">
                    <label for="categoryTitle">Title</label>
                    <input type="title" class="form-control" name="title" id="categoryTitle" th:field="*{title}">
                </div>
                <div class="form-group my-1 p-2 row">
                    <label for="categoryDescription">Description</label>
                    <textarea rows="5" type="description" class="form-control" name="description" id="categoryDescription" th:field="*{description}">
                    </textarea>
                </div>
                <div class="form-check my-1 p-2 row">
                    <label for="languages">Select Language</label>
                    <div id="languages" class="row ml-2">

                        <div class="col-2" >
                            <input class="form-check-input" type="radio" value="en" th:field="*{language}" id="englishLanguage" th:selected="selected">
                            <label class="form-check-label" for="englishLanguage">
                                English
                            </label>
                        </div>
                        <div class="col-2" >
                            <input class="form-check-input" type="radio" value="ne" th:field="*{language}" id="nepaliLanguage">
                            <label class="form-check-label" for="nepaliLanguage">
                                Nepali
                            </label>
                        </div>
                    </div>
                </div>
                <button type="submit" class="btn btn-primary m-2">Submit</button>
            </form>

Category Service Implementation:
This is just for the reference and proof that I have not done anything wrong.

@Service
public class CategoryServiceImpl implements CategoryService {
    @Autowired
    private CategoryRepository repository;
    @Override
    public Category save(Category document) {
        return repository.save(document);
    }

    @Override
    public Category getById(Long id) {
        return repository.getOne(id);
    }

    @Override
    public void delete(Category document) {
        repository.delete(document);
    }

    @Override
    public void deleteById(Long id) {
        repository.deleteById(id);
    }

    @Override
    public List<Category> getAllCategories() {
        return repository.findAll();
    }
}

save route in CategoryAdminController:

This function is taking categoryAddForm from the form and calls save() function in categoryAddForm.

@PostMapping(value = "/save")
public ModelAndView submitCategory(@ModelAttribute("categoryForm") CategoryAddForm categoryForm, BindingResult result){
    categoryForm.save();
    if(result.hasErrors()){
        return new ModelAndView("redirect:/admin/category/add?error");
    }
    return new ModelAndView("redirect:/admin/category/add");
}
英文:

I am using a pojo for handling form request and I am trying to access service using Autowired. But it keeps returning null inspite of whatever I try changing. I will publish all my code, please take a look into it.

CategoryAddForm:

In this page, I am trying to use categoryService but it seems be empty(null) and when I try using any function inside the service, I get nullpointerexception. I have not tried to initialize the autowired class anywhere.

@Getter
@Setter
@AllArgsConstructor
@NoArgsConstructor
@Component
public class CategoryAddForm {
private Long id;
private String title;
private String description;
private String language;
private String image_url;
@Autowired
CategoryService categoryService;
public Category save() {
Category category;
if(this.id==null) {
if(this.language==null || this.language.trim().equals(&quot;en&quot;)) {
category = Category.builder()
.title_en(this.title)
.description_en(this.description)
.image_url(this.image_url)
.en_available(true)
.count(0l).build();
System.out.println(&quot;New for English: \n id: &quot;+this.id+&quot; \n title:&quot;+this.title+&quot;\n description: &quot;+this.description+&quot;\n language: &quot;+this.language);
System.out.println(categoryService);
//                categoryService.save(category);
}
else {
category = Category.builder()
.title_np(this.title)
.description_np(this.description)
.np_available(true)
.en_available(false)
.count(0l).build();
System.out.println(&quot;New for Nepali: \n id: &quot;+this.id+&quot; \n title:&quot;+this.title+&quot;\n description: &quot;+this.description+&quot;\n language: &quot;+this.language);
System.out.println(categoryService);
//                categoryService.save(category);
}
}
else {
if(this.language==null || this.language.trim().equals(&quot;en&quot;)) {
category = Category.builder()
.id(this.id)
.title_en(this.title)
.description_en(this.description)
.en_available(true)
.image_url(this.image_url).build();
}
else {
category = Category.builder()
.id(this.id)
.title_np(this.title)
.description_np(this.description)
.np_available(true)
.image_url(this.image_url).build();
}
}
System.out.println(category);
return categoryService.save(category);
}
}

Form page:

This page sends categoryForm object to /save in controller which invokes the save function that is inside CategoryAddForm

            &lt;form th:action=&quot;@{&#39;/admin/category/save&#39;}&quot; method=&quot;post&quot; th:object=&quot;${categoryForm}&quot;&gt;
&lt;div class=&quot;form-group my-1 p-2 row&quot;&gt;
&lt;label for=&quot;categoryTitle&quot;&gt;Title&lt;/label&gt;
&lt;input type=&quot;title&quot; class=&quot;form-control&quot; name=&quot;title&quot; id=&quot;categoryTitle&quot; th:field=&quot;*{title}&quot;&gt;
&lt;/div&gt;
&lt;div class=&quot;form-group my-1 p-2 row&quot;&gt;
&lt;label for=&quot;categoryDescription&quot;&gt;Description&lt;/label&gt;
&lt;textarea rows=&quot;5&quot; type=&quot;description&quot; class=&quot;form-control&quot; name=&quot;description&quot; id=&quot;categoryDescription&quot; th:field=&quot;*{description}&quot;&gt;
&lt;/textarea&gt;
&lt;/div&gt;
&lt;div class=&quot;form-check my-1 p-2 row&quot;&gt;
&lt;label for=&quot;languages&quot;&gt;Select Language&lt;/label&gt;
&lt;div id=&quot;languages&quot; class=&quot;row ml-2&quot;&gt;
&lt;div class=&quot;col-2&quot; &gt;
&lt;input class=&quot;form-check-input&quot; type=&quot;radio&quot; value=&quot;en&quot; th:field=&quot;*{language}&quot; id=&quot;englishLanguage&quot; th:selected=&quot;selected&quot;&gt;
&lt;label class=&quot;form-check-label&quot; for=&quot;englishLanguage&quot;&gt;
English
&lt;/label&gt;
&lt;/div&gt;
&lt;div class=&quot;col-2&quot; &gt;
&lt;input class=&quot;form-check-input&quot; type=&quot;radio&quot; value=&quot;ne&quot; th:field=&quot;*{language}&quot; id=&quot;nepaliLanguage&quot;&gt;
&lt;label class=&quot;form-check-label&quot; for=&quot;nepaliLanguage&quot;&gt;
Nepali
&lt;/label&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;button type=&quot;submit&quot; class=&quot;btn btn-primary m-2&quot;&gt;Submit&lt;/button&gt;
&lt;/form&gt;

Category Service Implementation:
This is just for the reference and proof that I have not done anything wrong.

@Service
public class CategoryServiceImpl implements CategoryService {
@Autowired
private CategoryRepository repository;
@Override
public Category save(Category document) {
return repository.save(document);
}
@Override
public Category getById(Long id) {
return repository.getOne(id);
}
@Override
public void delete(Category document) {
repository.delete(document);
}
@Override
public void deleteById(Long id) {
repository.deleteById(id);
}
@Override
public List&lt;Category&gt; getAllCategories() {
return repository.findAll();
}
}

save route in CategoryAdminController:

This function is taking categoryAddForm from the form and calls save() function in categoryAddForm.

@PostMapping(value = &quot;/save&quot;)
public ModelAndView submitCategory(@ModelAttribute(&quot;categoryForm&quot;) CategoryAddForm categoryForm, BindingResult result){
categoryForm.save();
if(result.hasErrors()){
return new ModelAndView(&quot;redirect:/admin/category/add?error&quot;);
}
return new ModelAndView(&quot;redirect:/admin/category/add&quot;);
}

答案1

得分: 1

问题是每次进行请求时都在创建一个新的CategoryAddForm,而且你没有让Spring来管理你的Bean。如果你每次都创建一个新的CategoryAddForm实例,Spring就不会知道它需要将你的服务注入进去。我认为你可以尝试通过构造函数来进行注入。

英文:

The problem is that you are creating a new CategoryAddForm every time you make a reuqest and you are not letting spring manage your beans. If you are creating a new instance of CategorAddForm, spring won't know that he needs to inject your service into it. I think you can try to inject by constructor.

huangapple
  • 本文由 发表于 2020年8月28日 19:14:22
  • 转载请务必保留本文链接:https://go.coder-hub.com/63632702.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定