CAS 界面根据不同的域名显示不同的界面
概要
在实际需求中,客户想通过不同的域名显示不同的登录界面,比如输入 manage.aps.cn 显示运维管理登录,business.aps.cn 显示业务管理登录。
实现方法
1.准备两套登录UI
在cas目录 WEB-INF/view/jsp目录下整两份UI。
增加两个属性文件,这些属性文件和UI有关系。
查看一下 business.properties
cas 默认显示界面是在cas.properties 文件中配置,配置完成后,不能再变更了,因此需要能够实现切换UI。
2.代码实现
我的思路是通过根据域名动态改变 这个basename。在过滤器中获取域名,并动态改变basename。
实现方式在过滤器中,判断当前的访问域名,判定需要访问哪个UI并进行切换。
修改源码:
org.springframework.web.servlet.view.ResourceBundleViewResolver,
这个代码原本是不能实现UI切换的。
package org.springframework.web.servlet.view; import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.MissingResourceException;
import java.util.ResourceBundle;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.DisposableBean;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.beans.factory.support.PropertiesBeanDefinitionReader;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.core.Ordered;
import org.springframework.web.context.support.GenericWebApplicationContext;
import org.springframework.web.servlet.View; public class ResourceBundleViewResolver extends AbstractCachingViewResolver
implements Ordered, InitializingBean, DisposableBean
{
public static final String DEFAULT_BASENAME = "views";
private int order = 2147483647; private ThreadLocal<String> baseNameLocal= new ThreadLocal<>(); private ClassLoader bundleClassLoader = Thread.currentThread().getContextClassLoader();
private String defaultParentView;
private Locale[] localesToInitialize;
private final Map<Locale, BeanFactory> localeCache = new HashMap(); private final Map<List<ResourceBundle>, ConfigurableApplicationContext> bundleCache = new HashMap(); public void setOrder(int order)
{
this.order = order; } public int getOrder() {
return this.order;
} public void setBasename(String basename)
{
this.baseNameLocal.set(basename);
} public void setBundleClassLoader(ClassLoader classLoader)
{
this.bundleClassLoader = classLoader;
} protected ClassLoader getBundleClassLoader()
{
return this.bundleClassLoader;
} public void setDefaultParentView(String defaultParentView)
{
this.defaultParentView = defaultParentView;
} public void setLocalesToInitialize(Locale[] localesToInitialize)
{
this.localesToInitialize = localesToInitialize;
} public void afterPropertiesSet()
throws BeansException
{
if (this.localesToInitialize != null)
for (Locale locale : this.localesToInitialize)
initFactory(locale);
} protected View loadView(String viewName, Locale locale)
throws Exception
{
BeanFactory factory = initFactory(locale);
try {
return (View)factory.getBean(viewName, View.class);
}
catch (NoSuchBeanDefinitionException ex) {
}
return null;
} protected synchronized BeanFactory initFactory(Locale locale)
throws BeansException
{ List<ResourceBundle> bundles = new LinkedList(); String baseName="manage"; if(this.baseNameLocal.get()!=null){
baseName=this.baseNameLocal.get();
} ResourceBundle bundle = getBundle(baseName, locale);
bundles.add(bundle); GenericWebApplicationContext factory = new GenericWebApplicationContext();
factory.setParent(getApplicationContext());
factory.setServletContext(getServletContext()); PropertiesBeanDefinitionReader reader = new PropertiesBeanDefinitionReader(factory);
reader.setDefaultParentBean(this.defaultParentView);
reader.registerBeanDefinitions(bundle); factory.refresh(); return factory;
} protected ResourceBundle getBundle(String basename, Locale locale)
throws MissingResourceException
{
return ResourceBundle.getBundle(basename, locale, getBundleClassLoader());
} public void destroy()
throws BeansException
{
for (ConfigurableApplicationContext factory : this.bundleCache.values()) {
factory.close();
}
this.localeCache.clear();
this.bundleCache.clear();
}
}
增加一个过滤器,根据域名修改 页面视图目录。
package com.redxun.cas; import java.io.IOException; import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest; import org.springframework.web.servlet.view.ResourceBundleViewResolver; public class ViewSelectFilter implements Filter{ @Override
public void destroy() { } @Override
public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)
throws IOException, ServletException {
HttpServletRequest request=(HttpServletRequest)req;
ResourceBundleViewResolver resolver=(ResourceBundleViewResolver) SpringContextHolder.getBean("viewResolver");
String serverName=request.getServerName();
String pre=serverName.substring(0,serverName.indexOf("."));
resolver.setBasename(pre); chain.doFilter(req, res);
} @Override
public void init(FilterConfig arg0) throws ServletException { } }
修改 cas-servlet.xml配置。
<bean id="viewResolver" class="org.springframework.web.servlet.view.ResourceBundleViewResolver"
p:order="0">
<property name="basename" value="${cas.viewResolver.basename}" />
<property name="cache" value="false"></property>
</bean>
配置过滤器
<filter>
<filter-name>ViewSelectFilter</filter-name>
<filter-class>com.redxun.cas.ViewSelectFilter</filter-class>
</filter> <filter-mapping>
<filter-name>ViewSelectFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
测试效果
在host添加域名映射
192.168.1.77 manage.aps.cn
192.168.1.77 business.aps.cn
测试效果如下:
访问:manage.aps.cn
business.aps.cn
另外一个知识点,我们在过滤器中需要获取,spring mvc的上下文。
我们需要实现一个获取上下文的类。实现接口:ApplicationContextAware
package com.redxun.cas; import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware; public class SpringContextHolder implements ApplicationContextAware {
private static ApplicationContext _ctx; @Override
public void setApplicationContext(ApplicationContext ctx) throws BeansException {
_ctx=ctx;
}
public static Object getBean(String beanId){
return _ctx.getBean(beanId);
}
public static Object getBean(Class cls){
return _ctx.getBean(cls);
}
}
这里配置也是有要求的需要配置 cas-servlet.xml配置文件中。
配置如下:
<bean id="springContextHolder" class="com.redxun.cas.SpringContextHolder"></bean>
CAS 界面根据不同的域名显示不同的界面的更多相关文章
- OpenStack配置串口显示虚机界面
OpenStack配置串口显示虚机界面 OpenStack的horizon能够显示虚拟机的界面.horizon是web界面,在我们的电脑上,姑且称之为本地,虚拟机运行在远端服务器上,称之为远端.本地显 ...
- 直接拨号、将电话号码传入拨号程序、调用拨号程序、调用系统浏览器浏览网页、调用系统程序查看联系人、显示系统设置界面和显示Wi-Fi设置界面代码
直接拨号.将电话号码传入拨号程序.调用拨号程序.调用系统浏览器浏览网页.调用系统程序查看联系人.显示系统设置界面和显示Wi-Fi设置界面代码 拨打号码的代码如下: Intent callIntent= ...
- wxPython制作跑monkey工具(python3)-带显示设备列表界面
一. wxPython制作跑monkey工具(python3)-带显示设备列表界面 源代码 Run Monkey.py #!/usr/bin/env python import wx import ...
- iOS从当前隐藏导航界面push到下一个显示导航界面出现闪一下的问题
本文转载至 http://blog.csdn.net/woaifen3344/article/details/41284319 navios 如果有朋友遇到从当前隐藏导航界面push到下一个显示导航界 ...
- Android图形显示系统——上层显示1:界面绘制大纲
Android显示之应用界面绘制 越到上层,跟业务关联越直接.代码就越繁杂.Android上层显示的代码正是如此.此外,java语言本身繁复的特点(比C语言多了满屏的try-catch,比C++少了析 ...
- swift项目实战--微博的未登录界面的实现,和监听未登录界面两个按钮的两种实现方法
1.未登录界面的实现 微博项目中,用户不登录的话,显示的是未登录的界面.项目中TabBarVC的子控制器都是tableViewVC,所以抽取了父类,让父类判断用户是否登录,决定显示什么样的界面.loa ...
- WinForm开发-界面控件到实体,实体到界面控件自动绑定
在WinForm开发中,我们是不是为绑定界面控件的数据而每个控件每个控件的赋值?在保存修改时是不是也是每个控件每个控件的赋值到实体中?字段一多,那简直就是噩梦.有没有像Web中那样方便的方法直接就自动 ...
- .NetCore 下开发独立的(RPL)含有界面的组件包 (三)构建界面
.NetCore 下开发独立的(RPL)含有界面的组件包 (一)准备工作 .NetCore 下开发独立的(RPL)含有界面的组件包 (二)扩展中间件及服 务 .NetCore 下开发独立的(RPL)含 ...
- 【iOS开发】IOS界面开发使用viewWithTag:(int)findTag方法获取界面元素
http://blog.csdn.net/lxp1021/article/details/43952551 今天在开发OS界面的时候,遇到通过界面UIview viewWithTag:(int)fin ...
随机推荐
- 创建文件指针数组c++
#include<fstream>using namespace std; void main(){ for (int i=0; i<=1; i++) { char szName[1 ...
- Python: print stdout同行输出
项目中发现,PyCharm运行youtube_dl下载,其进度在同行显示,即替换上行输出. 稍做研究,记录下来: #coding=utf-8 from __future__ import print_ ...
- c#: 判断Firefox是否安装
1.源起: KV项目需要给浏览器安装下载插件,就需要判断是否安装对应浏览器,发现判断卸载目录方法,32位程序在.net 2.0运行环境下,常规方法不能访问64位注册表位置,导致不能判断. 2.卸载键值 ...
- Mysql的随机抽取
方法一 SELECT * FROM SHARE ORDER BY RAND( ) LIMIT 1; 在MYSQL的官方手册,里面针对RAND()的提示大概意思就是,在ORDER BY从句里面不能使用R ...
- Bootstrap(4) 表单和图片
1.表单 基本格式,实现基本的表单样式 <form class="form-horizontal"> <div class="form-group&qu ...
- ELK logstash 启动慢的解决方法
最近开始测试部署ELK, 在部署logstash的时候出现一个故障: logstash在第一次安装完成以后启动正常, 但是之后启动时间越来越长, 5分钟以上甚至10多分钟.以至于怀疑程序错误, 在重装 ...
- listView 解决焦点冲突问题 item项和子控件之间的冲突
listView 在item布局的顶级布局中设置 android:descendantFocusability="blocksDescendants"可以阻止子控件获取焦点 这样使 ...
- 解决Eclipse添加新server时无法选择Tomcat7的问题
在Eclipse中创建了一个Web工程后,需要将该工程部署到Tomcat中进行发布.有时就会遇到在New Server对话框中选择了Tomcat 6/7后却无法单击“Next”按钮的问题,如下图所示: ...
- 向kafka批量发送已存在的txt文件
需要利用kafka发送txt或log文件,有两种方式:1.自己写程序:2.利用kafka自带脚本. 自己写程序: import org.apache.kafka.clients.producer.Ka ...
- Hibbernate详解一
这里先做一个简单的入门,后面有详解 记住图解原理: 这里只是没有整合spring等项目使用的hibernate的使用详解. 一.Hibernate简介 1.Hibernate在开发中所处的位置 2.O ...