Base64 编码数组中的单行

Base64 encode single row in an array

我正在构建一个 Android 应用程序,它应该能够拍照,然后将其存储在数据库中。我把那部分记下来了。但是,当我尝试再次将它加载到我的应用程序中时,它就变得棘手了。

我将图像作为 longblob 存储在我的数据库中,并且我可以从 logcat 中的 json 读数中看到 longblob 作为字符串返回。一个很长的字符串,我无法处理。当我尝试添加到我的 gson 创建的包装器 class 时,它只是给了我一个空指针。

现在,我在 php 文件中看到了多个建议我 base64_encode 它的地方。我找到了一种方法来做到这一点,但只能通过在 php 文件中添加另一个数组,并且我想避免在我的 java 代码中处理不同的数组。

我的 php 到目前为止看起来是这样的:

<?php
function resultToArray($result) {
    $rows = array();
    while($row = $result->fetch_assoc()) {
        $rows[] = $row;

       foreach($rows as $key=>$value){ /* Creating this extra array is what I'm looking to avoid. */
           $newArrData[$key] =  $spots[$key];
           $newArrData[$key]['Image'] = base64_encode($spots[$key]['Image']);
       }
     }
     return $rows;
}
$mysqli = new mysqli("host", "username", "password", "db_to_use");
$email = $mysqli->real_escape_string($_GET['email']);
$mysqli->set_charset('utf8');
$query = ("SELECT * FROM Cards WHERE Email_FK='{$email}'");
$result = $mysqli->query($query);
$rows = resultToArray($result);
echo json_encode($rows);

$result->free();
?>

我要返回 9 个不同的值,包括图像。有没有办法避免创建 newArrData 数组,所以我只需要在我的代码中处理这个数组?

我的包装器 class 在 java 代码中:

import java.io.Serializable;

/**
 * Created by KasperG on 22/04/2015.
 */
public class Card implements Serializable {
    private String Email_FK;
    private String BarcodeNumbers;
    private String MemberNumber;
    private String StoreID;
    private String CardID;
    private String HasBarcode;
    private String StoreName;
    private String CustomCard;
    //private Base64 Image;


    public Card() {

    }

    public Card(String barcodeNumbers, String memberNumber, String storeID, String hasBarcode, String cardID, String storeName, String CustomCard) {
        this.StoreID = storeID;
        if (barcodeNumbers.isEmpty()) {
            this.BarcodeNumbers = null;
        } else {
            this.BarcodeNumbers = barcodeNumbers;
        }
        if (memberNumber.isEmpty()) {
            this.MemberNumber = null;
        } else {
            this.MemberNumber = memberNumber;
        }
        this.HasBarcode = hasBarcode;
        this.CardID = cardID;
        this.StoreName = storeName;
        this.CustomCard = CustomCard;
    }
    /*
    public Card(String memberNumber, String storeID) {
        this.memberNumber = memberNumber;
        this.storeID = storeID;
    }
    */

    public String getBarcodeNumbers() {
        return BarcodeNumbers;
    }

    public String getMemberNumber() {
        return MemberNumber;
    }

    public String getHasBarcode() {
        return HasBarcode;
    }

    public String getCardID() {
        return CardID;
    }

    public String getStoreName() {
        return StoreName;
    }

    public int getStoreID() {
        return Integer.parseInt(StoreID);
    }

    public String getCustomStore() { return CustomCard; }

    //public Base64 getImageString() { return Image; }


    @Override
    public String toString() {
        return "MemberNumber: " + MemberNumber + "\n" +
                "BarcodeNumbers: " + BarcodeNumbers + "\n" +
                "Store ID: " + StoreID + "\n" +
                "Has Barcode " + HasBarcode + "\n" +
                "Card ID: " + CardID + "\n" +
                "Store Name: " + StoreName + "\n" +
                "Custom Card? " + CustomCard + "\n" +
                "Image String: " /*+ Image*/;
    }
}

"Image" 变量是故意取消注释的,因为如果我不这样做,它根本不起作用!

然后我使用 gson 从包装器创建 class;

public ArrayList<Card> getCards(MyCardsScreenActivity activity) {
    myCards = activity;

    String email = SaveSharedPreferences.getUserName(activity);
    ArrayList<Card> cards = new ArrayList<>();
    try {
        String link = "http://test.wallyy.com/new_get_card_info.php?email=" + email;
        HttpClient client = new DefaultHttpClient();
        HttpGet request = new HttpGet();
        request.setURI(new URI(link));
        HttpResponse response = client.execute(request);
        String data = EntityUtils.toString(response.getEntity());
        Log.d("Pass3?", data.toString());

        Gson gson = new Gson();
        Card[] cards1 = gson.fromJson(data.toString(), Card[].class);
        for(Card card : cards1) {
            cards.add(card);
            Log.d("Card toString;\n", card.toString());
        }
    }
    catch(Exception ex) {}

    if (!cards.isEmpty()) {
        myCards.setHasCards(true);
    }
    else {
        myCards.setHasCards(false);
    }
    return cards;
}

谁能给我指出正确的方向?

编辑: 根据@CJ Wurtz 的建议,我将 php 文件更改为此;

while($row = $result->fetch_assoc()) {
        $row['Image'] = base64_encode($row['Image']);
        $rows[] = $row;
    }

然而,这在 Android 端仍然不起作用。将我的包装器 class 更新为此;

public class Card implements Serializable {
    private String Email_FK;
    private String BarcodeNumbers;
    private String MemberNumber;
    private String StoreID;
    private String CardID;
    private String HasBarcode;
    private String StoreName;
    private String CustomCard;
    private Base64 Image;


    public Card() {

    }

但是在我添加 Image 变量的那一刻,gson 没有创建包装器的任何实例 class。

重新编辑:刚刚意识到我粘贴了错误的 http 方法。更新后的 public ArrayList<Card> getCards(MyCardsScreenActivity) {...} 是我要创建包装器实例 class 并将它们添加到数组列表的那个。

为什么不直接用 base64_encoded 版本覆盖 "Image" 元素?

即:

while($row = $result->fetch_assoc()) {
    $row['Image'] = base64_encode($row['Image']);
    $rows[] = $row;
}

我不确定 $spots 数组来自哪里,所以这个解决方案可能不适合您,但基本上只是说对于从数据库返回的每一行,更新该数组在将行添加到最终结果数组之前,您将 return.

我的包装器 class 设置错误。我不确定如何处理来自服务器的响应,但通过对我的包装器进行一些更改 class,我让它工作了。

我的包装器 class 现在看起来像这样;

    import java.io.Serializable;

    /**
     * Created by KasperG on 22/04/2015.
     */
    public class Card implements Serializable {
        private String Email_FK;
        private String BarcodeNumbers;
        private String MemberNumber;
        private String StoreID;
        private String CardID;
        private String HasBarcode;
        private String StoreName;
        private String CustomCard;
        private String Image;


        public Card() {

        }

        public Card(String barcodeNumbers, String memberNumber, String storeID, String hasBarcode, String cardID, String storeName, String CustomCard, String Image) {
            this.StoreID = storeID;
            if (barcodeNumbers.isEmpty()) {
                this.BarcodeNumbers = null;
            } else {
                this.BarcodeNumbers = barcodeNumbers;
            }
            if (memberNumber.isEmpty()) {
                this.MemberNumber = null;
            } else {
                this.MemberNumber = memberNumber;
            }
            this.HasBarcode = hasBarcode;
            this.CardID = cardID;
            this.StoreName = storeName;
            this.CustomCard = CustomCard;
            this.Image = Image;
        }

        public String getBarcodeNumbers() {
            return BarcodeNumbers;
        }

        public String getMemberNumber() {
            return MemberNumber;
        }

        public String getHasBarcode() {
            return HasBarcode;
        }

        public String getCardID() {
            return CardID;
        }

        public String getStoreName() {
            return StoreName;
        }

        public int getStoreID() {
            return Integer.parseInt(StoreID);
        }

        public String getCustomStore() { return CustomCard; }

       public String getImageString() { return Image; }


        @Override
        public String toString() {
            return "MemberNumber: " + MemberNumber + "\n" +
                    "BarcodeNumbers: " + BarcodeNumbers + "\n" +
                    "Store ID: " + StoreID + "\n" +
                    "Has Barcode " + HasBarcode + "\n" +
                    "Card ID: " + CardID + "\n" +
                    "Store Name: " + StoreName + "\n" +
                    "Custom Card? " + CustomCard + "\n" +
                    "Image String: " + Image;
        }
    }

将 Image 变量的类型更改为 String,实现了这个;

public ArrayList<Card> getCards(MyCardsScreenActivity activity) {
        myCards = activity;

        String email = SaveSharedPreferences.getUserName(activity);
        ArrayList<Card> cards = new ArrayList<>();
        try {
            String link = "http://address.com/new_get_card_info.php?email=" + email;
            HttpClient client = new DefaultHttpClient();
            HttpGet request = new HttpGet();
            request.setURI(new URI(link));
            HttpResponse response = client.execute(request);
            String data = EntityUtils.toString(response.getEntity());
            Log.d("Pass3?", data.toString());

            Gson gson = new Gson();
            Card[] cards1 = gson.fromJson(data.toString(), Card[].class);
            for(Card card : cards1) {
                cards.add(card);
                Log.d("Card toString;\n", card.toString());
            }
        }
        catch(Exception ex) {}

        if (!cards.isEmpty()) {
            myCards.setHasCards(true);
        }
        else {
            myCards.setHasCards(false);
        }
        return cards;
    }

工作。然后我只需要处理那个字符串;

byte[] bytes = Base64.decode(card.getImageString(), Base64.DEFAULT);
bitmap = BitmapFactory.decodeByteArray(bytes, 0, bytes.length);

再次抱歉问题表述不当。以后我会尽量切题的。