1/* 2 * Copyright (C) 2018 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License 15 */ 16 17package com.android.server.testing.shadows; 18 19import android.app.backup.BackupDataOutput; 20 21import org.robolectric.annotation.Implementation; 22import org.robolectric.annotation.Implements; 23 24import java.io.ByteArrayOutputStream; 25import java.io.FileDescriptor; 26import java.io.FileOutputStream; 27import java.io.IOException; 28import java.io.ObjectOutputStream; 29 30/** 31 * Shadow for {@link BackupDataOutput}. Format written does NOT match implementation. To read data 32 * written with this shadow you should also declare shadow {@link ShadowBackupDataInput}. 33 */ 34@Implements(BackupDataOutput.class) 35public class ShadowBackupDataOutput { 36 private long mQuota; 37 private int mTransportFlags; 38 private ObjectOutputStream mOutput; 39 40 @Implementation 41 public void __constructor__(FileDescriptor fd, long quota, int transportFlags) { 42 try { 43 mOutput = new ObjectOutputStream(new FileOutputStream(fd)); 44 } catch (IOException e) { 45 throw new AssertionError(e); 46 } 47 mQuota = quota; 48 mTransportFlags = transportFlags; 49 } 50 51 @Implementation 52 public long getQuota() { 53 return mQuota; 54 } 55 56 @Implementation 57 public int getTransportFlags() { 58 return mTransportFlags; 59 } 60 61 @Implementation 62 public int writeEntityHeader(String key, int dataSize) throws IOException { 63 final int size; 64 try (ByteArrayOutputStream byteStream = new ByteArrayOutputStream()) { 65 writeEntityHeader(new ObjectOutputStream(byteStream), key, dataSize); 66 size = byteStream.size(); 67 } 68 writeEntityHeader(mOutput, key, dataSize); 69 return size; 70 } 71 72 private void writeEntityHeader(ObjectOutputStream stream, String key, int dataSize) 73 throws IOException { 74 // Write the int first because readInt() throws EOFException, to know when stream ends 75 stream.writeInt(dataSize); 76 stream.writeUTF(key); 77 stream.flush(); 78 } 79 80 @Implementation 81 public int writeEntityData(byte[] data, int size) throws IOException { 82 mOutput.write(data, 0, size); 83 mOutput.flush(); 84 return size; 85 } 86} 87