Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cocoa/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用反射替换java.net.URL URLStreamHandlerFactory是个好主意吗?_Java_Tomcat_Reflection_Custom Protocol - Fatal编程技术网

使用反射替换java.net.URL URLStreamHandlerFactory是个好主意吗?

使用反射替换java.net.URL URLStreamHandlerFactory是个好主意吗?,java,tomcat,reflection,custom-protocol,Java,Tomcat,Reflection,Custom Protocol,在Java中,我们至少可以通过两种方式注册自定义协议处理程序: 通过设置系统属性“java.protocol.handler.pkgs” 使用URL.setURLStreamHandlerFactory 有关更多详细信息,请查看 我不能使用第一个选项,因为我必须向服务器(tomcat)类路径添加大量jar文件,以使引导类加载器的处理程序实现可见。此外,还需要一些初始化,这必须在应用程序上下文中完成 第二个选项的问题是工厂只能注册一次(请检查java.net.URL#setURLStreamHan

在Java中,我们至少可以通过两种方式注册自定义协议处理程序:

  • 通过设置系统属性“java.protocol.handler.pkgs”
  • 使用URL.setURLStreamHandlerFactory
  • 有关更多详细信息,请查看

    我不能使用第一个选项,因为我必须向服务器(tomcat)类路径添加大量jar文件,以使引导类加载器的处理程序实现可见。此外,还需要一些初始化,这必须在应用程序上下文中完成

    第二个选项的问题是工厂只能注册一次(请检查java.net.URL#setURLStreamHandlerFactory),不幸的是,它是由Tomcat完成的

    我可以做的是创建一个装饰器工厂,它将通过协议处理程序扩展现有的装饰器工厂。而不是使用relfection将静态字段URL#factory设置为null,并使用URL#setURLStreamHandlerFactory以标准方式注册(再次?)我的“decoratorFactory”。我只是想知道在这里使用反射是否是个好主意。。。?保安怎么样

    我想这样做:

    try {
            Field factoryField = URL.class.getDeclaredField("factory");
            factoryField.setAccessible(true);
            //  get current factory
            Object currentFactory = factoryField.get(null);
            //  define a decorator factory
            MyFactoryDecorator mfd = new MyFactoryDecorator(currentFactory);
            //  set the factory to null and register MyFactoryDecorator using URL#setURLStreamHandlerFactory.
            factoryField.set(null, null);
            URL.setURLStreamHandlerFactory(mfd);
        } catch (NoSuchFieldException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
    

    Idk,但如果您创建了一个新的URLStreamHandlerFactory,但实际上并不包含实现,该怎么办?它只是坐在那里,然后在运行时通过应用程序上下文查找调用时实例化真正的实现。理论上,您可以在开始时通过system属性实例化这个新的代理处理程序,但也可以在实际调用时使用您想要的代理处理程序

    更新:

    实际上,我认为上面的链接提到了这个策略:

    另一种方法是使用工厂注册,但提供一个工厂类,该类本身支持使用不同名称注册多个不同的流处理程序

    这种方法支持使用java.net.URL类的代码,但它确实需要对每个协议进行注册调用,因此需要对应用程序进行更改,然后才能使用新的URL。然而,这种方法绕过了上面讨论的多类加载器的问题,因为工厂是由用户代码类加载器加载的,而不是由URL类的类加载器加载的


    我不太熟悉你在做什么,也不知道注册是如何进行的,所以根据你在做什么,这可能会有点复杂。Idk,如果您是否需要额外注册,但听起来它可能会解决.jar/app上下文问题。

    Idk,如果这可以工作,但是如果您创建一个新的URLStreamHandlerFactory,但实际上不包含实现,该怎么办?它只是坐在那里,然后在运行时通过应用程序上下文查找调用时实例化真正的实现。理论上,您可以在开始时通过system属性实例化这个新的代理处理程序,但也可以在实际调用时使用您想要的代理处理程序

    更新:

    实际上,我认为上面的链接提到了这个策略:

    另一种方法是使用工厂注册,但提供一个工厂类,该类本身支持使用不同名称注册多个不同的流处理程序

    这种方法支持使用java.net.URL类的代码,但它确实需要对每个协议进行注册调用,因此需要对应用程序进行更改,然后才能使用新的URL。然而,这种方法绕过了上面讨论的多类加载器的问题,因为工厂是由用户代码类加载器加载的,而不是由URL类的类加载器加载的

    我不太熟悉你在做什么,也不知道注册是如何进行的,所以根据你在做什么,这可能会有点复杂。Idk,如果您是否需要额外注册,但听起来它可能会解决.jar/app上下文问题。

    每当我在同一句话中听到“好主意”和“反思”时,我都会畏缩每当我在同一句话中听到“好主意”和“反思”时,我都会畏缩