真机Retrofit请求Header未被服务器接收问题求助
Retrofit拦截器添加Header真机失效问题
我在Android应用中使用Interceptor为Retrofit请求添加并发送Header,但真机发送请求时服务器接收不到Header,模拟器发送则正常;同时Logcat中也无法看到这些Header日志,恳请指导问题所在。
private ApiClient() { HttpLoggingInterceptor logging = new HttpLoggingInterceptor(); // set your desired log level logging.setLevel(HttpLoggingInterceptor.Level.HEADERS); logging.setLevel(HttpLoggingInterceptor.Level.BODY); OkHttpClient.Builder httpClient = new OkHttpClient.Builder(); httpClient.connectTimeout(60, TimeUnit.SECONDS); httpClient.readTimeout(60, TimeUnit.SECONDS); httpClient.writeTimeout(60, TimeUnit.SECONDS); httpClient.retryOnConnectionFailure(true); // add your other interceptors … // add logging as last interceptor httpClient.addInterceptor(logging); Interceptor jsonInterceptor = new Interceptor() { @Override public okhttp3.Response intercept(Chain chain) throws IOException { String appVersion = BuildConfig.VERSION_NAME; Request request = chain.request().newBuilder() .header("Content-Type", "application/json") .header("app-version", appVersion) .header("device", "Android") .header("AppPackage", BuildConfig.APPLICATION_ID) .build(); return chain.proceed(request); } }; httpClient.addInterceptor(jsonInterceptor); httpClient.addInterceptor(chain -> { //analytics logging interceptor for testing only Request request = chain.request(); okhttp3.Response response = chain.proceed(request); return response; }); httpClient.addInterceptor(chain -> { Request request = chain.request(); okhttp3.Response response = chain.proceed(request); int tryCount = 0; int retryLimit = 2; while (!response.isSuccessful() && tryCount < retryLimit) { tryCount++; response.close(); response = chain.proceed(request); } return response; }); Gson gson = new GsonBuilder().serializeNulls().create(); retrofit = new Retrofit.Builder() .baseUrl(BASE_URL) .addConverterFactory(GsonConverterFactory.create(gson)) .client(httpClient.build()) .build(); apiInterface = retrofit.create(ApiInterface.class); }
问题根源与解决方法
1. 拦截器顺序错误(核心问题)
OkHttp的拦截器按添加顺序执行,你把日志拦截器放在了最前面,此时添加Header的拦截器还未执行,所以Logcat看不到自定义Header;同时真机环境下可能因后续拦截器的执行逻辑,导致Header未被正确携带到最终请求中。
修正:将日志拦截器移到所有业务拦截器(尤其是添加Header的拦截器)之后,确保日志能捕获到完整的请求信息。
2. 重复设置日志级别
连续调用setLevel会覆盖之前的设置,Level.BODY已经包含了HEADERS的日志内容,只需保留一次设置即可。
3. Header覆盖风险
使用.header()会覆盖同名的已有Header,如果你的Retrofit接口注解中已经定义了Content-Type,自定义的Header会被覆盖。改用.addHeader()可以避免这个问题,确保所有自定义Header都被添加。
4. 重试拦截器的请求复用问题
你的重试逻辑中使用的是原始请求对象,如果原始请求未携带Header(因拦截器顺序问题),重试的请求也不会包含Header。修正后确保重试时使用经过Header处理后的请求对象。
5. 真机网络环境排查
部分真机可能存在代理、VPN或系统网络设置拦截请求Header,可尝试关闭代理、切换网络(如从WiFi切换到移动数据),或检查是否有安全软件拦截了网络请求。
修正后的完整代码
private ApiClient() { HttpLoggingInterceptor logging = new HttpLoggingInterceptor(); // 只设置一次级别,BODY包含HEADERS日志 logging.setLevel(HttpLoggingInterceptor.Level.BODY); OkHttpClient.Builder httpClient = new OkHttpClient.Builder(); httpClient.connectTimeout(60, TimeUnit.SECONDS); httpClient.readTimeout(60, TimeUnit.SECONDS); httpClient.writeTimeout(60, TimeUnit.SECONDS); httpClient.retryOnConnectionFailure(true); // 1. 先添加自定义Header拦截器,确保所有请求都携带Header Interceptor jsonInterceptor = new Interceptor() { @Override public okhttp3.Response intercept(Chain chain) throws IOException { String appVersion = BuildConfig.VERSION_NAME; Request request = chain.request().newBuilder() .addHeader("Content-Type", "application/json") .addHeader("app-version", appVersion) .addHeader("device", "Android") .addHeader("AppPackage", BuildConfig.APPLICATION_ID) .build(); return chain.proceed(request); } }; httpClient.addInterceptor(jsonInterceptor); // 2. 添加分析日志拦截器 httpClient.addInterceptor(chain -> { Request request = chain.request(); okhttp3.Response response = chain.proceed(request); return response; }); // 3. 添加重试拦截器,使用处理后的请求对象 httpClient.addInterceptor(chain -> { Request request = chain.request(); okhttp3.Response response = chain.proceed(request); int tryCount = 0; int retryLimit = 2; while (!response.isSuccessful() && tryCount < retryLimit) { tryCount++; response.close(); response = chain.proceed(request); } return response; }); // 4. 最后添加日志拦截器,捕获完整请求信息 httpClient.addInterceptor(logging); Gson gson = new GsonBuilder().serializeNulls().create(); retrofit = new Retrofit.Builder() .baseUrl(BASE_URL) .addConverterFactory(GsonConverterFactory.create(gson)) .client(httpClient.build()) .build(); apiInterface = retrofit.create(ApiInterface.class); }
内容的提问来源于stack exchange,提问作者momersaleem
相关产品推荐
相关产品推荐

