Home | History | Annotate | Download | only in cts
      1 /*
      2  * Copyright (C) 2016 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 
     17 package android.print.cts;
     18 
     19 import android.app.Activity;
     20 import android.app.PendingIntent;
     21 import android.content.Intent;
     22 import android.print.PrintAttributes;
     23 import android.print.PrintAttributes.Margins;
     24 import android.print.PrintAttributes.MediaSize;
     25 import android.print.PrintAttributes.Resolution;
     26 import android.print.PrintDocumentAdapter;
     27 import android.print.PrinterCapabilitiesInfo;
     28 import android.print.PrinterId;
     29 import android.print.PrinterInfo;
     30 import android.print.test.BasePrintTest;
     31 import android.print.test.services.FirstPrintService;
     32 import android.print.test.services.PrintServiceCallbacks;
     33 import android.print.test.services.PrinterDiscoverySessionCallbacks;
     34 import android.print.test.services.SecondPrintService;
     35 import android.print.test.services.StubbablePrinterDiscoverySession;
     36 import android.support.test.runner.AndroidJUnit4;
     37 import android.support.test.uiautomator.UiObject;
     38 import android.support.test.uiautomator.UiSelector;
     39 import android.text.TextUtils;
     40 
     41 import org.junit.Test;
     42 import org.junit.runner.RunWith;
     43 
     44 import java.util.ArrayList;
     45 import java.util.List;
     46 
     47 /**
     48  * Tests all allowed types of printerInfo
     49  */
     50 @RunWith(AndroidJUnit4.class)
     51 public class PrinterInfoTest extends BasePrintTest {
     52     private static final String NAMED_PRINTERS_NAME_PREFIX = "Printer ";
     53 
     54     /** The printer discovery session used in this test */
     55     private static StubbablePrinterDiscoverySession sDiscoverySession;
     56 
     57     private boolean isValidStatus(int status) {
     58         return status == PrinterInfo.STATUS_IDLE
     59                 || status == PrinterInfo.STATUS_BUSY
     60                 || status == PrinterInfo.STATUS_UNAVAILABLE;
     61     }
     62 
     63     /**
     64      * Create a mock {@link PrinterDiscoverySessionCallbacks} that discovers a printers with all
     65      * possible combinations of interesting printers.
     66      *
     67      * @return The mock session callbacks
     68      */
     69     private PrinterDiscoverySessionCallbacks createFirstMockPrinterDiscoverySessionCallbacks() {
     70         return createMockPrinterDiscoverySessionCallbacks(invocation -> {
     71             // Get the session.
     72             sDiscoverySession = ((PrinterDiscoverySessionCallbacks) invocation.getMock())
     73                     .getSession();
     74 
     75             if (sDiscoverySession.getPrinters().isEmpty()) {
     76                 final int INVALID_RES_ID = 0xffffffff;
     77 
     78                 final PrinterInfo.Builder badPrinter = new PrinterInfo.Builder(
     79                         sDiscoverySession.getService().generatePrinterId("bad printer"),
     80                         "badPrinter", PrinterInfo.STATUS_UNAVAILABLE);
     81 
     82                 String[] localPrinterIds = {
     83                         "Printer", null
     84                 };
     85 
     86                 String[] names = {
     87                         NAMED_PRINTERS_NAME_PREFIX, "", null
     88                 };
     89                 int[] statusList = {
     90                         PrinterInfo.STATUS_IDLE, PrinterInfo.STATUS_BUSY,
     91                         PrinterInfo.STATUS_UNAVAILABLE, 0, 42
     92                 };
     93                 int[] iconResourceIds = {
     94                         R.drawable.red_printer, 0, INVALID_RES_ID, -1
     95                 };
     96 
     97                 boolean[] hasCustomPrinterIcons = {
     98                         true, false
     99                 };
    100 
    101                 String[] descriptions = {
    102                         "Description", "", null
    103                 };
    104 
    105                 PendingIntent[] infoIntents = {
    106                         PendingIntent.getActivity(getActivity(), 0,
    107                                 new Intent(getActivity(), Activity.class),
    108                                 PendingIntent.FLAG_IMMUTABLE),
    109                         null
    110                 };
    111 
    112                 PrinterCapabilitiesInfo[] capabilityList = {
    113                         // The printerId not used in PrinterCapabilitiesInfo
    114                         new PrinterCapabilitiesInfo.Builder(sDiscoverySession.getService()
    115                                 .generatePrinterId("unused"))
    116                                         .setMinMargins(new Margins(200, 200, 200, 200))
    117                                         .addMediaSize(MediaSize.ISO_A4, true)
    118                                         .addResolution(
    119                                                 new Resolution("300x300", "300x300", 300, 300),
    120                                                 true)
    121                                         .setColorModes(PrintAttributes.COLOR_MODE_COLOR,
    122                                                 PrintAttributes.COLOR_MODE_COLOR)
    123                                         .build(),
    124                         null
    125                 };
    126 
    127                 List<PrinterInfo> printers = new ArrayList<>();
    128                 for (String localPrinterId : localPrinterIds) {
    129                     for (String name : names) {
    130                         for (int status : statusList) {
    131                             for (int iconResourceId : iconResourceIds) {
    132                                 for (boolean hasCustomPrinterIcon : hasCustomPrinterIcons) {
    133                                     for (String description : descriptions) {
    134                                         for (PendingIntent infoIntent : infoIntents) {
    135                                             for (PrinterCapabilitiesInfo capabilities
    136                                                     : capabilityList) {
    137                                                 // printerId
    138                                                 RuntimeException e = null;
    139                                                 PrinterId printerId = null;
    140                                                 try {
    141                                                     if (localPrinterId == null) {
    142                                                         printerId = sDiscoverySession
    143                                                                 .getService()
    144                                                                 .generatePrinterId(
    145                                                                         localPrinterId);
    146                                                     } else {
    147                                                         printerId = sDiscoverySession
    148                                                                 .getService()
    149                                                                 .generatePrinterId(
    150                                                                         localPrinterId
    151                                                                                 + printers
    152                                                                                         .size());
    153                                                     }
    154                                                 } catch (RuntimeException ex) {
    155                                                     e = ex;
    156                                                 }
    157 
    158                                                 // Expect exception if localId is null
    159                                                 if (localPrinterId == null) {
    160                                                     if (e == null) {
    161                                                         throw new IllegalStateException();
    162                                                     }
    163                                                 } else if (e != null) {
    164                                                     throw e;
    165                                                 }
    166 
    167                                                 // Constructor
    168                                                 PrinterInfo.Builder b = null;
    169                                                 e = null;
    170                                                 try {
    171                                                     b = new PrinterInfo.Builder(
    172                                                             printerId, name, status);
    173                                                 } catch (RuntimeException ex) {
    174                                                     e = ex;
    175                                                 }
    176 
    177                                                 // Expect exception if any of the parameters was
    178                                                 // bad
    179                                                 if (printerId == null
    180                                                         || TextUtils.isEmpty(name)
    181                                                         || !isValidStatus(status)) {
    182                                                     if (e == null) {
    183                                                         throw new IllegalStateException();
    184                                                     } else {
    185                                                         b = badPrinter;
    186                                                     }
    187                                                 } else if (e != null) {
    188                                                     throw e;
    189                                                 }
    190 
    191                                                 // IconResourceId
    192                                                 e = null;
    193                                                 try {
    194                                                     b.setIconResourceId(iconResourceId);
    195                                                 } catch (RuntimeException ex) {
    196                                                     e = ex;
    197                                                 }
    198 
    199                                                 // Expect exception if iconResourceId was bad
    200                                                 // We do allow invalid Ids as the printerInfo
    201                                                 // might be created after the package of the
    202                                                 // printer is already gone if the printer is a
    203                                                 // historical printer.
    204                                                 if (iconResourceId < 0) {
    205                                                     if (e == null) {
    206                                                         throw new IllegalStateException();
    207                                                     } else {
    208                                                         b = badPrinter;
    209                                                     }
    210                                                 } else if (e != null) {
    211                                                     throw e;
    212                                                 }
    213 
    214                                                 // Status
    215                                                 e = null;
    216                                                 try {
    217                                                     b.setStatus(status);
    218                                                 } catch (RuntimeException ex) {
    219                                                     e = ex;
    220                                                 }
    221 
    222                                                 // Expect exception is status is not valid
    223                                                 if (!isValidStatus(status)) {
    224                                                     if (e == null) {
    225                                                         throw new IllegalStateException();
    226                                                     } else {
    227                                                         b = badPrinter;
    228                                                     }
    229                                                 } else if (e != null) {
    230                                                     throw e;
    231                                                 }
    232 
    233                                                 // Name
    234                                                 e = null;
    235                                                 try {
    236                                                     b.setName(name);
    237                                                 } catch (RuntimeException ex) {
    238                                                     e = ex;
    239                                                 }
    240 
    241                                                 // Expect exception if name is empty
    242                                                 if (TextUtils.isEmpty(name)) {
    243                                                     if (e == null) {
    244                                                         throw new IllegalStateException();
    245                                                     } else {
    246                                                         b = badPrinter;
    247                                                     }
    248                                                 } else if (e != null) {
    249                                                     throw e;
    250                                                 }
    251 
    252                                                 // hasCustomPrinterIcon
    253                                                 b.setHasCustomPrinterIcon(hasCustomPrinterIcon);
    254 
    255                                                 // Description
    256                                                 b.setDescription(description);
    257 
    258                                                 // InfoIntent
    259                                                 b.setInfoIntent(infoIntent);
    260 
    261                                                 // Capabilities
    262                                                 b.setCapabilities(capabilities);
    263 
    264                                                 PrinterInfo printer = b.build();
    265 
    266                                                 // Don't create bad printers
    267                                                 if (b == badPrinter) {
    268                                                     continue;
    269                                                 }
    270 
    271                                                 // Verify get* methods
    272                                                 if (printer.getId() != printerId
    273                                                         || printer.getName() != name
    274                                                         || printer.getStatus() != status
    275                                                         || printer
    276                                                                 .getDescription() != description
    277                                                         || printer.getCapabilities()
    278                                                                 != capabilities) {
    279                                                     throw new IllegalStateException();
    280                                                 }
    281 
    282                                                 printers.add(printer);
    283                                             }
    284                                         }
    285                                     }
    286                                 }
    287                             }
    288                         }
    289                     }
    290                 }
    291 
    292                 sDiscoverySession.addPrinters(printers);
    293             }
    294             return null;
    295         }, null, null, invocation -> null, invocation -> null, null, invocation -> {
    296             // Take a note onDestroy was called.
    297             onPrinterDiscoverySessionDestroyCalled();
    298             return null;
    299         });
    300     }
    301 
    302     /**
    303      * Create mock service callback for a session.
    304      *
    305      * @param sessionCallbacks The callbacks of the session
    306      */
    307     private PrintServiceCallbacks createFirstMockPrinterServiceCallbacks(
    308             final PrinterDiscoverySessionCallbacks sessionCallbacks) {
    309         return createMockPrintServiceCallbacks(
    310                 invocation -> sessionCallbacks,
    311                 null, null);
    312     }
    313 
    314     /**
    315      * Test that all printInfos possible can be used and that invalid printInfos throw exceptions.
    316      *
    317      * @throws Exception If anything is unexpected.
    318      */
    319     @Test
    320     public void printerInfos() throws Exception {
    321         // Create the session of the printers that we will be checking.
    322         PrinterDiscoverySessionCallbacks sessionCallbacks
    323                 = createFirstMockPrinterDiscoverySessionCallbacks();
    324 
    325         // Create the service callbacks for the first print service.
    326         PrintServiceCallbacks serviceCallbacks = createFirstMockPrinterServiceCallbacks(
    327                 sessionCallbacks);
    328 
    329         // Configure the print services.
    330         FirstPrintService.setCallbacks(serviceCallbacks);
    331 
    332         // We don't use the second service, but we have to still configure it
    333         SecondPrintService.setCallbacks(createMockPrintServiceCallbacks(null, null, null));
    334 
    335         // Create a print adapter that respects the print contract.
    336         PrintDocumentAdapter adapter = createDefaultPrintDocumentAdapter(1);
    337 
    338         // Start printing.
    339         print(adapter);
    340 
    341         // Wait for write of the first page.
    342         waitForWriteAdapterCallback(1);
    343 
    344         // Open destination spinner
    345         UiObject destinationSpinner = getUiDevice().findObject(new UiSelector().resourceId(
    346                 "com.android.printspooler:id/destination_spinner"));
    347         destinationSpinner.click();
    348 
    349         // Wait until spinner is opened
    350         getUiDevice().waitForIdle();
    351 
    352         // Exit print spooler
    353         getUiDevice().pressBack();
    354         getUiDevice().pressBack();
    355         getUiDevice().pressBack();
    356     }
    357 }
    358