Spring Context init(java) [英] Spring Context init (java)

查看:132
本文介绍了Spring Context init(java)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我是春天的初学者,我遇到了基本的上下文初始化问题,我找不到任何简单的教程。
所以我想做的是基本的依赖注入,我已经看到我只需要将类标记为@Componant或@Service,并使用@Autowired直接将它们注入目标文件中。
为此,我需要正确设置我的spring上下文(我需要构建一个Web服务+使用JPA,所以我想构建一个webapp)

I'm a beginner with spring and I am having problem with basic context init and I can't find any easy tutorial. So what I want to do is basic dependency injection and I have seen I only have to mark classes as @Componant or @Service and inject them directly within target fiels with @Autowired. For this I need to set properly my spring context (I'll need to build a web service + use JPA so I want to build a webapp)

我正在使用JDK 1.8,maven 3.2.1

I'm using JDK 1.8, maven 3.2.1

我想做一个基本的依赖注入。
=>我想在那里注入一个storeImpl实例,但这会导致空指针异常
=>这项工作完全没有注入(私有商店storeImpl = new storeImpl();)

I want to do a basic dependency injection. => I want to inject a storeImpl instance there but this lead to a null pointer exception => this work perfectly without injection ( private Store storeImpl = new storeImpl(); )

package com.mycompany.app.controller;

@Controller
public class Controller
{
    @Autowired
    private Store storeImpl;

    public void use()
    {
        storeImpl.get();
    }
}


package com.mycompany.app.store;

public interface Store {
    boolean get();

}


package com.mycompany.app.store;

@Component
public class StoreImpl implements Store {
    @Override
    public boolean get()
    {
        return true;
    }
}

=>我的主要(我测试我的适用于此的应用程序):

public class App
{
    public static void main(String[] args)
    {
        Controller controller = new Controller();
        controller.use();
    }
}

=>我的pom.xml

=> my pom.xml

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>com.mycompany.app</groupId>
  <artifactId>my-app</artifactId>
  <packaging>jar</packaging>
  <version>1.0-SNAPSHOT</version>
  <name>my-app</name>
  <url>http://maven.apache.org</url>

    <properties>
        <spring.version>4.0.4.RELEASE</spring.version>
    </properties>

  <dependencies>
      <dependency>
          <groupId>junit</groupId>
          <artifactId>junit</artifactId>
          <version>3.8.1</version>
          <scope>test</scope>
      </dependency>

      <dependency>
          <groupId>org.jsoup</groupId>
          <artifactId>jsoup</artifactId>
          <version>1.7.1</version>
      </dependency>

      <dependency>
          <groupId>org.projectlombok</groupId>
          <artifactId>lombok</artifactId>
          <version>1.12.6</version>
          <scope>provided</scope>
      </dependency>




      <dependency>
          <groupId>org.springframework</groupId>
          <artifactId>spring-core</artifactId>
          <version>${spring.version}</version>
      </dependency>

      <dependency>
          <groupId>org.springframework</groupId>
          <artifactId>spring-context</artifactId>
          <version>${spring.version}</version>
      </dependency>

      <dependency>
          <groupId>org.springframework</groupId>
          <artifactId>spring-context-support</artifactId>
          <version>${spring.version}</version>
      </dependency>
      <dependency>
          <groupId>org.springframework</groupId>
          <artifactId>spring-web</artifactId>
          <version>${spring.version}</version>
      </dependency>
      <dependency>
          <groupId>org.springframework</groupId>
          <artifactId>spring-webmvc</artifactId>
          <version>${spring.version}</version>
      </dependency>
      <dependency>
          <groupId>org.springframework</groupId>
          <artifactId>spring-aop</artifactId>
          <version>${spring.version}</version>
      </dependency>


      <dependency>
          <groupId>org.springframework.data</groupId>
          <artifactId>spring-data-jpa</artifactId>
          <version>1.5.2.RELEASE</version>
      </dependency>


      <dependency>
          <groupId>org.hibernate</groupId>
          <artifactId>hibernate-core</artifactId>
          <version>4.3.5.Final</version>
      </dependency>

      <dependency>
          <groupId>javax.servlet</groupId>
          <artifactId>javax.servlet-api</artifactId>
          <version>3.0.1</version>
          <scope>provided</scope>
      </dependency>
  </dependencies>

  <build>
    <plugins>
        <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.1</version>
            <configuration>
                <source>1.8</source>
                <target>1.8</target>
            </configuration>
      </plugin>
    </plugins>
    </build>
</project>

=>我的web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xmlns="http://java.sun.com/xml/ns/javaee"
         xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
         http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
         version="3.0">

    <display-name>Archetype Created Web Application</display-name>

    <servlet>
        <servlet-name>dispatcher</servlet-name>
        <servlet-class>
            org.springframework.web.servlet.DispatcherServlet
        </servlet-class>
        <load-on-startup>1</load-on-startup>
    </servlet>

    <servlet-mapping>
        <servlet-name>dispatcher</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>

    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>/META-INF/spring-context.xml</param-value>

    </context-param>

    <listener>
        <listener-class>
            org.springframework.web.context.ContextLoaderListener
        </listener-class>
    </listener>
</web-app>

=>我的spring-context.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/mvc
        http://www.springframework.org/schema/mvc/spring-mvc.xsd">

    <!--<context:component-scan base-package="com.mycompany.app"/>-->
    <context:component-scan base-package="com.mycompany.app">
       <!-- <context:exclude-filter type="annotation" expression="org.springframework.stereotype.Controller" />-->
    </context:component-scan>

</beans>

=>我的项目架构

my-app
  src
    main
      java
        com.mycompagny.app
          controller
            Controller.java
          store
            Store.java
            StoreImpl.java

          app.java

       ressources
         META-INF
           spring-context.xml

       webapp
         WEB-INF
           web.xml


  test
   java

pom.xml






=> main()的堆栈跟踪


=> stacktrace of main()

Exception in thread "main" java.lang.NullPointerException
    at com.mycompany.app.controller.Controller.run(Controller.java:25)
    at com.mycompany.app.App.main(App.java:19)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:483)
    at com.intellij.rt.execution.application.AppMain.main(AppMain.java:134)

所以我的问题是我的注入字段(storeImpl)为null。
我想我错过了一些关于context init的东西?
再次感谢您的帮助和您的回答

So my problem is my injected field (storeImpl) is null. And I think I miss something with context init ? Thanks again for your help and yourr grats answer

推荐答案

您有几个问题(以下内容显而易见:你的帖子)。

You have a couple of problems (the following are apparent from your post).


  1. 混合不同版本的Spring的罐子

  2. 注释的错误位置

  3. applicationcontext中的重复。

  4. 使用版本化的XSD文件。

  5. web.xml中的版本冲突

  1. Mixing jars of different versions of Spring
  2. Wrong location of annotations
  3. Duplication in your applicationcontext.
  4. Using versioned XSD files.
  5. Conflicting versioning in web.xml

1。混合不同版本的Spring的罐子

  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-core</artifactId>
      <version>4.0.3.RELEASE</version>
  </dependency>

  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>4.0.4.RELEASE</version>
  </dependency>

  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context-support</artifactId>
      <version>4.0.3.RELEASE</version>
  </dependency>
  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-web</artifactId>
      <version>4.0.1.RELEASE</version>
  </dependency>
  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-webmvc</artifactId>
      <version>4.0.1.RELEASE</version>
  </dependency>
  <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>servlet-api</artifactId>
      <version>2.5</version>
  </dependency>

  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-aop</artifactId>
      <version>3.0.5.RELEASE</version>
  </dependency>

您的pom上堆满了来自不同弹簧版本的罐子(3.0.5,4.0.1,4.0。 3和4.0.3)。如果你想要麻烦,那么这就是你要走的路。始终坚持单一版本的框架,不要混合来自不同版本的罐子。这不仅适用于Spring,而是适用于每个(多jar)框架。

Your pom is littered with jars from different spring versions (3.0.5, 4.0.1, 4.0.3 and 4.0.3). If you want trouble then that is the way to go. Always stick to a single version of a framework and don't mix jars from different versions. This isn't only for Spring but goes for every (multi jar) framework out-there.

使用maven的强大功能来帮助你,指定一个属性来保存你想要使用的Spring版本并使用该属性。

Use the power of maven to help you, specify a property to hold the version of Spring you want to use and use that property.

<properties>
    <spring.version>4.0.4.RELEASE</spring.version>
</properties>
<dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-core</artifactId>
      <version>${spring.version}</version>
  </dependency>

  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>${spring.version}</version>
  </dependency>

  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context-support</artifactId>
      <version>${spring.version}</version>
  </dependency>
  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-web</artifactId>
      <version>${spring.version}</version>
  </dependency>
  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-webmvc</artifactId>
      <version>${spring.version}</version>
  </dependency>
  <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-aop</artifactId>
      <version>${spring.version}</version>
  </dependency>

您可能需要添加更多内容,具体取决于Spring Data JPA引入的依赖项,如果是有不同的版本。

You might need to add a couple more depending on which dependencies Spring Data JPA is pulling in, if that has different versions.

2。注释的位置错误

@Service
public interface Store {
    boolean get();
}

注释不是从接口继承的,所以在界面上添加注释很漂亮没用。对于特定的注释,例如 @Transactional ,Spring有一些hacks,但不适用于此。将注释移动到具体实现,不要将其放在界面上。

Annotations aren't inherited from interfaces so putting the annotation on the interface is pretty much useless. Spring has some hacks in place for specific annotations like @Transactional but not for this. Move the annotation to the concrete implementation and don't put it on the interface.

@Service
public class Controller {
    @Autowired
    private Store storeImpl;

    public void use() {
       storeImpl.get();
    }
}

我在这里看不到任何东西 @Controller 或者什么也没有 @RequestMapping 所以我不确定你认为Spring如何检测和处理这个类。

I don't see anything here no @Controller or what so ever also no @RequestMapping so I'm not sure how you think that Spring detects and handles this class.

3。在applicationcontext中重复。

< context:annotation-config /> 将其从使用< context:component-scan /> 已经隐含了您的上下文。

<context:annotation-config /> remove it from your context as that is already implied by the use of <context:component-scan />.

< mvc:annotation-driven /> 应仅在<$加载的xml文件中c $ c> DispatcherServlet 在你的情况下(如果你已发布实际代码)应该是 dispatcher-servlet.xml

<mvc:annotation-driven /> should be only in the xml file loaded by the DispatcherServlet in your case (if you have posted actual code) that should be the dispatcher-servlet.xml.

您的xml文件中都有相同的< context:component-scan .. /> 元素,这将导致bean重复。由 ContextLoaderListener 加载的文件应该加载除 @Controllers DispatcherServlet 应仅加载 @Controllers 并忽略其他任何内容。要在组件扫描时使用包含/排除过滤器。

You have the same <context:component-scan .. /> element in both your xml files, this will ead to bean duplication. The files loaded by the ContextLoaderListener should load anything but @Controllers and the DispatcherServlet should load only @Controllers and ignore anything else. To accomplish that use include/exclude filters when component scanning.

将此用于 ContextLoaderListener

<context:component-scan base-package="com.mycompany.app">
    <context:exclude-filter type="annotation" expression="org.springframework.stereotype. Controller" />
<context:component-scan>

将此用于 DispatcherServlet

<context:component-scan base-package="com.mycompany.app" use-default-filters="false >
    <context:include-filter type="annotation" expression="org.springframework.stereotype. Controller" />
<context:component-scan>

也不要将 DispatcherServlet 的配置导入 ContextLoaderListener ,因为这将再次导致bean重复。

Also don't import the configuration of the DispatcherServlet into the ContextLoaderListener as this will again lead to bean duplication.

4.使用版本化的XSD文件。

xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context-3.0.xsd
        http://www.springframework.org/schema/mvc
        http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd">

您的架构位置使用版本化的XSD文件,建议使用无版本的xsd文件。这将确保将加载属于您当前版本的xsd版本。

Your schema locations use versioned XSD files, it is recommended to use versionless xsd files. This will ensure that the xsd version belonging to your current spring version will be loaded.

xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/mvc
        http://www.springframework.org/schema/mvc/spring-mvc.xsd">

5。 web.xml中的版本控制冲突

<!DOCTYPE web-app PUBLIC
    "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
    "http://java.sun.com/dtd/web-app_2_3.dtd" >

<web-app id="WebApp_ID" version="2.4"
     xmlns="http://java.sun.com/xml/ns/j2ee"
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
     xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee
    http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">

你想要什么版本2.3的2.4?你在你的pom中包括servlet-api 2.5,我希望你想要3.0版本。相应地更改标题(和maven依赖关系)。

What is it you want version 2.3 of 2.4? You including servlet-api 2.5 in your pom and I would expect that you want version 3.0. Change your header (and maven dependency) accordingly.

web.xml 标题更改为以下内容。

Change your web.xml header to the following.

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee"
     xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
     version="3.0">

更新你的pom.xml以包含servlet 3.0规范。

Update your pom.xml to include the servlet 3.0 spec.

<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>3.0.1</version>
    <scope>provided</scope>
</dependency>

这篇关于Spring Context init(java)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆