javaspringboot怎么获得根目录sudo读写权限

javaspringboot怎么获得根目录sudo读写权限,第1张

您好,要获得JavaSpringBoot的根目录sudo读写权限,首先需要确保您的用户有sudo权限,如果没有,可以使用sudo命令进行授权。接下来,您可以使用chmod命令来更改文件或目录的权限,例如:chmod 777 /path/to/file/or/directory,这样就可以让您的用户拥有读写权限。此外,您还可以使用chown命令来更改文件或目录的所有者,例如:chown username /path/to/file/or/directory,这样就可以让您的用户拥有读写权限。最后,您还可以使用chgrp命令来更改文件或目录的组,例如:chgrp groupname /path/to/file/or/directory,这样就可以让您的用户拥有读写权限。总之,要获得JavaSpringBoot的根目录sudo读写权限,您需要确保您的用户有sudo权限,并且使用chmod、chown和chgrp命令来更改文件或目录的权限、所有者和组。

先上一张类图:

这里借用在web项目中的加载过程来熟悉Spring ApplicationContext的加载过程:

1 在一般的Web项目中,我们很多情况下是利用orgspringframeworkwebcontextContextLoaderListener这个类进行容器的初始化。该类会被Web容器(如Tomcat)自动实例化,并调用contextInitialized方法

/

Initialize the root web application context

/

@Override

public void contextInitialized(ServletContextEvent event) {

initWebApplicationContext(eventgetServletContext());

}

2 initWebApplicationContext方式是从父类ContextLoader中继承来的。该方法的大致的逻辑是:判定web容器中是否注册了ROOT_APPLICATION_CONTEXT_STTRIBUTE(为WebApplicationContextclassgetName()+ “ROOT”)的属性,如果有,则抛出异常,以此保证一个Web容器中只有一个Spring根容器;创建容器的时候,要判定需要实例化哪种类来实例化当前web容器的Spring根容器,如果我们设置了名称为“contextClass”的context-param,则取我们设置的类,该类应当实现ConfigurableWebApplicationContext接口或继承自实现了该接口的子类(如XmlWebApplicationContext、GroovyWebApplicationContext和AnnotationConfigWebApplicationContext),通常我们都不会设置,Spring会默认取与ContextLoader同目录下的ContextLoaderproperties中记录的类名作为根容器的类型(默认是orgspringframeworkwebcontextsupportXmlWebApplicationContext);实例化容器;配置容器;设置容器为Web容器的属性。下面代码中去掉了log和异常等部分。

public WebApplicationContext initWebApplicationContext(ServletContext servletContext) {

if(servletContextgetAttribute(WebApplicationContextROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE) != null) {

throw new IllegalStateException(

"Cannot initialize context because there is already a root application context present - " +

"check whether you have multiple ContextLoader definitions in your webxml!");

}

if (thiscontext == null) {

thiscontext = createWebApplicationContext(servletContext);

}

if (thiscontext instanceof ConfigurableWebApplicationContext) {

ConfigurableWebApplicationContext cwac = (ConfigurableWebApplicationContext) thiscontext;

if (!cwacisActive()) {

if (cwacgetParent() == null) {

ApplicationContext parent = loadParentContext(servletContext);

cwacsetParent(parent);

}

configureAndRefreshWebApplicationContext(cwac, servletContext);

}

}

servletContextsetAttribute(WebApplicationContextROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE,thiscontext);

ClassLoader ccl = ThreadcurrentThread()getContextClassLoader();

if (ccl == ContextLoaderclassgetClassLoader()) {

currentContext = thiscontext;

}

else if (ccl != null) {

currentContextPerThreadput(ccl, thiscontext);

}

return thiscontext;

}

3 configureAndRefreshWebApplicationContext方法负责对容器进行初始化,该方法的逻辑主要有一下几点:设置一个contextId(从contextId这个param获取,如果没有则默认是WebApplicationContext的类名 + “:” + servlet context的路径);设置配置位置(从contextConfigLocation 这个param获取,如果未配置,则默认是/WEB-INF/applicationContextxml,在XmlWebApplicationContext中可以看出);自定义该congtext;调用该Context的refresh()方法。

protected void configureAndRefreshWebApplicationContext(ConfigurableWebApplicationContextwac, ServletContext sc) {

if (ObjectUtilsidentityToString(wac)equals(wacgetId())) {

String idParam = scgetInitParameter(CONTEXT_ID_PARAM);

if (idParam != null) {

wacsetId(idParam);

}

else {

wacsetId(ConfigurableWebApplicationContextAPPLICATION_CONTEXT_ID_PREFIX +

ObjectUtilsgetDisplayString(scgetContextPath()));

}

}

wacsetServletContext(sc);

String configLocationParam = scgetInitParameter(CONFIG_LOCATION_PARAM);

if (configLocationParam != null) {

wacsetConfigLocation(configLocationParam);

}

ConfigurableEnvironment env = wacgetEnvironment();

if (env instanceof ConfigurableWebEnvironment) {

((ConfigurableWebEnvironment) env)initPropertySources(sc, null);

}

customizeContext(sc, wac);

wacrefresh();

}

4 ConfigurableApplicationContext接口的实现类AbstractApplicationContext中的refresh方法,定义了一个模版,在该方法里,会完成加载资源、配置文件解析、Bean定义的注册、组件的初始化等工作。每一步工作都定义在响应的方法中,清晰明了。下面的方法省略了异常处理。

synchronized (thisstartupShutdownMonitor) {

prepareRefresh(); //准备

ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();//获得一个Bean工厂

prepareBeanFactory(beanFactory); //准备好工厂

postProcessBeanFactory(beanFactory);//处理工厂时执行

invokeBeanFactoryPostProcessors(beanFactory);//执行工厂处理

registerBeanPostProcessors(beanFactory);//注册bean产生拦截器

initMessageSource();//初始化消息源

initApplicationEventMulticaster();//初始化应用事件广播器

onRefresh();//初始化该容器子类其他特定的bean

registerListeners();//检查监听器并注册

finishBeanFactoryInitialization(beanFactory);// 初始化非lazy的singleton的bean

finishRefresh();//发布结束fresh消息

}

5 这几个方法中比较重要的方法是obtainFreshBeanFactory方法和finishBeanFactoryInitialization方法,一个用来获得bean工厂,一个用来实例化bean并注入的。这里先分析obtainFreshBeanFactory方法。在继承链中,AbstractApplicationContext实现了该方法,并定义了refreshBeanFactory方法让后代实现。AbstractRefreshableApplicationContext又实现了refreshBeanFactory方法,如果有一个BeanFactory销毁它,然后再创建一个。

protected final void refreshBeanFactory() throws BeansException {

if (hasBeanFactory()) {

destroyBeans();

closeBeanFactory();

}

try {

DefaultListableBeanFactory beanFactory = createBeanFactory();

beanFactorysetSerializationId(getId());

customizeBeanFactory(beanFactory);

loadBeanDefinitions(beanFactory);

synchronized (thisbeanFactoryMonitor) {

thisbeanFactory = beanFactory;

}

}

}

6 loadBeanDefinitions方法会由子类实现,在XmlWebApplicationContext中就实现了该方法。该方法的逻辑为:new一个XmlBeanDefinitionReader;设置该Reader的ResourceLoader(XmlWebApplicationContext设置的是它自己,因为它间接实现了ResourceLoader接口);、使用该Reader加载Bean定义。

protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throwsBeansException, IOException {

XmlBeanDefinitionReader beanDefinitionReader = newXmlBeanDefinitionReader(beanFactory);

beanDefinitionReadersetEnvironment(getEnvironment());

beanDefinitionReadersetResourceLoader(this);

beanDefinitionReadersetEntityResolver(new ResourceEntityResolver(this));

initBeanDefinitionReader(beanDefinitionReader);

loadBeanDefinitions(beanDefinitionReader);

}

7 loadeBeanDefinitions方法会使用reader从每个配置中读取bean定义。该方法大概逻辑为:从每个location解析出一些resouce(代表特定的资源,如一个文件)。在AbstractBeanDefinitionReader中实现的loadBeanDefinitions(String,Set<Resource> actualResources) 方法如下:

public int loadBeanDefinitions(String location, Set<Resource> actualResources) throwsBeanDefinitionStoreException {

ResourceLoader resourceLoader = getResourceLoader();

if (resourceLoader == null) {

throw new BeanDefinitionStoreException(

"Cannot import bean definitions from location [" + location + "]: no ResourceLoader available");

}

if (resourceLoader instanceof ResourcePatternResolver) {

try {

Resource[] resources = ((ResourcePatternResolver)resourceLoader)getResources(location);

int loadCount = loadBeanDefinitions(resources);

if (actualResources != null) {

for (Resource resource : resources) {

actualResourcesadd(resource);

}

}

if (loggerisDebugEnabled()) {

loggerdebug("Loaded " + loadCount + " bean definitions from location pattern [" +location + "]");

}

return loadCount;

}

catch (IOException ex) {

throw new BeanDefinitionStoreException(

"Could not resolve bean definition resource pattern [" + location + "]", ex);

}

}

else {

Resource resource = resourceLoadergetResource(location);

int loadCount = loadBeanDefinitions(resource);

if (actualResources != null) {

actualResourcesadd(resource);

}

if (loggerisDebugEnabled()) {

loggerdebug("Loaded " + loadCount + " bean definitions from location [" + location + "]");

}

return loadCount;

}

}

8 在XmlBeanDefinitionReader中才是真正的加载Bean定义的实现。它从每个Resource中获得输入流,封装成InputSource;调用doLoadBeanDefinitions从该InputSource中获得一个Document,并使用registerBeanDefinitions方法根据该Document注册BeanDefinitions;registerBeanDefinitions方法中先是创建一个DefaultBeanDefinitionDocumentReader实例,再使用该实例来注册BeanDefinition;该实例会从Document的根元素开始注册BeanDefinition。值得注意的是在该类又会委派一个BeanDefinitionParserDelegate来解析Document元素。

protected void parseBeanDefinitions(Element root, BeanDefinitionParserDelegate delegate) {

if (delegateisDefaultNamespace(root)) {

NodeList nl = rootgetChildNodes();

for (int i = 0; i < nlgetLength(); i++) {

Node node = nlitem(i);

if (node instanceof Element) {

Element ele = (Element) node;

if (delegateisDefaultNamespace(ele)) {

parseDefaultElement(ele, delegate);

}

else {

delegateparseCustomElement(ele);

}

}

}

}

else {

delegateparseCustomElement(root);

}

}

9 BeanDefinitionParserDelegate会根据节点的命名空间使用不同的NamespaceHandler进行解析。在XmlBeanDefinitionReader创建DefaultBeanDefinitionDocumentReader时候会传入一个XmlReaderContext,该Context中保存了一个NamespaceHandlerResolver,该HandlerResolver维护一个Map,用来解析对于一个命名空间的具体Handler,其默认使用META-INF/springhandlers 文件保存Handler的种类,Spring支持的Handler如下图:

BeanDefinitionDelegate使用获得的NamespaceHandler解析元素节点,获得BeanDefinition。

10. 不同的NamespaceHandler解析过程不一样。同时,一个NamespaceHandler中有多个Parser来解析不同种类的元素。以ContextNamspaceHandler为例,它支持的Parser如下图所示:

通过Bean工厂获得 BeanFactory bf = new XmlBeanFactory(ClassPassResource(//xxxml));

通过上下文 ApplicationContext ac=new ClassPathXmlApplicationContext("/xxxml");

<bean id="springBean" scope="prototype" class=""<property name="name" value="chen"/</bean<bean id="myAction" scope="prototype" class=""<property name="springBean" ref="springBean"/</bean如果是j2ee应用,启动web应用时将会自动加载ApplicationContext实例(Spring容器负责创建Bean实例)一旦struts2的myAction实例化,其中的SpringBean也会被自动注入进来,从而达到使用SpringBean的目的。[问题]但是仍有需要通过代码来调用SpringBean的情况:1)对于不是由spring创建管理的类,如在java 代码中直接使用new去创建一个对象,并且想在这个对象中使用SpringBean;因为这个对象并不是由Spring容器创建管理的类,所以即使它有setter方法,容器的springBean也不会被注入。2)动态更改springBean中的属性值,如在代码运行时,name值需要发生变动;3)对于一个独立的应用程序[解决]定义一个非Spring容器创建管理的类public class NonSpringClass implements ServletContextAware {private SpringBean springBean;//如果 testGetBean不是被Spring容器创建管理,即使它有setter方法,容器的springBean也不会被注入。public void setSpringBean(SpringBean springBean){thisspringBean=springBean;}//利用ApplicationContext 从spring容器中获得springBean;//Spring有两个核心接口BeanFactory和ApplicationContext,其中ApplicationContext是BeanFactory的子接口,//它们代表了Spring容器,Spring容器是产生Bean的工厂,用于管理容器中的Bean。

在Spring中,我们经常使用xml的配置文件去将Java对象交给Spring容器进行管理。然后在编写类似如下的测试类,那么我们应该如何去将xml配置文件自动导入全局呢?请接着看下面

我们也可以使用注解的方式,避免了每次都要指定配置文件的路径,还得获取Context的方式。

编写Bean

编写配置文件,resource/config/productxml

编写配置类,使用@Configuration注解,并使用@ImportResource注解指定需要扫描的配置文件,这样他就能自动加入SpringContext。

这样,就能将配置文件加载到全局的Context,将ProdcuctBean交给Spring去管理。<br />

编写测试类,使用自动注入的方式将Bean注入ProductBean对象

测试成功!

以上就是关于javaspringboot怎么获得根目录sudo读写权限全部的内容,包括:javaspringboot怎么获得根目录sudo读写权限、spring怎么初始化的、如何从当前spring容器中获得bean等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!

欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/web/9775901.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2023-05-01
下一篇2023-05-01

发表评论

登录后才能评论

评论列表(0条)

    保存