在Map中解析JSON,android

时间:2017-09-23 23:07:13

标签: android json

如何通过java代码获取此JSON http://api.fixer.io/latest并在地图中写入“费率”?

1 个答案:

答案 0 :(得分:0)

  

如何通过java代码获取此JSON http://api.fixer.io/latest并编写mas" rates"在地图?

您可以使用GsonRetrofitRxjava来实现此目的。

以下是依赖项 - build.gradle(应用程序级别):

allprojects {
    repositories {
        google()
        jcenter()
    }

    project.ext {
        gsonVersion = "2.8.0"
        retrofit2Version = "2.3.0"
        okHttp3Version = "3.8.1"
        rxandroidVersion = "1.2.0"
        rxjavaVersion = "1.1.4"
    }
}

在模块级build.gradle:

dependencies {
    implementation fileTree(dir: 'libs', include: ['*.jar'])
    implementation 'com.android.support:appcompat-v7:26.1.0'
    implementation 'com.android.support.constraint:constraint-layout:1.0.2'
    testImplementation 'junit:junit:4.12'

    androidTestImplementation('com.android.support.test.espresso:espresso-core:3.0.1', {
            exclude group: 'com.android.support', module: 'support-annotations'
        })

    compile "com.google.code.gson:gson:$rootProject.ext.gsonVersion"
    compile "com.squareup.okhttp3:okhttp:$rootProject.ext.okHttp3Version"
    compile "com.squareup.okhttp3:okhttp-urlconnection:$rootProject.ext.okHttp3Version"
    compile "com.squareup.retrofit2:retrofit:$rootProject.ext.retrofit2Version"
    compile "com.squareup.retrofit2:converter-gson:$rootProject.ext.retrofit2Version"
    compile "io.reactivex:rxandroid:$rootProject.ext.rxandroidVersion"
    compile "io.reactivex:rxjava:$rootProject.ext.rxjavaVersion"
}

我在我的清单文件中添加了<uses-permission android:name="android.permission.INTERNET" />,然后创建了一个界面来处理来自您提供的url的数据:

import retrofit2.Call;
import retrofit2.http.GET;

public interface RestInterface {
    @GET("/latest")
    Call<ResultFromAPI> getJsonObjects();
}

首先,我在浏览器中访问了网址并收到了一个Json文本,我将其复制并粘贴到json2pojo中,然后我为目标语言,源类型注释样式等做了以下选择:< / p>

json2pojoimg

单击预览,您将看到可以从URL创建响应(Json文本)的类。

接下来,我创建了一些类来包含来自url的响应:

import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;

public class ResultFromAPI {

    @SerializedName("base")
    @Expose
    private String base;

    @SerializedName("date")
    @Expose
    private String date;

    @SerializedName("rates")
    @Expose
    private Rates rates;

    public String getBase() {
        return base;
    }

    public void setBase(String base) {
        this.base = base;
    }

    public String getDate() {
        return date;
    }

    public void setDate(String date) {
        this.date = date;
    }

    public Rates getRates() {
        return rates;
    }

    public void setRates(Rates rates) {
        this.rates = rates;
    }
}

这是费率等级:

import com.google.gson.annotations.Expose;
import com.google.gson.annotations.SerializedName;

public class Rates {

    @SerializedName("AUD")
    @Expose
    private Double aUD;

    @SerializedName("BGN")
    @Expose
    private Double bGN;

    @SerializedName("BRL")
    @Expose
    private Double bRL;

    @SerializedName("CAD")
    @Expose
    private Double cAD;

    @SerializedName("CHF")
    @Expose
    private Double cHF;

    @SerializedName("CNY")
    @Expose
    private Double cNY;

    @SerializedName("CZK")
    @Expose
    private Double cZK;

    @SerializedName("DKK")
    @Expose
    private Double dKK;

    @SerializedName("GBP")
    @Expose
    private Double gBP;

    @SerializedName("HKD")
    @Expose
    private Double hKD;

    @SerializedName("HRK")
    @Expose
    private Double hRK;

    @SerializedName("HUF")
    @Expose
    private Double hUF;

    @SerializedName("IDR")
    @Expose
    private Integer iDR;

    @SerializedName("ILS")
    @Expose
    private Double iLS;

    @SerializedName("INR")
    @Expose
    private Double iNR;

    @SerializedName("JPY")
    @Expose
    private Double jPY;

    @SerializedName("KRW")
    @Expose
    private Double kRW;

    @SerializedName("MXN")
    @Expose
    private Double mXN;

    @SerializedName("MYR")
    @Expose
    private Double mYR;

    @SerializedName("NOK")
    @Expose
    private Double nOK;

    @SerializedName("NZD")
    @Expose
    private Double nZD;

    @SerializedName("PHP")
    @Expose
    private Double pHP;

    @SerializedName("PLN")
    @Expose
    private Double pLN;

    @SerializedName("RON")
    @Expose
    private Double rON;

    @SerializedName("RUB")
    @Expose
    private Double rUB;

    @SerializedName("SEK")
    @Expose
    private Double sEK;

    @SerializedName("SGD")
    @Expose
    private Double sGD;

    @SerializedName("THB")
    @Expose
    private Double tHB;

    @SerializedName("TRY")
    @Expose
    private Double tRY;

    @SerializedName("USD")
    @Expose
    private Double uSD;

    @SerializedName("ZAR")
    @Expose
    private Double zAR;

    public Double getAUD() {
        return aUD;
    }

    public void setAUD(Double aUD) {
        this.aUD = aUD;
    }

    public Double getBGN() {
        return bGN;
    }

    public void setBGN(Double bGN) {
        this.bGN = bGN;
    }

    public Double getBRL() {
        return bRL;
    }

    public void setBRL(Double bRL) {
        this.bRL = bRL;
    }

    public Double getCAD() {
        return cAD;
    }

    public void setCAD(Double cAD) {
        this.cAD = cAD;
    }

    public Double getCHF() {
        return cHF;
    }

    public void setCHF(Double cHF) {
        this.cHF = cHF;
    }

    public Double getCNY() {
        return cNY;
    }

    public void setCNY(Double cNY) {
        this.cNY = cNY;
    }

    public Double getCZK() {
        return cZK;
    }

    public void setCZK(Double cZK) {
        this.cZK = cZK;
    }

    public Double getDKK() {
        return dKK;
    }

    public void setDKK(Double dKK) {
        this.dKK = dKK;
    }

    public Double getGBP() {
        return gBP;
    }

    public void setGBP(Double gBP) {
        this.gBP = gBP;
    }

    public Double getHKD() {
        return hKD;
    }

    public void setHKD(Double hKD) {
        this.hKD = hKD;
    }

    public Double getHRK() {
        return hRK;
    }

    public void setHRK(Double hRK) {
        this.hRK = hRK;
    }

    public Double getHUF() {
        return hUF;
    }

    public void setHUF(Double hUF) {
        this.hUF = hUF;
    }

    public Integer getIDR() {
        return iDR;
    }

    public void setIDR(Integer iDR) {
        this.iDR = iDR;
    }

    public Double getILS() {
        return iLS;
    }

    public void setILS(Double iLS) {
        this.iLS = iLS;
    }

    public Double getINR() {
        return iNR;
    }

    public void setINR(Double iNR) {
        this.iNR = iNR;
    }

    public Double getJPY() {
        return jPY;
    }

    public void setJPY(Double jPY) {
        this.jPY = jPY;
    }

    public Double getKRW() {
        return kRW;
    }

    public void setKRW(Double kRW) {
        this.kRW = kRW;
    }

    public Double getMXN() {
        return mXN;
    }

    public void setMXN(Double mXN) {
        this.mXN = mXN;
    }

    public Double getMYR() {
        return mYR;
    }

    public void setMYR(Double mYR) {
        this.mYR = mYR;
    }

    public Double getNOK() {
        return nOK;
    }

    public void setNOK(Double nOK) {
        this.nOK = nOK;
    }

    public Double getNZD() {
        return nZD;
    }

    public void setNZD(Double nZD) {
        this.nZD = nZD;
    }

    public Double getPHP() {
        return pHP;
    }

    public void setPHP(Double pHP) {
        this.pHP = pHP;
    }

    public Double getPLN() {
        return pLN;
    }

    public void setPLN(Double pLN) {
        this.pLN = pLN;
    }

    public Double getRON() {
        return rON;
    }

    public void setRON(Double rON) {
        this.rON = rON;
    }

    public Double getRUB() {
        return rUB;
    }

    public void setRUB(Double rUB) {
        this.rUB = rUB;
    }

    public Double getSEK() {
        return sEK;
    }

    public void setSEK(Double sEK) {
        this.sEK = sEK;
    }

    public Double getSGD() {
        return sGD;
    }

    public void setSGD(Double sGD) {
        this.sGD = sGD;
    }

    public Double getTHB() {
        return tHB;
    }

    public void setTHB(Double tHB) {
        this.tHB = tHB;
    }

    public Double getTRY() {
        return tRY;
    }

    public void setTRY(Double tRY) {
        this.tRY = tRY;
    }

    public Double getUSD() {
        return uSD;
    }

    public void setUSD(Double uSD) {
        this.uSD = uSD;
    }

    public Double getZAR() {
        return zAR;
    }

    public void setZAR(Double zAR) {
        this.zAR = zAR;
    }
}

接下来,我创建了将负责处理调用的类(使用之前创建的rest接口),它还将负责接收响应:

import android.support.annotation.NonNull;
import android.support.annotation.WorkerThread;
import android.util.Log;

import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import rx.Observable;
import rx.functions.Action1;

public class CallToFixerAPI {

    private static final String TAG = "CallToFixerAPITAG_";
    private final RestInterface restInterface;

    public CallToFixerAPI(RestInterface restInterface) {
        this.restInterface = restInterface;
    }

    @WorkerThread
    public void call(String url, final Action1<ResultFromAPI> responseAction1) throws Exception {
        try {
            Call<ResultFromAPI> call = restInterface.getJsonObjects();

            call.enqueue(new Callback<ResultFromAPI>() {
                @Override
                public void onResponse(@NonNull Call<ResultFromAPI> call,
                                       @NonNull Response<ResultFromAPI> responseFromAPI) {
                    Observable.just(responseFromAPI.body()).subscribe(responseAction1);
                }

                @Override
                public void onFailure(@NonNull Call<ResultFromAPI> call,
                                      @NonNull Throwable t) {
                    Log.e(TAG, "onFailure: " + t.getMessage());
                }
            });
        } catch (Exception e) {
            Log.e(TAG, "Failed to execute call to fixer api: " + url + ": " + e.toString());
        }
    }
}

最后,我在MainActivity中将所有内容捆绑在一起:

import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import retrofit2.Retrofit;
import retrofit2.converter.gson.GsonConverterFactory;
import rx.Observable;
import rx.functions.Action1;

public class MainActivity extends AppCompatActivity {

    private static final String TAG = "MainActivityTAG_";
    private CallToFixerAPI callToFixerAPI;
    private HashMap<String, Object> ratesHashMap = new HashMap<>();

    public static Map<String, Object> ConvertObjectToMap(Object obj)
            throws IllegalAccessException, IllegalArgumentException, InvocationTargetException {
        Method[] methods = obj.getClass().getMethods();

        Map<String, Object> map = new HashMap<>();
        for (Method m : methods) {
            if (m.getName().startsWith("get") && !m.getName().startsWith("getClass")) {
                Object value = m.invoke(obj);
                map.put(m.getName().substring(3), value);
            }
        }
        return map;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        String url = "http://api.fixer.io/";

        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl(url)
                .addConverterFactory(GsonConverterFactory.create())
                .build();

        RestInterface restInterface = retrofit.create(RestInterface.class);

        callToFixerAPI = new CallToFixerAPI(restInterface);

        getResponseFromAPI(url, new Action1<ResultFromAPI>() {
            @Override
            public void call(ResultFromAPI resultFromAPI) {
                Log.d(TAG, "Base is: " + resultFromAPI.getBase());
                Log.d(TAG, "Date is: " + resultFromAPI.getDate());
                try {
                    ratesHashMap = (HashMap<String, Object>) ConvertObjectToMap(resultFromAPI.getRates());
                    Log.d(TAG, "Rates are: " + ratesHashMap);
                } catch (IllegalAccessException | InvocationTargetException e) {
                    e.printStackTrace();
                }
            }
        });
    }

    public void getResponseFromAPI(String url, final Action1<ResultFromAPI> resultAction1) {
        try {
            callToFixerAPI.call(url, new Action1<ResultFromAPI>() {
                @Override
                public void call(ResultFromAPI results) {
                    Observable.just(results).subscribe(resultAction1);
                }
            });
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

我知道如果您是Android新手,或者如果您不了解Rxjava或Retrofit,这可能看起来很多,但如果您按照上述步骤操作并且可以在没有编译的情况下编译程序如果出现任何错误,您应该在调试器模式下使用MainActivityCallToFixerAPI中的多个断点运行应用。

我建议在所有Log.d语句和以Observable.just(...)开头的任何句子中添加断点。

注意

  • 我正在使用Android Studio 3.0 - 因此,如果您还没有使用Android Studio 3.0,那么有些内容可能会与您的IDE不同。
  • 我故意将所有内容添加到Logcat(Android监视器),屏幕上没有任何内容,答案太长了。另外,我决定如何最好地向您显示ratesHashMap