JAVA中读取配置文件以及修改配置文件

1.ServletContext方式

    采用ServletContext读取配置文件realpath,然后通过文件流读出来。

    优点:可以读取任意位置的文件

               采用文件流读取,所以可以读取不同格式的文件

    缺点:不能在servlet外面读取配置文件

    实现:

package com.xunjie.common.utils;

import java.io.FileInputStream;
import java.io.InputStreamReader;
import java.util.Properties;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class Profile {
	// 采用ServletContext读取配置文件的realpath,然后通过文件流读取出来
	public void readProfileByServletContext(HttpServletRequest request, HttpServletResponse response) {
		// 通过servletcontext读取到文件路径
		String realPath = request.getServletContext().getRealPath("jdbc.properties");
		//InputStream 是字节输入流的所有类的超类,一般我们使用它的子类,如FileInputStream
		InputStreamReader reader;
		//Properties类,主要用于读取Java的配置文件
		Properties props = new Properties();
		try {
			// 建议使用Reader来读,因为reader体系中有个InputStreamReader可以指定编码
			reader = new InputStreamReader(new FileInputStream(realPath), "utf-8");
			// load ( InputStream inStream)方法
			// 从输入流中读取属性列表(键和元素对)。 通过对指定的文件(比如说上面的jdbc.properties文件)进行装载来获取该文件中的所有键 - 值对。 以供 getProperty ( String key) 来搜索。
			props.load(reader);
		} catch (Exception e) {
			e.printStackTrace();
		}
		// getProperty ( String key)方法,用指定的键在此属性列表中搜索属性。也就是通过参数 key ,得到 key 所对应的 value。
		String jdbcUrl = props.getProperty("url");
		System.out.println(jdbcUrl);
		System.out.println(realPath);
	}
}

    使用Junit测试输出结果

    Junit使用参考:https://blog.csdn.net/qq_37725650/article/details/79409589

package com.xunjie.test;

import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.mock.web.MockHttpServletRequest;
import org.springframework.mock.web.MockHttpServletResponse;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import com.xunjie.common.utils.Profile;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = { "classpath:spring.xml" })
public class ProfileTest {

	private MockHttpServletRequest request;
	private MockHttpServletResponse response;

	@Before
	public void setUp() {
		request = new MockHttpServletRequest();
		request.setCharacterEncoding("UTF-8");
		response = new MockHttpServletResponse();
	}

	@Test
	public void test() {
		System.err.println("-----测试开始-start-----");
		Profile profile = new Profile();
		profile.readProfileByServletContext(request, response);
		System.err.println("-----测试结束-end-----");
	}
}

测试结果:

-----测试开始-start-----
jdbc:mysql://127.0.0.1:3306/yeebi?useUnicode=true&&characterEncoding=UTF-8
E:\WorkSpace\xunjie\xunjie\target\classes\jdbc.properties
-----测试结束-end-----

2.通过ResourceBundle类获取配置文件资源

    优点:1可以以全限定类名的方式加载资源2可以在非web应用里加载资源

    缺点:只能加载类下面的资源文件,且只能读取properties文件

	/**
	 * @Title: getProfileByResourceBundle
	 * @Description: 通过ResourceBundle类获取配置文件资源
	 * @param propertyName 配置文件名称
	 * 调用方式:  
     * 1.配置文件放在resource源包下,不用加后缀  
     *  PropertiesUtil.getProfileByResourceBundle("message");  
     * 2.放在包里面的  
     *  PropertiesUtil.getProfileByResourceBundle("com.test.message");
	 * @return Map<String,String> 以Map键值对方式返回配置文件内容
	 */
	public static Map<String, String> getProfileByResourceBundle(String propertyName) {
		// 获得资源包
		ResourceBundle rb = ResourceBundle.getBundle(propertyName.trim());
		// 通过资源包拿到所有的key
		Enumeration<String> allKey = rb.getKeys();
		Map<String, String> profileMap = new HashMap<String, String>();
		// 遍历key 得到 value
		while (allKey.hasMoreElements()) {
			String key = allKey.nextElement();
			String value = (String) rb.getString(key);
			//将文件内容存入map
			profileMap.put(key, value);
		}
		return profileMap;
	}

    测试运行结果:

	public static void main(String[] args) {
		//我的文件直接放在了src下,所以直接传入文件名称就可以了
		Map<String, String> profileMap = Profile.getProfileByResourceBundle("jdbc");
		String jdbcUrl = profileMap.get("url");
		System.out.println(jdbcUrl);
	}
控制台输出:
jdbc:mysql://127.0.0.1:3306/yeebi?useUnicode=true&&characterEncoding=UTF-8
3.通过ClassLoader方式进行读取
/**
	 * @Title: getProfileByClassLoader
	 * @Description: 采用ClassLoader(类加载器)方式进行读取配置信息
	 * @return Map<String,Object> 以Map键值对方式返回配置文件内容
	 * 优点:可以在非Web应用中读取配置资源信息,可以读取任意的资源文件信息  
	 * 缺点:只能加载类classes下面的资源文件
	 * @throws
	 */
	public static Map<String, Object> getProfileByClassLoader() {
		// 通过ClassLoader获取到文件输入流对象
		// 配置文件放在resource源包下,直接写文件名即可,需要后缀名"jdbc.properties"
		// 放在包里面的,需要写上包路径,例如:在test包下"com/test/jdbc.properties"),Profile为当前所在类类名
		InputStream in = Profile.class.getClassLoader().getResourceAsStream("jdbc.properties");
		// 获取文件的位置
		String filePath = Profile.class.getClassLoader().getResource("jdbc.properties").getFile();
		System.out.println(filePath);
		BufferedReader reader = new BufferedReader(new InputStreamReader(in));
		Properties props = new Properties();
		Map<String, Object> profileMap = new HashMap<String, Object>();
		try {
			props.load(reader);
			for (Object key : props.keySet()) {
				profileMap.put(key.toString(), props.getProperty(key.toString()));
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
		return profileMap;
	}

测试运行结果:

public static void main(String[] args) {
		Map<String, Object> profileMap = Profile.getProfileByClassLoader();
		System.out.println(profileMap.get("url"));
	}
控制台输出:
/E:/WorkSpace/xunjie/xunjie/target/classes/jdbc.properties
jdbc:mysql://127.0.0.1:3306/yeebi?useUnicode=true&&characterEncoding=UTF-8

4.使用Sping提供的PropertiesLoaderUtils类读取配置文件

    当然需要导入spring核心包

/**
	 * @Title: getProfileByPropertiesLoaderUtils
	 * @Description: Spring 提供的 PropertiesLoaderUtils 允许您直接通过基于类路径的文件地址加载属性资源
	 * 最大的好处就是:实时加载配置文件,修改后立即生效,不必重启 
	 * @return Map<String,Object>
	 */
	public static Map<String, Object> getProfileByPropertiesLoaderUtils() {
		Properties props = new Properties();
		Map<String, Object> profileMap = new HashMap<String, Object>();
		try {
			props = PropertiesLoaderUtils.loadAllProperties("jdbc.properties");
			for (Object key : props.keySet()) {
				profileMap.put(key.toString(), props.getProperty(key.toString()));
			}
		} catch (IOException e) {
			System.out.println(e.getMessage());
		}
		return profileMap;
	}  

   测试运行结果:

	public static void main(String[] args) {
		Map<String, Object> profileMap = Profile.getProfileByPropertiesLoaderUtils();
		System.out.println(profileMap.get("url"));
	}
控制台输出:
jdbc:mysql://127.0.0.1:3306/yeebi?useUnicode=true&&characterEncoding=UTF-8

5.修改配置文件

只是修改了classes下的文件,源文件并没有改变。

	/**  
	 * 传递键值对的Map,更新properties文件  
	 *   
	 * @param fileName  
	 *            文件名(放在resource源包目录下),需要后缀  
	 * @param keyValueMap  
	 *            键值对Map  
	 */
	public static void updateProperties(String fileName, Map<String, String> keyValueMap) {
		// 输入流
		// InputStream
		// inputStream=PropertiesUtil.class.getClassLoader().getResourceAsStream(fileName);
		// 获取文件的路径
		String filePath = Profile.class.getClassLoader().getResource(fileName).getFile();
		System.out.println("propertiesPath:" + filePath);
		Properties props = new Properties();
		BufferedReader br = null;
		BufferedWriter bw = null;
		try {
			// 从输入流中读取属性列表(键和元素对)
			br = new BufferedReader(new InputStreamReader(new FileInputStream(filePath)));
			props.load(br);
			br.close();
			// 写入属性文件
			bw = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(filePath)));
			// 清空旧的文件
			// props.clear();
			for (String key : keyValueMap.keySet())
				props.setProperty(key, keyValueMap.get(key));
			props.store(bw, "改变数据");
			System.out.println(props.getProperty("url"));
			bw.close();
		} catch (IOException e) {
			e.printStackTrace();
			System.err.println("Visit " + filePath + " for updating " + "" + " value error");
		} finally {
			try {
				br.close();
				bw.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

修改前:


运行测试结果即修改后:

	public static void main(String[] args) {
		Profile.updateProperties("jdbc.properties", new HashMap<String, String>() {
			{
				put("initialSize", "6");
				put("test", "修改文件属性");
			}
		});
	}


猜你喜欢

转载自blog.csdn.net/qq_37725650/article/details/79744847