GWT多模块项目编译报错:找不到Spring Security相关类源码
问题原因
GWT编译器需要把所有客户端可访问的代码编译成JavaScript,而org.springframework.security.core.GrantedAuthority和org.springframework.security.core.userdetails.User是纯服务器端类,没有对应的GWT客户端实现或源码支持。当你的DTO类被GWT的<source>路径包含,且直接继承/依赖这些Spring类时,GWT找不到它们的源码,就会抛出"No source code is available"错误。
解决方案
以下是几种可行的解决思路,按推荐优先级排序:
1. 拆分DTO,隔离客户端与服务器端依赖
这是最规范的做法,核心是让客户端用的DTO不依赖任何服务器端框架类:
- 创建纯客户端友好的
UserSessionDTO,只保留客户端需要的字段(比如用List<String>存储权限名称,而非Spring的GrantedAuthority):
// 放在GWTRPCModular-shared或GWTRPCModular-model的客户端可访问路径下 public class UserSessionDTO implements Serializable { private static final long serialVersionUID = 1L; private String username; private List<String> authorities; // GWT序列化要求必须有空构造函数 public UserSessionDTO() {} public UserSessionDTO(String username, List<String> authorities) { this.username = username; this.authorities = authorities; } // getter/setter方法 public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public List<String> getAuthorities() { return authorities; } public void setAuthorities(List<String> authorities) { this.authorities = authorities; } }
- 在服务器端,把Spring的
User对象转换为这个纯DTO:
// 服务器端代码示例 User springUser = ...; // 从Spring Security获取用户实例 List<String> authorityNames = springUser.getAuthorities() .stream() .map(GrantedAuthority::getAuthority) .collect(Collectors.toList()); UserSessionDTO clientDto = new UserSessionDTO(springUser.getUsername(), authorityNames);
2. 调整GWT编译路径,排除依赖Spring的类
如果遗留项目结构不允许拆分DTO,可以把依赖Spring的类移出GWT的客户端编译范围:
- 修改模块的
.gwt.xml文件,用<exclude>标签排除包含Spring依赖的DTO类:
<source path="model"> <exclude name="dto/UserSessionDTO.java"/> </source>
- 或者把模型模块拆成
model-client(无Spring依赖,供GWT客户端编译)和model-server(依赖Spring,仅服务器端使用),由服务器端负责两类DTO的转换。
3. 自定义GWT模拟类(不推荐)
如果必须在共享层保留Spring类依赖,可以手动编写GWT客户端的模拟类,但这种方式维护成本高,易出现序列化问题:
- 创建一个GWT模块文件
com.spring.security.gwt.SpringSecurity.gwt.xml:
<module> <source path="client"/> </module>
- 在
com.spring.security.gwt.client包下编写GrantedAuthority和User的模拟实现(仅保留客户端需要的方法,且实现Serializable):
public class GrantedAuthority implements Serializable { private String authority; public GrantedAuthority() {} public String getAuthority() { return authority; } public void setAuthority(String authority) { this.authority = authority; } } public class User implements Serializable { private String username; private Collection<GrantedAuthority> authorities; public User() {} // 按需实现必要的getter/setter }
- 在你的GWT模块的
.gwt.xml中继承这个自定义模块:
<inherits name="com.spring.security.gwt.SpringSecurity"/>
注意:这种方式要保证模拟类与Spring服务器端类的序列化结构完全一致,否则RPC调用会出错;且Spring版本更新时需要同步修改模拟类,不推荐长期使用。
验证步骤
- 执行
mvn clean install确保依赖加载正常 - 重新执行
mvn package,检查GWT编译是否通过
内容的提问来源于stack exchange,提问作者Oscar Londoño
相关产品推荐
相关产品推荐

