溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

Feign怎么自定義注解翻譯器

發(fā)布時間:2022-03-17 08:58:57 來源:億速云 閱讀:191 作者:iii 欄目:開發(fā)技術(shù)

本篇內(nèi)容主要講解“Feign怎么自定義注解翻譯器”,感興趣的朋友不妨來看看。本文介紹的方法操作簡單快捷,實用性強。下面就讓小編來帶大家學(xué)習(xí)“Feign怎么自定義注解翻譯器”吧!

    Feign自定義注解翻譯器

    新建自定義注解MyUrl

    package org.crazyit.cloud.contract; 
    import java.lang.annotation.ElementType;
    import java.lang.annotation.Retention;
    import java.lang.annotation.RetentionPolicy;
    import java.lang.annotation.Target;
     
    //這個注解只能定義方法
    @Target(ElementType.METHOD)
    @Retention(RetentionPolicy.RUNTIME)
    public @interface MyUrl {
        //為注解配置兩個屬性
        String url();
        String method();
    }

    新建接口,使用MyUrl注解

    package org.crazyit.cloud.contract; 
    public interface ContractClient { 
        @MyUrl(url = "/hello", method = "GET")
        public String hello();
    }

    定義注解翻譯器

    package org.crazyit.cloud.contract; 
    import java.lang.annotation.Annotation;
    import java.lang.reflect.Method; 
    import feign.Contract.BaseContract;
    import feign.MethodMetadata; 
    public class MyContract extends BaseContract {
     
        @Override
        protected void processAnnotationOnClass(MethodMetadata data, Class<?> clz) {
            // 處理類級別注解
     
        }
     
        @Override
        protected void processAnnotationOnMethod(MethodMetadata data,
                Annotation annotation, Method method) {
            // 注解是MyUrl類型的,才處理
            if(MyUrl.class.isInstance(annotation)) {
                MyUrl myUrl = method.getAnnotation(MyUrl.class);
                String url = myUrl.url();
                String httpMethod = myUrl.method();
                data.template().method(httpMethod);
                data.template().append(url);
            }
        }
     
        @Override
        protected boolean processAnnotationsOnParameter(MethodMetadata data,
                Annotation[] annotations, int paramIndex) {
            // 處理參數(shù)級別注解
            return false;
        } 
    }

    測試類

    package org.crazyit.cloud.contract; 
    import org.crazyit.cloud.jaxrs.RsClient; 
    import feign.Feign;
    import feign.jaxrs.JAXRSContract;
     
    public class ContractMain { 
        public static void main(String[] args) {
            ContractClient client = Feign.builder()
                    .contract(new MyContract())
                    .target(ContractClient.class,
                    "http://localhost:8080");
            String result = client.hello();
            System.out.println(result);
        }
     
    }

    啟動服務(wù)類

    測試

    Hello World

    Feign注解說明

    Feign是常用的微服務(wù)rpc調(diào)用框架,下面對一些注解說明

    @Target({ElementType.TYPE})
    @Retention(RetentionPolicy.RUNTIME)
    @Documented
    @Inherited
    public @interface FeignClient {
        /**
         * value和name的作用一樣,如果沒有配置url那么配置的值將作為服務(wù)名稱,用于服務(wù)發(fā)現(xiàn)。反之只是一個名稱。
         *
         */
        @AliasFor("name")
        String value() default "";
        /**
         * serviceId已經(jīng)廢棄了,直接使用name即可。
         */
        /** @deprecated */
        @Deprecated
        String serviceId() default "";
        /**
         *某個服務(wù)提供的接口不止定義在一個類中,這樣啟動時會報Bean的名稱沖突。
         * 解決方法:
         * 1:參數(shù)配置添加
         *  spring.main.allow-bean-definition-overriding=true
         *
         * 2:給每個client指定contextid
         *
         */
        String contextId() default "";
        /**
         *
         *  在注冊Feign Client Configuration的時候需要一個名稱,名稱是通過getClientName方法獲取的.
         *  查看源碼可知,如果配置了contextId就會用contextId,
         *  如果沒有配置就會去value,然后是name,最后是serviceId。
         *  默認(rèn)都沒有配置,當(dāng)出現(xiàn)一個服務(wù)有多個Feign Client的時候就會報錯了。
         *
         *  其次的作用是在注冊FeignClient中,contextId會作為Client 別名的一部分,如果配置了qualifier優(yōu)先用qualifier作為別名。
         *
         */
        /**
         *見 value
         *
         */
        @AliasFor("value")
        String name() default "";
        /**
         *
         * 在注冊FeignClient中,指定client別名
         *
         */
        String qualifier() default "";
        /**
         *
         * url用于配置指定服務(wù)的地址,相當(dāng)于直接請求這個服務(wù),不經(jīng)過Ribbon的服務(wù)選擇。像調(diào)試等場景可以使用。
         *
         */
        String url() default "";
        /**
         *
         * 當(dāng)調(diào)用請求發(fā)生404錯誤時,decode404的值為true,那么會執(zhí)行decoder解碼,否則拋出異常。
         *
         */
        boolean decode404() default false;
        /**
         *
         * configuration是配置Feign配置類,在配置類中可以自定義Feign的Encoder、Decoder、LogLevel、Contract等。
         * 具體查看FeignConfiguration類
         *
         */
        Class<?>[] configuration() default {};
        /**
         *
         * 定義容錯的處理類,也就是回退邏輯,fallback的類必須實現(xiàn)Feign Client的接口,無法知道熔斷的異常信息。
         *
         *
         *
         *
         * 舉例:
         * //實現(xiàn)調(diào)用接口方法
         * @Component
         * public class UserRemoteClientFallback implements UserRemoteClient {
         * 	    @Override
         * 	    public User getUser(int id) {
         * 		    return new User(0, "默認(rèn)fallback");
         * 	    }
         * }
         *
         * //user服務(wù)
         * @FeignClient(value = "user", fallback = UserRemoteClientFallback.class)
         * public interface UserRemoteClient {
         * 	    @GetMapping("/user/get")
         * 	    public User getUser(@RequestParam("id")int id);
         * }
         *
         *
         */
        Class<?> fallback() default void.class;
        /**
         *
         * 也是容錯的處理,可以知道熔斷的異常信息。熔斷的另一種處理方法。
         *
         * //服務(wù)類作為參數(shù)傳入FallbackFactory模板參數(shù)
         * @Component
         * public class UserRemoteClientFallbackFactory implements FallbackFactory<UserRemoteClient> {
         * 	private Logger logger = LoggerFactory.getLogger(UserRemoteClientFallbackFactory.class);
         *
         * 	@Override
         * 	public UserRemoteClient create(Throwable cause) {
         * 		return new UserRemoteClient() {
         * 			@Override
         * 			public User getUser(int id) {
         * 				logger.error("UserRemoteClient.getUser異常", cause);
         * 				return new User(0, "默認(rèn)");
         * 			}
         * 		};
         * 	}
         * }
         *
         */
        Class<?> fallbackFactory() default void.class;
        /**
         *
         * path定義當(dāng)前FeignClient訪問接口時的統(tǒng)一前綴
         * 比如接口地址是/user/get, 如果你定義了前綴是user, 那么具體方法上的路徑就只需要寫/get 即可。
         *
         * @FeignClient(name = "user", path="user")
         * public interface UserRemoteClient {
         * 	    @GetMapping("/get")
         * 	    public User getUser(@RequestParam("id") int id);
         * }
         *
         */
        String path() default "";
        /**
         *  primary對應(yīng)的是@Primary注解,默認(rèn)為true.
         *  官方這樣設(shè)置也是有原因的。當(dāng)我們的Feign實現(xiàn)了fallback后,也就意味著Feign Client有多個相同的Bean在Spring容器中,
         *  當(dāng)我們在使用@Autowired(建議使用@Resource注入對象)進(jìn)行注入的時候,不知道注入哪個,所以我們需要設(shè)置一個優(yōu)先級高的,@Primary注解就是干這件事情的。
         *
         *
         */
        boolean primary() default true;
    }

    到此,相信大家對“Feign怎么自定義注解翻譯器”有了更深的了解,不妨來實際操作一番吧!這里是億速云網(wǎng)站,更多相關(guān)內(nèi)容可以進(jìn)入相關(guān)頻道進(jìn)行查詢,關(guān)注我們,繼續(xù)學(xué)習(xí)!

    向AI問一下細(xì)節(jié)

    免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

    AI